From 235578ef4762e9628c668683785bbb7db8b384e7 Mon Sep 17 00:00:00 2001 From: Maru Newby Date: Fri, 14 Mar 2014 22:14:09 +0000 Subject: [PATCH] Stop removing ip allocations on port delete The _delete_port() method was manually removing related IPAllocation instances despite the existence of a perfectly good cascade deletion relationship in the model. This patch puts an end to that nonsense and the potential for deadlock that it represented. Closes-bug: #1288379 Related-Bug: #1283522 Change-Id: Ib31550fa9000fc75768a327cb6cc1c419e06568f --- neutron/db/db_base_plugin_v2.py | 30 +----------------------------- neutron/db/l3_db.py | 6 ++++-- 2 files changed, 5 insertions(+), 31 deletions(-) diff --git a/neutron/db/db_base_plugin_v2.py b/neutron/db/db_base_plugin_v2.py index 4db152eb28..dafead7b61 100644 --- a/neutron/db/db_base_plugin_v2.py +++ b/neutron/db/db_base_plugin_v2.py @@ -1428,35 +1428,7 @@ class NeutronDbPluginV2(neutron_plugin_base_v2.NeutronPluginBaseV2, enable_eagerloads(False).filter_by(id=id)) if not context.is_admin: query = query.filter_by(tenant_id=context.tenant_id) - port = query.with_lockmode('update').one() - - allocated_qry = context.session.query( - models_v2.IPAllocation).with_lockmode('update') - # recycle all of the IP's - allocated = allocated_qry.filter_by(port_id=id) - for a in allocated: - subnet = self._get_subnet(context, a['subnet_id']) - # Check if IP was allocated from allocation pool - if NeutronDbPluginV2._check_ip_in_allocation_pool( - context, a['subnet_id'], subnet['gateway_ip'], - a['ip_address']): - NeutronDbPluginV2._delete_ip_allocation(context, - a['network_id'], - a['subnet_id'], - a['ip_address']) - else: - # IPs out of allocation pool will not be recycled, but - # we do need to delete the allocation from the DB - NeutronDbPluginV2._delete_ip_allocation( - context, a['network_id'], - a['subnet_id'], a['ip_address']) - msg_dict = {'address': a['ip_address'], - 'subnet_id': a['subnet_id']} - msg = _("%(address)s (%(subnet_id)s) is not " - "recycled") % msg_dict - LOG.debug(msg) - - context.session.delete(port) + query.delete() def get_port(self, context, id, fields=None): port = self._get_port(context, id) diff --git a/neutron/db/l3_db.py b/neutron/db/l3_db.py index e2ada9c0e5..6096b19d3c 100644 --- a/neutron/db/l3_db.py +++ b/neutron/db/l3_db.py @@ -236,7 +236,10 @@ class L3_NAT_db_mixin(l3.RouterPluginBase): if vpnservice: vpnservice.check_router_in_use(context, id) - # delete any gw port + context.session.delete(router) + + # Delete the gw port after the router has been removed to + # avoid a constraint violation. device_filter = {'device_id': [id], 'device_owner': [DEVICE_OWNER_ROUTER_GW]} ports = self._core_plugin.get_ports(context.elevated(), @@ -245,7 +248,6 @@ class L3_NAT_db_mixin(l3.RouterPluginBase): self._core_plugin._delete_port(context.elevated(), ports[0]['id']) - context.session.delete(router) self.l3_rpc_notifier.router_deleted(context, id) def get_router(self, context, id, fields=None):