1 //===-- tsan_symbolize.cc -------------------------------------------------===//
3 // This file is distributed under the University of Illinois Open Source
4 // License. See LICENSE.TXT for details.
6 //===----------------------------------------------------------------------===//
8 // This file is a part of ThreadSanitizer (TSan), a race detector.
10 //===----------------------------------------------------------------------===//
12 #include "tsan_symbolize.h"
14 #include "sanitizer_common/sanitizer_common.h"
15 #include "sanitizer_common/sanitizer_placement_new.h"
16 #include "sanitizer_common/sanitizer_symbolizer.h"
17 #include "tsan_flags.h"
18 #include "tsan_report.h"
23 void EnterSymbolizer() {
24 ThreadState
*thr
= cur_thread();
25 CHECK(!thr
->in_symbolizer
);
26 thr
->in_symbolizer
= true;
27 thr
->ignore_interceptors
++;
30 void ExitSymbolizer() {
31 ThreadState
*thr
= cur_thread();
32 CHECK(thr
->in_symbolizer
);
33 thr
->in_symbolizer
= false;
34 thr
->ignore_interceptors
--;
37 // May be overriden by JIT/JAVA/etc,
38 // whatever produces PCs marked with kExternalPCBit.
39 SANITIZER_WEAK_DEFAULT_IMPL
40 bool __tsan_symbolize_external(uptr pc
, char *func_buf
, uptr func_siz
,
41 char *file_buf
, uptr file_siz
, int *line
,
46 SymbolizedStack
*SymbolizeCode(uptr addr
) {
47 // Check if PC comes from non-native land.
48 if (addr
& kExternalPCBit
) {
49 // Declare static to not consume too much stack space.
50 // We symbolize reports in a single thread, so this is fine.
51 static char func_buf
[1024];
52 static char file_buf
[1024];
54 SymbolizedStack
*frame
= SymbolizedStack::New(addr
);
55 if (__tsan_symbolize_external(addr
, func_buf
, sizeof(func_buf
), file_buf
,
56 sizeof(file_buf
), &line
, &col
)) {
57 frame
->info
.function
= internal_strdup(func_buf
);
58 frame
->info
.file
= internal_strdup(file_buf
);
59 frame
->info
.line
= line
;
60 frame
->info
.column
= col
;
64 return Symbolizer::GetOrInit()->SymbolizePC(addr
);
67 ReportLocation
*SymbolizeData(uptr addr
) {
69 if (!Symbolizer::GetOrInit()->SymbolizeData(addr
, &info
))
71 ReportLocation
*ent
= ReportLocation::New(ReportLocationGlobal
);
72 internal_memcpy(&ent
->global
, &info
, sizeof(info
));
76 void SymbolizeFlush() {
77 Symbolizer::GetOrInit()->Flush();