C11 atomic lock alignment in data_t#685
Conversation
| /* Locks */ | ||
|
|
||
| typedef volatile atomic_flag parsec_atomic_lock_t; | ||
| typedef union { |
There was a problem hiding this comment.
This is ugly. What if you remove the volatile completely ? Or move it outside the union as in
typedef volatile union parsec_atomic_lock_u {
atomic_flag flag;
int atomic_external_aligner;
} parsec_atomic_lock_t;There was a problem hiding this comment.
the volatile is not useful I removed it and it passes all tests
|
I'm really puzzled by this. That a compiler can decide to implement the atomic_flag_t as |
|
the next field in data_t is a uint8_t so it packs tightly with the bool, then the whole rest of the data_t structure is not aligned in memory in the same way when looked at from a file that includes atomic-external.h versus atomic-c11.h. That ends up causing crashes when we dereference fields in the data_t, and obtain garbage from fields with a differing |
|
According to the code in data_internal.h the next field in the |
|
Interesting / facetious :) We saw that behavior while debugging the PR #671 where indeed the IMHO, it is fragile to rely on the alignment of the next field in some structure to guarantee the types with atomic-external.h and without are compatible. I prefer the (admittedly not very aesthetic) solution of forcing the base type to be compatible with what we expose in atomic-external.h |
atomic_external.h, leading to misaligned static structures (like data_t) so, when C11 atomics are enabled, we force the size of atomic_lock_t to be at least one int long, regardless, to match the expected alignment.
90a03ce to
d567b31
Compare
c11 atomic_flag can be shorter (bool) than the volatile int type used in atomic_external.h, leading to misaligned static structures (like data_t) so, when C11 atomics are enabled, we force the size of atomic_lock_t to be at least one int long, regardless, to match the expected alignment.