2 * Copyright (c) 2015 NetIDE Consortium and others. All rights reserved.
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
8 package org.opendaylight.openflowjava.protocol.impl.serialization.factories;
10 import io.netty.buffer.ByteBuf;
11 import io.netty.buffer.UnpooledByteBufAllocator;
12 import java.util.HashMap;
13 import java.util.List;
15 import org.opendaylight.openflowjava.protocol.api.extensibility.OFSerializer;
16 import org.opendaylight.openflowjava.protocol.api.extensibility.SerializerRegistry;
17 import org.opendaylight.openflowjava.protocol.api.extensibility.SerializerRegistryInjector;
18 import org.opendaylight.openflowjava.protocol.api.keys.MessageTypeKey;
19 import org.opendaylight.openflowjava.protocol.api.util.EncodeConstants;
20 import org.opendaylight.openflowjava.protocol.impl.util.ListSerializer;
21 import org.opendaylight.openflowjava.protocol.impl.util.TypeKeyMaker;
22 import org.opendaylight.openflowjava.protocol.impl.util.TypeKeyMakerFactory;
23 import org.opendaylight.openflowjava.util.ByteBufUtils;
24 import org.opendaylight.openflowjava.util.ExperimenterSerializerKeyFactory;
25 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225.ActionRelatedTableFeatureProperty;
26 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225.ExperimenterIdTableFeatureProperty;
27 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225.InstructionRelatedTableFeatureProperty;
28 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225.NextTableRelatedTableFeatureProperty;
29 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225.OxmRelatedTableFeatureProperty;
30 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev150225.table.features.properties.container.table.feature.properties.NextTableIds;
31 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.action.rev150203.actions.grouping.Action;
32 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.instruction.rev130731.instructions.grouping.Instruction;
33 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.ActionType;
34 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.GroupCapabilities;
35 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.GroupTypes;
36 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.MeterBandTypeBitmap;
37 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.MeterFlags;
38 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.MultipartRequestFlags;
39 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.PortConfig;
40 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.PortFeatures;
41 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.PortState;
42 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.TableConfig;
43 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev150225.match.entries.grouping.MatchEntry;
44 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev150225.match.grouping.Match;
45 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.MeterBandCommons;
46 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.MultipartReplyMessage;
47 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.buckets.grouping.BucketsList;
48 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.meter.band.header.MeterBand;
49 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.meter.band.header.meter.band.MeterBandDropCase;
50 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.meter.band.header.meter.band.MeterBandDscpRemarkCase;
51 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.meter.band.header.meter.band.MeterBandExperimenterCase;
52 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.meter.band.header.meter.band.meter.band.drop._case.MeterBandDrop;
53 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.meter.band.header.meter.band.meter.band.dscp.remark._case.MeterBandDscpRemark;
54 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.meter.band.header.meter.band.meter.band.experimenter._case.MeterBandExperimenter;
55 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.MultipartReplyBody;
56 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.MultipartReplyAggregateCase;
57 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.MultipartReplyDescCase;
58 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.MultipartReplyExperimenterCase;
59 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.MultipartReplyFlowCase;
60 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.MultipartReplyGroupCase;
61 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.MultipartReplyGroupDescCase;
62 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.MultipartReplyGroupFeaturesCase;
63 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.MultipartReplyMeterCase;
64 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.MultipartReplyMeterConfigCase;
65 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.MultipartReplyMeterFeaturesCase;
66 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.MultipartReplyPortDescCase;
67 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.MultipartReplyPortStatsCase;
68 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.MultipartReplyQueueCase;
69 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.MultipartReplyTableCase;
70 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.MultipartReplyTableFeaturesCase;
71 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.aggregate._case.MultipartReplyAggregate;
72 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.desc._case.MultipartReplyDesc;
73 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.experimenter._case.MultipartReplyExperimenter;
74 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.flow._case.MultipartReplyFlow;
75 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.flow._case.multipart.reply.flow.FlowStats;
76 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.group._case.MultipartReplyGroup;
77 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.group._case.multipart.reply.group.GroupStats;
78 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.group._case.multipart.reply.group.group.stats.BucketStats;
79 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.group.desc._case.MultipartReplyGroupDesc;
80 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.group.desc._case.multipart.reply.group.desc.GroupDesc;
81 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.group.features._case.MultipartReplyGroupFeatures;
82 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.meter._case.MultipartReplyMeter;
83 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.meter._case.multipart.reply.meter.MeterStats;
84 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.meter._case.multipart.reply.meter.meter.stats.MeterBandStats;
85 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.meter.config._case.MultipartReplyMeterConfig;
86 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.meter.config._case.multipart.reply.meter.config.MeterConfig;
87 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.meter.config._case.multipart.reply.meter.config.meter.config.Bands;
88 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.meter.features._case.MultipartReplyMeterFeatures;
89 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.port.desc._case.MultipartReplyPortDesc;
90 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.port.desc._case.multipart.reply.port.desc.Ports;
91 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.port.stats._case.MultipartReplyPortStats;
92 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.port.stats._case.multipart.reply.port.stats.PortStats;
93 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.queue._case.MultipartReplyQueue;
94 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.queue._case.multipart.reply.queue.QueueStats;
95 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.table._case.MultipartReplyTable;
96 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.table._case.multipart.reply.table.TableStats;
97 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.table.features._case.MultipartReplyTableFeatures;
98 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.multipart.reply.multipart.reply.body.multipart.reply.table.features._case.multipart.reply.table.features.TableFeatures;
99 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.table.features.properties.grouping.TableFeatureProperties;
102 * @author giuseppex.petralia@intel.com
105 public class MultipartReplyMessageFactory implements OFSerializer<MultipartReplyMessage>, SerializerRegistryInjector {
107 private static final byte MESSAGE_TYPE = 19;
108 private SerializerRegistry registry;
109 private static final byte PADDING = 4;
110 private static final byte PORT_DESC_PADDING_1 = 4;
111 private static final byte PORT_DESC_PADDING_2 = 2;
112 private static final int FLOW_STATS_LENGTH_INDEX = 0;
113 private static final byte FLOW_STATS_PADDING_1 = 1;
114 private static final byte FLOW_STATS_PADDING_2 = 6;
115 private static final byte AGGREGATE_PADDING = 4;
116 private static final byte TABLE_PADDING = 3;
117 private static final byte PORT_STATS_PADDING = 4;
118 private static final byte GROUP_STATS_PADDING_1 = 2;
119 private static final byte GROUP_STATS_PADDING_2 = 4;
120 private static final int GROUP_STATS_LENGTH_INDEX = 0;
121 private static final int GROUP_DESC_LENGTH_INDEX = 0;
122 private static final int BUCKET_LENGTH_INDEX = 0;
123 private static final byte GROUP_DESC_PADDING = 1;
124 private static final byte BUCKET_PADDING = 4;
125 private static final int METER_LENGTH_INDEX = 4;
126 private static final byte METER_PADDING = 6;
127 private static final int METER_CONFIG_LENGTH_INDEX = 0;
128 private static final short LENGTH_OF_METER_BANDS = 16;
129 private static final byte METER_FEATURES_PADDING = 2;
130 private static final int TABLE_FEATURES_LENGTH_INDEX = 0;
131 private static final byte TABLE_FEATURES_PADDING = 5;
132 private static final byte INSTRUCTIONS_CODE = 0;
133 private static final byte INSTRUCTIONS_MISS_CODE = 1;
134 private static final byte NEXT_TABLE_CODE = 2;
135 private static final byte NEXT_TABLE_MISS_CODE = 3;
136 private static final byte WRITE_ACTIONS_CODE = 4;
137 private static final byte WRITE_ACTIONS_MISS_CODE = 5;
138 private static final byte APPLY_ACTIONS_CODE = 6;
139 private static final byte APPLY_ACTIONS_MISS_CODE = 7;
140 private static final byte MATCH_CODE = 8;
141 private static final byte WILDCARDS_CODE = 10;
142 private static final byte WRITE_SETFIELD_CODE = 12;
143 private static final byte WRITE_SETFIELD_MISS_CODE = 13;
144 private static final byte APPLY_SETFIELD_CODE = 14;
145 private static final byte APPLY_SETFIELD_MISS_CODE = 15;
148 public void injectSerializerRegistry(SerializerRegistry serializerRegistry) {
149 this.registry = serializerRegistry;
153 public void serialize(MultipartReplyMessage message, ByteBuf outBuffer) {
154 ByteBufUtils.writeOFHeader(MESSAGE_TYPE, message, outBuffer, EncodeConstants.EMPTY_LENGTH);
155 outBuffer.writeShort(message.getType().getIntValue());
156 writeFlags(message.getFlags(), outBuffer);
157 outBuffer.writeZero(PADDING);
158 switch (message.getType()) {
160 serializeDescBody(message.getMultipartReplyBody(), outBuffer);
163 serializeFlowBody(message.getMultipartReplyBody(), outBuffer, message);
166 serializeAggregateBody(message.getMultipartReplyBody(), outBuffer);
169 serializeTableBody(message.getMultipartReplyBody(), outBuffer);
172 serializePortStatsBody(message.getMultipartReplyBody(), outBuffer);
175 serializeQueueBody(message.getMultipartReplyBody(), outBuffer);
178 serializeGroupBody(message.getMultipartReplyBody(), outBuffer);
181 serializeGroupDescBody(message.getMultipartReplyBody(), outBuffer, message);
183 case OFPMPGROUPFEATURES:
184 serializeGroupFeaturesBody(message.getMultipartReplyBody(), outBuffer);
187 serializeMeterBody(message.getMultipartReplyBody(), outBuffer);
189 case OFPMPMETERCONFIG:
190 serializeMeterConfigBody(message.getMultipartReplyBody(), outBuffer);
192 case OFPMPMETERFEATURES:
193 serializeMeterFeaturesBody(message.getMultipartReplyBody(), outBuffer);
195 case OFPMPTABLEFEATURES:
196 serializeTableFeaturesBody(message.getMultipartReplyBody(), outBuffer);
199 serializePortDescBody(message.getMultipartReplyBody(), outBuffer);
201 case OFPMPEXPERIMENTER:
202 serializeExperimenterBody(message.getMultipartReplyBody(), outBuffer);
205 ByteBufUtils.updateOFHeaderLength(outBuffer);
208 private void serializeExperimenterBody(MultipartReplyBody body, ByteBuf outBuffer) {
209 MultipartReplyExperimenterCase experimenterCase = (MultipartReplyExperimenterCase) body;
210 MultipartReplyExperimenter experimenterBody = experimenterCase.getMultipartReplyExperimenter();
211 // TODO: experimenterBody does not have get methods
214 private void writeFlags(MultipartRequestFlags flags, ByteBuf outBuffer) {
215 Map<Integer, Boolean> map = new HashMap<>();
216 map.put(0, flags.isOFPMPFREQMORE());
217 int bitmap = ByteBufUtils.fillBitMaskFromMap(map);
218 outBuffer.writeShort(bitmap);
221 private void serializeTableFeaturesBody(MultipartReplyBody body, ByteBuf outBuffer) {
222 MultipartReplyTableFeaturesCase tableFeaturesCase = (MultipartReplyTableFeaturesCase) body;
223 MultipartReplyTableFeatures tableFeatures = tableFeaturesCase.getMultipartReplyTableFeatures();
224 for (TableFeatures tableFeature : tableFeatures.getTableFeatures()) {
225 ByteBuf tableFeatureBuff = UnpooledByteBufAllocator.DEFAULT.buffer();
226 tableFeatureBuff.writeShort(EncodeConstants.EMPTY_LENGTH);
227 tableFeatureBuff.writeByte(tableFeature.getTableId());
228 tableFeatureBuff.writeZero(TABLE_FEATURES_PADDING);
229 write32String(tableFeature.getName(), tableFeatureBuff);
230 tableFeatureBuff.writeBytes(tableFeature.getMetadataMatch());
231 tableFeatureBuff.writeZero(64 - tableFeature.getMetadataMatch().length);
232 tableFeatureBuff.writeBytes(tableFeature.getMetadataWrite());
233 tableFeatureBuff.writeZero(64 - tableFeature.getMetadataWrite().length);
234 writeTableConfig(tableFeature.getConfig(), tableFeatureBuff);
235 tableFeatureBuff.writeInt(tableFeature.getMaxEntries().intValue());
236 for (TableFeatureProperties tableFeatureProp : tableFeature.getTableFeatureProperties()) {
237 switch (tableFeatureProp.getType()) {
238 case OFPTFPTINSTRUCTIONS:
239 writeInstructionRelatedTableProperty(tableFeatureBuff, tableFeatureProp, INSTRUCTIONS_CODE);
241 case OFPTFPTINSTRUCTIONSMISS:
242 writeInstructionRelatedTableProperty(tableFeatureBuff, tableFeatureProp, INSTRUCTIONS_MISS_CODE);
244 case OFPTFPTNEXTTABLES:
245 writeNextTableRelatedTableProperty(tableFeatureBuff, tableFeatureProp, NEXT_TABLE_CODE);
247 case OFPTFPTNEXTTABLESMISS:
248 writeNextTableRelatedTableProperty(tableFeatureBuff, tableFeatureProp, NEXT_TABLE_MISS_CODE);
250 case OFPTFPTWRITEACTIONS:
251 writeActionsRelatedTableProperty(tableFeatureBuff, tableFeatureProp, WRITE_ACTIONS_CODE);
253 case OFPTFPTWRITEACTIONSMISS:
254 writeActionsRelatedTableProperty(tableFeatureBuff, tableFeatureProp, WRITE_ACTIONS_MISS_CODE);
256 case OFPTFPTAPPLYACTIONS:
257 writeActionsRelatedTableProperty(tableFeatureBuff, tableFeatureProp, APPLY_ACTIONS_CODE);
259 case OFPTFPTAPPLYACTIONSMISS:
260 writeActionsRelatedTableProperty(tableFeatureBuff, tableFeatureProp, APPLY_ACTIONS_MISS_CODE);
263 writeOxmRelatedTableProperty(tableFeatureBuff, tableFeatureProp, MATCH_CODE);
265 case OFPTFPTWILDCARDS:
266 writeOxmRelatedTableProperty(tableFeatureBuff, tableFeatureProp, WILDCARDS_CODE);
268 case OFPTFPTWRITESETFIELD:
269 writeOxmRelatedTableProperty(tableFeatureBuff, tableFeatureProp, WRITE_SETFIELD_CODE);
271 case OFPTFPTWRITESETFIELDMISS:
272 writeOxmRelatedTableProperty(tableFeatureBuff, tableFeatureProp, WRITE_SETFIELD_MISS_CODE);
274 case OFPTFPTAPPLYSETFIELD:
275 writeOxmRelatedTableProperty(tableFeatureBuff, tableFeatureProp, APPLY_SETFIELD_CODE);
277 case OFPTFPTAPPLYSETFIELDMISS:
278 writeOxmRelatedTableProperty(tableFeatureBuff, tableFeatureProp, APPLY_SETFIELD_MISS_CODE);
280 case OFPTFPTEXPERIMENTER:
281 writeExperimenterRelatedTableProperty(tableFeatureBuff, tableFeatureProp);
283 case OFPTFPTEXPERIMENTERMISS:
284 writeExperimenterRelatedTableProperty(tableFeatureBuff, tableFeatureProp);
288 tableFeatureBuff.setShort(TABLE_FEATURES_LENGTH_INDEX, tableFeatureBuff.readableBytes());
289 outBuffer.writeBytes(tableFeatureBuff);
293 private void writeExperimenterRelatedTableProperty(final ByteBuf output, final TableFeatureProperties property) {
294 long expId = property.getAugmentation(ExperimenterIdTableFeatureProperty.class).getExperimenter().getValue();
295 OFSerializer<TableFeatureProperties> serializer = registry.getSerializer(ExperimenterSerializerKeyFactory
296 .createMultipartRequestTFSerializerKey(EncodeConstants.OF13_VERSION_ID, expId));
297 serializer.serialize(property, output);
300 private void writeOxmRelatedTableProperty(final ByteBuf output, final TableFeatureProperties property,
302 int startIndex = output.writerIndex();
303 output.writeShort(code);
304 int lengthIndex = output.writerIndex();
305 output.writeShort(EncodeConstants.EMPTY_LENGTH);
306 List<MatchEntry> entries = property.getAugmentation(OxmRelatedTableFeatureProperty.class).getMatchEntry();
307 if (entries != null) {
308 TypeKeyMaker<MatchEntry> keyMaker = TypeKeyMakerFactory
309 .createMatchEntriesKeyMaker(EncodeConstants.OF13_VERSION_ID);
310 ListSerializer.serializeHeaderList(entries, keyMaker, registry, output);
312 int length = output.writerIndex() - startIndex;
313 output.setShort(lengthIndex, length);
314 output.writeZero(paddingNeeded(length));
317 private void writeActionsRelatedTableProperty(final ByteBuf output, final TableFeatureProperties property,
319 int startIndex = output.writerIndex();
320 output.writeShort(code);
321 int lengthIndex = output.writerIndex();
322 output.writeShort(EncodeConstants.EMPTY_LENGTH);
323 List<Action> actions = property.getAugmentation(ActionRelatedTableFeatureProperty.class).getAction();
324 if (actions != null) {
325 TypeKeyMaker<Action> keyMaker = TypeKeyMakerFactory.createActionKeyMaker(EncodeConstants.OF13_VERSION_ID);
326 ListSerializer.serializeHeaderList(actions, keyMaker, registry, output);
328 int length = output.writerIndex() - startIndex;
329 output.setShort(lengthIndex, length);
330 output.writeZero(paddingNeeded(length));
333 private static void writeNextTableRelatedTableProperty(final ByteBuf output, final TableFeatureProperties property,
335 int startIndex = output.writerIndex();
336 output.writeShort(code);
337 int lengthIndex = output.writerIndex();
338 output.writeShort(EncodeConstants.EMPTY_LENGTH);
339 List<NextTableIds> nextTableIds = property.getAugmentation(NextTableRelatedTableFeatureProperty.class)
341 if (nextTableIds != null) {
342 for (NextTableIds next : nextTableIds) {
343 output.writeByte(next.getTableId());
346 int length = output.writerIndex() - startIndex;
347 output.setShort(lengthIndex, length);
348 output.writeZero(paddingNeeded(length));
351 private void writeInstructionRelatedTableProperty(final ByteBuf output, final TableFeatureProperties property,
353 int startIndex = output.writerIndex();
354 output.writeShort(code);
355 int lengthIndex = output.writerIndex();
356 output.writeShort(EncodeConstants.EMPTY_LENGTH);
357 List<Instruction> instructions = property.getAugmentation(InstructionRelatedTableFeatureProperty.class)
359 if (instructions != null) {
360 TypeKeyMaker<Instruction> keyMaker = TypeKeyMakerFactory
361 .createInstructionKeyMaker(EncodeConstants.OF13_VERSION_ID);
362 ListSerializer.serializeHeaderList(instructions, keyMaker, registry, output);
364 int length = output.writerIndex() - startIndex;
365 output.setShort(lengthIndex, length);
366 output.writeZero(paddingNeeded(length));
369 private static int paddingNeeded(final int length) {
370 int paddingRemainder = length % EncodeConstants.PADDING;
372 if (paddingRemainder != 0) {
373 result = EncodeConstants.PADDING - paddingRemainder;
378 private void writeTableConfig(TableConfig tableConfig, ByteBuf outBuffer) {
379 Map<Integer, Boolean> map = new HashMap<>();
380 map.put(0, tableConfig.isOFPTCDEPRECATEDMASK());
381 int bitmap = ByteBufUtils.fillBitMaskFromMap(map);
382 outBuffer.writeInt(bitmap);
385 private void serializeMeterFeaturesBody(MultipartReplyBody body, ByteBuf outBuffer) {
386 MultipartReplyMeterFeaturesCase meterFeaturesCase = (MultipartReplyMeterFeaturesCase) body;
387 MultipartReplyMeterFeatures meterFeatures = meterFeaturesCase.getMultipartReplyMeterFeatures();
388 outBuffer.writeInt(meterFeatures.getMaxMeter().intValue());
389 writeBandTypes(meterFeatures.getBandTypes(), outBuffer);
390 writeMeterFlags(meterFeatures.getCapabilities(), outBuffer);
391 outBuffer.writeByte(meterFeatures.getMaxBands());
392 outBuffer.writeByte(meterFeatures.getMaxColor());
393 outBuffer.writeZero(METER_FEATURES_PADDING);
396 private void writeBandTypes(MeterBandTypeBitmap bandTypes, ByteBuf outBuffer) {
397 Map<Integer, Boolean> map = new HashMap<>();
398 map.put(0, bandTypes.isOFPMBTDROP());
399 map.put(1, bandTypes.isOFPMBTDSCPREMARK());
400 int bitmap = ByteBufUtils.fillBitMaskFromMap(map);
401 outBuffer.writeInt(bitmap);
404 private void serializeMeterConfigBody(MultipartReplyBody body, ByteBuf outBuffer) {
405 MultipartReplyMeterConfigCase meterConfigCase = (MultipartReplyMeterConfigCase) body;
406 MultipartReplyMeterConfig meter = meterConfigCase.getMultipartReplyMeterConfig();
407 for (MeterConfig meterConfig : meter.getMeterConfig()) {
408 ByteBuf meterConfigBuff = UnpooledByteBufAllocator.DEFAULT.buffer();
409 meterConfigBuff.writeShort(EncodeConstants.EMPTY_LENGTH);
410 writeMeterFlags(meterConfig.getFlags(), meterConfigBuff);
411 meterConfigBuff.writeInt(meterConfig.getMeterId().getValue().intValue());
412 for (Bands currentBand : meterConfig.getBands()) {
413 MeterBand meterBand = currentBand.getMeterBand();
414 if (meterBand instanceof MeterBandDropCase) {
415 MeterBandDropCase dropBandCase = (MeterBandDropCase) meterBand;
416 MeterBandDrop dropBand = dropBandCase.getMeterBandDrop();
417 writeBandCommonFields(dropBand, meterConfigBuff);
418 } else if (meterBand instanceof MeterBandDscpRemarkCase) {
419 MeterBandDscpRemarkCase dscpRemarkBandCase = (MeterBandDscpRemarkCase) meterBand;
420 MeterBandDscpRemark dscpRemarkBand = dscpRemarkBandCase.getMeterBandDscpRemark();
421 writeBandCommonFields(dscpRemarkBand, meterConfigBuff);
422 } else if (meterBand instanceof MeterBandExperimenterCase) {
423 MeterBandExperimenterCase experimenterBandCase = (MeterBandExperimenterCase) meterBand;
424 MeterBandExperimenter experimenterBand = experimenterBandCase.getMeterBandExperimenter();
425 writeBandCommonFields(experimenterBand, meterConfigBuff);
428 meterConfigBuff.setShort(METER_CONFIG_LENGTH_INDEX, meterConfigBuff.readableBytes());
429 outBuffer.writeBytes(meterConfigBuff);
433 private static void writeBandCommonFields(final MeterBandCommons meterBand, final ByteBuf outBuffer) {
434 outBuffer.writeShort(meterBand.getType().getIntValue());
435 outBuffer.writeShort(LENGTH_OF_METER_BANDS);
436 outBuffer.writeInt(meterBand.getRate().intValue());
437 outBuffer.writeInt(meterBand.getBurstSize().intValue());
440 private void writeMeterFlags(MeterFlags flags, ByteBuf outBuffer) {
441 Map<Integer, Boolean> map = new HashMap<>();
442 map.put(0, flags.isOFPMFKBPS());
443 map.put(1, flags.isOFPMFPKTPS());
444 map.put(2, flags.isOFPMFBURST());
445 map.put(3, flags.isOFPMFSTATS());
446 int bitmap = ByteBufUtils.fillBitMaskFromMap(map);
447 outBuffer.writeShort(bitmap);
450 private void serializeMeterBody(MultipartReplyBody body, ByteBuf outBuffer) {
451 MultipartReplyMeterCase meterCase = (MultipartReplyMeterCase) body;
452 MultipartReplyMeter meter = meterCase.getMultipartReplyMeter();
453 for (MeterStats meterStats : meter.getMeterStats()) {
454 ByteBuf meterStatsBuff = UnpooledByteBufAllocator.DEFAULT.buffer();
455 meterStatsBuff.writeInt(meterStats.getMeterId().getValue().intValue());
456 meterStatsBuff.writeInt(EncodeConstants.EMPTY_LENGTH);
457 meterStatsBuff.writeZero(METER_PADDING);
458 meterStatsBuff.writeInt(meterStats.getFlowCount().intValue());
459 meterStatsBuff.writeLong(meterStats.getPacketInCount().longValue());
460 meterStatsBuff.writeLong(meterStats.getByteInCount().longValue());
461 meterStatsBuff.writeInt(meterStats.getDurationSec().intValue());
462 meterStatsBuff.writeInt(meterStats.getDurationNsec().intValue());
463 for (MeterBandStats meterBandStats : meterStats.getMeterBandStats()) {
464 meterStatsBuff.writeLong(meterBandStats.getPacketBandCount().longValue());
465 meterStatsBuff.writeLong(meterBandStats.getByteBandCount().longValue());
467 meterStatsBuff.setInt(METER_LENGTH_INDEX, meterStatsBuff.readableBytes());
468 outBuffer.writeBytes(meterStatsBuff);
472 private void serializeGroupFeaturesBody(MultipartReplyBody body, ByteBuf outBuffer) {
473 MultipartReplyGroupFeaturesCase groupFeaturesCase = (MultipartReplyGroupFeaturesCase) body;
474 MultipartReplyGroupFeatures groupFeatures = groupFeaturesCase.getMultipartReplyGroupFeatures();
475 writeGroupTypes(groupFeatures.getTypes(), outBuffer);
476 writeGroupCapabilities(groupFeatures.getCapabilities(), outBuffer);
477 for (Long maxGroups : groupFeatures.getMaxGroups()) {
478 outBuffer.writeInt(maxGroups.intValue());
480 for (ActionType action : groupFeatures.getActionsBitmap()) {
481 writeActionType(action, outBuffer);
485 private void writeActionType(ActionType action, ByteBuf outBuffer) {
486 Map<Integer, Boolean> map = new HashMap<>();
487 map.put(0, action.isOFPATOUTPUT());
488 map.put(1, action.isOFPATCOPYTTLOUT());
489 map.put(2, action.isOFPATCOPYTTLIN());
490 map.put(3, action.isOFPATSETMPLSTTL());
491 map.put(4, action.isOFPATDECMPLSTTL());
492 map.put(5, action.isOFPATPUSHVLAN());
493 map.put(6, action.isOFPATPOPVLAN());
494 map.put(7, action.isOFPATPUSHMPLS());
495 map.put(8, action.isOFPATPOPMPLS());
496 map.put(9, action.isOFPATSETQUEUE());
497 map.put(10, action.isOFPATGROUP());
498 map.put(11, action.isOFPATSETNWTTL());
499 map.put(12, action.isOFPATDECNWTTL());
500 map.put(13, action.isOFPATSETFIELD());
501 map.put(14, action.isOFPATPUSHPBB());
502 map.put(15, action.isOFPATPOPPBB());
503 map.put(16, action.isOFPATEXPERIMENTER());
504 int bitmap = ByteBufUtils.fillBitMaskFromMap(map);
505 outBuffer.writeInt(bitmap);
508 private void writeGroupCapabilities(GroupCapabilities capabilities, ByteBuf outBuffer) {
509 Map<Integer, Boolean> map = new HashMap<>();
510 map.put(0, capabilities.isOFPGFCSELECTWEIGHT());
511 map.put(1, capabilities.isOFPGFCSELECTLIVENESS());
512 map.put(2, capabilities.isOFPGFCCHAINING());
513 map.put(3, capabilities.isOFPGFCCHAININGCHECKS());
514 int bitmap = ByteBufUtils.fillBitMaskFromMap(map);
515 outBuffer.writeInt(bitmap);
518 private void writeGroupTypes(GroupTypes types, ByteBuf outBuffer) {
519 Map<Integer, Boolean> map = new HashMap<>();
520 map.put(0, types.isOFPGTALL());
521 map.put(1, types.isOFPGTSELECT());
522 map.put(2, types.isOFPGTINDIRECT());
523 map.put(3, types.isOFPGTFF());
524 int bitmap = ByteBufUtils.fillBitMaskFromMap(map);
525 outBuffer.writeInt(bitmap);
528 private void serializeGroupDescBody(MultipartReplyBody body, ByteBuf outBuffer, MultipartReplyMessage message) {
529 MultipartReplyGroupDescCase groupDescCase = (MultipartReplyGroupDescCase) body;
530 MultipartReplyGroupDesc group = groupDescCase.getMultipartReplyGroupDesc();
531 for (GroupDesc groupDesc : group.getGroupDesc()) {
532 ByteBuf groupDescBuff = UnpooledByteBufAllocator.DEFAULT.buffer();
533 groupDescBuff.writeShort(EncodeConstants.EMPTY_LENGTH);
534 groupDescBuff.writeByte(groupDesc.getType().getIntValue());
535 groupDescBuff.writeZero(GROUP_DESC_PADDING);
536 groupDescBuff.writeInt(groupDesc.getGroupId().getValue().intValue());
537 for (BucketsList bucket : groupDesc.getBucketsList()) {
538 ByteBuf bucketBuff = UnpooledByteBufAllocator.DEFAULT.buffer();
539 bucketBuff.writeShort(EncodeConstants.EMPTY_LENGTH);
540 bucketBuff.writeShort(bucket.getWeight());
541 bucketBuff.writeInt(bucket.getWatchPort().getValue().intValue());
542 bucketBuff.writeInt(bucket.getWatchGroup().intValue());
543 bucketBuff.writeZero(BUCKET_PADDING);
544 ListSerializer.serializeList(bucket.getAction(),
545 TypeKeyMakerFactory.createActionKeyMaker(message.getVersion()), registry, bucketBuff);
546 bucketBuff.setShort(BUCKET_LENGTH_INDEX, bucketBuff.readableBytes());
547 groupDescBuff.writeBytes(bucketBuff);
549 groupDescBuff.setShort(GROUP_DESC_LENGTH_INDEX, groupDescBuff.readableBytes());
550 outBuffer.writeBytes(groupDescBuff);
554 private void serializeGroupBody(MultipartReplyBody body, ByteBuf outBuffer) {
555 MultipartReplyGroupCase groupCase = (MultipartReplyGroupCase) body;
556 MultipartReplyGroup group = groupCase.getMultipartReplyGroup();
557 for (GroupStats groupStats : group.getGroupStats()) {
558 ByteBuf groupStatsBuff = UnpooledByteBufAllocator.DEFAULT.buffer();
559 groupStatsBuff.writeShort(EncodeConstants.EMPTY_LENGTH);
560 groupStatsBuff.writeZero(GROUP_STATS_PADDING_1);
561 groupStatsBuff.writeInt(groupStats.getGroupId().getValue().intValue());
562 groupStatsBuff.writeInt(groupStats.getRefCount().intValue());
563 groupStatsBuff.writeZero(GROUP_STATS_PADDING_2);
564 groupStatsBuff.writeLong(groupStats.getPacketCount().longValue());
565 groupStatsBuff.writeLong(groupStats.getByteCount().longValue());
566 groupStatsBuff.writeInt(groupStats.getDurationSec().intValue());
567 groupStatsBuff.writeInt(groupStats.getDurationNsec().intValue());
568 for (BucketStats bucketStats : groupStats.getBucketStats()) {
569 groupStatsBuff.writeLong(bucketStats.getPacketCount().longValue());
570 groupStatsBuff.writeLong(bucketStats.getByteCount().longValue());
572 groupStatsBuff.setShort(GROUP_STATS_LENGTH_INDEX, groupStatsBuff.readableBytes());
573 outBuffer.writeBytes(groupStatsBuff);
577 private void serializeQueueBody(MultipartReplyBody body, ByteBuf outBuffer) {
578 MultipartReplyQueueCase queueCase = (MultipartReplyQueueCase) body;
579 MultipartReplyQueue queue = queueCase.getMultipartReplyQueue();
580 for (QueueStats queueStats : queue.getQueueStats()) {
581 outBuffer.writeInt(queueStats.getPortNo().intValue());
582 outBuffer.writeInt(queueStats.getQueueId().intValue());
583 outBuffer.writeLong(queueStats.getTxBytes().longValue());
584 outBuffer.writeLong(queueStats.getTxPackets().longValue());
585 outBuffer.writeLong(queueStats.getTxErrors().longValue());
586 outBuffer.writeInt(queueStats.getDurationSec().intValue());
587 outBuffer.writeInt(queueStats.getDurationNsec().intValue());
591 private void serializePortStatsBody(MultipartReplyBody body, ByteBuf outBuffer) {
592 MultipartReplyPortStatsCase portStatsCase = (MultipartReplyPortStatsCase) body;
593 MultipartReplyPortStats portStats = portStatsCase.getMultipartReplyPortStats();
594 for (PortStats portStat : portStats.getPortStats()) {
595 outBuffer.writeInt(portStat.getPortNo().intValue());
596 outBuffer.writeZero(PORT_STATS_PADDING);
597 outBuffer.writeLong(portStat.getRxPackets().longValue());
598 outBuffer.writeLong(portStat.getTxPackets().longValue());
599 outBuffer.writeLong(portStat.getRxBytes().longValue());
600 outBuffer.writeLong(portStat.getTxBytes().longValue());
601 outBuffer.writeLong(portStat.getRxDropped().longValue());
602 outBuffer.writeLong(portStat.getTxDropped().longValue());
603 outBuffer.writeLong(portStat.getRxErrors().longValue());
604 outBuffer.writeLong(portStat.getTxErrors().longValue());
605 outBuffer.writeLong(portStat.getRxFrameErr().longValue());
606 outBuffer.writeLong(portStat.getRxOverErr().longValue());
607 outBuffer.writeLong(portStat.getRxCrcErr().longValue());
608 outBuffer.writeLong(portStat.getCollisions().longValue());
609 outBuffer.writeInt(portStat.getDurationSec().intValue());
610 outBuffer.writeInt(portStat.getDurationNsec().intValue());
614 private void serializeTableBody(MultipartReplyBody body, ByteBuf outBuffer) {
615 MultipartReplyTableCase tableCase = (MultipartReplyTableCase) body;
616 MultipartReplyTable table = tableCase.getMultipartReplyTable();
617 for (TableStats tableStats : table.getTableStats()) {
618 outBuffer.writeByte(tableStats.getTableId());
619 outBuffer.writeZero(TABLE_PADDING);
620 outBuffer.writeInt(tableStats.getActiveCount().intValue());
621 outBuffer.writeLong(tableStats.getLookupCount().longValue());
622 outBuffer.writeLong(tableStats.getMatchedCount().longValue());
626 private void serializeAggregateBody(MultipartReplyBody body, ByteBuf outBuffer) {
627 MultipartReplyAggregateCase aggregateCase = (MultipartReplyAggregateCase) body;
628 MultipartReplyAggregate aggregate = aggregateCase.getMultipartReplyAggregate();
629 outBuffer.writeLong(aggregate.getPacketCount().longValue());
630 outBuffer.writeLong(aggregate.getByteCount().longValue());
631 outBuffer.writeInt(aggregate.getFlowCount().intValue());
632 outBuffer.writeZero(AGGREGATE_PADDING);
635 private void serializeFlowBody(MultipartReplyBody body, ByteBuf outBuffer, MultipartReplyMessage message) {
636 MultipartReplyFlowCase flowCase = (MultipartReplyFlowCase) body;
637 MultipartReplyFlow flow = flowCase.getMultipartReplyFlow();
638 for (FlowStats flowStats : flow.getFlowStats()) {
639 ByteBuf flowStatsBuff = UnpooledByteBufAllocator.DEFAULT.buffer();
640 flowStatsBuff.writeShort(EncodeConstants.EMPTY_LENGTH);
641 flowStatsBuff.writeByte(new Long(flowStats.getTableId()).byteValue());
642 flowStatsBuff.writeZero(FLOW_STATS_PADDING_1);
643 flowStatsBuff.writeInt(flowStats.getDurationSec().intValue());
644 flowStatsBuff.writeInt(flowStats.getDurationNsec().intValue());
645 flowStatsBuff.writeShort(flowStats.getPriority());
646 flowStatsBuff.writeShort(flowStats.getIdleTimeout());
647 flowStatsBuff.writeShort(flowStats.getHardTimeout());
648 flowStatsBuff.writeZero(FLOW_STATS_PADDING_2);
649 flowStatsBuff.writeLong(flowStats.getCookie().longValue());
650 flowStatsBuff.writeLong(flowStats.getPacketCount().longValue());
651 flowStatsBuff.writeLong(flowStats.getByteCount().longValue());
652 OFSerializer<Match> matchSerializer = registry.<Match, OFSerializer<Match>> getSerializer(
653 new MessageTypeKey<>(message.getVersion(), Match.class));
654 matchSerializer.serialize(flowStats.getMatch(), flowStatsBuff);
655 ListSerializer.serializeList(flowStats.getInstruction(),
656 TypeKeyMakerFactory.createInstructionKeyMaker(message.getVersion()), registry, flowStatsBuff);
658 flowStatsBuff.setShort(FLOW_STATS_LENGTH_INDEX, flowStatsBuff.readableBytes());
659 outBuffer.writeBytes(flowStatsBuff);
663 private void serializeDescBody(MultipartReplyBody body, ByteBuf outBuffer) {
664 MultipartReplyDescCase descCase = (MultipartReplyDescCase) body;
665 MultipartReplyDesc desc = descCase.getMultipartReplyDesc();
666 write256String(desc.getMfrDesc(), outBuffer);
667 write256String(desc.getHwDesc(), outBuffer);
668 write256String(desc.getSwDesc(), outBuffer);
669 write32String(desc.getSerialNum(), outBuffer);
670 write256String(desc.getDpDesc(), outBuffer);
673 private void write256String(String toWrite, ByteBuf outBuffer) {
674 byte[] nameBytes = toWrite.getBytes();
675 if (nameBytes.length < 256) {
676 byte[] nameBytesPadding = new byte[256];
678 for (byte b : nameBytes) {
679 nameBytesPadding[i] = b;
682 for (; i < 256; i++) {
683 nameBytesPadding[i] = 0x0;
685 outBuffer.writeBytes(nameBytesPadding);
687 outBuffer.writeBytes(nameBytes);
691 private void write32String(String toWrite, ByteBuf outBuffer) {
692 byte[] nameBytes = toWrite.getBytes();
693 if (nameBytes.length < 32) {
694 byte[] nameBytesPadding = new byte[32];
696 for (byte b : nameBytes) {
697 nameBytesPadding[i] = b;
700 for (; i < 32; i++) {
701 nameBytesPadding[i] = 0x0;
703 outBuffer.writeBytes(nameBytesPadding);
705 outBuffer.writeBytes(nameBytes);
709 private void serializePortDescBody(MultipartReplyBody body, ByteBuf outBuffer) {
710 MultipartReplyPortDescCase portCase = (MultipartReplyPortDescCase) body;
711 MultipartReplyPortDesc portDesc = portCase.getMultipartReplyPortDesc();
712 for (Ports port : portDesc.getPorts()) {
713 outBuffer.writeInt(port.getPortNo().intValue()); // Assuming PortNo
715 outBuffer.writeZero(PORT_DESC_PADDING_1);
716 writeMacAddress(port.getHwAddr().getValue(), outBuffer);
717 outBuffer.writeZero(PORT_DESC_PADDING_2);
718 writeName(port.getName(), outBuffer);
719 writePortConfig(port.getConfig(), outBuffer);
720 writePortState(port.getState(), outBuffer);
721 writePortFeatures(port.getCurrentFeatures(), outBuffer);
722 writePortFeatures(port.getAdvertisedFeatures(), outBuffer);
723 writePortFeatures(port.getSupportedFeatures(), outBuffer);
724 writePortFeatures(port.getPeerFeatures(), outBuffer);
725 outBuffer.writeInt(port.getCurrSpeed().intValue());
726 outBuffer.writeInt(port.getMaxSpeed().intValue());
730 private void writeName(String name, ByteBuf outBuffer) {
731 byte[] nameBytes = name.getBytes();
732 if (nameBytes.length < 16) {
733 byte[] nameBytesPadding = new byte[16];
735 for (byte b : nameBytes) {
736 nameBytesPadding[i] = b;
739 for (; i < 16; i++) {
740 nameBytesPadding[i] = 0x0;
742 outBuffer.writeBytes(nameBytesPadding);
744 outBuffer.writeBytes(nameBytes);
749 private void writeMacAddress(String macAddress, ByteBuf outBuffer) {
750 String[] macAddressParts = macAddress.split(":");
751 byte[] macAddressBytes = new byte[6];
752 for (int i = 0; i < 6; i++) {
753 Integer hex = Integer.parseInt(macAddressParts[i], 16);
754 macAddressBytes[i] = hex.byteValue();
756 outBuffer.writeBytes(macAddressBytes);
759 private void writePortConfig(PortConfig config, ByteBuf outBuffer) {
760 Map<Integer, Boolean> map = new HashMap<>();
761 map.put(0, config.isPortDown());
762 map.put(2, config.isNoRecv());
763 map.put(5, config.isNoFwd());
764 map.put(6, config.isNoPacketIn());
765 int bitmap = ByteBufUtils.fillBitMaskFromMap(map);
766 outBuffer.writeInt(bitmap);
769 private void writePortState(PortState state, ByteBuf outBuffer) {
770 Map<Integer, Boolean> map = new HashMap<>();
771 map.put(0, state.isLinkDown());
772 map.put(1, state.isBlocked());
773 map.put(2, state.isLive());
774 int bitmap = ByteBufUtils.fillBitMaskFromMap(map);
775 outBuffer.writeInt(bitmap);
778 private void writePortFeatures(PortFeatures features, ByteBuf outBuffer) {
779 Map<Integer, Boolean> map = new HashMap<>();
780 map.put(0, features.is_10mbHd());
781 map.put(1, features.is_10mbFd());
782 map.put(2, features.is_100mbHd());
783 map.put(3, features.is_100mbFd());
784 map.put(4, features.is_1gbHd());
785 map.put(5, features.is_1gbFd());
786 map.put(6, features.is_10gbFd());
787 map.put(7, features.is_40gbFd());
788 map.put(8, features.is_100gbFd());
789 map.put(9, features.is_1tbFd());
790 map.put(10, features.isOther());
791 map.put(11, features.isCopper());
792 map.put(12, features.isFiber());
793 map.put(13, features.isAutoneg());
794 map.put(14, features.isPause());
795 map.put(15, features.isPauseAsym());
796 int bitmap = ByteBufUtils.fillBitMaskFromMap(map);
797 outBuffer.writeInt(bitmap);