Created separte classes for Policy and Tunnel.
Change-Id: I54be25a232ae36d8c19b21a0cb789a16beaf8b7d
diff --git a/conf/onos.properties b/conf/onos.properties
index a3e1d19..89b4c80 100644
--- a/conf/onos.properties
+++ b/conf/onos.properties
@@ -23,4 +23,4 @@
# Uncomment and list all the ZooKeeper instances after localhost on multi-instance deployment.
#net.onrc.onos.core.registry.ZookeeperRegistry.connectionString = localhost:2181,otherhost:2181
# Specify a network configuration file to be used by the NetworkConfigManager
-net.onrc.onos.core.configmanager.NetworkConfigManager.networkConfigFile = conf/sr-ecmp.conf
+net.onrc.onos.core.configmanager.NetworkConfigManager.networkConfigFile = conf/sr-ecmp10.conf
diff --git a/src/main/java/net/onrc/onos/apps/segmentrouting/ISegmentRoutingService.java b/src/main/java/net/onrc/onos/apps/segmentrouting/ISegmentRoutingService.java
index 446384e..349aa40 100644
--- a/src/main/java/net/onrc/onos/apps/segmentrouting/ISegmentRoutingService.java
+++ b/src/main/java/net/onrc/onos/apps/segmentrouting/ISegmentRoutingService.java
@@ -6,9 +6,8 @@
import net.floodlightcontroller.core.module.IFloodlightService;
import net.floodlightcontroller.util.MACAddress;
-import net.onrc.onos.apps.segmentrouting.SegmentRoutingManager.PolicyInfo;
-import net.onrc.onos.apps.segmentrouting.SegmentRoutingManager.TunnelInfo;
import net.onrc.onos.apps.segmentrouting.SegmentRoutingManager.removeTunnelMessages;
+import net.onrc.onos.apps.segmentrouting.SegmentRoutingPolicy.PolicyType;
import net.onrc.onos.core.util.IPv4Net;
/**
@@ -52,8 +51,27 @@
*/
public boolean createPolicy(String pid, MACAddress srcMac, MACAddress dstMac,
Short etherType, IPv4Net srcIp, IPv4Net dstIp, Byte ipProto,
+ Short srcPort, Short dstPort, int priority, String tid, PolicyType type);
+
+ /**
+ * Create a policy for policy based segment routing
+ *
+ * @param pid Unique Policy Identifier
+ * @param srcIP Source IP address in CIDR format
+ * @param dstIP Destination IP address in CIDR format
+ * @param ipProto IP protocol type
+ * @param srcPort Source L4 port
+ * @param dstPort Destination L4 port
+ * @param priority Priority of the policy
+ * @param tid SR Tunnel Id to be associated with this policy
+ *
+ * @return "true/false" depending tunnel creation status
+ */
+ public boolean createPolicy(String pid, MACAddress srcMac, MACAddress dstMac,
+ Short etherType, IPv4Net srcIp, IPv4Net dstIp, Byte ipProto,
Short srcPort, Short dstPort, int priority, String tid);
+
/**
* Remove a policy given policy Id
*
@@ -68,7 +86,7 @@
* @return Collection<TunnelInfo>
*/
- public Collection<TunnelInfo> getTunnelTable();
+ public Collection<SegmentRoutingTunnel> getTunnelTable();
/**
* Get the first group ID for the tunnel for specific source router
* If Segment Stitching was required to create the tunnel, there are
@@ -84,7 +102,7 @@
* return list of all the policies currently there in Segment Router
* @return Collection<PolicyInfo>
*/
- public Collection<PolicyInfo> getPoclicyTable();
+ public Collection<SegmentRoutingPolicy> getPoclicyTable();
/**
* Returns the Adjacency Info for the node
*
diff --git a/src/main/java/net/onrc/onos/apps/segmentrouting/SegmentRoutingManager.java b/src/main/java/net/onrc/onos/apps/segmentrouting/SegmentRoutingManager.java
index dbd3b7e..34b1a8c 100644
--- a/src/main/java/net/onrc/onos/apps/segmentrouting/SegmentRoutingManager.java
+++ b/src/main/java/net/onrc/onos/apps/segmentrouting/SegmentRoutingManager.java
@@ -33,6 +33,8 @@
import net.floodlightcontroller.util.MACAddress;
import net.onrc.onos.api.packet.IPacketListener;
import net.onrc.onos.api.packet.IPacketService;
+import net.onrc.onos.apps.segmentrouting.SegmentRoutingPolicy.PolicyType;
+import net.onrc.onos.apps.segmentrouting.SegmentRoutingTunnel.TunnelRouteInfo;
import net.onrc.onos.apps.segmentrouting.web.SegmentRoutingWebRoutable;
import net.onrc.onos.core.drivermanager.OFSwitchImplDellOSR;
import net.onrc.onos.core.flowprogrammer.IFlowPusherService;
@@ -114,8 +116,8 @@
private HashMap<String, LinkData> linksDown;
private HashMap<String, LinkData> linksToAdd;
private ConcurrentLinkedQueue<TopologyEvents> topologyEventQueue;
- private HashMap<String, PolicyInfo> policyTable;
- private HashMap<String, TunnelInfo> tunnelTable;
+ private HashMap<String, SegmentRoutingPolicy> policyTable;
+ private HashMap<String, SegmentRoutingTunnel> tunnelTable;
private HashMap<Integer, HashMap<Integer, List<Integer>>> adjacencySidTable;
// Flag whether transit router supports ECMP or not
@@ -190,8 +192,8 @@
topologyEventQueue = new ConcurrentLinkedQueue<TopologyEvents>();
packetService = context.getServiceImpl(IPacketService.class);
restApi = context.getServiceImpl(IRestApiService.class);
- policyTable = new HashMap<String, PolicyInfo>();
- tunnelTable = new HashMap<String, TunnelInfo>();
+ policyTable = new HashMap<String, SegmentRoutingPolicy>();
+ tunnelTable = new HashMap<String, SegmentRoutingTunnel>();
adjacencySidTable = new HashMap<Integer,HashMap<Integer, List<Integer>>>();
packetService.registerPacketListener(this);
@@ -1063,138 +1065,15 @@
// ************************************
/**
- * Enums for policy type
- *
- */
- public enum PolicyType{
- TUNNEL_FLOW,
- LOADBALANCE,
- AVOID,
- DENY
- }
- public class PolicyInfo {
- private String policyId;
- private PacketMatch match;
- private int priority;
- private String tunnelId;
- private PolicyType type;
-
- public PolicyInfo(String pid, PolicyType type, PacketMatch match, int priority,
- String tid) {
- this.policyId = pid;
- this.match = match;
- this.priority = priority;
- this.tunnelId = tid;
- this.type = type;
- }
-
- public PolicyInfo(String pid, PacketMatch match, int priority,
- String tid) {
- this.policyId = pid;
- this.match = match;
- this.priority = priority;
- this.tunnelId = tid;
- this.type = PolicyType.TUNNEL_FLOW;
- }
- public String getPolicyId(){
- return this.policyId;
- }
- public PacketMatch getMatch(){
- return this.match;
- }
- public int getPriority(){
- return this.priority;
- }
- public String getTunnelId(){
- return this.tunnelId;
- }
- public PolicyType getType(){
- return this.type;
- }
- }
-
- public class TunnelInfo {
- private String tunnelId;
- private List<Integer> labelIds;
- private List<TunnelRouteInfo> routes;
-
- public TunnelInfo(String tid, List<Integer> labelIds,
- List<TunnelRouteInfo> routes) {
- this.tunnelId = tid;
- this.labelIds = labelIds;
- this.routes = routes;
- }
- public String getTunnelId(){
- return this.tunnelId;
- }
-
- public List<Integer> getLabelids() {
- return this.labelIds;
- }
- public List<TunnelRouteInfo> getRoutes(){
- return this.routes;
- }
- }
-
- public class TunnelRouteInfo {
-
- private String srcSwDpid;
- private List<Dpid> fwdSwDpids;
- private List<String> route;
- private int gropuId;
-
- public TunnelRouteInfo() {
- fwdSwDpids = new ArrayList<Dpid>();
- route = new ArrayList<String>();
- }
-
- private void setSrcDpid(String dpid) {
- this.srcSwDpid = dpid;
- }
-
- private void setFwdSwDpid(List<Dpid> dpid) {
- this.fwdSwDpids = dpid;
- }
-
- private void addRoute(String id) {
- route.add(id);
- }
-
- private void setRoute(List<String> r) {
- this.route = r;
- }
-
- private void setGroupId(int groupId) {
- this.gropuId = groupId;
- }
-
- public String getSrcSwDpid() {
- return this.srcSwDpid;
- }
-
- public List<Dpid> getFwdSwDpid() {
- return this.fwdSwDpids;
- }
-
- public List<String> getRoute() {
- return this.route;
- }
-
- public int getGroupId() {
- return this.gropuId;
- }
- }
-
- /**
* Return the Tunnel table
*
* @return collection of TunnelInfo
*/
- public Collection<TunnelInfo> getTunnelTable() {
+ public Collection<SegmentRoutingTunnel> getTunnelTable() {
return this.tunnelTable.values();
}
- public Collection<PolicyInfo> getPoclicyTable() {
+ public Collection<SegmentRoutingPolicy> getPoclicyTable() {
return this.policyTable.values();
}
@@ -1204,24 +1083,22 @@
* @param tid tunnel ID
* @return List of DPID
*/
- public List<Integer> getTunnelInfo(String tid) {
- TunnelInfo tunnelInfo = tunnelTable.get(tid);
- return tunnelInfo.labelIds;
-
+ public SegmentRoutingTunnel getTunnelInfo(String tid) {
+ return tunnelTable.get(tid);
}
/**
* Get the first group ID for the tunnel for specific source router
* If Segment Stitching was required to create the tunnel, there are
- * mutiple source routers.
+ * multiple source routers.
*
* @param tunnelId ID for the tunnel
* @param dpid source router DPID
* @return the first group ID of the tunnel
*/
public int getTunnelGroupId(String tunnelId, String dpid) {
- TunnelInfo tunnelInfo = tunnelTable.get(tunnelId);
- for (TunnelRouteInfo routeInfo: tunnelInfo.getRoutes()) {
+ SegmentRoutingTunnel tunnel = tunnelTable.get(tunnelId);
+ for (TunnelRouteInfo routeInfo: tunnel.getRoutes()) {
String tunnelSrcDpid = routeInfo.getSrcSwDpid();
if (tunnelSrcDpid.equals(dpid))
return routeInfo.getGroupId();
@@ -1240,70 +1117,24 @@
*/
public boolean createTunnel(String tunnelId, List<Integer> labelIds) {
- if (labelIds.isEmpty() || labelIds.size() < 2) {
- log.debug("Wrong tunnel information");
+ SegmentRoutingTunnel srTunnel =
+ new SegmentRoutingTunnel(this, tunnelId, labelIds);
+ if (srTunnel.createTunnel()) {
+ tunnelTable.put(tunnelId, srTunnel);
+ return true;
+ }
+ else {
return false;
}
-
- List<String> Ids = new ArrayList<String>();
- for (Integer label : labelIds) {
- Ids.add(label.toString());
- }
-
- List<TunnelRouteInfo> stitchingRule = getStitchingRule(Ids);
- if (stitchingRule == null) {
- log.debug("Failed to get a tunnel rule.");
- return false;
- }
-
- for (TunnelRouteInfo route: stitchingRule) {
- NeighborSet ns = new NeighborSet();
- for (Dpid dpid: route.getFwdSwDpid())
- ns.addDpid(dpid);
-
- printTunnelInfo(route.srcSwDpid, tunnelId, route.getRoute(), ns);
- int groupId = -1;
- if ((groupId =createGroupsForTunnel(tunnelId, route, ns)) < 0) {
- log.debug("Failed to create a tunnel at driver.");
- return false;
- }
- route.setGroupId(groupId);
- }
-
- TunnelInfo tunnelInfo = new TunnelInfo(tunnelId, labelIds,
- stitchingRule);
- tunnelTable.put(tunnelId, tunnelInfo);
-
- return true;
}
- /**
- * Create groups for the tunnel
- *
- * @param tunnelId tunnel ID
- * @param routeInfo label stacks for the tunnel
- * @param ns NeighborSet to forward packets
- * @return group ID, return -1 if it fails
- */
- private int createGroupsForTunnel(String tunnelId, TunnelRouteInfo routeInfo,
- NeighborSet ns) {
+ @Override
+ public boolean createPolicy(String pid, MACAddress srcMac, MACAddress dstMac,
+ Short etherType, IPv4Net srcIp, IPv4Net dstIp, Byte ipProto,
+ Short srcPort, Short dstPort, int priority, String tid) {
- IOF13Switch targetSw = (IOF13Switch) floodlightProvider.getMasterSwitch(
- getSwId(routeInfo.srcSwDpid));
-
- if (targetSw == null) {
- log.debug("Switch {} is gone.", routeInfo.srcSwDpid);
- return -1;
- }
-
- List<Integer> Ids = new ArrayList<Integer>();
- for (String IdStr: routeInfo.route)
- Ids.add(Integer.parseInt(IdStr));
-
- List<PortNumber> ports = getPortsFromNeighborSet(routeInfo.srcSwDpid, ns);
- int groupId = targetSw.createGroup(Ids, ports);
-
- return groupId;
+ return createPolicy(pid, srcMac, dstMac, etherType, srcIp, dstIp, ipProto,
+ srcPort, dstPort, priority, tid, PolicyType.TUNNEL_FLOW);
}
/**
@@ -1315,7 +1146,15 @@
*/
public boolean createPolicy(String pid, MACAddress srcMac, MACAddress dstMac,
Short etherType, IPv4Net srcIp, IPv4Net dstIp, Byte ipProto,
- Short srcTcpPort, Short dstTcpPort, int priority, String tid) {
+ Short srcTcpPort, Short dstTcpPort, int priority, String tid,
+ PolicyType type) {
+
+ // Sanity check
+ SegmentRoutingTunnel tunnelInfo = tunnelTable.get(tid);
+ if (tunnelInfo == null) {
+ log.warn("Tunnel {} is not defined", tid);
+ return false;
+ }
PacketMatchBuilder packetBuilder = new PacketMatchBuilder();
@@ -1338,199 +1177,23 @@
if (dstTcpPort > 0)
packetBuilder.setDstTcpPort(dstTcpPort);
PacketMatch policyMatch = packetBuilder.build();
- TunnelInfo tunnelInfo = tunnelTable.get(tid);
- if (tunnelInfo == null) {
- log.debug("Tunnel {} is not defined", tid);
+
+ if (type == PolicyType.TUNNEL_FLOW) {
+ SegmentRoutingPolicy srPolicy =
+ new SegmentRoutingPolicyTunnel(this,pid, type, policyMatch,
+ priority, tid);
+ if (srPolicy.createPolicy()) {
+ policyTable.put(pid, srPolicy);
+ return true;
+ }
+ else { log.warn("Failed to create a policy");
+ return false;
+ }
+ }
+ else {
+ log.warn("No other policy is supported yet.");
return false;
}
- List<TunnelRouteInfo> routes = tunnelInfo.routes;
-
- for (TunnelRouteInfo route : routes) {
- List<Action> actions = new ArrayList<>();
-
- // Check PHP was done by stitching
- // If no MPLS label is added, then NW TTL needs to be decremented
- if (route.getRoute().isEmpty()) {
- DecNwTtlAction decNwTtlAction = new DecNwTtlAction(1);
- actions.add(decNwTtlAction);
- }
-
- GroupAction groupAction = new GroupAction();
- groupAction.setGroupId(route.getGroupId());
- actions.add(groupAction);
-
- MatchAction matchAction = new MatchAction(new MatchActionId(
- matchActionId++),
- new SwitchPort((long) 0, (short) 0), policyMatch, priority,
- actions);
- MatchActionOperationEntry maEntry =
- new MatchActionOperationEntry(Operator.ADD, matchAction);
-
- IOF13Switch sw13 = (IOF13Switch) floodlightProvider.getMasterSwitch(
- getSwId(route.srcSwDpid));
-
- if (sw13 != null) {
- printMatchActionOperationEntry(sw13, maEntry);
- try {
- sw13.pushFlow(maEntry);
- } catch (IOException e) {
- e.printStackTrace();
- return false;
- }
- }
- }
-
- PolicyInfo policyInfo = new PolicyInfo(pid, policyMatch, priority, tid);
- policyTable.put(pid, policyInfo);
-
- return true;
- }
-
- /**
- * Split the nodes IDs into multiple tunnel if Segment Stitching is required.
- * We assume that the first node ID is the one of source router, and the last
- * node ID is that of the destination router.
- *
- * @param route list of node IDs
- * @return List of the TunnelRoutInfo
- */
- private List<TunnelRouteInfo> getStitchingRule(List<String> route) {
-
- if (route.isEmpty() || route.size() < 3)
- return null;
-
- List<TunnelRouteInfo> rules = new ArrayList<TunnelRouteInfo>();
-
- Switch srcSw = this.getSwitchFromNodeId(route.get(0));
- if (srcSw == null) {
- log.warn("Switch is not found for Node SID {}", route.get(0));
- return null;
- }
- String srcDpid = srcSw.getDpid().toString();
-
- int i = 0;
- TunnelRouteInfo routeInfo = new TunnelRouteInfo();
- boolean checkNeighbor = false;
- String prevAdjacencySid = null;
- String prevNodeId = null;
-
- for (String nodeId: route) {
- // The first node ID is always the source router.
- // We assume that the first ID cannot be an Adjacency SID.
- if (i == 0) {
- srcSw = getSwitchFromNodeId(nodeId);
- if (srcDpid == null)
- srcDpid = srcSw.getDpid().toString();
- routeInfo.setSrcDpid(srcDpid);
- checkNeighbor = true;
- i++;
- }
- // if this is the first node ID to put the label stack..
- else if (i == 1) {
- if (checkNeighbor) {
- List<Dpid> fwdSws = getDpidIfNeighborOf(nodeId, srcSw);
- // if nodeId is NOT the neighbor of srcSw..
- if (fwdSws.isEmpty()) {
- fwdSws = getForwardingSwitchForNodeId(srcSw,nodeId);
- if (fwdSws == null || fwdSws.isEmpty()) {
- log.warn("There is no route from node {} to node {}",
- srcSw.getDpid(), nodeId);
- return null;
- }
- routeInfo.addRoute(nodeId);
- i++;
- }
- routeInfo.setFwdSwDpid(fwdSws);
- // we check only the next node ID of the source router
- checkNeighbor = false;
- }
- // if neighbor check is already done, then just add it
- else {
- routeInfo.addRoute(nodeId);
- i++;
- }
- }
- // if i > 1
- else {
- // If the adjacency SID is pushed and the next SID is the destination
- // of the adjacency SID, then do not add the SID.
- if (prevAdjacencySid != null) {
- if (isAdjacencySidNeighborOf(prevNodeId, prevAdjacencySid, nodeId)) {
- prevAdjacencySid = null;
- prevNodeId = nodeId;
- continue;
- }
- prevAdjacencySid = null;
- }
- routeInfo.addRoute(nodeId);
- i++;
- }
-
- // If the adjacency ID is added the label stack,
- // then we need to check if the next node is the destination of the adjacency SID
- if (isAdjacencySid(nodeId))
- prevAdjacencySid = nodeId;
-
- // If the number of labels reaches the limit, start over the procedure
- if (i == MAX_NUM_LABELS+1) {
-
- rules.add(routeInfo);
- routeInfo = new TunnelRouteInfo();
-
- if (isAdjacencySid(nodeId)) {
- // If the previous sub tunnel finishes with adjacency SID,
- // then we need to start the procedure from the adjacency
- // destination ID.
- List<Switch> destNodeList =
- getAdjacencyDestinationNode(prevNodeId, nodeId);
- if (destNodeList == null || destNodeList.isEmpty()) {
- log.warn("Cannot find destination node for adjacencySID {}",
- nodeId);
- return null;
- }
- // If the previous sub tunnel finishes with adjacency SID with
- // multiple ports, then we need to remove the adjacency Sid
- // from the previous sub tunnel and start the new sub tunnel
- // with the adjacency Sid. Technically, the new subtunnel
- // forward packets to the port assigned to the adjacency Sid
- // and the label stack starts with the next ID.
- // This is to avoid to install new policy rule to multiple nodes for stitching when the
- // adjacency Sid that has more than one port.
- if (destNodeList.size() > 1) {
- rules.get(rules.size()-1).route.remove(nodeId);
- srcSw = getSwitchFromNodeId(prevNodeId);
- List<Dpid> fwdSws = getDpidIfNeighborOf(nodeId, srcSw);
- routeInfo.setFwdSwDpid(fwdSws);
- routeInfo.setSrcDpid(srcSw.getDpid().toString());
- i = 1;
- checkNeighbor = false;
- continue;
- }
- else {
- srcSw = destNodeList.get(0);
- }
- }
- else {
- srcSw = getSwitchFromNodeId(nodeId);
- }
- srcDpid = srcSw.getDpid().toString();
- routeInfo.setSrcDpid(srcDpid);
- i = 1;
- checkNeighbor = true;
- }
-
- if (prevAdjacencySid == null)
- prevNodeId = nodeId;
- }
-
-
- if (i < MAX_NUM_LABELS+1 && (routeInfo.getFwdSwDpid() != null &&
- !routeInfo.getFwdSwDpid().isEmpty())) {
- rules.add(routeInfo);
- // NOTE: empty label stack can happen, but forwarding destination should be set
- }
-
- return rules;
}
/**
@@ -1548,53 +1211,22 @@
* @return
*/
public boolean removePolicy(String pid) {
- PolicyInfo policyInfo = policyTable.get(pid);
- if (policyInfo == null)
+ //Sanity check
+ SegmentRoutingPolicy policy = policyTable.get(pid);
+ if (policy == null) {
+ log.warn("Cannot find the policy {}", pid);
return false;
- PacketMatch policyMatch = policyInfo.match;
- String tid = policyInfo.tunnelId;
- int priority = policyInfo.priority;
-
- List<Action> actions = new ArrayList<>();
- int gropuId = 0; // dummy group ID
- GroupAction groupAction = new GroupAction();
- groupAction.setGroupId(gropuId);
- actions.add(groupAction);
-
- MatchAction matchAction = new MatchAction(new MatchActionId(
- matchActionId++),
- new SwitchPort((long) 0, (short) 0), policyMatch, priority,
- actions);
- MatchActionOperationEntry maEntry =
- new MatchActionOperationEntry(Operator.REMOVE, matchAction);
-
- TunnelInfo tunnelInfo = tunnelTable.get(tid);
- if (tunnelInfo == null)
+ }
+ if (policy.removePolicy()) {
+ policyTable.remove(pid);
+ log.debug("Policy {} is removed.", pid);
+ return true;
+ }
+ else {
+ log.warn("Faild to remove the policy {}", pid);
return false;
- List<TunnelRouteInfo> routes = tunnelInfo.routes;
-
- for (TunnelRouteInfo route : routes) {
- IOF13Switch sw13 = (IOF13Switch) floodlightProvider.getMasterSwitch(
- getSwId(route.srcSwDpid));
-
- if (sw13 == null) {
- return false;
- }
- else {
- printMatchActionOperationEntry(sw13, maEntry);
- try {
- sw13.pushFlow(maEntry);
- } catch (IOException e) {
- e.printStackTrace();
- log.debug("policy remove failed due to pushFlow() exception");
- return false;
- }
- }
}
- policyTable.remove(pid);
- log.debug("Policy {} is removed.", pid);
- return true;
}
public enum removeTunnelMessages{
@@ -1636,183 +1268,51 @@
public removeTunnelMessages removeTunnel(String tunnelId) {
// Check if the tunnel is used for any policy
- for (PolicyInfo policyInfo: policyTable.values()) {
- if (policyInfo.tunnelId.equals(tunnelId)) {
- log.debug("Tunnel {} is still used for the policy {}.",
- policyInfo.policyId, tunnelId);
- return removeTunnelMessages.ERROR_REFERENCED;
+ for (SegmentRoutingPolicy policy: policyTable.values()) {
+ if (policy.getType() == PolicyType.TUNNEL_FLOW) {
+ String tid = ((SegmentRoutingPolicyTunnel)policy).getTunnelId();
+ if (tid.equals(tunnelId)) {
+ log.debug("Tunnel {} is still used for the policy {}.",
+ policy.getPolicyId(), tunnelId);
+ return removeTunnelMessages.ERROR_REFERENCED;
+ }
}
}
- TunnelInfo tunnelInfo = tunnelTable.get(tunnelId);
- if (tunnelInfo == null)
+ SegmentRoutingTunnel tunnel = tunnelTable.get(tunnelId);
+ if (tunnel == null) {
+ log.warn("Tunnul object does not exist {}", tunnelId);
return removeTunnelMessages.ERROR_TUNNEL;
-
- List<TunnelRouteInfo> routes = tunnelInfo.routes;
- for (TunnelRouteInfo route: routes) {
- IOF13Switch sw13 = (IOF13Switch) floodlightProvider.getMasterSwitch(
- getSwId(route.srcSwDpid));
-
- if (sw13 == null) {
- return removeTunnelMessages.ERROR_SWITCH;
+ }
+ else {
+ if (tunnel.removeTunnel()) {
+ tunnelTable.remove(tunnelId);
+ log.debug("Tunnel {} was removed successfully.", tunnelId);
+ return removeTunnelMessages.SUCCESS;
}
else {
- if (!sw13.removeGroup(route.getGroupId())) {
- log.warn("Faied to remove the tunnel {} at driver",
- tunnelId);
- return removeTunnelMessages.ERROR_DRIVER;
- }
+ log.warn("Faild in removing the tunnel {}", tunnelId);
+ return removeTunnelMessages.ERROR_DRIVER;
}
}
-
- tunnelTable.remove(tunnelId);
- log.debug("Tunnel {} was removed successfully.", tunnelId);
-
- return removeTunnelMessages.SUCCESS;
}
// ************************************
// Utility functions
// ************************************
- /**
- * Get the destination Nodes of the adjacency Sid
- *
- * @param nodeId node ID of the adjacency Sid
- * @param adjacencySid adjacency Sid
- * @return List of Switch, empty list if not found
- */
- private List<Switch> getAdjacencyDestinationNode(String nodeId, String adjacencySid) {
- List<Switch> dstSwList = new ArrayList<Switch>();
+ public long getNextMatchActionID() {
+ return this.matchActionId++;
+ }
+
+ public List<Integer> getAdacencyPorts(int nodeSid, int adjacencySid) {
HashMap<Integer, List<Integer>> adjacencySidInfo =
- adjacencySidTable.get(Integer.valueOf(nodeId));
- List<Integer> ports = adjacencySidInfo.get(Integer.valueOf(adjacencySid));
- Switch srcSw = getSwitchFromNodeId(nodeId);
- for (Integer port: ports) {
- for (Link link: srcSw.getOutgoingLinks()) {
- if (link.getSrcPort().getPortNumber().value() == port) {
- dstSwList.add(link.getDstSwitch());
- }
- }
- }
-
- return dstSwList;
-
- }
-
- /**
- * Get the DPID of the router with node ID IF the node ID is the neighbor of the
- * Switch srcSW.
- * If the nodeId is the adjacency Sid, then it returns the destination router DPIDs.
- *
- * @param nodeId Node ID to check
- * @param srcSw target Switch
- * @return List of DPID of nodeId, empty list if the nodeId is not the neighbor of srcSW
- */
- private List<Dpid> getDpidIfNeighborOf(String nodeId, Switch srcSw) {
- List<Dpid> fwdSws = new ArrayList<Dpid>();
- // if the nodeID is the adjacency ID, then we need to regard it as the
- // neighbor node ID and need to return the destination router DPID(s)
- if (isAdjacencySid(nodeId)) {
- String srcNodeId = this.getMplsLabel(srcSw.getDpid().toString());
- HashMap<Integer, List<Integer>> adjacencySidInfo =
- adjacencySidTable.get(Integer.valueOf(srcNodeId));
- List<Integer> ports = adjacencySidInfo.get(Integer.valueOf(nodeId));
-
- for (Integer port: ports) {
- for (Link link: srcSw.getOutgoingLinks()) {
- if (link.getSrcPort().getPortNumber().value() == port) {
- fwdSws.add(link.getDstSwitch().getDpid());
- }
- }
- }
- }
- else {
- List<Dpid> fwdSwDpids = getForwardingSwitchForNodeId(srcSw,nodeId);
- if (fwdSwDpids == null || fwdSwDpids.isEmpty()) {
- log.warn("There is no route from node {} to node {}",
- srcSw.getDpid(), nodeId);
- return fwdSws;
- }
-
- for (Dpid dpid: fwdSwDpids) {
- if (getMplsLabel(dpid.toString()).toString().equals(nodeId)) {
- fwdSws.add(dpid);
- break;
- }
- }
- }
-
- return fwdSws;
- }
-
- /**
- * Get port numbers of the neighbor set.
- * If ECMP in transit router is not supported, then only one port should be returned
- * regardless of number of nodes in neighbor set.
- *
- * @param srcSwDpid source switch
- * @param ns Neighbor set of the switch
- * @return List of PortNumber, null if not found
- */
- private List<PortNumber> getPortsFromNeighborSet(String srcSwDpid, NeighborSet ns) {
-
- List<PortNumber> portList = new ArrayList<PortNumber>();
- Switch srcSwitch = mutableTopology.getSwitch(new Dpid(srcSwDpid));
- if (srcSwitch == null)
+ adjacencySidTable.get(Integer.valueOf(nodeSid));
+ if (adjacencySidInfo == null)
return null;
- IOF13Switch srcSwitch13 = (IOF13Switch)floodlightProvider.getMasterSwitch(
- getSwId(srcSwitch.getDpid().toString()));
-
- for (Dpid neighborDpid: ns.getDpids()) {
- if (srcSwitch13 instanceof OFSwitchImplDellOSR &&
- ns.getDpids().size() == 1) {
- Switch dstSwitch = mutableTopology.getSwitch(neighborDpid);
- if (isTransitRouter(srcSwitch) && isTransitRouter(dstSwitch)) {
- Link link = srcSwitch.getLinkToNeighbor(neighborDpid);
- portList.add(link.getSrcPort().getNumber());
- break;
- }
- }
- else {
- for (Link link: srcSwitch.getOutgoingLinks()) {
- if (link.getDstSwitch().getDpid().equals(neighborDpid)) {
- portList.add(link.getSrcPort().getNumber());
- }
- }
- }
- }
-
- return portList;
- }
-
- /**
- * Check whether the router with preNodeid is connected to the router
- * with nodeId via adjacencySid or not
- *
- * @param prevNodeId the router node ID of the adjacencySid
- * @param adjacencySid adjacency SID
- * @param nodeId the router node ID to check
- * @return
- */
- private boolean isAdjacencySidNeighborOf(String prevNodeId, String adjacencySid, String nodeId) {
-
- HashMap<Integer, List<Integer>> adjacencySidInfo = adjacencySidTable.get(Integer.valueOf(prevNodeId));
- List<Integer> ports = adjacencySidInfo.get(Integer.valueOf(adjacencySid));
-
- for (Integer port: ports) {
- Switch sw = getSwitchFromNodeId(prevNodeId);
- for (Link link: sw.getOutgoingLinks()) {
- if (link.getSrcPort().getPortNumber().value() == port) {
- if (getMplsLabel(link.getDstPort().getDpid().toString()).equals(nodeId)) {
- return true;
- }
- }
- }
- }
-
- return false;
+ else
+ return adjacencySidInfo.get(Integer.valueOf(adjacencySid));
}
/**
@@ -1821,7 +1321,7 @@
* @param nodeId to check
* @return true if the node ID is the adjacency ID, false otherwise
*/
- private boolean isAdjacencySid(String nodeId) {
+ public boolean isAdjacencySid(String nodeId) {
// XXX The rule might change
if (Integer.parseInt(nodeId) > 10000)
return true;
@@ -1977,7 +1477,7 @@
* @param sw router switch to check
* @return true if the switch is the transit router, false otherwise
*/
- private boolean isTransitRouter(Switch sw) {
+ public boolean isTransitRouter(Switch sw) {
int i = 0;
for(Switch neighbor: sw.getNeighbors()) {
i++;
@@ -1997,7 +1497,7 @@
* @param nodeId destination node Id
* @return list of switch DPID to forward packets to
*/
- private List<Dpid> getForwardingSwitchForNodeId(Switch srcSw, String nodeId) {
+ public List<Dpid> getForwardingSwitchForNodeId(Switch srcSw, String nodeId) {
List<Dpid> fwdSws = new ArrayList<Dpid>();
Switch destSw = null;
@@ -2048,7 +1548,7 @@
* @param nodeId node ID for switch
* @return Switch
*/
- private Switch getSwitchFromNodeId(String nodeId) {
+ public Switch getSwitchFromNodeId(String nodeId) {
for (Switch sw : mutableTopology.getSwitches()) {
String id = sw.getStringAttribute("nodeSid");
@@ -2115,7 +1615,7 @@
* @param dipid DPID of the switch
* @return MPLS label for the switch
*/
- private String getMplsLabel(String dpid) {
+ public String getMplsLabel(String dpid) {
String mplsLabel = null;
for (Switch sw : mutableTopology.getSwitches()) {
@@ -2269,6 +1769,19 @@
arpHandler.sendArpRequest(sw, destinationAddress, inPort);
}
+ public IOF13Switch getIOF13Switch(String dpid) {
+
+ IOF13Switch targetSw = (IOF13Switch) floodlightProvider.getMasterSwitch(
+ getSwId(dpid));
+
+ return targetSw;
+ }
+
+ public Switch getSwitch(String dpid) {
+ return mutableTopology.getSwitch(new Dpid(dpid));
+ }
+
+
// ************************************
// Test functions
// ************************************
@@ -2371,27 +1884,7 @@
}
- /**
- * print tunnel info - used only for debugging.
- * @param targetSw
- *
- * @param fwdSwDpids
- * @param ids
- * @param tunnelId
- */
- private void printTunnelInfo(String targetSw, String tunnelId,
- List<String> ids, NeighborSet ns) {
- StringBuilder logStr = new StringBuilder("In switch " +
- targetSw + ", create a tunnel " + tunnelId + " " + " of push ");
- for (String id: ids)
- logStr.append(id + "-");
- logStr.append(" output to ");
- for (Dpid dpid: ns.getDpids())
- logStr.append(dpid + " - ");
- log.debug(logStr.toString());
-
- }
/**
* Debugging function to print out the Match Action Entry
@@ -2399,7 +1892,7 @@
*
* @param maEntry
*/
- private void printMatchActionOperationEntry(
+ public void printMatchActionOperationEntry(
IOF13Switch sw13, MatchActionOperationEntry maEntry) {
StringBuilder logStr = new StringBuilder("In switch " + sw13.getId() + ", ");
@@ -2628,4 +2121,5 @@
}
+
}
diff --git a/src/main/java/net/onrc/onos/apps/segmentrouting/web/SegmentRouterPolicyResource.java b/src/main/java/net/onrc/onos/apps/segmentrouting/web/SegmentRouterPolicyResource.java
index a1a8a71..0df169e 100644
--- a/src/main/java/net/onrc/onos/apps/segmentrouting/web/SegmentRouterPolicyResource.java
+++ b/src/main/java/net/onrc/onos/apps/segmentrouting/web/SegmentRouterPolicyResource.java
@@ -7,7 +7,9 @@
import java.util.List;
import net.onrc.onos.apps.segmentrouting.ISegmentRoutingService;
-import net.onrc.onos.apps.segmentrouting.SegmentRoutingManager.PolicyInfo;
+import net.onrc.onos.apps.segmentrouting.SegmentRoutingPolicy;
+import net.onrc.onos.apps.segmentrouting.SegmentRoutingPolicy.PolicyType;
+import net.onrc.onos.apps.segmentrouting.SegmentRoutingPolicyTunnel;
import net.onrc.onos.core.matchaction.match.PacketMatch;
import net.onrc.onos.core.packet.IPv4;
import net.onrc.onos.core.util.IPv4Net;
@@ -111,12 +113,15 @@
(ISegmentRoutingService) getContext().getAttributes().
get(ISegmentRoutingService.class.getCanonicalName());
List<SegmentRouterPolicyInfo> policyList = new ArrayList<SegmentRouterPolicyInfo>();
- Collection<PolicyInfo> policies = segmentRoutingService.getPoclicyTable();
- Iterator<PolicyInfo> piI = policies.iterator();
+ Collection<SegmentRoutingPolicy> policies = segmentRoutingService.getPoclicyTable();
+ Iterator<SegmentRoutingPolicy> piI = policies.iterator();
while(piI.hasNext()){
- PolicyInfo policy = piI.next();
+ SegmentRoutingPolicy policy = piI.next();
String policyId = policy.getPolicyId();
- String tunnelId = policy.getTunnelId();
+ String tunnelId = null;
+ if (policy.getType() == PolicyType.TUNNEL_FLOW) {
+ tunnelId = ((SegmentRoutingPolicyTunnel)policy).getTunnelId();
+ }
int priority = policy.getPriority();
String policyType = policy.getType().name();
PacketMatch flowEntries = policy.getMatch();
diff --git a/src/main/java/net/onrc/onos/apps/segmentrouting/web/SegmentRouterTunnelResource.java b/src/main/java/net/onrc/onos/apps/segmentrouting/web/SegmentRouterTunnelResource.java
index 7990e48..63b26b6 100644
--- a/src/main/java/net/onrc/onos/apps/segmentrouting/web/SegmentRouterTunnelResource.java
+++ b/src/main/java/net/onrc/onos/apps/segmentrouting/web/SegmentRouterTunnelResource.java
@@ -3,16 +3,16 @@
import java.io.IOException;
import java.util.ArrayList;
import java.util.Collection;
-import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
-import java.util.Map;
import net.onrc.onos.apps.segmentrouting.ISegmentRoutingService;
-import net.onrc.onos.apps.segmentrouting.SegmentRoutingManager.PolicyInfo;
-import net.onrc.onos.apps.segmentrouting.SegmentRoutingManager.TunnelInfo;
-import net.onrc.onos.apps.segmentrouting.SegmentRoutingManager.TunnelRouteInfo;
import net.onrc.onos.apps.segmentrouting.SegmentRoutingManager.removeTunnelMessages;
+import net.onrc.onos.apps.segmentrouting.SegmentRoutingPolicy;
+import net.onrc.onos.apps.segmentrouting.SegmentRoutingPolicy.PolicyType;
+import net.onrc.onos.apps.segmentrouting.SegmentRoutingPolicyTunnel;
+import net.onrc.onos.apps.segmentrouting.SegmentRoutingTunnel;
+import net.onrc.onos.apps.segmentrouting.SegmentRoutingTunnel.TunnelRouteInfo;
import org.codehaus.jackson.map.ObjectMapper;
import org.restlet.resource.Delete;
@@ -79,18 +79,19 @@
ISegmentRoutingService segmentRoutingService =
(ISegmentRoutingService) getContext().getAttributes().
get(ISegmentRoutingService.class.getCanonicalName());
- Iterator<TunnelInfo> ttI = segmentRoutingService.getTunnelTable().iterator();
+ Iterator<SegmentRoutingTunnel> ttI = segmentRoutingService.getTunnelTable().iterator();
List<SegmentRouterTunnelInfo> infoList = new ArrayList<SegmentRouterTunnelInfo>();
while(ttI.hasNext()){
- TunnelInfo tunnelInfo = ttI.next();
+ SegmentRoutingTunnel tunnelInfo = ttI.next();
List<Integer> tunnelPath = tunnelInfo.getLabelids();
String tunnelId = tunnelInfo.getTunnelId();
- Collection<PolicyInfo> policies = segmentRoutingService.getPoclicyTable();
- Iterator<PolicyInfo> piI = policies.iterator();
+ Collection<SegmentRoutingPolicy> policies = segmentRoutingService.getPoclicyTable();
+ Iterator<SegmentRoutingPolicy> piI = policies.iterator();
String policiesId = "";
while(piI.hasNext()){
- PolicyInfo policy = piI.next();
- if(policy.getTunnelId().equals(tunnelId)){
+ SegmentRoutingPolicy policy = piI.next();
+ if(policy.getType() == PolicyType.TUNNEL_FLOW &&
+ ((SegmentRoutingPolicyTunnel)policy).getTunnelId().equals(tunnelId)){
policiesId += (policy.getPolicyId()+",");
}
}
@@ -103,7 +104,7 @@
while(trI.hasNext()){
TunnelRouteInfo label = trI.next();
labelStack.add(label.getRoute());
- Integer gId = segmentRoutingService.getTunnelGroupId(tunnelId,
+ Integer gId = segmentRoutingService.getTunnelGroupId(tunnelId,
label.getSrcSwDpid());
dpidGroup.add(label.getSrcSwDpid() + "/"+ gId);
}