__sync_bool_compare_and_swap always returns zero

168 Views Asked by At

Am I misunderstanding the builtin CAS operators in gcc?

From the docs:

bool __sync_bool_compare_and_swap (type *ptr, type oldval type newval, ...)

type __sync_val_compare_and_swap (type *ptr, type oldval type newval, ...) These builtins perform an atomic compare and swap. That is, if the current value of *ptr is oldval, then write newval into *ptr.

The “bool” version returns true if the comparison is successful and newval was written. The “val” version returns the contents of *ptr before the operation.

But, yet, in my debugger:

atomic_cas (ax=0x5555555728b0 <__libc_csu_init>, checkval=0, newval=0) at atomic.c:18
18      int atomic_cas(int *ax, int checkval, int newval) {
(gdb) n
19         return __sync_bool_compare_and_swap(&ax, checkval, newval);
(gdb) p *ax
$1 = 0
(gdb) p checkval
$2 = 0
(gdb) p newval
$3 = 1
(gdb) p *ax == checkval
$4 = 1
(gdb) call atomic_cas(ax, checkval, newval)
$5 = 0

... and in fact:

(gdb) call atomic_cas(ax, 0, 1)
$6 = 0
(gdb) call atomic_cas(ax, 1, 0)
$7 = 0
(gdb) call atomic_cas(ax, 1, 1)
$8 = 0

What gives here? Is this a bug in gcc or am I doing something wrong?

(Notice: I'm aware the sync_* are deprecated, please don't tell me how I should move to the newer atomics. I'm also aware that it's silly for this function call to exist - it's just a test.)

0

There are 0 best solutions below