diff --git a/of-save/lib/gen-src/main/java/org/projectfloodlight/openflow/protocol/ver13/OFDescStatsReplyVer13.java b/of-save/lib/gen-src/main/java/org/projectfloodlight/openflow/protocol/ver13/OFDescStatsReplyVer13.java
new file mode 100644
index 0000000..4343d37
--- /dev/null
+++ b/of-save/lib/gen-src/main/java/org/projectfloodlight/openflow/protocol/ver13/OFDescStatsReplyVer13.java
@@ -0,0 +1,621 @@
+// Copyright (c) 2008 The Board of Trustees of The Leland Stanford Junior University
+// Copyright (c) 2011, 2012 Open Networking Foundation
+// Copyright (c) 2012, 2013 Big Switch Networks, Inc.
+// This library was generated by the LoxiGen Compiler.
+// See the file LICENSE.txt which should have been included in the source distribution
+
+// Automatically generated by LOXI from template of_class.java
+// Do not modify
+
+package org.projectfloodlight.openflow.protocol.ver13;
+
+import org.projectfloodlight.openflow.protocol.*;
+import org.projectfloodlight.openflow.protocol.action.*;
+import org.projectfloodlight.openflow.protocol.actionid.*;
+import org.projectfloodlight.openflow.protocol.bsntlv.*;
+import org.projectfloodlight.openflow.protocol.errormsg.*;
+import org.projectfloodlight.openflow.protocol.meterband.*;
+import org.projectfloodlight.openflow.protocol.instruction.*;
+import org.projectfloodlight.openflow.protocol.instructionid.*;
+import org.projectfloodlight.openflow.protocol.match.*;
+import org.projectfloodlight.openflow.protocol.oxm.*;
+import org.projectfloodlight.openflow.protocol.queueprop.*;
+import org.projectfloodlight.openflow.types.*;
+import org.projectfloodlight.openflow.util.*;
+import org.projectfloodlight.openflow.exceptions.*;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import java.util.Set;
+import com.google.common.collect.ImmutableSet;
+import org.jboss.netty.buffer.ChannelBuffer;
+import com.google.common.hash.PrimitiveSink;
+import com.google.common.hash.Funnel;
+
+class OFDescStatsReplyVer13 implements OFDescStatsReply {
+    private static final Logger logger = LoggerFactory.getLogger(OFDescStatsReplyVer13.class);
+    // version: 1.3
+    final static byte WIRE_VERSION = 4;
+    final static int LENGTH = 1072;
+
+        private final static long DEFAULT_XID = 0x0L;
+        private final static Set<OFStatsReplyFlags> DEFAULT_FLAGS = ImmutableSet.<OFStatsReplyFlags>of();
+        private final static String DEFAULT_MFR_DESC = "";
+        private final static String DEFAULT_HW_DESC = "";
+        private final static String DEFAULT_SW_DESC = "";
+        private final static String DEFAULT_SERIAL_NUM = "";
+        private final static String DEFAULT_DP_DESC = "";
+
+    // OF message fields
+    private final long xid;
+    private final Set<OFStatsReplyFlags> flags;
+    private final String mfrDesc;
+    private final String hwDesc;
+    private final String swDesc;
+    private final String serialNum;
+    private final String dpDesc;
+//
+    // Immutable default instance
+    final static OFDescStatsReplyVer13 DEFAULT = new OFDescStatsReplyVer13(
+        DEFAULT_XID, DEFAULT_FLAGS, DEFAULT_MFR_DESC, DEFAULT_HW_DESC, DEFAULT_SW_DESC, DEFAULT_SERIAL_NUM, DEFAULT_DP_DESC
+    );
+
+    // package private constructor - used by readers, builders, and factory
+    OFDescStatsReplyVer13(long xid, Set<OFStatsReplyFlags> flags, String mfrDesc, String hwDesc, String swDesc, String serialNum, String dpDesc) {
+        this.xid = xid;
+        this.flags = flags;
+        this.mfrDesc = mfrDesc;
+        this.hwDesc = hwDesc;
+        this.swDesc = swDesc;
+        this.serialNum = serialNum;
+        this.dpDesc = dpDesc;
+    }
+
+    // Accessors for OF message fields
+    @Override
+    public OFVersion getVersion() {
+        return OFVersion.OF_13;
+    }
+
+    @Override
+    public OFType getType() {
+        return OFType.STATS_REPLY;
+    }
+
+    @Override
+    public long getXid() {
+        return xid;
+    }
+
+    @Override
+    public OFStatsType getStatsType() {
+        return OFStatsType.DESC;
+    }
+
+    @Override
+    public Set<OFStatsReplyFlags> getFlags() {
+        return flags;
+    }
+
+    @Override
+    public String getMfrDesc() {
+        return mfrDesc;
+    }
+
+    @Override
+    public String getHwDesc() {
+        return hwDesc;
+    }
+
+    @Override
+    public String getSwDesc() {
+        return swDesc;
+    }
+
+    @Override
+    public String getSerialNum() {
+        return serialNum;
+    }
+
+    @Override
+    public String getDpDesc() {
+        return dpDesc;
+    }
+
+
+
+    public OFDescStatsReply.Builder createBuilder() {
+        return new BuilderWithParent(this);
+    }
+
+    static class BuilderWithParent implements OFDescStatsReply.Builder {
+        final OFDescStatsReplyVer13 parentMessage;
+
+        // OF message fields
+        private boolean xidSet;
+        private long xid;
+        private boolean flagsSet;
+        private Set<OFStatsReplyFlags> flags;
+        private boolean mfrDescSet;
+        private String mfrDesc;
+        private boolean hwDescSet;
+        private String hwDesc;
+        private boolean swDescSet;
+        private String swDesc;
+        private boolean serialNumSet;
+        private String serialNum;
+        private boolean dpDescSet;
+        private String dpDesc;
+
+        BuilderWithParent(OFDescStatsReplyVer13 parentMessage) {
+            this.parentMessage = parentMessage;
+        }
+
+    @Override
+    public OFVersion getVersion() {
+        return OFVersion.OF_13;
+    }
+
+    @Override
+    public OFType getType() {
+        return OFType.STATS_REPLY;
+    }
+
+    @Override
+    public long getXid() {
+        return xid;
+    }
+
+    @Override
+    public OFDescStatsReply.Builder setXid(long xid) {
+        this.xid = xid;
+        this.xidSet = true;
+        return this;
+    }
+    @Override
+    public OFStatsType getStatsType() {
+        return OFStatsType.DESC;
+    }
+
+    @Override
+    public Set<OFStatsReplyFlags> getFlags() {
+        return flags;
+    }
+
+    @Override
+    public OFDescStatsReply.Builder setFlags(Set<OFStatsReplyFlags> flags) {
+        this.flags = flags;
+        this.flagsSet = true;
+        return this;
+    }
+    @Override
+    public String getMfrDesc() {
+        return mfrDesc;
+    }
+
+    @Override
+    public OFDescStatsReply.Builder setMfrDesc(String mfrDesc) {
+        this.mfrDesc = mfrDesc;
+        this.mfrDescSet = true;
+        return this;
+    }
+    @Override
+    public String getHwDesc() {
+        return hwDesc;
+    }
+
+    @Override
+    public OFDescStatsReply.Builder setHwDesc(String hwDesc) {
+        this.hwDesc = hwDesc;
+        this.hwDescSet = true;
+        return this;
+    }
+    @Override
+    public String getSwDesc() {
+        return swDesc;
+    }
+
+    @Override
+    public OFDescStatsReply.Builder setSwDesc(String swDesc) {
+        this.swDesc = swDesc;
+        this.swDescSet = true;
+        return this;
+    }
+    @Override
+    public String getSerialNum() {
+        return serialNum;
+    }
+
+    @Override
+    public OFDescStatsReply.Builder setSerialNum(String serialNum) {
+        this.serialNum = serialNum;
+        this.serialNumSet = true;
+        return this;
+    }
+    @Override
+    public String getDpDesc() {
+        return dpDesc;
+    }
+
+    @Override
+    public OFDescStatsReply.Builder setDpDesc(String dpDesc) {
+        this.dpDesc = dpDesc;
+        this.dpDescSet = true;
+        return this;
+    }
+
+
+        @Override
+        public OFDescStatsReply build() {
+                long xid = this.xidSet ? this.xid : parentMessage.xid;
+                Set<OFStatsReplyFlags> flags = this.flagsSet ? this.flags : parentMessage.flags;
+                if(flags == null)
+                    throw new NullPointerException("Property flags must not be null");
+                String mfrDesc = this.mfrDescSet ? this.mfrDesc : parentMessage.mfrDesc;
+                if(mfrDesc == null)
+                    throw new NullPointerException("Property mfrDesc must not be null");
+                String hwDesc = this.hwDescSet ? this.hwDesc : parentMessage.hwDesc;
+                if(hwDesc == null)
+                    throw new NullPointerException("Property hwDesc must not be null");
+                String swDesc = this.swDescSet ? this.swDesc : parentMessage.swDesc;
+                if(swDesc == null)
+                    throw new NullPointerException("Property swDesc must not be null");
+                String serialNum = this.serialNumSet ? this.serialNum : parentMessage.serialNum;
+                if(serialNum == null)
+                    throw new NullPointerException("Property serialNum must not be null");
+                String dpDesc = this.dpDescSet ? this.dpDesc : parentMessage.dpDesc;
+                if(dpDesc == null)
+                    throw new NullPointerException("Property dpDesc must not be null");
+
+                //
+                return new OFDescStatsReplyVer13(
+                    xid,
+                    flags,
+                    mfrDesc,
+                    hwDesc,
+                    swDesc,
+                    serialNum,
+                    dpDesc
+                );
+        }
+
+    }
+
+    static class Builder implements OFDescStatsReply.Builder {
+        // OF message fields
+        private boolean xidSet;
+        private long xid;
+        private boolean flagsSet;
+        private Set<OFStatsReplyFlags> flags;
+        private boolean mfrDescSet;
+        private String mfrDesc;
+        private boolean hwDescSet;
+        private String hwDesc;
+        private boolean swDescSet;
+        private String swDesc;
+        private boolean serialNumSet;
+        private String serialNum;
+        private boolean dpDescSet;
+        private String dpDesc;
+
+    @Override
+    public OFVersion getVersion() {
+        return OFVersion.OF_13;
+    }
+
+    @Override
+    public OFType getType() {
+        return OFType.STATS_REPLY;
+    }
+
+    @Override
+    public long getXid() {
+        return xid;
+    }
+
+    @Override
+    public OFDescStatsReply.Builder setXid(long xid) {
+        this.xid = xid;
+        this.xidSet = true;
+        return this;
+    }
+    @Override
+    public OFStatsType getStatsType() {
+        return OFStatsType.DESC;
+    }
+
+    @Override
+    public Set<OFStatsReplyFlags> getFlags() {
+        return flags;
+    }
+
+    @Override
+    public OFDescStatsReply.Builder setFlags(Set<OFStatsReplyFlags> flags) {
+        this.flags = flags;
+        this.flagsSet = true;
+        return this;
+    }
+    @Override
+    public String getMfrDesc() {
+        return mfrDesc;
+    }
+
+    @Override
+    public OFDescStatsReply.Builder setMfrDesc(String mfrDesc) {
+        this.mfrDesc = mfrDesc;
+        this.mfrDescSet = true;
+        return this;
+    }
+    @Override
+    public String getHwDesc() {
+        return hwDesc;
+    }
+
+    @Override
+    public OFDescStatsReply.Builder setHwDesc(String hwDesc) {
+        this.hwDesc = hwDesc;
+        this.hwDescSet = true;
+        return this;
+    }
+    @Override
+    public String getSwDesc() {
+        return swDesc;
+    }
+
+    @Override
+    public OFDescStatsReply.Builder setSwDesc(String swDesc) {
+        this.swDesc = swDesc;
+        this.swDescSet = true;
+        return this;
+    }
+    @Override
+    public String getSerialNum() {
+        return serialNum;
+    }
+
+    @Override
+    public OFDescStatsReply.Builder setSerialNum(String serialNum) {
+        this.serialNum = serialNum;
+        this.serialNumSet = true;
+        return this;
+    }
+    @Override
+    public String getDpDesc() {
+        return dpDesc;
+    }
+
+    @Override
+    public OFDescStatsReply.Builder setDpDesc(String dpDesc) {
+        this.dpDesc = dpDesc;
+        this.dpDescSet = true;
+        return this;
+    }
+//
+        @Override
+        public OFDescStatsReply build() {
+            long xid = this.xidSet ? this.xid : DEFAULT_XID;
+            Set<OFStatsReplyFlags> flags = this.flagsSet ? this.flags : DEFAULT_FLAGS;
+            if(flags == null)
+                throw new NullPointerException("Property flags must not be null");
+            String mfrDesc = this.mfrDescSet ? this.mfrDesc : DEFAULT_MFR_DESC;
+            if(mfrDesc == null)
+                throw new NullPointerException("Property mfrDesc must not be null");
+            String hwDesc = this.hwDescSet ? this.hwDesc : DEFAULT_HW_DESC;
+            if(hwDesc == null)
+                throw new NullPointerException("Property hwDesc must not be null");
+            String swDesc = this.swDescSet ? this.swDesc : DEFAULT_SW_DESC;
+            if(swDesc == null)
+                throw new NullPointerException("Property swDesc must not be null");
+            String serialNum = this.serialNumSet ? this.serialNum : DEFAULT_SERIAL_NUM;
+            if(serialNum == null)
+                throw new NullPointerException("Property serialNum must not be null");
+            String dpDesc = this.dpDescSet ? this.dpDesc : DEFAULT_DP_DESC;
+            if(dpDesc == null)
+                throw new NullPointerException("Property dpDesc must not be null");
+
+
+            return new OFDescStatsReplyVer13(
+                    xid,
+                    flags,
+                    mfrDesc,
+                    hwDesc,
+                    swDesc,
+                    serialNum,
+                    dpDesc
+                );
+        }
+
+    }
+
+
+    final static Reader READER = new Reader();
+    static class Reader implements OFMessageReader<OFDescStatsReply> {
+        @Override
+        public OFDescStatsReply readFrom(ChannelBuffer bb) throws OFParseError {
+            int start = bb.readerIndex();
+            // fixed value property version == 4
+            byte version = bb.readByte();
+            if(version != (byte) 0x4)
+                throw new OFParseError("Wrong version: Expected=OFVersion.OF_13(4), got="+version);
+            // fixed value property type == 19
+            byte type = bb.readByte();
+            if(type != (byte) 0x13)
+                throw new OFParseError("Wrong type: Expected=OFType.STATS_REPLY(19), got="+type);
+            int length = U16.f(bb.readShort());
+            if(length != 1072)
+                throw new OFParseError("Wrong length: Expected=1072(1072), got="+length);
+            if(bb.readableBytes() + (bb.readerIndex() - start) < length) {
+                // Buffer does not have all data yet
+                bb.readerIndex(start);
+                return null;
+            }
+            if(logger.isTraceEnabled())
+                logger.trace("readFrom - length={}", length);
+            long xid = U32.f(bb.readInt());
+            // fixed value property statsType == 0
+            short statsType = bb.readShort();
+            if(statsType != (short) 0x0)
+                throw new OFParseError("Wrong statsType: Expected=OFStatsType.DESC(0), got="+statsType);
+            Set<OFStatsReplyFlags> flags = OFStatsReplyFlagsSerializerVer13.readFrom(bb);
+            // pad: 4 bytes
+            bb.skipBytes(4);
+            String mfrDesc = ChannelUtils.readFixedLengthString(bb, 256);
+            String hwDesc = ChannelUtils.readFixedLengthString(bb, 256);
+            String swDesc = ChannelUtils.readFixedLengthString(bb, 256);
+            String serialNum = ChannelUtils.readFixedLengthString(bb, 32);
+            String dpDesc = ChannelUtils.readFixedLengthString(bb, 256);
+
+            OFDescStatsReplyVer13 descStatsReplyVer13 = new OFDescStatsReplyVer13(
+                    xid,
+                      flags,
+                      mfrDesc,
+                      hwDesc,
+                      swDesc,
+                      serialNum,
+                      dpDesc
+                    );
+            if(logger.isTraceEnabled())
+                logger.trace("readFrom - read={}", descStatsReplyVer13);
+            return descStatsReplyVer13;
+        }
+    }
+
+    public void putTo(PrimitiveSink sink) {
+        FUNNEL.funnel(this, sink);
+    }
+
+    final static OFDescStatsReplyVer13Funnel FUNNEL = new OFDescStatsReplyVer13Funnel();
+    static class OFDescStatsReplyVer13Funnel implements Funnel<OFDescStatsReplyVer13> {
+        private static final long serialVersionUID = 1L;
+        @Override
+        public void funnel(OFDescStatsReplyVer13 message, PrimitiveSink sink) {
+            // fixed value property version = 4
+            sink.putByte((byte) 0x4);
+            // fixed value property type = 19
+            sink.putByte((byte) 0x13);
+            // fixed value property length = 1072
+            sink.putShort((short) 0x430);
+            sink.putLong(message.xid);
+            // fixed value property statsType = 0
+            sink.putShort((short) 0x0);
+            OFStatsReplyFlagsSerializerVer13.putTo(message.flags, sink);
+            // skip pad (4 bytes)
+            sink.putUnencodedChars(message.mfrDesc);
+            sink.putUnencodedChars(message.hwDesc);
+            sink.putUnencodedChars(message.swDesc);
+            sink.putUnencodedChars(message.serialNum);
+            sink.putUnencodedChars(message.dpDesc);
+        }
+    }
+
+
+    public void writeTo(ChannelBuffer bb) {
+        WRITER.write(bb, this);
+    }
+
+    final static Writer WRITER = new Writer();
+    static class Writer implements OFMessageWriter<OFDescStatsReplyVer13> {
+        @Override
+        public void write(ChannelBuffer bb, OFDescStatsReplyVer13 message) {
+            // fixed value property version = 4
+            bb.writeByte((byte) 0x4);
+            // fixed value property type = 19
+            bb.writeByte((byte) 0x13);
+            // fixed value property length = 1072
+            bb.writeShort((short) 0x430);
+            bb.writeInt(U32.t(message.xid));
+            // fixed value property statsType = 0
+            bb.writeShort((short) 0x0);
+            OFStatsReplyFlagsSerializerVer13.writeTo(bb, message.flags);
+            // pad: 4 bytes
+            bb.writeZero(4);
+            ChannelUtils.writeFixedLengthString(bb, message.mfrDesc, 256);
+            ChannelUtils.writeFixedLengthString(bb, message.hwDesc, 256);
+            ChannelUtils.writeFixedLengthString(bb, message.swDesc, 256);
+            ChannelUtils.writeFixedLengthString(bb, message.serialNum, 32);
+            ChannelUtils.writeFixedLengthString(bb, message.dpDesc, 256);
+
+
+        }
+    }
+
+    @Override
+    public String toString() {
+        StringBuilder b = new StringBuilder("OFDescStatsReplyVer13(");
+        b.append("xid=").append(xid);
+        b.append(", ");
+        b.append("flags=").append(flags);
+        b.append(", ");
+        b.append("mfrDesc=").append(mfrDesc);
+        b.append(", ");
+        b.append("hwDesc=").append(hwDesc);
+        b.append(", ");
+        b.append("swDesc=").append(swDesc);
+        b.append(", ");
+        b.append("serialNum=").append(serialNum);
+        b.append(", ");
+        b.append("dpDesc=").append(dpDesc);
+        b.append(")");
+        return b.toString();
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj)
+            return true;
+        if (obj == null)
+            return false;
+        if (getClass() != obj.getClass())
+            return false;
+        OFDescStatsReplyVer13 other = (OFDescStatsReplyVer13) obj;
+
+        if( xid != other.xid)
+            return false;
+        if (flags == null) {
+            if (other.flags != null)
+                return false;
+        } else if (!flags.equals(other.flags))
+            return false;
+        if (mfrDesc == null) {
+            if (other.mfrDesc != null)
+                return false;
+        } else if (!mfrDesc.equals(other.mfrDesc))
+            return false;
+        if (hwDesc == null) {
+            if (other.hwDesc != null)
+                return false;
+        } else if (!hwDesc.equals(other.hwDesc))
+            return false;
+        if (swDesc == null) {
+            if (other.swDesc != null)
+                return false;
+        } else if (!swDesc.equals(other.swDesc))
+            return false;
+        if (serialNum == null) {
+            if (other.serialNum != null)
+                return false;
+        } else if (!serialNum.equals(other.serialNum))
+            return false;
+        if (dpDesc == null) {
+            if (other.dpDesc != null)
+                return false;
+        } else if (!dpDesc.equals(other.dpDesc))
+            return false;
+        return true;
+    }
+
+    @Override
+    public int hashCode() {
+        final int prime = 31;
+        int result = 1;
+
+        result = prime *  (int) (xid ^ (xid >>> 32));
+        result = prime * result + ((flags == null) ? 0 : flags.hashCode());
+        result = prime * result + ((mfrDesc == null) ? 0 : mfrDesc.hashCode());
+        result = prime * result + ((hwDesc == null) ? 0 : hwDesc.hashCode());
+        result = prime * result + ((swDesc == null) ? 0 : swDesc.hashCode());
+        result = prime * result + ((serialNum == null) ? 0 : serialNum.hashCode());
+        result = prime * result + ((dpDesc == null) ? 0 : dpDesc.hashCode());
+        return result;
+    }
+
+}
