ogl_beamforming

Ultrasound Beamforming Implemented with OpenGL
git clone anongit@rnpnr.xyz:ogl_beamforming.git
Log | Files | Refs | Feed | Submodules | README | LICENSE

Commit: ba86ef9b9376f4680770a8c180235265ec1ff959
Parent: 8408acf219120932b5db273588d2542b87954356
Author: Randy Palamar
Date:   Sun,  6 Apr 2025 17:53:22 -0600

core: use atomic_cas to ensure shared memory locks are transferred correctly

There was a moment of time between the load and inc that could
have caused a double increment on the lock giving an invalid state.

Diffstat:
Mbeamformer_work_queue.c | 3+--
Mintrinsics.c | 12+++++++-----
Mstatic.c | 4+---
3 files changed, 9 insertions(+), 10 deletions(-)

diff --git a/beamformer_work_queue.c b/beamformer_work_queue.c @@ -57,8 +57,7 @@ try_wait_sync(i32 *sync, i32 timeout_ms, os_wait_on_value_fn *os_wait_on_value) b32 result = 0; for (;;) { i32 current = atomic_load(sync); - if (current) { - atomic_inc(sync, -current); + if (current && atomic_cas(sync, &current, 0)) { result = 1; break; } else if (!timeout_ms) { diff --git a/intrinsics.c b/intrinsics.c @@ -4,11 +4,13 @@ #define sqrt_f32(a) __builtin_sqrtf(a) #define atan2_f32(y, x) __builtin_atan2f(y, x) -#define atomic_store(ptr, n) __atomic_store_n(ptr, n, __ATOMIC_RELEASE) -#define atomic_load(ptr) __atomic_load_n(ptr, __ATOMIC_ACQUIRE) -#define atomic_and(ptr, n) __atomic_and_fetch(ptr, n, __ATOMIC_RELEASE) -#define atomic_add(ptr, n) __atomic_add_fetch(ptr, n, __ATOMIC_RELEASE) -#define atomic_inc(ptr, n) __atomic_fetch_add(ptr, n, __ATOMIC_ACQ_REL) +#define atomic_store(ptr, n) __atomic_store_n(ptr, n, __ATOMIC_RELEASE) +#define atomic_load(ptr) __atomic_load_n(ptr, __ATOMIC_ACQUIRE) +#define atomic_swap(ptr, n) __atomic_exchange_n(ptr, n, __ATOMIC_RELEASE) +#define atomic_and(ptr, n) __atomic_and_fetch(ptr, n, __ATOMIC_RELEASE) +#define atomic_add(ptr, n) __atomic_add_fetch(ptr, n, __ATOMIC_RELEASE) +#define atomic_inc(ptr, n) __atomic_fetch_add(ptr, n, __ATOMIC_ACQ_REL) +#define atomic_cas(ptr, cptr, n) __atomic_compare_exchange_n(ptr, cptr, n, 0, __ATOMIC_SEQ_CST, __ATOMIC_SEQ_CST) static FORCE_INLINE u32 clz_u32(u32 a) diff --git a/static.c b/static.c @@ -256,10 +256,8 @@ static OS_THREAD_ENTRY_POINT_FN(compute_worker_thread_entry_point) for (;;) { for (;;) { i32 current = atomic_load(&ctx->sync_variable); - if (current) { - atomic_inc(&ctx->sync_variable, -current); + if (current && atomic_swap(&ctx->sync_variable, 0) == current) break; - } ctx->asleep = 1; os_wait_on_value(&ctx->sync_variable, current, -1);