2 * Copyright (c) 2016 Cisco Systems, Inc. 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.openflowplugin.openflow.md.core.sal.convertor.match;
10 import java.util.Collection;
11 import java.util.Collections;
13 import org.opendaylight.openflowplugin.api.openflow.md.util.OpenflowVersion;
14 import org.opendaylight.openflowplugin.openflow.md.core.sal.convertor.common.Convertor;
15 import org.opendaylight.openflowplugin.openflow.md.core.sal.convertor.data.VersionDatapathIdConvertorData;
16 import org.opendaylight.openflowplugin.openflow.md.util.ActionUtil;
17 import org.opendaylight.openflowplugin.openflow.md.util.InventoryDataServiceUtil;
18 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.Dscp;
19 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.IetfInetUtil;
20 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.Ipv4Prefix;
21 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.flow.MatchBuilder;
22 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.ethernet.match.fields.EthernetDestinationBuilder;
23 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.ethernet.match.fields.EthernetSourceBuilder;
24 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.ethernet.match.fields.EthernetTypeBuilder;
25 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.EthernetMatchBuilder;
26 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.Icmpv4MatchBuilder;
27 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.IpMatchBuilder;
28 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.VlanMatchBuilder;
29 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.layer._3.match.Ipv4MatchBuilder;
30 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.layer._4.match.TcpMatchBuilder;
31 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.layer._4.match.UdpMatchBuilder;
32 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.vlan.match.fields.VlanIdBuilder;
33 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.oxm.rev150225.match.v10.grouping.MatchV10;
34 import org.opendaylight.yangtools.yang.common.Uint16;
35 import org.opendaylight.yangtools.yang.common.Uint32;
36 import org.opendaylight.yangtools.yang.common.Uint64;
37 import org.opendaylight.yangtools.yang.common.Uint8;
40 * Converts Openflow 1.0 specific flow match to MD-SAL format flow match.
46 * VersionDatapathIdConvertorData data = new VersionDatapathIdConvertorData(version);
47 * data.setDatapathId(datapathId);
48 * Optional<MatchBuilder> salMatch = convertorManager.convert(ofMatchV10, data);
52 public class MatchV10ResponseConvertor extends Convertor<MatchV10, MatchBuilder, VersionDatapathIdConvertorData> {
53 private static final short PROTO_TCP = 6;
54 private static final short PROTO_UDP = 17;
55 private static final short PROTO_ICMPV4 = 1;
56 private static final String NO_IP = "0.0.0.0/0";
57 private static final Set<Class<?>> TYPES = Collections.singleton(MatchV10.class);
60 public Collection<Class<?>> getTypes() {
65 public MatchBuilder convert(final MatchV10 source, final VersionDatapathIdConvertorData datapathIdConvertorData) {
66 MatchBuilder matchBuilder = new MatchBuilder();
67 EthernetMatchBuilder ethMatchBuilder = new EthernetMatchBuilder();
68 VlanMatchBuilder vlanMatchBuilder = new VlanMatchBuilder();
69 Ipv4MatchBuilder ipv4MatchBuilder = new Ipv4MatchBuilder();
70 IpMatchBuilder ipMatchBuilder = new IpMatchBuilder();
71 OpenflowVersion ofVersion = OpenflowVersion.get(datapathIdConvertorData.getVersion());
72 Uint64 datapathid = datapathIdConvertorData.getDatapathId();
74 if (!source.getWildcards().getINPORT() && source.getInPort() != null) {
75 matchBuilder.setInPort(InventoryDataServiceUtil.nodeConnectorIdfromDatapathPortNo(datapathid,
76 Uint32.valueOf(source.getInPort()), ofVersion));
79 if (!source.getWildcards().getDLSRC() && source.getDlSrc() != null) {
80 EthernetSourceBuilder ethSrcBuilder = new EthernetSourceBuilder();
81 ethSrcBuilder.setAddress(source.getDlSrc());
82 ethMatchBuilder.setEthernetSource(ethSrcBuilder.build());
83 matchBuilder.setEthernetMatch(ethMatchBuilder.build());
85 if (!source.getWildcards().getDLDST() && source.getDlDst() != null) {
86 EthernetDestinationBuilder ethDstBuilder = new EthernetDestinationBuilder();
87 ethDstBuilder.setAddress(source.getDlDst());
88 ethMatchBuilder.setEthernetDestination(ethDstBuilder.build());
89 matchBuilder.setEthernetMatch(ethMatchBuilder.build());
91 if (!source.getWildcards().getDLTYPE() && source.getDlType() != null) {
92 EthernetTypeBuilder ethTypeBuilder = new EthernetTypeBuilder();
93 ethTypeBuilder.setType(new org.opendaylight.yang.gen.v1.urn.opendaylight.l2.types.rev130827.EtherType(
94 Uint32.valueOf(source.getDlType())));
95 ethMatchBuilder.setEthernetType(ethTypeBuilder.build());
96 matchBuilder.setEthernetMatch(ethMatchBuilder.build());
98 if (!source.getWildcards().getDLVLAN() && source.getDlVlan() != null) {
99 Uint16 vlanId = source.getDlVlan();
100 if (vlanId.toJava() == 0xffff) {
101 vlanId = Uint16.ZERO;
104 vlanMatchBuilder.setVlanId(new VlanIdBuilder()
105 .setVlanId(new org.opendaylight.yang.gen.v1.urn.opendaylight.l2.types.rev130827.VlanId(vlanId))
106 .setVlanIdPresent(!Uint16.ZERO.equals(vlanId))
108 matchBuilder.setVlanMatch(vlanMatchBuilder.build());
110 if (!source.getWildcards().getDLVLANPCP() && source.getDlVlanPcp() != null) {
111 vlanMatchBuilder.setVlanPcp(new org.opendaylight.yang.gen.v1.urn.opendaylight.l2.types.rev130827.VlanPcp(
112 source.getDlVlanPcp()));
113 matchBuilder.setVlanMatch(vlanMatchBuilder.build());
115 if (!source.getWildcards().getDLTYPE() && source.getNwSrc() != null) {
116 final Ipv4Prefix prefix;
117 if (source.getNwSrcMask() != null) {
118 prefix = IetfInetUtil.ipv4PrefixFor(source.getNwSrc(), source.getNwSrcMask().toJava());
120 //Openflow Spec : 1.3.2
121 //An all-one-bits oxm_mask is equivalent to specifying 0 for oxm_hasmask and omitting oxm_mask.
122 // So when user specify 32 as a mast, switch omit that mast and we get null as a mask in flow
123 // statistics response.
124 prefix = IetfInetUtil.ipv4PrefixFor(source.getNwSrc());
126 if (!NO_IP.equals(prefix.getValue())) {
127 ipv4MatchBuilder.setIpv4Source(prefix);
128 matchBuilder.setLayer3Match(ipv4MatchBuilder.build());
131 if (!source.getWildcards().getDLTYPE() && source.getNwDst() != null) {
132 final Ipv4Prefix prefix;
133 if (source.getNwDstMask() != null) {
134 prefix = IetfInetUtil.ipv4PrefixFor(source.getNwDst(), source.getNwDstMask().toJava());
136 //Openflow Spec : 1.3.2
137 //An all-one-bits oxm_mask is equivalent to specifying 0 for oxm_hasmask and omitting oxm_mask.
138 // So when user specify 32 as a mast, switch omit that mast and we get null as a mask in flow
139 // statistics response.
140 prefix = IetfInetUtil.ipv4PrefixFor(source.getNwDst());
142 if (!NO_IP.equals(prefix.getValue())) {
143 ipv4MatchBuilder.setIpv4Destination(prefix);
144 matchBuilder.setLayer3Match(ipv4MatchBuilder.build());
147 if (!source.getWildcards().getNWPROTO() && source.getNwProto() != null) {
148 Uint8 nwProto = source.getNwProto();
149 ipMatchBuilder.setIpProtocol(nwProto);
150 matchBuilder.setIpMatch(ipMatchBuilder.build());
152 int proto = nwProto.intValue();
153 if (proto == PROTO_TCP) {
154 TcpMatchBuilder tcpMatchBuilder = new TcpMatchBuilder();
155 boolean hasTcp = false;
156 if (!source.getWildcards().getTPSRC() && source.getTpSrc() != null) {
157 tcpMatchBuilder.setTcpSourcePort(new org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf
158 .inet.types.rev130715.PortNumber(source.getTpSrc()));
161 if (!source.getWildcards().getTPDST() && source.getTpDst() != null) {
162 tcpMatchBuilder.setTcpDestinationPort(new org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang
163 .ietf.inet.types.rev130715.PortNumber(source.getTpDst()));
168 matchBuilder.setLayer4Match(tcpMatchBuilder.build());
170 } else if (proto == PROTO_UDP) {
171 UdpMatchBuilder udpMatchBuilder = new UdpMatchBuilder();
172 boolean hasUdp = false;
173 if (!source.getWildcards().getTPSRC() && source.getTpSrc() != null) {
174 udpMatchBuilder.setUdpSourcePort(new org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf
175 .inet.types.rev130715.PortNumber(source.getTpSrc()));
178 if (!source.getWildcards().getTPDST() && source.getTpDst() != null) {
179 udpMatchBuilder.setUdpDestinationPort(new org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang
180 .ietf.inet.types.rev130715.PortNumber(source.getTpDst()));
185 matchBuilder.setLayer4Match(udpMatchBuilder.build());
187 } else if (proto == PROTO_ICMPV4) {
188 Icmpv4MatchBuilder icmpv4MatchBuilder = new Icmpv4MatchBuilder();
189 boolean hasIcmpv4 = false;
190 if (!source.getWildcards().getTPSRC()) {
191 Uint16 type = source.getTpSrc();
193 icmpv4MatchBuilder.setIcmpv4Type(type.toUint8());
197 if (!source.getWildcards().getTPDST()) {
198 Uint16 code = source.getTpDst();
200 icmpv4MatchBuilder.setIcmpv4Code(code.toUint8());
206 matchBuilder.setIcmpv4Match(icmpv4MatchBuilder.build());
210 if (!source.getWildcards().getNWTOS() && source.getNwTos() != null) {
211 ipMatchBuilder.setIpDscp(new Dscp(ActionUtil.tosToDscp(source.getNwTos())));
212 matchBuilder.setIpMatch(ipMatchBuilder.build());