From e7993324b18d7dbd98747f866f33878fbde219e1 Mon Sep 17 00:00:00 2001 From: nomorecaddy Date: Wed, 2 Oct 2013 07:24:27 -0500 Subject: [PATCH 1/3] first push --- pox/openflow/webservice.py | 1 + 1 file changed, 1 insertion(+) diff --git a/pox/openflow/webservice.py b/pox/openflow/webservice.py index 93bf63060..57c445d58 100644 --- a/pox/openflow/webservice.py +++ b/pox/openflow/webservice.py @@ -37,6 +37,7 @@ get_switches Get list of switches and their basic info. + Example - Make a hub: curl -i -X POST -d '{"method":"set_table","params":{"dpid": "00-00-00-00-00-01","flows":[{"actions":[{"type":"OFPAT_OUTPUT", From 3020af3eefaad58a0d9611f5fec84b612a70f869 Mon Sep 17 00:00:00 2001 From: nomorecaddy Date: Wed, 2 Oct 2013 07:30:51 -0500 Subject: [PATCH 2/3] added the add_flow and del_flow commands to webservice.py --- pox/openflow/webservice.py | 92 +++++++++++++++++++++++++++++++++++++- 1 file changed, 91 insertions(+), 1 deletion(-) diff --git a/pox/openflow/webservice.py b/pox/openflow/webservice.py index 57c445d58..b778b4ea6 100644 --- a/pox/openflow/webservice.py +++ b/pox/openflow/webservice.py @@ -25,6 +25,14 @@ Sets the flow table on a switch. dpid - a string dpid flows - a list of flow entries + add_flow + Adds a flow entry on the switch. + dpid - a string dpid + flow - a flow entry to be added + del_flow + Deletes a flow entry on the switch. + dpid - a string dpid + flow - a flow entry to be added get_switch_desc Gets switch details. dpid - a string dpid @@ -37,7 +45,6 @@ get_switches Get list of switches and their basic info. - Example - Make a hub: curl -i -X POST -d '{"method":"set_table","params":{"dpid": "00-00-00-00-00-01","flows":[{"actions":[{"type":"OFPAT_OUTPUT", @@ -181,6 +188,73 @@ def _handle_ErrorIn (self, event): self._finish(make_error("OpenFlow Error", data=event.asString())) +class OFAddFlowRequest (OFConRequest): + + def _init (self, flows = []): + self.done = False + + xid = of.generate_xid() + self.xid = xid + + self.count = len(flows) + + for flow in flows: + fm = dict_to_flow_mod(flow) + fm.xid = xid + + self._con.send(fm) + self._con.send(of.ofp_barrier_request(xid=xid)) + + def _handle_BarrierIn (self, event): + if event.ofp.xid != self.xid: return + if self.done: return + self.count -= 1 + if self.count <= 0: + self._result('flowmod', True) + self.done = True + + def _handle_ErrorIn (self, event): + if event.ofp.xid != self.xid: return + if self.done: return + self.clear_table() + self.done = True + self._finish(make_error("OpenFlow Error", data=event.asString())) + + +class OFDelFlowRequest (OFConRequest): + + def _init (self, flows = []): + self.done = False + + xid = of.generate_xid() + self.xid = xid + + self.count = len(flows) + + for flow in flows: + fm = dict_to_flow_mod(flow) + fm.command = 4 # OFPFC_DELETE_STRICT + fm.xid = xid + + self._con.send(fm) + self._con.send(of.ofp_barrier_request(xid=xid)) + + def _handle_BarrierIn (self, event): + if event.ofp.xid != self.xid: return + if self.done: return + self.count -= 1 + if self.count <= 0: + self._result('flowmod', True) + self.done = True + + def _handle_ErrorIn (self, event): + if event.ofp.xid != self.xid: return + if self.done: return + self.clear_table() + self.done = True + self._finish(make_error("OpenFlow Error", data=event.asString())) + + class OFRequestHandler (JSONRPCHandler): def _exec_set_table (self, dpid, flows): @@ -191,6 +265,22 @@ def _exec_set_table (self, dpid, flows): return OFSetTableRequest(con, flows).get_response() + def _exec_add_flow (self, dpid, flows): + dpid = strToDPID(dpid) + con = core.openflow.getConnection(dpid) + if con is None: + return make_error("No such switch") + + return OFAddFlowRequest(con, flows).get_response() + + def _exec_del_flow (self, dpid, flows): + dpid = strToDPID(dpid) + con = core.openflow.getConnection(dpid) + if con is None: + return make_error("No such switch") + + return OFDelFlowRequest(con, flows).get_response() + def _exec_get_switch_desc (self, dpid): dpid = strToDPID(dpid) con = core.openflow.getConnection(dpid) From d286b3a4f5f5c6a38eebb1d2fef2e95b0e2f0a12 Mon Sep 17 00:00:00 2001 From: nomorecaddy Date: Tue, 8 Oct 2013 10:11:39 -0500 Subject: [PATCH 3/3] added method get_switch to take one switch at a time --- pox/openflow/of_json.py | 31 +++++++++++++++++++++++++++++++ pox/openflow/webservice.py | 8 ++++++++ 2 files changed, 39 insertions(+) diff --git a/pox/openflow/of_json.py b/pox/openflow/of_json.py index b21365ea2..9b538dd9d 100644 --- a/pox/openflow/of_json.py +++ b/pox/openflow/of_json.py @@ -327,3 +327,34 @@ def list_switches (ofnexus = None): r.sort(key=lambda item:item['dpid']) return r + +def list_switch (dpidToList, ofnexus = None): + if ofnexus is None: + from pox.core import core + ofnexus = core.openflow + + r = [] + for dpid,con in ofnexus._connections.iteritems(): + if dpid == dpidToList: + ports = [] + for p in con.ports.values(): + pdict = { + 'port_no':p.port_no, + 'hw_addr':str(p.hw_addr), + 'name':p.name} + for bit,name in of.ofp_port_config_map.items(): + if p.config & bit: + pdict[name.split('OFPPC_', 1)[-1].lower()] = True + for bit,name in of.ofp_port_state_map.items(): + if p.state & bit: + pdict[name.split('OFPPS_', 1)[-1].lower()] = True + ports.append(pdict) + ports.sort(key=lambda item:item['port_no']) + + rr = { + 'dpid':dpidToStr(dpid), + 'n_tables':con.features.n_tables, + 'ports':ports} + r.append(rr) + + return r diff --git a/pox/openflow/webservice.py b/pox/openflow/webservice.py index b778b4ea6..4d74239f2 100644 --- a/pox/openflow/webservice.py +++ b/pox/openflow/webservice.py @@ -300,6 +300,14 @@ def _exec_get_flow_stats (self, dpid, *args, **kw): def _exec_get_switches (self): return {'result':list_switches()} + def _exec_get_switch (self, dpid): + dpid = strToDPID(dpid) + con = core.openflow.getConnection(dpid) + if con is None: + return make_error("No such switch") + + return {'result':list_switch(dpid)} + def launch (username='', password=''):