[compiler-rt] a0b1f3a - [hwasan] Check for overflow when searching candidates.

Florian Mayer via llvm-commits llvm-commits at lists.llvm.org
Tue Jul 6 03:22:24 PDT 2021


Author: Florian Mayer
Date: 2021-07-06T11:22:13+01:00
New Revision: a0b1f3aac57a9becb28d6a9c50f4d2eee7ba6c82

URL: https://github.com/llvm/llvm-project/commit/a0b1f3aac57a9becb28d6a9c50f4d2eee7ba6c82
DIFF: https://github.com/llvm/llvm-project/commit/a0b1f3aac57a9becb28d6a9c50f4d2eee7ba6c82.diff

LOG: [hwasan] Check for overflow when searching candidates.

If the fault address is at the boundary of memory regions, this could
cause us to segfault otherwise.

Ran test with old compiler_rt to make sure it fails.

Reviewed By: eugenis

Differential Revision: https://reviews.llvm.org/D105032

Added: 
    compiler-rt/test/hwasan/TestCases/tag-mismatch-border-address.c

Modified: 
    compiler-rt/lib/hwasan/hwasan_mapping.h
    compiler-rt/lib/hwasan/hwasan_report.cpp

Removed: 
    


################################################################################
diff  --git a/compiler-rt/lib/hwasan/hwasan_mapping.h b/compiler-rt/lib/hwasan/hwasan_mapping.h
index 20b449aa70a6..fae66d5719e5 100644
--- a/compiler-rt/lib/hwasan/hwasan_mapping.h
+++ b/compiler-rt/lib/hwasan/hwasan_mapping.h
@@ -65,6 +65,11 @@ inline uptr MemToShadowSize(uptr size) {
 
 bool MemIsApp(uptr p);
 
+inline bool MemIsShadow(uptr p) {
+  return (kLowShadowStart <= p && p <= kLowShadowEnd) ||
+         (kHighShadowStart <= p && p <= kHighShadowEnd);
+}
+
 }  // namespace __hwasan
 
 #endif  // HWASAN_MAPPING_H

diff  --git a/compiler-rt/lib/hwasan/hwasan_report.cpp b/compiler-rt/lib/hwasan/hwasan_report.cpp
index d4d836bd4894..cf23c2962889 100644
--- a/compiler-rt/lib/hwasan/hwasan_report.cpp
+++ b/compiler-rt/lib/hwasan/hwasan_report.cpp
@@ -395,12 +395,14 @@ void PrintAddressDescription(
   tag_t *candidate = nullptr, *left = tag_ptr, *right = tag_ptr;
   uptr candidate_distance = 0;
   for (; candidate_distance < 1000; candidate_distance++) {
-    if (TagsEqual(addr_tag, left)) {
+    if (MemIsShadow(reinterpret_cast<uptr>(left)) &&
+        TagsEqual(addr_tag, left)) {
       candidate = left;
       break;
     }
     --left;
-    if (TagsEqual(addr_tag, right)) {
+    if (MemIsShadow(reinterpret_cast<uptr>(right)) &&
+        TagsEqual(addr_tag, right)) {
       candidate = right;
       break;
     }

diff  --git a/compiler-rt/test/hwasan/TestCases/tag-mismatch-border-address.c b/compiler-rt/test/hwasan/TestCases/tag-mismatch-border-address.c
new file mode 100644
index 000000000000..b66ab5b4baba
--- /dev/null
+++ b/compiler-rt/test/hwasan/TestCases/tag-mismatch-border-address.c
@@ -0,0 +1,30 @@
+// Make sure we do not segfault when checking an address close to kLowMemEnd.
+// RUN: %clang_hwasan  %s -o %t
+// RUN: not %run %t 2>&1 | FileCheck %s --check-prefix=CHECK
+
+// REQUIRES: stable-runtime
+// REQUIRES: aarch64-target-arch
+
+#include <sanitizer/hwasan_interface.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <sys/mman.h>
+
+static volatile char sink;
+extern void *__hwasan_shadow_memory_dynamic_address;
+
+int main(int argc, char **argv) {
+  void *high_addr = (char *)__hwasan_shadow_memory_dynamic_address - 0x1000;
+  void *r = mmap(high_addr, 4096, PROT_READ, MAP_FIXED | MAP_ANON | MAP_PRIVATE,
+                 -1, 0);
+  if (r == MAP_FAILED) {
+    fprintf(stderr, "Failed to mmap\n");
+    abort();
+  }
+  volatile char *x = (char *)__hwasan_tag_pointer(r, 4);
+  sink = *x;
+}
+
+// CHECK-NOT: Failed to mmap
+// CHECK-NOT: Segmentation fault
+// CHECK-NOT: SEGV


        


More information about the llvm-commits mailing list