arch_topology: Make register_cpu_capacity_sysctl() tolerant to late CPUs

JIRA: https://issues.redhat.com/browse/RHEL-112493

commit c72bbf200162a3b4b9e1baedec9008d8d710b427
Author: James Morse <james.morse@arm.com>
Date:   Tue Nov 21 13:43:54 2023 +0000

    arch_topology: Make register_cpu_capacity_sysctl() tolerant to late CPUs

    register_cpu_capacity_sysctl() adds a property to sysfs that describes
    the CPUs capacity. This is done from a subsys_initcall() that assumes
    all possible CPUs are registered.

    With CPU hotplug, possible CPUs aren't registered until they become
    present, (or for arm64 enabled). This leads to messages during boot:
    | register_cpu_capacity_sysctl: too early to get CPU1 device!
    and once these CPUs are added to the system, the file is missing.

    Move this to a cpuhp callback, so that the file is created once
    CPUs are brought online. This covers CPUs that are added late by
    mechanisms like hotplug.
    One observable difference is the file is now missing for offline CPUs.

    Signed-off-by: James Morse <james.morse@arm.com>
    Reviewed-by: Gavin Shan <gshan@redhat.com>
    Signed-off-by: "Russell King (Oracle)" <rmk+kernel@armlinux.org.uk>
    Reviewed-by: Jonathan Cameron <Jonathan.Cameron@huawei.com>
    Reviewed-by: Thomas Gleixner <tglx@linutronix.de>
    Link: https://lore.kernel.org/r/E1r5R2g-00CsyV-Ss@rmk-PC.armlinux.org.uk
    Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>

Signed-off-by: David Arcari <darcari@redhat.com>
This commit is contained in:
David Arcari 2025-09-04 10:19:53 -04:00
parent e1b5a25dcf
commit 6504a8361f
1 changed files with 26 additions and 12 deletions

View File

@ -219,20 +219,34 @@ static DECLARE_WORK(update_topology_flags_work, update_topology_flags_workfn);
static DEVICE_ATTR_RO(cpu_capacity);
static int cpu_capacity_sysctl_add(unsigned int cpu)
{
struct device *cpu_dev = get_cpu_device(cpu);
if (!cpu_dev)
return -ENOENT;
device_create_file(cpu_dev, &dev_attr_cpu_capacity);
return 0;
}
static int cpu_capacity_sysctl_remove(unsigned int cpu)
{
struct device *cpu_dev = get_cpu_device(cpu);
if (!cpu_dev)
return -ENOENT;
device_remove_file(cpu_dev, &dev_attr_cpu_capacity);
return 0;
}
static int register_cpu_capacity_sysctl(void)
{
int i;
struct device *cpu;
for_each_possible_cpu(i) {
cpu = get_cpu_device(i);
if (!cpu) {
pr_err("%s: too early to get CPU%d device!\n",
__func__, i);
continue;
}
device_create_file(cpu, &dev_attr_cpu_capacity);
}
cpuhp_setup_state(CPUHP_AP_ONLINE_DYN, "topology/cpu-capacity",
cpu_capacity_sysctl_add, cpu_capacity_sysctl_remove);
return 0;
}