Skip to contentSkip to conversation

cpufreq: intel_pstate: Use raw_smp_processor_id() in hwp_get_cpu_scaling()

PATCH In review Xi Ruoyao 5 participants 6 messages Apr 12, 2025 – Apr 14, 2025

Subsystems (2)
lore
Share & tools
lore

Xi Ruoyao

author
#0 lore raw

PATCH 1/1 cpufreq: intel_pstate: Use raw_smp_processor_id() in hwp_get_cpu_scaling()

Use raw_smp_processor_id() instead of plain smp_processor_id() in hwp_get_cpu_scaling(), otherwise we get some errors on a Lenovo Thinkpad T14P Gen 2:

    BUG: using smp_processor_id() in preemptible [00000000] code: swapper/0/1
    caller is hwp_get_cpu_scaling+0x7f/0xc0
Fixes b52aaeeadfac ("cpufreq: intel_pstate: Avoid SMP calls to get cpu-type")
---
 drivers/cpufreq/intel_pstate.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/cpufreq/intel_pstate.c +1 -1
index 4aad79d26c64..bfc20b978240 100644
@@ -2209,7 +2209,7 @@ static int knl_get_turbo_pstate(int cpu)
 static int hwp_get_cpu_scaling(int cpu)
 {
 	if (hybrid_scaling_factor) {
-		struct cpuinfo_x86 *c = &cpu_data(smp_processor_id());
+		struct cpuinfo_x86 *c = &cpu_data(raw_smp_processor_id());
 		u8 cpu_type = c->topo.intel_type;
 
 		/*
Signature · 1 line
2.49.0
maintainer Acked-by on v1 1/1
#1 lore raw
Quoted 5 lines · Xi Ruoyao

Use raw_smp_processor_id() instead of plain smp_processor_id() in hwp_get_cpu_scaling(), otherwise we get some errors on a Lenovo Thinkpad
T14P Gen 2:

Quoted 7 lines
    BUG: using smp_processor_id() in preemptible [00000000] code:

swapper/0/1
    caller is hwp_get_cpu_scaling+0x7f/0xc0

Fixes b52aaeeadfac ("cpufreq: intel_pstate: Avoid SMP calls to get

cpu-type")

Quoted 20 lines

---
 drivers/cpufreq/intel_pstate.c | 2 +-

 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/cpufreq/intel_pstate.c +1 -1
index 4aad79d26c64..bfc20b978240 100644
@@ -2209,7 +2209,7 @@ static int knl_get_turbo_pstate(int cpu)
  static int hwp_get_cpu_scaling(int cpu)
  {
  	if (hybrid_scaling_factor) {
-		struct cpuinfo_x86 *c =
 &cpu_data(smp_processor_id());
+		struct cpuinfo_x86 *c =
 &cpu_data(raw_smp_processor_id());
  		u8 cpu_type = c->topo.intel_type;


  /*

#2 lore raw
Quoted 10 lines · CEST srinivas pandruvada
Quoted 9 lines · Xi Ruoyao

Use raw_smp_processor_id() instead of plain smp_processor_id() in hwp_get_cpu_scaling(), otherwise we get some errors on a Lenovo Thinkpad
T14P Gen 2:

    BUG: using smp_processor_id() in preemptible [00000000] code:
swapper/0/1
    caller is hwp_get_cpu_scaling+0x7f/0xc0
Quoted 5 lines
Quoted 3 lines
Fixes b52aaeeadfac ("cpufreq: intel_pstate: Avoid SMP calls to get

cpu-type")

It's still broken after this patch though because the function should use the cpu_data() of the target CPU and not of the CPU running the code.

The patch below should fix it.

===
From: Rafael J. Wysocki <[email protected]>
Subject: [PATCH v1] cpufreq: intel_pstate: Fix hwp_get_cpu_scaling()

Commit b52aaeeadfac ("cpufreq: intel_pstate: Avoid SMP calls to get cpu-type") introduced two issues into hwp_get_cpu_scaling(). First, it made that function use the CPU type of the CPU running the code even though the target CPU is passed as the argument to it and second, it used smp_processor_id() for that even though hwp_get_cpu_scaling() runs in preemptible context.

Fix both of these problems by simply passing "cpu" to cpu_data().

Fixes b52aaeeadfac ("cpufreq: intel_pstate: Avoid SMP calls to get cpu-type")
---
 drivers/cpufreq/intel_pstate.c |    2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/cpufreq/intel_pstate.c +1 -1
@@ -2336,7 +2336,7 @@
 static int hwp_get_cpu_scaling(int cpu)
 {
 	if (hybrid_scaling_factor) {
-		struct cpuinfo_x86 *c = &cpu_data(smp_processor_id());
+		struct cpuinfo_x86 *c = &cpu_data(cpu);
 		u8 cpu_type = c->topo.intel_type;
 
 		/*
#3 lore raw
Quoted 16 lines · Rafael J. Wysocki
Quoted 15 lines · CEST srinivas pandruvada
Quoted 13 lines · Xi Ruoyao

Use raw_smp_processor_id() instead of plain smp_processor_id() in hwp_get_cpu_scaling(), otherwise we get some errors on a Lenovo Thinkpad
T14P Gen 2:

    BUG: using smp_processor_id() in preemptible [00000000] code:

swapper/0/1
    caller is hwp_get_cpu_scaling+0x7f/0xc0

Fixes b52aaeeadfac ("cpufreq: intel_pstate: Avoid SMP calls to

get
cpu-type")

Quoted 5 lines
Quoted 1 line

It's still broken after this patch though because the function should use the cpu_data() of the target CPU and not of the CPU running the code.

That is correct. The below patch should work.

Thanks,
Srinivas

Quoted 43 lines

The patch below should fix it.

===
From: Rafael J. Wysocki <[email protected]>
Subject: [PATCH v1] cpufreq: intel_pstate: Fix hwp_get_cpu_scaling()

Commit b52aaeeadfac ("cpufreq: intel_pstate: Avoid SMP calls to get cpu-type") introduced two issues into hwp_get_cpu_scaling().  First, it made that function use the CPU type of the CPU running the code even though the target CPU is passed as the argument to it and second,
it used smp_processor_id() for that even though hwp_get_cpu_scaling() runs in preemptible context.

Fix both of these problems by simply passing "cpu" to cpu_data().

Fixes b52aaeeadfac ("cpufreq: intel_pstate: Avoid SMP calls to get

cpu-type")
Link:
https://lore.kernel.org/linux-pm/[email protected]/

---
 drivers/cpufreq/intel_pstate.c |    2 +-

 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/cpufreq/intel_pstate.c +1 -1
@@ -2336,7 +2336,7 @@
  static int hwp_get_cpu_scaling(int cpu)
  {
  	if (hybrid_scaling_factor) {
-		struct cpuinfo_x86 *c =
 &cpu_data(smp_processor_id());
+		struct cpuinfo_x86 *c = &cpu_data(cpu);
  		u8 cpu_type = c->topo.intel_type;


  /*

#4 lore raw
Quoted 18 lines · srinivas pandruvada
Quoted 16 lines · Rafael J. Wysocki
Quoted 15 lines · CEST srinivas pandruvada
Quoted 13 lines · Xi Ruoyao

Use raw_smp_processor_id() instead of plain smp_processor_id() in hwp_get_cpu_scaling(), otherwise we get some errors on a Lenovo Thinkpad
T14P Gen 2:

    BUG: using smp_processor_id() in preemptible [00000000] code:
swapper/0/1
    caller is hwp_get_cpu_scaling+0x7f/0xc0
Fixes b52aaeeadfac ("cpufreq: intel_pstate: Avoid SMP calls to

get
cpu-type")

Quoted 7 lines
Quoted 5 lines
Quoted 1 line

It's still broken after this patch though because the function should use the cpu_data() of the target CPU and not of the CPU running the code.

That is correct. The below patch should work.

OK, I'll add an ACK from you to it then if you don't mind.

Quoted 45 lines
Quoted 43 lines

The patch below should fix it.

===
From: Rafael J. Wysocki <[email protected]>
Subject: [PATCH v1] cpufreq: intel_pstate: Fix hwp_get_cpu_scaling()

Commit b52aaeeadfac ("cpufreq: intel_pstate: Avoid SMP calls to get cpu-type") introduced two issues into hwp_get_cpu_scaling(). First, it made that function use the CPU type of the CPU running the code even though the target CPU is passed as the argument to it and second,
it used smp_processor_id() for that even though hwp_get_cpu_scaling() runs in preemptible context.

Fix both of these problems by simply passing "cpu" to cpu_data().

Fixes b52aaeeadfac ("cpufreq: intel_pstate: Avoid SMP calls to get

cpu-type")
Link:
https://lore.kernel.org/linux-pm/[email protected]/

---
 drivers/cpufreq/intel_pstate.c |    2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/cpufreq/intel_pstate.c +1 -1
@@ -2336,7 +2336,7 @@
 static int hwp_get_cpu_scaling(int cpu)
 {
      if (hybrid_scaling_factor) {
-             struct cpuinfo_x86 *c =
 &cpu_data(smp_processor_id());
+             struct cpuinfo_x86 *c = &cpu_data(cpu);
              u8 cpu_type = c->topo.intel_type;
 
              /*
#5 lore raw
In reply to Rafael J. Wysocki
Quoted 11 lines · Rafael J. Wysocki
Quoted 10 lines · CEST srinivas pandruvada
Quoted 9 lines · Xi Ruoyao

Use raw_smp_processor_id() instead of plain smp_processor_id() in hwp_get_cpu_scaling(), otherwise we get some errors on a Lenovo Thinkpad
T14P Gen 2:

    BUG: using smp_processor_id() in preemptible [00000000] code:
swapper/0/1
    caller is hwp_get_cpu_scaling+0x7f/0xc0
Quoted 8 lines
Quoted 5 lines
Quoted 3 lines
Fixes b52aaeeadfac ("cpufreq: intel_pstate: Avoid SMP calls to get

cpu-type")

It's still broken after this patch though because the function should use the cpu_data() of the target CPU and not of the CPU running the code.

Sorry for missing that.

I noticed that find_hybrid_pmu_for_cpu() doesn't take the cpu argument. Does it suffer from the same problem?

init_hybrid_pmu(int cpu)

{
	struct cpu_hw_events *cpuc = &per_cpu(cpu_hw_events, cpu);
	struct x86_hybrid_pmu *pmu = find_hybrid_pmu_for_cpu();