All of lore.kernel.org
 help / color / mirror / Atom feed
From: Igor Mammedov <imammedo@redhat.com>
To: Babu Moger <babu.moger@amd.com>
Cc: qemu-devel@nongnu.org, pbonzini@redhat.com, ehabkost@redhat.com,
	rth@twiddle.net
Subject: Re: [PATCH v2 3/3] hw/386: Fix uninitialized memory with -device and CPU hotplug
Date: Mon, 27 Jul 2020 18:36:12 +0200	[thread overview]
Message-ID: <20200727183612.684fe574@redhat.com> (raw)
In-Reply-To: <159362467562.36204.11074523095942812006.stgit@naples-babu.amd.com>

On Wed, 01 Jul 2020 12:31:15 -0500
Babu Moger <babu.moger@amd.com> wrote:

> Noticed the following command failure while testing CPU hotplug.
> 
> $ qemu-system-x86_64 -machine q35,accel=kvm -smp 1,maxcpus=2,
>   cores=1, threads=1,sockets=2 -cpu EPYC -device EPYC-x86_64-
>   cpu,core-id=0,socket-id=1,thread-id=0
> 
>   qemu-system-x86_64: -device EPYC-x86_64-cpu,core-id=0,socket-id=1,
>   thread-id=0: Invalid CPU [socket: 21855, die: 0, core: 0, thread: 0]
>   with APIC ID 21855, valid index range 0:1
> 
> This happens because APIC ID is calculated using uninitialized memory.
> This is happening after the addition of new field node_id in X86CPUTopoIDs
> structure. The node_id field is uninitialized while calling
> apicid_from_topo_ids. The problem is discussed in the thread below.
> https://lore.kernel.org/qemu-devel/20200602171838.GG577771@habkost.net/
> 
> Fix the problem by initializing the node_id from the device being added.
> 
> Fixes:
> Link: https://bugzilla.redhat.com/show_bug.cgi?id=1828750
> 
> Signed-off-by: Babu Moger <babu.moger@amd.com>
> ---
>  hw/i386/pc.c |   10 ++++++++++
>  1 file changed, 10 insertions(+)
> 
> diff --git a/hw/i386/pc.c b/hw/i386/pc.c
> index e613b2299f..aa9fb48834 100644
> --- a/hw/i386/pc.c
> +++ b/hw/i386/pc.c
> @@ -1553,6 +1553,15 @@ static void pc_cpu_pre_plug(HotplugHandler *hotplug_dev,
>              cpu->die_id = 0;
>          }
>  
so this is from 
 'if (cpu->apic_id == UNASSIGNED_APIC_ID) {'
branch, meaning cpu comes from -device/device_add

> +        /*
> +         * If node_id is not set, initialize it to zero for now. If the user
> +         * does not pass the correct node in case of numa configuration, it
> +         * will be rejected eventually.
> +         */
> +        if (cpu->node_id < 0) {
which means that user hasn't provided 'node-id',
in which case we should error out asking for specifying NUMA node-id along with other options

(1)
However that's not enough since by contract query-hotpluggbale-cpus shall provide all attributes
necessary to hotplug CPU, which makes node-id is not an optional in case of EPYC cpu.
So we need to initialize ms->possible_cpus->cpus[i].props.[has_]node_id by the time
we start creating CPUs.

here are 2 variants:
(2)
  * single node:
      nodes_per_pkg 1 and ms->smp.sockets == 1

    since it's the only node and mapping of RAM/CPU is unambigiuos,
    we can deal with it by moving auto_enable_numa into MachineState
    and enabling it in case EPYC CPU is used

  * multiple nodes:
      - ms->smp.sockets > 1
      - nodes_per_pkg > 1
    we can't make up NUMA nodes automatically, and have to ask user to use -numa options
    to provide nodes along with CPU/RAM mapping. So in case NUMA wasn't configured
    explicitly, we can only error out. (that also applies to CPU created implicitly by board '-smp X')

(3) Once user supplied mapping we need to checks that it matches EPYC topology,


(4) As for CPUID, current code in CPUID_Fn8000001E_ECX
      if (nodes <= 4) { /* here nodes is nodes_per_pkg */
         / goes by stricly spec /
         *ecx = ((nodes - 1) << 8) | (topo_ids.pkg_id << 2) | topo_ids.node_id;
         /* makes up system wide NUMA node IDs which happen to match system wide
            NUMA node IDs created by -numa, when -smp + -numa produces nodes_per_pkg is in that range,
            basically user has no idea when this happens
          */
      } else {
         /* makeup new algorithm system wide NUMA node IDs generation for out of spec behaviour */
      }
     
    problem with both branches is that might lead to inconsistentcy between system wide
    NUMA node id in CPUID_Fn8000001E_ECX and the one configured with -numa which goes to
    SRAT ACPI table and should go to CPU::node-id property.

    Considering that out of spec behaviour is allowed we probably schould replace both branches
    with
       *ecx = ((nodes - 1) << 8) | cpu->node_id;
    which ensures consistency of system wide NUMA node ids and add checks for max nodes/max node id.

checks could be done early in cpu's realize() function.



> +            cpu->node_id = 0;
> +        }

>          if (cpu->socket_id < 0) {
>              error_setg(errp, "CPU socket-id is not set");
>              return;
> @@ -1587,6 +1596,7 @@ static void pc_cpu_pre_plug(HotplugHandler *hotplug_dev,
>          }
>  
>          topo_ids.pkg_id = cpu->socket_id;
> +        topo_ids.node_id = cpu->node_id;
>          topo_ids.die_id = cpu->die_id;
>          topo_ids.core_id = cpu->core_id;
>          topo_ids.smt_id = cpu->thread_id;
> 



      reply	other threads:[~2020-07-27 16:37 UTC|newest]

Thread overview: 23+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2020-07-01 17:30 [PATCH v2 0/3] Fix couple of issues with AMD topology Babu Moger
2020-07-01 17:31 ` [PATCH v2 1/3] hw/i386: Initialize topo_ids from CpuInstanceProperties Babu Moger
2020-07-13  9:08   ` Igor Mammedov
2020-07-13 15:02     ` Babu Moger
2020-07-13 16:17       ` Igor Mammedov
2020-07-13 16:43         ` Babu Moger
2020-07-13 17:32           ` Igor Mammedov
2020-07-13 19:30             ` Babu Moger
2020-07-14 16:41               ` Igor Mammedov
2020-07-14 17:26                 ` Babu Moger
2020-07-14 18:26                   ` Igor Mammedov
2020-07-24 17:05               ` Igor Mammedov
2020-07-27 15:49                 ` Babu Moger
2020-07-27 17:14                   ` Igor Mammedov
2020-07-27 23:59                     ` Babu Moger
2020-07-29 14:12                       ` Igor Mammedov
2020-07-29 21:22                         ` Babu Moger
2020-07-30 11:27                           ` Igor Mammedov
2020-07-01 17:31 ` [PATCH v2 2/3] hw/i386: Build apic_id " Babu Moger
2020-07-13  9:15   ` Igor Mammedov
2020-07-13 15:00     ` Babu Moger
2020-07-01 17:31 ` [PATCH v2 3/3] hw/386: Fix uninitialized memory with -device and CPU hotplug Babu Moger
2020-07-27 16:36   ` Igor Mammedov [this message]

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20200727183612.684fe574@redhat.com \
    --to=imammedo@redhat.com \
    --cc=babu.moger@amd.com \
    --cc=ehabkost@redhat.com \
    --cc=pbonzini@redhat.com \
    --cc=qemu-devel@nongnu.org \
    --cc=rth@twiddle.net \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.