From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from eggs.gnu.org ([2001:4830:134:3::10]:41292) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1YsYgC-0007bl-Ko for qemu-devel@nongnu.org; Wed, 13 May 2015 11:34:41 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1YsYg7-0000XT-CD for qemu-devel@nongnu.org; Wed, 13 May 2015 11:34:40 -0400 Received: from e23smtp08.au.ibm.com ([202.81.31.141]:45941) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1YsYg6-0000W0-OC for qemu-devel@nongnu.org; Wed, 13 May 2015 11:34:35 -0400 Received: from /spool/local by e23smtp08.au.ibm.com with IBM ESMTP SMTP Gateway: Authorized Use Only! Violators will be prosecuted for from ; Thu, 14 May 2015 01:34:31 +1000 Received: from d23relay08.au.ibm.com (d23relay08.au.ibm.com [9.185.71.33]) by d23dlp03.au.ibm.com (Postfix) with ESMTP id BA1FE357804C for ; Thu, 14 May 2015 01:34:27 +1000 (EST) Received: from d23av04.au.ibm.com (d23av04.au.ibm.com [9.190.235.139]) by d23relay08.au.ibm.com (8.14.9/8.14.9/NCO v10.0) with ESMTP id t4DFYJsj10879082 for ; Thu, 14 May 2015 01:34:27 +1000 Received: from d23av04.au.ibm.com (localhost [127.0.0.1]) by d23av04.au.ibm.com (8.14.4/8.14.4/NCO v10.0 AVout) with ESMTP id t4DFXt1u008401 for ; Thu, 14 May 2015 01:33:55 +1000 Date: Wed, 13 May 2015 21:03:33 +0530 From: Bharata B Rao Message-ID: <20150513153333.GD4858@in.ibm.com> References: <1430982264-25497-1-git-send-email-bharata@linux.vnet.ibm.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1430982264-25497-1-git-send-email-bharata@linux.vnet.ibm.com> Subject: Re: [Qemu-devel] [RFC PATCH v0] numa: API to lookup NUMA node by address Reply-To: bharata@linux.vnet.ibm.com List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: qemu-devel@nongnu.org Cc: pbonzini@redhat.com, imammedo@redhat.com, Eduardo Habkost , david@gibson.dropbear.id.au CC'ing Eduardo... Does this approach look sane ? Currently only PowerPC needs this, however is this API correct from other architectures' perspective ? On Thu, May 07, 2015 at 12:34:24PM +0530, Bharata B Rao wrote: > Keep track of start and end address of each NUMA node in numa_info > structure so that lookup of node by address becomes easier. Add > an API numa_get_node() to lookup a node by address. > > This is needed by sPAPR PowerPC to support > ibm,dynamic-reconfiguration-memory device tree node which is needed for > memory hotplug. > > Signed-off-by: Bharata B Rao > Reviewed-by: David Gibson > --- > This patch was earlier posted as part of sPAPR hotplug patchset here: > https://lists.gnu.org/archive/html/qemu-ppc/2015-04/msg00204.html > > include/sysemu/numa.h | 3 +++ > numa.c | 61 +++++++++++++++++++++++++++++++++++++++++++++++++++ > 2 files changed, 64 insertions(+) > > diff --git a/include/sysemu/numa.h b/include/sysemu/numa.h > index 6523b4d..19c0ba3 100644 > --- a/include/sysemu/numa.h > +++ b/include/sysemu/numa.h > @@ -15,11 +15,14 @@ typedef struct node_info { > DECLARE_BITMAP(node_cpu, MAX_CPUMASK_BITS); > struct HostMemoryBackend *node_memdev; > bool present; > + ram_addr_t mem_start; > + ram_addr_t mem_end; > } NodeInfo; > extern NodeInfo numa_info[MAX_NODES]; > void parse_numa_opts(MachineClass *mc); > void numa_post_machine_init(void); > void query_numa_node_mem(uint64_t node_mem[]); > extern QemuOptsList qemu_numa_opts; > +uint32_t numa_get_node(ram_addr_t addr, Error **errp); > > #endif > diff --git a/numa.c b/numa.c > index c975fb2..fdf333b 100644 > --- a/numa.c > +++ b/numa.c > @@ -53,6 +53,63 @@ static int max_numa_nodeid; /* Highest specified NUMA node ID, plus one. > int nb_numa_nodes; > NodeInfo numa_info[MAX_NODES]; > > +/* > + * Given an address, return the index of the NUMA node to which the > + * address belongs to. > + */ > +uint32_t numa_get_node(ram_addr_t addr, Error **errp) > +{ > + uint32_t i; > + MemoryDeviceInfoList *info_list = NULL; > + MemoryDeviceInfoList **prev = &info_list; > + MemoryDeviceInfoList *info; > + > + for (i = 0; i < nb_numa_nodes; i++) { > + if (addr >= numa_info[i].mem_start && addr < numa_info[i].mem_end) { > + return i; > + } > + } > + > + /* > + * If this @addr falls under cold or hotplugged memory regions, > + * check there too. > + */ > + qmp_pc_dimm_device_list(qdev_get_machine(), &prev); > + for (info = info_list; info; info = info->next) { > + MemoryDeviceInfo *value = info->value; > + > + if (value) { > + switch (value->kind) { > + case MEMORY_DEVICE_INFO_KIND_DIMM: > + if (addr >= value->dimm->addr && > + addr < (value->dimm->addr + value->dimm->size)) { > + qapi_free_MemoryDeviceInfoList(info_list); > + return value->dimm->node; > + } > + break; > + default: > + break; > + } > + } > + } > + qapi_free_MemoryDeviceInfoList(info_list); > + error_setg(errp, "Address 0x" RAM_ADDR_FMT " doesn't belong to any " > + "NUMA node", addr); > + > + return -1; > +} > + > +static void numa_set_mem_address(int nodenr) > +{ > + if (nodenr) { > + numa_info[nodenr].mem_start = numa_info[nodenr-1].mem_end; > + } else { > + numa_info[nodenr].mem_start = 0; > + } > + numa_info[nodenr].mem_end = numa_info[nodenr].mem_start + > + numa_info[nodenr].node_mem; > +} > + > static void numa_node_parse(NumaNodeOptions *node, QemuOpts *opts, Error **errp) > { > uint16_t nodenr; > @@ -276,6 +333,10 @@ void parse_numa_opts(MachineClass *mc) > } > > for (i = 0; i < nb_numa_nodes; i++) { > + numa_set_mem_address(i); > + } > + > + for (i = 0; i < nb_numa_nodes; i++) { > if (!bitmap_empty(numa_info[i].node_cpu, MAX_CPUMASK_BITS)) { > break; > } > -- > 2.1.0