b08a3728d7fd4315a57ca67d34cbb6c3d9d6330a
[openflowplugin.git] / openflowplugin / src / main / java / org / opendaylight / openflowplugin / openflow / md / core / sal / convertor / FlowConvertor.java
1 /**
2  * Copyright (c) 2013 Ericsson. 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
9 package org.opendaylight.openflowplugin.openflow.md.core.sal.convertor;
10
11 import java.math.BigInteger;
12 import java.nio.ByteBuffer;
13 import java.util.ArrayList;
14 import java.util.List;
15
16 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.Ipv4Address;
17 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.Ipv4Prefix;
18 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.Ipv6Address;
19 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.Ipv6Prefix;
20 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev100924.MacAddress;
21 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.AddFlowInput;
22 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.RemoveFlowInput;
23 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.UpdateFlowInput;
24 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.Flow;
25 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.ApplyActions;
26 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.ClearActions;
27 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.GoToTable;
28 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.Meter;
29 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.WriteActions;
30 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.WriteMetadata;
31 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.arp.match.fields.ArpSourceHardwareAddress;
32 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.arp.match.fields.ArpTargetHardwareAddress;
33 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.ethernet.match.fields.EthernetDestination;
34 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.ethernet.match.fields.EthernetSource;
35 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.EthernetMatch;
36 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.Icmpv4Match;
37 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.Icmpv6Match;
38 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.IpMatch;
39 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.Layer3Match;
40 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.Layer4Match;
41 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.ProtocolMatchFields;
42 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.VlanMatch;
43 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.layer._3.match.ArpMatch;
44 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.layer._3.match.Ipv4Match;
45 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.layer._3.match.Ipv6Match;
46 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.layer._4.match.SctpMatch;
47 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.layer._4.match.TcpMatch;
48 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.layer._4.match.UdpMatch;
49 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.ActionsInstruction;
50 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.ActionsInstructionBuilder;
51 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.BosMatchEntry;
52 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.BosMatchEntryBuilder;
53 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.DscpMatchEntry;
54 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.DscpMatchEntryBuilder;
55 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.EcnMatchEntry;
56 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.EcnMatchEntryBuilder;
57 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.EthTypeMatchEntry;
58 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.EthTypeMatchEntryBuilder;
59 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.Icmpv4CodeMatchEntry;
60 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.Icmpv4CodeMatchEntryBuilder;
61 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.Icmpv4TypeMatchEntry;
62 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.Icmpv4TypeMatchEntryBuilder;
63 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.Icmpv6CodeMatchEntry;
64 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.Icmpv6CodeMatchEntryBuilder;
65 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.Icmpv6TypeMatchEntry;
66 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.Icmpv6TypeMatchEntryBuilder;
67 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.Ipv4AddressMatchEntry;
68 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.Ipv4AddressMatchEntryBuilder;
69 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.Ipv6AddressMatchEntry;
70 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.Ipv6AddressMatchEntryBuilder;
71 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.Ipv6FlabelMatchEntry;
72 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.Ipv6FlabelMatchEntryBuilder;
73 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.IsidMatchEntry;
74 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.IsidMatchEntryBuilder;
75 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.MacAddressMatchEntry;
76 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.MacAddressMatchEntryBuilder;
77 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.MaskMatchEntry;
78 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.MaskMatchEntryBuilder;
79 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.MetadataInstruction;
80 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.MetadataInstructionBuilder;
81 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.MetadataMatchEntry;
82 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.MetadataMatchEntryBuilder;
83 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.MeterIdInstruction;
84 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.MeterIdInstructionBuilder;
85 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.MplsLabelMatchEntry;
86 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.MplsLabelMatchEntryBuilder;
87 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.OpCodeMatchEntry;
88 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.OpCodeMatchEntryBuilder;
89 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.PortMatchEntry;
90 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.PortMatchEntryBuilder;
91 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.PortNumberMatchEntry;
92 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.PortNumberMatchEntryBuilder;
93 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.ProtocolNumberMatchEntry;
94 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.ProtocolNumberMatchEntryBuilder;
95 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.PseudoFieldMatchEntry;
96 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.PseudoFieldMatchEntry.PseudoField;
97 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.PseudoFieldMatchEntryBuilder;
98 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.TableIdInstruction;
99 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.TableIdInstructionBuilder;
100 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.TcMatchEntry;
101 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.TcMatchEntryBuilder;
102 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.VlanPcpMatchEntryBuilder;
103 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.VlanVidMatchEntry;
104 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.augments.rev131002.VlanVidMatchEntryBuilder;
105 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.instruction.rev130731.instructions.Instructions;
106 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.instruction.rev130731.instructions.InstructionsBuilder;
107 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.EtherType;
108 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.FlowModCommand;
109 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.PortNumber;
110 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.TableId;
111 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.ArpOp;
112 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.ArpSha;
113 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.ArpSpa;
114 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.ArpTha;
115 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.ArpTpa;
116 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.EthDst;
117 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.EthSrc;
118 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.EthType;
119 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.Icmpv4Code;
120 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.Icmpv4Type;
121 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.Icmpv6Code;
122 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.Icmpv6Type;
123 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.InPhyPort;
124 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.InPort;
125 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.IpDscp;
126 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.IpProto;
127 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.Ipv4Dst;
128 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.Ipv4Src;
129 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.Ipv6Dst;
130 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.Ipv6Exthdr;
131 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.Ipv6Flabel;
132 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.Ipv6NdSll;
133 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.Ipv6NdTarget;
134 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.Ipv6NdTll;
135 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.Ipv6Src;
136 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.Metadata;
137 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.MplsBos;
138 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.MplsLabel;
139 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.MplsTc;
140 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.OpenflowBasicClass;
141 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.PbbIsid;
142 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.SctpDst;
143 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.SctpSrc;
144 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.TcpDst;
145 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.TcpSrc;
146 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.TunnelId;
147 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.UdpDst;
148 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.UdpSrc;
149 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.VlanPcp;
150 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.VlanVid;
151 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.oxm.fields.MatchEntries;
152 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev130731.oxm.fields.MatchEntriesBuilder;
153 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.FlowModInput;
154 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.FlowModInputBuilder;
155 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.match.grouping.MatchBuilder;
156 import org.slf4j.Logger;
157 import org.slf4j.LoggerFactory;
158
159 /**
160  * Utility class for converting a MD-SAL Flow into the OF flow mod
161  */
162 public class FlowConvertor {
163     private static final Logger logger = LoggerFactory.getLogger(FlowConvertor.class);
164     private static final String PREFIX_SEPARATOR = "/";
165
166     public static FlowModInput toFlowModInput(Flow flow, short version) {
167         FlowModInputBuilder flowMod = new FlowModInputBuilder();
168
169         flowMod.setCookie(flow.getCookie());
170
171         if (flow.getCookieMask() != null) {
172             flowMod.setCookieMask(new BigInteger(flow.getCookieMask().toString()));
173         }
174
175         if (flow.getTableId() != null) {
176             flowMod.setTableId(new TableId(flow.getTableId().longValue()));
177         }
178
179         if (flow instanceof AddFlowInput) {
180             flowMod.setCommand(FlowModCommand.OFPFCADD);
181         } else if (flow instanceof RemoveFlowInput) {
182             if (flow.isStrict()) {
183                 flowMod.setCommand(FlowModCommand.OFPFCDELETESTRICT);
184             } else {
185                 flowMod.setCommand(FlowModCommand.OFPFCDELETE);
186             }
187         } else if (flow instanceof UpdateFlowInput) {
188             if (flow.isStrict()) {
189                 flowMod.setCommand(FlowModCommand.OFPFCMODIFYSTRICT);
190             } else {
191                 flowMod.setCommand(FlowModCommand.OFPFCMODIFY);
192             }
193         }
194
195         flowMod.setIdleTimeout(flow.getIdleTimeout());
196         flowMod.setHardTimeout(flow.getHardTimeout());
197         flowMod.setPriority(flow.getPriority());
198         flowMod.setBufferId(flow.getBufferId());
199
200         if (flow.getOutPort() != null) {
201             flowMod.setOutPort(new PortNumber(flow.getOutPort().longValue()));
202         }
203
204         flowMod.setOutGroup(flow.getOutGroup());
205
206         org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.FlowModFlags flowModFlags = flow.getFlags();
207         org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.FlowModFlags ofFlowModFlags = null;
208         if (flowModFlags != null) {
209             ofFlowModFlags = new org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.FlowModFlags(
210                     flowModFlags.isCHECKOVERLAP(), flowModFlags.isNOBYTCOUNTS(), flowModFlags.isNOPKTCOUNTS(),
211                     flowModFlags.isRESETCOUNTS(), flowModFlags.isSENDFLOWREM());
212         }
213         flowMod.setFlags(ofFlowModFlags);
214
215         if (flow.getMatch() != null) {
216             MatchBuilder matchBuilder = new MatchBuilder();
217             matchBuilder.setMatchEntries(toMatch(flow.getMatch()));
218             flowMod.setMatch(matchBuilder.build());
219         }
220
221         if (flow.getInstructions() != null) {
222             flowMod.setInstructions(toInstructions(flow.getInstructions(), version));
223         }
224         flowMod.setVersion(version);
225         return flowMod.build();
226     }
227
228     public static List<MatchEntries> toMatch(
229             org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.Match match) {
230
231         MatchEntriesBuilder matchEntriesBuilder = new MatchEntriesBuilder();
232         List<MatchEntries> matchEntriesList = new ArrayList<>();
233
234         if (match.getInPort() != null) {
235             matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
236             matchEntriesBuilder.setHasMask(false);
237             matchEntriesBuilder.setOxmMatchField(InPort.class);
238             PortNumberMatchEntryBuilder port = new PortNumberMatchEntryBuilder();
239             port.setPortNumber(new PortNumber(match.getInPort()));
240             matchEntriesBuilder.addAugmentation(PortNumberMatchEntry.class, port.build());
241             matchEntriesList.add(matchEntriesBuilder.build());
242         }
243
244         if (match.getInPhyPort() != null) {
245             matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
246             matchEntriesBuilder.setHasMask(false);
247             matchEntriesBuilder.setOxmMatchField(InPhyPort.class);
248             PortNumberMatchEntryBuilder phyPort = new PortNumberMatchEntryBuilder();
249             phyPort.setPortNumber(new PortNumber(match.getInPhyPort()));
250             matchEntriesBuilder.addAugmentation(PortNumberMatchEntry.class, phyPort.build());
251             matchEntriesList.add(matchEntriesBuilder.build());
252         }
253
254         if (match.getMetadata() != null) {
255             matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
256             matchEntriesBuilder.setHasMask(false);
257             matchEntriesBuilder.setOxmMatchField(Metadata.class);
258             addMetadataAugmentation(matchEntriesBuilder, match.getMetadata().getMetadata());
259             if (match.getMetadata().getMetadataMask() != null) {
260                 addMaskAugmentation(matchEntriesBuilder, match.getMetadata().getMetadataMask());
261             }
262             matchEntriesList.add(matchEntriesBuilder.build());
263         }
264
265         if (match.getEthernetMatch() != null) {
266             EthernetMatch ethernetMatch = match.getEthernetMatch();
267             EthernetDestination ethernetDestination = ethernetMatch.getEthernetDestination();
268             if (ethernetDestination != null) {
269                 matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
270                 matchEntriesBuilder.setHasMask(false);
271                 matchEntriesBuilder.setOxmMatchField(EthDst.class);
272                 addMacAddressAugmentation(matchEntriesBuilder, ethernetDestination.getAddress());
273                 if (ethernetDestination.getMask() != null) {
274                     addMaskAugmentation(matchEntriesBuilder, ethernetDestination.getMask());
275                 }
276                 matchEntriesList.add(matchEntriesBuilder.build());
277             }
278
279             EthernetSource ethernetSource = ethernetMatch.getEthernetSource();
280             if (ethernetSource != null) {
281                 matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
282                 matchEntriesBuilder.setHasMask(false);
283                 matchEntriesBuilder.setOxmMatchField(EthSrc.class);
284                 addMacAddressAugmentation(matchEntriesBuilder, ethernetSource.getAddress());
285                 if (ethernetSource.getMask() != null) {
286                     addMaskAugmentation(matchEntriesBuilder, ethernetSource.getMask());
287                 }
288                 matchEntriesList.add(matchEntriesBuilder.build());
289             }
290
291             if (ethernetMatch.getEthernetType() != null) {
292                 matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
293                 matchEntriesBuilder.setHasMask(false);
294                 matchEntriesBuilder.setOxmMatchField(EthType.class);
295                 EthTypeMatchEntryBuilder ethertypeBuilder = new EthTypeMatchEntryBuilder();
296                 ethertypeBuilder.setEthType(new EtherType(ethernetMatch.getEthernetType().getType().getValue()
297                         .intValue()));
298                 matchEntriesBuilder.addAugmentation(EthTypeMatchEntry.class, ethertypeBuilder.build());
299                 matchEntriesList.add(matchEntriesBuilder.build());
300             }
301         }
302
303         VlanMatch vlanMatch = match.getVlanMatch();
304         if (vlanMatch != null) {
305             if (vlanMatch.getVlanId() != null) {
306                 // verify
307                 matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
308                 matchEntriesBuilder.setHasMask(true);
309                 matchEntriesBuilder.setOxmMatchField(VlanVid.class);
310                 VlanVidMatchEntryBuilder vlanVidBuilder = new VlanVidMatchEntryBuilder();
311                 Integer vidEntryValue = vlanMatch.getVlanId().getVlanId().getValue();
312                 vlanVidBuilder.setCfiBit(vidEntryValue != 0);
313                 vlanVidBuilder.setVlanVid(vidEntryValue);
314                 matchEntriesBuilder.addAugmentation(VlanVidMatchEntry.class, vlanVidBuilder.build());
315                 if (vlanMatch.getVlanId().getMask() != null) {
316                     addMaskAugmentation(matchEntriesBuilder, vlanMatch.getVlanId().getMask());
317                 }
318                 matchEntriesList.add(matchEntriesBuilder.build());
319             }
320
321             if (vlanMatch.getVlanPcp() != null) {
322                 matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
323                 matchEntriesBuilder.setHasMask(false);
324                 matchEntriesBuilder.setOxmMatchField(VlanPcp.class);
325                 VlanPcpMatchEntryBuilder vlanPcpBuilder = new VlanPcpMatchEntryBuilder();
326                 vlanPcpBuilder.setVlanPcp(vlanMatch.getVlanPcp().getValue());
327                 matchEntriesBuilder.addAugmentation(VlanVidMatchEntry.class, vlanPcpBuilder.build());
328                 matchEntriesList.add(matchEntriesBuilder.build());
329             }
330         }
331
332         IpMatch ipMatch = match.getIpMatch();
333         if (ipMatch != null) {
334             if (ipMatch.getIpDscp() != null) {
335                 matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
336                 matchEntriesBuilder.setHasMask(false);
337                 matchEntriesBuilder.setOxmMatchField(IpDscp.class);
338                 DscpMatchEntryBuilder dscpBuilder = new DscpMatchEntryBuilder();
339                 dscpBuilder.setDscp(ipMatch.getIpDscp());
340                 matchEntriesBuilder.addAugmentation(DscpMatchEntry.class, dscpBuilder.build());
341                 matchEntriesList.add(matchEntriesBuilder.build());
342             }
343
344             if (ipMatch.getIpEcn() != null) {
345                 matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
346                 matchEntriesBuilder.setHasMask(false);
347                 matchEntriesBuilder.setOxmMatchField(IpDscp.class);
348                 EcnMatchEntryBuilder ecnBuilder = new EcnMatchEntryBuilder();
349                 ecnBuilder.setEcn(ipMatch.getIpEcn());
350                 matchEntriesBuilder.addAugmentation(EcnMatchEntry.class, ecnBuilder.build());
351                 matchEntriesList.add(matchEntriesBuilder.build());
352             }
353
354             if (ipMatch.getIpProto() != null) {
355                 matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
356                 matchEntriesBuilder.setHasMask(false);
357                 matchEntriesBuilder.setOxmMatchField(IpProto.class);
358                 ProtocolNumberMatchEntryBuilder protoNumberBuilder = new ProtocolNumberMatchEntryBuilder();
359                 protoNumberBuilder.setProtocolNumber((short) ipMatch.getIpProto().getIntValue());
360                 matchEntriesBuilder.addAugmentation(ProtocolNumberMatchEntry.class, protoNumberBuilder.build());
361                 matchEntriesList.add(matchEntriesBuilder.build());
362             }
363
364         }
365
366         Layer4Match layer4Match = match.getLayer4Match();
367         if (layer4Match != null) {
368             if (layer4Match instanceof TcpMatch) {
369                 TcpMatch tcpMatch = (TcpMatch) layer4Match;
370                 if (tcpMatch.getTcpSourcePort() != null) {
371                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
372                     matchEntriesBuilder.setHasMask(false);
373                     matchEntriesBuilder.setOxmMatchField(TcpSrc.class);
374                     addPortAugmentation(matchEntriesBuilder, tcpMatch.getTcpSourcePort());
375                     matchEntriesList.add(matchEntriesBuilder.build());
376                 }
377
378                 if (tcpMatch.getTcpDestinationPort() != null) {
379                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
380                     matchEntriesBuilder.setHasMask(false);
381                     matchEntriesBuilder.setOxmMatchField(TcpDst.class);
382                     addPortAugmentation(matchEntriesBuilder, tcpMatch.getTcpDestinationPort());
383                     matchEntriesList.add(matchEntriesBuilder.build());
384                 }
385             }
386
387             else if (layer4Match instanceof UdpMatch) {
388                 UdpMatch udpMatch = (UdpMatch) layer4Match;
389                 if (udpMatch.getUdpSourcePort() != null) {
390                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
391                     matchEntriesBuilder.setHasMask(false);
392                     matchEntriesBuilder.setOxmMatchField(UdpSrc.class);
393                     addPortAugmentation(matchEntriesBuilder, udpMatch.getUdpSourcePort());
394                     matchEntriesList.add(matchEntriesBuilder.build());
395                 }
396
397                 if (udpMatch.getUdpDestinationPort() != null) {
398                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
399                     matchEntriesBuilder.setHasMask(false);
400                     matchEntriesBuilder.setOxmMatchField(UdpDst.class);
401                     addPortAugmentation(matchEntriesBuilder, udpMatch.getUdpDestinationPort());
402                     matchEntriesList.add(matchEntriesBuilder.build());
403                 }
404             }
405
406             else if (layer4Match instanceof SctpMatch) {
407                 SctpMatch sctpMatch = (SctpMatch) layer4Match;
408                 if (sctpMatch.getSctpSourcePort() != null) {
409                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
410                     matchEntriesBuilder.setHasMask(false);
411                     matchEntriesBuilder.setOxmMatchField(SctpSrc.class);
412                     addPortAugmentation(matchEntriesBuilder, sctpMatch.getSctpSourcePort());
413                     matchEntriesList.add(matchEntriesBuilder.build());
414                 }
415
416                 if (sctpMatch.getSctpDestinationPort() != null) {
417                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
418                     matchEntriesBuilder.setHasMask(false);
419                     matchEntriesBuilder.setOxmMatchField(SctpDst.class);
420                     addPortAugmentation(matchEntriesBuilder, sctpMatch.getSctpDestinationPort());
421                     matchEntriesList.add(matchEntriesBuilder.build());
422                 }
423             }
424         }
425
426         Icmpv4Match icmpv4Match = match.getIcmpv4Match();
427         if (icmpv4Match != null) {
428             if (icmpv4Match.getIcmpv4Type() != null) {
429                 matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
430                 matchEntriesBuilder.setHasMask(false);
431                 matchEntriesBuilder.setOxmMatchField(Icmpv4Type.class);
432                 Icmpv4TypeMatchEntryBuilder icmpv4TypeBuilder = new Icmpv4TypeMatchEntryBuilder();
433                 icmpv4TypeBuilder.setIcmpv4Type(icmpv4Match.getIcmpv4Type());
434                 matchEntriesBuilder.addAugmentation(Icmpv4TypeMatchEntry.class, icmpv4TypeBuilder.build());
435                 matchEntriesList.add(matchEntriesBuilder.build());
436             }
437
438             if (icmpv4Match.getIcmpv4Code() != null) {
439                 matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
440                 matchEntriesBuilder.setHasMask(false);
441                 matchEntriesBuilder.setOxmMatchField(Icmpv4Code.class);
442                 Icmpv4CodeMatchEntryBuilder icmpv4CodeBuilder = new Icmpv4CodeMatchEntryBuilder();
443                 icmpv4CodeBuilder.setIcmpv4Code(icmpv4Match.getIcmpv4Code());
444                 matchEntriesBuilder.addAugmentation(Icmpv4CodeMatchEntry.class, icmpv4CodeBuilder.build());
445                 matchEntriesList.add(matchEntriesBuilder.build());
446             }
447         }
448
449         Icmpv6Match icmpv6Match = match.getIcmpv6Match();
450         if (icmpv6Match != null) {
451             if (icmpv6Match.getIcmpv6Type() != null) {
452                 matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
453                 matchEntriesBuilder.setHasMask(false);
454                 matchEntriesBuilder.setOxmMatchField(Icmpv6Type.class);
455                 Icmpv6TypeMatchEntryBuilder icmpv6TypeBuilder = new Icmpv6TypeMatchEntryBuilder();
456                 icmpv6TypeBuilder.setIcmpv6Type(icmpv6Match.getIcmpv6Type());
457                 matchEntriesBuilder.addAugmentation(Icmpv6TypeMatchEntry.class, icmpv6TypeBuilder.build());
458                 matchEntriesList.add(matchEntriesBuilder.build());
459             }
460
461             if (icmpv6Match.getIcmpv6Code() != null) {
462                 matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
463                 matchEntriesBuilder.setHasMask(false);
464                 matchEntriesBuilder.setOxmMatchField(Icmpv6Code.class);
465                 Icmpv6CodeMatchEntryBuilder icmpv6CodeBuilder = new Icmpv6CodeMatchEntryBuilder();
466                 icmpv6CodeBuilder.setIcmpv6Code(icmpv6Match.getIcmpv6Code());
467                 matchEntriesBuilder.addAugmentation(Icmpv6CodeMatchEntry.class, icmpv6CodeBuilder.build());
468                 matchEntriesList.add(matchEntriesBuilder.build());
469             }
470         }
471
472         Layer3Match layer3Match = match.getLayer3Match();
473         if (layer3Match != null) {
474             if (layer3Match instanceof Ipv4Match) {
475                 Ipv4Match ipv4Match = (Ipv4Match) layer3Match;
476                 if (ipv4Match.getIpv4Source() != null) {
477                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
478                     matchEntriesBuilder.setHasMask(false);
479                     matchEntriesBuilder.setOxmMatchField(Ipv4Src.class);
480                     addIpv4PrefixAugmentation(matchEntriesBuilder, ipv4Match.getIpv4Source());
481                     matchEntriesList.add(matchEntriesBuilder.build());
482                 }
483                 if (ipv4Match.getIpv4Destination() != null) {
484                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
485                     matchEntriesBuilder.setHasMask(false);
486                     matchEntriesBuilder.setOxmMatchField(Ipv4Dst.class);
487                     addIpv4PrefixAugmentation(matchEntriesBuilder, ipv4Match.getIpv4Destination());
488                     matchEntriesList.add(matchEntriesBuilder.build());
489                 }
490             }
491
492             else if (layer3Match instanceof ArpMatch) {
493                 ArpMatch arpMatch = (ArpMatch) layer3Match;
494                 if (arpMatch.getArpOp() != null) {
495                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
496                     matchEntriesBuilder.setHasMask(false);
497                     matchEntriesBuilder.setOxmMatchField(ArpOp.class);
498                     OpCodeMatchEntryBuilder opcodeBuilder = new OpCodeMatchEntryBuilder();
499                     opcodeBuilder.setOpCode(arpMatch.getArpOp());
500                     matchEntriesBuilder.addAugmentation(OpCodeMatchEntry.class, opcodeBuilder.build());
501                     matchEntriesList.add(matchEntriesBuilder.build());
502                 }
503
504                 if (arpMatch.getArpSourceTransportAddress() != null) {
505                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
506                     matchEntriesBuilder.setHasMask(false);
507                     matchEntriesBuilder.setOxmMatchField(ArpSpa.class);
508                     addIpv4PrefixAugmentation(matchEntriesBuilder, arpMatch.getArpSourceTransportAddress());
509                     matchEntriesList.add(matchEntriesBuilder.build());
510                 }
511
512                 if (arpMatch.getArpTargetTransportAddress() != null) {
513                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
514                     matchEntriesBuilder.setHasMask(false);
515                     matchEntriesBuilder.setOxmMatchField(ArpTpa.class);
516                     addIpv4PrefixAugmentation(matchEntriesBuilder, arpMatch.getArpTargetTransportAddress());
517                     matchEntriesList.add(matchEntriesBuilder.build());
518                 }
519
520                 ArpSourceHardwareAddress arpSourceHardwareAddress = arpMatch.getArpSourceHardwareAddress();
521                 if (arpSourceHardwareAddress != null) {
522                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
523                     matchEntriesBuilder.setHasMask(false);
524                     matchEntriesBuilder.setOxmMatchField(ArpSha.class);
525                     addMacAddressAugmentation(matchEntriesBuilder, arpSourceHardwareAddress.getAddress());
526                     if (arpSourceHardwareAddress.getMask() != null) {
527                         addMaskAugmentation(matchEntriesBuilder, arpSourceHardwareAddress.getMask());
528                     }
529                     matchEntriesList.add(matchEntriesBuilder.build());
530                 }
531
532                 ArpTargetHardwareAddress arpTargetHardwareAddress = arpMatch.getArpTargetHardwareAddress();
533                 if (arpTargetHardwareAddress != null) {
534                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
535                     matchEntriesBuilder.setHasMask(false);
536                     matchEntriesBuilder.setOxmMatchField(ArpTha.class);
537                     addMacAddressAugmentation(matchEntriesBuilder, arpTargetHardwareAddress.getAddress());
538                     if (arpTargetHardwareAddress.getMask() != null) {
539                         addMaskAugmentation(matchEntriesBuilder, arpTargetHardwareAddress.getMask());
540                     }
541                     matchEntriesList.add(matchEntriesBuilder.build());
542                 }
543             }
544
545             else if (layer3Match instanceof Ipv6Match) {
546                 Ipv6Match ipv6Match = (Ipv6Match) layer3Match;
547                 if (ipv6Match.getIpv6Source() != null) {
548                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
549                     matchEntriesBuilder.setHasMask(false);
550                     matchEntriesBuilder.setOxmMatchField(Ipv6Src.class);
551                     addIpv6PrefixAugmentation(matchEntriesBuilder, ipv6Match.getIpv6Source());
552                     matchEntriesList.add(matchEntriesBuilder.build());
553                 }
554
555                 if (ipv6Match.getIpv6Destination() != null) {
556                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
557                     matchEntriesBuilder.setHasMask(false);
558                     matchEntriesBuilder.setOxmMatchField(Ipv6Dst.class);
559                     addIpv6PrefixAugmentation(matchEntriesBuilder, ipv6Match.getIpv6Destination());
560                     matchEntriesList.add(matchEntriesBuilder.build());
561                 }
562
563                 if (ipv6Match.getIpv6Label() != null) {
564                     // verify
565                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
566                     matchEntriesBuilder.setHasMask(false);
567                     matchEntriesBuilder.setOxmMatchField(Ipv6Flabel.class);
568                     Ipv6FlabelMatchEntryBuilder ipv6FlabelBuilder = new Ipv6FlabelMatchEntryBuilder();
569                     ipv6FlabelBuilder.setIpv6Flabel(ipv6Match.getIpv6Label().getIpv6Flabel());
570                     matchEntriesBuilder.addAugmentation(Ipv6FlabelMatchEntry.class, ipv6FlabelBuilder.build());
571                     if (ipv6Match.getIpv6Label().getFlabelMask() != null) {
572                         addMaskAugmentation(matchEntriesBuilder, ipv6Match.getIpv6Label().getFlabelMask());
573                     }
574                     matchEntriesList.add(matchEntriesBuilder.build());
575                 }
576
577                 if (ipv6Match.getIpv6NdTarget() != null) {
578                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
579                     matchEntriesBuilder.setHasMask(false);
580                     matchEntriesBuilder.setOxmMatchField(Ipv6NdTarget.class);
581                     addIpv6AddressAugmentation(matchEntriesBuilder, ipv6Match.getIpv6NdTarget());
582                     matchEntriesList.add(matchEntriesBuilder.build());
583                 }
584
585                 if (ipv6Match.getIpv6NdSll() != null) {
586                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
587                     matchEntriesBuilder.setHasMask(false);
588                     matchEntriesBuilder.setOxmMatchField(Ipv6NdSll.class);
589                     addMacAddressAugmentation(matchEntriesBuilder, ipv6Match.getIpv6NdSll());
590                     matchEntriesList.add(matchEntriesBuilder.build());
591                 }
592
593                 if (ipv6Match.getIpv6NdTll() != null) {
594                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
595                     matchEntriesBuilder.setHasMask(false);
596                     matchEntriesBuilder.setOxmMatchField(Ipv6NdTll.class);
597                     addMacAddressAugmentation(matchEntriesBuilder, ipv6Match.getIpv6NdTll());
598                     matchEntriesList.add(matchEntriesBuilder.build());
599                 }
600
601                 if (ipv6Match.getIpv6Exthdr() != null) {
602                     // verify
603                     matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
604                     matchEntriesBuilder.setHasMask(false);
605                     matchEntriesBuilder.setOxmMatchField(Ipv6Exthdr.class);
606                     PseudoFieldMatchEntryBuilder pseudoBuilder = new PseudoFieldMatchEntryBuilder();
607                     Integer bitmap = ipv6Match.getIpv6Exthdr();
608                     final Boolean NONEXT = ((bitmap) & (1 << 0)) != 0;
609                     final Boolean ESP = ((bitmap) & (1 << 1)) != 0;
610                     final Boolean AUTH = ((bitmap) & (1 << 2)) != 0;
611                     final Boolean DEST = ((bitmap) & (1 << 3)) != 0;
612                     final Boolean FRAG = ((bitmap) & (1 << 4)) != 0;
613                     final Boolean ROUTER = ((bitmap) & (1 << 5)) != 0;
614                     final Boolean HOP = ((bitmap) & (1 << 6)) != 0;
615                     final Boolean UNREP = ((bitmap) & (1 << 7)) != 0;
616                     final Boolean UNSEQ = ((bitmap) & (1 << 8)) != 0;
617                     pseudoBuilder.setPseudoField(new PseudoField(AUTH, DEST, ESP, FRAG, HOP, NONEXT, ROUTER, UNREP,
618                             UNSEQ));
619                     matchEntriesBuilder.addAugmentation(PseudoFieldMatchEntry.class, pseudoBuilder.build());
620                     addMaskAugmentation(matchEntriesBuilder, ByteBuffer.allocate(2).putInt(bitmap).array());
621                     matchEntriesList.add(matchEntriesBuilder.build());
622                 }
623             }
624         }
625
626         ProtocolMatchFields protocolMatchFields = match.getProtocolMatchFields();
627         if (protocolMatchFields != null) {
628             if (protocolMatchFields.getMplsLabel() != null) {
629                 matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
630                 matchEntriesBuilder.setHasMask(false);
631                 matchEntriesBuilder.setOxmMatchField(MplsLabel.class);
632                 MplsLabelMatchEntryBuilder mplsLabelBuilder = new MplsLabelMatchEntryBuilder();
633                 mplsLabelBuilder.setMplsLabel(protocolMatchFields.getMplsLabel());
634                 matchEntriesBuilder.addAugmentation(MplsLabelMatchEntry.class, mplsLabelBuilder.build());
635                 matchEntriesList.add(matchEntriesBuilder.build());
636             }
637
638             if (protocolMatchFields.getMplsBos() != null) {
639                 matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
640                 matchEntriesBuilder.setHasMask(false);
641                 matchEntriesBuilder.setOxmMatchField(MplsBos.class);
642                 BosMatchEntryBuilder bosBuilder = new BosMatchEntryBuilder();
643                 if (protocolMatchFields.getMplsBos() != 0) {
644                     bosBuilder.setBos(true);
645                 } else {
646                     bosBuilder.setBos(false);
647                 }
648                 matchEntriesBuilder.addAugmentation(BosMatchEntry.class, bosBuilder.build());
649                 matchEntriesList.add(matchEntriesBuilder.build());
650             }
651
652             if (protocolMatchFields.getMplsTc() != null) {
653                 matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
654                 matchEntriesBuilder.setHasMask(false);
655                 matchEntriesBuilder.setOxmMatchField(MplsTc.class);
656                 TcMatchEntryBuilder tcBuilder = new TcMatchEntryBuilder();
657                 tcBuilder.setTc(protocolMatchFields.getMplsTc());
658                 matchEntriesBuilder.addAugmentation(TcMatchEntry.class, tcBuilder.build());
659                 matchEntriesList.add(matchEntriesBuilder.build());
660             }
661
662             if (protocolMatchFields.getPbb() != null) {
663                 matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
664                 // verify
665                 matchEntriesBuilder.setHasMask(false);
666                 matchEntriesBuilder.setOxmMatchField(PbbIsid.class);
667                 IsidMatchEntryBuilder isidBuilder = new IsidMatchEntryBuilder();
668                 isidBuilder.setIsid(protocolMatchFields.getPbb().getPbbIsid());
669                 matchEntriesBuilder.addAugmentation(IsidMatchEntry.class, isidBuilder.build());
670                 if (protocolMatchFields.getPbb().getPbbMask() != null) {
671                     addMaskAugmentation(matchEntriesBuilder, protocolMatchFields.getPbb().getPbbMask());
672                 }
673                 matchEntriesList.add(matchEntriesBuilder.build());
674             }
675         }
676
677         if (match.getTunnel() != null) {
678             matchEntriesBuilder.setOxmClass(OpenflowBasicClass.class);
679             matchEntriesBuilder.setHasMask(false);
680             matchEntriesBuilder.setOxmMatchField(TunnelId.class);
681             addMetadataAugmentation(matchEntriesBuilder, match.getTunnel().getTunnelId());
682             if (match.getTunnel().getTunnelMask() != null) {
683                 addMaskAugmentation(matchEntriesBuilder, match.getTunnel().getTunnelMask());
684             }
685         }
686
687         return matchEntriesList;
688     }
689
690     private static List<Instructions> toInstructions(
691             org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.flow.Instructions instructions,
692             short version) {
693         List<Instructions> instructionsList = new ArrayList<>();
694         InstructionsBuilder instructionBuilder = new InstructionsBuilder();
695
696         for (org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.list.Instruction instruction : instructions
697                 .getInstruction()) {
698             org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.Instruction curInstruction = instruction
699                     .getInstruction();
700             if (curInstruction instanceof GoToTable) {
701                 GoToTable goToTable = (GoToTable) curInstruction;
702                 instructionBuilder
703                         .setType(org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.instruction.rev130731.GotoTable.class);
704                 TableIdInstructionBuilder tableBuilder = new TableIdInstructionBuilder();
705                 tableBuilder.setTableId(goToTable.getTableId());
706                 instructionBuilder.addAugmentation(TableIdInstruction.class, tableBuilder.build());
707             }
708
709             else if (curInstruction instanceof WriteMetadata) {
710                 WriteMetadata writeMetadata = (WriteMetadata) curInstruction;
711                 instructionBuilder
712                         .setType(org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.instruction.rev130731.WriteMetadata.class);
713                 MetadataInstructionBuilder metadataBuilder = new MetadataInstructionBuilder();
714                 metadataBuilder.setMetadata(writeMetadata.getMetadata().toByteArray());
715                 metadataBuilder.setMetadataMask(writeMetadata.getMetadataMask().toByteArray());
716                 instructionBuilder.addAugmentation(MetadataInstruction.class, metadataBuilder.build());
717             }
718
719             else if (curInstruction instanceof WriteActions) {
720                 WriteActions writeActions = (WriteActions) curInstruction;
721                 instructionBuilder
722                         .setType(org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.instruction.rev130731.WriteActions.class);
723                 ActionsInstructionBuilder actionsInstructionBuilder = new ActionsInstructionBuilder();
724                 actionsInstructionBuilder.setActionsList(ActionConvertor.getActionList(writeActions.getAction(),
725                         version));
726                 instructionBuilder.addAugmentation(ActionsInstruction.class, actionsInstructionBuilder.build());
727             }
728
729             else if (curInstruction instanceof ApplyActions) {
730                 ApplyActions applyActions = (ApplyActions) curInstruction;
731                 instructionBuilder
732                         .setType(org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.instruction.rev130731.ApplyActions.class);
733                 ActionsInstructionBuilder actionsInstructionBuilder = new ActionsInstructionBuilder();
734                 actionsInstructionBuilder.setActionsList(ActionConvertor.getActionList(applyActions.getAction(),
735                         version));
736                 instructionBuilder.addAugmentation(ActionsInstruction.class, actionsInstructionBuilder.build());
737             }
738
739             else if (curInstruction instanceof ClearActions) {
740                 ClearActions clearActions = (ClearActions) curInstruction;
741                 instructionBuilder
742                         .setType(org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.instruction.rev130731.ClearActions.class);
743                 ActionsInstructionBuilder actionsInstructionBuilder = new ActionsInstructionBuilder();
744                 actionsInstructionBuilder.setActionsList(ActionConvertor.getActionList(clearActions.getAction(),
745                         version));
746                 instructionBuilder.addAugmentation(ActionsInstruction.class, actionsInstructionBuilder.build());
747             }
748
749             else if (curInstruction instanceof Meter) {
750                 Meter meter = (Meter) curInstruction;
751                 instructionBuilder
752                         .setType(org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.instruction.rev130731.Meter.class);
753                 MeterIdInstructionBuilder meterBuilder = new MeterIdInstructionBuilder();
754                 Long meterId = Long.parseLong(meter.getMeter());
755                 meterBuilder.setMeterId(meterId);
756                 instructionBuilder.addAugmentation(MeterIdInstruction.class, meterBuilder.build());
757             }
758
759             instructionsList.add(instructionBuilder.build());
760         }
761         return instructionsList;
762     }
763
764     private static void addMaskAugmentation(MatchEntriesBuilder builder, byte[] mask) {
765         MaskMatchEntryBuilder maskBuilder = new MaskMatchEntryBuilder();
766         maskBuilder.setMask(mask);
767         builder.addAugmentation(MaskMatchEntry.class, maskBuilder.build());
768         builder.setHasMask(true);
769     }
770
771     private static void addIpv6AddressAugmentation(MatchEntriesBuilder builder, Ipv6Address address) {
772         Ipv6AddressMatchEntryBuilder ipv6AddressBuilder = new Ipv6AddressMatchEntryBuilder();
773         ipv6AddressBuilder.setIpv6Address(address);
774         builder.addAugmentation(Ipv6AddressMatchEntry.class, ipv6AddressBuilder.build());
775     }
776
777     private static void addIpv6PrefixAugmentation(MatchEntriesBuilder builder, Ipv6Prefix address) {
778         // TODO: bug
779         String[] addressParts = address.getValue().split(PREFIX_SEPARATOR);
780         Integer prefix = null;
781         if (addressParts.length == 2) {
782             prefix = Integer.parseInt(addressParts[1]);
783         }
784
785         Ipv6Address ipv6Address = new Ipv6Address(addressParts[0]);
786         Ipv6AddressMatchEntryBuilder ipv6AddressBuilder = new Ipv6AddressMatchEntryBuilder();
787         ipv6AddressBuilder.setIpv6Address(ipv6Address);
788         builder.addAugmentation(Ipv6AddressMatchEntry.class, ipv6AddressBuilder.build());
789         if (prefix != null) {
790             addMaskAugmentation(builder, ByteBuffer.allocate(2).putInt(prefix).array());
791         }
792     }
793
794     private static void addMetadataAugmentation(MatchEntriesBuilder builder, BigInteger metadata) {
795         MetadataMatchEntryBuilder metadataMatchEntry = new MetadataMatchEntryBuilder();
796         metadataMatchEntry.setMetadata(metadata.toByteArray());
797         builder.addAugmentation(MetadataMatchEntry.class, metadataMatchEntry.build());
798     }
799
800     private static void addIpv4PrefixAugmentation(MatchEntriesBuilder builder, Ipv4Prefix address) {
801         String[] addressParts = address.getValue().split(PREFIX_SEPARATOR);
802         Integer prefix = null;
803         if (addressParts.length < 2) {
804             prefix = 0;
805         } else {
806             prefix = Integer.parseInt(addressParts[1]);
807         }
808
809         Ipv4Address ipv4Address = new Ipv4Address(addressParts[0]);
810         Ipv4AddressMatchEntryBuilder ipv4AddressBuilder = new Ipv4AddressMatchEntryBuilder();
811         ipv4AddressBuilder.setIpv4Address(ipv4Address);
812         builder.addAugmentation(Ipv4AddressMatchEntry.class, ipv4AddressBuilder.build());
813         if (prefix != 0) {
814             int mask = 0xffffffff << (32 - prefix);
815             byte[] maskBytes = new byte[4];
816
817             for (int currByte = 3; currByte >= 0; --currByte) {
818                 maskBytes[currByte] = 0;
819                 maskBytes[currByte] |= ((mask >>> 8 * (3 - currByte)) & (0xff));
820             }
821             addMaskAugmentation(builder, maskBytes);
822         }
823     }
824
825     private static void addMacAddressAugmentation(MatchEntriesBuilder builder, MacAddress address) {
826         MacAddressMatchEntryBuilder macAddress = new MacAddressMatchEntryBuilder();
827         macAddress.setMacAddress(address);
828         builder.addAugmentation(MacAddressMatchEntry.class, macAddress.build());
829     }
830
831     private static void addPortAugmentation(MatchEntriesBuilder builder,
832             org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.PortNumber port) {
833         PortMatchEntryBuilder portBuilder = new PortMatchEntryBuilder();
834         portBuilder.setPort(port);
835         builder.addAugmentation(PortMatchEntry.class, portBuilder.build());
836     }
837 }