this patch makes ofctl_rest enable getting Description of a port. usage)
URI: /stats/portdesc/<dpid> method: GET e.g. ) curl http://localhost:8080/stats/portdesc/1 {"1": [{"hw_addr": "c6:d8:19:4a:e1:4f", "curr": 0, "supported": 0, "max_speed": 0, "advertised": 0, "peer": 0, "port_no": 4294967294, "curr_speed": 0, "name": "s1", "state": 1, "config": 1}, {"hw_addr": "8e:96:a1:14:d8:a1", "curr": 2112, "supported": 0, "max_speed": 0, "advertised": 0, "peer": 0, "port_no": 1, "curr_speed": 10000000, "name": "s1-eth1", "state": 0, "config": 0}]} Signed-off-by: TAKAHASHI Minoru <[email protected]> --- ryu/app/ofctl_rest.py | 45 ++++++++++++++++++++++++++++++++++++++++++++- ryu/lib/ofctl_v1_0.py | 25 +++++++++++++++++++++++++ ryu/lib/ofctl_v1_2.py | 27 +++++++++++++++++++++++++++ ryu/lib/ofctl_v1_3.py | 27 +++++++++++++++++++++++++++ 4 files changed, 123 insertions(+), 1 deletion(-) diff --git a/ryu/app/ofctl_rest.py b/ryu/app/ofctl_rest.py index ac857c0..bafbb02 100644 --- a/ryu/app/ofctl_rest.py +++ b/ryu/app/ofctl_rest.py @@ -68,6 +68,9 @@ LOG = logging.getLogger('ryu.app.ofctl_rest') # # get groups stats of the switch # GET /stats/group/<dpid> +# +# get ports description of the switch +# GET /stats/portdesc/<dpid> # Update the switch stats # @@ -264,6 +267,24 @@ class StatsController(ControllerBase): body = json.dumps(groups) return Response(content_type='application/json', body=body) + def get_port_desc(self, req, dpid, **_kwargs): + dp = self.dpset.get(int(dpid)) + if dp is None: + return Response(status=404) + + if dp.ofproto.OFP_VERSION == ofproto_v1_0.OFP_VERSION: + groups = ofctl_v1_0.get_port_desc(dp, self.waiters) + elif dp.ofproto.OFP_VERSION == ofproto_v1_2.OFP_VERSION: + groups = ofctl_v1_2.get_port_desc(dp, self.waiters) + elif dp.ofproto.OFP_VERSION == ofproto_v1_3.OFP_VERSION: + groups = ofctl_v1_3.get_port_desc(dp, self.waiters) + else: + LOG.debug('Unsupported OF protocol') + return Response(status=501) + + body = json.dumps(groups) + return Response(content_type='application/json', body=body) + def mod_flow_entry(self, req, cmd, **_kwargs): try: flow = eval(req.body) @@ -517,6 +538,11 @@ class RestStatsApi(app_manager.RyuApp): controller=StatsController, action='get_group_stats', conditions=dict(method=['GET'])) + uri = path + '/portdesc/{dpid}' + mapper.connect('stats', uri, + controller=StatsController, action='get_port_desc', + conditions=dict(method=['GET'])) + uri = path + '/flowentry/{cmd}' mapper.connect('stats', uri, controller=StatsController, action='mod_flow_entry', @@ -556,7 +582,9 @@ class RestStatsApi(app_manager.RyuApp): ofp_event.EventOFPMeterConfigStatsReply, ofp_event.EventOFPGroupStatsReply, ofp_event.EventOFPGroupFeaturesStatsReply, - ofp_event.EventOFPGroupDescStatsReply], MAIN_DISPATCHER) + ofp_event.EventOFPGroupDescStatsReply, + ofp_event.EventOFPPortDescStatsReply + ], MAIN_DISPATCHER) def stats_reply_handler(self, ev): msg = ev.msg dp = msg.datapath @@ -580,3 +608,18 @@ class RestStatsApi(app_manager.RyuApp): return del self.waiters[dp.id][msg.xid] lock.set() + + @set_ev_cls([ofp_event.EventOFPSwitchFeatures], MAIN_DISPATCHER) + def features_reply_handler(self, ev): + msg = ev.msg + dp = msg.datapath + + if dp.id not in self.waiters: + return + if msg.xid not in self.waiters[dp.id]: + return + lock, msgs = self.waiters[dp.id][msg.xid] + msgs.append(msg) + + del self.waiters[dp.id][msg.xid] + lock.set() diff --git a/ryu/lib/ofctl_v1_0.py b/ryu/lib/ofctl_v1_0.py index 729e7db..06e9b04 100644 --- a/ryu/lib/ofctl_v1_0.py +++ b/ryu/lib/ofctl_v1_0.py @@ -280,6 +280,31 @@ def get_port_stats(dp, waiters): return ports +def get_port_desc(dp, waiters): + + stats = dp.ofproto_parser.OFPFeaturesRequest(dp) + msgs = [] + send_stats_request(dp, stats, waiters, msgs) + + descs = [] + + for msg in msgs: + stats = msg.ports + for stat in stats.values(): + d = {'port_no': stat.port_no, + 'hw_addr': stat.hw_addr, + 'name': stat.name, + 'config': stat.config, + 'state': stat.state, + 'curr': stat.curr, + 'advertised': stat.advertised, + 'supported': stat.supported, + 'peer': stat.peer} + descs.append(d) + descs = {str(dp.id): descs} + return descs + + def mod_flow_entry(dp, flow, cmd): cookie = int(flow.get('cookie', 0)) priority = int(flow.get('priority', diff --git a/ryu/lib/ofctl_v1_2.py b/ryu/lib/ofctl_v1_2.py index d4794ce..0571754 100644 --- a/ryu/lib/ofctl_v1_2.py +++ b/ryu/lib/ofctl_v1_2.py @@ -742,6 +742,33 @@ def get_group_desc(dp, waiters): return descs +def get_port_desc(dp, waiters): + + stats = dp.ofproto_parser.OFPFeaturesRequest(dp) + msgs = [] + send_stats_request(dp, stats, waiters, msgs) + + descs = [] + + for msg in msgs: + stats = msg.ports + for stat in stats.values(): + d = {'port_no': stat.port_no, + 'hw_addr': stat.hw_addr, + 'name': stat.name, + 'config': stat.config, + 'state': stat.state, + 'curr': stat.curr, + 'advertised': stat.advertised, + 'supported': stat.supported, + 'peer': stat.peer, + 'curr_speed': stat.curr_speed, + 'max_speed': stat.max_speed} + descs.append(d) + descs = {str(dp.id): descs} + return descs + + def mod_flow_entry(dp, flow, cmd): cookie = int(flow.get('cookie', 0)) cookie_mask = int(flow.get('cookie_mask', 0)) diff --git a/ryu/lib/ofctl_v1_3.py b/ryu/lib/ofctl_v1_3.py index 8d6da8a..327c5b1 100644 --- a/ryu/lib/ofctl_v1_3.py +++ b/ryu/lib/ofctl_v1_3.py @@ -889,6 +889,33 @@ def get_group_desc(dp, waiters): return descs +def get_port_desc(dp, waiters): + + stats = dp.ofproto_parser.OFPPortDescStatsRequest(dp, 0) + msgs = [] + send_stats_request(dp, stats, waiters, msgs) + + descs = [] + + for msg in msgs: + stats = msg.body + for stat in stats: + d = {'port_no': stat.port_no, + 'hw_addr': stat.hw_addr, + 'name': stat.name, + 'config': stat.config, + 'state': stat.state, + 'curr': stat.curr, + 'advertised': stat.advertised, + 'supported': stat.supported, + 'peer': stat.peer, + 'curr_speed': stat.curr_speed, + 'max_speed': stat.max_speed} + descs.append(d) + descs = {str(dp.id): descs} + return descs + + def mod_flow_entry(dp, flow, cmd): cookie = int(flow.get('cookie', 0)) cookie_mask = int(flow.get('cookie_mask', 0)) -- 1.7.10.4 ------------------------------------------------------------------------------ Open source business process management suite built on Java and Eclipse Turn processes into business applications with Bonita BPM Community Edition Quickly connect people, data, and systems into organized workflows Winner of BOSSIE, CODIE, OW2 and Gartner awards http://p.sf.net/sfu/Bonitasoft _______________________________________________ Ryu-devel mailing list [email protected] https://lists.sourceforge.net/lists/listinfo/ryu-devel
