From 18af8d16cf71b75081f20184d34206ff4ebce025 Mon Sep 17 00:00:00 2001 From: Yury Gribov Date: Fri, 17 Apr 2015 07:51:02 +0000 Subject: [PATCH] asan.c (set_sanitized_sections): New function. 2015-04-17 Yury Gribov gcc/ * asan.c (set_sanitized_sections): New function. (section_sanitized_p): Ditto. (asan_protect_global): Optionally sanitize user-defined sections. * asan.h (set_sanitized_sections): Declare new function. * common.opt (fsanitize-sections): New option. * doc/invoke.texi (-fsanitize-sections): Document new option. * opts-global.c (handle_common_deferred_options): Handle new option. gcc/testsuite/ * c-c++-common/asan/user-section-1.c: New test. From-SVN: r222168 --- gcc/ChangeLog | 12 ++++++++++++ gcc/asan.c | 31 ++++++++++++++++++++++++++++++- gcc/asan.h | 2 ++ gcc/common.opt | 5 +++++ gcc/doc/invoke.texi | 7 ++++++- gcc/opts-global.c | 4 ++++ gcc/testsuite/ChangeLog | 4 ++++ 7 files changed, 63 insertions(+), 2 deletions(-) diff --git a/gcc/ChangeLog b/gcc/ChangeLog index d572d495935..523ad74c98d 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,15 @@ +2015-04-17 Yury Gribov + + * asan.c (set_sanitized_sections): New function. + (section_sanitized_p): Ditto. + (asan_protect_global): Optionally sanitize user-defined + sections. + * asan.h (set_sanitized_sections): Declare new function. + * common.opt (fsanitize-sections): New option. + * doc/invoke.texi (-fsanitize-sections): Document new option. + * opts-global.c (handle_common_deferred_options): Handle new + option. + 2015-04-17 Jakub Jelinek PR debug/65771 diff --git a/gcc/asan.c b/gcc/asan.c index 9e4a6299817..6706af7008c 100644 --- a/gcc/asan.c +++ b/gcc/asan.c @@ -272,6 +272,7 @@ along with GCC; see the file COPYING3. If not see static unsigned HOST_WIDE_INT asan_shadow_offset_value; static bool asan_shadow_offset_computed; +static const char *sanitized_sections; /* Sets shadow offset to value in string VAL. */ @@ -294,6 +295,33 @@ set_asan_shadow_offset (const char *val) return true; } +/* Set list of user-defined sections that need to be sanitized. */ + +void +set_sanitized_sections (const char *secs) +{ + sanitized_sections = secs; +} + +/* Checks whether section SEC should be sanitized. */ + +static bool +section_sanitized_p (const char *sec) +{ + if (!sanitized_sections) + return false; + size_t len = strlen (sec); + const char *p = sanitized_sections; + while ((p = strstr (p, sec))) + { + if ((p == sanitized_sections || p[-1] == ',') + && (p[len] == 0 || p[len] == ',')) + return true; + ++p; + } + return false; +} + /* Returns Asan shadow offset. */ static unsigned HOST_WIDE_INT @@ -1374,7 +1402,8 @@ asan_protect_global (tree decl) to be an array of such vars, putting padding in there breaks this assumption. */ || (DECL_SECTION_NAME (decl) != NULL - && !symtab_node::get (decl)->implicit_section) + && !symtab_node::get (decl)->implicit_section + && !section_sanitized_p (DECL_SECTION_NAME (decl))) || DECL_SIZE (decl) == 0 || ASAN_RED_ZONE_SIZE * BITS_PER_UNIT > MAX_OFILE_ALIGNMENT || !valid_constant_size_p (DECL_SIZE_UNIT (decl)) diff --git a/gcc/asan.h b/gcc/asan.h index 51fd9ccc380..10ffaca3b86 100644 --- a/gcc/asan.h +++ b/gcc/asan.h @@ -79,6 +79,8 @@ asan_red_zone_size (unsigned int size) extern bool set_asan_shadow_offset (const char *); +extern void set_sanitized_sections (const char *); + /* Return TRUE if builtin with given FCODE will be intercepted by libasan. */ diff --git a/gcc/common.opt b/gcc/common.opt index b49ac46610c..380848c7087 100644 --- a/gcc/common.opt +++ b/gcc/common.opt @@ -897,6 +897,11 @@ fasan-shadow-offset= Common Joined RejectNegative Var(common_deferred_options) Defer -fasan-shadow-offset= Use custom shadow memory offset. +fsanitize-sections= +Common Joined RejectNegative Var(common_deferred_options) Defer +-fsanitize-sections= Sanitize global variables +in user-defined sections. + fsanitize-recover= Common Report Joined After diagnosing undefined behavior attempt to continue execution diff --git a/gcc/doc/invoke.texi b/gcc/doc/invoke.texi index bb173854663..f5f79b81028 100644 --- a/gcc/doc/invoke.texi +++ b/gcc/doc/invoke.texi @@ -301,7 +301,8 @@ Objective-C and Objective-C++ Dialects}. @xref{Debugging Options,,Options for Debugging Your Program or GCC}. @gccoptlist{-d@var{letters} -dumpspecs -dumpmachine -dumpversion @gol -fsanitize=@var{style} -fsanitize-recover -fsanitize-recover=@var{style} @gol --fasan-shadow-offset=@var{number} -fsanitize-undefined-trap-on-error @gol +-fasan-shadow-offset=@var{number} -fsanitize-sections=@var{s1,s2,...} @gol +-fsanitize-undefined-trap-on-error @gol -fcheck-pointer-bounds -fchkp-check-incomplete-type @gol -fchkp-first-field-has-own-bounds -fchkp-narrow-bounds @gol -fchkp-narrow-to-innermost-array -fchkp-optimize @gol @@ -5803,6 +5804,10 @@ This option forces GCC to use custom shadow offset in AddressSanitizer checks. It is useful for experimenting with different shadow memory layouts in Kernel AddressSanitizer. +@item -fsanitize-sections=@var{s1,s2,...} +@opindex fsanitize-sections +Sanitize global variables in selected user-defined sections. + @item -fsanitize-recover@r{[}=@var{opts}@r{]} @opindex fsanitize-recover @opindex fno-sanitize-recover diff --git a/gcc/opts-global.c b/gcc/opts-global.c index b61bdcf3ccc..1035b8d14c6 100644 --- a/gcc/opts-global.c +++ b/gcc/opts-global.c @@ -458,6 +458,10 @@ handle_common_deferred_options (void) error ("unrecognized shadow offset %qs", opt->arg); break; + case OPT_fsanitize_sections_: + set_sanitized_sections (opt->arg); + break; + default: gcc_unreachable (); } diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 2bf85769dc6..b406be4797f 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,7 @@ +2015-04-17 Yury Gribov + + * c-c++-common/asan/user-section-1.c: New test. + 2015-04-17 Jakub Jelinek PR debug/65771 -- 2.30.2