summaryrefslogtreecommitdiffstats
path: root/nova/compute/manager.py
diff options
context:
space:
mode:
Diffstat (limited to 'nova/compute/manager.py')
-rwxr-xr-xnova/compute/manager.py76
1 files changed, 54 insertions, 22 deletions
diff --git a/nova/compute/manager.py b/nova/compute/manager.py
index 0c6d4f640..dbef94596 100755
--- a/nova/compute/manager.py
+++ b/nova/compute/manager.py
@@ -106,6 +106,9 @@ compute_opts = [
default=False,
help='Whether to start guests that were running before the '
'host rebooted'),
+ cfg.IntOpt('network_allocate_retries',
+ default=0,
+ help="Number of times to retry network allocation on failures"),
]
interval_opts = [
@@ -409,7 +412,8 @@ class ComputeManager(manager.SchedulerDependentManager):
'trying to set it to ERROR'),
instance_uuid=instance_uuid)
- def _get_instances_on_driver(self, context, filters=None):
+ def _get_instances_on_driver(self, context, filters=None,
+ columns_to_join=None):
"""Return a list of instance records for the instances found
on the hypervisor which satisfy the specified filters. If filters=None
return a list of instance records for all the instances found on the
@@ -421,7 +425,7 @@ class ComputeManager(manager.SchedulerDependentManager):
driver_uuids = self.driver.list_instance_uuids()
filters['uuid'] = driver_uuids
local_instances = self.conductor_api.instance_get_all_by_filters(
- context, filters, columns_to_join=[])
+ context, filters, columns_to_join=columns_to_join)
return local_instances
except NotImplementedError:
pass
@@ -430,7 +434,7 @@ class ComputeManager(manager.SchedulerDependentManager):
# to brute force.
driver_instances = self.driver.list_instances()
instances = self.conductor_api.instance_get_all_by_filters(
- context, filters, columns_to_join=[])
+ context, filters, columns_to_join=columns_to_join)
name_map = dict((instance['name'], instance) for instance in instances)
local_instances = []
for driver_instance in driver_instances:
@@ -1151,6 +1155,50 @@ class ComputeManager(manager.SchedulerDependentManager):
expected_task_state=(task_states.SCHEDULING,
None))
+ def _allocate_network_async(self, context, instance, requested_networks,
+ macs, security_groups, is_vpn):
+ """Method used to allocate networks in the background.
+
+ Broken out for testing.
+ """
+ LOG.debug(_("Allocating IP information in the background."),
+ instance=instance)
+ retries = CONF.network_allocate_retries
+ if retries < 0:
+ LOG.warn(_("Treating negative config value (%(retries)s) for "
+ "'network_allocate_retries' as 0."),
+ {'retries': retries})
+ attempts = retries > 1 and retries + 1 or 1
+ retry_time = 1
+ for attempt in range(1, attempts + 1):
+ try:
+ nwinfo = self.network_api.allocate_for_instance(
+ context, instance, vpn=is_vpn,
+ requested_networks=requested_networks,
+ macs=macs,
+ conductor_api=self.conductor_api,
+ security_groups=security_groups)
+ LOG.debug(_('Instance network_info: |%s|'), nwinfo,
+ instance=instance)
+ return nwinfo
+ except Exception:
+ exc_info = sys.exc_info()
+ log_info = {'attempt': attempt,
+ 'attempts': attempts}
+ if attempt == attempts:
+ LOG.exception(_('Instance failed network setup '
+ 'after %(attempts)d attempt(s)'),
+ log_info)
+ raise exc_info[0], exc_info[1], exc_info[2]
+ LOG.warn(_('Instance failed network setup '
+ '(attempt %(attempt)d of %(attempts)d)'),
+ log_info, instance=instance)
+ time.sleep(retry_time)
+ retry_time *= 2
+ if retry_time > 30:
+ retry_time = 30
+ # Not reached.
+
def _allocate_network(self, context, instance, requested_networks, macs,
security_groups):
"""Start network allocation asynchronously. Return an instance
@@ -1165,25 +1213,9 @@ class ComputeManager(manager.SchedulerDependentManager):
task_state=task_states.NETWORKING,
expected_task_state=None)
is_vpn = pipelib.is_vpn_image(instance['image_ref'])
-
- def async_alloc():
- LOG.debug(_("Allocating IP information in the background."),
- instance=instance)
- try:
- nwinfo = self.network_api.allocate_for_instance(
- context, instance, vpn=is_vpn,
- requested_networks=requested_networks,
- macs=macs,
- conductor_api=self.conductor_api,
- security_groups=security_groups)
- except Exception:
- with excutils.save_and_reraise_exception():
- LOG.exception(_('Instance failed network setup'),
- instance=instance)
- LOG.debug(_('Instance network_info: |%s|'), nwinfo,
- instance=instance)
- return nwinfo
- return network_model.NetworkInfoAsyncWrapper(async_alloc)
+ return network_model.NetworkInfoAsyncWrapper(
+ self._allocate_network_async, context, instance,
+ requested_networks, macs, security_groups, is_vpn)
def _prep_block_device(self, context, instance, bdms):
"""Set up the block device for an instance with error logging."""