Hi! Another problem from the compiler side when working on the asan testsuite is that at higher -O* levels the __asan_report_* noreturn calls are cross-jumped, but the library relies on their locus to print accurrate locations when symbolized. Without it, asan might report an error completely elsewhere in a function.
This patch disables cross-jumping of such builtins. Alternatively, I could introduce some attribute (no_cross_jump?), ECF_NO_CROSS_JUMP, add those attributes to those builtins (and let users add those too to functions they wish), and look at ECF_NO_CROSS_JUMP instead during cross-jumping. 2012-12-05 Jakub Jelinek <ja...@redhat.com> * sanitizer.def: Add comment about importance of ordering of BUILT_IN_ASAN_REPORT* builtins. * cfgcleanup.c (old_insns_match_p): Don't cross-jump __asan_report_* builtins. --- gcc/sanitizer.def.jj 2012-12-04 14:19:36.000000000 +0100 +++ gcc/sanitizer.def 2012-12-05 09:38:01.205958515 +0100 @@ -29,6 +29,8 @@ along with GCC; see the file COPYING3. /* Address Sanitizer */ DEF_SANITIZER_BUILTIN(BUILT_IN_ASAN_INIT, "__asan_init", BT_FN_VOID, ATTR_NOTHROW_LEAF_LIST) +/* Do not reorder the BUILT_IN_ASAN_REPORT* builtins, e.g. cfgcleanup.c + relies on this order. */ DEF_SANITIZER_BUILTIN(BUILT_IN_ASAN_REPORT_LOAD1, "__asan_report_load1", BT_FN_VOID_PTR, ATTR_NORETURN_NOTHROW_LEAF_LIST) DEF_SANITIZER_BUILTIN(BUILT_IN_ASAN_REPORT_LOAD2, "__asan_report_load2", --- gcc/cfgcleanup.c.jj 2012-11-20 09:37:47.000000000 +0100 +++ gcc/cfgcleanup.c 2012-12-05 09:37:23.389181984 +0100 @@ -1138,6 +1138,28 @@ old_insns_match_p (int mode ATTRIBUTE_UN CALL_INSN_FUNCTION_USAGE (i2)) || SIBLING_CALL_P (i1) != SIBLING_CALL_P (i2)) return dir_none; + + /* For address sanitizer, never crossjump __asan_report_* builtins, + otherwise errors might be reported on incorrect lines. */ + if (flag_asan) + { + rtx call = get_call_rtx_from (i1); + if (call && GET_CODE (XEXP (XEXP (call, 0), 0)) == SYMBOL_REF) + { + rtx symbol = XEXP (XEXP (call, 0), 0); + if (SYMBOL_REF_DECL (symbol) + && TREE_CODE (SYMBOL_REF_DECL (symbol)) == FUNCTION_DECL) + { + if ((DECL_BUILT_IN_CLASS (SYMBOL_REF_DECL (symbol)) + == BUILT_IN_NORMAL) + && DECL_FUNCTION_CODE (SYMBOL_REF_DECL (symbol)) + >= BUILT_IN_ASAN_REPORT_LOAD1 + && DECL_FUNCTION_CODE (SYMBOL_REF_DECL (symbol)) + <= BUILT_IN_ASAN_REPORT_STORE16) + return dir_none; + } + } + } } #ifdef STACK_REGS Jakub