summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--lib/asan/asan_mapping.h3
-rw-r--r--lib/asan/asan_rtl.cc14
2 files changed, 16 insertions, 1 deletions
diff --git a/lib/asan/asan_mapping.h b/lib/asan/asan_mapping.h
index 8b4857e6d..937c57b28 100644
--- a/lib/asan/asan_mapping.h
+++ b/lib/asan/asan_mapping.h
@@ -178,7 +178,8 @@ static const u64 kWindowsShadowOffset32 = 3ULL << 28; // 0x30000000
// With the zero shadow base we can not actually map pages starting from 0.
// This constant is somewhat arbitrary.
-#define kZeroBaseShadowStart 4096
+#define kZeroBaseShadowStart 0
+#define kZeroBaseMaxShadowStart (1 << 18)
#define kShadowGapBeg (kLowShadowEnd ? kLowShadowEnd + 1 \
: kZeroBaseShadowStart)
diff --git a/lib/asan/asan_rtl.cc b/lib/asan/asan_rtl.cc
index 4fa8ea2f0..7ff657bc5 100644
--- a/lib/asan/asan_rtl.cc
+++ b/lib/asan/asan_rtl.cc
@@ -301,6 +301,20 @@ static void ProtectGap(uptr addr, uptr size) {
void *res = MmapNoAccess(addr, size, "shadow gap");
if (addr == (uptr)res)
return;
+ // A few pages at the start of the address space can not be protected.
+ // But we really want to protect as much as possible, to prevent this memory
+ // being returned as a result of a non-FIXED mmap().
+ if (addr == kZeroBaseShadowStart) {
+ uptr step = GetPageSizeCached();
+ while (size > step && addr < kZeroBaseMaxShadowStart) {
+ addr += step;
+ size -= step;
+ void *res = MmapNoAccess(addr, size, "shadow gap");
+ if (addr == (uptr)res)
+ return;
+ }
+ }
+
Report("ERROR: Failed to protect the shadow gap. "
"ASan cannot proceed correctly. ABORTING.\n");
DumpProcessMap();