2 * Copyright (c) 2017 Pantheon Technologies s.r.o. 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
9 package org.opendaylight.openflowplugin.impl.protocol.deserialization.multipart;
11 import com.google.common.collect.ImmutableMap;
12 import io.netty.buffer.ByteBuf;
14 import java.util.Optional;
15 import org.opendaylight.openflowjava.protocol.api.keys.MatchEntryDeserializerKey;
16 import org.opendaylight.openflowjava.protocol.api.util.EncodeConstants;
17 import org.opendaylight.openflowjava.protocol.api.util.OxmMatchConstants;
18 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.ArpOp;
19 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.ArpSha;
20 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.ArpSpa;
21 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.ArpTha;
22 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.ArpTpa;
23 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.EthDst;
24 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.EthSrc;
25 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.Icmpv4Code;
26 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.Icmpv4Type;
27 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.Icmpv6Code;
28 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.Icmpv6Type;
29 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.InPhyPort;
30 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.InPort;
31 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.IpDscp;
32 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.IpEcn;
33 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.IpProto;
34 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.Ipv4Dst;
35 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.Ipv4Src;
36 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.Ipv6Dst;
37 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.Ipv6Exthdr;
38 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.Ipv6Flabel;
39 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.Ipv6NdSll;
40 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.Ipv6NdTarget;
41 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.Ipv6NdTll;
42 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.Ipv6Src;
43 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.MatchField;
44 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.Metadata;
45 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.MplsBos;
46 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.MplsLabel;
47 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.MplsTc;
48 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.PbbIsid;
49 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.SctpDst;
50 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.SctpSrc;
51 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.TcpDst;
52 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.TcpFlags;
53 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.TcpSrc;
54 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.TunnelId;
55 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.UdpDst;
56 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.UdpSrc;
57 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.VlanPcp;
58 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.VlanVid;
59 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.set.field.match.SetFieldMatch;
60 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.set.field.match.SetFieldMatchBuilder;
61 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.set.field.match.SetFieldMatchKey;
63 public class TableFeaturesMatchFieldDeserializer {
66 * Mapping of match entry code to match set field class.
68 private final Map<MatchEntryDeserializerKey, Class<? extends MatchField>> codeToFieldMap = ImmutableMap
69 .<MatchEntryDeserializerKey, Class<? extends MatchField>>builder()
70 .put(new MatchEntryDeserializerKey(
71 EncodeConstants.OF13_VERSION_ID,
72 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
73 OxmMatchConstants.ARP_OP), ArpOp.class)
74 .put(new MatchEntryDeserializerKey(
75 EncodeConstants.OF13_VERSION_ID,
76 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
77 OxmMatchConstants.ARP_SHA), ArpSha.class)
78 .put(new MatchEntryDeserializerKey(
79 EncodeConstants.OF13_VERSION_ID,
80 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
81 OxmMatchConstants.ARP_SPA), ArpSpa.class)
82 .put(new MatchEntryDeserializerKey(
83 EncodeConstants.OF13_VERSION_ID,
84 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
85 OxmMatchConstants.ARP_THA), ArpTha.class)
86 .put(new MatchEntryDeserializerKey(
87 EncodeConstants.OF13_VERSION_ID,
88 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
89 OxmMatchConstants.ARP_TPA), ArpTpa.class)
90 .put(new MatchEntryDeserializerKey(
91 EncodeConstants.OF13_VERSION_ID,
92 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
93 OxmMatchConstants.ETH_DST), EthDst.class)
94 .put(new MatchEntryDeserializerKey(
95 EncodeConstants.OF13_VERSION_ID,
96 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
97 OxmMatchConstants.ETH_SRC), EthSrc.class)
98 .put(new MatchEntryDeserializerKey(
99 EncodeConstants.OF13_VERSION_ID,
100 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
101 OxmMatchConstants.ICMPV4_CODE), Icmpv4Code.class)
102 .put(new MatchEntryDeserializerKey(
103 EncodeConstants.OF13_VERSION_ID,
104 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
105 OxmMatchConstants.ICMPV4_TYPE), Icmpv4Type.class)
106 .put(new MatchEntryDeserializerKey(
107 EncodeConstants.OF13_VERSION_ID,
108 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
109 OxmMatchConstants.ICMPV6_CODE), Icmpv6Code.class)
110 .put(new MatchEntryDeserializerKey(
111 EncodeConstants.OF13_VERSION_ID,
112 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
113 OxmMatchConstants.ICMPV6_TYPE), Icmpv6Type.class)
114 .put(new MatchEntryDeserializerKey(
115 EncodeConstants.OF13_VERSION_ID,
116 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
117 OxmMatchConstants.IN_PHY_PORT), InPhyPort.class)
118 .put(new MatchEntryDeserializerKey(
119 EncodeConstants.OF13_VERSION_ID,
120 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
121 OxmMatchConstants.IN_PORT), InPort.class)
122 .put(new MatchEntryDeserializerKey(
123 EncodeConstants.OF13_VERSION_ID,
124 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
125 OxmMatchConstants.IP_DSCP), IpDscp.class)
126 .put(new MatchEntryDeserializerKey(
127 EncodeConstants.OF13_VERSION_ID,
128 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
129 OxmMatchConstants.IP_ECN), IpEcn.class)
130 .put(new MatchEntryDeserializerKey(
131 EncodeConstants.OF13_VERSION_ID,
132 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
133 OxmMatchConstants.IP_PROTO), IpProto.class)
134 .put(new MatchEntryDeserializerKey(
135 EncodeConstants.OF13_VERSION_ID,
136 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
137 OxmMatchConstants.IPV4_DST), Ipv4Dst.class)
138 .put(new MatchEntryDeserializerKey(
139 EncodeConstants.OF13_VERSION_ID,
140 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
141 OxmMatchConstants.IPV4_SRC), Ipv4Src.class)
142 .put(new MatchEntryDeserializerKey(
143 EncodeConstants.OF13_VERSION_ID,
144 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
145 OxmMatchConstants.IPV6_DST), Ipv6Dst.class)
146 .put(new MatchEntryDeserializerKey(
147 EncodeConstants.OF13_VERSION_ID,
148 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
149 OxmMatchConstants.IPV6_SRC), Ipv6Src.class)
150 .put(new MatchEntryDeserializerKey(
151 EncodeConstants.OF13_VERSION_ID,
152 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
153 OxmMatchConstants.IPV6_EXTHDR), Ipv6Exthdr.class)
154 .put(new MatchEntryDeserializerKey(
155 EncodeConstants.OF13_VERSION_ID,
156 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
157 OxmMatchConstants.IPV6_FLABEL), Ipv6Flabel.class)
158 .put(new MatchEntryDeserializerKey(
159 EncodeConstants.OF13_VERSION_ID,
160 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
161 OxmMatchConstants.IPV6_ND_SLL), Ipv6NdSll.class)
162 .put(new MatchEntryDeserializerKey(
163 EncodeConstants.OF13_VERSION_ID,
164 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
165 OxmMatchConstants.IPV6_ND_TLL), Ipv6NdTll.class)
166 .put(new MatchEntryDeserializerKey(
167 EncodeConstants.OF13_VERSION_ID,
168 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
169 OxmMatchConstants.IPV6_ND_TARGET), Ipv6NdTarget.class)
170 .put(new MatchEntryDeserializerKey(
171 EncodeConstants.OF13_VERSION_ID,
172 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
173 OxmMatchConstants.METADATA), Metadata.class)
174 .put(new MatchEntryDeserializerKey(
175 EncodeConstants.OF13_VERSION_ID,
176 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
177 OxmMatchConstants.MPLS_BOS), MplsBos.class)
178 .put(new MatchEntryDeserializerKey(
179 EncodeConstants.OF13_VERSION_ID,
180 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
181 OxmMatchConstants.MPLS_LABEL), MplsLabel.class)
182 .put(new MatchEntryDeserializerKey(
183 EncodeConstants.OF13_VERSION_ID,
184 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
185 OxmMatchConstants.MPLS_TC), MplsTc.class)
186 .put(new MatchEntryDeserializerKey(
187 EncodeConstants.OF13_VERSION_ID,
188 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
189 OxmMatchConstants.PBB_ISID), PbbIsid.class)
190 .put(new MatchEntryDeserializerKey(
191 EncodeConstants.OF13_VERSION_ID,
192 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
193 OxmMatchConstants.SCTP_DST), SctpDst.class)
194 .put(new MatchEntryDeserializerKey(
195 EncodeConstants.OF13_VERSION_ID,
196 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
197 OxmMatchConstants.SCTP_SRC), SctpSrc.class)
198 .put(new MatchEntryDeserializerKey(
199 EncodeConstants.OF13_VERSION_ID,
200 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
201 OxmMatchConstants.TCP_SRC), TcpSrc.class)
202 .put(new MatchEntryDeserializerKey(
203 EncodeConstants.OF13_VERSION_ID,
204 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
205 OxmMatchConstants.TCP_DST), TcpDst.class)
206 .put(new MatchEntryDeserializerKey(
207 EncodeConstants.OF13_VERSION_ID,
208 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
209 OxmMatchConstants.TUNNEL_ID), TunnelId.class)
210 .put(new MatchEntryDeserializerKey(
211 EncodeConstants.OF13_VERSION_ID,
212 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
213 OxmMatchConstants.UDP_SRC), UdpSrc.class)
214 .put(new MatchEntryDeserializerKey(
215 EncodeConstants.OF13_VERSION_ID,
216 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
217 OxmMatchConstants.UDP_DST), UdpDst.class)
218 .put(new MatchEntryDeserializerKey(
219 EncodeConstants.OF13_VERSION_ID,
220 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
221 OxmMatchConstants.VLAN_PCP), VlanPcp.class)
222 .put(new MatchEntryDeserializerKey(
223 EncodeConstants.OF13_VERSION_ID,
224 OxmMatchConstants.OPENFLOW_BASIC_CLASS,
225 OxmMatchConstants.VLAN_VID), VlanVid.class)
226 .put(new MatchEntryDeserializerKey(
227 EncodeConstants.OF13_VERSION_ID,
228 OxmMatchConstants.EXPERIMENTER_CLASS,
229 OxmMatchConstants.NXM_NX_TCP_FLAG), TcpFlags.class)
233 * Processes match entry header and returns if it have mask, or not.
235 * @param in input buffer
236 * @return SetFieldMatchBuilder with hasMask properly set
238 protected static SetFieldMatchBuilder processHeader(ByteBuf in) {
239 in.skipBytes(EncodeConstants.SIZE_OF_SHORT_IN_BYTES); // skip oxm_class
240 boolean hasMask = (in.readUnsignedByte() & 1) != 0;
241 in.skipBytes(EncodeConstants.SIZE_OF_BYTE_IN_BYTES); // skip match entry length
243 return new SetFieldMatchBuilder()
244 .setHasMask(hasMask);
248 * Deserialize match field if deserializer supports it, otherwise returns empty optional.
250 * @param message input buffer
251 * @return set field match
253 public Optional<SetFieldMatch> deserialize(ByteBuf message) {
254 int oxmClass = message.getUnsignedShort(message.readerIndex());
255 int oxmField = message.getUnsignedByte(message.readerIndex()
256 + EncodeConstants.SIZE_OF_SHORT_IN_BYTES) >>> 1;
259 if (oxmClass == EncodeConstants.EXPERIMENTER_VALUE) {
260 expId = message.getUnsignedInt(message.readerIndex() + EncodeConstants.SIZE_OF_SHORT_IN_BYTES
261 + 2 * EncodeConstants.SIZE_OF_BYTE_IN_BYTES);
264 final MatchEntryDeserializerKey key =
265 new MatchEntryDeserializerKey(EncodeConstants.OF13_VERSION_ID, oxmClass, oxmField);
267 key.setExperimenterId(expId);
270 .ofNullable(codeToFieldMap.get(key))
271 .map(clazz -> processHeader(message)
272 .setKey(new SetFieldMatchKey(clazz))