self._fake_delete_gpfs_file)
self.stubs.Set(GPFSDriver, '_create_sparse_file',
self._fake_create_sparse_file)
- self.stubs.Set(GPFSDriver, '_create_regular_file',
- self._fake_create_regular_file)
+ self.stubs.Set(GPFSDriver, '_allocate_file_blocks',
+ self._fake_allocate_file_blocks)
self.stubs.Set(GPFSDriver, '_get_available_capacity',
self._fake_get_available_capacity)
self.stubs.Set(image_utils, 'qemu_img_info',
self.volume.delete_volume(self.context, volume_id)
self.assertFalse(os.path.exists(path))
+ def test_create_volume_with_attributes(self):
+ self.stubs.Set(GPFSDriver, '_gpfs_change_attributes',
+ self._fake_gpfs_change_attributes)
+ attributes = {'dio': 'yes', 'data_pool_name': 'ssd_pool',
+ 'replicas': '2', 'write_affinity_depth': '1',
+ 'block_group_factor': '1',
+ 'write_affinity_failure-group':
+ '1,1,1:2;2,1,1:2;2,0,3:4'}
+ vol = self._create_volume(size=1, metadata=attributes)
+ volume_id = vol['id']
+ self.assertTrue(os.path.exists(self.volumes_path))
+ self.volume.create_volume(self.context, volume_id)
+ path = self.volumes_path + '/' + vol['name']
+ self.assertTrue(os.path.exists(path))
+ self.volume.delete_volume(self.context, volume_id)
+ self.assertFalse(os.path.exists(path))
+
def _create_snapshot(self, volume_id, size='0'):
"""Create a snapshot object."""
snap = {}
def _fake_create_sparse_file(self, path, size):
self._fake_create_file(path)
- def _fake_create_regular_file(self, path, size):
+ def _fake_allocate_file_blocks(self, path, size):
self._fake_create_file(path)
+ def _fake_gpfs_change_attributes(self, options, path):
+ pass
+
def _fake_gpfs_redirect(self, src):
return True
self._execute('truncate', '-s', sizestr, path, run_as_root=True)
self._execute('chmod', '666', path, run_as_root=True)
- def _create_regular_file(self, path, size):
- """Creates regular file of given size."""
+ def _allocate_file_blocks(self, path, size):
+ """Preallocate file blocks by writing zeros."""
block_size_mb = 1
block_count = size * units.GiB / (block_size_mb * units.MiB)
'bs=%dM' % block_size_mb,
'count=%d' % block_count,
run_as_root=True)
- self._execute('chmod', '666', path, run_as_root=True)
+
+ def _gpfs_change_attributes(self, options, path):
+ cmd = ['mmchattr']
+ cmd.extend(options)
+ cmd.append(path)
+ self._execute(*cmd, run_as_root=True)
+
+ def _set_volume_attributes(self, path, metadata):
+ """Set various GPFS attributes for this volume."""
+
+ options = []
+ for item in metadata:
+ if item['key'] == 'data_pool_name':
+ options.extend(['-P', item['value']])
+ elif item['key'] == 'replicas':
+ options.extend(['-r', item['value'], '-m', item['value']])
+ elif item['key'] == 'dio':
+ options.extend(['-D', item['value']])
+ elif item['key'] == 'write_affinity_depth':
+ options.extend(['--write-affinity-depth', item['value']])
+ elif item['key'] == 'block_group_factor':
+ options.extend(['--block-group-factor', item['value']])
+ elif item['key'] == 'write_affinity_failure_group':
+ options.extend(['--write-affinity-failure-group',
+ item['value']])
+
+ if options:
+ self._gpfs_change_attributes(options, path)
def create_volume(self, volume):
"""Creates a GPFS volume."""
volume_path = self.local_path(volume)
volume_size = volume['size']
- if self.configuration.gpfs_sparse_volumes:
- self._create_sparse_file(volume_path, volume_size)
- else:
- self._create_regular_file(volume_path, volume_size)
+ # Create a sparse file first; allocate blocks later if requested
+ self._create_sparse_file(volume_path, volume_size)
+ # Set the attributes prior to allocating any blocks so that
+ # they are allocated according to the policy
v_metadata = volume.get('volume_metadata')
+ self._set_volume_attributes(volume_path, v_metadata)
+
+ if not self.configuration.gpfs_sparse_volumes:
+ self._allocate_file_blocks(volume_path, volume_size)
+
fstype = None
fslabel = None
for item in v_metadata:
mmgetstate: CommandFilter, /usr/lpp/mmfs/bin/mmgetstate, root
mmclone: CommandFilter, /usr/lpp/mmfs/bin/mmclone, root
mmlsattr: CommandFilter, /usr/lpp/mmfs/bin/mmlsattr, root
+mmchattr: CommandFilter, /usr/lpp/mmfs/bin/mmchattr, root
mmlsconfig: CommandFilter, /usr/lpp/mmfs/bin/mmlsconfig, root
mmlsfs: CommandFilter, /usr/lpp/mmfs/bin/mmlsfs, root
find: CommandFilter, find, root