22
22
using namespace __rtsan ;
23
23
using namespace __sanitizer ;
24
24
25
+ namespace {
26
+ enum class InitializationState : u8 {
27
+ Uninitialized,
28
+ Initializing,
29
+ Initialized,
30
+ };
31
+ } // namespace
32
+
25
33
static StaticSpinMutex rtsan_inited_mutex;
26
34
static atomic_uint8_t rtsan_initialized = {0 };
27
35
28
- static void SetInitialized () {
29
- atomic_store (&rtsan_initialized, 1 , memory_order_release);
36
+ static void SetInitializationState (InitializationState state) {
37
+ atomic_store (&rtsan_initialized, static_cast <u8 >(state),
38
+ memory_order_release);
39
+ }
40
+
41
+ static InitializationState GetInitializationState () {
42
+ return static_cast <InitializationState>(
43
+ atomic_load (&rtsan_initialized, memory_order_acquire));
30
44
}
31
45
32
46
static auto PrintDiagnosticsAndDieAction (DiagnosticsInfo info) {
@@ -39,13 +53,14 @@ static auto PrintDiagnosticsAndDieAction(DiagnosticsInfo info) {
39
53
extern " C" {
40
54
41
55
SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_init () {
42
- CHECK (!__rtsan_is_initialized ());
56
+ CHECK (GetInitializationState () == InitializationState::Uninitialized);
57
+ SetInitializationState (InitializationState::Initializing);
43
58
44
59
SanitizerToolName = " RealtimeSanitizer" ;
45
60
InitializeFlags ();
46
61
InitializeInterceptors ();
47
62
48
- SetInitialized ( );
63
+ SetInitializationState (InitializationState::Initialized );
49
64
}
50
65
51
66
SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_ensure_initialized () {
@@ -62,7 +77,7 @@ SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_ensure_initialized() {
62
77
}
63
78
64
79
SANITIZER_INTERFACE_ATTRIBUTE bool __rtsan_is_initialized () {
65
- return atomic_load (&rtsan_initialized, memory_order_acquire ) == 1 ;
80
+ return GetInitializationState ( ) == InitializationState::Initialized ;
66
81
}
67
82
68
83
SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_realtime_enter () {
@@ -83,6 +98,10 @@ SANITIZER_INTERFACE_ATTRIBUTE void __rtsan_enable() {
83
98
84
99
SANITIZER_INTERFACE_ATTRIBUTE void
85
100
__rtsan_notify_intercepted_call (const char *func_name) {
101
+ // While initializing, we need all intercepted functions to behave normally
102
+ if (GetInitializationState () == InitializationState::Initializing)
103
+ return ;
104
+
86
105
__rtsan_ensure_initialized ();
87
106
GET_CALLER_PC_BP;
88
107
ExpectNotRealtime (
0 commit comments