X-Git-Url: https://git.opendaylight.org/gerrit/gitweb?p=controller.git;a=blobdiff_plain;f=opendaylight%2Fsal%2Fapi%2Fsrc%2Fmain%2Fjava%2Forg%2Fopendaylight%2Fcontroller%2Fsal%2Fpacket%2FIPv4.java;h=7a7a5a757fb4ab4ff7184da84a25662f42729e07;hp=e55873d6930e159d2ef3c922387ea9a4ff376a38;hb=541d0a36997f292bb037a2199463431eee538358;hpb=11837100975c9ad113e12668c09ecd78f9433f73 diff --git a/opendaylight/sal/api/src/main/java/org/opendaylight/controller/sal/packet/IPv4.java b/opendaylight/sal/api/src/main/java/org/opendaylight/controller/sal/packet/IPv4.java index e55873d693..7a7a5a757f 100644 --- a/opendaylight/sal/api/src/main/java/org/opendaylight/controller/sal/packet/IPv4.java +++ b/opendaylight/sal/api/src/main/java/org/opendaylight/controller/sal/packet/IPv4.java @@ -18,8 +18,6 @@ import java.util.LinkedHashMap; import java.util.Map; import java.util.Random; -import org.apache.commons.lang3.builder.EqualsBuilder; -import org.apache.commons.lang3.builder.HashCodeBuilder; import org.apache.commons.lang3.tuple.ImmutablePair; import org.apache.commons.lang3.tuple.Pair; import org.opendaylight.controller.sal.utils.IPProtocols; @@ -29,13 +27,11 @@ import org.slf4j.LoggerFactory; /** * Class that represents the IPv4 packet objects - * - * */ public class IPv4 extends Packet { protected static final Logger logger = LoggerFactory - .getLogger(IPv4.class); + .getLogger(IPv4.class); private static final String VERSION = "Version"; private static final String HEADERLENGTH = "HeaderLength"; private static final String DIFFSERV = "DiffServ"; @@ -51,7 +47,7 @@ public class IPv4 extends Packet { private static final String DIP = "DestinationIPAddress"; private static final String OPTIONS = "Options"; - public static Map> protocolClassMap; + public static final Map> protocolClassMap; static { protocolClassMap = new HashMap>(); protocolClassMap.put(IPProtocols.ICMP.byteValue(), ICMP.class); @@ -78,7 +74,8 @@ public class IPv4 extends Packet { } }; - private Map fieldValues; + private final Map fieldValues; + /** * Default constructor that sets the version to 4, headerLength to 5, @@ -90,14 +87,15 @@ public class IPv4 extends Packet { fieldValues = new HashMap(); hdrFieldCoordMap = fieldCoordinates; hdrFieldsMap = fieldValues; + corrupted = false; setVersion((byte) 4); setHeaderLength((byte) 5); setDiffServ((byte) 0); + setECN((byte) 0); setIdentification(generateId()); setFlags((byte) 2); setFragmentOffset((short) 0); - setECN((byte) 0); } /** @@ -112,14 +110,15 @@ public class IPv4 extends Packet { fieldValues = new HashMap(); hdrFieldCoordMap = fieldCoordinates; hdrFieldsMap = fieldValues; + corrupted = false; setVersion((byte) 4); setHeaderLength((byte) 5); setDiffServ((byte) 0); + setECN((byte) 0); setIdentification(generateId()); setFlags((byte) 2); setFragmentOffset((short) 0); - setECN((byte) 0); } /** @@ -139,21 +138,22 @@ public class IPv4 extends Packet { } /** - * Gets the header length in bits, from the header length stored and options if any - * @return HeaderLength to serialize code + * Gets the header size in bits + * @return The number of bits constituting the header */ @Override public int getHeaderSize() { int headerLen = this.getHeaderLen(); - if (headerLen == 0) + if (headerLen == 0) { headerLen = 20; + } byte[] options = hdrFieldsMap.get(OPTIONS); - if (options != null) + if (options != null) { headerLen += options.length; + } return headerLen * NetUtils.NumBitsInAByte; - } /** @@ -378,9 +378,9 @@ public class IPv4 extends Packet { * @param checksum the checksum to set */ /*public IPv4 setChecksum() { - short ipChecksum = computeChecksum(); + short ipChecksum = computeChecksum(); byte[] checksum = BitBufferHelper.toByteArray(ipChecksum); - fieldValues.put(CHECKSUM, checksum); + fieldValues.put(CHECKSUM, checksum); return this; }*/ @@ -442,27 +442,33 @@ public class IPv4 extends Packet { } /** - * Computes the header checksum - * @param byte[] hdrBytes - serialized bytes - * @param int endBitOffset - end bit Offset - * @return short - the computed checksum + * Computes the IPv4 header checksum on the passed stream of bytes + * representing the packet + * + * @param data + * The byte stream + * @param offset + * The byte offset from where the IPv4 packet starts + * @return The computed checksum */ - private short computeChecksum(byte[] hdrBytes, int endByteOffset) { - int startByteOffset = endByteOffset - getHeaderLen(); + short computeChecksum(byte[] data, int start) { + int end = start + getHeaderLen(); short checkSum = (short) 0; int sum = 0, carry = 0, finalSum = 0; int parsedHex = 0; - int checksumStartByte = startByteOffset + getfieldOffset(CHECKSUM) - / NetUtils.NumBitsInAByte; + int checksumStart = start + + (getfieldOffset(CHECKSUM) / NetUtils.NumBitsInAByte); - for (int i = startByteOffset; i <= (endByteOffset - 1); i = i + 2) { - //Skip, if the current bytes are checkSum bytes - if (i == checksumStartByte) + for (int i = start; i <= (end - 1); i = i + 2) { + // Skip, if the current bytes are checkSum bytes + if (i == checksumStart) { continue; + } StringBuffer sbuffer = new StringBuffer(); - sbuffer.append(String.format("%02X", hdrBytes[i])); - if (i < (hdrBytes.length - 1)) - sbuffer.append(String.format("%02X", hdrBytes[i + 1])); + sbuffer.append(String.format("%02X", data[i])); + if (i < (data.length - 1)) { + sbuffer.append(String.format("%02X", data[i + 1])); + } parsedHex = Integer.valueOf(sbuffer.toString(), 16); sum += parsedHex; @@ -470,17 +476,8 @@ public class IPv4 extends Packet { carry = (sum >> 16) & 0xFF; finalSum = (sum & 0xFFFF) + carry; checkSum = (short) ~((short) finalSum & 0xFFFF); - return checkSum; - } - @Override - public int hashCode() { - return HashCodeBuilder.reflectionHashCode(this); - } - - @Override - public boolean equals(Object obj) { - return EqualsBuilder.reflectionEquals(this, obj); + return checkSum; } @Override @@ -496,26 +493,37 @@ public class IPv4 extends Packet { byte[] options = getOptions(); return ((options == null) ? 0 : (options.length - getHeaderLen())); } - return (((Pair) hdrFieldCoordMap.get(fieldName)) - .getRight()); + return hdrFieldCoordMap.get(fieldName).getRight(); } @Override /** * Method to perform post serialization - like computation of checksum of serialized header - * @param serializedBytes + * @param data * @return void - * @Exception throws exception + * @Exception throws PacketException */ - protected void postSerializeCustomOperation(byte[] serializedBytes) - throws Exception { - int startOffset = this.getfieldOffset(CHECKSUM); - int numBits = this.getfieldnumBits(CHECKSUM); - byte[] checkSum = BitBufferHelper.toByteArray(computeChecksum( - serializedBytes, serializedBytes.length)); - BitBufferHelper.setBytes(serializedBytes, checkSum, startOffset, - numBits); - return; + protected void postSerializeCustomOperation(byte[] data) + throws PacketException { + + // Recompute the total length field here + byte[] totalLength = BitBufferHelper.toByteArray((short) data.length); + try { + BitBufferHelper.setBytes(data, totalLength, getfieldOffset(TOTLENGTH), + getfieldnumBits(TOTLENGTH)); + } catch (BufferException e) { + throw new PacketException(e.getMessage()); + } + + // Now compute the Header Checksum + byte[] checkSum = BitBufferHelper.toByteArray(computeChecksum(data, 0)); + + try { + BitBufferHelper.setBytes(data, checkSum, getfieldOffset(CHECKSUM), + getfieldnumBits(CHECKSUM)); + } catch (BufferException e) { + throw new PacketException(e.getMessage()); + } } @Override @@ -524,32 +532,39 @@ public class IPv4 extends Packet { * bytes in Total Length * @param payload - Packet */ + /** + * Set the total length field in the IPv4 Object + * Note: this field will get overwritten during serialization phase. + */ public void setPayload(Packet payload) { this.payload = payload; /* - * Deriving the Total Lenght here - * TODO: See if we can derive the total length during - * another phase (during serialization/deserialization) - * */ + * Deriving the Total Length here + */ int payloadLength = 0; - try { - payloadLength = payload.serialize().length; - } catch (Exception e) { - logger.error("",e); + if (payload != null) { + try { + payloadLength = payload.serialize().length; + } catch (PacketException e) { + logger.error("", e); + } } + this.setTotalLength((short) (this.getHeaderLen() + payloadLength)); } - @Override + /** * Method to perform post deserialization - like compare computed checksum with * the one obtained from IP header */ - protected void postDeserializeCustomOperation(byte[] data, int endBitOffset) { - int endByteOffset = endBitOffset / NetUtils.NumBitsInAByte; - int computedChecksum = computeChecksum(data, endByteOffset); - int actualChecksum = BitBufferHelper.getInt(fieldValues.get(CHECKSUM)); - if (computedChecksum != actualChecksum) + @Override + protected void postDeserializeCustomOperation(byte[] data, int startBitOffset) { + int start = startBitOffset / NetUtils.NumBitsInAByte; + short computedChecksum = computeChecksum(data, start); + short actualChecksum = BitBufferHelper.getShort(fieldValues.get(CHECKSUM)); + if (computedChecksum != actualChecksum) { corrupted = true; + } } }