Added initial implementation (untested) of code (controlled by REST API)
for measuring the performance of writing Flow state to the Network MAP.
Currently, the semantics are:
1. Call multiple times the following REST call to store internally
each flow:
http://localhost:8080/wm/flow/measurement-store-path/json
Each call is similar to the "add-shortest-path" REST call
when adding a regular flow: the JSON object contains the endpoints
and the match conditions.
The "measurement-store-path" Flow is stored internally and will
be used later for measurement purpose.
2. Use the following REST call to start the measurements:
http://localhost:8080/wm/flow/measurement-install-paths/{num-threads}/json
The "num-threads" argument is used to specify how many threads should
be used to install the measurement flows.
3. Use the following REST call to obtain how long time (in nanoseconds)
it took to install the measurement flows in the Network MAP:
http://localhost:8080/wm/flow/measurement-get-install-paths-time-nsec/json
4. Use the following REST call to clear the measurement flows that
were stored internally in Step 1:
http://localhost:8080/wm/flow/measurement-clear-all-paths/json
Note that in Step 4 the installed Flows are NOT deleted from the
Network MAP.
NOTE: Step (2) and (3) can be repeated multiple times (e.g., for a different
number of theads) for the same set of Flows that were stored in Step (1).
However, it might be desirable that Step (3) is followed by an explicit
deletion of the installed Flows from the Network MAP (and the switches).
diff --git a/src/main/java/net/floodlightcontroller/flowcache/web/FlowWebRoutable.java b/src/main/java/net/floodlightcontroller/flowcache/web/FlowWebRoutable.java
index 962dbbb..9fa5e63 100644
--- a/src/main/java/net/floodlightcontroller/flowcache/web/FlowWebRoutable.java
+++ b/src/main/java/net/floodlightcontroller/flowcache/web/FlowWebRoutable.java
@@ -22,6 +22,10 @@
router.attach("/getall-by-endpoints/{src-dpid}/{src-port}/{dst-dpid}/{dst-port}/json", GetAllFlowsByEndpointsResource.class);
router.attach("/getall/json", GetAllFlowsResource.class);
router.attach("/getsummary/{flow-id}/{max-flows}/json", GetSummaryFlowsResource.class);
+ router.attach("/measurement-store-path/json", MeasurementStorePathFlowResource.class);
+ router.attach("/measurement-install-paths/{num-threads}/json", MeasurementInstallPathsFlowResource.class);
+ router.attach("/measurement-get-install-paths-time-nsec/json", MeasurementGetInstallPathsTimeNsecFlowResource.class);
+ router.attach("/measurement-clear-all-paths/json", MeasurementClearAllPathsFlowResource.class);
return router;
}
diff --git a/src/main/java/net/floodlightcontroller/flowcache/web/MeasurementClearAllPathsFlowResource.java b/src/main/java/net/floodlightcontroller/flowcache/web/MeasurementClearAllPathsFlowResource.java
new file mode 100644
index 0000000..f69180d
--- /dev/null
+++ b/src/main/java/net/floodlightcontroller/flowcache/web/MeasurementClearAllPathsFlowResource.java
@@ -0,0 +1,35 @@
+package net.floodlightcontroller.flowcache.web;
+
+import net.floodlightcontroller.flowcache.IFlowService;
+import net.floodlightcontroller.util.FlowId;
+
+import org.openflow.util.HexString;
+import org.restlet.resource.Get;
+import org.restlet.resource.ServerResource;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class MeasurementClearAllPathsFlowResource extends ServerResource {
+ protected static Logger log = LoggerFactory.getLogger(MeasurementClearAllPathsFlowResource.class);
+
+ @Get("json")
+ public Boolean retrieve() {
+ Boolean result = false;
+
+ IFlowService flowService =
+ (IFlowService)getContext().getAttributes().
+ get(IFlowService.class.getCanonicalName());
+
+ if (flowService == null) {
+ log.debug("ONOS Flow Service not found");
+ return result;
+ }
+
+ // Extract the arguments
+ log.debug("Measurement Clear All Paths");
+
+ // Process the request
+ result = flowService.measurementClearAllPaths();
+ return result;
+ }
+}
diff --git a/src/main/java/net/floodlightcontroller/flowcache/web/MeasurementGetInstallPathsTimeNsecFlowResource.java b/src/main/java/net/floodlightcontroller/flowcache/web/MeasurementGetInstallPathsTimeNsecFlowResource.java
new file mode 100644
index 0000000..3dc1d08
--- /dev/null
+++ b/src/main/java/net/floodlightcontroller/flowcache/web/MeasurementGetInstallPathsTimeNsecFlowResource.java
@@ -0,0 +1,37 @@
+package net.floodlightcontroller.flowcache.web;
+
+import net.floodlightcontroller.flowcache.IFlowService;
+import net.floodlightcontroller.util.FlowId;
+
+import org.openflow.util.HexString;
+import org.restlet.resource.Get;
+import org.restlet.resource.ServerResource;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class MeasurementGetInstallPathsTimeNsecFlowResource extends ServerResource {
+ protected static Logger log = LoggerFactory.getLogger(MeasurementGetInstallPathsTimeNsecFlowResource.class);
+
+ @Get("json")
+ public Long retrieve() {
+ Long result = null;
+
+ IFlowService flowService =
+ (IFlowService)getContext().getAttributes().
+ get(IFlowService.class.getCanonicalName());
+
+ if (flowService == null) {
+ log.debug("ONOS Flow Service not found");
+ return result;
+ }
+
+ // Extract the arguments
+
+ // Process the request
+ result = flowService.measurementGetInstallPathsTimeNsec();
+
+ log.debug("Measurement Get Install Paths Time (nsec): " + result);
+
+ return result;
+ }
+}
diff --git a/src/main/java/net/floodlightcontroller/flowcache/web/MeasurementInstallPathsFlowResource.java b/src/main/java/net/floodlightcontroller/flowcache/web/MeasurementInstallPathsFlowResource.java
new file mode 100644
index 0000000..1bba4b1
--- /dev/null
+++ b/src/main/java/net/floodlightcontroller/flowcache/web/MeasurementInstallPathsFlowResource.java
@@ -0,0 +1,37 @@
+package net.floodlightcontroller.flowcache.web;
+
+import net.floodlightcontroller.flowcache.IFlowService;
+import net.floodlightcontroller.util.FlowId;
+
+import org.openflow.util.HexString;
+import org.restlet.resource.Get;
+import org.restlet.resource.ServerResource;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class MeasurementInstallPathsFlowResource extends ServerResource {
+ protected static Logger log = LoggerFactory.getLogger(MeasurementInstallPathsFlowResource.class);
+
+ @Get("json")
+ public Boolean retrieve() {
+ Boolean result = false;
+
+ IFlowService flowService =
+ (IFlowService)getContext().getAttributes().
+ get(IFlowService.class.getCanonicalName());
+
+ if (flowService == null) {
+ log.debug("ONOS Flow Service not found");
+ return result;
+ }
+
+ // Extract the arguments
+ String numThreadsStr = (String) getRequestAttributes().get("num-threads");
+ Integer numThreads = new Integer(numThreadsStr);
+ log.debug("Measurement Install Paths Number of Threads " + numThreadsStr);
+
+ // Process the request
+ result = flowService.measurementInstallPaths(numThreads);
+ return result;
+ }
+}
diff --git a/src/main/java/net/floodlightcontroller/flowcache/web/MeasurementStorePathFlowResource.java b/src/main/java/net/floodlightcontroller/flowcache/web/MeasurementStorePathFlowResource.java
new file mode 100644
index 0000000..e68ceb7
--- /dev/null
+++ b/src/main/java/net/floodlightcontroller/flowcache/web/MeasurementStorePathFlowResource.java
@@ -0,0 +1,65 @@
+package net.floodlightcontroller.flowcache.web;
+
+import java.io.IOException;
+
+import net.floodlightcontroller.flowcache.IFlowService;
+import net.floodlightcontroller.util.FlowId;
+import net.floodlightcontroller.util.FlowPath;
+
+import org.codehaus.jackson.JsonGenerationException;
+import org.codehaus.jackson.map.ObjectMapper;
+import org.codehaus.jackson.map.JsonMappingException;
+import org.codehaus.jackson.map.ObjectMapper;
+import org.restlet.resource.Post;
+import org.restlet.resource.ServerResource;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class MeasurementStorePathFlowResource extends ServerResource {
+
+ protected static Logger log = LoggerFactory.getLogger(MeasurementStorePathFlowResource.class);
+
+ @Post("json")
+ public FlowId store(String flowJson) {
+ FlowId result = new FlowId();
+
+ IFlowService flowService =
+ (IFlowService)getContext().getAttributes().
+ get(IFlowService.class.getCanonicalName());
+
+ if (flowService == null) {
+ log.debug("ONOS Flow Service not found");
+ return result;
+ }
+
+ //
+ // Extract the arguments
+ // NOTE: The "flow" is specified in JSON format.
+ //
+ ObjectMapper mapper = new ObjectMapper();
+ String flowPathStr = flowJson;
+ FlowPath flowPath = null;
+ log.debug("Measurement Store Flow Path: " + flowPathStr);
+ try {
+ flowPath = mapper.readValue(flowPathStr, FlowPath.class);
+ } catch (JsonGenerationException e) {
+ e.printStackTrace();
+ } catch (JsonMappingException e) {
+ e.printStackTrace();
+ } catch (IOException e) {
+ e.printStackTrace();
+ }
+
+ // Process the request
+ if (flowPath != null) {
+ FlowPath addedFlowPath =
+ flowService.measurementStorePathFlow(flowPath);
+ if (addedFlowPath == null)
+ result = new FlowId(); // Error: Return empty Flow Id
+ else
+ result = addedFlowPath.flowId();
+ }
+
+ return result;
+ }
+}