2012-12-24 15:36:14 +04:00
|
|
|
#ifndef __CR_ATOMIC_H__
|
|
|
|
#define __CR_ATOMIC_H__
|
2011-11-18 16:09:01 +04:00
|
|
|
|
2011-12-26 20:33:09 +04:00
|
|
|
#include "types.h"
|
|
|
|
|
2012-09-11 17:55:15 +04:00
|
|
|
typedef struct {
|
|
|
|
u32 counter;
|
|
|
|
} atomic_t;
|
|
|
|
|
2011-11-18 16:09:01 +04:00
|
|
|
#define atomic_set(mem, v) \
|
|
|
|
({ \
|
2012-09-11 17:55:15 +04:00
|
|
|
u32 ret__ = v; \
|
2011-11-18 16:09:01 +04:00
|
|
|
asm volatile ("lock xchg %0, %1\n" \
|
2012-09-11 17:55:15 +04:00
|
|
|
: "+r" (ret__), "+m" ((mem)->counter) \
|
2011-11-18 16:09:01 +04:00
|
|
|
: \
|
|
|
|
: "cc", "memory"); \
|
|
|
|
})
|
|
|
|
|
|
|
|
#define atomic_get(mem) \
|
|
|
|
({ \
|
|
|
|
u32 ret__ = 0; \
|
|
|
|
asm volatile ("lock xadd %0, %1\n" \
|
2012-09-11 17:55:15 +04:00
|
|
|
: "+r" (ret__), "+m" ((mem)->counter) \
|
2011-11-18 16:09:01 +04:00
|
|
|
: \
|
|
|
|
: "cc", "memory"); \
|
|
|
|
ret__; \
|
|
|
|
})
|
|
|
|
|
|
|
|
#define atomic_inc(mem) \
|
|
|
|
({ \
|
|
|
|
u32 ret__ = 1; \
|
|
|
|
asm volatile ("lock xadd %0, %1\n" \
|
2012-09-11 17:55:15 +04:00
|
|
|
: "+r" (ret__), "+m" ((mem)->counter) \
|
2011-11-18 16:09:01 +04:00
|
|
|
: \
|
|
|
|
: "cc", "memory"); \
|
|
|
|
ret__; \
|
|
|
|
})
|
|
|
|
|
|
|
|
#define atomic_dec(mem) \
|
|
|
|
({ \
|
|
|
|
u32 ret__ = -1; \
|
|
|
|
asm volatile ("lock xadd %0, %1\n" \
|
2012-09-11 17:55:15 +04:00
|
|
|
: "+r" (ret__), "+m" ((mem)->counter) \
|
2011-11-18 16:09:01 +04:00
|
|
|
: \
|
|
|
|
: "cc", "memory"); \
|
|
|
|
ret__; \
|
|
|
|
})
|
|
|
|
|
2012-09-11 17:55:23 +04:00
|
|
|
/* true if the result is 0, or false for all other cases. */
|
|
|
|
#define atomic_dec_and_test(mem) \
|
|
|
|
({ \
|
|
|
|
unsigned char ret__; \
|
|
|
|
asm volatile ("lock decl %0; sete %1\n" \
|
|
|
|
: "+m" ((mem)->counter), "=qm" (ret__) \
|
|
|
|
: \
|
|
|
|
: "cc", "memory"); \
|
|
|
|
ret__ != 0; \
|
|
|
|
})
|
|
|
|
|
2011-11-18 16:09:01 +04:00
|
|
|
#endif /* ATOMIC_H__ */
|