From cd50fd1151531c48d34d14975f160c8913ccd56a Mon Sep 17 00:00:00 2001 From: liyingjun Date: Wed, 24 Jul 2019 16:03:33 +0800 Subject: [PATCH] Fixes physical memory fetching for aarch64 The output for aarch64[1] `lshw -quiet -json` is a bit different from x86_64, this will lead to 0 physical memory calculated currently. This patch aims to make it compatible for aarch64 when getting physical memory [1]: http://paste.openstack.org/show/754789/ Change-Id: Ib7b4ee857d8550e3d75ac8a53c61f0ecab45feff --- ironic_python_agent/hardware.py | 5 + .../tests/unit/test_hardware.py | 109 ++++++++++++++++++ ...hysical-memory-arm64-957755f6cd91ad85.yaml | 6 + 3 files changed, 120 insertions(+) create mode 100644 releasenotes/notes/fix-physical-memory-arm64-957755f6cd91ad85.yaml diff --git a/ironic_python_agent/hardware.py b/ironic_python_agent/hardware.py index e9dd689a5..e1ae6855c 100644 --- a/ironic_python_agent/hardware.py +++ b/ironic_python_agent/hardware.py @@ -866,6 +866,11 @@ class GenericHardwareManager(HardwareManager): if sys_child['id'] == 'core': for core_child in sys_child['children']: if _MEMORY_ID_RE.match(core_child['id']): + if (not core_child.get("children") and + core_child.get('size')): + value = ("%(size)s %(units)s" % core_child) + physical += int(UNIT_CONVERTER(value).to + ('MB').magnitude) for bank in core_child.get('children', ()): if bank.get('size'): value = ("%(size)s %(units)s" % bank) diff --git a/ironic_python_agent/tests/unit/test_hardware.py b/ironic_python_agent/tests/unit/test_hardware.py index a36c52038..b14aa8783 100644 --- a/ironic_python_agent/tests/unit/test_hardware.py +++ b/ironic_python_agent/tests/unit/test_hardware.py @@ -565,6 +565,105 @@ LSHW_JSON_OUTPUT_V2 = (""" } """, "") +LSHW_JSON_OUTPUT_ARM64 = (""" +{ + "id" : "debian", + "class" : "system", + "claimed" : true, + "description" : "Computer", + "width" : 64, + "capabilities" : { + "cp15_barrier" : true, + "setend" : true, + "swp" : true + }, + "children" : [ + { + "id" : "core", + "class" : "bus", + "claimed" : true, + "description" : "Motherboard", + "physid" : "0", + "children" : [ + { + "id" : "memory", + "class" : "memory", + "claimed" : true, + "description" : "System memory", + "physid" : "0", + "units" : "bytes", + "size" : 4143972352 + }, + { + "id" : "cpu:0", + "class" : "processor", + "claimed" : true, + "physid" : "1", + "businfo" : "cpu@0", + "capabilities" : { + "fp" : "Floating point instructions", + "asimd" : "Advanced SIMD", + "evtstrm" : "Event stream", + "aes" : "AES instructions", + "pmull" : "PMULL instruction", + "sha1" : "SHA1 instructions", + "sha2" : "SHA2 instructions", + "crc32" : "CRC extension", + "cpuid" : true + } + }, + { + "id" : "pci:0", + "class" : "bridge", + "claimed" : true, + "handle" : "PCIBUS:0002:e9", + "physid" : "100", + "businfo" : "pci@0002:e8:00.0", + "version" : "01", + "width" : 32, + "clock" : 33000000, + "configuration" : { + "driver" : "pcieport" + }, + "capabilities" : { + "pci" : true, + "pm" : "Power Management", + "msi" : "Message Signalled Interrupts", + "pciexpress" : "PCI Express", + "bus_master" : "bus mastering", + "cap_list" : "PCI capabilities listing" + } + } + ] + }, + { + "id" : "network:0", + "class" : "network", + "claimed" : true, + "description" : "Ethernet interface", + "physid" : "2", + "logicalname" : "enahisic2i2", + "serial" : "d0:ef:c1:e9:bf:33", + "configuration" : { + "autonegotiation" : "off", + "broadcast" : "yes", + "driver" : "hns", + "driverversion" : "2.0", + "firmware" : "N/A", + "link" : "no", + "multicast" : "yes", + "port" : "fibre" + }, + "capabilities" : { + "ethernet" : true, + "physical" : "Physical interface", + "fibre" : "optical fibre" + } + } + ] +} +""", "") + SMARTCTL_NORMAL_OUTPUT = (""" smartctl 6.2 2017-02-27 r4394 [x86_64-linux-3.10.0-693.21.1.el7.x86_64] (local build) Copyright (C) 2002-13, Bruce Allen, Christian Franke, www.smartmontools.org @@ -1400,6 +1499,16 @@ class TestGenericHardwareManager(base.IronicAgentTest): self.assertEqual(3952 * 1024 * 1024, mem.total) self.assertIsNone(mem.physical_mb) + @mock.patch('psutil.virtual_memory', autospec=True) + @mock.patch.object(utils, 'execute', autospec=True) + def test_get_memory_arm64_lshw(self, mocked_execute, mocked_psutil): + mocked_psutil.return_value.total = 3952 * 1024 * 1024 + mocked_execute.return_value = LSHW_JSON_OUTPUT_ARM64 + mem = self.hardware.get_memory() + + self.assertEqual(3952 * 1024 * 1024, mem.total) + self.assertEqual(3952, mem.physical_mb) + @mock.patch('ironic_python_agent.netutils.get_hostname', autospec=True) def test_list_hardware_info(self, mocked_get_hostname): self.hardware.list_network_interfaces = mock.Mock() diff --git a/releasenotes/notes/fix-physical-memory-arm64-957755f6cd91ad85.yaml b/releasenotes/notes/fix-physical-memory-arm64-957755f6cd91ad85.yaml new file mode 100644 index 000000000..5601d97b9 --- /dev/null +++ b/releasenotes/notes/fix-physical-memory-arm64-957755f6cd91ad85.yaml @@ -0,0 +1,6 @@ +--- +fixes: + - | + Fixes issue that 0 physical memory calculated for aarch64. Since output + for aarch64 `lshw -quiet -json` is a bit different from x86_64. This fix + is compatible with both x86_64 and arm64.