Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
torvalds
GitHub Repository: torvalds/linux
Path: blob/master/arch/microblaze/include/asm/futex.h
26442 views
1
/* SPDX-License-Identifier: GPL-2.0 */
2
#ifndef _ASM_MICROBLAZE_FUTEX_H
3
#define _ASM_MICROBLAZE_FUTEX_H
4
5
#ifdef __KERNEL__
6
7
#include <linux/futex.h>
8
#include <linux/uaccess.h>
9
#include <asm/errno.h>
10
11
#define __futex_atomic_op(insn, ret, oldval, uaddr, oparg) \
12
({ \
13
__asm__ __volatile__ ( \
14
"1: lwx %0, %2, r0; " \
15
insn \
16
"2: swx %1, %2, r0; \
17
addic %1, r0, 0; \
18
bnei %1, 1b; \
19
3: \
20
.section .fixup,\"ax\"; \
21
4: brid 3b; \
22
addik %1, r0, %3; \
23
.previous; \
24
.section __ex_table,\"a\"; \
25
.word 1b,4b,2b,4b; \
26
.previous;" \
27
: "=&r" (oldval), "=&r" (ret) \
28
: "r" (uaddr), "i" (-EFAULT), "r" (oparg) \
29
); \
30
})
31
32
static inline int
33
arch_futex_atomic_op_inuser(int op, int oparg, int *oval, u32 __user *uaddr)
34
{
35
int oldval = 0, ret;
36
37
if (!access_ok(uaddr, sizeof(u32)))
38
return -EFAULT;
39
40
switch (op) {
41
case FUTEX_OP_SET:
42
__futex_atomic_op("or %1,%4,%4;", ret, oldval, uaddr, oparg);
43
break;
44
case FUTEX_OP_ADD:
45
__futex_atomic_op("add %1,%0,%4;", ret, oldval, uaddr, oparg);
46
break;
47
case FUTEX_OP_OR:
48
__futex_atomic_op("or %1,%0,%4;", ret, oldval, uaddr, oparg);
49
break;
50
case FUTEX_OP_ANDN:
51
__futex_atomic_op("andn %1,%0,%4;", ret, oldval, uaddr, oparg);
52
break;
53
case FUTEX_OP_XOR:
54
__futex_atomic_op("xor %1,%0,%4;", ret, oldval, uaddr, oparg);
55
break;
56
default:
57
ret = -ENOSYS;
58
}
59
60
if (!ret)
61
*oval = oldval;
62
63
return ret;
64
}
65
66
static inline int
67
futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr,
68
u32 oldval, u32 newval)
69
{
70
int ret = 0, cmp;
71
u32 prev;
72
73
if (!access_ok(uaddr, sizeof(u32)))
74
return -EFAULT;
75
76
__asm__ __volatile__ ("1: lwx %1, %3, r0; \
77
cmp %2, %1, %4; \
78
bnei %2, 3f; \
79
2: swx %5, %3, r0; \
80
addic %2, r0, 0; \
81
bnei %2, 1b; \
82
3: \
83
.section .fixup,\"ax\"; \
84
4: brid 3b; \
85
addik %0, r0, %6; \
86
.previous; \
87
.section __ex_table,\"a\"; \
88
.word 1b,4b,2b,4b; \
89
.previous;" \
90
: "+r" (ret), "=&r" (prev), "=&r"(cmp) \
91
: "r" (uaddr), "r" (oldval), "r" (newval), "i" (-EFAULT));
92
93
*uval = prev;
94
return ret;
95
}
96
97
#endif /* __KERNEL__ */
98
99
#endif
100
101