blob: 39694b4ef273577fe3c53c90f01dcf727911668c [file] [log] [blame]
Thomas Vachuska781d18b2014-10-27 10:31:25 -07001/*
Thomas Vachuska4f1a60c2014-10-28 13:39:07 -07002 * Copyright 2014 Open Networking Laboratory
Thomas Vachuska781d18b2014-10-27 10:31:25 -07003 *
Thomas Vachuska4f1a60c2014-10-28 13:39:07 -07004 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
Thomas Vachuska781d18b2014-10-27 10:31:25 -07007 *
Thomas Vachuska4f1a60c2014-10-28 13:39:07 -07008 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
Thomas Vachuska781d18b2014-10-27 10:31:25 -070015 */
Brian O'Connorabafb502014-12-02 22:26:20 -080016package org.onosproject.provider.of.flow.impl;
Jonathan Hart86e59352014-10-22 10:42:16 -070017
Thomas Vachuskaf4df0052015-01-06 12:30:11 -080018import org.onlab.packet.Ip4Address;
19import org.onosproject.net.PortNumber;
Brian O'Connorabafb502014-12-02 22:26:20 -080020import org.onosproject.net.flow.FlowRule;
21import org.onosproject.net.flow.TrafficTreatment;
22import org.onosproject.net.flow.instructions.Instruction;
23import org.onosproject.net.flow.instructions.Instructions.OutputInstruction;
24import org.onosproject.net.flow.instructions.L2ModificationInstruction;
25import org.onosproject.net.flow.instructions.L2ModificationInstruction.ModEtherInstruction;
26import org.onosproject.net.flow.instructions.L2ModificationInstruction.ModVlanIdInstruction;
27import org.onosproject.net.flow.instructions.L2ModificationInstruction.ModVlanPcpInstruction;
28import org.onosproject.net.flow.instructions.L3ModificationInstruction;
29import org.onosproject.net.flow.instructions.L3ModificationInstruction.ModIPInstruction;
Jonathan Hart86e59352014-10-22 10:42:16 -070030import org.projectfloodlight.openflow.protocol.OFFactory;
31import org.projectfloodlight.openflow.protocol.OFFlowAdd;
32import org.projectfloodlight.openflow.protocol.OFFlowDelete;
33import org.projectfloodlight.openflow.protocol.OFFlowMod;
34import org.projectfloodlight.openflow.protocol.OFFlowModFlags;
35import org.projectfloodlight.openflow.protocol.action.OFAction;
Thomas Vachuskaf4df0052015-01-06 12:30:11 -080036import org.projectfloodlight.openflow.protocol.action.OFActionOutput;
Jonathan Hart86e59352014-10-22 10:42:16 -070037import org.projectfloodlight.openflow.protocol.match.Match;
38import org.projectfloodlight.openflow.types.IPv4Address;
39import org.projectfloodlight.openflow.types.MacAddress;
40import org.projectfloodlight.openflow.types.OFBufferId;
41import org.projectfloodlight.openflow.types.OFPort;
42import org.projectfloodlight.openflow.types.U64;
43import org.projectfloodlight.openflow.types.VlanPcp;
44import org.projectfloodlight.openflow.types.VlanVid;
45import org.slf4j.Logger;
46import org.slf4j.LoggerFactory;
47
Thomas Vachuskaf4df0052015-01-06 12:30:11 -080048import java.util.Collections;
49import java.util.LinkedList;
50import java.util.List;
51import java.util.Optional;
52
Jonathan Hart86e59352014-10-22 10:42:16 -070053/**
54 * Flow mod builder for OpenFlow 1.0.
55 */
56public class FlowModBuilderVer10 extends FlowModBuilder {
57
alshabib10580802015-02-18 18:30:33 -080058 private final Logger log = LoggerFactory.getLogger(getClass());
Thomas Vachuskaf4df0052015-01-06 12:30:11 -080059 private static final int OFPCML_NO_BUFFER = 0xffff;
Jonathan Hart86e59352014-10-22 10:42:16 -070060
61 private final TrafficTreatment treatment;
62
63 /**
64 * Constructor for a flow mod builder for OpenFlow 1.0.
65 *
66 * @param flowRule the flow rule to transform into a flow mod
67 * @param factory the OpenFlow factory to use to build the flow mod
Pavlin Radoslavov119fd5c2014-11-25 19:08:19 -080068 * @param xid the transaction ID
Jonathan Hart86e59352014-10-22 10:42:16 -070069 */
Brian O'Connor427a1762014-11-19 18:40:32 -080070 protected FlowModBuilderVer10(FlowRule flowRule,
71 OFFactory factory, Optional<Long> xid) {
72 super(flowRule, factory, xid);
Jonathan Hart86e59352014-10-22 10:42:16 -070073
74 this.treatment = flowRule.treatment();
75 }
76
77 @Override
78 public OFFlowAdd buildFlowAdd() {
79 Match match = buildMatch();
80 List<OFAction> actions = buildActions();
81
82 long cookie = flowRule().id().value();
83
alshabib4785eec2014-12-04 16:45:45 -080084
Jonathan Hart86e59352014-10-22 10:42:16 -070085 OFFlowAdd fm = factory().buildFlowAdd()
Brian O'Connor427a1762014-11-19 18:40:32 -080086 .setXid(xid)
Jonathan Hart86e59352014-10-22 10:42:16 -070087 .setCookie(U64.of(cookie))
88 .setBufferId(OFBufferId.NO_BUFFER)
89 .setActions(actions)
90 .setMatch(match)
91 .setFlags(Collections.singleton(OFFlowModFlags.SEND_FLOW_REM))
92 .setPriority(flowRule().priority())
93 .build();
94
95 return fm;
96 }
97
98 @Override
99 public OFFlowMod buildFlowMod() {
100 Match match = buildMatch();
101 List<OFAction> actions = buildActions();
102
103 long cookie = flowRule().id().value();
104
Jonathan Hart86e59352014-10-22 10:42:16 -0700105 OFFlowMod fm = factory().buildFlowModify()
Brian O'Connor427a1762014-11-19 18:40:32 -0800106 .setXid(xid)
Jonathan Hart86e59352014-10-22 10:42:16 -0700107 .setCookie(U64.of(cookie))
108 .setBufferId(OFBufferId.NO_BUFFER)
109 .setActions(actions)
110 .setMatch(match)
111 .setFlags(Collections.singleton(OFFlowModFlags.SEND_FLOW_REM))
112 .setPriority(flowRule().priority())
113 .build();
114
115 return fm;
116 }
117
118 @Override
119 public OFFlowDelete buildFlowDel() {
120 Match match = buildMatch();
Jonathan Hart86e59352014-10-22 10:42:16 -0700121
122 long cookie = flowRule().id().value();
123
124 OFFlowDelete fm = factory().buildFlowDelete()
Brian O'Connor427a1762014-11-19 18:40:32 -0800125 .setXid(xid)
Jonathan Hart86e59352014-10-22 10:42:16 -0700126 .setCookie(U64.of(cookie))
127 .setBufferId(OFBufferId.NO_BUFFER)
Jonathan Hart86e59352014-10-22 10:42:16 -0700128 .setMatch(match)
129 .setFlags(Collections.singleton(OFFlowModFlags.SEND_FLOW_REM))
130 .setPriority(flowRule().priority())
131 .build();
132
133 return fm;
134 }
135
136 private List<OFAction> buildActions() {
137 List<OFAction> acts = new LinkedList<>();
138 if (treatment == null) {
139 return acts;
140 }
141 for (Instruction i : treatment.instructions()) {
142 switch (i.type()) {
143 case DROP:
144 log.warn("Saw drop action; assigning drop action");
145 return new LinkedList<>();
146 case L2MODIFICATION:
147 acts.add(buildL2Modification(i));
148 break;
149 case L3MODIFICATION:
150 acts.add(buildL3Modification(i));
151 break;
152 case OUTPUT:
153 OutputInstruction out = (OutputInstruction) i;
Thomas Vachuskaf4df0052015-01-06 12:30:11 -0800154 OFActionOutput.Builder action = factory().actions().buildOutput()
155 .setPort(OFPort.of((int) out.port().toLong()));
156 if (out.port().equals(PortNumber.CONTROLLER)) {
157 action.setMaxLen(OFPCML_NO_BUFFER);
158 }
159 acts.add(action.build());
Jonathan Hart86e59352014-10-22 10:42:16 -0700160 break;
161 case L0MODIFICATION:
162 case GROUP:
163 log.warn("Instruction type {} not supported with protocol version {}",
164 i.type(), factory().getVersion());
165 break;
166 default:
167 log.warn("Instruction type {} not yet implemented.", i.type());
168 }
169 }
170
171 return acts;
172 }
173
174 private OFAction buildL3Modification(Instruction i) {
175 L3ModificationInstruction l3m = (L3ModificationInstruction) i;
176 ModIPInstruction ip;
Pavlin Radoslavov23e398d2014-11-05 15:17:57 -0800177 Ip4Address ip4;
Jonathan Hart86e59352014-10-22 10:42:16 -0700178 switch (l3m.subtype()) {
Pavlin Radoslavovfebe82c2015-02-11 19:08:15 -0800179 case IPV4_SRC:
Jonathan Hart86e59352014-10-22 10:42:16 -0700180 ip = (ModIPInstruction) i;
Pavlin Radoslavov23e398d2014-11-05 15:17:57 -0800181 ip4 = ip.ip().getIp4Address();
182 return factory().actions().setNwSrc(IPv4Address.of(ip4.toInt()));
Pavlin Radoslavovfebe82c2015-02-11 19:08:15 -0800183 case IPV4_DST:
184 ip = (ModIPInstruction) i;
185 ip4 = ip.ip().getIp4Address();
186 return factory().actions().setNwDst(IPv4Address.of(ip4.toInt()));
Jonathan Hart86e59352014-10-22 10:42:16 -0700187 default:
188 log.warn("Unimplemented action type {}.", l3m.subtype());
189 break;
190 }
191 return null;
192 }
193
194 private OFAction buildL2Modification(Instruction i) {
195 L2ModificationInstruction l2m = (L2ModificationInstruction) i;
196 ModEtherInstruction eth;
197 switch (l2m.subtype()) {
198 case ETH_DST:
199 eth = (ModEtherInstruction) l2m;
200 return factory().actions().setDlDst(MacAddress.of(eth.mac().toLong()));
201 case ETH_SRC:
202 eth = (ModEtherInstruction) l2m;
203 return factory().actions().setDlSrc(MacAddress.of(eth.mac().toLong()));
204 case VLAN_ID:
205 ModVlanIdInstruction vlanId = (ModVlanIdInstruction) l2m;
Ray Milkey78081052014-11-05 10:38:12 -0800206 return factory().actions().setVlanVid(VlanVid.ofVlan(vlanId.vlanId().toShort()));
Jonathan Hart86e59352014-10-22 10:42:16 -0700207 case VLAN_PCP:
208 ModVlanPcpInstruction vlanPcp = (ModVlanPcpInstruction) l2m;
209 return factory().actions().setVlanPcp(VlanPcp.of(vlanPcp.vlanPcp()));
alshabibab21b2d2015-03-04 18:35:33 -0800210 case STRIP_VLAN:
211 return factory().actions().stripVlan();
Jonathan Hart86e59352014-10-22 10:42:16 -0700212 default:
213 log.warn("Unimplemented action type {}.", l2m.subtype());
214 break;
215 }
216 return null;
217 }
218
219}