Skip to content

Commit 3aee2ef

Browse files
author
git apple-llvm automerger
committed
Merge commit '96313d2de45a' from llvm.org/release/11.x into apple/stable/20200714
2 parents 505da1b + 96313d2 commit 3aee2ef

File tree

2 files changed

+87
-67
lines changed

2 files changed

+87
-67
lines changed

compiler-rt/lib/tsan/rtl/tsan_rtl_report.cpp

Lines changed: 50 additions & 53 deletions
Original file line numberDiff line numberDiff line change
@@ -439,65 +439,61 @@ void RestoreStack(int tid, const u64 epoch, VarSizeStackTrace *stk,
439439
ExtractTagFromStack(stk, tag);
440440
}
441441

442-
static bool HandleRacyStacks(ThreadState *thr, VarSizeStackTrace traces[2],
443-
uptr addr_min, uptr addr_max) {
444-
bool equal_stack = false;
445-
RacyStacks hash;
446-
bool equal_address = false;
447-
RacyAddress ra0 = {addr_min, addr_max};
448-
{
449-
ReadLock lock(&ctx->racy_mtx);
450-
if (flags()->suppress_equal_stacks) {
451-
hash.hash[0] = md5_hash(traces[0].trace, traces[0].size * sizeof(uptr));
452-
hash.hash[1] = md5_hash(traces[1].trace, traces[1].size * sizeof(uptr));
453-
for (uptr i = 0; i < ctx->racy_stacks.Size(); i++) {
454-
if (hash == ctx->racy_stacks[i]) {
455-
VPrintf(2,
456-
"ThreadSanitizer: suppressing report as doubled (stack)\n");
457-
equal_stack = true;
458-
break;
459-
}
460-
}
461-
}
462-
if (flags()->suppress_equal_addresses) {
463-
for (uptr i = 0; i < ctx->racy_addresses.Size(); i++) {
464-
RacyAddress ra2 = ctx->racy_addresses[i];
465-
uptr maxbeg = max(ra0.addr_min, ra2.addr_min);
466-
uptr minend = min(ra0.addr_max, ra2.addr_max);
467-
if (maxbeg < minend) {
468-
VPrintf(2, "ThreadSanitizer: suppressing report as doubled (addr)\n");
469-
equal_address = true;
470-
break;
471-
}
472-
}
442+
static bool FindRacyStacks(const RacyStacks &hash) {
443+
for (uptr i = 0; i < ctx->racy_stacks.Size(); i++) {
444+
if (hash == ctx->racy_stacks[i]) {
445+
VPrintf(2, "ThreadSanitizer: suppressing report as doubled (stack)\n");
446+
return true;
473447
}
474448
}
475-
if (!equal_stack && !equal_address)
449+
return false;
450+
}
451+
452+
static bool HandleRacyStacks(ThreadState *thr, VarSizeStackTrace traces[2]) {
453+
if (!flags()->suppress_equal_stacks)
476454
return false;
477-
if (!equal_stack) {
478-
Lock lock(&ctx->racy_mtx);
479-
ctx->racy_stacks.PushBack(hash);
480-
}
481-
if (!equal_address) {
482-
Lock lock(&ctx->racy_mtx);
483-
ctx->racy_addresses.PushBack(ra0);
455+
RacyStacks hash;
456+
hash.hash[0] = md5_hash(traces[0].trace, traces[0].size * sizeof(uptr));
457+
hash.hash[1] = md5_hash(traces[1].trace, traces[1].size * sizeof(uptr));
458+
{
459+
ReadLock lock(&ctx->racy_mtx);
460+
if (FindRacyStacks(hash))
461+
return true;
484462
}
485-
return true;
463+
Lock lock(&ctx->racy_mtx);
464+
if (FindRacyStacks(hash))
465+
return true;
466+
ctx->racy_stacks.PushBack(hash);
467+
return false;
486468
}
487469

488-
static void AddRacyStacks(ThreadState *thr, VarSizeStackTrace traces[2],
489-
uptr addr_min, uptr addr_max) {
490-
Lock lock(&ctx->racy_mtx);
491-
if (flags()->suppress_equal_stacks) {
492-
RacyStacks hash;
493-
hash.hash[0] = md5_hash(traces[0].trace, traces[0].size * sizeof(uptr));
494-
hash.hash[1] = md5_hash(traces[1].trace, traces[1].size * sizeof(uptr));
495-
ctx->racy_stacks.PushBack(hash);
470+
static bool FindRacyAddress(const RacyAddress &ra0) {
471+
for (uptr i = 0; i < ctx->racy_addresses.Size(); i++) {
472+
RacyAddress ra2 = ctx->racy_addresses[i];
473+
uptr maxbeg = max(ra0.addr_min, ra2.addr_min);
474+
uptr minend = min(ra0.addr_max, ra2.addr_max);
475+
if (maxbeg < minend) {
476+
VPrintf(2, "ThreadSanitizer: suppressing report as doubled (addr)\n");
477+
return true;
478+
}
496479
}
497-
if (flags()->suppress_equal_addresses) {
498-
RacyAddress ra0 = {addr_min, addr_max};
499-
ctx->racy_addresses.PushBack(ra0);
480+
return false;
481+
}
482+
483+
static bool HandleRacyAddress(ThreadState *thr, uptr addr_min, uptr addr_max) {
484+
if (!flags()->suppress_equal_addresses)
485+
return false;
486+
RacyAddress ra0 = {addr_min, addr_max};
487+
{
488+
ReadLock lock(&ctx->racy_mtx);
489+
if (FindRacyAddress(ra0))
490+
return true;
500491
}
492+
Lock lock(&ctx->racy_mtx);
493+
if (FindRacyAddress(ra0))
494+
return true;
495+
ctx->racy_addresses.PushBack(ra0);
496+
return false;
501497
}
502498

503499
bool OutputReport(ThreadState *thr, const ScopedReport &srep) {
@@ -618,6 +614,8 @@ void ReportRace(ThreadState *thr) {
618614
if (IsExpectedReport(addr_min, addr_max - addr_min))
619615
return;
620616
}
617+
if (HandleRacyAddress(thr, addr_min, addr_max))
618+
return;
621619

622620
ReportType typ = ReportTypeRace;
623621
if (thr->is_vptr_access && freed)
@@ -668,7 +666,7 @@ void ReportRace(ThreadState *thr) {
668666
if (IsFiredSuppression(ctx, typ, traces[1]))
669667
return;
670668

671-
if (HandleRacyStacks(thr, traces, addr_min, addr_max))
669+
if (HandleRacyStacks(thr, traces))
672670
return;
673671

674672
// If any of the accesses has a tag, treat this as an "external" race.
@@ -711,7 +709,6 @@ void ReportRace(ThreadState *thr) {
711709
if (!OutputReport(thr, rep))
712710
return;
713711

714-
AddRacyStacks(thr, traces, addr_min, addr_max);
715712
}
716713

717714
void PrintCurrentStack(ThreadState *thr, uptr pc) {

compiler-rt/lib/tsan/tests/rtl/tsan_test_util_posix.cpp

Lines changed: 37 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,8 @@
2727
#include <unistd.h>
2828
#include <errno.h>
2929

30+
#define CALLERPC (__builtin_return_address(0))
31+
3032
using namespace __tsan;
3133

3234
static __thread bool expect_report;
@@ -249,22 +251,42 @@ void ScopedThread::Impl::HandleEvent(Event *ev) {
249251
switch (ev->type) {
250252
case Event::READ:
251253
case Event::WRITE: {
252-
void (*tsan_mop)(void *addr) = 0;
254+
void (*tsan_mop)(void *addr, void *pc) = 0;
253255
if (ev->type == Event::READ) {
254256
switch (ev->arg /*size*/) {
255-
case 1: tsan_mop = __tsan_read1; break;
256-
case 2: tsan_mop = __tsan_read2; break;
257-
case 4: tsan_mop = __tsan_read4; break;
258-
case 8: tsan_mop = __tsan_read8; break;
259-
case 16: tsan_mop = __tsan_read16; break;
257+
case 1:
258+
tsan_mop = __tsan_read1_pc;
259+
break;
260+
case 2:
261+
tsan_mop = __tsan_read2_pc;
262+
break;
263+
case 4:
264+
tsan_mop = __tsan_read4_pc;
265+
break;
266+
case 8:
267+
tsan_mop = __tsan_read8_pc;
268+
break;
269+
case 16:
270+
tsan_mop = __tsan_read16_pc;
271+
break;
260272
}
261273
} else {
262274
switch (ev->arg /*size*/) {
263-
case 1: tsan_mop = __tsan_write1; break;
264-
case 2: tsan_mop = __tsan_write2; break;
265-
case 4: tsan_mop = __tsan_write4; break;
266-
case 8: tsan_mop = __tsan_write8; break;
267-
case 16: tsan_mop = __tsan_write16; break;
275+
case 1:
276+
tsan_mop = __tsan_write1_pc;
277+
break;
278+
case 2:
279+
tsan_mop = __tsan_write2_pc;
280+
break;
281+
case 4:
282+
tsan_mop = __tsan_write4_pc;
283+
break;
284+
case 8:
285+
tsan_mop = __tsan_write8_pc;
286+
break;
287+
case 16:
288+
tsan_mop = __tsan_write16_pc;
289+
break;
268290
}
269291
}
270292
CHECK_NE(tsan_mop, 0);
@@ -274,7 +296,7 @@ void ScopedThread::Impl::HandleEvent(Event *ev) {
274296
const int ErrCode = ECHRNG;
275297
#endif
276298
errno = ErrCode;
277-
tsan_mop(ev->ptr);
299+
tsan_mop(ev->ptr, (void *)ev->arg2);
278300
CHECK_EQ(ErrCode, errno); // In no case must errno be changed.
279301
break;
280302
}
@@ -327,7 +349,7 @@ void ScopedThread::Impl::HandleEvent(Event *ev) {
327349
}
328350

329351
void *ScopedThread::Impl::ScopedThreadCallback(void *arg) {
330-
__tsan_func_entry(__builtin_return_address(0));
352+
__tsan_func_entry(CALLERPC);
331353
Impl *impl = (Impl*)arg;
332354
for (;;) {
333355
Event* ev = (Event*)atomic_load(&impl->event, memory_order_acquire);
@@ -392,7 +414,8 @@ void ScopedThread::Detach() {
392414

393415
void ScopedThread::Access(void *addr, bool is_write,
394416
int size, bool expect_race) {
395-
Event event(is_write ? Event::WRITE : Event::READ, addr, size);
417+
Event event(is_write ? Event::WRITE : Event::READ, addr, size,
418+
(uptr)CALLERPC);
396419
if (expect_race)
397420
event.ExpectReport(ReportTypeRace);
398421
impl_->send(&event);

0 commit comments

Comments
 (0)