def set_execute(self, execute):
self._execute = execute
+ def _is_non_recoverable(self, err, non_recoverable_list):
+ for item in non_recoverable_list:
+ if item in err:
+ return True
+
+ return False
+
def _try_execute(self, *command, **kwargs):
# NOTE(vish): Volume commands can partially fail due to timing, but
# running them a second time on failure will usually
# recover nicely.
+
+ non_recoverable = kwargs.pop('no_retry_list', [])
+
tries = 0
while True:
try:
self._execute(*command, **kwargs)
return True
- except exception.ProcessExecutionError:
+ except exception.ProcessExecutionError as ex:
tries = tries + 1
- if tries >= self.configuration.num_shell_tries:
+
+ if tries >= self.configuration.num_shell_tries or\
+ self._is_non_recoverable(ex.stderr, non_recoverable):
raise
+
LOG.exception(_("Recovering from a failed execute. "
"Try number %s"), tries)
time.sleep(tries ** 2)
super(FakeISCSIDriver, self).__init__(execute=self.fake_execute,
*args, **kwargs)
+ def create_volume(self, volume):
+ pass
+
def check_for_setup_error(self):
"""No setup necessary in fake mode."""
pass
raise exception.VolumeBackendAPIException(data=exception_message)
def _create_volume(self, volume_name, sizestr):
+
+ no_retry_list = ['Insufficient free extents',
+ 'One or more specified logical volume(s) not found']
+
cmd = ['lvcreate', '-L', sizestr, '-n', volume_name,
self.configuration.volume_group]
if self.configuration.lvm_mirrors:
# http://red.ht/U2BPOD
cmd += ['-R', str(rsize)]
- self._try_execute(*cmd, run_as_root=True)
+ self._try_execute(*cmd, run_as_root=True, no_retry_list=no_retry_list)
def _copy_volume(self, srcstr, deststr, size_in_g, clearing=False):
# Use O_DIRECT to avoid thrashing the system buffer cache