From 13e28135d6fb4906af9cd1d54f22172ad5e4a0dd Mon Sep 17 00:00:00 2001 From: Max Filippov Date: Wed, 16 Oct 2019 00:49:54 -0700 Subject: xtensa: use "m" constraint instead of "a" in atomic.h assembly Use "m" constraint instead of "r" for the address, as "m" allows compiler to access adjacent locations using base + offset, while "r" requires updating the base register every time. Signed-off-by: Max Filippov --- arch/xtensa/include/asm/atomic.h | 52 +++++++++++++++++++++------------------- 1 file changed, 28 insertions(+), 24 deletions(-) (limited to 'arch/xtensa') diff --git a/arch/xtensa/include/asm/atomic.h b/arch/xtensa/include/asm/atomic.h index 6bc5309a2ce8..3e7c6134ed32 100644 --- a/arch/xtensa/include/asm/atomic.h +++ b/arch/xtensa/include/asm/atomic.h @@ -124,13 +124,14 @@ static inline void atomic_##op(int i, atomic_t * v) \ int result; \ \ __asm__ __volatile__( \ - "1: l32i %[tmp], %[addr], 0\n" \ + "1: l32i %[tmp], %[mem]\n" \ " wsr %[tmp], scompare1\n" \ " " #op " %[result], %[tmp], %[i]\n" \ - " s32c1i %[result], %[addr], 0\n" \ + " s32c1i %[result], %[mem]\n" \ " bne %[result], %[tmp], 1b\n" \ - : [result] "=&a" (result), [tmp] "=&a" (tmp) \ - : [i] "a" (i), [addr] "a" (v) \ + : [result] "=&a" (result), [tmp] "=&a" (tmp), \ + [mem] "+m" (*v) \ + : [i] "a" (i) \ : "memory" \ ); \ } \ @@ -142,14 +143,15 @@ static inline int atomic_##op##_return(int i, atomic_t * v) \ int result; \ \ __asm__ __volatile__( \ - "1: l32i %[tmp], %[addr], 0\n" \ + "1: l32i %[tmp], %[mem]\n" \ " wsr %[tmp], scompare1\n" \ " " #op " %[result], %[tmp], %[i]\n" \ - " s32c1i %[result], %[addr], 0\n" \ + " s32c1i %[result], %[mem]\n" \ " bne %[result], %[tmp], 1b\n" \ " " #op " %[result], %[result], %[i]\n" \ - : [result] "=&a" (result), [tmp] "=&a" (tmp) \ - : [i] "a" (i), [addr] "a" (v) \ + : [result] "=&a" (result), [tmp] "=&a" (tmp), \ + [mem] "+m" (*v) \ + : [i] "a" (i) \ : "memory" \ ); \ \ @@ -163,13 +165,14 @@ static inline int atomic_fetch_##op(int i, atomic_t * v) \ int result; \ \ __asm__ __volatile__( \ - "1: l32i %[tmp], %[addr], 0\n" \ + "1: l32i %[tmp], %[mem]\n" \ " wsr %[tmp], scompare1\n" \ " " #op " %[result], %[tmp], %[i]\n" \ - " s32c1i %[result], %[addr], 0\n" \ + " s32c1i %[result], %[mem]\n" \ " bne %[result], %[tmp], 1b\n" \ - : [result] "=&a" (result), [tmp] "=&a" (tmp) \ - : [i] "a" (i), [addr] "a" (v) \ + : [result] "=&a" (result), [tmp] "=&a" (tmp), \ + [mem] "+m" (*v) \ + : [i] "a" (i) \ : "memory" \ ); \ \ @@ -185,13 +188,13 @@ static inline void atomic_##op(int i, atomic_t * v) \ \ __asm__ __volatile__( \ " rsil a15, "__stringify(TOPLEVEL)"\n" \ - " l32i %[result], %[addr], 0\n" \ + " l32i %[result], %[mem]\n" \ " " #op " %[result], %[result], %[i]\n" \ - " s32i %[result], %[addr], 0\n" \ + " s32i %[result], %[mem]\n" \ " wsr a15, ps\n" \ " rsync\n" \ - : [result] "=&a" (vval) \ - : [i] "a" (i), [addr] "a" (v) \ + : [result] "=&a" (vval), [mem] "+m" (*v) \ + : [i] "a" (i) \ : "a15", "memory" \ ); \ } \ @@ -203,13 +206,13 @@ static inline int atomic_##op##_return(int i, atomic_t * v) \ \ __asm__ __volatile__( \ " rsil a15,"__stringify(TOPLEVEL)"\n" \ - " l32i %[result], %[addr], 0\n" \ + " l32i %[result], %[mem]\n" \ " " #op " %[result], %[result], %[i]\n" \ - " s32i %[result], %[addr], 0\n" \ + " s32i %[result], %[mem]\n" \ " wsr a15, ps\n" \ " rsync\n" \ - : [result] "=&a" (vval) \ - : [i] "a" (i), [addr] "a" (v) \ + : [result] "=&a" (vval), [mem] "+m" (*v) \ + : [i] "a" (i) \ : "a15", "memory" \ ); \ \ @@ -223,13 +226,14 @@ static inline int atomic_fetch_##op(int i, atomic_t * v) \ \ __asm__ __volatile__( \ " rsil a15,"__stringify(TOPLEVEL)"\n" \ - " l32i %[result], %[addr], 0\n" \ + " l32i %[result], %[mem]\n" \ " " #op " %[tmp], %[result], %[i]\n" \ - " s32i %[tmp], %[addr], 0\n" \ + " s32i %[tmp], %[mem]\n" \ " wsr a15, ps\n" \ " rsync\n" \ - : [result] "=&a" (vval), [tmp] "=&a" (tmp) \ - : [i] "a" (i), [addr] "a" (v) \ + : [result] "=&a" (vval), [tmp] "=&a" (tmp), \ + [mem] "+m" (*v) \ + : [i] "a" (i) \ : "a15", "memory" \ ); \ \ -- cgit v1.2.3