summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMikhail Kashkarov <m.kashkarov@partner.samsung.com>2019-06-28 21:31:32 +0300
committerDongkyun Son <dongkyun.s@samsung.com>2019-07-22 12:16:35 +0000
commitd0abe09c4a743e0176d949ca4e10186369b51498 (patch)
tree813998f197ff82df47d8de3b33ffd61d7b55e734
parent1f34038093e95f5e302bf8f010e3efec921c69d5 (diff)
downloadlinaro-gcc-d0abe09c4a743e0176d949ca4e10186369b51498.tar.gz
linaro-gcc-d0abe09c4a743e0176d949ca4e10186369b51498.tar.bz2
linaro-gcc-d0abe09c4a743e0176d949ca4e10186369b51498.zip
Enable build-tunable asan shadow scale size
Use the following for the project config (3 is default): %define asan_shadow_scale 3 Macros: asan_shadow_scale 3 :Macros + backport https://reviews.llvm.org/D39471 for x86_64 shadow offset + backport https://reviews.llvm.org/D39472 for minimum redzone size + backport https://reviews.llvm.org/D39473 for internal alloc min alignment + backport https://reviews.llvm.org/D39474 to avoid assert failure for non-default shadow scale Change-Id: I23b231f03d6ab47c6b4264f8c7837eb1197f4cc4
-rw-r--r--gcc/asan.h4
-rw-r--r--gcc/config/i386/i386.c15
-rw-r--r--libsanitizer/asan/asan_activation.cc7
-rw-r--r--libsanitizer/asan/asan_fake_stack.cc4
-rw-r--r--libsanitizer/asan/asan_flags.cc4
-rw-r--r--libsanitizer/asan/asan_mapping.h7
-rw-r--r--libsanitizer/asan/asan_rtl.cc1
-rw-r--r--libsanitizer/sanitizer_common/sanitizer_allocator.cc9
-rw-r--r--libsanitizer/sanitizer_common/sanitizer_common.h2
-rw-r--r--packaging/gcc-aarch64.spec1
-rw-r--r--packaging/gcc-armv7hl.spec1
-rw-r--r--packaging/gcc-armv7l.spec1
-rw-r--r--packaging/linaro-gcc.spec1
13 files changed, 48 insertions, 9 deletions
diff --git a/gcc/asan.h b/gcc/asan.h
index 511da9a5bbc..66f7e901a5a 100644
--- a/gcc/asan.h
+++ b/gcc/asan.h
@@ -43,7 +43,11 @@ extern hash_set <tree> *asan_used_labels;
/* Shadow memory is found at
(address >> ASAN_SHADOW_SHIFT) + asan_shadow_offset (). */
+#if defined(ASAN_SHADOW_SCALE)
+#define ASAN_SHADOW_SHIFT ASAN_SHADOW_SCALE
+#else
#define ASAN_SHADOW_SHIFT 3
+#endif
#define ASAN_SHADOW_GRANULARITY (1UL << ASAN_SHADOW_SHIFT)
/* Red zone size, stack and global variables are padded by ASAN_RED_ZONE_SIZE
diff --git a/gcc/config/i386/i386.c b/gcc/config/i386/i386.c
index 898c2470895..bd043c4c79a 100644
--- a/gcc/config/i386/i386.c
+++ b/gcc/config/i386/i386.c
@@ -79,6 +79,7 @@ along with GCC; see the file COPYING3. If not see
#include "dojump.h"
#include "fold-const-call.h"
#include "tree-ssanames.h"
+#include "asan.h"
/* This file should be included last. */
#include "target-def.h"
@@ -7374,12 +7375,20 @@ ix86_legitimate_combined_insn (rtx_insn *insn)
/* Implement the TARGET_ASAN_SHADOW_OFFSET hook. */
+#if !defined(TARGET_MACHO) && !defined(ASAN_SHADOW_SHIFT)
+# error ASAN_SHADOW_SHIFT is not defined
+#endif
+
+static const unsigned HOST_WIDE_INT asan_short_64bit_shadow_offset =
+ 0x7FFFFFFF & (~0xFFFULL << ASAN_SHADOW_SHIFT);
+
static unsigned HOST_WIDE_INT
ix86_asan_shadow_offset (void)
{
- return TARGET_LP64 ? (TARGET_MACHO ? (HOST_WIDE_INT_1 << 44)
- : HOST_WIDE_INT_C (0x7fff8000))
- : (HOST_WIDE_INT_1 << 29);
+ return TARGET_LP64
+ ? (TARGET_MACHO ? (HOST_WIDE_INT_1 << 44)
+ : asan_short_64bit_shadow_offset)
+ : (HOST_WIDE_INT_1 << 29);
}
/* Argument support functions. */
diff --git a/libsanitizer/asan/asan_activation.cc b/libsanitizer/asan/asan_activation.cc
index 26798e7103b..0c0ae095cb8 100644
--- a/libsanitizer/asan/asan_activation.cc
+++ b/libsanitizer/asan/asan_activation.cc
@@ -14,8 +14,10 @@
#include "asan_allocator.h"
#include "asan_flags.h"
#include "asan_internal.h"
+#include "asan_mapping.h"
#include "asan_poisoning.h"
#include "asan_stack.h"
+#include "sanitizer_common/sanitizer_common.h"
#include "sanitizer_common/sanitizer_flags.h"
namespace __asan {
@@ -107,8 +109,9 @@ void AsanDeactivate() {
AllocatorOptions disabled = asan_deactivated_flags.allocator_options;
disabled.quarantine_size_mb = 0;
- disabled.min_redzone = 16; // Redzone must be at least 16 bytes long.
- disabled.max_redzone = 16;
+ // Redzone must be at least Max(16, granularity) bytes long.
+ disabled.min_redzone = Max(16, (int)SHADOW_GRANULARITY);
+ disabled.max_redzone = disabled.min_redzone;
disabled.alloc_dealloc_mismatch = false;
disabled.may_return_null = true;
ReInitializeAllocator(disabled);
diff --git a/libsanitizer/asan/asan_fake_stack.cc b/libsanitizer/asan/asan_fake_stack.cc
index bf7566a334e..a2e3f4ecc90 100644
--- a/libsanitizer/asan/asan_fake_stack.cc
+++ b/libsanitizer/asan/asan_fake_stack.cc
@@ -26,9 +26,9 @@ static const u64 kAllocaRedzoneMask = 31UL;
// For small size classes inline PoisonShadow for better performance.
ALWAYS_INLINE void SetShadow(uptr ptr, uptr size, uptr class_id, u64 magic) {
- CHECK_EQ(SHADOW_SCALE, 3); // This code expects SHADOW_SCALE=3.
u64 *shadow = reinterpret_cast<u64*>(MemToShadow(ptr));
- if (class_id <= 6) {
+ if (SHADOW_SCALE == 3 && class_id <= 6) {
+ // This code expects SHADOW_SCALE=3.
for (uptr i = 0; i < (((uptr)1) << class_id); i++) {
shadow[i] = magic;
// Make sure this does not become memset.
diff --git a/libsanitizer/asan/asan_flags.cc b/libsanitizer/asan/asan_flags.cc
index 39473bba64d..66398412ed0 100644
--- a/libsanitizer/asan/asan_flags.cc
+++ b/libsanitizer/asan/asan_flags.cc
@@ -13,6 +13,7 @@
#include "asan_activation.h"
#include "asan_flags.h"
#include "asan_interface_internal.h"
+#include "asan_mapping.h"
#include "asan_stack.h"
#include "lsan/lsan_common.h"
#include "sanitizer_common/sanitizer_common.h"
@@ -133,6 +134,9 @@ void InitializeFlags() {
SanitizerToolName);
Die();
}
+ // Ensure that redzone is at least SHADOW_GRANULARITY.
+ if (f->redzone < (int)SHADOW_GRANULARITY)
+ f->redzone = SHADOW_GRANULARITY;
// Make "strict_init_order" imply "check_initialization_order".
// TODO(samsonov): Use a single runtime flag for an init-order checker.
if (f->strict_init_order) {
diff --git a/libsanitizer/asan/asan_mapping.h b/libsanitizer/asan/asan_mapping.h
index b9fa5f79481..040cde68ae4 100644
--- a/libsanitizer/asan/asan_mapping.h
+++ b/libsanitizer/asan/asan_mapping.h
@@ -122,11 +122,16 @@
// || `[0x30000000, 0x35ffffff]` || LowShadow ||
// || `[0x00000000, 0x2fffffff]` || LowMem ||
+#if defined(ASAN_SHADOW_SCALE)
+static const u64 kDefaultShadowScale = ASAN_SHADOW_SCALE;
+#else
static const u64 kDefaultShadowScale = 3;
+#endif
static const u64 kDefaultShadowSentinel = ~(uptr)0;
static const u64 kDefaultShadowOffset32 = 1ULL << 29; // 0x20000000
static const u64 kDefaultShadowOffset64 = 1ULL << 44;
-static const u64 kDefaultShort64bitShadowOffset = 0x7FFF8000; // < 2G.
+static const u64 kDefaultShort64bitShadowOffset =
+ 0x7FFFFFFF & (~0xFFFULL << kDefaultShadowScale); // < 2G.
static const u64 kIosShadowOffset32 = 1ULL << 30; // 0x40000000
static const u64 kIosShadowOffset64 = 0x120200000;
static const u64 kIosSimShadowOffset32 = 1ULL << 30;
diff --git a/libsanitizer/asan/asan_rtl.cc b/libsanitizer/asan/asan_rtl.cc
index 5bafb9a78cf..9ff29001259 100644
--- a/libsanitizer/asan/asan_rtl.cc
+++ b/libsanitizer/asan/asan_rtl.cc
@@ -469,6 +469,7 @@ static void AsanInitInternal() {
MaybeReexec();
// Setup internal allocator callback.
+ SetLowLevelAllocateMinAlignment(SHADOW_GRANULARITY);
SetLowLevelAllocateCallback(OnLowLevelAllocate);
InitializeAsanInterceptors();
diff --git a/libsanitizer/sanitizer_common/sanitizer_allocator.cc b/libsanitizer/sanitizer_common/sanitizer_allocator.cc
index 5af4fba2bc7..d68c2072ff4 100644
--- a/libsanitizer/sanitizer_common/sanitizer_allocator.cc
+++ b/libsanitizer/sanitizer_common/sanitizer_allocator.cc
@@ -175,11 +175,13 @@ void InternalFree(void *addr, InternalAllocatorCache *cache) {
}
// LowLevelAllocator
+constexpr uptr kLowLevelAllocatorDefaultAlignment = 8;
+static uptr low_level_alloc_min_alignment = kLowLevelAllocatorDefaultAlignment;
static LowLevelAllocateCallback low_level_alloc_callback;
void *LowLevelAllocator::Allocate(uptr size) {
// Align allocation size.
- size = RoundUpTo(size, 8);
+ size = RoundUpTo(size, low_level_alloc_min_alignment);
if (allocated_end_ - allocated_current_ < (sptr)size) {
uptr size_to_allocate = Max(size, GetPageSizeCached());
allocated_current_ =
@@ -196,6 +198,11 @@ void *LowLevelAllocator::Allocate(uptr size) {
return res;
}
+void SetLowLevelAllocateMinAlignment(uptr alignment) {
+ CHECK(IsPowerOfTwo(alignment));
+ low_level_alloc_min_alignment = Max(alignment, low_level_alloc_min_alignment);
+}
+
void SetLowLevelAllocateCallback(LowLevelAllocateCallback callback) {
low_level_alloc_callback = callback;
}
diff --git a/libsanitizer/sanitizer_common/sanitizer_common.h b/libsanitizer/sanitizer_common/sanitizer_common.h
index fb06aa45109..79017ca591b 100644
--- a/libsanitizer/sanitizer_common/sanitizer_common.h
+++ b/libsanitizer/sanitizer_common/sanitizer_common.h
@@ -174,6 +174,8 @@ class LowLevelAllocator {
char *allocated_end_;
char *allocated_current_;
};
+// Set the min alignment of LowLevelAllocator to at least alignment.
+void SetLowLevelAllocateMinAlignment(uptr alignment);
typedef void (*LowLevelAllocateCallback)(uptr ptr, uptr size);
// Allows to register tool-specific callbacks for LowLevelAllocator.
// Passing NULL removes the callback.
diff --git a/packaging/gcc-aarch64.spec b/packaging/gcc-aarch64.spec
index 52a7c9d3fb4..25eaa9423e1 100644
--- a/packaging/gcc-aarch64.spec
+++ b/packaging/gcc-aarch64.spec
@@ -727,6 +727,7 @@ if [ ! -z "$(echo $RPM_OPT_FLAGS | grep -o "\B\-Wformat\-")" ]; then
fi
%{?asan: RPM_OPT_FLAGS=$(echo $RPM_OPT_FLAGS -DASAN_INIT_FIRST) }
+%{?asan_shadow_scale: RPM_OPT_FLAGS=$(echo $RPM_OPT_FLAGS -Wp,-DASAN_SHADOW_SCALE=%{asan_shadow_scale})}
%ifarch armv7l armv7hl aarch64
%undefine gcc_profiledbootstrap
diff --git a/packaging/gcc-armv7hl.spec b/packaging/gcc-armv7hl.spec
index 3540bfe1e27..b5a36ff0727 100644
--- a/packaging/gcc-armv7hl.spec
+++ b/packaging/gcc-armv7hl.spec
@@ -727,6 +727,7 @@ if [ ! -z "$(echo $RPM_OPT_FLAGS | grep -o "\B\-Wformat\-")" ]; then
fi
%{?asan: RPM_OPT_FLAGS=$(echo $RPM_OPT_FLAGS -DASAN_INIT_FIRST) }
+%{?asan_shadow_scale: RPM_OPT_FLAGS=$(echo $RPM_OPT_FLAGS -Wp,-DASAN_SHADOW_SCALE=%{asan_shadow_scale})}
%ifarch armv7l armv7hl aarch64
%undefine gcc_profiledbootstrap
diff --git a/packaging/gcc-armv7l.spec b/packaging/gcc-armv7l.spec
index f9a624167f2..fda85b88306 100644
--- a/packaging/gcc-armv7l.spec
+++ b/packaging/gcc-armv7l.spec
@@ -727,6 +727,7 @@ if [ ! -z "$(echo $RPM_OPT_FLAGS | grep -o "\B\-Wformat\-")" ]; then
fi
%{?asan: RPM_OPT_FLAGS=$(echo $RPM_OPT_FLAGS -DASAN_INIT_FIRST) }
+%{?asan_shadow_scale: RPM_OPT_FLAGS=$(echo $RPM_OPT_FLAGS -Wp,-DASAN_SHADOW_SCALE=%{asan_shadow_scale})}
%ifarch armv7l armv7hl aarch64
%undefine gcc_profiledbootstrap
diff --git a/packaging/linaro-gcc.spec b/packaging/linaro-gcc.spec
index 52a1b5f5f78..fde4e38354d 100644
--- a/packaging/linaro-gcc.spec
+++ b/packaging/linaro-gcc.spec
@@ -724,6 +724,7 @@ if [ ! -z "$(echo $RPM_OPT_FLAGS | grep -o "\B\-Wformat\-")" ]; then
fi
%{?asan: RPM_OPT_FLAGS=$(echo $RPM_OPT_FLAGS -DASAN_INIT_FIRST) }
+%{?asan_shadow_scale: RPM_OPT_FLAGS=$(echo $RPM_OPT_FLAGS -Wp,-DASAN_SHADOW_SCALE=%{asan_shadow_scale})}
%ifarch armv7l armv7hl aarch64
%undefine gcc_profiledbootstrap