google / sanitizers

AddressSanitizer, ThreadSanitizer, MemorySanitizer
Other
11.01k stars 998 forks source link

False positive: LeakSanitizer detects "leak" in immortal static object #1753

Open jemfinch opened 2 months ago

jemfinch commented 2 months ago

It seems like if your class stores a pointer as a uintptr_t and stores any information in the MSBs of the resulting integer, LeakSanitizer believes it's leaked the allocated memory:

#include <bit>
#include <cstdint>

struct StoresPointerAsInteger {
  static constexpr uintptr_t kMask = 1ULL << 63;
  StoresPointerAsInteger() : p(std::bit_cast<uintptr_t>(new int) | kMask) {}
  ~StoresPointerAsInteger() { delete std::bit_cast<int*>(p & ~kMask); }
  uintptr_t p;
};

int main(int argc, char** argv) {
  static auto* p = new StoresPointerAsInteger;
}

This tickles LeakSanitizer for me.

jemfinch commented 2 months ago

So I think I'm running afoul of MaybeUserPointer at https://github.com/llvm/llvm-project/blob/3d65bd935a91439c483c56a966edc283a2b1130d/compiler-rt/lib/lsan/lsan_common.cpp#L260 which is returning false if certain MSBs of the word are set. I'm not personally familiar with LAM_U57, but I would like to keep using the 16 MSBs that my processor isn't using. Definitely willing to learn more about why I shouldn't, though.