Fixes disk size issue during image boot on Hyper-V

Fixes bug: 1135155

The local root disk size provided in the instance flavor was not properly
taken into account in the Hyper-V driver, this patches provides a
fix for this feature.

In order to resize VHD images with differencing disks (CoW), the cached
base disk is copied to a new file, which is resized to the size
specified in the flavor and cached. This is necessary due to the fact that
differencing VHD disks cannot be resized.

The procedure described above is applied during image spawn, resize and
live migration as needed.

Trying to spawn an instance with a local root disk size smaller than the
image VHD max. internal size will result in an error.

Change-Id: I04f18f0e25c92ed1e1f9f6f18750329a3f9f1711
This commit is contained in:
Alessandro Pilotti
2013-03-04 11:34:42 +02:00
parent 8de9c1a59e
commit 7f84fb4e89
2 changed files with 29 additions and 8 deletions

View File

@@ -41,7 +41,7 @@ def get_fake_instance_data(name, project_id, user_id):
{'name': 'm1.tiny',
'memory_mb': 512,
'vcpus': 1,
'root_gb': 0,
'root_gb': 1024,
'flavorid': 1,
'rxtx_factor': 1}
}
@@ -69,8 +69,6 @@ def get_fake_volume_info_data(target_portal, volume_id):
'target_portal': target_portal,
'target_lun': 1,
'auth_method': 'CHAP',
'auth_method': 'fake',
'auth_method': 'fake',
}
}
@@ -121,6 +119,9 @@ def stub_out_db_instance_api(stubs):
def __getitem__(self, key):
return self.get(key)
def __setitem__(self, key, value):
self.values[key] = value
def __str__(self):
return str(self.values)

View File

@@ -154,6 +154,8 @@ class HyperVAPITestCase(test.TestCase):
self._mox.StubOutWithMock(vhdutils.VHDUtils, 'merge_vhd')
self._mox.StubOutWithMock(vhdutils.VHDUtils, 'get_vhd_parent_path')
self._mox.StubOutWithMock(vhdutils.VHDUtils, 'get_vhd_info')
self._mox.StubOutWithMock(vhdutils.VHDUtils, 'resize_vhd')
self._mox.StubOutWithMock(vhdutils.VHDUtils, 'validate_vhd')
self._mox.StubOutWithMock(hostutils.HostUtils, 'get_cpus_info')
self._mox.StubOutWithMock(hostutils.HostUtils,
@@ -567,6 +569,8 @@ class HyperVAPITestCase(test.TestCase):
self.flags(use_cow_images=cow)
instance_data = self._get_instance_data()
instance = db.instance_create(self._context, instance_data)
instance['system_metadata'] = {}
network_info = fake_network.fake_get_instance_nw_info(self.stubs,
spectacular=True)
@@ -579,10 +583,14 @@ class HyperVAPITestCase(test.TestCase):
None)
m.AndReturn(False)
vhdutils.VHDUtils.get_vhd_info(mox.Func(self._check_img_path))
m = vhdutils.VHDUtils.get_vhd_info(mox.Func(self._check_img_path))
m.AndReturn({'MaxInternalSize': 1024})
fake.PathUtils.copyfile(mox.IsA(str), mox.IsA(str))
vhdutils.VHDUtils.resize_vhd(mox.IsA(str), mox.IsA(object))
self._mox.ReplayAll()
self._conn.pre_live_migration(self._context, instance_data,
self._conn.pre_live_migration(self._context, instance,
None, network_info)
self._mox.VerifyAll()
@@ -697,6 +705,7 @@ class HyperVAPITestCase(test.TestCase):
self._instance_data = self._get_instance_data()
instance = db.instance_create(self._context, self._instance_data)
instance['system_metadata'] = {}
image = db_fakes.get_fake_image_data(self._project_id, self._user_id)
@@ -763,12 +772,16 @@ class HyperVAPITestCase(test.TestCase):
m.AndReturn(boot_from_volume)
if not boot_from_volume:
vhdutils.VHDUtils.get_vhd_info(mox.Func(self._check_img_path))
m = vhdutils.VHDUtils.get_vhd_info(mox.Func(self._check_img_path))
m.AndReturn({'MaxInternalSize': 1024})
if cow:
vhdutils.VHDUtils.create_differencing_vhd(
mox.IsA(str), mox.Func(self._check_img_path))
fake.PathUtils.copyfile(mox.IsA(str), mox.IsA(str))
vhdutils.VHDUtils.resize_vhd(mox.IsA(str), mox.IsA(object))
vhdutils.VHDUtils.create_differencing_vhd(mox.IsA(str),
mox.IsA(str))
else:
vhdutils.VHDUtils.resize_vhd(mox.IsA(str), mox.IsA(object))
fake.PathUtils.copyfile(mox.IsA(str), mox.IsA(str))
self._setup_create_instance_mocks(setup_vif_mocks_func,
@@ -1009,6 +1022,7 @@ class HyperVAPITestCase(test.TestCase):
def test_finish_migration(self):
self._instance_data = self._get_instance_data()
instance = db.instance_create(self._context, self._instance_data)
instance['system_metadata'] = {}
network_info = fake_network.fake_get_instance_nw_info(
self.stubs, spectacular=True)
@@ -1032,6 +1046,12 @@ class HyperVAPITestCase(test.TestCase):
vhdutils.VHDUtils.reconnect_parent_vhd(mox.IsA(str), mox.IsA(str))
m = vhdutils.VHDUtils.get_vhd_info(mox.IsA(str))
m.AndReturn({'MaxInternalSize': 1024})
m = fake.PathUtils.exists(mox.IsA(str))
m.AndReturn(True)
self._set_vm_name(instance['name'])
self._setup_create_instance_mocks(None, False)