2 * Copyright (C) 2013 Red Hat, Inc.
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 * Authors : Madhu Venugopal, Brent Salisbury
10 package org.opendaylight.ovsdb.neutron.provider;
12 import java.math.BigInteger;
13 import java.net.InetAddress;
14 import java.util.ArrayList;
15 import java.util.List;
18 import java.util.concurrent.ExecutionException;
19 import java.util.concurrent.Future;
21 import org.opendaylight.controller.md.sal.common.api.TransactionStatus;
22 import org.opendaylight.controller.md.sal.common.api.data.DataModification;
23 import org.opendaylight.controller.networkconfig.neutron.NeutronNetwork;
24 import org.opendaylight.controller.sal.binding.api.data.DataBrokerService;
25 import org.opendaylight.controller.sal.core.Node;
26 import org.opendaylight.controller.sal.utils.HexEncode;
27 import org.opendaylight.controller.sal.utils.ServiceHelper;
28 import org.opendaylight.controller.sal.utils.Status;
29 import org.opendaylight.controller.sal.utils.StatusCode;
30 import org.opendaylight.controller.switchmanager.ISwitchManager;
31 import org.opendaylight.ovsdb.lib.notation.OvsDBMap;
32 import org.opendaylight.ovsdb.lib.notation.OvsDBSet;
33 import org.opendaylight.ovsdb.lib.notation.UUID;
34 import org.opendaylight.ovsdb.lib.table.Bridge;
35 import org.opendaylight.ovsdb.lib.table.Interface;
36 import org.opendaylight.ovsdb.lib.table.Port;
37 import org.opendaylight.ovsdb.neutron.AdminConfigManager;
38 import org.opendaylight.ovsdb.neutron.IMDSALConsumer;
39 import org.opendaylight.ovsdb.neutron.InternalNetworkManager;
40 import org.opendaylight.ovsdb.neutron.TenantNetworkManager;
41 import org.opendaylight.ovsdb.plugin.IConnectionServiceInternal;
42 import org.opendaylight.ovsdb.plugin.OVSDBConfigService;
43 import org.opendaylight.ovsdb.plugin.StatusWithUuid;
44 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.Ipv4Prefix;
45 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.PortNumber;
46 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.Uri;
47 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev100924.MacAddress;
48 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.DecNwTtlCaseBuilder;
49 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.DropActionCaseBuilder;
50 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.OutputActionCase;
51 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.OutputActionCaseBuilder;
52 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.SetFieldCaseBuilder;
53 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.SetNwDstActionCaseBuilder;
54 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.SetNwSrcActionCaseBuilder;
55 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.SetVlanIdActionCaseBuilder;
56 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.StripVlanActionCaseBuilder;
57 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.dec.nw.ttl._case.DecNwTtl;
58 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.dec.nw.ttl._case.DecNwTtlBuilder;
59 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.drop.action._case.DropAction;
60 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.drop.action._case.DropActionBuilder;
61 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.output.action._case.OutputActionBuilder;
62 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.set.field._case.SetFieldBuilder;
63 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.set.nw.dst.action._case.SetNwDstActionBuilder;
64 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.set.nw.src.action._case.SetNwSrcActionBuilder;
65 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.set.vlan.id.action._case.SetVlanIdActionBuilder;
66 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.strip.vlan.action._case.StripVlanAction;
67 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.action.strip.vlan.action._case.StripVlanActionBuilder;
68 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.list.Action;
69 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.list.ActionBuilder;
70 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.action.list.ActionKey;
71 import org.opendaylight.yang.gen.v1.urn.opendaylight.action.types.rev131112.address.address.Ipv4Builder;
72 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowCapableNode;
73 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowId;
74 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.Table;
75 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.TableKey;
76 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.Flow;
77 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.FlowBuilder;
78 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.FlowKey;
79 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.flow.Instructions;
80 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.flow.InstructionsBuilder;
81 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.flow.MatchBuilder;
82 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.ApplyActionsCase;
83 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.ApplyActionsCaseBuilder;
84 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.GoToTableCaseBuilder;
85 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.apply.actions._case.ApplyActionsBuilder;
86 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.instruction.go.to.table._case.GoToTableBuilder;
87 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.list.Instruction;
88 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.list.InstructionBuilder;
89 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.list.InstructionKey;
90 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.NodeConnectorId;
91 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.NodeId;
92 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.Nodes;
93 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.NodeBuilder;
94 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.NodeKey;
95 import org.opendaylight.yang.gen.v1.urn.opendaylight.l2.types.rev130827.EtherType;
96 import org.opendaylight.yang.gen.v1.urn.opendaylight.l2.types.rev130827.VlanId;
97 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.arp.match.fields.ArpSourceHardwareAddressBuilder;
98 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.arp.match.fields.ArpTargetHardwareAddressBuilder;
99 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.ethernet.match.fields.EthernetDestinationBuilder;
100 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.ethernet.match.fields.EthernetSourceBuilder;
101 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.ethernet.match.fields.EthernetTypeBuilder;
102 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.EthernetMatchBuilder;
103 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.Icmpv4MatchBuilder;
104 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.IpMatchBuilder;
105 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.TunnelBuilder;
106 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.VlanMatchBuilder;
107 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.layer._3.match.ArpMatchBuilder;
108 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.layer._3.match.Ipv4MatchBuilder;
109 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.layer._4.match.TcpMatchBuilder;
110 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.match.layer._4.match.UdpMatchBuilder;
111 import org.opendaylight.yang.gen.v1.urn.opendaylight.model.match.types.rev131026.vlan.match.fields.VlanIdBuilder;
112 import org.opendaylight.yangtools.yang.binding.DataObject;
113 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
114 import org.opendaylight.yangtools.yang.common.RpcResult;
115 import org.slf4j.Logger;
116 import org.slf4j.LoggerFactory;
122 class OF13ProviderManager extends ProviderNetworkManager {
123 private static final Logger logger = LoggerFactory.getLogger(OF13ProviderManager.class);
124 private DataBrokerService dataBrokerService;
125 private static final short TABLE_0_DEFAULT_INGRESS = 0;
126 private static final short TABLE_1_ISOLATE_TENANT = 10;
127 private static final short TABLE_2_LOCAL_FORWARD = 20;
130 public boolean hasPerTenantTunneling() {
134 private Status getTunnelReadinessStatus (Node node, String tunnelKey) {
135 InetAddress srcTunnelEndPoint = AdminConfigManager.getManager().getTunnelEndPoint(node);
136 if (srcTunnelEndPoint == null) {
137 logger.error("Tunnel Endpoint not configured for Node {}", node);
138 return new Status(StatusCode.NOTFOUND, "Tunnel Endpoint not configured for "+ node);
141 if (!InternalNetworkManager.getManager().isInternalNetworkNeutronReady(node)) {
142 logger.error(node+" is not Overlay ready");
143 return new Status(StatusCode.NOTACCEPTABLE, node+" is not Overlay ready");
146 if (!TenantNetworkManager.getManager().isTenantNetworkPresentInNode(node, tunnelKey)) {
147 logger.debug(node+" has no VM corresponding to segment "+ tunnelKey);
148 return new Status(StatusCode.NOTACCEPTABLE, node+" has no VM corresponding to segment "+ tunnelKey);
150 return new Status(StatusCode.SUCCESS);
153 private String getTunnelName(String tunnelType, InetAddress dst) {
154 return tunnelType+"-"+dst.getHostAddress();
157 private boolean isTunnelPresent(Node node, String tunnelName, String bridgeUUID) throws Exception {
158 OVSDBConfigService ovsdbTable = (OVSDBConfigService)ServiceHelper.getGlobalInstance(OVSDBConfigService.class, this);
159 Bridge bridge = (Bridge)ovsdbTable.getRow(node, Bridge.NAME.getName(), bridgeUUID);
160 if (bridge != null) {
161 Set<UUID> ports = bridge.getPorts();
162 for (UUID portUUID : ports) {
163 Port port = (Port)ovsdbTable.getRow(node, Port.NAME.getName(), portUUID.toString());
164 if (port != null && port.getName().equalsIgnoreCase(tunnelName)) return true;
170 private Status addTunnelPort (Node node, String tunnelType, InetAddress src, InetAddress dst) {
172 String bridgeUUID = null;
173 String tunnelBridgeName = AdminConfigManager.getManager().getIntegrationBridgeName();
174 OVSDBConfigService ovsdbTable = (OVSDBConfigService)ServiceHelper.getGlobalInstance(OVSDBConfigService.class, this);
175 Map<String, org.opendaylight.ovsdb.lib.table.Table<?>> bridgeTable = ovsdbTable.getRows(node, Bridge.NAME.getName());
176 if (bridgeTable != null) {
177 for (String uuid : bridgeTable.keySet()) {
178 Bridge bridge = (Bridge)bridgeTable.get(uuid);
179 if (bridge.getName().equals(tunnelBridgeName)) {
185 if (bridgeUUID == null) {
186 logger.error("Could not find Bridge {} in {}", tunnelBridgeName, node);
187 return new Status(StatusCode.NOTFOUND, "Could not find "+tunnelBridgeName+" in "+node);
189 String portName = getTunnelName(tunnelType, dst);
191 if (this.isTunnelPresent(node, portName, bridgeUUID)) {
192 logger.trace("Tunnel {} is present in {} of {}", portName, tunnelBridgeName, node);
193 return new Status(StatusCode.SUCCESS);
196 Port tunnelPort = new Port();
197 tunnelPort.setName(portName);
198 StatusWithUuid statusWithUuid = ovsdbTable.insertRow(node, Port.NAME.getName(), bridgeUUID, tunnelPort);
199 if (!statusWithUuid.isSuccess()) {
200 logger.error("Failed to insert Tunnel port {} in {}", portName, bridgeUUID);
201 return statusWithUuid;
204 String tunnelPortUUID = statusWithUuid.getUuid().toString();
205 String interfaceUUID = null;
207 while ((interfaceUUID == null) && (timeout > 0)) {
208 tunnelPort = (Port)ovsdbTable.getRow(node, Port.NAME.getName(), tunnelPortUUID);
209 OvsDBSet<UUID> interfaces = tunnelPort.getInterfaces();
210 if (interfaces == null || interfaces.size() == 0) {
211 // Wait for the OVSDB update to sync up the Local cache.
216 interfaceUUID = interfaces.toArray()[0].toString();
217 Interface intf = (Interface)ovsdbTable.getRow(node, Interface.NAME.getName(), interfaceUUID);
218 if (intf == null) interfaceUUID = null;
221 if (interfaceUUID == null) {
222 logger.error("Cannot identify Tunnel Interface for port {}/{}", portName, tunnelPortUUID);
223 return new Status(StatusCode.INTERNALERROR);
226 Interface tunInterface = new Interface();
227 tunInterface.setType(tunnelType);
228 OvsDBMap<String, String> options = new OvsDBMap<String, String>();
229 options.put("key", "flow");
230 options.put("local_ip", src.getHostAddress());
231 options.put("remote_ip", dst.getHostAddress());
232 tunInterface.setOptions(options);
233 Status status = ovsdbTable.updateRow(node, Interface.NAME.getName(), tunnelPortUUID, interfaceUUID, tunInterface);
234 logger.debug("Tunnel {} add status : {}", tunInterface, status);
236 } catch (Exception e) {
237 logger.error("Exception in addTunnelPort", e);
238 return new Status(StatusCode.INTERNALERROR);
242 private void programLocalBridgeRules(Node node, Long dpid, String segmentationId, String attachedMac, long localPort) {
246 * Match: VM sMac and Local Ingress Port
247 * Action:Action: Set Tunnel ID and GOTO Local Table (5)
250 writeLocalInPort(dpid, TABLE_0_DEFAULT_INGRESS, TABLE_1_ISOLATE_TENANT, segmentationId, localPort, attachedMac);
255 * Match: Drop any remaining Ingress Local VM Packets
256 * Action: Drop w/ a low priority
259 writeDropSrcIface(dpid, localPort);
264 * Match: Match TunID and Destination DL/dMAC Addr
265 * Action: Output Port
266 * table=2,tun_id=0x5,dl_dst=00:00:00:00:00:01 actions=output:2
269 writeLocalUcastOut(dpid, TABLE_2_LOCAL_FORWARD, segmentationId, localPort, attachedMac);
274 * Match: Tunnel ID and dMAC (::::FF:FF)
275 * table=2,priority=16384,tun_id=0x5,dl_dst=ff:ff:ff:ff:ff:ff \
276 * actions=output:2,3,4,5
279 writeLocalBcastOut(dpid, TABLE_2_LOCAL_FORWARD, segmentationId, localPort);
282 * TODO : Optimize the following 2 writes to be restricted only for the very first port known in a segment.
287 * Match: Any remaining Ingress Local VM Packets
288 * Action: Drop w/ a low priority
289 * -------------------------------------------
290 * table=1,priority=8192,tun_id=0x5 actions=goto_table:2
293 writeTunnelMiss(dpid, TABLE_1_ISOLATE_TENANT, TABLE_2_LOCAL_FORWARD, segmentationId);
298 * Match: Any Remaining Flows w/a TunID
299 * Action: Drop w/ a low priority
300 * table=2,priority=8192,tun_id=0x5 actions=drop
303 writeLocalTableMiss(dpid, TABLE_2_LOCAL_FORWARD, segmentationId);
306 private void programLocalIngressTunnelBridgeRules(Node node, Long dpid, String segmentationId, String attachedMac, long tunnelOFPort, long localPort) {
310 * Match: Ingress Port, Tunnel ID
311 * Action: GOTO Local Table (10)
314 writeTunnelIn(dpid, TABLE_0_DEFAULT_INGRESS, TABLE_2_LOCAL_FORWARD, segmentationId, tunnelOFPort);
319 * Match: Match Tunnel ID and L2 ::::FF:FF Flooding
320 * Action: Flood to selected destination TEPs
321 * -------------------------------------------
322 * table=1,priority=16384,tun_id=0x5,dl_dst=ff:ff:ff:ff:ff:ff \
323 * actions=output:10,output:11,goto_table:2
326 writeTunnelFloodOut(dpid, TABLE_1_ISOLATE_TENANT, TABLE_2_LOCAL_FORWARD, segmentationId, tunnelOFPort);
330 private void programRemoteEgressTunnelBridgeRules(Node node, Long dpid, String segmentationId, String attachedMac, long tunnelOFPort, long localPort) {
334 * Match: Drop any remaining Ingress Local VM Packets
335 * Action: Drop w/ a low priority
336 * -------------------------------------------
337 * table=1,tun_id=0x5,dl_dst=00:00:00:00:00:08 \
338 * actions=output:11,goto_table:2
341 writeTunnelOut(dpid, TABLE_1_ISOLATE_TENANT, TABLE_2_LOCAL_FORWARD, segmentationId, tunnelOFPort, attachedMac);
344 private Long getIntegrationBridgeOFDPID (Node node) {
346 String bridgeName = AdminConfigManager.getManager().getIntegrationBridgeName();
347 String brIntId = this.getInternalBridgeUUID(node, bridgeName);
348 if (brIntId == null) {
349 logger.error("Unable to spot Bridge Identifier for {} in {}", bridgeName, node);
353 OVSDBConfigService ovsdbTable = (OVSDBConfigService) ServiceHelper.getGlobalInstance(OVSDBConfigService.class, this);
354 Bridge bridge = (Bridge) ovsdbTable.getRow(node, Bridge.NAME.getName(), brIntId);
355 Set<String> dpids = bridge.getDatapath_id();
356 if (dpids == null || dpids.size() == 0) return 0L;
357 return Long.valueOf(HexEncode.stringToLong((String) dpids.toArray()[0]));
358 } catch (Exception e) {
359 logger.error("Error finding Integration Bridge's OF DPID", e);
363 private void programLocalRules (String tunnelType, String segmentationId, Node node, Interface intf) {
365 Long dpid = this.getIntegrationBridgeOFDPID(node);
367 logger.debug("Openflow Datapath-ID not set for the integration bridge in {}", node);
371 Set<BigInteger> of_ports = intf.getOfport();
372 if (of_ports == null || of_ports.size() <= 0) {
373 logger.error("Could NOT Identify OF value for port {} on {}", intf.getName(), node);
376 long localPort = ((BigInteger)of_ports.toArray()[0]).longValue();
378 Map<String, String> externalIds = intf.getExternal_ids();
379 if (externalIds == null) {
380 logger.error("No external_ids seen in {}", intf);
384 String attachedMac = externalIds.get(TenantNetworkManager.EXTERNAL_ID_VM_MAC);
385 if (attachedMac == null) {
386 logger.error("No AttachedMac seen in {}", intf);
390 programLocalBridgeRules(node, dpid, segmentationId, attachedMac, localPort);
391 } catch (Exception e) {
392 logger.error("Exception in programming Local Rules for "+intf+" on "+node, e);
396 private void programTunnelRules (String tunnelType, String segmentationId, InetAddress dst, Node node,
397 Interface intf, boolean local) {
400 Long dpid = this.getIntegrationBridgeOFDPID(node);
402 logger.debug("Openflow Datapath-ID not set for the integration bridge in {}", node);
405 OVSDBConfigService ovsdbTable = (OVSDBConfigService) ServiceHelper.getGlobalInstance(OVSDBConfigService.class, this);
407 Set<BigInteger> of_ports = intf.getOfport();
408 if (of_ports == null || of_ports.size() <= 0) {
409 logger.error("Could NOT Identify OF value for port {} on {}", intf.getName(), node);
412 long localPort = ((BigInteger)of_ports.toArray()[0]).longValue();
414 Map<String, String> externalIds = intf.getExternal_ids();
415 if (externalIds == null) {
416 logger.error("No external_ids seen in {}", intf);
420 String attachedMac = externalIds.get(TenantNetworkManager.EXTERNAL_ID_VM_MAC);
421 if (attachedMac == null) {
422 logger.error("No AttachedMac seen in {}", intf);
426 Map<String, org.opendaylight.ovsdb.lib.table.Table<?>> intfs = ovsdbTable.getRows(node, Interface.NAME.getName());
428 for (org.opendaylight.ovsdb.lib.table.Table<?> row : intfs.values()) {
429 Interface tunIntf = (Interface)row;
430 if (tunIntf.getName().equals(this.getTunnelName(tunnelType, dst))) {
431 of_ports = tunIntf.getOfport();
432 if (of_ports == null || of_ports.size() <= 0) {
433 logger.error("Could NOT Identify Tunnel port {} on {}", tunIntf.getName(), node);
436 long tunnelOFPort = ((BigInteger)of_ports.toArray()[0]).longValue();
438 if (tunnelOFPort == -1) {
439 logger.error("Could NOT Identify Tunnel port {} -> OF ({}) on {}", tunIntf.getName(), tunnelOFPort, node);
442 logger.debug("Identified Tunnel port {} -> OF ({}) on {}", tunIntf.getName(), tunnelOFPort, node);
445 programRemoteEgressTunnelBridgeRules(node, dpid, segmentationId, attachedMac, tunnelOFPort, localPort);
447 programLocalIngressTunnelBridgeRules(node, dpid, segmentationId, attachedMac, tunnelOFPort, localPort);
452 } catch (Exception e) {
458 public Status handleInterfaceUpdate(String tunnelType, String tunnelKey, Node srcNode, Interface intf) {
459 ISwitchManager switchManager = (ISwitchManager) ServiceHelper.getInstance(ISwitchManager.class, "default", this);
460 if (switchManager == null) {
461 logger.error("Unable to identify SwitchManager");
463 Long dpid = this.getIntegrationBridgeOFDPID(srcNode);
465 logger.debug("Openflow Datapath-ID not set for the integration bridge in {}", srcNode);
466 return new Status(StatusCode.NOTFOUND);
468 Set<Node> ofNodes = switchManager.getNodes();
469 boolean ofNodeFound = false;
470 if (ofNodes != null) {
471 for (Node ofNode : ofNodes) {
472 if (ofNode.toString().contains(dpid+"")) {
473 logger.debug("Identified the Openflow node via toString {}", ofNode);
479 logger.error("Unable to find any Node from SwitchManager");
482 logger.error("Unable to find OF Node for {} with update {} on node {}", dpid, intf, srcNode);
483 return new Status(StatusCode.NOTFOUND);
487 IConnectionServiceInternal connectionService = (IConnectionServiceInternal)ServiceHelper.getGlobalInstance(IConnectionServiceInternal.class, this);
488 List<Node> nodes = connectionService.getNodes();
489 nodes.remove(srcNode);
490 this.programLocalRules(tunnelType, tunnelKey, srcNode, intf);
492 for (Node dstNode : nodes) {
493 InetAddress src = AdminConfigManager.getManager().getTunnelEndPoint(srcNode);
494 InetAddress dst = AdminConfigManager.getManager().getTunnelEndPoint(dstNode);
495 Status status = addTunnelPort(srcNode, tunnelType, src, dst);
496 if (status.isSuccess()) {
497 this.programTunnelRules(tunnelType, tunnelKey, dst, srcNode, intf, true);
499 addTunnelPort(dstNode, tunnelType, dst, src);
500 if (status.isSuccess()) {
501 this.programTunnelRules(tunnelType, tunnelKey, src, dstNode, intf, false);
505 return new Status(StatusCode.SUCCESS);
508 private Status triggerInterfaceUpdates(Node node) {
510 OVSDBConfigService ovsdbTable = (OVSDBConfigService)ServiceHelper.getGlobalInstance(OVSDBConfigService.class, this);
511 Map<String, org.opendaylight.ovsdb.lib.table.Table<?>> intfs = ovsdbTable.getRows(node, Interface.NAME.getName());
513 for (org.opendaylight.ovsdb.lib.table.Table<?> row : intfs.values()) {
514 Interface intf = (Interface)row;
515 NeutronNetwork network = TenantNetworkManager.getManager().getTenantNetworkForInterface(intf);
516 logger.debug("Trigger Interface update for {}", intf);
517 if (network != null) {
518 this.handleInterfaceUpdate(network.getProviderNetworkType(), network.getProviderSegmentationID(), node, intf);
522 } catch (Exception e) {
523 logger.error("Error Triggering the lost interface updates for "+ node, e);
524 return new Status(StatusCode.INTERNALERROR, e.getLocalizedMessage());
526 return new Status(StatusCode.SUCCESS);
529 public Status handleInterfaceUpdate(String tunnelType, String tunnelKey) {
530 // TODO Auto-generated method stub
535 public Status handleInterfaceDelete(String tunnelType, String tunnelKey, Node source, Interface intf,
536 boolean isLastInstanceOnNode) {
537 // TODO Auto-generated method stub
542 public void initializeFlowRules(Node node) {
543 this.initializeFlowRules(node, AdminConfigManager.getManager().getIntegrationBridgeName());
544 this.triggerInterfaceUpdates(node);
551 private void initializeFlowRules(Node node, String bridgeName) {
552 Long dpid = this.getIntegrationBridgeOFDPID(node);
554 logger.debug("Openflow Datapath-ID not set for the integration bridge in {}", node);
561 * Match: LLDP (0x88CCL)
562 * Action: Packet_In to Controller Reserved Port
569 * Create an LLDP Flow Rule to encapsulate into
570 * a packet_in that is sent to the controller
571 * for topology handling.
572 * Match: Ethertype 0x88CCL
573 * Action: Punt to Controller in a Packet_In msg
576 private void writeLLDPRule(Long dpidLong) {
578 String nodeName = "openflow:" + dpidLong;
579 EtherType etherType = new EtherType(0x88CCL);
581 MatchBuilder matchBuilder = new MatchBuilder();
582 NodeBuilder nodeBuilder = createNodeBuilder(nodeName);
583 FlowBuilder flowBuilder = new FlowBuilder();
585 // Create Match(es) and Set them in the FlowBuilder Object
586 flowBuilder.setMatch(createEtherTypeMatch(matchBuilder, etherType).build());
588 // Create the OF Actions and Instructions
589 InstructionBuilder ib = new InstructionBuilder();
590 InstructionsBuilder isb = new InstructionsBuilder();
592 // Instructions List Stores Individual Instructions
593 List<Instruction> instructions = new ArrayList<Instruction>();
595 // Call the InstructionBuilder Methods Containing Actions
596 createSendToControllerInstructions(ib);
598 ib.setKey(new InstructionKey(0));
599 instructions.add(ib.build());
601 // Add InstructionBuilder to the Instruction(s)Builder List
602 isb.setInstruction(instructions);
604 // Add InstructionsBuilder to FlowBuilder
605 flowBuilder.setInstructions(isb.build());
607 String flowId = "LLDP";
608 flowBuilder.setId(new FlowId(flowId));
609 FlowKey key = new FlowKey(new FlowId(flowId));
610 flowBuilder.setBarrier(true);
611 flowBuilder.setTableId((short) 0);
612 flowBuilder.setKey(key);
613 flowBuilder.setFlowName(flowId);
614 flowBuilder.setHardTimeout(0);
615 flowBuilder.setIdleTimeout(0);
616 writeFlow(flowBuilder, nodeBuilder);
620 * (Table:0) Ingress Tunnel Traffic
621 * Match: OpenFlow InPort and Tunnel ID
622 * Action: GOTO Local Table (10)
623 * table=0,tun_id=0x5,in_port=10, actions=goto_table:2
626 private void writeTunnelIn(Long dpidLong, Short writeTable, Short goToTableId, String segmentationId, Long ofPort) {
628 String nodeName = "openflow:" + dpidLong;
630 BigInteger tunnelId = new BigInteger(segmentationId);
631 MatchBuilder matchBuilder = new MatchBuilder();
632 NodeBuilder nodeBuilder = createNodeBuilder(nodeName);
633 FlowBuilder flowBuilder = new FlowBuilder();
635 // Create Match(es) and Set them in the FlowBuilder Object
636 flowBuilder.setMatch(createTunnelIDMatch(matchBuilder, tunnelId).build());
637 flowBuilder.setMatch(createInPortMatch(matchBuilder, dpidLong, ofPort).build());
639 // Create the OF Actions and Instructions
640 InstructionBuilder ib = new InstructionBuilder();
641 InstructionsBuilder isb = new InstructionsBuilder();
643 // Instructions List Stores Individual Instructions
644 List<Instruction> instructions = new ArrayList<Instruction>();
646 // Call the InstructionBuilder Methods Containing Actions
647 createGotoTableInstructions(ib, goToTableId);
649 ib.setKey(new InstructionKey(0));
650 instructions.add(ib.build());
652 // Add InstructionBuilder to the Instruction(s)Builder List
653 isb.setInstruction(instructions);
655 // Add InstructionsBuilder to FlowBuilder
656 flowBuilder.setInstructions(isb.build());
658 String flowId = "TunnelIn_"+segmentationId+"_"+ofPort;
659 // Add Flow Attributes
660 flowBuilder.setId(new FlowId(flowId));
661 FlowKey key = new FlowKey(new FlowId(flowId));
662 flowBuilder.setStrict(true);
663 flowBuilder.setBarrier(false);
664 flowBuilder.setTableId(writeTable);
665 flowBuilder.setKey(key);
666 flowBuilder.setFlowName(flowId);
667 flowBuilder.setHardTimeout(0);
668 flowBuilder.setIdleTimeout(0);
669 writeFlow(flowBuilder, nodeBuilder);
673 * (Table:0) Egress VM Traffic Towards TEP
674 * Match: Destination Ethernet Addr and OpenFlow InPort
675 * Instruction: Set TunnelID and GOTO Table Tunnel Table (n)
676 * table=0,in_port=2,dl_src=00:00:00:00:00:01 \
677 * actions=set_field:5->tun_id,goto_table=1"
680 private void writeLocalInPort(Long dpidLong, Short writeTable, Short goToTableId, String segmentationId, Long inPort, String attachedMac) {
682 String nodeName = "openflow:" + dpidLong;
684 MatchBuilder matchBuilder = new MatchBuilder();
685 NodeBuilder nodeBuilder = createNodeBuilder(nodeName);
686 FlowBuilder flowBuilder = new FlowBuilder();
688 // Create the OF Match using MatchBuilder
689 flowBuilder.setMatch(createEthSrcMatch(matchBuilder, new MacAddress(attachedMac)).build());
690 // TODO Broken In_Port Match
691 flowBuilder.setMatch(createInPortMatch(matchBuilder, dpidLong, inPort).build());
693 String flowId = "LocalMac_"+segmentationId+"_"+inPort+"_"+attachedMac;
694 // Add Flow Attributes
695 flowBuilder.setId(new FlowId(flowId));
696 FlowKey key = new FlowKey(new FlowId(flowId));
697 flowBuilder.setStrict(true);
698 flowBuilder.setBarrier(false);
699 flowBuilder.setTableId(writeTable);
700 flowBuilder.setKey(key);
701 flowBuilder.setFlowName(flowId);
702 flowBuilder.setHardTimeout(0);
703 flowBuilder.setIdleTimeout(0);
705 // Instantiate the Builders for the OF Actions and Instructions
706 InstructionBuilder ib = new InstructionBuilder();
707 InstructionsBuilder isb = new InstructionsBuilder();
709 // Instructions List Stores Individual Instructions
710 List<Instruction> instructions = new ArrayList<Instruction>();
712 // GOTO Instuctions Need to be added first to the List
713 createGotoTableInstructions(ib, goToTableId);
715 ib.setKey(new InstructionKey(0));
716 instructions.add(ib.build());
717 // TODO Broken SetTunID
718 createSetTunnelIdInstructions(ib, new BigInteger(segmentationId));
720 ib.setKey(new InstructionKey(1));
721 instructions.add(ib.build());
723 // Add InstructionBuilder to the Instruction(s)Builder List
724 isb.setInstruction(instructions);
726 // Add InstructionsBuilder to FlowBuilder
727 flowBuilder.setInstructions(isb.build());
729 writeFlow(flowBuilder, nodeBuilder);
733 * (Table:0) Drop frames sourced from a VM that do not
734 * match the associated MAC address of the local VM.
735 * Match: Low priority anything not matching the VM SMAC
737 * table=0,priority=16384,in_port=1 actions=drop"
740 private void writeDropSrcIface(Long dpidLong, Long inPort) {
742 String nodeName = "openflow:" + dpidLong;
744 MatchBuilder matchBuilder = new MatchBuilder();
745 NodeBuilder nodeBuilder = createNodeBuilder(nodeName);
746 FlowBuilder flowBuilder = new FlowBuilder();
748 // Create the OF Match using MatchBuilder
749 flowBuilder.setMatch(createInPortMatch(matchBuilder, dpidLong, inPort).build());
751 // Instantiate the Builders for the OF Actions and Instructions
752 InstructionBuilder ib = new InstructionBuilder();
753 InstructionsBuilder isb = new InstructionsBuilder();
755 // Instructions List Stores Individual Instructions
756 List<Instruction> instructions = new ArrayList<Instruction>();
758 // Call the InstructionBuilder Methods Containing Actions
759 createDropInstructions(ib);
761 ib.setKey(new InstructionKey(0));
762 instructions.add(ib.build());
764 // Add InstructionBuilder to the Instruction(s)Builder List
765 isb.setInstruction(instructions);
767 // Add InstructionsBuilder to FlowBuilder
768 flowBuilder.setInstructions(isb.build());
770 String flowId = "DropFilter_"+inPort;
771 // Add Flow Attributes
772 flowBuilder.setId(new FlowId(flowId));
773 FlowKey key = new FlowKey(new FlowId(flowId));
774 flowBuilder.setStrict(true);
775 flowBuilder.setBarrier(false);
776 flowBuilder.setTableId((short) 0);
777 flowBuilder.setKey(key);
778 flowBuilder.setFlowName(flowId);
779 flowBuilder.setPriority(8192);
780 flowBuilder.setHardTimeout(0);
781 flowBuilder.setIdleTimeout(0);
782 writeFlow(flowBuilder, nodeBuilder);
786 * (Table:1) Egress Tunnel Traffic
787 * Match: Destination Ethernet Addr and Local InPort
788 * Instruction: Set TunnelID and GOTO Table Tunnel Table (n)
789 * table=1,tun_id=0x5,dl_dst=00:00:00:00:00:08 \
790 * actions=output:10,goto_table:2"
793 private void writeTunnelOut(Long dpidLong, Short writeTable, Short goToTableId, String segmentationId , Long OFPortOut, String attachedMac) {
795 String nodeName = "openflow:" + dpidLong;
797 MatchBuilder matchBuilder = new MatchBuilder();
798 NodeBuilder nodeBuilder = createNodeBuilder(nodeName);
799 FlowBuilder flowBuilder = new FlowBuilder();
801 // Create the OF Match using MatchBuilder
802 flowBuilder.setMatch(createTunnelIDMatch(matchBuilder, new BigInteger(segmentationId)).build());
803 flowBuilder.setMatch(createDestEthMatch(matchBuilder, new MacAddress(attachedMac), null).build());
805 String flowId = "TunnelOut_"+segmentationId+"_"+OFPortOut+"_"+attachedMac;
806 // Add Flow Attributes
807 flowBuilder.setId(new FlowId(flowId));
808 FlowKey key = new FlowKey(new FlowId(flowId));
809 flowBuilder.setStrict(true);
810 flowBuilder.setBarrier(false);
811 flowBuilder.setTableId(writeTable);
812 flowBuilder.setKey(key);
813 flowBuilder.setFlowName(flowId);
814 flowBuilder.setHardTimeout(0);
815 flowBuilder.setIdleTimeout(0);
816 // Instantiate the Builders for the OF Actions and Instructions
817 InstructionBuilder ib = new InstructionBuilder();
818 InstructionsBuilder isb = new InstructionsBuilder();
820 // Instructions List Stores Individual Instructions
821 List<Instruction> instructions = new ArrayList<Instruction>();
824 createGotoTableInstructions(ib, goToTableId);
826 ib.setKey(new InstructionKey(0));
827 instructions.add(ib.build());
828 // Set the Output Port/Iface
829 createOutputPortInstructions(ib, dpidLong, OFPortOut);
831 ib.setKey(new InstructionKey(1));
832 instructions.add(ib.build());
834 // Add InstructionBuilder to the Instruction(s)Builder List
835 isb.setInstruction(instructions);
837 // Add InstructionsBuilder to FlowBuilder
838 flowBuilder.setInstructions(isb.build());
840 writeFlow(flowBuilder, nodeBuilder);
844 * (Table:1) Egress Tunnel Traffic
845 * Match: Destination Ethernet Addr and Local InPort
846 * Instruction: Set TunnelID and GOTO Table Tunnel Table (n)
847 * table=1,priority=16384,tun_id=0x5,dl_dst=ff:ff:ff:ff:ff:ff \
848 * actions=output:10,output:11,goto_table:2
851 private void writeTunnelFloodOut(Long dpidLong, Short writeTable, Short localTable, String segmentationId, Long OFPortOut) {
853 String nodeName = "openflow:" + dpidLong;
855 MatchBuilder matchBuilder = new MatchBuilder();
856 NodeBuilder nodeBuilder = createNodeBuilder(nodeName);
857 FlowBuilder flowBuilder = new FlowBuilder();
859 // Create the OF Match using MatchBuilder
861 flowBuilder.setMatch(createTunnelIDMatch(matchBuilder, new BigInteger(segmentationId)).build());
864 flowBuilder.setMatch(createDestEthMatch(matchBuilder, new MacAddress("01:00:00:00:00:00"), new MacAddress("01:00:00:00:00:00")).build());
866 String flowId = "TunnelFloodOut_"+segmentationId;
867 // Add Flow Attributes
868 flowBuilder.setId(new FlowId(flowId));
869 FlowKey key = new FlowKey(new FlowId(flowId));
870 flowBuilder.setBarrier(true);
871 flowBuilder.setTableId(writeTable);
872 flowBuilder.setKey(key);
873 flowBuilder.setPriority(16384);
874 flowBuilder.setFlowName(flowId);
875 flowBuilder.setHardTimeout(0);
876 flowBuilder.setIdleTimeout(0);
878 Flow flow = this.getFlow(flowBuilder, nodeBuilder);
879 // Instantiate the Builders for the OF Actions and Instructions
880 InstructionBuilder ib = new InstructionBuilder();
881 InstructionsBuilder isb = new InstructionsBuilder();
882 List<Instruction> instructions = new ArrayList<Instruction>();
883 List<Instruction> existingInstructions = null;
885 Instructions ins = flow.getInstructions();
887 existingInstructions = ins.getInstruction();
891 createGotoTableInstructions(ib, localTable);
893 ib.setKey(new InstructionKey(0));
894 instructions.add(ib.build());
895 // Set the Output Port/Iface
896 createOutputPortInstructions(ib, dpidLong, OFPortOut, existingInstructions);
898 ib.setKey(new InstructionKey(1));
899 instructions.add(ib.build());
901 // Add InstructionBuilder to the Instruction(s)Builder List
902 isb.setInstruction(instructions);
904 // Add InstructionsBuilder to FlowBuilder
905 flowBuilder.setInstructions(isb.build());
907 writeFlow(flowBuilder, nodeBuilder);
911 * (Table:1) Table Drain w/ Catch All
913 * Action: GOTO Local Table (10)
914 * table=2,priority=8192,tun_id=0x5 actions=drop
917 private void writeTunnelMiss(Long dpidLong, Short writeTable, Short goToTableId, String segmentationId) {
919 String nodeName = "openflow:" + dpidLong;
921 MatchBuilder matchBuilder = new MatchBuilder();
922 NodeBuilder nodeBuilder = createNodeBuilder(nodeName);
923 FlowBuilder flowBuilder = new FlowBuilder();
925 // Create Match(es) and Set them in the FlowBuilder Object
926 flowBuilder.setMatch(createTunnelIDMatch(matchBuilder, new BigInteger(segmentationId)).build());
928 // Create the OF Actions and Instructions
929 InstructionBuilder ib = new InstructionBuilder();
930 InstructionsBuilder isb = new InstructionsBuilder();
932 // Instructions List Stores Individual Instructions
933 List<Instruction> instructions = new ArrayList<Instruction>();
935 // Call the InstructionBuilder Methods Containing Actions
936 createGotoTableInstructions(ib, goToTableId);
938 ib.setKey(new InstructionKey(0));
939 instructions.add(ib.build());
941 // Add InstructionBuilder to the Instruction(s)Builder List
942 isb.setInstruction(instructions);
944 // Add InstructionsBuilder to FlowBuilder
945 flowBuilder.setInstructions(isb.build());
947 String flowId = "TunnelMiss_"+segmentationId;
948 // Add Flow Attributes
949 flowBuilder.setId(new FlowId(flowId));
950 FlowKey key = new FlowKey(new FlowId(flowId));
951 flowBuilder.setStrict(true);
952 flowBuilder.setBarrier(false);
953 flowBuilder.setTableId(writeTable);
954 flowBuilder.setKey(key);
955 flowBuilder.setPriority(8192);
956 flowBuilder.setFlowName(flowId);
957 flowBuilder.setHardTimeout(0);
958 flowBuilder.setIdleTimeout(0);
959 writeFlow(flowBuilder, nodeBuilder);
963 * (Table:1) Local Broadcast Flood
964 * Match: Tunnel ID and dMAC
965 * Action: Output Port
966 * table=2,tun_id=0x5,dl_dst=00:00:00:00:00:01 actions=output:2
969 private void writeLocalUcastOut(Long dpidLong, Short writeTable, String segmentationId, Long localPort, String attachedMac) {
971 String nodeName = "openflow:" + dpidLong;
973 MatchBuilder matchBuilder = new MatchBuilder();
974 NodeBuilder nodeBuilder = createNodeBuilder(nodeName);
975 FlowBuilder flowBuilder = new FlowBuilder();
977 // Create the OF Match using MatchBuilder
978 flowBuilder.setMatch(createTunnelIDMatch(matchBuilder, new BigInteger(segmentationId)).build());
979 flowBuilder.setMatch(createDestEthMatch(matchBuilder, new MacAddress(attachedMac), null).build());
981 String flowId = "UcastOut_"+segmentationId+"_"+localPort+"_"+attachedMac;
982 // Add Flow Attributes
983 flowBuilder.setId(new FlowId(flowId));
984 FlowKey key = new FlowKey(new FlowId(flowId));
985 flowBuilder.setStrict(true);
986 flowBuilder.setBarrier(false);
987 flowBuilder.setTableId(writeTable);
988 flowBuilder.setKey(key);
989 flowBuilder.setFlowName(flowId);
990 flowBuilder.setHardTimeout(0);
991 flowBuilder.setIdleTimeout(0);
993 // Instantiate the Builders for the OF Actions and Instructions
994 InstructionBuilder ib = new InstructionBuilder();
995 InstructionsBuilder isb = new InstructionsBuilder();
997 // Instructions List Stores Individual Instructions
998 List<Instruction> instructions = new ArrayList<Instruction>();
1000 // Set the Output Port/Iface
1001 createOutputPortInstructions(ib, dpidLong, localPort);
1003 ib.setKey(new InstructionKey(0));
1004 instructions.add(ib.build());
1006 // Add InstructionBuilder to the Instruction(s)Builder List
1007 isb.setInstruction(instructions);
1009 // Add InstructionsBuilder to FlowBuilder
1010 flowBuilder.setInstructions(isb.build());
1011 writeFlow(flowBuilder, nodeBuilder);
1015 * (Table:1) Local Broadcast Flood
1016 * Match: Tunnel ID and dMAC (::::FF:FF)
1017 * table=2,priority=16384,tun_id=0x5,dl_dst=ff:ff:ff:ff:ff:ff \
1018 * actions=output:2,3,4,5
1021 private void writeLocalBcastOut(Long dpidLong, Short writeTable, String segmentationId, Long localPort) {
1023 String nodeName = "openflow:" + dpidLong;
1025 MatchBuilder matchBuilder = new MatchBuilder();
1026 NodeBuilder nodeBuilder = createNodeBuilder(nodeName);
1027 FlowBuilder flowBuilder = new FlowBuilder();
1029 // Create the OF Match using MatchBuilder
1030 flowBuilder.setMatch(createTunnelIDMatch(matchBuilder, new BigInteger(segmentationId)).build());
1031 flowBuilder.setMatch(createDestEthMatch(matchBuilder, new MacAddress("01:00:00:00:00:00"), new MacAddress("01:00:00:00:00:00")).build());
1033 String flowId = "BcastOut_"+segmentationId;
1034 // Add Flow Attributes
1035 flowBuilder.setId(new FlowId(flowId));
1036 FlowKey key = new FlowKey(new FlowId(flowId));
1037 flowBuilder.setStrict(true);
1038 flowBuilder.setBarrier(false);
1039 flowBuilder.setTableId(writeTable);
1040 flowBuilder.setKey(key);
1041 flowBuilder.setPriority(16384);
1042 flowBuilder.setFlowName(flowId);
1043 flowBuilder.setHardTimeout(0);
1044 flowBuilder.setIdleTimeout(0);
1045 Flow flow = this.getFlow(flowBuilder, nodeBuilder);
1046 // Instantiate the Builders for the OF Actions and Instructions
1047 InstructionBuilder ib = new InstructionBuilder();
1048 InstructionsBuilder isb = new InstructionsBuilder();
1049 List<Instruction> instructions = new ArrayList<Instruction>();
1050 List<Instruction> existingInstructions = null;
1052 Instructions ins = flow.getInstructions();
1054 existingInstructions = ins.getInstruction();
1058 // Broken OutPort TODO: localPort needs to be a list of Ports)
1059 createOutputPortInstructions(ib, dpidLong, localPort, existingInstructions);
1061 ib.setKey(new InstructionKey(0));
1062 instructions.add(ib.build());
1064 // Add InstructionBuilder to the Instruction(s)Builder List
1065 isb.setInstruction(instructions);
1067 // Add InstructionsBuilder to FlowBuilder
1068 flowBuilder.setInstructions(isb.build());
1070 writeFlow(flowBuilder, nodeBuilder);
1074 * (Table:1) Local Table Miss
1075 * Match: Any Remaining Flows w/a TunID
1076 * Action: Drop w/ a low priority
1077 * table=2,priority=8192,tun_id=0x5 actions=drop
1080 private void writeLocalTableMiss(Long dpidLong, Short writeTable, String segmentationId) {
1082 String nodeName = "openflow:" + dpidLong;
1084 MatchBuilder matchBuilder = new MatchBuilder();
1085 NodeBuilder nodeBuilder = createNodeBuilder(nodeName);
1086 FlowBuilder flowBuilder = new FlowBuilder();
1088 // Create Match(es) and Set them in the FlowBuilder Object
1089 flowBuilder.setMatch(createTunnelIDMatch(matchBuilder, new BigInteger(segmentationId)).build());
1091 // Create the OF Actions and Instructions
1092 InstructionBuilder ib = new InstructionBuilder();
1093 InstructionsBuilder isb = new InstructionsBuilder();
1095 // Instructions List Stores Individual Instructions
1096 List<Instruction> instructions = new ArrayList<Instruction>();
1098 // Call the InstructionBuilder Methods Containing Actions
1099 createDropInstructions(ib);
1101 ib.setKey(new InstructionKey(0));
1102 instructions.add(ib.build());
1104 // Add InstructionBuilder to the Instruction(s)Builder List
1105 isb.setInstruction(instructions);
1107 // Add InstructionsBuilder to FlowBuilder
1108 flowBuilder.setInstructions(isb.build());
1110 String flowId = "LocalTableMiss_"+segmentationId;
1111 // Add Flow Attributes
1112 flowBuilder.setId(new FlowId(flowId));
1113 FlowKey key = new FlowKey(new FlowId(flowId));
1114 flowBuilder.setStrict(true);
1115 flowBuilder.setBarrier(false);
1116 flowBuilder.setTableId(writeTable);
1117 flowBuilder.setKey(key);
1118 flowBuilder.setPriority(8192);
1119 flowBuilder.setFlowName(flowId);
1120 flowBuilder.setHardTimeout(0);
1121 flowBuilder.setIdleTimeout(0);
1122 writeFlow(flowBuilder, nodeBuilder);
1125 private Flow getFlow(FlowBuilder flowBuilder, NodeBuilder nodeBuilder) {
1126 IMDSALConsumer mdsalConsumer = (IMDSALConsumer) ServiceHelper.getInstance(IMDSALConsumer.class, "default", this);
1127 if (mdsalConsumer == null) {
1128 logger.error("ERROR finding MDSAL Service. Its possible that writeFlow is called too soon ?");
1132 dataBrokerService = mdsalConsumer.getDataBrokerService();
1134 if (dataBrokerService == null) {
1135 logger.error("ERROR finding reference for DataBrokerService. Please check out the MD-SAL support on the Controller.");
1139 InstanceIdentifier<Flow> path1 = InstanceIdentifier.builder(Nodes.class).child(org.opendaylight.yang.gen.v1.urn.opendaylight.inventory
1140 .rev130819.nodes.Node.class, nodeBuilder.getKey()).augmentation(FlowCapableNode.class).child(Table.class,
1141 new TableKey(flowBuilder.getTableId())).child(Flow.class, flowBuilder.getKey()).build();
1142 return (Flow)dataBrokerService.readConfigurationData(path1);
1145 private void writeFlow(FlowBuilder flowBuilder, NodeBuilder nodeBuilder) {
1146 IMDSALConsumer mdsalConsumer = (IMDSALConsumer) ServiceHelper.getInstance(IMDSALConsumer.class, "default", this);
1147 if (mdsalConsumer == null) {
1148 logger.error("ERROR finding MDSAL Service. Its possible that writeFlow is called too soon ?");
1152 dataBrokerService = mdsalConsumer.getDataBrokerService();
1154 if (dataBrokerService == null) {
1155 logger.error("ERROR finding reference for DataBrokerService. Please check out the MD-SAL support on the Controller.");
1158 DataModification<InstanceIdentifier<?>, DataObject> modification = dataBrokerService.beginTransaction();
1159 InstanceIdentifier<Flow> path1 = InstanceIdentifier.builder(Nodes.class).child(org.opendaylight.yang.gen.v1.urn.opendaylight.inventory
1160 .rev130819.nodes.Node.class, nodeBuilder.getKey()).augmentation(FlowCapableNode.class).child(Table.class,
1161 new TableKey(flowBuilder.getTableId())).child(Flow.class, flowBuilder.getKey()).build();
1162 modification.putOperationalData(nodeBuilderToInstanceId(nodeBuilder), nodeBuilder.build());
1163 modification.putOperationalData(path1, flowBuilder.build());
1164 modification.putConfigurationData(nodeBuilderToInstanceId(nodeBuilder), nodeBuilder.build());
1165 modification.putConfigurationData(path1, flowBuilder.build());
1166 Future<RpcResult<TransactionStatus>> commitFuture = modification.commit();
1168 RpcResult<TransactionStatus> result = commitFuture.get();
1169 TransactionStatus status = result.getResult();
1170 logger.debug("Transaction Status "+status.toString()+" for Flow "+flowBuilder.getFlowName());
1171 } catch (InterruptedException e) {
1172 logger.error(e.getMessage(), e);
1173 } catch (ExecutionException e) {
1174 logger.error(e.getMessage(), e);
1179 * Create Ingress Port Match dpidLong, inPort
1181 * @param matchBuilder Map matchBuilder MatchBuilder Object without a match
1182 * @param dpidLong Long the datapath ID of a switch/node
1183 * @param inPort Long ingress port on a switch
1184 * @return matchBuilder Map MatchBuilder Object with a match
1186 protected static MatchBuilder createInPortMatch(MatchBuilder matchBuilder, Long dpidLong, Long inPort) {
1188 NodeConnectorId ncid = new NodeConnectorId("openflow:" + dpidLong + ":" + inPort);
1189 logger.debug("createInPortMatch() Node Connector ID is - Type=openflow: DPID={} inPort={} ", dpidLong, inPort);
1190 matchBuilder.setInPort(NodeConnectorId.getDefaultInstance(ncid.getValue()));
1191 matchBuilder.setInPort(ncid);
1193 return matchBuilder;
1197 * Create EtherType Match
1199 * @param matchBuilder Map matchBuilder MatchBuilder Object without a match
1200 * @param etherType Long EtherType
1201 * @return matchBuilder Map MatchBuilder Object with a match
1203 protected static MatchBuilder createEtherTypeMatch(MatchBuilder matchBuilder, EtherType etherType) {
1205 EthernetMatchBuilder ethernetMatch = new EthernetMatchBuilder();
1206 EthernetTypeBuilder ethTypeBuilder = new EthernetTypeBuilder();
1207 ethTypeBuilder.setType(new EtherType(etherType));
1208 ethernetMatch.setEthernetType(ethTypeBuilder.build());
1209 matchBuilder.setEthernetMatch(ethernetMatch.build());
1211 return matchBuilder;
1215 * Create Ethernet Source Match
1217 * @param matchBuilder MatchBuilder Object without a match yet
1218 * @param sMacAddr String representing a source MAC
1219 * @return matchBuilder Map MatchBuilder Object with a match
1221 protected static MatchBuilder createEthSrcMatch(MatchBuilder matchBuilder, MacAddress sMacAddr) {
1223 EthernetMatchBuilder ethernetMatch = new EthernetMatchBuilder();
1224 EthernetSourceBuilder ethSourceBuilder = new EthernetSourceBuilder();
1225 ethSourceBuilder.setAddress(new MacAddress(sMacAddr));
1226 ethernetMatch.setEthernetSource(ethSourceBuilder.build());
1227 matchBuilder.setEthernetMatch(ethernetMatch.build());
1229 return matchBuilder;
1233 * Create Ethernet Destination Match
1235 * @param matchBuilder MatchBuilder Object without a match yet
1236 * @param vlanId Integer representing a VLAN ID Integer representing a VLAN ID
1237 * @return matchBuilder Map MatchBuilder Object with a match
1240 protected static MatchBuilder createVlanIdMatch(MatchBuilder matchBuilder, VlanId vlanId) {
1242 VlanMatchBuilder vlanMatchBuilder = new VlanMatchBuilder();
1243 VlanIdBuilder vlanIdBuilder = new VlanIdBuilder();
1244 vlanIdBuilder.setVlanId(new VlanId(vlanId));
1245 vlanMatchBuilder.setVlanId(vlanIdBuilder.build());
1246 matchBuilder.setVlanMatch(vlanMatchBuilder.build());
1248 return matchBuilder;
1252 * Create Ethernet Destination Match
1254 * @param matchBuilder MatchBuilder Object without a match yet
1255 * @param dMacAddr String representing a destination MAC
1256 * @return matchBuilder Map MatchBuilder Object with a match
1259 protected static MatchBuilder createDestEthMatch(MatchBuilder matchBuilder, MacAddress dMacAddr, MacAddress mask) {
1261 EthernetMatchBuilder ethernetMatch = new EthernetMatchBuilder();
1262 EthernetDestinationBuilder ethDestinationBuilder = new EthernetDestinationBuilder();
1263 ethDestinationBuilder.setAddress(new MacAddress(dMacAddr));
1265 ethDestinationBuilder.setMask(mask);
1267 ethernetMatch.setEthernetDestination(ethDestinationBuilder.build());
1268 matchBuilder.setEthernetMatch(ethernetMatch.build());
1270 return matchBuilder;
1274 * Tunnel ID Match Builder
1276 * @param matchBuilder MatchBuilder Object without a match yet
1277 * @param tunnelId BigInteger representing a tunnel ID
1278 * @return matchBuilder Map MatchBuilder Object with a match
1280 protected static MatchBuilder createTunnelIDMatch(MatchBuilder matchBuilder, BigInteger tunnelId) {
1282 TunnelBuilder tunnelBuilder = new TunnelBuilder();
1283 tunnelBuilder.setTunnelId(tunnelId);
1284 matchBuilder.setTunnel(tunnelBuilder.build());
1286 return matchBuilder;
1290 * Match ICMP code and type
1292 * @param matchBuilder MatchBuilder Object without a match yet
1293 * @param type short representing an ICMP type
1294 * @param code short representing an ICMP code
1295 * @return matchBuilder Map MatchBuilder Object with a match
1297 protected static MatchBuilder createICMPv4Match(MatchBuilder matchBuilder, short type, short code) {
1299 EthernetMatchBuilder eth = new EthernetMatchBuilder();
1300 EthernetTypeBuilder ethTypeBuilder = new EthernetTypeBuilder();
1301 ethTypeBuilder.setType(new EtherType(0x0800L));
1302 eth.setEthernetType(ethTypeBuilder.build());
1303 matchBuilder.setEthernetMatch(eth.build());
1305 // Build the IPv4 Match requied per OVS Syntax
1306 IpMatchBuilder ipmatch = new IpMatchBuilder();
1307 ipmatch.setIpProtocol((short) 1);
1308 matchBuilder.setIpMatch(ipmatch.build());
1310 // Build the ICMPv4 Match
1311 Icmpv4MatchBuilder icmpv4match = new Icmpv4MatchBuilder();
1312 icmpv4match.setIcmpv4Type(type);
1313 icmpv4match.setIcmpv4Code(code);
1314 matchBuilder.setIcmpv4Match(icmpv4match.build());
1316 return matchBuilder;
1320 * @param matchBuilder MatchBuilder Object without a match yet
1321 * @param dstip String containing an IPv4 prefix
1322 * @return matchBuilder Map Object with a match
1324 private static MatchBuilder createDstL3IPv4Match(MatchBuilder matchBuilder, Ipv4Prefix dstip) {
1326 EthernetMatchBuilder eth = new EthernetMatchBuilder();
1327 EthernetTypeBuilder ethTypeBuilder = new EthernetTypeBuilder();
1328 ethTypeBuilder.setType(new EtherType(0x0800L));
1329 eth.setEthernetType(ethTypeBuilder.build());
1330 matchBuilder.setEthernetMatch(eth.build());
1332 Ipv4MatchBuilder ipv4match = new Ipv4MatchBuilder();
1333 ipv4match.setIpv4Destination(dstip);
1335 matchBuilder.setLayer3Match(ipv4match.build());
1337 return matchBuilder;
1342 * @param matchBuilder MatchBuilder Object without a match yet
1343 * @param srcip String containing an IPv4 prefix
1344 * @return matchBuilder Map Object with a match
1346 private static MatchBuilder createSrcL3IPv4Match(MatchBuilder matchBuilder, Ipv4Prefix srcip) {
1348 EthernetMatchBuilder eth = new EthernetMatchBuilder();
1349 EthernetTypeBuilder ethTypeBuilder = new EthernetTypeBuilder();
1350 ethTypeBuilder.setType(new EtherType(0x0800L));
1351 eth.setEthernetType(ethTypeBuilder.build());
1352 matchBuilder.setEthernetMatch(eth.build());
1354 Ipv4MatchBuilder ipv4Match = new Ipv4MatchBuilder();
1355 Ipv4MatchBuilder ipv4match = new Ipv4MatchBuilder();
1356 ipv4match.setIpv4Source(srcip);
1357 matchBuilder.setLayer3Match(ipv4match.build());
1359 return matchBuilder;
1364 * Create Source TCP Port Match
1366 * @param matchBuilder @param matchbuilder MatchBuilder Object without a match yet
1367 * @param tcpport Integer representing a source TCP port
1368 * @return matchBuilder Map MatchBuilder Object with a match
1370 protected static MatchBuilder createSetSrcTcpMatch(MatchBuilder matchBuilder, PortNumber tcpport) {
1372 EthernetMatchBuilder ethType = new EthernetMatchBuilder();
1373 EthernetTypeBuilder ethTypeBuilder = new EthernetTypeBuilder();
1374 ethTypeBuilder.setType(new EtherType(0x0800L));
1375 ethType.setEthernetType(ethTypeBuilder.build());
1376 matchBuilder.setEthernetMatch(ethType.build());
1378 IpMatchBuilder ipmatch = new IpMatchBuilder();
1379 ipmatch.setIpProtocol((short) 6);
1380 matchBuilder.setIpMatch(ipmatch.build());
1382 TcpMatchBuilder tcpmatch = new TcpMatchBuilder();
1383 tcpmatch.setTcpSourcePort(tcpport);
1384 matchBuilder.setLayer4Match(tcpmatch.build());
1386 return matchBuilder;
1391 * Create Destination TCP Port Match
1393 * @param matchBuilder MatchBuilder Object without a match yet
1394 * @param tcpport Integer representing a destination TCP port
1395 * @return matchBuilder Map MatchBuilder Object with a match
1397 protected static MatchBuilder createSetDstTcpMatch(MatchBuilder matchBuilder, PortNumber tcpport) {
1399 EthernetMatchBuilder ethType = new EthernetMatchBuilder();
1400 EthernetTypeBuilder ethTypeBuilder = new EthernetTypeBuilder();
1401 ethTypeBuilder.setType(new EtherType(0x0800L));
1402 ethType.setEthernetType(ethTypeBuilder.build());
1403 matchBuilder.setEthernetMatch(ethType.build());
1405 IpMatchBuilder ipmatch = new IpMatchBuilder();
1406 ipmatch.setIpProtocol((short) 6);
1407 matchBuilder.setIpMatch(ipmatch.build());
1409 PortNumber dstport = new PortNumber(tcpport);
1410 TcpMatchBuilder tcpmatch = new TcpMatchBuilder();
1412 tcpmatch.setTcpDestinationPort(tcpport);
1413 matchBuilder.setLayer4Match(tcpmatch.build());
1415 return matchBuilder;
1419 * Create Send to Controller Reserved Port Instruction (packet_in)
1421 * @param ib Map InstructionBuilder without any instructions
1422 * @return ib Map InstructionBuilder with instructions
1425 protected static InstructionBuilder createSendToControllerInstructions(InstructionBuilder ib) {
1427 List<Action> actionList = new ArrayList<Action>();
1428 ActionBuilder ab = new ActionBuilder();
1430 OutputActionBuilder output = new OutputActionBuilder();
1431 output.setMaxLength(56);
1432 Uri value = new Uri("CONTROLLER");
1433 output.setOutputNodeConnector(value);
1434 ab.setAction(new OutputActionCaseBuilder().setOutputAction(output.build()).build());
1436 ab.setKey(new ActionKey(0));
1437 actionList.add(ab.build());
1439 // Create an Apply Action
1440 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1441 aab.setAction(actionList);
1443 // Wrap our Apply Action in an Instruction
1444 ib.setInstruction(new ApplyActionsCaseBuilder().setApplyActions(aab.build()).build());
1450 * Create Output Port Instruction
1452 * @param ib Map InstructionBuilder without any instructions
1453 * @param dpidLong Long the datapath ID of a switch/node
1454 * @param port Long representing a port on a switch/node
1455 * @return ib InstructionBuilder Map with instructions
1457 protected static InstructionBuilder createOutputPortInstructions(InstructionBuilder ib, Long dpidLong, Long port) {
1459 NodeConnectorId ncid = new NodeConnectorId("openflow:" + dpidLong + ":" + port);
1460 logger.debug("createOutputPortInstructions() Node Connector ID is - Type=openflow: DPID={} inPort={} ", dpidLong, port);
1462 List<Action> actionList = new ArrayList<Action>();
1463 ActionBuilder ab = new ActionBuilder();
1464 OutputActionBuilder oab = new OutputActionBuilder();
1465 oab.setOutputNodeConnector(ncid);
1467 ab.setAction(new OutputActionCaseBuilder().setOutputAction(oab.build()).build());
1469 ab.setKey(new ActionKey(0));
1470 actionList.add(ab.build());
1472 // Create an Apply Action
1473 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1474 aab.setAction(actionList);
1475 ib.setInstruction(new ApplyActionsCaseBuilder().setApplyActions(aab.build()).build());
1481 * Create Output Port Instruction
1483 * @param ib Map InstructionBuilder without any instructions
1484 * @param dpidLong Long the datapath ID of a switch/node
1485 * @param port Long representing a port on a switch/node
1486 * @return ib InstructionBuilder Map with instructions
1488 protected static InstructionBuilder createOutputPortInstructions(InstructionBuilder ib, Long dpidLong, Long port , List<Instruction> instructions) {
1490 NodeConnectorId ncid = new NodeConnectorId("openflow:" + dpidLong + ":" + port);
1491 logger.debug("createOutputPortInstructions() Node Connector ID is - Type=openflow: DPID={} port={} existingInstructions={}", dpidLong, port, instructions);
1493 List<Action> actionList = new ArrayList<Action>();
1494 ActionBuilder ab = new ActionBuilder();
1496 List<Action> existingActions = null;
1497 if (instructions != null) {
1498 for (Instruction in : instructions) {
1499 if (in.getInstruction() instanceof ApplyActionsCase) {
1500 existingActions = (((ApplyActionsCase) in.getInstruction()).getApplyActions().getAction());
1501 actionList.addAll(existingActions);
1506 OutputActionBuilder oab = new OutputActionBuilder();
1507 oab.setOutputNodeConnector(ncid);
1508 ab.setAction(new OutputActionCaseBuilder().setOutputAction(oab.build()).build());
1510 ab.setKey(new ActionKey(0));
1511 Action newAction = ab.build();
1512 boolean addNew = true;
1513 for (Action action : actionList) {
1514 if (action.getAction() instanceof OutputActionCase) {
1515 OutputActionCase opAction = (OutputActionCase)action.getAction();
1516 if (opAction.getOutputAction().getOutputNodeConnector().equals(new Uri(ncid))) {
1522 if (addNew) actionList.add(newAction);
1524 // Create an Apply Action
1525 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1526 aab.setAction(actionList);
1527 ib.setInstruction(new ApplyActionsCaseBuilder().setApplyActions(aab.build()).build());
1533 * Create Set Vlan ID Instruction
1535 * @param ib Map InstructionBuilder without any instructions
1536 * @param vlanId Integer representing a VLAN ID Integer representing a VLAN ID
1537 * @return ib Map InstructionBuilder with instructions
1539 protected static InstructionBuilder createSetVlanInstructions(InstructionBuilder ib, VlanId vlanId) {
1541 List<Action> actionList = new ArrayList<Action>();
1542 ActionBuilder ab = new ActionBuilder();
1544 SetVlanIdActionBuilder vl = new SetVlanIdActionBuilder();
1545 vl.setVlanId(vlanId);
1546 ab.setAction(new SetVlanIdActionCaseBuilder().setSetVlanIdAction(vl.build()).build());
1547 actionList.add(ab.build());
1548 // Create an Apply Action
1549 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1550 aab.setAction(actionList);
1552 // Wrap our Apply Action in an Instruction
1553 ib.setInstruction(new ApplyActionsCaseBuilder().setApplyActions(aab.build()).build());
1559 * Create Set IPv4 Destination Instruction
1561 * @param ib Map InstructionBuilder without any instructions
1562 * @return ib Map InstructionBuilder with instructions
1564 protected static InstructionBuilder createStripVlanInstructions(InstructionBuilder ib) {
1566 StripVlanActionBuilder stripVlanActionBuilder = new StripVlanActionBuilder();
1567 StripVlanAction vlanAction = stripVlanActionBuilder.build();
1568 ActionBuilder ab = new ActionBuilder();
1569 ab.setAction(new StripVlanActionCaseBuilder().setStripVlanAction(vlanAction).build());
1571 // Add our drop action to a list
1572 List<Action> actionList = new ArrayList<Action>();
1573 actionList.add(ab.build());
1575 // Create an Apply Action
1576 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1577 aab.setAction(actionList);
1579 // Wrap our Apply Action in an Instruction
1580 ib.setInstruction(new ApplyActionsCaseBuilder().setApplyActions(aab.build()).build());
1586 * Create Set IPv4 Source Instruction
1588 * @param ib Map InstructionBuilder without any instructions
1589 * @param prefixsrc String containing an IPv4 prefix
1590 * @return ib Map InstructionBuilder with instructions
1592 protected static InstructionBuilder createNwSrcInstructions(InstructionBuilder ib, Ipv4Prefix prefixsrc) {
1594 List<Action> actionList = new ArrayList<Action>();
1595 ActionBuilder ab = new ActionBuilder();
1597 SetNwSrcActionBuilder setNwsrcActionBuilder = new SetNwSrcActionBuilder();
1598 Ipv4Builder ipsrc = new Ipv4Builder();
1599 ipsrc.setIpv4Address(prefixsrc);
1600 setNwsrcActionBuilder.setAddress(ipsrc.build());
1601 ab.setAction(new SetNwSrcActionCaseBuilder().setSetNwSrcAction(setNwsrcActionBuilder.build()).build());
1602 actionList.add(ab.build());
1604 // Create an Apply Action
1605 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1606 aab.setAction(actionList);
1608 // Wrap our Apply Action in an Instruction
1609 ib.setInstruction(new ApplyActionsCaseBuilder().setApplyActions(aab.build()).build());
1615 * Create Set IPv4 Destination Instruction
1617 * @param ib Map InstructionBuilder without any instructions
1618 * @param prefixdst String containing an IPv4 prefix
1619 * @return ib Map InstructionBuilder with instructions
1621 protected static InstructionBuilder createNwDstInstructions(InstructionBuilder ib, Ipv4Prefix prefixdst) {
1623 List<Action> actionList = new ArrayList<Action>();
1624 ActionBuilder ab = new ActionBuilder();
1626 SetNwDstActionBuilder setNwDstActionBuilder = new SetNwDstActionBuilder();
1627 Ipv4Builder ipdst = new Ipv4Builder();
1628 ipdst.setIpv4Address(prefixdst);
1629 setNwDstActionBuilder.setAddress(ipdst.build());
1630 ab.setAction(new SetNwDstActionCaseBuilder().setSetNwDstAction(setNwDstActionBuilder.build()).build());
1631 actionList.add(ab.build());
1633 // Create an Apply Action
1634 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1635 aab.setAction(actionList);
1637 // Wrap our Apply Action in an Instruction
1638 ib.setInstruction(new ApplyActionsCaseBuilder().setApplyActions(aab.build()).build());
1644 * Create Drop Instruction
1646 * @param ib Map InstructionBuilder without any instructions
1647 * @return ib Map InstructionBuilder with instructions
1649 protected static InstructionBuilder createDropInstructions(InstructionBuilder ib) {
1651 DropActionBuilder dab = new DropActionBuilder();
1652 DropAction dropAction = dab.build();
1653 ActionBuilder ab = new ActionBuilder();
1654 ab.setAction(new DropActionCaseBuilder().setDropAction(dropAction).build());
1656 // Add our drop action to a list
1657 List<Action> actionList = new ArrayList<Action>();
1658 actionList.add(ab.build());
1660 // Create an Apply Action
1661 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1662 aab.setAction(actionList);
1664 // Wrap our Apply Action in an Instruction
1665 ib.setInstruction(new ApplyActionsCaseBuilder().setApplyActions(aab.build()).build());
1671 * Create GOTO Table Instruction Builder
1673 * @param ib Map InstructionBuilder without any instructions
1674 * @param tableId short representing a flow table ID short representing a flow table ID
1675 * @return ib Map InstructionBuilder with instructions
1677 protected static InstructionBuilder createGotoTableInstructions(InstructionBuilder ib, short tableId) {
1679 GoToTableBuilder gttb = new GoToTableBuilder();
1680 gttb.setTableId(tableId);
1682 // Wrap our Apply Action in an InstructionBuilder
1683 ib.setInstruction(new GoToTableCaseBuilder().setGoToTable(gttb.build()).build());
1689 * Create Set Tunnel ID Instruction Builder
1691 * @param ib Map InstructionBuilder without any instructions
1692 * @param tunnelId BigInteger representing a tunnel ID
1693 * @return ib Map InstructionBuilder with instructions
1695 protected static InstructionBuilder createSetTunnelIdInstructions(InstructionBuilder ib, BigInteger tunnelId) {
1697 List<Action> actionList = new ArrayList<Action>();
1698 ActionBuilder ab = new ActionBuilder();
1699 SetFieldBuilder setFieldBuilder = new SetFieldBuilder();
1701 // Build the Set Tunnel Field Action
1702 TunnelBuilder tunnel = new TunnelBuilder();
1703 tunnel.setTunnelId(tunnelId);
1704 setFieldBuilder.setTunnel(tunnel.build());
1705 ab.setAction(new SetFieldCaseBuilder().setSetField(setFieldBuilder.build()).build());
1706 actionList.add(ab.build());
1708 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1709 aab.setAction(actionList);
1711 // Wrap the Apply Action in an InstructionBuilder and return
1712 ib.setInstruction(new ApplyActionsCaseBuilder().setApplyActions(aab.build()).build());
1718 * Create Set Source TCP Port Instruction
1720 * @param ib Map InstructionBuilder without any instructions
1721 * @param tcpport Integer representing a source TCP port
1722 * @return ib Map InstructionBuilder with instructions
1724 protected static InstructionBuilder createSetSrcTCPPort(InstructionBuilder ib, PortNumber tcpport) {
1726 List<Action> actionList = new ArrayList<Action>();
1727 ActionBuilder ab = new ActionBuilder();
1728 SetFieldBuilder setFieldBuilder = new SetFieldBuilder();
1730 // Build the Destination TCP Port
1731 PortNumber tcpsrcport = new PortNumber(tcpport);
1732 TcpMatchBuilder tcpmatch = new TcpMatchBuilder();
1733 tcpmatch.setTcpSourcePort(tcpsrcport);
1735 setFieldBuilder.setLayer4Match(tcpmatch.build());
1736 ab.setAction(new SetFieldCaseBuilder().setSetField(setFieldBuilder.build()).build());
1737 ab.setKey(new ActionKey(1));
1738 actionList.add(ab.build());
1740 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1741 aab.setAction(actionList);
1742 ib.setInstruction(new ApplyActionsCaseBuilder().setApplyActions(aab.build()).build());
1748 * Create Set Destination TCP Port Instruction
1750 * @param ib Map InstructionBuilder without any instructions
1751 * @param tcpport Integer representing a source TCP port
1752 * @return ib Map InstructionBuilder with instructions
1754 protected static InstructionBuilder createSetDstTCPPort(InstructionBuilder ib, PortNumber tcpport) {
1756 List<Action> actionList = new ArrayList<Action>();
1757 ActionBuilder ab = new ActionBuilder();
1758 SetFieldBuilder setFieldBuilder = new SetFieldBuilder();
1760 // Build the Destination TCP Port
1761 PortNumber tcpdstport = new PortNumber(tcpport);
1762 TcpMatchBuilder tcpmatch = new TcpMatchBuilder();
1763 tcpmatch.setTcpDestinationPort(tcpdstport);
1765 setFieldBuilder.setLayer4Match(tcpmatch.build());
1766 ab.setAction(new SetFieldCaseBuilder().setSetField(setFieldBuilder.build()).build());
1767 ab.setKey(new ActionKey(1));
1768 actionList.add(ab.build());
1770 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1771 aab.setAction(actionList);
1772 ib.setInstruction(new ApplyActionsCaseBuilder().setApplyActions(aab.build()).build());
1778 * Create Set Source UDP Port Instruction
1780 * @param ib Map InstructionBuilder without any instructions
1781 * @param udpport Integer representing a source UDP port
1782 * @return ib Map InstructionBuilder with instructions
1784 protected static InstructionBuilder createSetSrcUDPPort(InstructionBuilder ib, PortNumber udpport) {
1786 List<Action> actionList = new ArrayList<Action>();
1787 ActionBuilder ab = new ActionBuilder();
1788 SetFieldBuilder setFieldBuilder = new SetFieldBuilder();
1790 // Build the Destination TCP Port
1791 PortNumber udpsrcport = new PortNumber(udpport);
1792 UdpMatchBuilder udpmatch = new UdpMatchBuilder();
1793 udpmatch.setUdpSourcePort(udpsrcport);
1795 setFieldBuilder.setLayer4Match(udpmatch.build());
1796 ab.setAction(new SetFieldCaseBuilder().setSetField(setFieldBuilder.build()).build());
1797 ab.setKey(new ActionKey(1));
1798 actionList.add(ab.build());
1800 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1801 aab.setAction(actionList);
1802 ib.setInstruction(new ApplyActionsCaseBuilder().setApplyActions(aab.build()).build());
1808 * Create Set Destination UDP Port Instruction
1810 * @param ib Map InstructionBuilder without any instructions
1811 * @param udpport Integer representing a destination UDP port
1812 * @return ib Map InstructionBuilder with instructions
1814 protected static InstructionBuilder createSetDstUDPPort(InstructionBuilder ib, PortNumber udpport) {
1816 List<Action> actionList = new ArrayList<Action>();
1817 ActionBuilder ab = new ActionBuilder();
1818 SetFieldBuilder setFieldBuilder = new SetFieldBuilder();
1820 // Build the Destination TCP Port
1821 PortNumber udpdstport = new PortNumber(udpport);
1822 UdpMatchBuilder udpmatch = new UdpMatchBuilder();
1823 udpmatch.setUdpDestinationPort(udpdstport);
1825 setFieldBuilder.setLayer4Match(udpmatch.build());
1826 ab.setAction(new SetFieldCaseBuilder().setSetField(setFieldBuilder.build()).build());
1827 ab.setKey(new ActionKey(1));
1828 actionList.add(ab.build());
1830 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1831 aab.setAction(actionList);
1832 ib.setInstruction(new ApplyActionsCaseBuilder().setApplyActions(aab.build()).build());
1838 * Create Set ICMP Code Instruction
1840 * @param ib Map InstructionBuilder without any instructions
1841 * @param code short repesenting an ICMP code
1842 * @return ib Map InstructionBuilder with instructions
1845 private static InstructionBuilder createSetIcmpCodeInstruction(InstructionBuilder ib, short code) {
1847 List<Action> actionList = new ArrayList<Action>();
1848 ActionBuilder ab = new ActionBuilder();
1849 SetFieldBuilder setFieldBuilder = new SetFieldBuilder();
1850 Icmpv4MatchBuilder icmpv4match = new Icmpv4MatchBuilder();
1852 // Build the ICMPv4 Code Match
1853 icmpv4match.setIcmpv4Code(code);
1854 setFieldBuilder.setIcmpv4Match(icmpv4match.build());
1856 ab.setAction(new SetFieldCaseBuilder().setSetField(setFieldBuilder.build()).build());
1857 ab.setKey(new ActionKey(0));
1858 actionList.add(ab.build());
1859 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1860 aab.setAction(actionList);
1862 // Wrap our Apply Action in an Instruction
1863 ib.setInstruction(new ApplyActionsCaseBuilder().setApplyActions(aab.build()).build());
1869 * Create Set ICMP Code Instruction
1871 * @param ib Map InstructionBuilder without any instructions
1872 * @return ib Map InstructionBuilder with instructions
1874 private static InstructionBuilder createSetIcmpTypeInstruction(InstructionBuilder ib, short type) {
1876 List<Action> actionList = new ArrayList<Action>();
1877 ActionBuilder ab = new ActionBuilder();
1878 SetFieldBuilder setFieldBuilder = new SetFieldBuilder();
1879 Icmpv4MatchBuilder icmpv4match = new Icmpv4MatchBuilder();
1881 // Build the ICMPv4 Code Match
1882 icmpv4match.setIcmpv4Code(type);
1883 setFieldBuilder.setIcmpv4Match(icmpv4match.build());
1885 ab.setAction(new SetFieldCaseBuilder().setSetField(setFieldBuilder.build()).build());
1886 ab.setKey(new ActionKey(1));
1887 actionList.add(ab.build());
1888 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1889 aab.setAction(actionList);
1891 // Wrap our Apply Action in an Instruction
1892 ib.setInstruction(new ApplyActionsCaseBuilder().setApplyActions(aab.build()).build());
1898 * Create Decrement TTL Instruction
1900 * @param ib Map InstructionBuilder without any instructions
1901 * @return ib Map InstructionBuilder with instructions
1903 private static InstructionBuilder createDecNwTtlInstructions(InstructionBuilder ib) {
1904 DecNwTtlBuilder decNwTtlBuilder = new DecNwTtlBuilder();
1905 DecNwTtl decNwTtl = decNwTtlBuilder.build();
1906 ActionBuilder ab = new ActionBuilder();
1907 ab.setAction(new DecNwTtlCaseBuilder().setDecNwTtl(decNwTtl).build());
1909 // Add our drop action to a list
1910 List<Action> actionList = new ArrayList<Action>();
1911 actionList.add(ab.build());
1913 // Create an Apply Action
1914 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1915 aab.setAction(actionList);
1917 // Wrap our Apply Action in an Instruction
1918 ib.setInstruction(new ApplyActionsCaseBuilder().setApplyActions(aab.build()).build());
1926 private static InstructionBuilder createSrcArpMacInstructions(InstructionBuilder ib, MacAddress macsrc) {
1928 List<Action> actionList = new ArrayList<Action>();
1929 ActionBuilder ab = new ActionBuilder();
1931 SetFieldBuilder setFieldBuilder = new SetFieldBuilder();
1932 ArpMatchBuilder arpmatch = new ArpMatchBuilder();
1933 ArpSourceHardwareAddressBuilder arpsrc = new ArpSourceHardwareAddressBuilder();
1934 arpsrc.setAddress(macsrc);
1935 arpmatch.setArpSourceHardwareAddress(arpsrc.build());
1936 setFieldBuilder.setLayer3Match(arpmatch.build());
1937 ab.setAction(new SetFieldCaseBuilder().setSetField(setFieldBuilder.build()).build());
1938 ab.setKey(new ActionKey(0));
1939 actionList.add(ab.build());
1941 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1942 aab.setAction(actionList);
1950 private static InstructionBuilder createDstArpMacInstructions(InstructionBuilder ib, MacAddress macdst) {
1952 List<Action> actionList = new ArrayList<Action>();
1953 ActionBuilder ab = new ActionBuilder();
1954 SetFieldBuilder setFieldBuilder = new SetFieldBuilder();
1956 ArpMatchBuilder arpmatch = new ArpMatchBuilder();
1957 ArpTargetHardwareAddressBuilder arpdst = new ArpTargetHardwareAddressBuilder();
1958 arpdst.setAddress(macdst);
1959 setFieldBuilder.setLayer3Match(arpmatch.build());
1960 ab.setAction(new SetFieldCaseBuilder().setSetField(setFieldBuilder.build()).build());
1961 ab.setKey(new ActionKey(0));
1962 actionList.add(ab.build());
1964 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1965 aab.setAction(actionList);
1973 private static InstructionBuilder createDstArpIpInstructions(InstructionBuilder ib, Ipv4Prefix dstiparp) {
1975 List<Action> actionList = new ArrayList<Action>();
1976 ActionBuilder ab = new ActionBuilder();
1977 SetFieldBuilder setFieldBuilder = new SetFieldBuilder();
1979 ArpMatchBuilder arpmatch = new ArpMatchBuilder();
1980 arpmatch.setArpTargetTransportAddress(dstiparp);
1981 setFieldBuilder.setLayer3Match(arpmatch.build());
1982 ab.setAction(new SetFieldCaseBuilder().setSetField(setFieldBuilder.build()).build());
1983 ab.setKey(new ActionKey(0));
1984 actionList.add(ab.build());
1986 ApplyActionsBuilder aab = new ApplyActionsBuilder();
1987 aab.setAction(actionList);
1995 private static InstructionBuilder createSrcArpIpInstructions(InstructionBuilder ib, Ipv4Prefix srciparp) {
1997 List<Action> actionList = new ArrayList<Action>();
1998 ActionBuilder ab = new ActionBuilder();
1999 SetFieldBuilder setFieldBuilder = new SetFieldBuilder();
2001 ArpMatchBuilder arpmatch = new ArpMatchBuilder();
2002 arpmatch.setArpSourceTransportAddress(srciparp);
2003 setFieldBuilder.setLayer3Match(arpmatch.build());
2004 ab.setAction(new SetFieldCaseBuilder().setSetField(setFieldBuilder.build()).build());
2005 ab.setKey(new ActionKey(0));
2006 actionList.add(ab.build());
2008 ApplyActionsBuilder aab = new ApplyActionsBuilder();
2009 aab.setAction(actionList);
2015 public void initializeOFFlowRules(Node openflowNode) {
2016 IConnectionServiceInternal connectionService = (IConnectionServiceInternal)ServiceHelper.getGlobalInstance(IConnectionServiceInternal.class, this);
2017 List<Node> ovsNodes = connectionService.getNodes();
2018 if (ovsNodes == null) return;
2019 for (Node ovsNode : ovsNodes) {
2020 Long dpid = this.getIntegrationBridgeOFDPID(ovsNode);
2021 logger.debug("Compare openflowNode to OVS br-int node {} vs {}", openflowNode.getID(), dpid);
2022 String openflowID = ""+openflowNode.getID();
2023 if (openflowID.contains(""+dpid)) {
2024 this.initializeFlowRules(ovsNode, AdminConfigManager.getManager().getIntegrationBridgeName());
2025 this.triggerInterfaceUpdates(ovsNode);
2030 private NodeBuilder createNodeBuilder(String nodeId) {
2031 NodeBuilder builder = new NodeBuilder();
2032 builder.setId(new NodeId(nodeId));
2033 builder.setKey(new NodeKey(builder.getId()));
2037 private InstanceIdentifier<org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.Node> nodeBuilderToInstanceId(NodeBuilder
2039 return InstanceIdentifier.builder(Nodes.class).child(org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.Node.class,
2040 node.getKey()).toInstance();