[ASan] Poison the leftmost shadow byte with a special value so that we can find
authorAlexander Potapenko <glider@google.com>
Thu, 15 Nov 2012 13:40:44 +0000 (13:40 +0000)
committerAlexander Potapenko <glider@google.com>
Thu, 15 Nov 2012 13:40:44 +0000 (13:40 +0000)
the beginning of the fake frame when reporting an use-after-return error.
Fixes http://code.google.com/p/address-sanitizer/issues/detail?id=126

llvm-svn: 168040

compiler-rt/lib/asan/asan_allocator.cc
compiler-rt/lib/asan/asan_internal.h
compiler-rt/lib/asan/asan_report.cc
compiler-rt/lib/asan/asan_thread.cc

index de37137..d864ea1 100644 (file)
@@ -998,6 +998,10 @@ void FakeStack::OnFree(uptr ptr, uptr size, uptr real_stack) {
   CHECK(fake_frame->descr != 0);
   CHECK(fake_frame->size_minus_one == size - 1);
   PoisonShadow(ptr, size, kAsanStackAfterReturnMagic);
+  CHECK(size >= SHADOW_GRANULARITY);
+  // Poison the leftmost shadow byte with a special value so that we can find
+  // the beginning of the fake frame when reporting an error.
+  PoisonShadow(ptr, SHADOW_GRANULARITY, kAsanStackAfterReturnLeftMagic);
 }
 
 }  // namespace __asan
index f9a6149..a473a04 100644 (file)
@@ -160,6 +160,7 @@ const int kAsanStackPartialRedzoneMagic = 0xf4;
 const int kAsanStackAfterReturnMagic = 0xf5;
 const int kAsanInitializationOrderMagic = 0xf6;
 const int kAsanUserPoisonedMemoryMagic = 0xf7;
+const int kAsanStackAfterReturnLeftMagic = 0xf8;
 const int kAsanGlobalRedzoneMagic = 0xf9;
 const int kAsanInternalHeapMagic = 0xfe;
 
index 2fbf8fd..86bb66c 100644 (file)
@@ -450,6 +450,7 @@ void __asan_report_error(uptr pc, uptr bp, uptr sp,
         bug_descr = "stack-buffer-overflow";
         break;
       case kAsanStackAfterReturnMagic:
+      case kAsanStackAfterReturnLeftMagic:
         bug_descr = "stack-use-after-return";
         break;
       case kAsanUserPoisonedMemoryMagic:
index bdb5022..9ac3962 100644 (file)
@@ -131,12 +131,14 @@ const char *AsanThread::GetFrameNameByAddr(uptr addr, uptr *offset) {
   u8 *shadow_bottom = (u8*)MemToShadow(bottom);
 
   while (shadow_ptr >= shadow_bottom &&
-      *shadow_ptr != kAsanStackLeftRedzoneMagic) {
+      *shadow_ptr != kAsanStackLeftRedzoneMagic &&
+      *shadow_ptr != kAsanStackAfterReturnLeftMagic) {
     shadow_ptr--;
   }
 
   while (shadow_ptr >= shadow_bottom &&
-      *shadow_ptr == kAsanStackLeftRedzoneMagic) {
+      (*shadow_ptr == kAsanStackLeftRedzoneMagic ||
+       *shadow_ptr == kAsanStackAfterReturnLeftMagic)) {
     shadow_ptr--;
   }