GNU Linux-libre 4.19.264-gnu1
[releases.git] / arch / sh / include / asm / futex-llsc.h
1 /* SPDX-License-Identifier: GPL-2.0 */
2 #ifndef __ASM_SH_FUTEX_LLSC_H
3 #define __ASM_SH_FUTEX_LLSC_H
4
5 static inline int atomic_futex_op_cmpxchg_inatomic(u32 *uval,
6                                                    u32 __user *uaddr,
7                                                    u32 oldval, u32 newval)
8 {
9         int err = 0;
10         __asm__ __volatile__(
11                 "synco\n"
12                 "1:\n\t"
13                 "movli.l        @%2, r0\n\t"
14                 "mov    r0, %1\n\t"
15                 "cmp/eq %1, %4\n\t"
16                 "bf     2f\n\t"
17                 "mov    %5, r0\n\t"
18                 "movco.l        r0, @%2\n\t"
19                 "bf     1b\n"
20                 "2:\n\t"
21                 "synco\n\t"
22 #ifdef CONFIG_MMU
23                 ".section       .fixup,\"ax\"\n"
24                 "3:\n\t"
25                 "mov.l  4f, %0\n\t"
26                 "jmp    @%0\n\t"
27                 " mov   %3, %0\n\t"
28                 ".balign        4\n"
29                 "4:     .long   2b\n\t"
30                 ".previous\n"
31                 ".section       __ex_table,\"a\"\n\t"
32                 ".long  1b, 3b\n\t"
33                 ".previous"
34 #endif
35                 :"+r" (err), "=&r" (*uval)
36                 :"r" (uaddr), "i" (-EFAULT), "r" (oldval), "r" (newval)
37                 :"t", "memory", "r0");
38         if (err) return err;
39         return 0;
40 }
41
42 #endif /* __ASM_SH_FUTEX_LLSC_H */