From: Nicholas Piggin <npig...@gmail.com>

[ Upstream commit 064996d62a33ffe10264b5af5dca92d54f60f806 ]

The SMP hardlockup watchdog cross-checks other CPUs for lockups, which
causes xmon headaches because it's assuming interrupts hard disabled
means no watchdog troubles. Try to improve that by calling
touch_nmi_watchdog() in obvious places where secondaries are spinning.

Also annotate these spin loops with spin_begin/end calls.

Signed-off-by: Nicholas Piggin <npig...@gmail.com>
Signed-off-by: Michael Ellerman <m...@ellerman.id.au>
Signed-off-by: Sasha Levin <alexander.le...@verizon.com>
---
 arch/powerpc/xmon/xmon.c | 17 +++++++++++++----
 1 file changed, 13 insertions(+), 4 deletions(-)

diff --git a/arch/powerpc/xmon/xmon.c b/arch/powerpc/xmon/xmon.c
index 760545519a0b..05751c9e7f53 100644
--- a/arch/powerpc/xmon/xmon.c
+++ b/arch/powerpc/xmon/xmon.c
@@ -496,14 +496,19 @@ static int xmon_core(struct pt_regs *regs, int fromipi)
 
  waiting:
        secondary = 1;
+       spin_begin();
        while (secondary && !xmon_gate) {
                if (in_xmon == 0) {
-                       if (fromipi)
+                       if (fromipi) {
+                               spin_end();
                                goto leave;
+                       }
                        secondary = test_and_set_bit(0, &in_xmon);
                }
-               barrier();
+               spin_cpu_relax();
+               touch_nmi_watchdog();
        }
+       spin_end();
 
        if (!secondary && !xmon_gate) {
                /* we are the first cpu to come in */
@@ -530,21 +535,25 @@ static int xmon_core(struct pt_regs *regs, int fromipi)
                mb();
                xmon_gate = 1;
                barrier();
+               touch_nmi_watchdog();
        }
 
  cmdloop:
        while (in_xmon) {
                if (secondary) {
+                       spin_begin();
                        if (cpu == xmon_owner) {
                                if (!test_and_set_bit(0, &xmon_taken)) {
                                        secondary = 0;
+                                       spin_end();
                                        continue;
                                }
                                /* missed it */
                                while (cpu == xmon_owner)
-                                       barrier();
+                                       spin_cpu_relax();
                        }
-                       barrier();
+                       spin_cpu_relax();
+                       touch_nmi_watchdog();
                } else {
                        cmd = cmds(regs);
                        if (cmd != 0) {
-- 
2.11.0

Reply via email to