Revert "powerpc/irq: Don't open code irq_soft_mask helpers"

This reverts commit ef5b570d3700fbb8628a58da0487486ceeb713cd.

Zhouyi reported that commit is causing crashes when running rcutorture
with KASAN enabled:

BUG: using smp_processor_id() in preemptible [00000000] code: rcu_torture_rea/100
caller is rcu_preempt_deferred_qs_irqrestore+0x74/0xed0
CPU: 4 PID: 100 Comm: rcu_torture_rea Tainted: G W 5.19.0-rc5-next-20220708-dirty #253
Call Trace:
dump_stack_lvl+0xbc/0x108 (unreliable)
check_preemption_disabled+0x154/0x160
rcu_preempt_deferred_qs_irqrestore+0x74/0xed0
__rcu_read_unlock+0x290/0x3b0
rcu_torture_read_unlock+0x30/0xb0
rcutorture_one_extend+0x198/0x810
rcu_torture_one_read+0x58c/0xc90
rcu_torture_reader+0x12c/0x360
kthread+0x1e8/0x220
ret_from_kernel_thread+0x5c/0x64

KASAN will generate instrumentation instructions around the
WRITE_ONCE(local_paca->irq_soft_mask, mask):

0xc000000000295cb0 <+0>: addis r2,r12,774
0xc000000000295cb4 <+4>: addi r2,r2,16464
0xc000000000295cb8 <+8>: mflr r0
0xc000000000295cbc <+12>: bl 0xc00000000008bb4c <mcount>
0xc000000000295cc0 <+16>: mflr r0
0xc000000000295cc4 <+20>: std r31,-8(r1)
0xc000000000295cc8 <+24>: addi r3,r13,2354
0xc000000000295ccc <+28>: mr r31,r13
0xc000000000295cd0 <+32>: std r0,16(r1)
0xc000000000295cd4 <+36>: stdu r1,-48(r1)
0xc000000000295cd8 <+40>: bl 0xc000000000609b98 <__asan_store1+8>
0xc000000000295cdc <+44>: nop
0xc000000000295ce0 <+48>: li r9,1
0xc000000000295ce4 <+52>: stb r9,2354(r31)
0xc000000000295ce8 <+56>: addi r1,r1,48
0xc000000000295cec <+60>: ld r0,16(r1)
0xc000000000295cf0 <+64>: ld r31,-8(r1)
0xc000000000295cf4 <+68>: mtlr r0

If there is a context switch before "stb r9,2354(r31)", r31 may
not equal to r13, in such case, irq soft mask will not work.

The usual solution of marking the code ineligible for instrumentation
forces the code out-of-line, which we would prefer to avoid. Christophe
proposed a partial revert, but Nick raised some concerns with that. So
for now do a full revert.

Reported-by: Zhouyi Zhou <zhouzhouyi@gmail.com>
[mpe: Construct change log based on Zhouyi's original report]
Signed-off-by: Michael Ellerman <mpe@ellerman.id.au>
Link: https://lore.kernel.org/r/20220831131052.42250-1-mpe@ellerman.id.au

Changed files
+36 -7
arch
powerpc
include
asm
+36 -7
arch/powerpc/include/asm/hw_irq.h
··· 113 113 114 114 static inline notrace unsigned long irq_soft_mask_return(void) 115 115 { 116 - return READ_ONCE(local_paca->irq_soft_mask); 116 + unsigned long flags; 117 + 118 + asm volatile( 119 + "lbz %0,%1(13)" 120 + : "=r" (flags) 121 + : "i" (offsetof(struct paca_struct, irq_soft_mask))); 122 + 123 + return flags; 117 124 } 118 125 119 126 /* ··· 147 140 if (IS_ENABLED(CONFIG_PPC_IRQ_SOFT_MASK_DEBUG)) 148 141 WARN_ON(mask && !(mask & IRQS_DISABLED)); 149 142 150 - WRITE_ONCE(local_paca->irq_soft_mask, mask); 151 - barrier(); 143 + asm volatile( 144 + "stb %0,%1(13)" 145 + : 146 + : "r" (mask), 147 + "i" (offsetof(struct paca_struct, irq_soft_mask)) 148 + : "memory"); 152 149 } 153 150 154 151 static inline notrace unsigned long irq_soft_mask_set_return(unsigned long mask) 155 152 { 156 - unsigned long flags = irq_soft_mask_return(); 153 + unsigned long flags; 157 154 158 - irq_soft_mask_set(mask); 155 + #ifdef CONFIG_PPC_IRQ_SOFT_MASK_DEBUG 156 + WARN_ON(mask && !(mask & IRQS_DISABLED)); 157 + #endif 158 + 159 + asm volatile( 160 + "lbz %0,%1(13); stb %2,%1(13)" 161 + : "=&r" (flags) 162 + : "i" (offsetof(struct paca_struct, irq_soft_mask)), 163 + "r" (mask) 164 + : "memory"); 159 165 160 166 return flags; 161 167 } 162 168 163 169 static inline notrace unsigned long irq_soft_mask_or_return(unsigned long mask) 164 170 { 165 - unsigned long flags = irq_soft_mask_return(); 171 + unsigned long flags, tmp; 166 172 167 - irq_soft_mask_set(flags | mask); 173 + asm volatile( 174 + "lbz %0,%2(13); or %1,%0,%3; stb %1,%2(13)" 175 + : "=&r" (flags), "=r" (tmp) 176 + : "i" (offsetof(struct paca_struct, irq_soft_mask)), 177 + "r" (mask) 178 + : "memory"); 179 + 180 + #ifdef CONFIG_PPC_IRQ_SOFT_MASK_DEBUG 181 + WARN_ON((mask | flags) && !((mask | flags) & IRQS_DISABLED)); 182 + #endif 168 183 169 184 return flags; 170 185 }