diff --git a/src/arch/host/include/arch/atomic.h b/src/arch/host/include/arch/atomic.h index 40613c6a3..797ba5f5e 100644 --- a/src/arch/host/include/arch/atomic.h +++ b/src/arch/host/include/arch/atomic.h @@ -17,9 +17,44 @@ typedef struct { volatile int32_t value; } atomic_t; +#if defined __GNUC__ && !defined __XCC__ + static inline int32_t arch_atomic_read(const atomic_t *a) { - return (*(volatile int32_t *)&a->value); + return __atomic_load_n(&a->value, __ATOMIC_SEQ_CST); +} + +static inline void arch_atomic_set(atomic_t *a, int32_t value) +{ + __atomic_store_n(&a->value, value, __ATOMIC_SEQ_CST); +} + +static inline void arch_atomic_init(atomic_t *a, int32_t value) +{ + __atomic_store_n(&a->value, value, __ATOMIC_SEQ_CST); +} + +static inline int32_t arch_atomic_add(atomic_t *a, int32_t value) +{ + return __atomic_add_fetch(&a->value, value, __ATOMIC_SEQ_CST); +} + +static inline int32_t arch_atomic_sub(atomic_t *a, int32_t value) +{ + return __atomic_sub_fetch(&a->value, value, __ATOMIC_SEQ_CST); +} + +#elif defined __XCC__ + +/* fake locking: obviously this does nothing, and provides no real locking */ +#define lock() do {} while (0) +#define unlock() do {} while (0) + +/* Fake atomic functions for xt-run static single-thread testbench */ + +static inline int32_t arch_atomic_read(const atomic_t *a) +{ + return a->value; } static inline void arch_atomic_set(atomic_t *a, int32_t value) @@ -32,17 +67,34 @@ static inline void arch_atomic_init(atomic_t *a, int32_t value) arch_atomic_set(a, value); } -/* use gcc atomic built-ins for host library */ static inline int32_t arch_atomic_add(atomic_t *a, int32_t value) { - return __sync_fetch_and_add(&a->value, value); + int32_t tmp; + + lock(); + tmp = a->value; + a->value += value; + unlock(); + return tmp; } static inline int32_t arch_atomic_sub(atomic_t *a, int32_t value) { - return __sync_fetch_and_sub(&a->value, value); + int32_t tmp; + + lock(); + tmp = a->value; + a->value -= value; + unlock(); + return tmp; } +#else + +#error "Not gcc, not xt-xcc" + +#endif + #endif /* __ARCH_ATOMIC_H__ */ #else