From patchwork Sun Mar 11 01:34:22 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Haozhong Zhang X-Patchwork-Id: 884190 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (mailfrom) smtp.mailfrom=nongnu.org (client-ip=2001:4830:134:3::11; helo=lists.gnu.org; envelope-from=qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org; receiver=) Authentication-Results: ozlabs.org; dmarc=none (p=none dis=none) header.from=intel.com Received: from lists.gnu.org (lists.gnu.org [IPv6:2001:4830:134:3::11]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 3zzNwp1hwTzB2WJ for ; Sun, 11 Mar 2018 12:35:38 +1100 (AEDT) Received: from localhost ([::1]:52544 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1euptg-0003wU-1v for incoming@patchwork.ozlabs.org; Sat, 10 Mar 2018 20:35:36 -0500 Received: from eggs.gnu.org ([2001:4830:134:3::10]:48729) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1eupsn-0003ul-K5 for qemu-devel@nongnu.org; Sat, 10 Mar 2018 20:34:42 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1eupsk-0004oA-Es for qemu-devel@nongnu.org; Sat, 10 Mar 2018 20:34:41 -0500 Received: from mga01.intel.com ([192.55.52.88]:17414) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1eupsk-0004nm-3X; Sat, 10 Mar 2018 20:34:38 -0500 X-Amp-Result: SKIPPED(no attachment in message) X-Amp-File-Uploaded: False Received: from fmsmga002.fm.intel.com ([10.253.24.26]) by fmsmga101.fm.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384; 10 Mar 2018 17:34:36 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.47,453,1515484800"; d="scan'208";a="26975157" Received: from hz-desktop.sh.intel.com (HELO localhost) ([10.239.13.35]) by fmsmga002.fm.intel.com with ESMTP; 10 Mar 2018 17:34:34 -0800 From: Haozhong Zhang To: qemu-devel@nongnu.org Date: Sun, 11 Mar 2018 09:34:22 +0800 Message-Id: <20180311013426.32610-2-haozhong.zhang@intel.com> X-Mailer: git-send-email 2.14.1 In-Reply-To: <20180311013426.32610-1-haozhong.zhang@intel.com> References: <20180311013426.32610-1-haozhong.zhang@intel.com> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 192.55.52.88 Subject: [Qemu-devel] [PATCH v5 1/5] pc-dimm: make qmp_pc_dimm_device_list() sort devices by address X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Haozhong Zhang , Xiao Guangrong , mst@redhat.com, Bharata B Rao , Alexander Graf , Eduardo Habkost , Markus Armbruster , qemu-ppc@nongnu.org, Stefan Hajnoczi , Paolo Bonzini , Marcel Apfelbaum , Igor Mammedov , Dan Williams , David Gibson , Richard Henderson Errors-To: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Sender: "Qemu-devel" Make qmp_pc_dimm_device_list() return sorted by start address list of devices so that it could be reused in places that would need sorted list*. Reuse existing pc_dimm_built_list() to get sorted list. While at it hide recursive callbacks from callers, so that: qmp_pc_dimm_device_list(qdev_get_machine(), &list); could be replaced with simpler: list = qmp_pc_dimm_device_list(); * follow up patch will use it in build_srat() Signed-off-by: Haozhong Zhang Reviewed-by: Igor Mammedov Acked-by: David Gibson for ppc part Reviewed-by: Bharata B Rao --- hw/mem/pc-dimm.c | 83 +++++++++++++++++++++++++----------------------- hw/ppc/spapr.c | 3 +- include/hw/mem/pc-dimm.h | 2 +- numa.c | 4 +-- qmp.c | 7 +--- stubs/qmp_pc_dimm.c | 4 +-- 6 files changed, 50 insertions(+), 53 deletions(-) diff --git a/hw/mem/pc-dimm.c b/hw/mem/pc-dimm.c index 6e74b61cb6..4d050fe2cd 100644 --- a/hw/mem/pc-dimm.c +++ b/hw/mem/pc-dimm.c @@ -162,45 +162,6 @@ uint64_t get_plugged_memory_size(void) return pc_existing_dimms_capacity(&error_abort); } -int qmp_pc_dimm_device_list(Object *obj, void *opaque) -{ - MemoryDeviceInfoList ***prev = opaque; - - if (object_dynamic_cast(obj, TYPE_PC_DIMM)) { - DeviceState *dev = DEVICE(obj); - - if (dev->realized) { - MemoryDeviceInfoList *elem = g_new0(MemoryDeviceInfoList, 1); - MemoryDeviceInfo *info = g_new0(MemoryDeviceInfo, 1); - PCDIMMDeviceInfo *di = g_new0(PCDIMMDeviceInfo, 1); - DeviceClass *dc = DEVICE_GET_CLASS(obj); - PCDIMMDevice *dimm = PC_DIMM(obj); - - if (dev->id) { - di->has_id = true; - di->id = g_strdup(dev->id); - } - di->hotplugged = dev->hotplugged; - di->hotpluggable = dc->hotpluggable; - di->addr = dimm->addr; - di->slot = dimm->slot; - di->node = dimm->node; - di->size = object_property_get_uint(OBJECT(dimm), PC_DIMM_SIZE_PROP, - NULL); - di->memdev = object_get_canonical_path(OBJECT(dimm->hostmem)); - - info->u.dimm.data = di; - elem->value = info; - elem->next = NULL; - **prev = elem; - *prev = &elem->next; - } - } - - object_child_foreach(obj, qmp_pc_dimm_device_list, opaque); - return 0; -} - static int pc_dimm_slot2bitmap(Object *obj, void *opaque) { unsigned long *bitmap = opaque; @@ -276,6 +237,50 @@ static int pc_dimm_built_list(Object *obj, void *opaque) return 0; } +MemoryDeviceInfoList *qmp_pc_dimm_device_list(void) +{ + GSList *dimms = NULL, *item; + MemoryDeviceInfoList *list = NULL, *prev = NULL; + + object_child_foreach(qdev_get_machine(), pc_dimm_built_list, &dimms); + + for (item = dimms; item; item = g_slist_next(item)) { + PCDIMMDevice *dimm = PC_DIMM(item->data); + Object *obj = OBJECT(dimm); + MemoryDeviceInfoList *elem = g_new0(MemoryDeviceInfoList, 1); + MemoryDeviceInfo *info = g_new0(MemoryDeviceInfo, 1); + PCDIMMDeviceInfo *di = g_new0(PCDIMMDeviceInfo, 1); + DeviceClass *dc = DEVICE_GET_CLASS(obj); + DeviceState *dev = DEVICE(obj); + + if (dev->id) { + di->has_id = true; + di->id = g_strdup(dev->id); + } + di->hotplugged = dev->hotplugged; + di->hotpluggable = dc->hotpluggable; + di->addr = dimm->addr; + di->slot = dimm->slot; + di->node = dimm->node; + di->size = object_property_get_uint(obj, PC_DIMM_SIZE_PROP, NULL); + di->memdev = object_get_canonical_path(OBJECT(dimm->hostmem)); + + info->u.dimm.data = di; + elem->value = info; + elem->next = NULL; + if (prev) { + prev->next = elem; + } else { + list = elem; + } + prev = elem; + } + + g_slist_free(dimms); + + return list; +} + uint64_t pc_dimm_get_free_addr(uint64_t address_space_start, uint64_t address_space_size, uint64_t *hint, uint64_t align, uint64_t size, diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 7e1c858566..44a0670d11 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -722,8 +722,7 @@ static int spapr_populate_drconf_memory(sPAPRMachineState *spapr, void *fdt) } if (hotplug_lmb_start) { - MemoryDeviceInfoList **prev = &dimms; - qmp_pc_dimm_device_list(qdev_get_machine(), &prev); + dimms = qmp_pc_dimm_device_list(); } /* ibm,dynamic-memory */ diff --git a/include/hw/mem/pc-dimm.h b/include/hw/mem/pc-dimm.h index d83b957829..1fc479281c 100644 --- a/include/hw/mem/pc-dimm.h +++ b/include/hw/mem/pc-dimm.h @@ -93,7 +93,7 @@ uint64_t pc_dimm_get_free_addr(uint64_t address_space_start, int pc_dimm_get_free_slot(const int *hint, int max_slots, Error **errp); -int qmp_pc_dimm_device_list(Object *obj, void *opaque); +MemoryDeviceInfoList *qmp_pc_dimm_device_list(void); uint64_t pc_existing_dimms_capacity(Error **errp); uint64_t get_plugged_memory_size(void); void pc_dimm_memory_plug(DeviceState *dev, MemoryHotplugState *hpms, diff --git a/numa.c b/numa.c index 398e2c9a85..94427046ec 100644 --- a/numa.c +++ b/numa.c @@ -520,12 +520,10 @@ void memory_region_allocate_system_memory(MemoryRegion *mr, Object *owner, static void numa_stat_memory_devices(NumaNodeMem node_mem[]) { - MemoryDeviceInfoList *info_list = NULL; - MemoryDeviceInfoList **prev = &info_list; + MemoryDeviceInfoList *info_list = qmp_pc_dimm_device_list(); MemoryDeviceInfoList *info; PCDIMMDeviceInfo *pcdimm_info; - qmp_pc_dimm_device_list(qdev_get_machine(), &prev); for (info = info_list; info; info = info->next) { MemoryDeviceInfo *value = info->value; diff --git a/qmp.c b/qmp.c index 8c7d1cc479..4b2517d8b5 100644 --- a/qmp.c +++ b/qmp.c @@ -731,12 +731,7 @@ void qmp_object_del(const char *id, Error **errp) MemoryDeviceInfoList *qmp_query_memory_devices(Error **errp) { - MemoryDeviceInfoList *head = NULL; - MemoryDeviceInfoList **prev = &head; - - qmp_pc_dimm_device_list(qdev_get_machine(), &prev); - - return head; + return qmp_pc_dimm_device_list(); } ACPIOSTInfoList *qmp_query_acpi_ospm_status(Error **errp) diff --git a/stubs/qmp_pc_dimm.c b/stubs/qmp_pc_dimm.c index 9ddc4f619a..b6b2cca89e 100644 --- a/stubs/qmp_pc_dimm.c +++ b/stubs/qmp_pc_dimm.c @@ -2,9 +2,9 @@ #include "qom/object.h" #include "hw/mem/pc-dimm.h" -int qmp_pc_dimm_device_list(Object *obj, void *opaque) +MemoryDeviceInfoList *qmp_pc_dimm_device_list(void) { - return 0; + return NULL; } uint64_t get_plugged_memory_size(void) From patchwork Sun Mar 11 01:34:23 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Haozhong Zhang X-Patchwork-Id: 884189 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (mailfrom) smtp.mailfrom=nongnu.org (client-ip=2001:4830:134:3::11; helo=lists.gnu.org; envelope-from=qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org; receiver=) Authentication-Results: ozlabs.org; dmarc=none (p=none dis=none) header.from=intel.com Received: from lists.gnu.org (lists.gnu.org [IPv6:2001:4830:134:3::11]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 3zzNwm5pS2zB2WG for ; Sun, 11 Mar 2018 12:35:36 +1100 (AEDT) Received: from localhost ([::1]:52545 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1euptc-0003wc-U5 for incoming@patchwork.ozlabs.org; Sat, 10 Mar 2018 20:35:34 -0500 Received: from eggs.gnu.org ([2001:4830:134:3::10]:48730) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1eupsn-0003um-Ka for qemu-devel@nongnu.org; Sat, 10 Mar 2018 20:34:42 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1eupsm-0004oo-Ci for qemu-devel@nongnu.org; Sat, 10 Mar 2018 20:34:41 -0500 Received: from mga01.intel.com ([192.55.52.88]:17414) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1eupsm-0004nm-1J for qemu-devel@nongnu.org; Sat, 10 Mar 2018 20:34:40 -0500 X-Amp-Result: SKIPPED(no attachment in message) X-Amp-File-Uploaded: False Received: from fmsmga002.fm.intel.com ([10.253.24.26]) by fmsmga101.fm.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384; 10 Mar 2018 17:34:39 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.47,453,1515484800"; d="scan'208";a="26975160" Received: from hz-desktop.sh.intel.com (HELO localhost) ([10.239.13.35]) by fmsmga002.fm.intel.com with ESMTP; 10 Mar 2018 17:34:37 -0800 From: Haozhong Zhang To: qemu-devel@nongnu.org Date: Sun, 11 Mar 2018 09:34:23 +0800 Message-Id: <20180311013426.32610-3-haozhong.zhang@intel.com> X-Mailer: git-send-email 2.14.1 In-Reply-To: <20180311013426.32610-1-haozhong.zhang@intel.com> References: <20180311013426.32610-1-haozhong.zhang@intel.com> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 192.55.52.88 Subject: [Qemu-devel] [PATCH v5 2/5] qmp: distinguish PC-DIMM and NVDIMM in MemoryDeviceInfoList X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Haozhong Zhang , Xiao Guangrong , mst@redhat.com, Markus Armbruster , Eduardo Habkost , dgilbert@redhat.com, Stefan Hajnoczi , Paolo Bonzini , Marcel Apfelbaum , Igor Mammedov , Dan Williams , Richard Henderson Errors-To: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Sender: "Qemu-devel" It may need to treat PC-DIMM and NVDIMM differently, e.g., when deciding the necessity of non-volatile flag bit in SRAT memory affinity structures. NVDIMMDeviceInfo, which inherits from PCDIMMDeviceInfo, is added to union type MemoryDeviceInfo to record information of NVDIMM devices. The NVDIMM-specific data is currently left empty and will be filled when necessary in the future. It also fixes "info memory-devices"/query-memory-devices which currently show nvdimm devices as dimm devices since object_dynamic_cast(obj, TYPE_PC_DIMM) happily cast nvdimm to TYPE_PC_DIMM which it's been inherited from. Signed-off-by: Haozhong Zhang Reviewed-by: Eric Blake --- hmp.c | 14 +++++++++++--- hw/mem/pc-dimm.c | 10 +++++++++- numa.c | 19 +++++++++++++------ qapi/misc.json | 6 +++++- 4 files changed, 38 insertions(+), 11 deletions(-) diff --git a/hmp.c b/hmp.c index 016cb5c4f1..011a7c6f35 100644 --- a/hmp.c +++ b/hmp.c @@ -2421,7 +2421,18 @@ void hmp_info_memory_devices(Monitor *mon, const QDict *qdict) switch (value->type) { case MEMORY_DEVICE_INFO_KIND_DIMM: di = value->u.dimm.data; + break; + + case MEMORY_DEVICE_INFO_KIND_NVDIMM: + di = value->u.nvdimm.data; + break; + + default: + di = NULL; + break; + } + if (di) { monitor_printf(mon, "Memory device [%s]: \"%s\"\n", MemoryDeviceInfoKind_str(value->type), di->id ? di->id : ""); @@ -2434,9 +2445,6 @@ void hmp_info_memory_devices(Monitor *mon, const QDict *qdict) di->hotplugged ? "true" : "false"); monitor_printf(mon, " hotpluggable: %s\n", di->hotpluggable ? "true" : "false"); - break; - default: - break; } } } diff --git a/hw/mem/pc-dimm.c b/hw/mem/pc-dimm.c index 4d050fe2cd..51350d9c2d 100644 --- a/hw/mem/pc-dimm.c +++ b/hw/mem/pc-dimm.c @@ -20,6 +20,7 @@ #include "qemu/osdep.h" #include "hw/mem/pc-dimm.h" +#include "hw/mem/nvdimm.h" #include "qapi/error.h" #include "qemu/config-file.h" #include "qapi/visitor.h" @@ -250,6 +251,7 @@ MemoryDeviceInfoList *qmp_pc_dimm_device_list(void) MemoryDeviceInfoList *elem = g_new0(MemoryDeviceInfoList, 1); MemoryDeviceInfo *info = g_new0(MemoryDeviceInfo, 1); PCDIMMDeviceInfo *di = g_new0(PCDIMMDeviceInfo, 1); + bool is_nvdimm = object_dynamic_cast(obj, TYPE_NVDIMM); DeviceClass *dc = DEVICE_GET_CLASS(obj); DeviceState *dev = DEVICE(obj); @@ -265,7 +267,13 @@ MemoryDeviceInfoList *qmp_pc_dimm_device_list(void) di->size = object_property_get_uint(obj, PC_DIMM_SIZE_PROP, NULL); di->memdev = object_get_canonical_path(OBJECT(dimm->hostmem)); - info->u.dimm.data = di; + if (!is_nvdimm) { + info->u.dimm.data = di; + info->type = MEMORY_DEVICE_INFO_KIND_DIMM; + } else { + info->u.nvdimm.data = di; + info->type = MEMORY_DEVICE_INFO_KIND_NVDIMM; + } elem->value = info; elem->next = NULL; if (prev) { diff --git a/numa.c b/numa.c index 94427046ec..1116c90af9 100644 --- a/numa.c +++ b/numa.c @@ -529,18 +529,25 @@ static void numa_stat_memory_devices(NumaNodeMem node_mem[]) if (value) { switch (value->type) { - case MEMORY_DEVICE_INFO_KIND_DIMM: { + case MEMORY_DEVICE_INFO_KIND_DIMM: pcdimm_info = value->u.dimm.data; + break; + + case MEMORY_DEVICE_INFO_KIND_NVDIMM: + pcdimm_info = value->u.nvdimm.data; + break; + + default: + pcdimm_info = NULL; + break; + } + + if (pcdimm_info) { node_mem[pcdimm_info->node].node_mem += pcdimm_info->size; if (pcdimm_info->hotpluggable && pcdimm_info->hotplugged) { node_mem[pcdimm_info->node].node_plugged_mem += pcdimm_info->size; } - break; - } - - default: - break; } } } diff --git a/qapi/misc.json b/qapi/misc.json index bcd5d10778..6bf082f612 100644 --- a/qapi/misc.json +++ b/qapi/misc.json @@ -2852,7 +2852,11 @@ # # Since: 2.1 ## -{ 'union': 'MemoryDeviceInfo', 'data': {'dimm': 'PCDIMMDeviceInfo'} } +{ 'union': 'MemoryDeviceInfo', + 'data': { 'dimm': 'PCDIMMDeviceInfo', + 'nvdimm': 'PCDIMMDeviceInfo' + } +} ## # @query-memory-devices: From patchwork Sun Mar 11 01:34:24 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Haozhong Zhang X-Patchwork-Id: 884191 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (mailfrom) smtp.mailfrom=nongnu.org (client-ip=2001:4830:134:3::11; helo=lists.gnu.org; envelope-from=qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org; receiver=) Authentication-Results: ozlabs.org; dmarc=none (p=none dis=none) header.from=intel.com Received: from lists.gnu.org (lists.gnu.org [IPv6:2001:4830:134:3::11]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 3zzNx65Md0zB2WG for ; Sun, 11 Mar 2018 12:35:54 +1100 (AEDT) Received: from localhost ([::1]:52547 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1euptw-0004Fe-Er for incoming@patchwork.ozlabs.org; Sat, 10 Mar 2018 20:35:52 -0500 Received: from eggs.gnu.org ([2001:4830:134:3::10]:48759) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1eupsp-0003w7-Ot for qemu-devel@nongnu.org; Sat, 10 Mar 2018 20:34:44 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1eupso-0004ps-GX for qemu-devel@nongnu.org; Sat, 10 Mar 2018 20:34:43 -0500 Received: from mga01.intel.com ([192.55.52.88]:17414) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1eupso-0004nm-4d for qemu-devel@nongnu.org; Sat, 10 Mar 2018 20:34:42 -0500 X-Amp-Result: SKIPPED(no attachment in message) X-Amp-File-Uploaded: False Received: from fmsmga002.fm.intel.com ([10.253.24.26]) by fmsmga101.fm.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384; 10 Mar 2018 17:34:41 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.47,453,1515484800"; d="scan'208";a="26975168" Received: from hz-desktop.sh.intel.com (HELO localhost) ([10.239.13.35]) by fmsmga002.fm.intel.com with ESMTP; 10 Mar 2018 17:34:40 -0800 From: Haozhong Zhang To: qemu-devel@nongnu.org Date: Sun, 11 Mar 2018 09:34:24 +0800 Message-Id: <20180311013426.32610-4-haozhong.zhang@intel.com> X-Mailer: git-send-email 2.14.1 In-Reply-To: <20180311013426.32610-1-haozhong.zhang@intel.com> References: <20180311013426.32610-1-haozhong.zhang@intel.com> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 192.55.52.88 Subject: [Qemu-devel] [PATCH v5 3/5] hw/acpi-build: build SRAT memory affinity structures for DIMM devices X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Haozhong Zhang , Xiao Guangrong , mst@redhat.com, Eduardo Habkost , Stefan Hajnoczi , Paolo Bonzini , Marcel Apfelbaum , Igor Mammedov , Dan Williams , Richard Henderson Errors-To: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Sender: "Qemu-devel" ACPI 6.2A Table 5-129 "SPA Range Structure" requires the proximity domain of a NVDIMM SPA range must match with corresponding entry in SRAT table. The address ranges of vNVDIMM in QEMU are allocated from the hot-pluggable address space, which is entirely covered by one SRAT memory affinity structure. However, users can set the vNVDIMM proximity domain in NFIT SPA range structure by the 'node' property of '-device nvdimm' to a value different than the one in the above SRAT memory affinity structure. In order to solve such proximity domain mismatch, this patch builds one SRAT memory affinity structure for each DIMM device present at boot time, including both PC-DIMM and NVDIMM, with the proximity domain specified in '-device pc-dimm' or '-device nvdimm'. The remaining hot-pluggable address space is covered by one or multiple SRAT memory affinity structures with the proximity domain of the last node as before. Signed-off-by: Haozhong Zhang --- hw/i386/acpi-build.c | 56 ++++++++++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 52 insertions(+), 4 deletions(-) diff --git a/hw/i386/acpi-build.c b/hw/i386/acpi-build.c index deb440f286..2c1f694da4 100644 --- a/hw/i386/acpi-build.c +++ b/hw/i386/acpi-build.c @@ -2323,6 +2323,55 @@ build_tpm2(GArray *table_data, BIOSLinker *linker, GArray *tcpalog) #define HOLE_640K_START (640 * 1024) #define HOLE_640K_END (1024 * 1024) +static void build_srat_hotpluggable_memory(GArray *table_data, uint64_t base, + uint64_t len, int default_node) +{ + MemoryDeviceInfoList *info_list = qmp_pc_dimm_device_list(); + MemoryDeviceInfoList *info; + MemoryDeviceInfo *mi; + PCDIMMDeviceInfo *di; + uint64_t end = base + len, cur, size; + bool is_nvdimm; + AcpiSratMemoryAffinity *numamem; + MemoryAffinityFlags flags; + + for (cur = base, info = info_list; + cur < end; + cur += size, info = info->next) { + numamem = acpi_data_push(table_data, sizeof *numamem); + + if (!info) { + build_srat_memory(numamem, cur, end - cur, default_node, + MEM_AFFINITY_HOTPLUGGABLE | MEM_AFFINITY_ENABLED); + break; + } + + mi = info->value; + is_nvdimm = (mi->type == MEMORY_DEVICE_INFO_KIND_NVDIMM); + di = !is_nvdimm ? mi->u.dimm.data : mi->u.nvdimm.data; + + if (cur < di->addr) { + build_srat_memory(numamem, cur, di->addr - cur, default_node, + MEM_AFFINITY_HOTPLUGGABLE | MEM_AFFINITY_ENABLED); + numamem = acpi_data_push(table_data, sizeof *numamem); + } + + size = di->size; + + flags = MEM_AFFINITY_ENABLED; + if (di->hotpluggable) { + flags |= MEM_AFFINITY_HOTPLUGGABLE; + } + if (is_nvdimm) { + flags |= MEM_AFFINITY_NON_VOLATILE; + } + + build_srat_memory(numamem, di->addr, size, di->node, flags); + } + + qapi_free_MemoryDeviceInfoList(info_list); +} + static void build_srat(GArray *table_data, BIOSLinker *linker, MachineState *machine) { @@ -2434,10 +2483,9 @@ build_srat(GArray *table_data, BIOSLinker *linker, MachineState *machine) * providing _PXM method if necessary. */ if (hotplugabble_address_space_size) { - numamem = acpi_data_push(table_data, sizeof *numamem); - build_srat_memory(numamem, pcms->hotplug_memory.base, - hotplugabble_address_space_size, pcms->numa_nodes - 1, - MEM_AFFINITY_HOTPLUGGABLE | MEM_AFFINITY_ENABLED); + build_srat_hotpluggable_memory(table_data, pcms->hotplug_memory.base, + hotplugabble_address_space_size, + pcms->numa_nodes - 1); } build_header(linker, table_data, From patchwork Sun Mar 11 01:34:25 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Haozhong Zhang X-Patchwork-Id: 884192 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (mailfrom) smtp.mailfrom=nongnu.org (client-ip=2001:4830:134:3::11; helo=lists.gnu.org; envelope-from=qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org; receiver=) Authentication-Results: ozlabs.org; dmarc=none (p=none dis=none) header.from=intel.com Received: from lists.gnu.org (lists.gnu.org [IPv6:2001:4830:134:3::11]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 3zzP0R1jZyzB2fh for ; Sun, 11 Mar 2018 12:38:47 +1100 (AEDT) Received: from localhost ([::1]:52565 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1eupwj-0006jw-2N for incoming@patchwork.ozlabs.org; Sat, 10 Mar 2018 20:38:45 -0500 Received: from eggs.gnu.org ([2001:4830:134:3::10]:48783) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1eupss-0003ye-3V for qemu-devel@nongnu.org; Sat, 10 Mar 2018 20:34:47 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1eupsr-0004qz-05 for qemu-devel@nongnu.org; Sat, 10 Mar 2018 20:34:46 -0500 Received: from mga01.intel.com ([192.55.52.88]:17414) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1eupsq-0004nm-Jp for qemu-devel@nongnu.org; Sat, 10 Mar 2018 20:34:44 -0500 X-Amp-Result: SKIPPED(no attachment in message) X-Amp-File-Uploaded: False Received: from fmsmga002.fm.intel.com ([10.253.24.26]) by fmsmga101.fm.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384; 10 Mar 2018 17:34:44 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.47,453,1515484800"; d="scan'208";a="26975178" Received: from hz-desktop.sh.intel.com (HELO localhost) ([10.239.13.35]) by fmsmga002.fm.intel.com with ESMTP; 10 Mar 2018 17:34:42 -0800 From: Haozhong Zhang To: qemu-devel@nongnu.org Date: Sun, 11 Mar 2018 09:34:25 +0800 Message-Id: <20180311013426.32610-5-haozhong.zhang@intel.com> X-Mailer: git-send-email 2.14.1 In-Reply-To: <20180311013426.32610-1-haozhong.zhang@intel.com> References: <20180311013426.32610-1-haozhong.zhang@intel.com> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 192.55.52.88 Subject: [Qemu-devel] [PATCH v5 4/5] tests/bios-tables-test: add test cases for DIMM proximity X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Haozhong Zhang , Xiao Guangrong , mst@redhat.com, Eduardo Habkost , Stefan Hajnoczi , Paolo Bonzini , Marcel Apfelbaum , Igor Mammedov , Dan Williams , Richard Henderson Errors-To: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Sender: "Qemu-devel" QEMU now builds one SRAT memory affinity structure for each PC-DIMM and NVDIMM device presented at boot time with the proximity domain specified in the device option 'node', rather than only one SRAT memory affinity structure covering the entire hotpluggable address space with the proximity domain of the last node. Add test cases on PC and Q35 machines with 4 proximity domains, and one PC-DIMM and one NVDIMM attached to the 2nd and 3rd proximity domains respectively. Check whether the QEMU-built SRAT tables match with the expected ones. The following ACPI tables need to be added for this test: tests/acpi-test-data/pc/APIC.dimmpxm tests/acpi-test-data/pc/DSDT.dimmpxm tests/acpi-test-data/pc/NFIT.dimmpxm tests/acpi-test-data/pc/SRAT.dimmpxm tests/acpi-test-data/pc/SSDT.dimmpxm tests/acpi-test-data/q35/APIC.dimmpxm tests/acpi-test-data/q35/DSDT.dimmpxm tests/acpi-test-data/q35/NFIT.dimmpxm tests/acpi-test-data/q35/SRAT.dimmpxm tests/acpi-test-data/q35/SSDT.dimmpxm New APIC and DSDT are needed because of the multiple processors configuration. New NFIT and SSDT are needed because of NVDIMM. Signed-off-by: Haozhong Zhang Suggested-by: Igor Mammedov --- tests/bios-tables-test.c | 38 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 38 insertions(+) diff --git a/tests/bios-tables-test.c b/tests/bios-tables-test.c index 65b271a173..34b55ff812 100644 --- a/tests/bios-tables-test.c +++ b/tests/bios-tables-test.c @@ -869,6 +869,42 @@ static void test_acpi_piix4_tcg_numamem(void) free_test_data(&data); } +static void test_acpi_tcg_dimm_pxm(const char *machine) +{ + test_data data; + + memset(&data, 0, sizeof(data)); + data.machine = machine; + data.variant = ".dimmpxm"; + test_acpi_one(" -machine nvdimm=on" + " -smp 4,sockets=4" + " -m 128M,slots=3,maxmem=1G" + " -numa node,mem=32M,nodeid=0" + " -numa node,mem=32M,nodeid=1" + " -numa node,mem=32M,nodeid=2" + " -numa node,mem=32M,nodeid=3" + " -numa cpu,node-id=0,socket-id=0" + " -numa cpu,node-id=1,socket-id=1" + " -numa cpu,node-id=2,socket-id=2" + " -numa cpu,node-id=3,socket-id=3" + " -object memory-backend-ram,id=ram0,size=128M" + " -object memory-backend-ram,id=nvm0,size=128M" + " -device pc-dimm,id=dimm0,memdev=ram0,node=1" + " -device nvdimm,id=dimm1,memdev=nvm0,node=2", + &data); + free_test_data(&data); +} + +static void test_acpi_q35_tcg_dimm_pxm(void) +{ + test_acpi_tcg_dimm_pxm(MACHINE_Q35); +} + +static void test_acpi_piix4_tcg_dimm_pxm(void) +{ + test_acpi_tcg_dimm_pxm(MACHINE_PC); +} + int main(int argc, char *argv[]) { const char *arch = qtest_get_arch(); @@ -893,6 +929,8 @@ int main(int argc, char *argv[]) qtest_add_func("acpi/q35/memhp", test_acpi_q35_tcg_memhp); qtest_add_func("acpi/piix4/numamem", test_acpi_piix4_tcg_numamem); qtest_add_func("acpi/q35/numamem", test_acpi_q35_tcg_numamem); + qtest_add_func("acpi/piix4/dimmpxm", test_acpi_piix4_tcg_dimm_pxm); + qtest_add_func("acpi/q35/dimmpxm", test_acpi_q35_tcg_dimm_pxm); } ret = g_test_run(); boot_sector_cleanup(disk);