Nikos Mavrogiannopoulos n.mavrogiannopoulos@gmail.com writes:
Is that really needed? I mean you are setting these values at the constructor, that is prior to any thread being created, and there shouldn't be multiple CPUs to worry about.
If the constructor thing works, it's no problem. And if ifunc is supported, I don't know how that really works, but I imagine the dynamic loader serializes calls to the resolver functions, and that whatever magic is used in the case of static libraries also is no problem.
So remains the case of no C extensions, where the initialization is hooked in via the initial values of all function pointers (the way it's done in GMP). Here, all bets on the timing of calls are off, the application can spawn multiple threads, and have the threads all call nettle for the first time.
So the problem is a bit obscure, but I think if we just replace initialized = 1 by _nettle_synchronous_write (&initialized, 1), implemented as
_nettle_synchronous_write: mfence movl %esi, (%rdi) mfence
it will be safe in all cases.
Regards, /Niels