linux-arm-kernel.lists.infradead.org archive mirror
 help / color / mirror / Atom feed
From: lorenzo.pieralisi@arm.com (Lorenzo Pieralisi)
To: linux-arm-kernel@lists.infradead.org
Subject: [PATCH v7 10/17] ARM64 / ACPI: Parse MADT for SMP initialization
Date: Tue, 20 Jan 2015 15:16:28 +0000	[thread overview]
Message-ID: <20150120151628.GI5398@red-moon> (raw)
In-Reply-To: <54BE53A3.5010706@linaro.org>

On Tue, Jan 20, 2015 at 01:09:55PM +0000, Hanjun Guo wrote:

[...]

> >> +{
> >> +       int cpu;
> >> +
> >> +       if (mpidr == INVALID_HWID) {
> >> +               pr_info("Skip MADT cpu entry with invalid MPIDR\n");
> >> +               return -EINVAL;
> >> +       }
> >> +
> >> +       total_cpus++;
> >> +       if (!enabled)
> >> +               return -EINVAL;
> >> +
> >> +       if (enabled_cpus >=  NR_CPUS) {
> >> +               pr_warn("NR_CPUS limit of %d reached, Processor %d/0x%llx ignored.\n",
> >> +                       NR_CPUS, total_cpus, mpidr);
> >> +               return -EINVAL;
> >> +       }
> >> +
> >> +       /* No need to check duplicate MPIDRs for the first CPU */
> >> +       if (enabled_cpus) {
> >> +               /*
> >> +                * Duplicate MPIDRs are a recipe for disaster. Scan
> >> +                * all initialized entries and check for
> >> +                * duplicates. If any is found just ignore the CPU.
> >> +                */
> >> +               for_each_possible_cpu(cpu) {
> >> +                       if (cpu_logical_map(cpu) == mpidr) {
> >> +                               pr_err("Firmware bug, duplicate CPU MPIDR: 0x%llx in MADT\n",
> >> +                                      mpidr);
> >> +                               return -EINVAL;
> >> +                       }
> >> +               }
> >> +
> >> +               /* allocate a logical cpu id for the new comer */
> >> +               cpu = cpumask_next_zero(-1, cpu_possible_mask);
> >> +       } else {
> >> +               /*
> >> +                * First GICC entry must be BSP as ACPI spec said
> >> +                * in section 5.2.12.15
> >> +                */
> >> +               if  (cpu_logical_map(0) != mpidr) {
> >> +                       pr_err("First GICC entry with MPIDR 0x%llx is not BSP\n",
> >> +                              mpidr);
> >> +                       return -EINVAL;
> >> +               }
> >> +
> >> +               /*
> >> +                * boot_cpu_init() already hold bit 0 in cpu_present_mask
> >
> > You mean cpu_possible_mask ? That's what you allocate from above.
> 
> Another hot-plug piece leaved, will update it.
> 
> >
> >> +                * for BSP, no need to allocate again.
> >> +                */
> >> +               cpu = 0;
> >> +       }
> >> +
> >> +       /* CPU 0 was already initialized */
> >> +       if (cpu) {
> >> +               cpu_ops[cpu] = cpu_get_ops(acpi_psci_present() ? "psci" : NULL);
> >> +               if (!cpu_ops[cpu])
> >> +                       return -EINVAL;
> >> +
> >> +               if (cpu_ops[cpu]->cpu_init(NULL, cpu))
> >> +                       return -EOPNOTSUPP;
> >> +
> >> +               /* map the logical cpu id to cpu MPIDR */
> >> +               cpu_logical_map(cpu) = mpidr;
> >> +
> >> +               set_cpu_possible(cpu, true);
> >> +       } else {
> >> +               /* get cpu0's ops, no need to return if ops is null */
> >> +               cpu_ops[0] = cpu_get_ops(acpi_psci_present() ? "psci" : NULL);
> >> +       }
> >
> > I do not see much point in calling cpu_get_ops with NULL, and adding
> > the check in it to return NULL when the parameter is NULL.
> >
> > What would you expect from cpu_get_ops when called with NULL other than
> > a NULL pointer ?
> 
> I'm lost here since it is best way for the implementation I think, any
> suggestions?

My suggestion is: no PSCI, no secondaries booting, that's what your code
wants to achieve, right ? What's the point in calling cpu_get_ops() when
PSCI is not present then ? What do you expect from calling cpu_get_ops(NULL)
other than a NULL pointer in return ?

Put it differently, if !acpi_psci_present() parsing code should bail out,
there are no CPU ops to initialize for secondaries, that's what I think
your aim is, correct ?

On a side note, if ACPI PSCI is not present you still keep booting on
the boot processor.

What piece of code initialize cpu_ops[0] in that case ? I could not
find any, basically you would run the kernel with cpu_ops[0] == NULL.

> 
> >
> > You could move:
> >
> > cpu_ops[cpu] = cpu_get_ops(acpi_psci_present() ? "psci" : NULL);
> >
> > out of the if and remove the else, do not know if it makes code clearer,
> > shorter for certain.
> >
> >> +
> >> +       enabled_cpus++;
> >> +       return cpu;
> >> +}
> >> +
> >> +static int __init
> >> +acpi_parse_gic_cpu_interface(struct acpi_subtable_header *header,
> >> +                               const unsigned long end)
> >> +{
> >> +       struct acpi_madt_generic_interrupt *processor;
> >> +
> >> +       processor = (struct acpi_madt_generic_interrupt *)header;
> >> +
> >> +       if (BAD_MADT_ENTRY(processor, end))
> >> +               return -EINVAL;
> >> +
> >> +       acpi_table_print_madt_entry(header);
> >> +
> >> +       acpi_map_gic_cpu_interface(processor->arm_mpidr & MPIDR_HWID_BITMASK,
> >> +               processor->flags & ACPI_MADT_ENABLED);
> >> +
> >> +       return 0;
> >> +}
> >> +
> >> +/* Parse GIC cpu interface entries in MADT for SMP init */
> >> +void __init acpi_smp_init_cpus(void)
> >> +{
> >> +       int count;
> >> +
> >> +       /*
> >> +        * do a partial walk of MADT to determine how many CPUs
> >> +        * we have including disabled CPUs, and get information
> >> +        * we need for SMP init
> >> +        */
> >> +       count = acpi_table_parse_madt(ACPI_MADT_TYPE_GENERIC_INTERRUPT,
> >> +                       acpi_parse_gic_cpu_interface, 0);
> >> +
> >> +       if (!count) {
> >> +               pr_err("No GIC CPU interface entries present\n");
> >> +               return;
> >> +       } else if (count < 0) {
> >> +               pr_err("Error parsing GIC CPU interface entry\n");
> >> +               return;
> >> +       }
> >> +
> >> +       /* Make boot-up look pretty */
> >> +       pr_info("%d CPUs enabled, %d CPUs total\n", enabled_cpus, total_cpus);
> >> +}
> >> +
> >>   static int __init acpi_parse_fadt(struct acpi_table_header *table)
> >>   {
> >>          struct acpi_table_fadt *fadt = (struct acpi_table_fadt *)table;
> >> @@ -62,8 +196,20 @@ static int __init acpi_parse_fadt(struct acpi_table_header *table)
> >>           * to get arm boot flags, or we will disable ACPI.
> >>           */
> >>          if (table->revision > 5 ||
> >> -           (table->revision == 5 && fadt->minor_revision >= 1))
> >> -               return 0;
> >> +           (table->revision == 5 && fadt->minor_revision >= 1)) {
> >> +               /*
> >> +                * ACPI 5.1 only has two explicit methods to boot up SMP,
> >> +                * PSCI and Parking protocol, but the Parking protocol is
> >> +                * only specified for ARMv7 now, so make PSCI as the only
> >> +                * way for the SMP boot protocol before some updates for
> >> +                * the ACPI spec or the Parking protocol spec.
> >> +                */
> >> +               if (acpi_psci_present())
> >> +                       return 0;
> >> +
> >> +               pr_warn("No PSCI support, will not bring up secondary CPUs\n");
> >> +               return -EOPNOTSUPP;
> >> +       }
> >>
> >>          pr_warn("Unsupported FADT revision %d.%d, should be 5.1+, will disable ACPI\n",
> >>                  table->revision, fadt->minor_revision);
> >> diff --git a/arch/arm64/kernel/cpu_ops.c b/arch/arm64/kernel/cpu_ops.c
> >> index cce9524..1ea7b9f 100644
> >> --- a/arch/arm64/kernel/cpu_ops.c
> >> +++ b/arch/arm64/kernel/cpu_ops.c
> >> @@ -27,7 +27,7 @@ extern const struct cpu_operations cpu_psci_ops;
> >>
> >>   const struct cpu_operations *cpu_ops[NR_CPUS];
> >>
> >> -static const struct cpu_operations *supported_cpu_ops[] __initconst = {
> >> +static const struct cpu_operations *supported_cpu_ops[] = {
> >
> > This __initconst removal should be explained either with code needing
> > it or through a comment. You can't make changes with future patches
> > in mind, since they may never get merged and you leave code in this
> > patch incomplete.
> >
> > As far as I know if physical CPU hotplug can't/won't be done on ARM64 your
> > patch would make changes that are not needed, and miss some changes
> > that are (eg removing enabled_cpus or make it __initdata).
> 
> I agree with you :)
> 
> >
> > You can't write a patch with assumptions on subsequent patches.
> >
> >>   #ifdef CONFIG_SMP
> >>          &smp_spin_table_ops,
> >>   #endif
> >> @@ -35,10 +35,13 @@ static const struct cpu_operations *supported_cpu_ops[] __initconst = {
> >>          NULL,
> >>   };
> >>
> >> -static const struct cpu_operations * __init cpu_get_ops(const char *name)
> >> +const struct cpu_operations *cpu_get_ops(const char *name)
> >
> > Ditto.
> >
> >>   {
> >>          const struct cpu_operations **ops = supported_cpu_ops;
> >>
> >> +       if (!name)
> >> +               return NULL;
> >> +
> >
> > See above.
> >
> >>          while (*ops) {
> >>                  if (!strcmp(name, (*ops)->name))
> >>                          return *ops;
> >> diff --git a/arch/arm64/kernel/setup.c b/arch/arm64/kernel/setup.c
> >> index ef5b1e1..54e39e3 100644
> >> --- a/arch/arm64/kernel/setup.c
> >> +++ b/arch/arm64/kernel/setup.c
> >> @@ -414,13 +414,16 @@ void __init setup_arch(char **cmdline_p)
> >>          if (acpi_disabled) {
> >>                  unflatten_device_tree();
> >>                  psci_dt_init();
> >> +               cpu_read_bootcpu_ops();
> >> +#ifdef CONFIG_SMP
> >> +               of_smp_init_cpus();
> >> +#endif
> >>          } else {
> >>                  psci_acpi_init();
> >> +               acpi_smp_init_cpus();
> >
> > With DT you call cpu_read_bootcpu_ops() and then of_smp_init_cpus()
> > with acpi you have one function that does both, it is not really
> > neat.
> 
> The mechanism for ACPI table entry scanning is that for every matched
> structure (such as GICC) found, the parse function will be called, so
> if we separate them it will duplicate the scanning of ACPI tables.

Call it acpi_init_cpus() then.

Lorenzo

  reply	other threads:[~2015-01-20 15:16 UTC|newest]

Thread overview: 156+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2015-01-14 15:04 [PATCH v7 00/17] Introduce ACPI for ARM64 based on ACPI 5.1 Hanjun Guo
2015-01-14 15:04 ` [PATCH v7 01/17] arm64: allow late use of early_ioremap Hanjun Guo
2015-01-15 18:44   ` Mark Langsdorf
2015-01-14 15:04 ` [PATCH v7 02/17] ARM64 / ACPI: Get RSDP and ACPI boot-time tables Hanjun Guo
2015-01-15 18:45   ` Mark Langsdorf
2015-01-14 15:04 ` [PATCH v7 03/17] ARM64 / ACPI: Introduce sleep-arm.c Hanjun Guo
2015-01-15 18:45   ` Mark Langsdorf
2015-01-14 15:04 ` [PATCH v7 04/17] ARM64 / ACPI: Introduce early_param for "acpi" and pass acpi=force to enable ACPI Hanjun Guo
2015-01-15 18:46   ` Mark Langsdorf
2015-01-19 11:42   ` Catalin Marinas
2015-01-19 11:55     ` Ard Biesheuvel
2015-01-19 13:51       ` Catalin Marinas
2015-01-19 14:00         ` Ard Biesheuvel
2015-01-19 14:22           ` Catalin Marinas
2015-01-19 15:13         ` Grant Likely
2015-01-19 16:59           ` Jon Masters
2015-01-19 17:52             ` Catalin Marinas
2015-01-19 18:01               ` Mark Rutland
2015-01-20  9:29                 ` Hanjun Guo
2015-01-20 10:56                   ` Catalin Marinas
2015-01-20 11:10                   ` Mark Rutland
2015-01-20 12:17                     ` Hanjun Guo
2015-01-20 12:31                     ` Leif Lindholm
2015-01-20 19:20                   ` Stefano Stabellini
2015-01-21  9:43                     ` Parth Dixit
2015-01-21 15:23                     ` Catalin Marinas
2015-01-21 15:29                       ` Jon Masters
2015-01-21 15:42                         ` Catalin Marinas
2015-01-21 15:56                           ` Graeme Gregory
2015-01-21 16:05                           ` Jon Masters
2015-01-21 16:16                             ` Catalin Marinas
2015-01-21 16:51                               ` Parth Dixit
2015-01-21 16:10                       ` Stefano Stabellini
2015-01-22 12:29                         ` Daniel Kiper
2015-01-28 17:58   ` [Linaro-acpi] " Timur Tabi
2015-01-28 18:08     ` Catalin Marinas
2015-01-28 18:08     ` Timur Tabi
2015-01-28 18:14       ` Catalin Marinas
2015-01-28 18:18         ` Timur Tabi
2015-01-29 15:19           ` Catalin Marinas
2015-01-29 18:20             ` Ard Biesheuvel
2015-01-29 18:21               ` Timur Tabi
2015-01-29 18:28                 ` Ard Biesheuvel
2015-01-29 18:34                   ` Timur Tabi
2015-01-29 18:44                     ` Jon Masters
2015-01-29 23:11                       ` Catalin Marinas
2015-01-29 23:16                         ` Jon Masters
2015-01-29 23:30                           ` Catalin Marinas
2015-01-30 11:13               ` Catalin Marinas
2015-01-30 14:48                 ` Timur Tabi
2015-01-30 15:12                   ` Ard Biesheuvel
2015-01-14 15:04 ` [PATCH v7 05/17] ARM64 / ACPI: If we chose to boot from acpi then disable FDT Hanjun Guo
2015-01-15 18:46   ` Mark Langsdorf
2015-01-19 11:45   ` Catalin Marinas
2015-01-14 15:04 ` [PATCH v7 06/17] ARM64 / ACPI: Make PCI optional for ACPI on ARM64 Hanjun Guo
2015-01-15 18:46   ` Mark Langsdorf
2015-01-16  9:49   ` Catalin Marinas
2015-01-18  6:25     ` Hanjun Guo
2015-01-18  6:31       ` Jon Masters
2015-01-18  6:46         ` Hanjun Guo
2015-01-18  9:29           ` Graeme Gregory
2015-01-18 12:32             ` Jon Masters
2015-01-19  4:26             ` Hanjun Guo
2015-01-19 10:37             ` Catalin Marinas
2015-01-19 10:42       ` Catalin Marinas
2015-01-20  2:39         ` Hanjun Guo
2015-01-20 11:00           ` Catalin Marinas
2015-01-20 11:56             ` Hanjun Guo
2015-01-20 12:26             ` [Linaro-acpi] " Tomasz Nowicki
2015-01-20 15:10               ` Catalin Marinas
2015-01-14 15:04 ` [PATCH v7 07/17] ARM64 / ACPI: Disable ACPI if FADT revision is less than 5.1 Hanjun Guo
2015-01-15 18:47   ` Mark Langsdorf
2015-01-16 14:33   ` Lorenzo Pieralisi
2015-01-18  5:49     ` Hanjun Guo
2015-01-19 11:50   ` Catalin Marinas
2015-01-20  3:05     ` Hanjun Guo
2015-01-14 15:04 ` [PATCH v7 08/17] ARM64 / ACPI: Get PSCI flags in FADT for PSCI init Hanjun Guo
2015-01-15 18:47   ` Mark Langsdorf
2015-01-14 15:04 ` [PATCH v7 09/17] ACPI / table: Print GIC information when MADT is parsed Hanjun Guo
2015-01-15 18:47   ` Mark Langsdorf
2015-01-14 15:04 ` [PATCH v7 10/17] ARM64 / ACPI: Parse MADT for SMP initialization Hanjun Guo
2015-01-15 18:48   ` Mark Langsdorf
2015-01-16 18:18   ` Lorenzo Pieralisi
2015-01-20 13:09     ` Hanjun Guo
2015-01-20 15:16       ` Lorenzo Pieralisi [this message]
2015-01-14 15:04 ` [PATCH v7 11/17] ACPI / processor: Make it possible to get CPU hardware ID via GICC Hanjun Guo
2015-01-15 18:48   ` Mark Langsdorf
2015-01-20 11:17   ` Catalin Marinas
2015-01-20 12:26     ` Hanjun Guo
2015-01-20 16:16   ` Lorenzo Pieralisi
2015-01-14 15:05 ` [PATCH v7 12/17] ARM64 / ACPI: Introduce ACPI_IRQ_MODEL_GIC and register device's gsi Hanjun Guo
2015-01-15 18:48   ` Mark Langsdorf
2015-01-16 10:45   ` Marc Zyngier
2015-01-14 15:05 ` [PATCH v7 13/17] ARM64 / ACPI: Add GICv2 specific ACPI boot support Hanjun Guo
2015-01-15 18:50   ` Mark Langsdorf
2015-01-16 11:15   ` Marc Zyngier
2015-01-16 13:54     ` Grant Likely
2015-01-16 14:37       ` Marc Zyngier
2015-01-22 12:46         ` Hanjun Guo
2015-01-22 14:46           ` Marc Zyngier
2015-01-23  9:38             ` Hanjun Guo
2015-01-27 16:12         ` Grant Likely
2015-01-29 15:29           ` Catalin Marinas
2015-01-29 16:06             ` Tomasz Nowicki
2015-01-20 10:40     ` Tomasz Nowicki
2015-01-20 13:05       ` Jon Masters
2015-01-14 15:05 ` [PATCH v7 14/17] ARM64 / ACPI: Parse GTDT to initialize arch timer Hanjun Guo
2015-01-15 18:50   ` Mark Langsdorf
2015-01-14 15:05 ` [PATCH v7 15/17] ARM64 / ACPI: Select ACPI_REDUCED_HARDWARE_ONLY if ACPI is enabled on ARM64 Hanjun Guo
2015-01-15 18:50   ` Mark Langsdorf
2015-01-14 15:05 ` [PATCH v7 16/17] ARM64 / ACPI: Enable ARM64 in Kconfig Hanjun Guo
2015-01-15 18:50   ` Mark Langsdorf
2015-01-14 15:05 ` [PATCH v7 17/17] Documentation: ACPI for ARM64 Hanjun Guo
2015-01-15 18:54   ` Mark Langsdorf
2015-01-15 16:26 ` [PATCH v7 00/17] Introduce ACPI for ARM64 based on ACPI 5.1 Grant Likely
2015-01-15 18:23   ` Catalin Marinas
2015-01-15 19:02     ` Mark Brown
2015-01-15 20:04       ` Jason Cooper
2015-01-15 20:31         ` Mark Brown
2015-01-15 20:51           ` Jason Cooper
2015-01-16 11:49             ` Mark Brown
2015-01-16  7:24           ` Hanjun Guo
2015-01-16 10:10         ` Catalin Marinas
2015-01-16 12:05           ` Mark Brown
2015-01-16 12:29             ` Will Deacon
2015-01-16 16:54               ` Mark Brown
2015-01-18  6:36           ` Hanjun Guo
2015-01-15 21:31     ` Al Stone
2015-01-15 21:38       ` Jon Masters
2015-01-16 10:20       ` Catalin Marinas
2015-01-16 15:17         ` [Linaro-acpi] " Al Stone
2015-01-16 15:23           ` Al Stone
2015-01-16 15:44           ` Suravee Suthikulpanit
2015-01-16  7:17     ` Hanjun Guo
2015-01-16 10:04       ` Catalin Marinas
2015-01-16 14:45       ` Tom Lendacky
2015-01-16 14:55         ` Will Deacon
2015-01-16 15:14           ` Arnd Bergmann
2015-01-16 15:25             ` Catalin Marinas
2015-01-16 15:33             ` Will Deacon
2015-01-16 15:40               ` Arnd Bergmann
2015-01-16 15:43                 ` [Linaro-acpi] " Arnd Bergmann
2015-01-16 15:49                 ` Will Deacon
2015-01-16 15:53                   ` [Linaro-acpi] " Arnd Bergmann
2015-01-17 17:53                     ` Rob Herring
2015-01-16 17:12                   ` Tom Lendacky
2015-01-16 15:16           ` Tom Lendacky
2015-01-16 16:29     ` Grant Likely
2015-01-16 17:20       ` [Linaro-acpi] " Arnd Bergmann
2015-01-17 11:52       ` Catalin Marinas
2015-01-15 18:58 ` Jon Masters
2015-01-15 19:49 ` Mark Langsdorf
2015-01-16  8:37   ` Hanjun Guo
2015-01-15 21:33 ` Suravee Suthikulanit
2015-01-27 17:46 ` Timur Tabi
2015-01-28 13:53   ` Hanjun Guo

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=20150120151628.GI5398@red-moon \
    --to=lorenzo.pieralisi@arm.com \
    --cc=linux-arm-kernel@lists.infradead.org \
    /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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).