]> git.proxmox.com Git - mirror_ubuntu-jammy-kernel.git/commitdiff
powerpc/numa: Detect support for coregroup
authorSrikar Dronamraju <srikar@linux.vnet.ibm.com>
Mon, 10 Aug 2020 07:18:31 +0000 (12:48 +0530)
committerMichael Ellerman <mpe@ellerman.id.au>
Wed, 16 Sep 2020 12:13:31 +0000 (22:13 +1000)
Add support for grouping cores based on the device-tree classification.
- The last domain in the associativity domains always refers to the
core.
- If primary reference domain happens to be the penultimate domain in
the associativity domains device-tree property, then there are no
coregroups. However if its not a penultimate domain, then there are
coregroups. There can be more than one coregroup. For now we would be
interested in the last or the smallest coregroups, i.e one sub-group
per DIE.

Currently there are no firmwares that are exposing this grouping. Hence
allow the basis for grouping to be abstract.  Once the firmware starts
using this grouping, code would be added to detect the type of grouping
and adjust the sd domain flags accordingly.

Signed-off-by: Srikar Dronamraju <srikar@linux.vnet.ibm.com>
Reviewed-by: Gautham R. Shenoy <ego@linux.vnet.ibm.com>
Signed-off-by: Michael Ellerman <mpe@ellerman.id.au>
Link: https://lore.kernel.org/r/20200810071834.92514-8-srikar@linux.vnet.ibm.com
arch/powerpc/include/asm/smp.h
arch/powerpc/kernel/smp.c
arch/powerpc/mm/numa.c

index b727f5f7b8f9381b17c649e9610645180374cb23..041f0b97c45b6ceadbe68f163eaf7742dc6f0fff 100644 (file)
@@ -28,6 +28,7 @@
 extern int boot_cpuid;
 extern int spinning_secondaries;
 extern u32 *cpu_to_phys_id;
+extern bool coregroup_enabled;
 
 extern void cpu_die(void);
 extern int cpu_to_chip_id(int cpu);
index 016a822eb8c44197f4537800f37833967dc258f3..a44b9350d2eff4de780a8c55f4b41dd0bb1fb83f 100644 (file)
@@ -75,6 +75,7 @@ static DEFINE_PER_CPU(int, cpu_state) = { 0 };
 
 struct task_struct *secondary_current;
 bool has_big_cores;
+bool coregroup_enabled;
 
 DEFINE_PER_CPU(cpumask_var_t, cpu_sibling_map);
 DEFINE_PER_CPU(cpumask_var_t, cpu_smallcore_map);
index 481951ac3e555af31753a859445c23773f94476e..b2c44c5a81fbb44571b638275b9f3c3d8b47a10c 100644 (file)
@@ -897,7 +897,9 @@ static void __init setup_node_data(int nid, u64 start_pfn, u64 end_pfn)
 static void __init find_possible_nodes(void)
 {
        struct device_node *rtas;
-       u32 numnodes, i;
+       const __be32 *domains;
+       int prop_length, max_nodes;
+       u32 i;
 
        if (!numa_enabled)
                return;
@@ -906,25 +908,31 @@ static void __init find_possible_nodes(void)
        if (!rtas)
                return;
 
-       if (of_property_read_u32_index(rtas, "ibm,current-associativity-domains",
-                               min_common_depth, &numnodes)) {
-               /*
-                * ibm,current-associativity-domains is a fairly recent
-                * property. If it doesn't exist, then fallback on
-                * ibm,max-associativity-domains. Current denotes what the
-                * platform can support compared to max which denotes what the
-                * Hypervisor can support.
-                */
-               if (of_property_read_u32_index(rtas, "ibm,max-associativity-domains",
-                               min_common_depth, &numnodes))
+       /*
+        * ibm,current-associativity-domains is a fairly recent property. If
+        * it doesn't exist, then fallback on ibm,max-associativity-domains.
+        * Current denotes what the platform can support compared to max
+        * which denotes what the Hypervisor can support.
+        */
+       domains = of_get_property(rtas, "ibm,current-associativity-domains",
+                                       &prop_length);
+       if (!domains) {
+               domains = of_get_property(rtas, "ibm,max-associativity-domains",
+                                       &prop_length);
+               if (!domains)
                        goto out;
        }
 
-       for (i = 0; i < numnodes; i++) {
+       max_nodes = of_read_number(&domains[min_common_depth], 1);
+       for (i = 0; i < max_nodes; i++) {
                if (!node_possible(i))
                        node_set(i, node_possible_map);
        }
 
+       prop_length /= sizeof(int);
+       if (prop_length > min_common_depth + 2)
+               coregroup_enabled = 1;
+
 out:
        of_node_put(rtas);
 }