Skip to content

Commit b99173e

Browse files
authored
Support threads in the new crt1-command.c ctor check. (#339)
Use an atomic compare-and-swap for checking whether constructors have been run, when threads are enabled.
1 parent a7af7c0 commit b99173e

1 file changed

Lines changed: 19 additions & 5 deletions

File tree

libc-bottom-half/crt/crt1-command.c

Lines changed: 19 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,33 @@
1+
#ifdef _REENTRANT
2+
#include <stdatomic.h>
3+
#endif
14
#include <wasi/api.h>
25
extern void __wasm_call_ctors(void);
36
extern int __main_void(void);
47
extern void __wasm_call_dtors(void);
58

6-
// Commands should only be called once per instance. This simple check ensures
7-
// that the `_start` function isn't started more than once.
8-
static volatile int started = 0;
9-
109
__attribute__((export_name("_start")))
1110
void _start(void) {
12-
// Don't allow the program to be called multiple times.
11+
// Commands should only be called once per instance. This simple check
12+
// ensures that the `_start` function isn't started more than once.
13+
//
14+
// We use `volatile` here to prevent the store to `started` from being
15+
// sunk past any subsequent code, and to prevent any compiler from
16+
// optimizing based on the knowledge that `_start` is the program
17+
// entrypoint.
18+
#ifdef _REENTRANT
19+
static volatile _Atomic int started = 0;
20+
int expected = 0;
21+
if (!atomic_compare_exchange_strong(&started, &expected, 1)) {
22+
__builtin_trap();
23+
}
24+
#else
25+
static volatile int started = 0;
1326
if (started != 0) {
1427
__builtin_trap();
1528
}
1629
started = 1;
30+
#endif
1731

1832
// The linker synthesizes this to call constructors.
1933
__wasm_call_ctors();

0 commit comments

Comments
 (0)