1 /* Copyright (C)2013 Pantheon Technologies, s.r.o. All rights reserved. */
\r
2 package org.opendaylight.openflowjava.protocol.impl.serialization.factories;
\r
4 import io.netty.buffer.ByteBuf;
\r
6 import java.util.List;
\r
8 import org.opendaylight.openflowjava.protocol.impl.serialization.OFSerializer;
\r
9 import org.opendaylight.openflowjava.protocol.impl.util.ByteBufUtils;
\r
10 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.HelloElementType;
\r
11 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.HelloInput;
\r
12 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.hello.Elements;
\r
13 import org.slf4j.Logger;
\r
14 import org.slf4j.LoggerFactory;
\r
17 * @author michal.polkorab
\r
20 public class HelloInputMessageFactory implements OFSerializer<HelloInput>{
\r
22 /** Code type of Hello message */
\r
23 private static final byte MESSAGE_TYPE = 0;
\r
24 private static int MESSAGE_LENGTH = 8;
\r
25 public static final byte HELLO_ELEMENT_HEADER_SIZE = 4;
\r
26 private static HelloInputMessageFactory instance;
\r
28 private static final Logger LOGGER = LoggerFactory
\r
29 .getLogger(HelloInputMessageFactory.class);
\r
32 private HelloInputMessageFactory() {
\r
33 // do nothing, just singleton
\r
37 * @return singleton factory
\r
39 public static synchronized HelloInputMessageFactory getInstance() {
\r
40 if (instance == null) {
\r
41 instance = new HelloInputMessageFactory();
\r
47 public void messageToBuffer(short version, ByteBuf out, HelloInput message) {
\r
48 int startWriterIndex = out.writerIndex();
\r
49 ByteBufUtils.writeOFHeader(instance, message, out);
\r
50 encodeElementsList(message, out);
\r
51 int endWriterIndex = out.writerIndex();
\r
52 int writtenBytesDiff = computeLength(message) - (endWriterIndex - startWriterIndex);
\r
53 LOGGER.info("writtenbytes: " + writtenBytesDiff);
\r
54 ByteBufUtils.padBuffer(writtenBytesDiff, out);
\r
58 public int computeLength(HelloInput message) {
\r
59 int length = MESSAGE_LENGTH;
\r
60 List<Elements> elements = message.getElements();
\r
61 if (elements != null) {
\r
62 for (Elements element : elements) {
\r
63 if (HelloElementType.VERSIONBITMAP.equals(element.getType())) {
\r
64 length += computeVersionBitmapLength(element);
\r
67 int paddingRemainder = length % EncodeConstants.PADDING;
\r
68 if (paddingRemainder != 0) {
\r
69 length += EncodeConstants.PADDING - paddingRemainder;
\r
76 public byte getMessageType() {
\r
77 return MESSAGE_TYPE;
\r
80 private static void encodeElementsList(HelloInput message, ByteBuf output) {
\r
81 int[] versionBitmap;
\r
83 if (message.getElements() != null) {
\r
84 for (Elements currElement : message.getElements()) {
\r
85 output.writeShort(currElement.getType().getIntValue());
\r
87 if (currElement.getType().equals(HelloElementType.VERSIONBITMAP)) {
\r
88 short bitmapLength = computeVersionBitmapLength(currElement);
\r
89 output.writeShort(bitmapLength);
\r
90 versionBitmap = ByteBufUtils.fillBitMaskFromList(currElement.getVersionBitmap());
\r
91 arraySize = (versionBitmap.length/Integer.SIZE);
\r
92 for (int i = 0; i < arraySize; i++) {
\r
93 output.writeInt(versionBitmap[i]);
\r
95 int padding = bitmapLength - arraySize * 4 - HELLO_ELEMENT_HEADER_SIZE;
\r
96 ByteBufUtils.padBuffer(padding , output);
\r
102 private static short computeVersionBitmapLength(Elements element) {
\r
103 short elementlength = HELLO_ELEMENT_HEADER_SIZE;
\r
104 if (!element.getVersionBitmap().isEmpty()) {
\r
105 elementlength += ((element.getVersionBitmap().size() - 1) / Integer.SIZE + 1) * 4;
\r
107 return elementlength;
\r