def setup_integration_br(self, integ_br): self.int_br = OVSBridge(integ_br, self.root_helper) self.int_br.remove_all_flows() # switch all traffic using L2 learning # TODO: Should this get replaced? would need to add # existing flows from db, then could make this a # lower priority flow decision # self.int_br.add_flow(priority=1, actions="normal") # TODO: from ryu these should probably go before add_flow or remove_flow self.int_br = OVSBridge(integ_br, self.root_helper) self.int_br.find_datapath_id() self.int_br.set_controller(ofp_controller_addr)
class OVSFloodlightQuantumAgent(object): def __init__(self, integ_br, root_helper): self.root_helper = root_helper #self.setup_integration_br(integ_br) # add controller stuff (ofp_controller_addr, ofp_rest_api_addr) = check_ofp_mode(db) #self.nw_id_external = rest_nw_id.NW_ID_EXTERNAL # TODO #self.api = OFPClient(ofp_rest_api_addr) # TODO May need to split out the ip from controller addr: "tcp:<ip>" # What format is controller addr in? self.api = FlClient(ofp_controller_addr) self.setup_integration_br(integ_br, ofp_controller_addr) def port_bound(self, port, vlan_id): self.int_br.set_db_attribute("Port", port.port_name, "tag", str(vlan_id)) self.int_br.delete_flows(match="in_port=%s" % port.ofport) def port_unbound(self, port, still_exists): if still_exists: self.int_br.clear_db_attribute("Port", port.port_name, "tag") def setup_integration_br(self, integ_br): self.int_br = OVSBridge(integ_br, self.root_helper) self.int_br.remove_all_flows() # switch all traffic using L2 learning # TODO: Should this get replaced? would need to add # existing flows from db, then could make this a # lower priority flow decision # self.int_br.add_flow(priority=1, actions="normal") # TODO: from ryu these should probably go before add_flow or remove_flow self.int_br = OVSBridge(integ_br, self.root_helper) self.int_br.find_datapath_id() self.int_br.set_controller(ofp_controller_addr) # ** Floodlight will already be setup as learning switch # Go through each external port on the int_br and update it # do I need to do the above? #for uplink in self.int_br.get_external_ports(): # self._port_update(self.nw_id_external, uplink) # TODO Not sure if still need port update or # if this can be replaced, probably # need some flavor of it to update all the # old flows during switch init def _port_update(self, network_id, uplink, db): vlan_id = db.get_vlan(network_id) # create a flow for each uplink port from the source port self.int_br.add_flow(vlan_id, in_port, uplink) # TODO : Need to setup loop to grab db entries and populate flows in the switch def daemon_loop(self, db): self.local_vlan_map = {} old_local_bindings = {} old_vif_ports = {} while True: all_bindings = {} try: ports = db.ports.all() except: ports = [] for port in ports: all_bindings[port.interface_id] = port vlan_bindings = {} try: vlan_binds = db.vlan_bindings.all() except: vlan_binds = [] for bind in vlan_binds: vlan_bindings[bind.network_id] = bind.vlan_id new_vif_ports = {} new_local_bindings = {} vif_ports = self.int_br.get_vif_ports() for p in vif_ports: new_vif_ports[p.vif_id] = p if p.vif_id in all_bindings: net_id = all_bindings[p.vif_id].network_id # Add flows for each port using the uplinks for uplink in self.int_br.get_external_ports(): vlan_id = db.get_vlan(net_id) self.int_br.add_flow(vlan_id, p, uplink) new_local_bindings[p.vif_id] = net_id if p not in old_vif_ports: # this is a new vif port, create a flow for it for uplink in self.int_br.get_external_ports(): self.api.create_flows(self.datapath_id, vlan_bindings[net_id], p, uplink) #else: # no binding, put him on the 'dead vlan' #self.int_br.set_db_attribute("Port", p.port_name, "tag", # DEAD_VLAN_TAG) #self.int_br.add_flow(priority=2, # match="in_port=%s" % p.ofport, actions="drop") old_b = old_local_bindings.get(p.vif_id, None) new_b = new_local_bindings.get(p.vif_id, None) if old_b != new_b: if old_b is not None: LOG.info("Removing binding to net-id = %s for %s" % (old_b, str(p))) self.port_unbound(p, True) if p.vif_id in all_bindings: all_bindings[p.vif_id].op_status = OP_STATUS_DOWN if new_b is not None: # If we don't have a binding we have to stick it on # the dead vlan net_id = all_bindings[p.vif_id].network_id vlan_id = vlan_bindings.get(net_id, DEAD_VLAN_TAG) self.port_bound(p, vlan_id) if p.vif_id in all_bindings: all_bindings[p.vif_id].op_status = OP_STATUS_UP LOG.info("Adding binding to net-id = %s " \ "for %s on vlan %s" % (new_b, str(p), vlan_id)) for vif_id in old_vif_ports: if vif_id not in new_vif_ports: LOG.info("Port Disappeared: %s" % vif_id) if vif_id in old_local_bindings: old_b = old_local_bindings[vif_id] self.port_unbound(old_vif_ports[vif_id], False) if vif_id in all_bindings: all_bindings[vif_id].op_status = OP_STATUS_DOWN old_vif_ports = new_vif_ports old_local_bindings = new_local_bindings db.commit() time.sleep(REFRESH_INTERVAL)