diff --git a/drivers/soc/qcom/hyp_core_ctl.c b/drivers/soc/qcom/hyp_core_ctl.c index c5a00da88e9a..2e490c09b561 100644 --- a/drivers/soc/qcom/hyp_core_ctl.c +++ b/drivers/soc/qcom/hyp_core_ctl.c @@ -109,7 +109,7 @@ static inline int pause_cpu(int cpu) cpumask_clear(&cpus_to_pause); cpumask_set_cpu(cpu, &cpus_to_pause); - ret = walt_pause_cpus(&cpus_to_pause); + ret = walt_pause_cpus(&cpus_to_pause, PAUSE_HYP); return ret; } @@ -122,7 +122,7 @@ static inline int resume_cpu(int cpu) cpumask_clear(&cpus_to_resume); cpumask_set_cpu(cpu, &cpus_to_resume); - ret = walt_resume_cpus(&cpus_to_resume); + ret = walt_resume_cpus(&cpus_to_resume, PAUSE_HYP); return ret; } diff --git a/drivers/thermal/qcom/thermal_pause.c b/drivers/thermal/qcom/thermal_pause.c index 0c926c220c94..5e367cb59cd4 100644 --- a/drivers/thermal/qcom/thermal_pause.c +++ b/drivers/thermal/qcom/thermal_pause.c @@ -102,7 +102,7 @@ static int thermal_pause_work(struct thermal_pause_cdev *thermal_pause_cdev) pr_debug("Pause:%*pbl\n", cpumask_pr_args(&thermal_pause_cdev->cpu_mask)); mutex_unlock(&cpus_pause_lock); - ret = walt_pause_cpus(&cpus_to_pause); + ret = walt_pause_cpus(&cpus_to_pause, PAUSE_THERMAL); mutex_lock(&cpus_pause_lock); if (ret == 0) { @@ -149,7 +149,7 @@ static int thermal_resume_work(struct thermal_pause_cdev *thermal_pause_cdev) pr_debug("Unpause:%*pbl\n", cpumask_pr_args(&cpus_to_unpause)); mutex_unlock(&cpus_pause_lock); - ret = walt_resume_cpus(&cpus_to_unpause); + ret = walt_resume_cpus(&cpus_to_unpause, PAUSE_THERMAL); mutex_lock(&cpus_pause_lock); if (ret == 0) { diff --git a/include/linux/sched/walt.h b/include/linux/sched/walt.h index 9bb6ceada1a7..34f771ace147 100644 --- a/include/linux/sched/walt.h +++ b/include/linux/sched/walt.h @@ -11,6 +11,12 @@ #include #include +enum pause_reason { + PAUSE_CORE_CTL = 0x01, + PAUSE_THERMAL = 0x02, + PAUSE_HYP = 0x04, +}; + #if IS_ENABLED(CONFIG_SCHED_WALT) #define MAX_CPUS_PER_CLUSTER 6 @@ -170,10 +176,11 @@ struct notifier_block; extern void core_ctl_notifier_register(struct notifier_block *n); extern void core_ctl_notifier_unregister(struct notifier_block *n); extern int core_ctl_set_boost(bool boost); -extern int walt_pause_cpus(struct cpumask *cpus); -extern int walt_resume_cpus(struct cpumask *cpus); -extern int walt_halt_cpus(struct cpumask *cpus); -extern int walt_start_cpus(struct cpumask *cpus); + +extern int walt_pause_cpus(struct cpumask *cpus, enum pause_reason reason); +extern int walt_resume_cpus(struct cpumask *cpus, enum pause_reason reason); +extern int walt_halt_cpus(struct cpumask *cpus, enum pause_reason reason); +extern int walt_start_cpus(struct cpumask *cpus, enum pause_reason reason); #else static inline int sched_lpm_disallowed_time(int cpu, u64 *timeout) { @@ -211,11 +218,11 @@ static inline void core_ctl_notifier_unregister(struct notifier_block *n) { } -inline int walt_pause_cpus(struct cpumask *cpus) +inline int walt_pause_cpus(struct cpumask *cpus, enum pause_reason reason) { return 0; } -inline int walt_resume_cpus(struct cpumask *cpus) +inline int walt_resume_cpus(struct cpumask *cpus, enum pause_reason reason) { return 0; } diff --git a/kernel/sched/walt/core_ctl.c b/kernel/sched/walt/core_ctl.c index 3bcb59d8f646..cdb123d90b8f 100644 --- a/kernel/sched/walt/core_ctl.c +++ b/kernel/sched/walt/core_ctl.c @@ -1163,7 +1163,7 @@ static void core_ctl_pause_cpus(struct cpumask *cpus_to_pause) cpumask_copy(&saved_cpus, cpus_to_pause); if (cpumask_any(cpus_to_pause) < nr_cpu_ids) { - if (walt_halt_cpus(cpus_to_pause) < 0) + if (walt_halt_cpus(cpus_to_pause, PAUSE_CORE_CTL) < 0) pr_debug("core_ctl pause operation failed cpus=%*pbl paused_by_us=%*pbl\n", cpumask_pr_args(cpus_to_pause), cpumask_pr_args(&cpus_paused_by_us)); @@ -1192,7 +1192,7 @@ static void core_ctl_resume_cpus(struct cpumask *cpus_to_unpause) cpumask_copy(&saved_cpus, cpus_to_unpause); if (cpumask_any(cpus_to_unpause) < nr_cpu_ids) { - if (walt_start_cpus(cpus_to_unpause) < 0) + if (walt_start_cpus(cpus_to_unpause, PAUSE_CORE_CTL) < 0) pr_debug("core_ctl resume operation failed cpus=%*pbl paused_by_us=%*pbl\n", cpumask_pr_args(cpus_to_unpause), cpumask_pr_args(&cpus_paused_by_us)); diff --git a/kernel/sched/walt/walt_halt.c b/kernel/sched/walt/walt_halt.c index 346180098231..f61528ef7cb2 100644 --- a/kernel/sched/walt/walt_halt.c +++ b/kernel/sched/walt/walt_halt.c @@ -20,7 +20,7 @@ static DEFINE_RAW_SPINLOCK(halt_lock); struct halt_cpu_state { u64 last_halt; - int ref_count; + u8 reason; }; static DEFINE_PER_CPU(struct halt_cpu_state, halt_state); @@ -333,20 +333,18 @@ static int start_cpus(struct cpumask *cpus) return 0; } -/* increment/decrement ref count for cpus in yield/halt mask */ -static void update_ref_counts(struct cpumask *cpus, bool halt) +/* update reason for cpus in yield/halt mask */ +static void update_reasons(struct cpumask *cpus, bool halt, enum pause_reason reason) { int cpu; struct halt_cpu_state *halt_cpu_state; for_each_cpu(cpu, cpus) { halt_cpu_state = per_cpu_ptr(&halt_state, cpu); - if (halt) { - halt_cpu_state->ref_count++; - } else { - WARN_ON_ONCE(halt_cpu_state->ref_count == 0); - halt_cpu_state->ref_count--; - } + if (halt) + halt_cpu_state->reason |= reason; + else + halt_cpu_state->reason &= ~reason; } } @@ -358,13 +356,13 @@ static void update_halt_cpus(struct cpumask *cpus) for_each_cpu(cpu, cpus) { halt_cpu_state = per_cpu_ptr(&halt_state, cpu); - if (halt_cpu_state->ref_count) + if (halt_cpu_state->reason) cpumask_clear_cpu(cpu, cpus); } } /* cpus will be modified */ -int walt_halt_cpus(struct cpumask *cpus) +int walt_halt_cpus(struct cpumask *cpus, enum pause_reason reason) { int ret = 0; cpumask_t requested_cpus; @@ -378,7 +376,7 @@ int walt_halt_cpus(struct cpumask *cpus) update_halt_cpus(cpus); if (cpumask_empty(cpus)) { - update_ref_counts(&requested_cpus, true); + update_reasons(&requested_cpus, true, reason); goto unlock; } @@ -388,21 +386,21 @@ int walt_halt_cpus(struct cpumask *cpus) pr_debug("halt_cpus failure ret=%d cpus=%*pbl\n", ret, cpumask_pr_args(&requested_cpus)); else - update_ref_counts(&requested_cpus, true); + update_reasons(&requested_cpus, true, reason); unlock: raw_spin_unlock_irqrestore(&halt_lock, flags); return ret; } -int walt_pause_cpus(struct cpumask *cpus) +int walt_pause_cpus(struct cpumask *cpus, enum pause_reason reason) { - return walt_halt_cpus(cpus); + return walt_halt_cpus(cpus, reason); } EXPORT_SYMBOL(walt_pause_cpus); /* cpus will be modified */ -int walt_start_cpus(struct cpumask *cpus) +int walt_start_cpus(struct cpumask *cpus, enum pause_reason reason) { int ret = 0; cpumask_t requested_cpus; @@ -410,9 +408,9 @@ int walt_start_cpus(struct cpumask *cpus) raw_spin_lock_irqsave(&halt_lock, flags); cpumask_copy(&requested_cpus, cpus); - update_ref_counts(&requested_cpus, false); + update_reasons(&requested_cpus, false, reason); - /* remove cpus that should still be halted, due to ref-counts */ + /* remove cpus that should still be halted */ update_halt_cpus(cpus); ret = start_cpus(cpus); @@ -421,7 +419,7 @@ int walt_start_cpus(struct cpumask *cpus) pr_debug("halt_cpus failure ret=%d cpus=%*pbl\n", ret, cpumask_pr_args(&requested_cpus)); /* restore/increment ref counts in case of error */ - update_ref_counts(&requested_cpus, true); + update_reasons(&requested_cpus, true, reason); } raw_spin_unlock_irqrestore(&halt_lock, flags); @@ -429,9 +427,9 @@ int walt_start_cpus(struct cpumask *cpus) return ret; } -int walt_resume_cpus(struct cpumask *cpus) +int walt_resume_cpus(struct cpumask *cpus, enum pause_reason reason) { - return walt_start_cpus(cpus); + return walt_start_cpus(cpus, reason); } EXPORT_SYMBOL(walt_resume_cpus);