IPA:'shred' utility to use configured iterations

Today, there is no option to configure number of iterations to be
done for shred block device erasing and defaults it to 1. This patch
adds a configuration option to change the number of passes to be done
to erase a block device.

Change-Id: I1921d33a6b364c4682b6c9baaf61ac092cfa11d7
Partial-Bug:#1465130
This commit is contained in:
Anusha Ramineni
2015-06-15 21:36:27 +05:30
parent a798a19056
commit 02f78453b2
2 changed files with 26 additions and 19 deletions

View File

@@ -151,7 +151,7 @@ class HardwareManager(object):
"""
block_devices = self.list_block_devices()
for block_device in block_devices:
self.erase_block_device(block_device)
self.erase_block_device(node, block_device)
def list_hardware_info(self):
hardware_info = {}
@@ -427,7 +427,7 @@ class GenericHardwareManager(HardwareManager):
raise errors.DeviceNotFound("No suitable device was found for "
"deployment using these hints %s" % root_device_hints)
def erase_block_device(self, block_device):
def erase_block_device(self, node, block_device):
# Check if the block device is virtual media and skip the device.
if self._is_virtual_media_device(block_device):
@@ -438,7 +438,7 @@ class GenericHardwareManager(HardwareManager):
if self._ata_erase(block_device):
return
if self._shred_block_device(block_device):
if self._shred_block_device(node, block_device):
return
msg = ('Unable to erase block device {0}: device is unsupported.'
@@ -446,15 +446,18 @@ class GenericHardwareManager(HardwareManager):
LOG.error(msg)
raise errors.IncompatibleHardwareMethodError(msg)
def _shred_block_device(self, block_device):
def _shred_block_device(self, node, block_device):
"""Erase a block device using shred.
:param node: Ironic node info.
:param block_device: a BlockDevice object to be erased
:returns: True if the erase succeeds, False if it fails for any reason
"""
info = node.get('driver_internal_info', {})
npasses = info.get('agent_erase_devices_iterations', 1)
try:
utils.execute('shred', '--force', '--zero', '--verbose',
'--iterations', '1', block_device.name)
'--iterations', npasses, block_device.name)
except (processutils.ProcessExecutionError, OSError) as e:
msg = ("Erasing block device %(dev)s failed with error %(err)s ",
{'dev': block_device.name, 'err': e})

View File

@@ -182,6 +182,8 @@ class TestGenericHardwareManager(test_base.BaseTestCase):
def setUp(self):
super(TestGenericHardwareManager, self).setUp()
self.hardware = hardware.GenericHardwareManager()
self.node = {'uuid': 'dda135fb-732d-4742-8e72-df8f3199d244',
'driver_internal_info': {}}
@mock.patch('os.listdir')
@mock.patch('os.path.exists')
@@ -409,7 +411,7 @@ class TestGenericHardwareManager(test_base.BaseTestCase):
block_device = hardware.BlockDevice('/dev/sda', 'big', 1073741824,
True)
self.hardware.erase_block_device(block_device)
self.hardware.erase_block_device(self.node, block_device)
mocked_execute.assert_has_calls([
mock.call('hdparm', '-I', '/dev/sda'),
mock.call('hdparm', '--user-master', 'u', '--security-set-pass',
@@ -422,6 +424,8 @@ class TestGenericHardwareManager(test_base.BaseTestCase):
@mock.patch.object(utils, 'execute')
def test_erase_block_device_nosecurity_shred(self, mocked_execute):
hdparm_output = HDPARM_INFO_TEMPLATE.split('\nSecurity:')[0]
info = self.node.get('driver_internal_info')
info['agent_erase_devices_iterations'] = 2
mocked_execute.side_effect = [
(hdparm_output, ''),
@@ -430,11 +434,11 @@ class TestGenericHardwareManager(test_base.BaseTestCase):
block_device = hardware.BlockDevice('/dev/sda', 'big', 1073741824,
True)
self.hardware.erase_block_device(block_device)
self.hardware.erase_block_device(self.node, block_device)
mocked_execute.assert_has_calls([
mock.call('hdparm', '-I', '/dev/sda'),
mock.call('shred', '--force', '--zero', '--verbose',
'--iterations', '1', '/dev/sda')
'--iterations', 2, '/dev/sda')
])
@mock.patch.object(utils, 'execute')
@@ -453,11 +457,11 @@ class TestGenericHardwareManager(test_base.BaseTestCase):
block_device = hardware.BlockDevice('/dev/sda', 'big', 1073741824,
True)
self.hardware.erase_block_device(block_device)
self.hardware.erase_block_device(self.node, block_device)
mocked_execute.assert_has_calls([
mock.call('hdparm', '-I', '/dev/sda'),
mock.call('shred', '--force', '--zero', '--verbose',
'--iterations', '1', '/dev/sda')
'--iterations', 1, '/dev/sda')
])
@mock.patch.object(hardware.GenericHardwareManager,
@@ -466,7 +470,7 @@ class TestGenericHardwareManager(test_base.BaseTestCase):
vm_mock.return_value = True
block_device = hardware.BlockDevice('/dev/sda', 'big', 1073741824,
True)
self.hardware.erase_block_device(block_device)
self.hardware.erase_block_device(self.node, block_device)
vm_mock.assert_called_once_with(self.hardware, block_device)
@mock.patch.object(os, 'readlink', autospec=True)
@@ -512,20 +516,20 @@ class TestGenericHardwareManager(test_base.BaseTestCase):
mocked_execute.side_effect = OSError
block_device = hardware.BlockDevice('/dev/sda', 'big', 1073741824,
True)
res = self.hardware._shred_block_device(block_device)
res = self.hardware._shred_block_device(self.node, block_device)
self.assertFalse(res)
mocked_execute.assert_called_once_with('shred', '--force', '--zero',
'--verbose', '--iterations', '1', '/dev/sda')
'--verbose', '--iterations', 1, '/dev/sda')
@mock.patch.object(utils, 'execute')
def test_erase_block_device_shred_fail_processerror(self, mocked_execute):
mocked_execute.side_effect = processutils.ProcessExecutionError
block_device = hardware.BlockDevice('/dev/sda', 'big', 1073741824,
True)
res = self.hardware._shred_block_device(block_device)
res = self.hardware._shred_block_device(self.node, block_device)
self.assertFalse(res)
mocked_execute.assert_called_once_with('shred', '--force', '--zero',
'--verbose', '--iterations', '1', '/dev/sda')
'--verbose', '--iterations', 1, '/dev/sda')
@mock.patch.object(utils, 'execute')
def test_erase_block_device_ata_security_enabled(self, mocked_execute):
@@ -544,7 +548,7 @@ class TestGenericHardwareManager(test_base.BaseTestCase):
True)
self.assertRaises(errors.BlockDeviceEraseError,
self.hardware.erase_block_device,
block_device)
self.node, block_device)
@mock.patch.object(utils, 'execute')
def test_erase_block_device_ata_frozen(self, mocked_execute):
@@ -563,7 +567,7 @@ class TestGenericHardwareManager(test_base.BaseTestCase):
True)
self.assertRaises(errors.BlockDeviceEraseError,
self.hardware.erase_block_device,
block_device)
self.node, block_device)
@mock.patch.object(utils, 'execute')
def test_erase_block_device_ata_failed(self, mocked_execute):
@@ -594,7 +598,7 @@ class TestGenericHardwareManager(test_base.BaseTestCase):
True)
self.assertRaises(errors.BlockDeviceEraseError,
self.hardware.erase_block_device,
block_device)
self.node, block_device)
def test_normal_vs_enhanced_security_erase(self):
@mock.patch.object(utils, 'execute')
@@ -617,7 +621,7 @@ class TestGenericHardwareManager(test_base.BaseTestCase):
block_device = hardware.BlockDevice('/dev/sda', 'big', 1073741824,
True)
test_case.hardware.erase_block_device(block_device)
test_case.hardware.erase_block_device(self.node, block_device)
mocked_execute.assert_any_call('hdparm', '--user-master', 'u',
expected_option,
'NULL', '/dev/sda')