Fix findbugs violations in openflowjava
[openflowplugin.git] / openflowjava / openflow-protocol-impl / src / main / java / org / opendaylight / openflowjava / protocol / impl / deserialization / factories / MultipartRequestInputMessageFactory.java
1 /*
2  * Copyright (c) 2015 NetIDE Consortium and others.  All rights reserved.
3  *
4  * This program and the accompanying materials are made available under the
5  * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6  * and is available at http://www.eclipse.org/legal/epl-v10.html
7  */
8 package org.opendaylight.openflowjava.protocol.impl.deserialization.factories;
9
10 import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;
11 import io.netty.buffer.ByteBuf;
12 import java.math.BigInteger;
13 import java.util.ArrayList;
14 import java.util.List;
15 import java.util.Objects;
16 import org.opendaylight.openflowjava.protocol.api.extensibility.DeserializerRegistry;
17 import org.opendaylight.openflowjava.protocol.api.extensibility.DeserializerRegistryInjector;
18 import org.opendaylight.openflowjava.protocol.api.extensibility.OFDeserializer;
19 import org.opendaylight.openflowjava.protocol.api.keys.MessageCodeKey;
20 import org.opendaylight.openflowjava.protocol.api.util.EncodeConstants;
21 import org.opendaylight.openflowjava.protocol.impl.util.CodeKeyMaker;
22 import org.opendaylight.openflowjava.protocol.impl.util.CodeKeyMakerFactory;
23 import org.opendaylight.openflowjava.protocol.impl.util.ListDeserializer;
24 import org.opendaylight.openflowjava.util.ByteBufUtils;
25 import org.opendaylight.openflowjava.util.ExperimenterDeserializerKeyFactory;
26 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225.ActionRelatedTableFeatureProperty;
27 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225.ActionRelatedTableFeaturePropertyBuilder;
28 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225.InstructionRelatedTableFeatureProperty;
29 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225.InstructionRelatedTableFeaturePropertyBuilder;
30 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225.NextTableRelatedTableFeatureProperty;
31 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225.NextTableRelatedTableFeaturePropertyBuilder;
32 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225.OxmRelatedTableFeatureProperty;
33 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225.OxmRelatedTableFeaturePropertyBuilder;
34 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225.table.features.properties.container.table.feature.properties.NextTableIds;
35 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225.table.features.properties.container.table.feature.properties.NextTableIdsBuilder;
36 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.action.rev150203.actions.grouping.Action;
37 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.instruction.rev130731.instructions.grouping.Instruction;
38 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.GroupId;
39 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.MeterId;
40 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.MultipartRequestFlags;
41 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.MultipartType;
42 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.TableConfig;
43 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.TableFeaturesPropType;
44 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev150225.match.entries.grouping.MatchEntry;
45 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev150225.match.grouping.Match;
46 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.MultipartRequestInput;
47 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.MultipartRequestInputBuilder;
48 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestAggregateCase;
49 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestAggregateCaseBuilder;
50 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestDescCase;
51 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestDescCaseBuilder;
52 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestExperimenterCase;
53 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestExperimenterCaseBuilder;
54 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestFlowCase;
55 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestFlowCaseBuilder;
56 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestGroupCase;
57 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestGroupCaseBuilder;
58 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestGroupDescCase;
59 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestGroupDescCaseBuilder;
60 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestGroupFeaturesCase;
61 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestGroupFeaturesCaseBuilder;
62 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestMeterCase;
63 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestMeterCaseBuilder;
64 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestMeterConfigCase;
65 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestMeterConfigCaseBuilder;
66 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestMeterFeaturesCase;
67 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestMeterFeaturesCaseBuilder;
68 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestPortDescCase;
69 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestPortDescCaseBuilder;
70 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestPortStatsCase;
71 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestPortStatsCaseBuilder;
72 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestQueueCase;
73 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestQueueCaseBuilder;
74 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestTableCase;
75 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestTableCaseBuilder;
76 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestTableFeaturesCase;
77 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.MultipartRequestTableFeaturesCaseBuilder;
78 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.multipart.request.aggregate._case.MultipartRequestAggregateBuilder;
79 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.multipart.request.desc._case.MultipartRequestDescBuilder;
80 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.multipart.request.experimenter._case.MultipartRequestExperimenterBuilder;
81 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.multipart.request.flow._case.MultipartRequestFlowBuilder;
82 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.multipart.request.group._case.MultipartRequestGroupBuilder;
83 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.multipart.request.group.desc._case.MultipartRequestGroupDescBuilder;
84 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.multipart.request.group.features._case.MultipartRequestGroupFeaturesBuilder;
85 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.multipart.request.meter._case.MultipartRequestMeterBuilder;
86 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.multipart.request.meter.config._case.MultipartRequestMeterConfigBuilder;
87 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.multipart.request.meter.features._case.MultipartRequestMeterFeaturesBuilder;
88 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.multipart.request.port.desc._case.MultipartRequestPortDescBuilder;
89 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.multipart.request.port.stats._case.MultipartRequestPortStatsBuilder;
90 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.multipart.request.queue._case.MultipartRequestQueueBuilder;
91 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.multipart.request.table._case.MultipartRequestTableBuilder;
92 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.multipart.request.table.features._case.MultipartRequestTableFeaturesBuilder;
93 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.multipart.request.table.features._case.multipart.request.table.features.TableFeatures;
94 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.request.multipart.request.body.multipart.request.table.features._case.multipart.request.table.features.TableFeaturesBuilder;
95 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.table.features.properties.grouping.TableFeatureProperties;
96 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.table.features.properties.grouping.TableFeaturePropertiesBuilder;
97
98 /**
99  * Translates MultipartRequestInput messages.
100  *
101  * @author giuseppex.petralia@intel.com
102  */
103 @SuppressFBWarnings("UWF_FIELD_NOT_INITIALIZED_IN_CONSTRUCTOR") // FB doesn't recognize Objects.requireNonNull
104 public class MultipartRequestInputMessageFactory
105         implements OFDeserializer<MultipartRequestInput>, DeserializerRegistryInjector {
106     private static final byte PADDING = 4;
107     private static final byte FLOW_PADDING_1 = 3;
108     private static final byte FLOW_PADDING_2 = 4;
109     private static final byte AGGREGATE_PADDING_1 = 3;
110     private static final byte AGGREGATE_PADDING_2 = 4;
111     private static final byte PADDING_IN_MULTIPART_REQUEST_TABLE_FEATURES = 5;
112     private static final byte MAX_TABLE_NAME_LENGTH = 32;
113     private static final byte MULTIPART_REQUEST_TABLE_FEATURES_STRUCTURE_LENGTH = 64;
114     private static final byte COMMON_PROPERTY_LENGTH = 4;
115
116     private DeserializerRegistry registry;
117
118     @Override
119     public void injectDeserializerRegistry(DeserializerRegistry deserializerRegistry) {
120         registry = deserializerRegistry;
121     }
122
123     @Override
124     public MultipartRequestInput deserialize(ByteBuf rawMessage) {
125         Objects.requireNonNull(registry);
126
127         MultipartRequestInputBuilder builder = new MultipartRequestInputBuilder();
128         builder.setVersion((short) EncodeConstants.OF13_VERSION_ID);
129         builder.setXid(rawMessage.readUnsignedInt());
130         int type = rawMessage.readUnsignedShort();
131         builder.setType(getMultipartType(type));
132         builder.setFlags(getMultipartRequestFlags(rawMessage.readUnsignedShort()));
133         rawMessage.skipBytes(PADDING);
134         switch (MultipartType.forValue(type)) {
135             case OFPMPDESC:
136                 builder.setMultipartRequestBody(setDesc(rawMessage));
137                 break;
138             case OFPMPFLOW:
139                 builder.setMultipartRequestBody(setFlow(rawMessage));
140                 break;
141             case OFPMPAGGREGATE:
142                 builder.setMultipartRequestBody(setAggregate(rawMessage));
143                 break;
144             case OFPMPTABLE:
145                 builder.setMultipartRequestBody(setTable(rawMessage));
146                 break;
147             case OFPMPTABLEFEATURES:
148                 builder.setMultipartRequestBody(setTableFeatures(rawMessage));
149                 break;
150             case OFPMPPORTSTATS:
151                 builder.setMultipartRequestBody(setPortStats(rawMessage));
152                 break;
153             case OFPMPPORTDESC:
154                 builder.setMultipartRequestBody(setPortDesc(rawMessage));
155                 break;
156             case OFPMPQUEUE:
157                 builder.setMultipartRequestBody(setQueue(rawMessage));
158                 break;
159             case OFPMPGROUP:
160                 builder.setMultipartRequestBody(setGroup(rawMessage));
161                 break;
162             case OFPMPGROUPDESC:
163                 builder.setMultipartRequestBody(setGroupDesc(rawMessage));
164                 break;
165             case OFPMPGROUPFEATURES:
166                 builder.setMultipartRequestBody(setGroupFeatures(rawMessage));
167                 break;
168             case OFPMPMETER:
169                 builder.setMultipartRequestBody(setMeter(rawMessage));
170                 break;
171             case OFPMPMETERCONFIG:
172                 builder.setMultipartRequestBody(setMeterConfig(rawMessage));
173                 break;
174             case OFPMPMETERFEATURES:
175                 builder.setMultipartRequestBody(setMeterFeatures(rawMessage));
176                 break;
177             case OFPMPEXPERIMENTER:
178                 builder.setMultipartRequestBody(setExperimenter(rawMessage));
179                 break;
180             default:
181                 break;
182         }
183
184         return builder.build();
185     }
186
187     private static MultipartType getMultipartType(int input) {
188         return MultipartType.forValue(input);
189     }
190
191     @SuppressWarnings("checkstyle:AbbreviationAsWordInName")
192     private static MultipartRequestFlags getMultipartRequestFlags(int input) {
193         final Boolean _oFPMPFREQMORE = (input & 1 << 0) != 0;
194         MultipartRequestFlags flag = new MultipartRequestFlags(_oFPMPFREQMORE);
195         return flag;
196     }
197
198     private MultipartRequestTableFeaturesCase setTableFeatures(ByteBuf input) {
199         MultipartRequestTableFeaturesCaseBuilder caseBuilder = new MultipartRequestTableFeaturesCaseBuilder();
200         MultipartRequestTableFeaturesBuilder tableFeaturesBuilder = new MultipartRequestTableFeaturesBuilder();
201         List<TableFeatures> features = new ArrayList<>();
202         while (input.readableBytes() > 0) {
203             TableFeaturesBuilder featuresBuilder = new TableFeaturesBuilder();
204             final int length = input.readUnsignedShort();
205             featuresBuilder.setTableId(input.readUnsignedByte());
206             input.skipBytes(PADDING_IN_MULTIPART_REQUEST_TABLE_FEATURES);
207             featuresBuilder.setName(ByteBufUtils.decodeNullTerminatedString(input, MAX_TABLE_NAME_LENGTH));
208             byte[] metadataMatch = new byte[EncodeConstants.SIZE_OF_LONG_IN_BYTES];
209             input.readBytes(metadataMatch);
210             featuresBuilder.setMetadataMatch(new BigInteger(1, metadataMatch));
211             byte[] metadataWrite = new byte[EncodeConstants.SIZE_OF_LONG_IN_BYTES];
212             input.readBytes(metadataWrite);
213             featuresBuilder.setMetadataWrite(new BigInteger(1, metadataWrite));
214             featuresBuilder.setConfig(createTableConfig(input.readUnsignedInt()));
215             featuresBuilder.setMaxEntries(input.readUnsignedInt());
216             featuresBuilder.setTableFeatureProperties(
217                     createTableFeaturesProperties(input, length - MULTIPART_REQUEST_TABLE_FEATURES_STRUCTURE_LENGTH));
218             features.add(featuresBuilder.build());
219         }
220         tableFeaturesBuilder.setTableFeatures(features);
221         caseBuilder.setMultipartRequestTableFeatures(tableFeaturesBuilder.build());
222         return caseBuilder.build();
223     }
224
225     private List<TableFeatureProperties> createTableFeaturesProperties(ByteBuf input, int length) {
226         List<TableFeatureProperties> properties = new ArrayList<>();
227         int tableFeaturesLength = length;
228         while (tableFeaturesLength > 0) {
229             int propStartIndex = input.readerIndex();
230             TableFeaturePropertiesBuilder builder = new TableFeaturePropertiesBuilder();
231             TableFeaturesPropType type = TableFeaturesPropType.forValue(input.readUnsignedShort());
232             builder.setType(type);
233             int propertyLength = input.readUnsignedShort();
234             int paddingRemainder = propertyLength % EncodeConstants.PADDING;
235             tableFeaturesLength -= propertyLength;
236             if (type.equals(TableFeaturesPropType.OFPTFPTINSTRUCTIONS)
237                     || type.equals(TableFeaturesPropType.OFPTFPTINSTRUCTIONSMISS)) {
238                 InstructionRelatedTableFeaturePropertyBuilder insBuilder =
239                         new InstructionRelatedTableFeaturePropertyBuilder();
240                 CodeKeyMaker keyMaker = CodeKeyMakerFactory.createInstructionsKeyMaker(EncodeConstants.OF13_VERSION_ID);
241                 List<Instruction> instructions = ListDeserializer.deserializeHeaders(EncodeConstants.OF13_VERSION_ID,
242                         propertyLength - COMMON_PROPERTY_LENGTH, input, keyMaker, registry);
243                 insBuilder.setInstruction(instructions);
244                 builder.addAugmentation(InstructionRelatedTableFeatureProperty.class, insBuilder.build());
245             } else if (type.equals(TableFeaturesPropType.OFPTFPTNEXTTABLES)
246                     || type.equals(TableFeaturesPropType.OFPTFPTNEXTTABLESMISS)) {
247                 propertyLength -= COMMON_PROPERTY_LENGTH;
248                 NextTableRelatedTableFeaturePropertyBuilder tableBuilder =
249                         new NextTableRelatedTableFeaturePropertyBuilder();
250                 List<NextTableIds> ids = new ArrayList<>();
251                 while (propertyLength > 0) {
252                     NextTableIdsBuilder nextTableIdsBuilder = new NextTableIdsBuilder();
253                     nextTableIdsBuilder.setTableId(input.readUnsignedByte());
254                     ids.add(nextTableIdsBuilder.build());
255                     propertyLength--;
256                 }
257                 tableBuilder.setNextTableIds(ids);
258                 builder.addAugmentation(NextTableRelatedTableFeatureProperty.class, tableBuilder.build());
259             } else if (type.equals(TableFeaturesPropType.OFPTFPTWRITEACTIONS)
260                     || type.equals(TableFeaturesPropType.OFPTFPTWRITEACTIONSMISS)
261                     || type.equals(TableFeaturesPropType.OFPTFPTAPPLYACTIONS)
262                     || type.equals(TableFeaturesPropType.OFPTFPTAPPLYACTIONSMISS)) {
263                 ActionRelatedTableFeaturePropertyBuilder actionBuilder = new ActionRelatedTableFeaturePropertyBuilder();
264                 CodeKeyMaker keyMaker = CodeKeyMakerFactory.createActionsKeyMaker(EncodeConstants.OF13_VERSION_ID);
265                 List<Action> actions = ListDeserializer.deserializeHeaders(EncodeConstants.OF13_VERSION_ID,
266                         propertyLength - COMMON_PROPERTY_LENGTH, input, keyMaker, registry);
267                 actionBuilder.setAction(actions);
268                 builder.addAugmentation(ActionRelatedTableFeatureProperty.class, actionBuilder.build());
269             } else if (type.equals(TableFeaturesPropType.OFPTFPTMATCH)
270                     || type.equals(TableFeaturesPropType.OFPTFPTWILDCARDS)
271                     || type.equals(TableFeaturesPropType.OFPTFPTWRITESETFIELD)
272                     || type.equals(TableFeaturesPropType.OFPTFPTWRITESETFIELDMISS)
273                     || type.equals(TableFeaturesPropType.OFPTFPTAPPLYSETFIELD)
274                     || type.equals(TableFeaturesPropType.OFPTFPTAPPLYSETFIELDMISS)) {
275                 OxmRelatedTableFeaturePropertyBuilder oxmBuilder = new OxmRelatedTableFeaturePropertyBuilder();
276                 CodeKeyMaker keyMaker = CodeKeyMakerFactory.createMatchEntriesKeyMaker(EncodeConstants.OF13_VERSION_ID);
277                 List<MatchEntry> entries = ListDeserializer.deserializeHeaders(EncodeConstants.OF13_VERSION_ID,
278                         propertyLength - COMMON_PROPERTY_LENGTH, input, keyMaker, registry);
279                 oxmBuilder.setMatchEntry(entries);
280                 builder.addAugmentation(OxmRelatedTableFeatureProperty.class, oxmBuilder.build());
281             } else if (type.equals(TableFeaturesPropType.OFPTFPTEXPERIMENTER)
282                     || type.equals(TableFeaturesPropType.OFPTFPTEXPERIMENTERMISS)) {
283                 long expId = input.readUnsignedInt();
284                 input.readerIndex(propStartIndex);
285                 OFDeserializer<TableFeatureProperties> propDeserializer = registry
286                         .getDeserializer(ExperimenterDeserializerKeyFactory
287                                 .createMultipartReplyTFDeserializerKey(EncodeConstants.OF13_VERSION_ID, expId));
288                 TableFeatureProperties expProp = propDeserializer.deserialize(input);
289                 properties.add(expProp);
290                 continue;
291             }
292             if (paddingRemainder != 0) {
293                 input.skipBytes(EncodeConstants.PADDING - paddingRemainder);
294                 tableFeaturesLength -= EncodeConstants.PADDING - paddingRemainder;
295             }
296             properties.add(builder.build());
297         }
298         return properties;
299     }
300
301     private static TableConfig createTableConfig(long input) {
302         boolean deprecated = (input & 3) != 0;
303         return new TableConfig(deprecated);
304     }
305
306     private MultipartRequestDescCase setDesc(ByteBuf input) {
307         MultipartRequestDescCaseBuilder caseBuilder = new MultipartRequestDescCaseBuilder();
308         MultipartRequestDescBuilder descBuilder = new MultipartRequestDescBuilder();
309         descBuilder.setEmpty(true);
310         caseBuilder.setMultipartRequestDesc(descBuilder.build());
311         return caseBuilder.build();
312     }
313
314     private MultipartRequestFlowCase setFlow(ByteBuf input) {
315         final MultipartRequestFlowCaseBuilder caseBuilder = new MultipartRequestFlowCaseBuilder();
316         MultipartRequestFlowBuilder flowBuilder = new MultipartRequestFlowBuilder();
317         flowBuilder.setTableId(input.readUnsignedByte());
318         input.skipBytes(FLOW_PADDING_1);
319         flowBuilder.setOutPort(input.readUnsignedInt());
320         flowBuilder.setOutGroup(input.readUnsignedInt());
321         input.skipBytes(FLOW_PADDING_2);
322         byte[] cookie = new byte[EncodeConstants.SIZE_OF_LONG_IN_BYTES];
323         input.readBytes(cookie);
324         flowBuilder.setCookie(new BigInteger(1, cookie));
325         final byte[] cookieMask = new byte[EncodeConstants.SIZE_OF_LONG_IN_BYTES];
326         input.readBytes(cookieMask);
327         flowBuilder.setCookieMask(new BigInteger(1, cookieMask));
328         OFDeserializer<Match> matchDeserializer = registry.getDeserializer(
329                 new MessageCodeKey(EncodeConstants.OF13_VERSION_ID, EncodeConstants.EMPTY_VALUE, Match.class));
330         flowBuilder.setMatch(matchDeserializer.deserialize(input));
331         caseBuilder.setMultipartRequestFlow(flowBuilder.build());
332         return caseBuilder.build();
333     }
334
335     private MultipartRequestAggregateCase setAggregate(ByteBuf input) {
336         final MultipartRequestAggregateCaseBuilder caseBuilder = new MultipartRequestAggregateCaseBuilder();
337         MultipartRequestAggregateBuilder aggregateBuilder = new MultipartRequestAggregateBuilder();
338         aggregateBuilder.setTableId(input.readUnsignedByte());
339         input.skipBytes(AGGREGATE_PADDING_1);
340         aggregateBuilder.setOutPort(input.readUnsignedInt());
341         aggregateBuilder.setOutGroup(input.readUnsignedInt());
342         input.skipBytes(AGGREGATE_PADDING_2);
343         byte[] cookie = new byte[EncodeConstants.SIZE_OF_LONG_IN_BYTES];
344         input.readBytes(cookie);
345         aggregateBuilder.setCookie(new BigInteger(1, cookie));
346         final byte[] cookieMask = new byte[EncodeConstants.SIZE_OF_LONG_IN_BYTES];
347         input.readBytes(cookieMask);
348         aggregateBuilder.setCookieMask(new BigInteger(1, cookieMask));
349         OFDeserializer<Match> matchDeserializer = registry.getDeserializer(
350                 new MessageCodeKey(EncodeConstants.OF13_VERSION_ID, EncodeConstants.EMPTY_VALUE, Match.class));
351         aggregateBuilder.setMatch(matchDeserializer.deserialize(input));
352         caseBuilder.setMultipartRequestAggregate(aggregateBuilder.build());
353         return caseBuilder.build();
354     }
355
356     private MultipartRequestPortDescCase setPortDesc(ByteBuf input) {
357         MultipartRequestPortDescCaseBuilder caseBuilder = new MultipartRequestPortDescCaseBuilder();
358         MultipartRequestPortDescBuilder portBuilder = new MultipartRequestPortDescBuilder();
359         portBuilder.setEmpty(true);
360         caseBuilder.setMultipartRequestPortDesc(portBuilder.build());
361         return caseBuilder.build();
362     }
363
364     private MultipartRequestPortStatsCase setPortStats(ByteBuf input) {
365         MultipartRequestPortStatsCaseBuilder caseBuilder = new MultipartRequestPortStatsCaseBuilder();
366         MultipartRequestPortStatsBuilder portBuilder = new MultipartRequestPortStatsBuilder();
367         portBuilder.setPortNo(input.readUnsignedInt());
368         caseBuilder.setMultipartRequestPortStats(portBuilder.build());
369         return caseBuilder.build();
370     }
371
372     private MultipartRequestQueueCase setQueue(ByteBuf input) {
373         MultipartRequestQueueCaseBuilder caseBuilder = new MultipartRequestQueueCaseBuilder();
374         MultipartRequestQueueBuilder queueBuilder = new MultipartRequestQueueBuilder();
375         queueBuilder.setPortNo(input.readUnsignedInt());
376         queueBuilder.setQueueId(input.readUnsignedInt());
377         caseBuilder.setMultipartRequestQueue(queueBuilder.build());
378         return caseBuilder.build();
379     }
380
381     private MultipartRequestGroupCase setGroup(ByteBuf input) {
382         MultipartRequestGroupCaseBuilder caseBuilder = new MultipartRequestGroupCaseBuilder();
383         MultipartRequestGroupBuilder groupBuilder = new MultipartRequestGroupBuilder();
384         groupBuilder.setGroupId(new GroupId(input.readUnsignedInt()));
385         caseBuilder.setMultipartRequestGroup(groupBuilder.build());
386         return caseBuilder.build();
387     }
388
389     private MultipartRequestGroupDescCase setGroupDesc(ByteBuf input) {
390         MultipartRequestGroupDescCaseBuilder caseBuilder = new MultipartRequestGroupDescCaseBuilder();
391         MultipartRequestGroupDescBuilder groupBuilder = new MultipartRequestGroupDescBuilder();
392         groupBuilder.setEmpty(true);
393         caseBuilder.setMultipartRequestGroupDesc(groupBuilder.build());
394         return caseBuilder.build();
395     }
396
397     private MultipartRequestGroupFeaturesCase setGroupFeatures(ByteBuf input) {
398         MultipartRequestGroupFeaturesCaseBuilder caseBuilder = new MultipartRequestGroupFeaturesCaseBuilder();
399         MultipartRequestGroupFeaturesBuilder groupBuilder = new MultipartRequestGroupFeaturesBuilder();
400         groupBuilder.setEmpty(true);
401         caseBuilder.setMultipartRequestGroupFeatures(groupBuilder.build());
402         return caseBuilder.build();
403     }
404
405     private MultipartRequestMeterCase setMeter(ByteBuf input) {
406         MultipartRequestMeterCaseBuilder caseBuilder = new MultipartRequestMeterCaseBuilder();
407         MultipartRequestMeterBuilder meterBuilder = new MultipartRequestMeterBuilder();
408         meterBuilder.setMeterId(new MeterId(input.readUnsignedInt()));
409         caseBuilder.setMultipartRequestMeter(meterBuilder.build());
410         return caseBuilder.build();
411     }
412
413     private MultipartRequestMeterConfigCase setMeterConfig(ByteBuf input) {
414         MultipartRequestMeterConfigCaseBuilder caseBuilder = new MultipartRequestMeterConfigCaseBuilder();
415         MultipartRequestMeterConfigBuilder meterBuilder = new MultipartRequestMeterConfigBuilder();
416         meterBuilder.setMeterId(new MeterId(input.readUnsignedInt()));
417         caseBuilder.setMultipartRequestMeterConfig(meterBuilder.build());
418         return caseBuilder.build();
419     }
420
421     private MultipartRequestMeterFeaturesCase setMeterFeatures(ByteBuf input) {
422         MultipartRequestMeterFeaturesCaseBuilder caseBuilder = new MultipartRequestMeterFeaturesCaseBuilder();
423         MultipartRequestMeterFeaturesBuilder meterBuilder = new MultipartRequestMeterFeaturesBuilder();
424         meterBuilder.setEmpty(true);
425         caseBuilder.setMultipartRequestMeterFeatures(meterBuilder.build());
426         return caseBuilder.build();
427     }
428
429     private MultipartRequestTableCase setTable(ByteBuf input) {
430         MultipartRequestTableCaseBuilder caseBuilder = new MultipartRequestTableCaseBuilder();
431         MultipartRequestTableBuilder tableBuilder = new MultipartRequestTableBuilder();
432         tableBuilder.setEmpty(true);
433         caseBuilder.setMultipartRequestTable(tableBuilder.build());
434         return caseBuilder.build();
435     }
436
437     private MultipartRequestExperimenterCase setExperimenter(ByteBuf input) {
438         MultipartRequestExperimenterCaseBuilder caseBuilder = new MultipartRequestExperimenterCaseBuilder();
439         MultipartRequestExperimenterBuilder experimenterBuilder = new MultipartRequestExperimenterBuilder();
440         caseBuilder.setMultipartRequestExperimenter(experimenterBuilder.build());
441         return caseBuilder.build();
442     }
443 }