summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSrikar Dronamraju <srikar@linux.ibm.com>2025-11-12 13:18:59 +0530
committerMadhavan Srinivasan <maddy@linux.ibm.com>2025-11-14 11:12:56 +0530
commitfb2ff9fa72e20a75cab0ffc9dc8735de68ed4d0d (patch)
tree3f26b35d8f477a472fdeb9d621c2cc44f79d4b49
parent2617bd81ae54128e63e764c48935e572e3dee501 (diff)
powerpc/smp: Expose die_id and die_cpumask
>From Power10 processors onwards, each chip has 2 hemispheres. For LPARs running on PowerVM Hypervisor, hypervisor determines the allocation of CPU groups to each LPAR, resulting in two LPARs with the same number of CPUs potentially having different numbers of CPUs from each hemisphere. Additionally, it is not feasible to ascertain the hemisphere based solely on the CPU number. Users wishing to assign their workload to all CPUs, or a subset of CPUs within a specific hemisphere, encounter difficulties in identifying the cpumask. To address this, it is proposed to expose hemisphere information as a die in sysfs. This aligns with other architectures and facilitates the identification of CPUs within the same hemisphere. Tools such as lstopo can also access this information. Please note: The hypervisor reveals the locality of the CPUs to hemispheres only in dedicated mode. Consequently, in systems where hemisphere information is unavailable, such as shared LPARs, the die_cpus information in sysfs will mirror package_cpus, with die_id set to -1. Without this change. $ grep . /sys/devices/system/cpu/cpu16/topology/{die*,package*} 2>/dev/null /sys/devices/system/cpu/cpu16/topology/package_cpus:000000,000000ff,ffff0000 /sys/devices/system/cpu/cpu16/topology/package_cpus_list:16-39 With this change. $ grep . /sys/devices/system/cpu/cpu16/topology/{die*,package*} 2>/dev/null /sys/devices/system/cpu/cpu16/topology/die_cpus:000000,00000000,00ff0000 /sys/devices/system/cpu/cpu16/topology/die_cpus_list:16-23 /sys/devices/system/cpu/cpu16/topology/die_id:2 /sys/devices/system/cpu/cpu16/topology/package_cpus:000000,000000ff,ffff0000 /sys/devices/system/cpu/cpu16/topology/package_cpus_list:16-39 snipped lstopo-no-graphics o/p Group0 L#0 (total=8747584KB) Package L#0 (total=3564096KB CPUModel="POWER10 (architected), altivec supported" CPURevision="2.0 (pvr 0080 0200)") NUMANode L#0 (P#0 local=3564096KB total=3564096KB) Die L#0 (P#0) Core L#0 (P#0) <snipped> Package L#1 (total=5183488KB CPUModel="POWER10 (architected), altivec supported" CPURevision="2.0 (pvr 0080 0200)") NUMANode L#1 (P#1 local=5183488KB total=5183488KB) Die L#2 (P#2) Core L#2 (P#16) L3Cache L#4 (size=4096KB linesize=128 ways=16) L2Cache L#4 (size=1024KB linesize=128 ways=8) L1dCache L#4 (size=32KB linesize=128 ways=8) L1iCache L#4 (size=48KB linesize=128 ways=6) PU L#16 (P#16) PU L#17 (P#18) PU L#18 (P#20) PU L#19 (P#22) L3Cache L#5 (size=4096KB linesize=128 ways=16) L2Cache L#5 (size=1024KB linesize=128 ways=8) L1dCache L#5 (size=32KB linesize=128 ways=8) L1iCache L#5 (size=48KB linesize=128 ways=6) PU L#20 (P#17) PU L#21 (P#19) PU L#22 (P#21) PU L#23 (P#23) Die L#3 (P#3) Core L#3 (P#24) L3Cache L#6 (size=4096KB linesize=128 ways=16) L2Cache L#6 (size=1024KB linesize=128 ways=8) L1dCache L#6 (size=32KB linesize=128 ways=8) L1iCache L#6 (size=48KB linesize=128 ways=6) PU L#24 (P#24) PU L#25 (P#26) PU L#26 (P#28) PU L#27 (P#30) L3Cache L#7 (size=4096KB linesize=128 ways=16) L2Cache L#7 (size=1024KB linesize=128 ways=8) L1dCache L#7 (size=32KB linesize=128 ways=8) L1iCache L#7 (size=48KB linesize=128 ways=6) PU L#28 (P#25) PU L#29 (P#27) PU L#30 (P#29) PU L#31 (P#31) Core L#4 (P#32) L3Cache L#8 (size=4096KB linesize=128 ways=16) L2Cache L#8 (size=1024KB linesize=128 ways=8) L1dCache L#8 (size=32KB linesize=128 ways=8) L1iCache L#8 (size=48KB linesize=128 ways=6) PU L#32 (P#32) PU L#33 (P#34) PU L#34 (P#36) PU L#35 (P#38) L3Cache L#9 (size=4096KB linesize=128 ways=16) L2Cache L#9 (size=1024KB linesize=128 ways=8) L1dCache L#9 (size=32KB linesize=128 ways=8) L1iCache L#9 (size=48KB linesize=128 ways=6) PU L#36 (P#33) PU L#37 (P#35) PU L#38 (P#37) PU L#39 (P#39) Group0 L#1 (total=7736896KB) Package L#2 (total=5170880KB CPUModel="POWER10 (architected), altivec supported" CPURevision="2.0 (pvr 0080 0200)") NUMANode L#2 (P#2 local=5170880KB total=5170880KB) Die L#4 (P#4) <snipped> Reviewed-by: Shrikanth Hegde <sshegde@linux.ibm.com> Signed-off-by: Srikar Dronamraju <srikar@linux.ibm.com> Signed-off-by: Madhavan Srinivasan <maddy@linux.ibm.com> Link: https://patch.msgid.link/20251112074859.814087-1-srikar@linux.ibm.com
-rw-r--r--arch/powerpc/include/asm/topology.h11
-rw-r--r--arch/powerpc/kernel/smp.c23
2 files changed, 30 insertions, 4 deletions
diff --git a/arch/powerpc/include/asm/topology.h b/arch/powerpc/include/asm/topology.h
index f19ca44512d1..66ed5fe1b718 100644
--- a/arch/powerpc/include/asm/topology.h
+++ b/arch/powerpc/include/asm/topology.h
@@ -132,15 +132,18 @@ static inline int cpu_to_coregroup_id(int cpu)
#include <asm/cputable.h>
struct cpumask *cpu_coregroup_mask(int cpu);
+const struct cpumask *cpu_die_mask(int cpu);
+int cpu_die_id(int cpu);
#ifdef CONFIG_PPC64
#include <asm/smp.h>
#define topology_physical_package_id(cpu) (cpu_to_chip_id(cpu))
-
-#define topology_sibling_cpumask(cpu) (per_cpu(cpu_sibling_map, cpu))
-#define topology_core_cpumask(cpu) (per_cpu(cpu_core_map, cpu))
-#define topology_core_id(cpu) (cpu_to_core_id(cpu))
+#define topology_sibling_cpumask(cpu) (per_cpu(cpu_sibling_map, cpu))
+#define topology_core_cpumask(cpu) (per_cpu(cpu_core_map, cpu))
+#define topology_core_id(cpu) (cpu_to_core_id(cpu))
+#define topology_die_id(cpu) (cpu_die_id(cpu))
+#define topology_die_cpumask(cpu) (cpu_die_mask(cpu))
#endif
#endif
diff --git a/arch/powerpc/kernel/smp.c b/arch/powerpc/kernel/smp.c
index 68edb66c2964..292fee8809bc 100644
--- a/arch/powerpc/kernel/smp.c
+++ b/arch/powerpc/kernel/smp.c
@@ -1085,6 +1085,29 @@ static int __init init_big_cores(void)
return 0;
}
+/*
+ * die_mask and die_id are only available on systems which support
+ * multiple coregroups within a same package. On all other systems, die_mask
+ * would be same as package mask and die_id would be set to -1.
+ */
+const struct cpumask *cpu_die_mask(int cpu)
+{
+ if (has_coregroup_support())
+ return per_cpu(cpu_coregroup_map, cpu);
+ else
+ return cpu_node_mask(cpu);
+}
+EXPORT_SYMBOL_GPL(cpu_die_mask);
+
+int cpu_die_id(int cpu)
+{
+ if (has_coregroup_support())
+ return cpu_to_coregroup_id(cpu);
+ else
+ return -1;
+}
+EXPORT_SYMBOL_GPL(cpu_die_id);
+
void __init smp_prepare_cpus(unsigned int max_cpus)
{
unsigned int cpu, num_threads;