Commit d994f2c8 authored by Uros Bizjak's avatar Uros Bizjak Committed by Ingo Molnar

locking/arch: Wire up local_try_cmpxchg()

Implement target specific support for local_try_cmpxchg()
and local_cmpxchg() using typed C wrappers that call their
_local counterpart and provide additional checking of
their input arguments.
Signed-off-by: default avatarUros Bizjak <ubizjak@gmail.com>
Signed-off-by: default avatarPeter Zijlstra (Intel) <peterz@infradead.org>
Signed-off-by: default avatarIngo Molnar <mingo@kernel.org>
Link: https://lore.kernel.org/r/20230405141710.3551-4-ubizjak@gmail.com
Cc: Linus Torvalds <torvalds@linux-foundation.org>
parent 8fc4fdda
...@@ -52,8 +52,16 @@ static __inline__ long local_sub_return(long i, local_t * l) ...@@ -52,8 +52,16 @@ static __inline__ long local_sub_return(long i, local_t * l)
return result; return result;
} }
#define local_cmpxchg(l, o, n) \ static __inline__ long local_cmpxchg(local_t *l, long old, long new)
(cmpxchg_local(&((l)->a.counter), (o), (n))) {
return cmpxchg_local(&l->a.counter, old, new);
}
static __inline__ bool local_try_cmpxchg(local_t *l, long *old, long new)
{
return try_cmpxchg_local(&l->a.counter, (s64 *)old, new);
}
#define local_xchg(l, n) (xchg_local(&((l)->a.counter), (n))) #define local_xchg(l, n) (xchg_local(&((l)->a.counter), (n)))
/** /**
......
...@@ -56,8 +56,17 @@ static inline long local_sub_return(long i, local_t *l) ...@@ -56,8 +56,17 @@ static inline long local_sub_return(long i, local_t *l)
return result; return result;
} }
#define local_cmpxchg(l, o, n) \ static inline long local_cmpxchg(local_t *l, long old, long new)
((long)cmpxchg_local(&((l)->a.counter), (o), (n))) {
return cmpxchg_local(&l->a.counter, old, new);
}
static inline bool local_try_cmpxchg(local_t *l, long *old, long new)
{
typeof(l->a.counter) *__old = (typeof(l->a.counter) *) old;
return try_cmpxchg_local(&l->a.counter, __old, new);
}
#define local_xchg(l, n) (atomic_long_xchg((&(l)->a), (n))) #define local_xchg(l, n) (atomic_long_xchg((&(l)->a), (n)))
/** /**
......
...@@ -94,8 +94,17 @@ static __inline__ long local_sub_return(long i, local_t * l) ...@@ -94,8 +94,17 @@ static __inline__ long local_sub_return(long i, local_t * l)
return result; return result;
} }
#define local_cmpxchg(l, o, n) \ static __inline__ long local_cmpxchg(local_t *l, long old, long new)
((long)cmpxchg_local(&((l)->a.counter), (o), (n))) {
return cmpxchg_local(&l->a.counter, old, new);
}
static __inline__ bool local_try_cmpxchg(local_t *l, long *old, long new)
{
typeof(l->a.counter) *__old = (typeof(l->a.counter) *) old;
return try_cmpxchg_local(&l->a.counter, __old, new);
}
#define local_xchg(l, n) (atomic_long_xchg((&(l)->a), (n))) #define local_xchg(l, n) (atomic_long_xchg((&(l)->a), (n)))
/** /**
......
...@@ -90,6 +90,17 @@ static __inline__ long local_cmpxchg(local_t *l, long o, long n) ...@@ -90,6 +90,17 @@ static __inline__ long local_cmpxchg(local_t *l, long o, long n)
return t; return t;
} }
static __inline__ bool local_try_cmpxchg(local_t *l, long *po, long n)
{
long o = *po, r;
r = local_cmpxchg(l, o, n);
if (unlikely(r != o))
*po = r;
return likely(r == o);
}
static __inline__ long local_xchg(local_t *l, long n) static __inline__ long local_xchg(local_t *l, long n)
{ {
long t; long t;
......
...@@ -120,8 +120,17 @@ static inline long local_sub_return(long i, local_t *l) ...@@ -120,8 +120,17 @@ static inline long local_sub_return(long i, local_t *l)
#define local_inc_return(l) (local_add_return(1, l)) #define local_inc_return(l) (local_add_return(1, l))
#define local_dec_return(l) (local_sub_return(1, l)) #define local_dec_return(l) (local_sub_return(1, l))
#define local_cmpxchg(l, o, n) \ static inline long local_cmpxchg(local_t *l, long old, long new)
(cmpxchg_local(&((l)->a.counter), (o), (n))) {
return cmpxchg_local(&l->a.counter, old, new);
}
static inline bool local_try_cmpxchg(local_t *l, long *old, long new)
{
typeof(l->a.counter) *__old = (typeof(l->a.counter) *) old;
return try_cmpxchg_local(&l->a.counter, __old, new);
}
/* Always has a lock prefix */ /* Always has a lock prefix */
#define local_xchg(l, n) (xchg(&((l)->a.counter), (n))) #define local_xchg(l, n) (xchg(&((l)->a.counter), (n)))
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment