A set of fixes to ensure that the FlowRuleManager can correctly account for flows
from the dataplane in a multi-table pipeline scenario
Change-Id: I9ca3ef9a77781f126a13538647c824b27f77101c
diff --git a/providers/openflow/device/src/test/java/org/onosproject/provider/of/device/impl/OpenFlowDeviceProviderTest.java b/providers/openflow/device/src/test/java/org/onosproject/provider/of/device/impl/OpenFlowDeviceProviderTest.java
index e92d1be..c83da17 100644
--- a/providers/openflow/device/src/test/java/org/onosproject/provider/of/device/impl/OpenFlowDeviceProviderTest.java
+++ b/providers/openflow/device/src/test/java/org/onosproject/provider/of/device/impl/OpenFlowDeviceProviderTest.java
@@ -49,6 +49,7 @@
import org.onosproject.openflow.controller.OpenFlowSwitchListener;
import org.onosproject.openflow.controller.PacketListener;
import org.onosproject.openflow.controller.RoleState;
+import org.onosproject.openflow.controller.OpenFlowSwitch.TableType;
import org.projectfloodlight.openflow.protocol.OFFactory;
import org.projectfloodlight.openflow.protocol.OFMessage;
import org.projectfloodlight.openflow.protocol.OFPortDesc;
@@ -56,6 +57,7 @@
import org.projectfloodlight.openflow.protocol.OFPortStatus;
import org.projectfloodlight.openflow.protocol.ver10.OFFactoryVer10;
import org.projectfloodlight.openflow.types.OFPort;
+import org.projectfloodlight.openflow.types.TableId;
import com.google.common.collect.HashMultimap;
import com.google.common.collect.Lists;
@@ -310,10 +312,6 @@
}
@Override
- public void sendMsg(OFMessage msg, TableType tableType) {
- }
-
- @Override
public void handleMessage(OFMessage fromSwitch) {
}
@@ -395,6 +393,17 @@
return "1.2.3.4:1";
}
+ @Override
+ public TableType getTableType(TableId tid) {
+ return TableType.NONE;
+ }
+
+ @Override
+ public void transformAndSendMsg(OFMessage msg, TableType tableType) {
+ // TODO Auto-generated method stub
+ }
+
+
}
}
diff --git a/providers/openflow/flow/src/main/java/org/onosproject/provider/of/flow/impl/FlowEntryBuilder.java b/providers/openflow/flow/src/main/java/org/onosproject/provider/of/flow/impl/FlowEntryBuilder.java
index 0b9b0cd..f0e4f84 100644
--- a/providers/openflow/flow/src/main/java/org/onosproject/provider/of/flow/impl/FlowEntryBuilder.java
+++ b/providers/openflow/flow/src/main/java/org/onosproject/provider/of/flow/impl/FlowEntryBuilder.java
@@ -34,6 +34,7 @@
import org.onosproject.net.flow.FlowEntry;
import org.onosproject.net.flow.FlowEntry.FlowEntryState;
import org.onosproject.net.flow.FlowRule;
+import org.onosproject.net.flow.FlowRule.Type;
import org.onosproject.net.flow.TrafficSelector;
import org.onosproject.net.flow.TrafficTreatment;
import org.onosproject.openflow.controller.Dpid;
@@ -87,6 +88,7 @@
public enum FlowType { STAT, REMOVED, MOD }
private final FlowType type;
+ private Type tableType = FlowRule.Type.DEFAULT;
public FlowEntryBuilder(Dpid dpid, OFFlowStatsEntry entry) {
@@ -99,6 +101,17 @@
this.type = FlowType.STAT;
}
+ public FlowEntryBuilder(Dpid dpid, OFFlowStatsEntry entry, Type tableType) {
+ this.stat = entry;
+ this.match = entry.getMatch();
+ this.actions = getActions(entry);
+ this.dpid = dpid;
+ this.removed = null;
+ this.flowMod = null;
+ this.type = FlowType.STAT;
+ this.tableType = tableType;
+ }
+
public FlowEntryBuilder(Dpid dpid, OFFlowRemoved removed) {
this.match = removed.getMatch();
this.removed = removed;
@@ -127,7 +140,8 @@
case STAT:
rule = new DefaultFlowRule(DeviceId.deviceId(Dpid.uri(dpid)),
buildSelector(), buildTreatment(), stat.getPriority(),
- stat.getCookie().getValue(), stat.getIdleTimeout(), false);
+ stat.getCookie().getValue(), stat.getIdleTimeout(), false,
+ tableType);
return new DefaultFlowEntry(rule, FlowEntryState.ADDED,
stat.getDurationSec(), stat.getPacketCount().getValue(),
stat.getByteCount().getValue());
diff --git a/providers/openflow/flow/src/main/java/org/onosproject/provider/of/flow/impl/FlowModBuilderVer13.java b/providers/openflow/flow/src/main/java/org/onosproject/provider/of/flow/impl/FlowModBuilderVer13.java
index 00bb197..4c2dc93 100644
--- a/providers/openflow/flow/src/main/java/org/onosproject/provider/of/flow/impl/FlowModBuilderVer13.java
+++ b/providers/openflow/flow/src/main/java/org/onosproject/provider/of/flow/impl/FlowModBuilderVer13.java
@@ -266,6 +266,8 @@
return OpenFlowSwitch.TableType.ETHER;
case COS:
return OpenFlowSwitch.TableType.COS;
+ case FIRST:
+ return OpenFlowSwitch.TableType.FIRST;
default:
return OpenFlowSwitch.TableType.NONE;
}
diff --git a/providers/openflow/flow/src/main/java/org/onosproject/provider/of/flow/impl/OpenFlowRuleProvider.java b/providers/openflow/flow/src/main/java/org/onosproject/provider/of/flow/impl/OpenFlowRuleProvider.java
index 928f7b0..bf4c73f 100644
--- a/providers/openflow/flow/src/main/java/org/onosproject/provider/of/flow/impl/OpenFlowRuleProvider.java
+++ b/providers/openflow/flow/src/main/java/org/onosproject/provider/of/flow/impl/OpenFlowRuleProvider.java
@@ -45,26 +45,17 @@
import org.onosproject.openflow.controller.OpenFlowSwitch;
import org.onosproject.openflow.controller.OpenFlowSwitchListener;
import org.onosproject.openflow.controller.RoleState;
-import org.projectfloodlight.openflow.protocol.OFActionType;
import org.projectfloodlight.openflow.protocol.OFBarrierRequest;
import org.projectfloodlight.openflow.protocol.OFErrorMsg;
import org.projectfloodlight.openflow.protocol.OFErrorType;
import org.projectfloodlight.openflow.protocol.OFFlowMod;
import org.projectfloodlight.openflow.protocol.OFFlowRemoved;
-import org.projectfloodlight.openflow.protocol.OFFlowStatsEntry;
import org.projectfloodlight.openflow.protocol.OFFlowStatsReply;
-import org.projectfloodlight.openflow.protocol.OFInstructionType;
import org.projectfloodlight.openflow.protocol.OFMessage;
import org.projectfloodlight.openflow.protocol.OFPortStatus;
import org.projectfloodlight.openflow.protocol.OFStatsReply;
import org.projectfloodlight.openflow.protocol.OFStatsType;
-import org.projectfloodlight.openflow.protocol.OFVersion;
-import org.projectfloodlight.openflow.protocol.action.OFAction;
-import org.projectfloodlight.openflow.protocol.action.OFActionOutput;
import org.projectfloodlight.openflow.protocol.errormsg.OFFlowModFailedErrorMsg;
-import org.projectfloodlight.openflow.protocol.instruction.OFInstruction;
-import org.projectfloodlight.openflow.protocol.instruction.OFInstructionApplyActions;
-import org.projectfloodlight.openflow.types.OFPort;
import org.slf4j.Logger;
import java.util.Collections;
@@ -85,8 +76,6 @@
@Component(immediate = true)
public class OpenFlowRuleProvider extends AbstractProvider implements FlowRuleProvider {
- private static final int LOWEST_PRIORITY = 0;
-
private final Logger log = getLogger(getClass());
@Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
@@ -160,7 +149,7 @@
Optional.empty()).buildFlowAdd());
} else {
OpenFlowSwitch.TableType type = getTableType(flowRule.type());
- sw.sendMsg(FlowModBuilder.builder(flowRule, sw.factory(),
+ sw.transformAndSendMsg(FlowModBuilder.builder(flowRule, sw.factory(),
Optional.empty()).buildFlowAdd(),
type);
}
@@ -181,7 +170,7 @@
sw.sendMsg(FlowModBuilder.builder(flowRule, sw.factory(),
Optional.empty()).buildFlowDel());
} else {
- sw.sendMsg(FlowModBuilder.builder(flowRule, sw.factory(),
+ sw.transformAndSendMsg(FlowModBuilder.builder(flowRule, sw.factory(),
Optional.empty()).buildFlowDel(), getTableType(flowRule.type()));
}
}
@@ -225,7 +214,7 @@
if (fbe.target().type() == FlowRule.Type.DEFAULT) {
sw.sendMsg(mod);
} else {
- sw.sendMsg(mod, getTableType(fbe.target().type()));
+ sw.transformAndSendMsg(mod, getTableType(fbe.target().type()));
}
}
OFBarrierRequest.Builder builder = sw.factory()
@@ -253,12 +242,38 @@
return OpenFlowSwitch.TableType.ETHER;
case COS:
return OpenFlowSwitch.TableType.COS;
+ case FIRST:
+ return OpenFlowSwitch.TableType.FIRST;
default:
return OpenFlowSwitch.TableType.NONE;
}
}
+ private FlowRule.Type getType(OpenFlowSwitch.TableType tableType) {
+ switch (tableType) {
+ case NONE:
+ return FlowRule.Type.DEFAULT;
+ case IP:
+ return FlowRule.Type.IP;
+ case MPLS:
+ return FlowRule.Type.MPLS;
+ case ACL:
+ return FlowRule.Type.ACL;
+ case VLAN_MPLS:
+ return FlowRule.Type.VLAN_MPLS;
+ case VLAN:
+ return FlowRule.Type.VLAN;
+ case ETHER:
+ return FlowRule.Type.ETHER;
+ case COS:
+ return FlowRule.Type.COS;
+ case FIRST:
+ return FlowRule.Type.FIRST;
+ default:
+ return FlowRule.Type.DEFAULT;
+ }
+ }
private class InternalFlowProvider
@@ -354,41 +369,18 @@
private void pushFlowMetrics(Dpid dpid, OFFlowStatsReply replies) {
DeviceId did = DeviceId.deviceId(Dpid.uri(dpid));
+ OpenFlowSwitch sw = controller.getSwitch(dpid);
List<FlowEntry> flowEntries = replies.getEntries().stream()
- .filter(entry -> !tableMissRule(dpid, entry))
- .map(entry -> new FlowEntryBuilder(dpid, entry).build())
+ .map(entry -> new FlowEntryBuilder(dpid, entry,
+ getType(sw.getTableType(entry.getTableId())))
+ .build())
.collect(Collectors.toList());
providerService.pushFlowMetrics(did, flowEntries);
}
- private boolean tableMissRule(Dpid dpid, OFFlowStatsEntry reply) {
- if (reply.getMatch().getMatchFields().iterator().hasNext()) {
- return false;
- }
- if (reply.getVersion().equals(OFVersion.OF_10)) {
- return reply.getPriority() == LOWEST_PRIORITY
- && reply.getActions().isEmpty();
- }
- for (OFInstruction ins : reply.getInstructions()) {
- if (ins.getType() == OFInstructionType.APPLY_ACTIONS) {
- OFInstructionApplyActions apply = (OFInstructionApplyActions) ins;
- List<OFAction> acts = apply.getActions();
- for (OFAction act : acts) {
- if (act.getType() == OFActionType.OUTPUT) {
- OFActionOutput out = (OFActionOutput) act;
- if (out.getPort() == OFPort.CONTROLLER) {
- return true;
- }
- }
- }
- }
- }
- return false;
- }
-
}
/**
diff --git a/providers/openflow/group/src/test/java/org/onosproject/provider/of/group/impl/OpenFlowGroupProviderTest.java b/providers/openflow/group/src/test/java/org/onosproject/provider/of/group/impl/OpenFlowGroupProviderTest.java
index 402e0ac..2cd2e55 100644
--- a/providers/openflow/group/src/test/java/org/onosproject/provider/of/group/impl/OpenFlowGroupProviderTest.java
+++ b/providers/openflow/group/src/test/java/org/onosproject/provider/of/group/impl/OpenFlowGroupProviderTest.java
@@ -1,6 +1,7 @@
package org.onosproject.provider.of.group.impl;
import com.google.common.collect.Lists;
+
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
@@ -41,6 +42,7 @@
import org.projectfloodlight.openflow.protocol.OFVersion;
import org.projectfloodlight.openflow.protocol.errormsg.OFGroupModFailedErrorMsg;
import org.projectfloodlight.openflow.types.OFGroup;
+import org.projectfloodlight.openflow.types.TableId;
import java.util.Collection;
import java.util.List;
@@ -310,11 +312,6 @@
}
@Override
- public void sendMsg(OFMessage msg, TableType tableType) {
-
- }
-
- @Override
public void handleMessage(OFMessage fromSwitch) {
}
@@ -398,5 +395,15 @@
public String channelId() {
return null;
}
+
+ @Override
+ public TableType getTableType(TableId tid) {
+ return TableType.NONE;
+ }
+
+ @Override
+ public void transformAndSendMsg(OFMessage msg, TableType tableType) {
+ // TODO Auto-generated method stub
+ }
}
}
\ No newline at end of file
diff --git a/providers/openflow/link/src/test/java/org/onosproject/provider/of/link/impl/OpenFlowLinkProviderTest.java b/providers/openflow/link/src/test/java/org/onosproject/provider/of/link/impl/OpenFlowLinkProviderTest.java
index 311a728..27138e1 100644
--- a/providers/openflow/link/src/test/java/org/onosproject/provider/of/link/impl/OpenFlowLinkProviderTest.java
+++ b/providers/openflow/link/src/test/java/org/onosproject/provider/of/link/impl/OpenFlowLinkProviderTest.java
@@ -46,6 +46,7 @@
import org.onosproject.openflow.controller.OpenflowControllerAdapter;
import org.onosproject.openflow.controller.PacketListener;
import org.onosproject.openflow.controller.RoleState;
+import org.onosproject.openflow.controller.OpenFlowSwitch.TableType;
import org.onlab.packet.Ethernet;
import org.onlab.packet.ONLabLddp;
import org.projectfloodlight.openflow.protocol.OFFactory;
@@ -56,6 +57,7 @@
import org.projectfloodlight.openflow.protocol.OFPortStatus;
import org.projectfloodlight.openflow.protocol.ver10.OFFactoryVer10;
import org.projectfloodlight.openflow.types.OFPort;
+import org.projectfloodlight.openflow.types.TableId;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
@@ -414,10 +416,6 @@
}
@Override
- public void sendMsg(OFMessage msg, TableType tableType) {
- }
-
- @Override
public void handleMessage(OFMessage fromSwitch) {
}
@@ -499,6 +497,15 @@
return "1.2.3.4:1";
}
+ @Override
+ public TableType getTableType(TableId tid) {
+ return TableType.NONE;
+ }
+
+ @Override
+ public void transformAndSendMsg(OFMessage msg, TableType tableType) {
+ // TODO Auto-generated method stub
+ }
}
}
diff --git a/providers/openflow/packet/src/test/java/org/onosproject/provider/of/packet/impl/OpenFlowPacketProviderTest.java b/providers/openflow/packet/src/test/java/org/onosproject/provider/of/packet/impl/OpenFlowPacketProviderTest.java
index 9f03527..02e604d 100644
--- a/providers/openflow/packet/src/test/java/org/onosproject/provider/of/packet/impl/OpenFlowPacketProviderTest.java
+++ b/providers/openflow/packet/src/test/java/org/onosproject/provider/of/packet/impl/OpenFlowPacketProviderTest.java
@@ -49,6 +49,7 @@
import org.onosproject.openflow.controller.OpenFlowSwitchListener;
import org.onosproject.openflow.controller.PacketListener;
import org.onosproject.openflow.controller.RoleState;
+import org.onosproject.openflow.controller.OpenFlowSwitch.TableType;
import org.onlab.packet.ARP;
import org.onlab.packet.Ethernet;
import org.projectfloodlight.openflow.protocol.OFFactory;
@@ -60,6 +61,7 @@
import org.projectfloodlight.openflow.types.MacAddress;
import org.projectfloodlight.openflow.types.OFBufferId;
import org.projectfloodlight.openflow.types.OFPort;
+import org.projectfloodlight.openflow.types.TableId;
import com.google.common.collect.Lists;
import com.google.common.collect.Sets;
@@ -347,10 +349,6 @@
}
@Override
- public void sendMsg(OFMessage msg, TableType tableType) {
- }
-
- @Override
public void handleMessage(OFMessage fromSwitch) {
}
@@ -432,6 +430,17 @@
return "1.2.3.4:1";
}
+ @Override
+ public TableType getTableType(TableId tid) {
+ return TableType.NONE;
+ }
+
+ @Override
+ public void transformAndSendMsg(OFMessage msg, TableType tableType) {
+ // TODO Auto-generated method stub
+
+ }
+
}
}