panic: use atomic_try_cmpxchg in panic() and nmi_panic()
Use atomic_try_cmpxchg instead of atomic_cmpxchg (*ptr, old, new) == old in panic() and nmi_panic(). x86 CMPXCHG instruction returns success in ZF flag, so this change saves a compare after cmpxchg (and related move instruction in front of cmpxchg). Also, rename cpu variable to this_cpu in nmi_panic() and try to unify logic flow between panic() and nmi_panic(). No functional change intended. [ubizjak@gmail.com: clean up if/else block] Link: https://lkml.kernel.org/r/20230906191200.68707-1-ubizjak@gmail.com Link: https://lkml.kernel.org/r/20230904152230.9227-1-ubizjak@gmail.com Signed-off-by: Uros Bizjak <ubizjak@gmail.com> Cc: Mark Rutland <mark.rutland@arm.com> Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
This commit is contained in:
parent
3983520491
commit
9734fe4dc2
|
@ -192,14 +192,15 @@ atomic_t panic_cpu = ATOMIC_INIT(PANIC_CPU_INVALID);
|
|||
*/
|
||||
void nmi_panic(struct pt_regs *regs, const char *msg)
|
||||
{
|
||||
int old_cpu, cpu;
|
||||
int old_cpu, this_cpu;
|
||||
|
||||
cpu = raw_smp_processor_id();
|
||||
old_cpu = atomic_cmpxchg(&panic_cpu, PANIC_CPU_INVALID, cpu);
|
||||
old_cpu = PANIC_CPU_INVALID;
|
||||
this_cpu = raw_smp_processor_id();
|
||||
|
||||
if (old_cpu == PANIC_CPU_INVALID)
|
||||
/* atomic_try_cmpxchg updates old_cpu on failure */
|
||||
if (atomic_try_cmpxchg(&panic_cpu, &old_cpu, this_cpu))
|
||||
panic("%s", msg);
|
||||
else if (old_cpu != cpu)
|
||||
else if (old_cpu != this_cpu)
|
||||
nmi_panic_self_stop(regs);
|
||||
}
|
||||
EXPORT_SYMBOL(nmi_panic);
|
||||
|
@ -311,15 +312,18 @@ void panic(const char *fmt, ...)
|
|||
* stop themself or will wait until they are stopped by the 1st CPU
|
||||
* with smp_send_stop().
|
||||
*
|
||||
* `old_cpu == PANIC_CPU_INVALID' means this is the 1st CPU which
|
||||
* comes here, so go ahead.
|
||||
* cmpxchg success means this is the 1st CPU which comes here,
|
||||
* so go ahead.
|
||||
* `old_cpu == this_cpu' means we came from nmi_panic() which sets
|
||||
* panic_cpu to this CPU. In this case, this is also the 1st CPU.
|
||||
*/
|
||||
old_cpu = PANIC_CPU_INVALID;
|
||||
this_cpu = raw_smp_processor_id();
|
||||
old_cpu = atomic_cmpxchg(&panic_cpu, PANIC_CPU_INVALID, this_cpu);
|
||||
|
||||
if (old_cpu != PANIC_CPU_INVALID && old_cpu != this_cpu)
|
||||
/* atomic_try_cmpxchg updates old_cpu on failure */
|
||||
if (atomic_try_cmpxchg(&panic_cpu, &old_cpu, this_cpu)) {
|
||||
/* go ahead */
|
||||
} else if (old_cpu != this_cpu)
|
||||
panic_smp_self_stop();
|
||||
|
||||
console_verbose();
|
||||
|
|
Loading…
Reference in New Issue