From 56688707138d2343a65e25f8c27586ffd44875cf Mon Sep 17 00:00:00 2001 From: Ryan Moore Date: Thu, 21 Nov 2013 15:38:56 +0000 Subject: [PATCH] Correct host managers free disk calculation Take lower of disk_least_available/free_disk_gb if they exist. When an instance exists in the database but not on the hypervisor (which can happen in some error cases), the 'missing' instance is included in the calculation of 'free_gb' but not included in 'disk_available_least'. Need to take the value that represents the minimum amount of free disk space available. Testing: COMPUTE_NODES in fakes.py includes the 4 possible test cases: disk_least_available or free_disk_gb = free_disk_mb None or 512 = 524288 1024 or None = 1048576 3333 or 3072 = 3145728 8192 or 8888 = 8388608 test: test_host_manager.py test_get_all_host_states: Already has existing tests looking for these cases - I've modifed the test data (in fakes.py) rather than creating new test data. Added check for Warning message for node 3 where physical disk (3333) is greater than database (3072) No impact on other tests. Change-Id: I4a18bf023a64d0cb198f77aab9daecb0786e93ff Closes-Bug: 1253599 --- nova/scheduler/host_manager.py | 11 +++++++++-- nova/tests/scheduler/fakes.py | 12 ++++++------ nova/tests/scheduler/test_host_manager.py | 3 +++ 3 files changed, 18 insertions(+), 8 deletions(-) diff --git a/nova/scheduler/host_manager.py b/nova/scheduler/host_manager.py index e47a2fd5b2..d8b6717f55 100644 --- a/nova/scheduler/host_manager.py +++ b/nova/scheduler/host_manager.py @@ -183,8 +183,15 @@ class HostState(object): all_ram_mb = compute['memory_mb'] # Assume virtual size is all consumed by instances if use qcow2 disk. - least = compute.get('disk_available_least') - free_disk_mb = least if least is not None else compute['free_disk_gb'] + free_gb = compute.get('free_disk_gb') + least_gb = compute.get('disk_available_least') + if least_gb > free_gb and free_gb: + # can occur when an instance in database is not on host + LOG.warn(_("Host has more disk space than database expected" + " (%(physical)sgb > %(database)sgb)") % + {'physical': least_gb, 'database': free_gb}) + free_disk_mb = min(val for val in [least_gb, + free_gb] if val is not None) free_disk_mb *= 1024 self.disk_mb_used = compute['local_gb_used'] * 1024 diff --git a/nova/tests/scheduler/fakes.py b/nova/tests/scheduler/fakes.py index 6d020c7603..6cb91a9f55 100644 --- a/nova/tests/scheduler/fakes.py +++ b/nova/tests/scheduler/fakes.py @@ -27,26 +27,26 @@ from nova.scheduler import host_manager COMPUTE_NODES = [ dict(id=1, local_gb=1024, memory_mb=1024, vcpus=1, - disk_available_least=512, free_ram_mb=512, vcpus_used=1, - free_disk_mb=512, local_gb_used=0, updated_at=None, + disk_available_least=None, free_ram_mb=512, vcpus_used=1, + free_disk_gb=512, local_gb_used=0, updated_at=None, service=dict(host='host1', disabled=False), hypervisor_hostname='node1', host_ip='127.0.0.1', hypervisor_version=0), dict(id=2, local_gb=2048, memory_mb=2048, vcpus=2, disk_available_least=1024, free_ram_mb=1024, vcpus_used=2, - free_disk_mb=1024, local_gb_used=0, updated_at=None, + free_disk_gb=None, local_gb_used=0, updated_at=None, service=dict(host='host2', disabled=True), hypervisor_hostname='node2', host_ip='127.0.0.1', hypervisor_version=0), dict(id=3, local_gb=4096, memory_mb=4096, vcpus=4, - disk_available_least=3072, free_ram_mb=3072, vcpus_used=1, - free_disk_mb=3072, local_gb_used=0, updated_at=None, + disk_available_least=3333, free_ram_mb=3072, vcpus_used=1, + free_disk_gb=3072, local_gb_used=0, updated_at=None, service=dict(host='host3', disabled=False), hypervisor_hostname='node3', host_ip='127.0.0.1', hypervisor_version=0), dict(id=4, local_gb=8192, memory_mb=8192, vcpus=8, disk_available_least=8192, free_ram_mb=8192, vcpus_used=0, - free_disk_mb=8192, local_gb_used=0, updated_at=None, + free_disk_gb=8888, local_gb_used=0, updated_at=None, service=dict(host='host4', disabled=False), hypervisor_hostname='node4', host_ip='127.0.0.1', hypervisor_version=0), diff --git a/nova/tests/scheduler/test_host_manager.py b/nova/tests/scheduler/test_host_manager.py index 8c9b63b59d..0888a1ff99 100644 --- a/nova/tests/scheduler/test_host_manager.py +++ b/nova/tests/scheduler/test_host_manager.py @@ -322,6 +322,9 @@ class HostManagerTestCase(test.NoDBTestCase): self.mox.StubOutWithMock(host_manager.LOG, 'warn') db.compute_node_get_all(context).AndReturn(fakes.COMPUTE_NODES) + # node 3 host physical disk space is greater than database + host_manager.LOG.warn("Host has more disk space than database expected" + " (3333gb > 3072gb)") # Invalid service host_manager.LOG.warn("No service for compute ID 5")