xref: /aosp_15_r20/external/compiler-rt/lib/msan/msan.h (revision 7c3d14c8b49c529e04be81a3ce6f5cc23712e4c6)
1*7c3d14c8STreehugger Robot //===-- msan.h --------------------------------------------------*- C++ -*-===//
2*7c3d14c8STreehugger Robot //
3*7c3d14c8STreehugger Robot //                     The LLVM Compiler Infrastructure
4*7c3d14c8STreehugger Robot //
5*7c3d14c8STreehugger Robot // This file is distributed under the University of Illinois Open Source
6*7c3d14c8STreehugger Robot // License. See LICENSE.TXT for details.
7*7c3d14c8STreehugger Robot //
8*7c3d14c8STreehugger Robot //===----------------------------------------------------------------------===//
9*7c3d14c8STreehugger Robot //
10*7c3d14c8STreehugger Robot // This file is a part of MemorySanitizer.
11*7c3d14c8STreehugger Robot //
12*7c3d14c8STreehugger Robot // Private MSan header.
13*7c3d14c8STreehugger Robot //===----------------------------------------------------------------------===//
14*7c3d14c8STreehugger Robot 
15*7c3d14c8STreehugger Robot #ifndef MSAN_H
16*7c3d14c8STreehugger Robot #define MSAN_H
17*7c3d14c8STreehugger Robot 
18*7c3d14c8STreehugger Robot #include "sanitizer_common/sanitizer_flags.h"
19*7c3d14c8STreehugger Robot #include "sanitizer_common/sanitizer_internal_defs.h"
20*7c3d14c8STreehugger Robot #include "sanitizer_common/sanitizer_stacktrace.h"
21*7c3d14c8STreehugger Robot #include "msan_interface_internal.h"
22*7c3d14c8STreehugger Robot #include "msan_flags.h"
23*7c3d14c8STreehugger Robot #include "ubsan/ubsan_platform.h"
24*7c3d14c8STreehugger Robot 
25*7c3d14c8STreehugger Robot #ifndef MSAN_REPLACE_OPERATORS_NEW_AND_DELETE
26*7c3d14c8STreehugger Robot # define MSAN_REPLACE_OPERATORS_NEW_AND_DELETE 1
27*7c3d14c8STreehugger Robot #endif
28*7c3d14c8STreehugger Robot 
29*7c3d14c8STreehugger Robot #ifndef MSAN_CONTAINS_UBSAN
30*7c3d14c8STreehugger Robot # define MSAN_CONTAINS_UBSAN CAN_SANITIZE_UB
31*7c3d14c8STreehugger Robot #endif
32*7c3d14c8STreehugger Robot 
33*7c3d14c8STreehugger Robot struct MappingDesc {
34*7c3d14c8STreehugger Robot   uptr start;
35*7c3d14c8STreehugger Robot   uptr end;
36*7c3d14c8STreehugger Robot   enum Type {
37*7c3d14c8STreehugger Robot     INVALID, APP, SHADOW, ORIGIN
38*7c3d14c8STreehugger Robot   } type;
39*7c3d14c8STreehugger Robot   const char *name;
40*7c3d14c8STreehugger Robot };
41*7c3d14c8STreehugger Robot 
42*7c3d14c8STreehugger Robot 
43*7c3d14c8STreehugger Robot #if SANITIZER_LINUX && defined(__mips64)
44*7c3d14c8STreehugger Robot 
45*7c3d14c8STreehugger Robot // Everything is above 0x00e000000000.
46*7c3d14c8STreehugger Robot const MappingDesc kMemoryLayout[] = {
47*7c3d14c8STreehugger Robot     {0x000000000000ULL, 0x00a000000000ULL, MappingDesc::INVALID, "invalid"},
48*7c3d14c8STreehugger Robot     {0x00a000000000ULL, 0x00c000000000ULL, MappingDesc::SHADOW, "shadow"},
49*7c3d14c8STreehugger Robot     {0x00c000000000ULL, 0x00e000000000ULL, MappingDesc::ORIGIN, "origin"},
50*7c3d14c8STreehugger Robot     {0x00e000000000ULL, 0x010000000000ULL, MappingDesc::APP, "app"}};
51*7c3d14c8STreehugger Robot 
52*7c3d14c8STreehugger Robot #define MEM_TO_SHADOW(mem) (((uptr)(mem)) & ~0x4000000000ULL)
53*7c3d14c8STreehugger Robot #define SHADOW_TO_ORIGIN(shadow) (((uptr)(shadow)) + 0x002000000000)
54*7c3d14c8STreehugger Robot 
55*7c3d14c8STreehugger Robot #elif SANITIZER_LINUX && defined(__aarch64__)
56*7c3d14c8STreehugger Robot 
57*7c3d14c8STreehugger Robot // The mapping describes both 39-bits and 42-bits.  AArch64 maps:
58*7c3d14c8STreehugger Robot // - 0x00000000000-0x00010000000: 39/42-bits program own segments
59*7c3d14c8STreehugger Robot // - 0x05500000000-0x05600000000: 39-bits PIE program segments
60*7c3d14c8STreehugger Robot // - 0x07f80000000-0x07fffffffff: 39-bits libraries segments
61*7c3d14c8STreehugger Robot // - 0x2aa00000000-0x2ab00000000: 42-bits PIE program segments
62*7c3d14c8STreehugger Robot // - 0x3ff00000000-0x3ffffffffff: 42-bits libraries segments
63*7c3d14c8STreehugger Robot // It is fragmented in multiples segments to increase the memory available
64*7c3d14c8STreehugger Robot // on 42-bits (12.21% of total VMA available for 42-bits and 13.28 for
65*7c3d14c8STreehugger Robot // 39 bits).
66*7c3d14c8STreehugger Robot const MappingDesc kMemoryLayout[] = {
67*7c3d14c8STreehugger Robot     {0x00000000000ULL, 0x01000000000ULL, MappingDesc::INVALID, "invalid"},
68*7c3d14c8STreehugger Robot     {0x01000000000ULL, 0x02000000000ULL, MappingDesc::SHADOW, "shadow-2"},
69*7c3d14c8STreehugger Robot     {0x02000000000ULL, 0x03000000000ULL, MappingDesc::ORIGIN, "origin-2"},
70*7c3d14c8STreehugger Robot     {0x03000000000ULL, 0x04000000000ULL, MappingDesc::SHADOW, "shadow-1"},
71*7c3d14c8STreehugger Robot     {0x04000000000ULL, 0x05000000000ULL, MappingDesc::ORIGIN, "origin-1"},
72*7c3d14c8STreehugger Robot     {0x05000000000ULL, 0x06000000000ULL, MappingDesc::APP, "app-1"},
73*7c3d14c8STreehugger Robot     {0x06000000000ULL, 0x07000000000ULL, MappingDesc::INVALID, "invalid"},
74*7c3d14c8STreehugger Robot     {0x07000000000ULL, 0x08000000000ULL, MappingDesc::APP, "app-2"},
75*7c3d14c8STreehugger Robot     {0x08000000000ULL, 0x09000000000ULL, MappingDesc::INVALID, "invalid"},
76*7c3d14c8STreehugger Robot     // The mappings below are used only for 42-bits VMA.
77*7c3d14c8STreehugger Robot     {0x09000000000ULL, 0x0A000000000ULL, MappingDesc::SHADOW, "shadow-3"},
78*7c3d14c8STreehugger Robot     {0x0A000000000ULL, 0x0B000000000ULL, MappingDesc::ORIGIN, "origin-3"},
79*7c3d14c8STreehugger Robot     {0x0B000000000ULL, 0x0F000000000ULL, MappingDesc::INVALID, "invalid"},
80*7c3d14c8STreehugger Robot     {0x0F000000000ULL, 0x10000000000ULL, MappingDesc::APP, "app-3"},
81*7c3d14c8STreehugger Robot     {0x10000000000ULL, 0x11000000000ULL, MappingDesc::INVALID, "invalid"},
82*7c3d14c8STreehugger Robot     {0x11000000000ULL, 0x12000000000ULL, MappingDesc::APP, "app-4"},
83*7c3d14c8STreehugger Robot     {0x12000000000ULL, 0x17000000000ULL, MappingDesc::INVALID, "invalid"},
84*7c3d14c8STreehugger Robot     {0x17000000000ULL, 0x18000000000ULL, MappingDesc::SHADOW, "shadow-4"},
85*7c3d14c8STreehugger Robot     {0x18000000000ULL, 0x19000000000ULL, MappingDesc::ORIGIN, "origin-4"},
86*7c3d14c8STreehugger Robot     {0x19000000000ULL, 0x20000000000ULL, MappingDesc::INVALID, "invalid"},
87*7c3d14c8STreehugger Robot     {0x20000000000ULL, 0x21000000000ULL, MappingDesc::APP, "app-5"},
88*7c3d14c8STreehugger Robot     {0x21000000000ULL, 0x26000000000ULL, MappingDesc::INVALID, "invalid"},
89*7c3d14c8STreehugger Robot     {0x26000000000ULL, 0x27000000000ULL, MappingDesc::SHADOW, "shadow-5"},
90*7c3d14c8STreehugger Robot     {0x27000000000ULL, 0x28000000000ULL, MappingDesc::ORIGIN, "origin-5"},
91*7c3d14c8STreehugger Robot     {0x28000000000ULL, 0x29000000000ULL, MappingDesc::SHADOW, "shadow-7"},
92*7c3d14c8STreehugger Robot     {0x29000000000ULL, 0x2A000000000ULL, MappingDesc::ORIGIN, "origin-7"},
93*7c3d14c8STreehugger Robot     {0x2A000000000ULL, 0x2B000000000ULL, MappingDesc::APP, "app-6"},
94*7c3d14c8STreehugger Robot     {0x2B000000000ULL, 0x2C000000000ULL, MappingDesc::INVALID, "invalid"},
95*7c3d14c8STreehugger Robot     {0x2C000000000ULL, 0x2D000000000ULL, MappingDesc::SHADOW, "shadow-6"},
96*7c3d14c8STreehugger Robot     {0x2D000000000ULL, 0x2E000000000ULL, MappingDesc::ORIGIN, "origin-6"},
97*7c3d14c8STreehugger Robot     {0x2E000000000ULL, 0x2F000000000ULL, MappingDesc::APP, "app-7"},
98*7c3d14c8STreehugger Robot     {0x2F000000000ULL, 0x39000000000ULL, MappingDesc::INVALID, "invalid"},
99*7c3d14c8STreehugger Robot     {0x39000000000ULL, 0x3A000000000ULL, MappingDesc::SHADOW, "shadow-9"},
100*7c3d14c8STreehugger Robot     {0x3A000000000ULL, 0x3B000000000ULL, MappingDesc::ORIGIN, "origin-9"},
101*7c3d14c8STreehugger Robot     {0x3B000000000ULL, 0x3C000000000ULL, MappingDesc::APP, "app-8"},
102*7c3d14c8STreehugger Robot     {0x3C000000000ULL, 0x3D000000000ULL, MappingDesc::INVALID, "invalid"},
103*7c3d14c8STreehugger Robot     {0x3D000000000ULL, 0x3E000000000ULL, MappingDesc::SHADOW, "shadow-8"},
104*7c3d14c8STreehugger Robot     {0x3E000000000ULL, 0x3F000000000ULL, MappingDesc::ORIGIN, "origin-8"},
105*7c3d14c8STreehugger Robot     {0x3F000000000ULL, 0x40000000000ULL, MappingDesc::APP, "app-9"},
106*7c3d14c8STreehugger Robot };
107*7c3d14c8STreehugger Robot # define MEM_TO_SHADOW(mem) ((uptr)mem ^ 0x6000000000ULL)
108*7c3d14c8STreehugger Robot # define SHADOW_TO_ORIGIN(shadow) (((uptr)(shadow)) + 0x1000000000ULL)
109*7c3d14c8STreehugger Robot 
110*7c3d14c8STreehugger Robot #elif SANITIZER_LINUX && SANITIZER_PPC64
111*7c3d14c8STreehugger Robot 
112*7c3d14c8STreehugger Robot const MappingDesc kMemoryLayout[] = {
113*7c3d14c8STreehugger Robot     {0x000000000000ULL, 0x000100000000ULL, MappingDesc::APP, "low memory"},
114*7c3d14c8STreehugger Robot     {0x000100000000ULL, 0x080000000000ULL, MappingDesc::INVALID, "invalid"},
115*7c3d14c8STreehugger Robot     {0x080000000000ULL, 0x180100000000ULL, MappingDesc::SHADOW, "shadow"},
116*7c3d14c8STreehugger Robot     {0x180100000000ULL, 0x1C0000000000ULL, MappingDesc::INVALID, "invalid"},
117*7c3d14c8STreehugger Robot     {0x1C0000000000ULL, 0x2C0100000000ULL, MappingDesc::ORIGIN, "origin"},
118*7c3d14c8STreehugger Robot     {0x2C0100000000ULL, 0x300000000000ULL, MappingDesc::INVALID, "invalid"},
119*7c3d14c8STreehugger Robot     {0x300000000000ULL, 0x400000000000ULL, MappingDesc::APP, "high memory"}};
120*7c3d14c8STreehugger Robot 
121*7c3d14c8STreehugger Robot // Maps low and high app ranges to contiguous space with zero base:
122*7c3d14c8STreehugger Robot //   Low:  0000 0000 0000 - 0000 ffff ffff  ->  1000 0000 0000 - 1000 ffff ffff
123*7c3d14c8STreehugger Robot //   High: 3000 0000 0000 - 3fff ffff ffff  ->  0000 0000 0000 - 0fff ffff ffff
124*7c3d14c8STreehugger Robot #define LINEARIZE_MEM(mem) \
125*7c3d14c8STreehugger Robot   (((uptr)(mem) & ~0x200000000000ULL) ^ 0x100000000000ULL)
126*7c3d14c8STreehugger Robot #define MEM_TO_SHADOW(mem) (LINEARIZE_MEM((mem)) + 0x080000000000ULL)
127*7c3d14c8STreehugger Robot #define SHADOW_TO_ORIGIN(shadow) (((uptr)(shadow)) + 0x140000000000ULL)
128*7c3d14c8STreehugger Robot 
129*7c3d14c8STreehugger Robot #elif SANITIZER_FREEBSD && SANITIZER_WORDSIZE == 64
130*7c3d14c8STreehugger Robot 
131*7c3d14c8STreehugger Robot // Low memory: main binary, MAP_32BIT mappings and modules
132*7c3d14c8STreehugger Robot // High memory: heap, modules and main thread stack
133*7c3d14c8STreehugger Robot const MappingDesc kMemoryLayout[] = {
134*7c3d14c8STreehugger Robot     {0x000000000000ULL, 0x010000000000ULL, MappingDesc::APP, "low memory"},
135*7c3d14c8STreehugger Robot     {0x010000000000ULL, 0x100000000000ULL, MappingDesc::INVALID, "invalid"},
136*7c3d14c8STreehugger Robot     {0x100000000000ULL, 0x310000000000ULL, MappingDesc::SHADOW, "shadow"},
137*7c3d14c8STreehugger Robot     {0x310000000000ULL, 0x380000000000ULL, MappingDesc::INVALID, "invalid"},
138*7c3d14c8STreehugger Robot     {0x380000000000ULL, 0x590000000000ULL, MappingDesc::ORIGIN, "origin"},
139*7c3d14c8STreehugger Robot     {0x590000000000ULL, 0x600000000000ULL, MappingDesc::INVALID, "invalid"},
140*7c3d14c8STreehugger Robot     {0x600000000000ULL, 0x800000000000ULL, MappingDesc::APP, "high memory"}};
141*7c3d14c8STreehugger Robot 
142*7c3d14c8STreehugger Robot // Maps low and high app ranges to contiguous space with zero base:
143*7c3d14c8STreehugger Robot //   Low:  0000 0000 0000 - 00ff ffff ffff  ->  2000 0000 0000 - 20ff ffff ffff
144*7c3d14c8STreehugger Robot //   High: 6000 0000 0000 - 7fff ffff ffff  ->  0000 0000 0000 - 1fff ffff ffff
145*7c3d14c8STreehugger Robot #define LINEARIZE_MEM(mem) \
146*7c3d14c8STreehugger Robot   (((uptr)(mem) & ~0xc00000000000ULL) ^ 0x200000000000ULL)
147*7c3d14c8STreehugger Robot #define MEM_TO_SHADOW(mem) (LINEARIZE_MEM((mem)) + 0x100000000000ULL)
148*7c3d14c8STreehugger Robot #define SHADOW_TO_ORIGIN(shadow) (((uptr)(shadow)) + 0x280000000000)
149*7c3d14c8STreehugger Robot 
150*7c3d14c8STreehugger Robot #elif SANITIZER_LINUX && SANITIZER_WORDSIZE == 64
151*7c3d14c8STreehugger Robot 
152*7c3d14c8STreehugger Robot #ifdef MSAN_LINUX_X86_64_OLD_MAPPING
153*7c3d14c8STreehugger Robot // Requries PIE binary and ASLR enabled.
154*7c3d14c8STreehugger Robot // Main thread stack and DSOs at 0x7f0000000000 (sometimes 0x7e0000000000).
155*7c3d14c8STreehugger Robot // Heap at 0x600000000000.
156*7c3d14c8STreehugger Robot const MappingDesc kMemoryLayout[] = {
157*7c3d14c8STreehugger Robot     {0x000000000000ULL, 0x200000000000ULL, MappingDesc::INVALID, "invalid"},
158*7c3d14c8STreehugger Robot     {0x200000000000ULL, 0x400000000000ULL, MappingDesc::SHADOW, "shadow"},
159*7c3d14c8STreehugger Robot     {0x400000000000ULL, 0x600000000000ULL, MappingDesc::ORIGIN, "origin"},
160*7c3d14c8STreehugger Robot     {0x600000000000ULL, 0x800000000000ULL, MappingDesc::APP, "app"}};
161*7c3d14c8STreehugger Robot 
162*7c3d14c8STreehugger Robot #define MEM_TO_SHADOW(mem) (((uptr)(mem)) & ~0x400000000000ULL)
163*7c3d14c8STreehugger Robot #define SHADOW_TO_ORIGIN(mem) (((uptr)(mem)) + 0x200000000000ULL)
164*7c3d14c8STreehugger Robot #else  // MSAN_LINUX_X86_64_OLD_MAPPING
165*7c3d14c8STreehugger Robot // All of the following configurations are supported.
166*7c3d14c8STreehugger Robot // ASLR disabled: main executable and DSOs at 0x555550000000
167*7c3d14c8STreehugger Robot // PIE and ASLR: main executable and DSOs at 0x7f0000000000
168*7c3d14c8STreehugger Robot // non-PIE: main executable below 0x100000000, DSOs at 0x7f0000000000
169*7c3d14c8STreehugger Robot // Heap at 0x700000000000.
170*7c3d14c8STreehugger Robot const MappingDesc kMemoryLayout[] = {
171*7c3d14c8STreehugger Robot     {0x000000000000ULL, 0x010000000000ULL, MappingDesc::APP, "app-1"},
172*7c3d14c8STreehugger Robot     {0x010000000000ULL, 0x100000000000ULL, MappingDesc::SHADOW, "shadow-2"},
173*7c3d14c8STreehugger Robot     {0x100000000000ULL, 0x110000000000ULL, MappingDesc::INVALID, "invalid"},
174*7c3d14c8STreehugger Robot     {0x110000000000ULL, 0x200000000000ULL, MappingDesc::ORIGIN, "origin-2"},
175*7c3d14c8STreehugger Robot     {0x200000000000ULL, 0x300000000000ULL, MappingDesc::SHADOW, "shadow-3"},
176*7c3d14c8STreehugger Robot     {0x300000000000ULL, 0x400000000000ULL, MappingDesc::ORIGIN, "origin-3"},
177*7c3d14c8STreehugger Robot     {0x400000000000ULL, 0x500000000000ULL, MappingDesc::INVALID, "invalid"},
178*7c3d14c8STreehugger Robot     {0x500000000000ULL, 0x510000000000ULL, MappingDesc::SHADOW, "shadow-1"},
179*7c3d14c8STreehugger Robot     {0x510000000000ULL, 0x600000000000ULL, MappingDesc::APP, "app-2"},
180*7c3d14c8STreehugger Robot     {0x600000000000ULL, 0x610000000000ULL, MappingDesc::ORIGIN, "origin-1"},
181*7c3d14c8STreehugger Robot     {0x610000000000ULL, 0x700000000000ULL, MappingDesc::INVALID, "invalid"},
182*7c3d14c8STreehugger Robot     {0x700000000000ULL, 0x800000000000ULL, MappingDesc::APP, "app-3"}};
183*7c3d14c8STreehugger Robot #define MEM_TO_SHADOW(mem) (((uptr)(mem)) ^ 0x500000000000ULL)
184*7c3d14c8STreehugger Robot #define SHADOW_TO_ORIGIN(mem) (((uptr)(mem)) + 0x100000000000ULL)
185*7c3d14c8STreehugger Robot #endif  // MSAN_LINUX_X86_64_OLD_MAPPING
186*7c3d14c8STreehugger Robot 
187*7c3d14c8STreehugger Robot #else
188*7c3d14c8STreehugger Robot #error "Unsupported platform"
189*7c3d14c8STreehugger Robot #endif
190*7c3d14c8STreehugger Robot 
191*7c3d14c8STreehugger Robot const uptr kMemoryLayoutSize = sizeof(kMemoryLayout) / sizeof(kMemoryLayout[0]);
192*7c3d14c8STreehugger Robot 
193*7c3d14c8STreehugger Robot #define MEM_TO_ORIGIN(mem) (SHADOW_TO_ORIGIN(MEM_TO_SHADOW((mem))))
194*7c3d14c8STreehugger Robot 
195*7c3d14c8STreehugger Robot #ifndef __clang__
196*7c3d14c8STreehugger Robot __attribute__((optimize("unroll-loops")))
197*7c3d14c8STreehugger Robot #endif
addr_is_type(uptr addr,MappingDesc::Type mapping_type)198*7c3d14c8STreehugger Robot inline bool addr_is_type(uptr addr, MappingDesc::Type mapping_type) {
199*7c3d14c8STreehugger Robot // It is critical for performance that this loop is unrolled (because then it is
200*7c3d14c8STreehugger Robot // simplified into just a few constant comparisons).
201*7c3d14c8STreehugger Robot #ifdef __clang__
202*7c3d14c8STreehugger Robot #pragma unroll
203*7c3d14c8STreehugger Robot #endif
204*7c3d14c8STreehugger Robot   for (unsigned i = 0; i < kMemoryLayoutSize; ++i)
205*7c3d14c8STreehugger Robot     if (kMemoryLayout[i].type == mapping_type &&
206*7c3d14c8STreehugger Robot         addr >= kMemoryLayout[i].start && addr < kMemoryLayout[i].end)
207*7c3d14c8STreehugger Robot       return true;
208*7c3d14c8STreehugger Robot   return false;
209*7c3d14c8STreehugger Robot }
210*7c3d14c8STreehugger Robot 
211*7c3d14c8STreehugger Robot #define MEM_IS_APP(mem) addr_is_type((uptr)(mem), MappingDesc::APP)
212*7c3d14c8STreehugger Robot #define MEM_IS_SHADOW(mem) addr_is_type((uptr)(mem), MappingDesc::SHADOW)
213*7c3d14c8STreehugger Robot #define MEM_IS_ORIGIN(mem) addr_is_type((uptr)(mem), MappingDesc::ORIGIN)
214*7c3d14c8STreehugger Robot 
215*7c3d14c8STreehugger Robot // These constants must be kept in sync with the ones in MemorySanitizer.cc.
216*7c3d14c8STreehugger Robot const int kMsanParamTlsSize = 800;
217*7c3d14c8STreehugger Robot const int kMsanRetvalTlsSize = 800;
218*7c3d14c8STreehugger Robot 
219*7c3d14c8STreehugger Robot namespace __msan {
220*7c3d14c8STreehugger Robot extern int msan_inited;
221*7c3d14c8STreehugger Robot extern bool msan_init_is_running;
222*7c3d14c8STreehugger Robot extern int msan_report_count;
223*7c3d14c8STreehugger Robot 
224*7c3d14c8STreehugger Robot bool ProtectRange(uptr beg, uptr end);
225*7c3d14c8STreehugger Robot bool InitShadow(bool init_origins);
226*7c3d14c8STreehugger Robot char *GetProcSelfMaps();
227*7c3d14c8STreehugger Robot void InitializeInterceptors();
228*7c3d14c8STreehugger Robot 
229*7c3d14c8STreehugger Robot void MsanAllocatorInit();
230*7c3d14c8STreehugger Robot void MsanAllocatorThreadFinish();
231*7c3d14c8STreehugger Robot void *MsanCalloc(StackTrace *stack, uptr nmemb, uptr size);
232*7c3d14c8STreehugger Robot void *MsanReallocate(StackTrace *stack, void *oldp, uptr size,
233*7c3d14c8STreehugger Robot                      uptr alignment, bool zeroise);
234*7c3d14c8STreehugger Robot void MsanDeallocate(StackTrace *stack, void *ptr);
235*7c3d14c8STreehugger Robot void InstallTrapHandler();
236*7c3d14c8STreehugger Robot void InstallAtExitHandler();
237*7c3d14c8STreehugger Robot 
238*7c3d14c8STreehugger Robot const char *GetStackOriginDescr(u32 id, uptr *pc);
239*7c3d14c8STreehugger Robot 
240*7c3d14c8STreehugger Robot void EnterSymbolizer();
241*7c3d14c8STreehugger Robot void ExitSymbolizer();
242*7c3d14c8STreehugger Robot bool IsInSymbolizer();
243*7c3d14c8STreehugger Robot 
244*7c3d14c8STreehugger Robot struct SymbolizerScope {
SymbolizerScopeSymbolizerScope245*7c3d14c8STreehugger Robot   SymbolizerScope() { EnterSymbolizer(); }
~SymbolizerScopeSymbolizerScope246*7c3d14c8STreehugger Robot   ~SymbolizerScope() { ExitSymbolizer(); }
247*7c3d14c8STreehugger Robot };
248*7c3d14c8STreehugger Robot 
249*7c3d14c8STreehugger Robot void PrintWarning(uptr pc, uptr bp);
250*7c3d14c8STreehugger Robot void PrintWarningWithOrigin(uptr pc, uptr bp, u32 origin);
251*7c3d14c8STreehugger Robot 
252*7c3d14c8STreehugger Robot void GetStackTrace(BufferedStackTrace *stack, uptr max_s, uptr pc, uptr bp,
253*7c3d14c8STreehugger Robot                    bool request_fast_unwind);
254*7c3d14c8STreehugger Robot 
255*7c3d14c8STreehugger Robot void ReportUMR(StackTrace *stack, u32 origin);
256*7c3d14c8STreehugger Robot void ReportExpectedUMRNotFound(StackTrace *stack);
257*7c3d14c8STreehugger Robot void ReportStats();
258*7c3d14c8STreehugger Robot void ReportAtExitStatistics();
259*7c3d14c8STreehugger Robot void DescribeMemoryRange(const void *x, uptr size);
260*7c3d14c8STreehugger Robot void ReportUMRInsideAddressRange(const char *what, const void *start, uptr size,
261*7c3d14c8STreehugger Robot                                  uptr offset);
262*7c3d14c8STreehugger Robot 
263*7c3d14c8STreehugger Robot // Unpoison first n function arguments.
264*7c3d14c8STreehugger Robot void UnpoisonParam(uptr n);
265*7c3d14c8STreehugger Robot void UnpoisonThreadLocalState();
266*7c3d14c8STreehugger Robot 
267*7c3d14c8STreehugger Robot // Returns a "chained" origin id, pointing to the given stack trace followed by
268*7c3d14c8STreehugger Robot // the previous origin id.
269*7c3d14c8STreehugger Robot u32 ChainOrigin(u32 id, StackTrace *stack);
270*7c3d14c8STreehugger Robot 
271*7c3d14c8STreehugger Robot const int STACK_TRACE_TAG_POISON = StackTrace::TAG_CUSTOM + 1;
272*7c3d14c8STreehugger Robot 
273*7c3d14c8STreehugger Robot #define GET_MALLOC_STACK_TRACE                                                 \
274*7c3d14c8STreehugger Robot   BufferedStackTrace stack;                                                    \
275*7c3d14c8STreehugger Robot   if (__msan_get_track_origins() && msan_inited)                               \
276*7c3d14c8STreehugger Robot   GetStackTrace(&stack, common_flags()->malloc_context_size,                   \
277*7c3d14c8STreehugger Robot                 StackTrace::GetCurrentPc(), GET_CURRENT_FRAME(),               \
278*7c3d14c8STreehugger Robot                 common_flags()->fast_unwind_on_malloc)
279*7c3d14c8STreehugger Robot 
280*7c3d14c8STreehugger Robot #define GET_STORE_STACK_TRACE_PC_BP(pc, bp)                                    \
281*7c3d14c8STreehugger Robot   BufferedStackTrace stack;                                                    \
282*7c3d14c8STreehugger Robot   if (__msan_get_track_origins() > 1 && msan_inited)                           \
283*7c3d14c8STreehugger Robot   GetStackTrace(&stack, flags()->store_context_size, pc, bp,                   \
284*7c3d14c8STreehugger Robot                 common_flags()->fast_unwind_on_malloc)
285*7c3d14c8STreehugger Robot 
286*7c3d14c8STreehugger Robot #define GET_FATAL_STACK_TRACE_PC_BP(pc, bp)                                    \
287*7c3d14c8STreehugger Robot   BufferedStackTrace stack;                                                    \
288*7c3d14c8STreehugger Robot   if (msan_inited)                                                             \
289*7c3d14c8STreehugger Robot   GetStackTrace(&stack, kStackTraceMax, pc, bp,                                \
290*7c3d14c8STreehugger Robot                 common_flags()->fast_unwind_on_fatal)
291*7c3d14c8STreehugger Robot 
292*7c3d14c8STreehugger Robot #define GET_STORE_STACK_TRACE \
293*7c3d14c8STreehugger Robot   GET_STORE_STACK_TRACE_PC_BP(StackTrace::GetCurrentPc(), GET_CURRENT_FRAME())
294*7c3d14c8STreehugger Robot 
295*7c3d14c8STreehugger Robot class ScopedThreadLocalStateBackup {
296*7c3d14c8STreehugger Robot  public:
ScopedThreadLocalStateBackup()297*7c3d14c8STreehugger Robot   ScopedThreadLocalStateBackup() { Backup(); }
~ScopedThreadLocalStateBackup()298*7c3d14c8STreehugger Robot   ~ScopedThreadLocalStateBackup() { Restore(); }
299*7c3d14c8STreehugger Robot   void Backup();
300*7c3d14c8STreehugger Robot   void Restore();
301*7c3d14c8STreehugger Robot  private:
302*7c3d14c8STreehugger Robot   u64 va_arg_overflow_size_tls;
303*7c3d14c8STreehugger Robot };
304*7c3d14c8STreehugger Robot 
305*7c3d14c8STreehugger Robot void MsanTSDInit(void (*destructor)(void *tsd));
306*7c3d14c8STreehugger Robot void *MsanTSDGet();
307*7c3d14c8STreehugger Robot void MsanTSDSet(void *tsd);
308*7c3d14c8STreehugger Robot void MsanTSDDtor(void *tsd);
309*7c3d14c8STreehugger Robot 
310*7c3d14c8STreehugger Robot }  // namespace __msan
311*7c3d14c8STreehugger Robot 
312*7c3d14c8STreehugger Robot #define MSAN_MALLOC_HOOK(ptr, size)       \
313*7c3d14c8STreehugger Robot   do {                                    \
314*7c3d14c8STreehugger Robot     if (&__sanitizer_malloc_hook) {       \
315*7c3d14c8STreehugger Robot       UnpoisonParam(2);                   \
316*7c3d14c8STreehugger Robot       __sanitizer_malloc_hook(ptr, size); \
317*7c3d14c8STreehugger Robot     }                                     \
318*7c3d14c8STreehugger Robot     RunMallocHooks(ptr, size);            \
319*7c3d14c8STreehugger Robot   } while (false)
320*7c3d14c8STreehugger Robot #define MSAN_FREE_HOOK(ptr)       \
321*7c3d14c8STreehugger Robot   do {                            \
322*7c3d14c8STreehugger Robot     if (&__sanitizer_free_hook) { \
323*7c3d14c8STreehugger Robot       UnpoisonParam(1);           \
324*7c3d14c8STreehugger Robot       __sanitizer_free_hook(ptr); \
325*7c3d14c8STreehugger Robot     }                             \
326*7c3d14c8STreehugger Robot     RunFreeHooks(ptr);            \
327*7c3d14c8STreehugger Robot   } while (false)
328*7c3d14c8STreehugger Robot 
329*7c3d14c8STreehugger Robot #endif  // MSAN_H
330