summaryrefslogtreecommitdiff
path: root/lib/asan
diff options
context:
space:
mode:
authorKostya Serebryany <kcc@google.com>2014-10-17 01:22:37 +0000
committerKostya Serebryany <kcc@google.com>2014-10-17 01:22:37 +0000
commitd97858de5d17a669dcdf6c0b3c0eaf9d6e4fef75 (patch)
treedd4948b70d5261f4d8b0d27b96f3ad289d5c9f17 /lib/asan
parent1365cf2482bfea7cdfb2edfe90dcb1c911d550e4 (diff)
[asan] the run-time part of intra-object-overflow detector (-fsanitize-address-field-padding=1). Note that all of this is still experimental; don't use unless you are brave.
git-svn-id: https://llvm.org/svn/llvm-project/compiler-rt/trunk@220013 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/asan')
-rw-r--r--lib/asan/asan_interface_internal.h4
-rw-r--r--lib/asan/asan_internal.h1
-rw-r--r--lib/asan/asan_poisoning.cc32
-rw-r--r--lib/asan/asan_report.cc7
4 files changed, 44 insertions, 0 deletions
diff --git a/lib/asan/asan_interface_internal.h b/lib/asan/asan_interface_internal.h
index a8399754a..edaf44d78 100644
--- a/lib/asan/asan_interface_internal.h
+++ b/lib/asan/asan_interface_internal.h
@@ -173,6 +173,10 @@ extern "C" {
void __asan_poison_cxx_array_cookie(uptr p);
SANITIZER_INTERFACE_ATTRIBUTE
uptr __asan_load_cxx_array_cookie(uptr *p);
+ SANITIZER_INTERFACE_ATTRIBUTE
+ void __asan_poison_intra_object_redzone(uptr p, uptr size);
+ SANITIZER_INTERFACE_ATTRIBUTE
+ void __asan_unpoison_intra_object_redzone(uptr p, uptr size);
} // extern "C"
#endif // ASAN_INTERFACE_INTERNAL_H
diff --git a/lib/asan/asan_internal.h b/lib/asan/asan_internal.h
index 798d687b8..f9f924308 100644
--- a/lib/asan/asan_internal.h
+++ b/lib/asan/asan_internal.h
@@ -135,6 +135,7 @@ const int kAsanStackUseAfterScopeMagic = 0xf8;
const int kAsanGlobalRedzoneMagic = 0xf9;
const int kAsanInternalHeapMagic = 0xfe;
const int kAsanArrayCookieMagic = 0xac;
+const int kAsanIntraObjectRedzone = 0xbb;
static const uptr kCurrentStackFrameMagic = 0x41B58AB3;
static const uptr kRetiredStackFrameMagic = 0x45E0360E;
diff --git a/lib/asan/asan_poisoning.cc b/lib/asan/asan_poisoning.cc
index f7f715d5d..1c6e92f69 100644
--- a/lib/asan/asan_poisoning.cc
+++ b/lib/asan/asan_poisoning.cc
@@ -61,6 +61,27 @@ void FlushUnneededASanShadowMemory(uptr p, uptr size) {
FlushUnneededShadowMemory(shadow_beg, shadow_end - shadow_beg);
}
+void AsanPoisonOrUnpoisonIntraObjectRedzone(uptr ptr, uptr size, bool poison) {
+ uptr end = ptr + size;
+ if (common_flags()->verbosity) {
+ Printf("__asan_%spoison_intra_object_redzone [%p,%p) %zd\n",
+ poison ? "" : "un", ptr, end, size);
+ if (common_flags()->verbosity >= 2)
+ PRINT_CURRENT_STACK();
+ }
+ CHECK(size);
+ CHECK_LE(size, 4096);
+ CHECK(IsAligned(end, SHADOW_GRANULARITY));
+ if (!IsAligned(ptr, SHADOW_GRANULARITY)) {
+ *(u8 *)MemToShadow(ptr) =
+ poison ? static_cast<u8>(ptr % SHADOW_GRANULARITY) : 0;
+ ptr |= SHADOW_GRANULARITY - 1;
+ ptr++;
+ }
+ for (; ptr < end; ptr += SHADOW_GRANULARITY)
+ *(u8*)MemToShadow(ptr) = poison ? kAsanIntraObjectRedzone : 0;
+}
+
} // namespace __asan
// ---------------------- Interface ---------------- {{{1
@@ -375,6 +396,17 @@ int __sanitizer_verify_contiguous_container(const void *beg_p,
return 0;
return 1;
}
+
+extern "C" SANITIZER_INTERFACE_ATTRIBUTE
+void __asan_poison_intra_object_redzone(uptr ptr, uptr size) {
+ AsanPoisonOrUnpoisonIntraObjectRedzone(ptr, size, true);
+}
+
+extern "C" SANITIZER_INTERFACE_ATTRIBUTE
+void __asan_unpoison_intra_object_redzone(uptr ptr, uptr size) {
+ AsanPoisonOrUnpoisonIntraObjectRedzone(ptr, size, false);
+}
+
// --- Implementation of LSan-specific functions --- {{{1
namespace __lsan {
bool WordIsPoisoned(uptr addr) {
diff --git a/lib/asan/asan_report.cc b/lib/asan/asan_report.cc
index 7e79adb70..27f1d346a 100644
--- a/lib/asan/asan_report.cc
+++ b/lib/asan/asan_report.cc
@@ -94,6 +94,8 @@ class Decorator: public __sanitizer::SanitizerCommonDecorator {
return Red();
case kAsanInternalHeapMagic:
return Yellow();
+ case kAsanIntraObjectRedzone:
+ return Yellow();
default:
return Default();
}
@@ -168,6 +170,8 @@ static void PrintLegend(InternalScopedString *str) {
kAsanContiguousContainerOOBMagic);
PrintShadowByte(str, " Array cookie: ",
kAsanArrayCookieMagic);
+ PrintShadowByte(str, " Intra object redzone: ",
+ kAsanIntraObjectRedzone);
PrintShadowByte(str, " ASan internal: ", kAsanInternalHeapMagic);
}
@@ -981,6 +985,9 @@ void __asan_report_error(uptr pc, uptr bp, uptr sp, uptr addr, int is_write,
case kAsanGlobalRedzoneMagic:
bug_descr = "global-buffer-overflow";
break;
+ case kAsanIntraObjectRedzone:
+ bug_descr = "intra-object-overflow";
+ break;
}
}