From: "Gautham R. Shenoy" <e...@linux.vnet.ibm.com> This patch adds two sysfs attributes named smallcore_thread_siblings and smallcore_thread_siblings_list to the "topology" attribute group for each CPU device.
The read-only attributes /sys/device/system/cpu/cpuN/topology/smallcore_thread_siblings and /sys/device/system/cpu/cpuN/topology/smallcore_thread_siblings_list will the online siblings of CPU N that share the L1 cache with it on big-core configurations in cpumask format and cpu-list format respectively. Signed-off-by: Gautham R. Shenoy <e...@linux.vnet.ibm.com> --- Documentation/ABI/testing/sysfs-devices-system-cpu | 14 ++++ arch/powerpc/kernel/sysfs.c | 88 ++++++++++++++++++++++ 2 files changed, 102 insertions(+) diff --git a/Documentation/ABI/testing/sysfs-devices-system-cpu b/Documentation/ABI/testing/sysfs-devices-system-cpu index 7331822..2a80dc2 100644 --- a/Documentation/ABI/testing/sysfs-devices-system-cpu +++ b/Documentation/ABI/testing/sysfs-devices-system-cpu @@ -511,3 +511,17 @@ Description: Control Symetric Multi Threading (SMT) If control status is "forceoff" or "notsupported" writes are rejected. + +What: /sys/devices/system/cpu/cpu#/topology/smallcore_thread_siblings + /sys/devices/system/cpu/cpu#/topology/smallcore_thread_siblings_list +Date: Sept 2018 +Contact: Linux for PowerPC mailing list <linuxppc-...@ozlabs.org> +Description: CPU topology files that describe the thread siblings of a + logical CPU that share the L1-cache with it on POWER9 + big-core configurations. + + smallcore_thread_siblings: internal kernel map of + cpu#'s hardware threads that share L1-cache with cpu#. + + smallcore_thread_siblings_list: human-readable list of + cpu#'s hardware threads that share L1-cache with cpu#. diff --git a/arch/powerpc/kernel/sysfs.c b/arch/powerpc/kernel/sysfs.c index 755dc98..f9c7d96 100644 --- a/arch/powerpc/kernel/sysfs.c +++ b/arch/powerpc/kernel/sysfs.c @@ -18,6 +18,7 @@ #include <asm/smp.h> #include <asm/pmc.h> #include <asm/firmware.h> +#include <asm/cputhreads.h> #include "cacheinfo.h" #include "setup.h" @@ -714,6 +715,62 @@ static void sysfs_create_dscr_default(void) #endif /* HAS_PPC_PMC_PA6T */ #endif /* HAS_PPC_PMC_CLASSIC */ +static ssize_t smallcore_thread_siblings_show(struct device *dev, + struct device_attribute *attr, + char *buf) +{ + int cpu = dev->id; + + return cpumap_print_to_pagebuf(false, buf, cpu_smallcore_mask(cpu)); +} +static DEVICE_ATTR_RO(smallcore_thread_siblings); + +static ssize_t smallcore_thread_siblings_list_show(struct device *dev, + struct device_attribute *attr, + char *buf) +{ + int cpu = dev->id; + + return cpumap_print_to_pagebuf(true, buf, cpu_smallcore_mask(cpu)); +} +static DEVICE_ATTR_RO(smallcore_thread_siblings_list); + +static struct attribute *smallcore_attrs[] = { + &dev_attr_smallcore_thread_siblings.attr, + &dev_attr_smallcore_thread_siblings_list.attr, + NULL +}; + +static const struct attribute_group smallcore_attr_group = { + .name = "topology", + .attrs = smallcore_attrs +}; + +static int smallcore_register_cpu_online(unsigned int cpu) +{ + int err; + struct device *cpu_dev = get_cpu_device(cpu); + + if (!has_big_cores) + return 0; + + err = sysfs_merge_group(&cpu_dev->kobj, &smallcore_attr_group); + + return err; +} + +static int smallcore_unregister_cpu_online(unsigned int cpu) +{ + struct device *cpu_dev = get_cpu_device(cpu); + + if (!has_big_cores) + return 0; + + sysfs_unmerge_group(&cpu_dev->kobj, &smallcore_attr_group); + + return 0; +} + static int register_cpu_online(unsigned int cpu) { struct cpu *c = &per_cpu(cpu_devices, cpu); @@ -1060,3 +1117,34 @@ static int __init topology_init(void) return 0; } subsys_initcall(topology_init); + +/* + * NOTE: The smallcore_register_cpu_online + * (resp. smallcore_unregister_cpu_online) callback will merge + * (resp. unmerge) a couple of additional attributes to the + * "topology" attribute group of a CPU device when the CPU comes + * online (resp. goes offline). + * + * Hence, the registration of these callbacks must happen after + * topology_sysfs_init() is called so that the topology + * attribute group is created before these additional attributes + * can be merged/unmerged. We cannot register these callbacks in + * topology_init() since this function is called before + * topology_sysfs_init(). Hence we define the following + * late_initcall for this purpose. + */ +static int __init smallcore_topology_init(void) +{ + int r; + + if (!has_big_cores) + return 0; + + r = cpuhp_setup_state(CPUHP_AP_ONLINE_DYN, + "powerpc/topology/smallcore:online", + smallcore_register_cpu_online, + smallcore_unregister_cpu_online); + WARN_ON(r < 0); + return 0; +} +late_initcall(smallcore_topology_init); -- 1.9.4