-
Notifications
You must be signed in to change notification settings - Fork 15.3k
Closed as not planned
Labels
Description
Here in compiler-rt sanitizer common code:
llvm-project/compiler-rt/lib/sanitizer_common/sanitizer_posix_libcdep.cpp
Lines 291 to 310 in 5861145
| bool IsAccessibleMemoryRange(uptr beg, uptr size) { | |
| uptr page_size = GetPageSizeCached(); | |
| // Checking too large memory ranges is slow. | |
| CHECK_LT(size, page_size * 10); | |
| int sock_pair[2]; | |
| if (pipe(sock_pair)) | |
| return false; | |
| uptr bytes_written = | |
| internal_write(sock_pair[1], reinterpret_cast<void *>(beg), size); | |
| int write_errno; | |
| bool result; | |
| if (internal_iserror(bytes_written, &write_errno)) { | |
| CHECK_EQ(EFAULT, write_errno); | |
| result = false; | |
| } else { | |
| result = (bytes_written == size); | |
| } | |
| internal_close(sock_pair[0]); | |
| internal_close(sock_pair[1]); | |
| return result; |
On line 296, the code calls pipe, which could be intercepted by sanitizers such as TSAN and make them produce false positives. This can be reproduced by the following example, which mixes UBSan and TSan:
// test.cpp
// g++ -std=c++17 -fsanitize=undefined -fsanitize=thread -o test test.cpp
#include <thread>
class Foo {
public:
void produce(int) {}
void consume() {}
void run() {
w1_ = std::thread{&Foo::produce, this, 0};
w2_ = std::thread{&Foo::consume, this};
w1_.join();
w2_.join();
}
private:
std::thread w1_;
std::thread w2_;
};
int main() {
Foo f;
f.run();
return 0;
}
Should we replace this pipe call with something like internal_pipe? I can draft a patch for this if necessary. Or this is not a considered scenario?