def notify_ovsdb_states(self, context, ovsdb_states): """RPC to notify the OVSDB servers connection state.""" for ovsdb_identifier, state in ovsdb_states.items(): if state == 'connected': pending_recs = db.get_all_pending_remote_macs_in_asc_order( context, ovsdb_identifier) if pending_recs: for pending_mac in pending_recs: logical_switch_uuid = pending_mac['logical_switch_uuid' ] mac = pending_mac['mac'] operation = pending_mac['operation'] try: if operation == 'insert' or operation == 'update': l_switch = ovsdb_schema.LogicalSwitch( logical_switch_uuid, None, None, None) locator_uuid = pending_mac.get( 'locator_uuid', None) dst_ip = pending_mac.get( 'dst_ip', None) locator = ovsdb_schema.PhysicalLocator( locator_uuid, dst_ip) mac_remote = ovsdb_schema.UcastMacsRemote( pending_mac.get('uuid', None), mac, logical_switch_uuid, locator_uuid, pending_mac['vm_ip']) if operation == 'insert': self.agent_rpc.add_vif_to_gateway( context, ovsdb_identifier, l_switch.__dict__, locator.__dict__, mac_remote.__dict__) else: # update operation self.agent_rpc.update_vif_to_gateway( context, ovsdb_identifier, locator.__dict__, mac_remote.__dict__) else: self.agent_rpc.delete_vif_from_gateway( context, ovsdb_identifier, logical_switch_uuid, [mac]) # As the pending operation is over, delete the # record from the pending_ucast_mac_remote table db.delete_pending_ucast_mac_remote( context, operation, ovsdb_identifier, logical_switch_uuid, mac) except Exception as ex: LOG.exception(_LE("Exception occurred = %s"), str(ex))
def test_delete_pending_ucast_mac_remote(self): timestamp = timeutils.utcnow() record_dict = self._get_pending_mac_dict(timestamp) self._create_pending_mac(record_dict) lib.delete_pending_ucast_mac_remote(self.ctx, record_dict['operation'], record_dict['ovsdb_identifier'], record_dict['logical_switch_uuid'], record_dict['mac']) count = self.ctx.session.query(models.UcastMacsRemotes).count() self.assertEqual(count, 0)
def test_delete_pending_ucast_mac_remote(self): timestamp = timeutils.utcnow() record_dict = self._get_pending_mac_dict(timestamp) self._create_pending_mac(record_dict) lib.delete_pending_ucast_mac_remote(self.ctx, record_dict['operation'], record_dict['ovsdb_identifier'], record_dict['logical_switch_uuid'], record_dict['mac']) count = self.ctx.session.query(models.UcastMacsRemotes).count() self.assertEqual(count, 0)
def notify_ovsdb_states(self, context, ovsdb_states): """RPC to notify the OVSDB servers connection state.""" for ovsdb_identifier, state in ovsdb_states.items(): if state == 'connected': pending_recs = db.get_all_pending_remote_macs_in_asc_order( context, ovsdb_identifier) if pending_recs: for pending_mac in pending_recs: logical_switch_uuid = pending_mac[ 'logical_switch_uuid'] mac = pending_mac['mac'] operation = pending_mac['operation'] try: if operation == 'insert' or operation == 'update': l_switch = ovsdb_schema.LogicalSwitch( logical_switch_uuid, None, None, None) locator_uuid = pending_mac.get( 'locator_uuid', None) dst_ip = pending_mac.get('dst_ip', None) locator = ovsdb_schema.PhysicalLocator( locator_uuid, dst_ip) mac_remote = ovsdb_schema.UcastMacsRemote( pending_mac.get('uuid', None), mac, logical_switch_uuid, locator_uuid, pending_mac['vm_ip']) if operation == 'insert': self.agent_rpc.add_vif_to_gateway( context, ovsdb_identifier, l_switch.__dict__, locator.__dict__, mac_remote.__dict__) else: # update operation self.agent_rpc.update_vif_to_gateway( context, ovsdb_identifier, locator.__dict__, mac_remote.__dict__) else: self.agent_rpc.delete_vif_from_gateway( context, ovsdb_identifier, logical_switch_uuid, [mac]) # As the pending operation is over, delete the # record from the pending_ucast_mac_remote table db.delete_pending_ucast_mac_remote( context, operation, ovsdb_identifier, logical_switch_uuid, mac) except Exception as ex: LOG.exception(_LE("Exception occurred = %s"), str(ex))
def delete_port_mac(self, context, port): """Process the deleted port and trigger the RPC to delete from the gateway. When the ML2 plugin invokes this call, the argument port is a single port dict, whereas the L2gateway service plugin sends it as a list of port dicts. """ ls_dict = {} mac_list = [] logical_switches = [] ovsdb_identifier = None if isinstance(port, list): from_l2gw_plugin = True network_id = port[0].get('network_id') ovsdb_identifier = port[0].get('ovsdb_identifier') lg_dict = {'logical_switch_name': network_id, 'ovsdb_identifier': ovsdb_identifier} logical_switch = db.get_logical_switch_by_name( context, lg_dict) logical_switches.append(logical_switch) port_list = port else: from_l2gw_plugin = False network_id = port.get('network_id') logical_switches = ( db.get_all_logical_switches_by_name( context, network_id)) l2gateway_connections = self.get_l2_gateway_connections( context, filters={'network_id': [network_id]}) if not l2gateway_connections: return port_list = [port] for port_dict in port_list: if port_dict['device_owner']: if logical_switches: for logical_switch in logical_switches: logical_switch_uuid = logical_switch.get('uuid') mac = port_dict.get("mac_address") if port_dict.get('ovsdb_identifier', None): ovsdb_identifier = port_dict.get( 'ovsdb_identifier') else: ovsdb_identifier = logical_switch.get( 'ovsdb_identifier') record_dict = {'mac': mac, 'logical_switch_uuid': logical_switch_uuid, 'ovsdb_identifier': ovsdb_identifier} rec_dict = {'logical_switch_id': logical_switch_uuid, 'ovsdb_identifier': ovsdb_identifier} if len(db.get_all_vlan_bindings_by_logical_switch( context, rec_dict)) > 1: if from_l2gw_plugin: ls = logical_switch.get('name') l2gateway_connections = ( self.get_l2_gateway_connections( context, filters={'network_id': [ls]})) if len(l2gateway_connections) > 1: continue ucast_mac_remote = ( db.get_ucast_mac_remote_by_mac_and_ls( context, record_dict)) del_count = 0 if not ucast_mac_remote: LOG.debug("delete_port_mac: MAC %s does" " not exist", mac) # It is possible that this MAC is present # in the pending_ucast_mac_remote table. # Delete this MAC as it was not inserted # into the OVSDB server earlier. del_count = db.delete_pending_ucast_mac_remote( context, 'insert', ovsdb_identifier, logical_switch_uuid, mac) if not del_count: mac_list = ls_dict.get(logical_switch_uuid, []) mac_list.append(mac) ls_dict[logical_switch_uuid] = mac_list else: LOG.debug("delete_port_mac:Logical Switch %s " "does not exist ", port_dict.get('network_id')) return for logical_switch_uuid, mac_list in ls_dict.items(): try: if mac_list: self.agent_rpc.delete_vif_from_gateway(context, ovsdb_identifier, logical_switch_uuid, mac_list) except messaging.MessagingTimeout: # If RPC is timed out, then the RabbitMQ # will retry the operation. LOG.exception(_LE("Communication error with " "the L2 gateway agent")) except Exception as ex: # The remote OVSDB server may be down. # We need to retry this operation later. LOG.debug("Exception occurred %s", str(ex)) db.add_pending_ucast_mac_remote( context, 'delete', ovsdb_identifier, logical_switch_uuid, None, mac_list)