Message ID | 20171026195043.20704-1-n54@gmx.com |
---|---|
State | New |
Headers | show |
Series | [v3] Add asan and ubsan support on NetBSD/amd64 | expand |
On Thu, Oct 26, 2017 at 09:50:43PM +0200, Kamil Rytarowski wrote: > $ make check-asan > $ make check-asan-dynamic > $ make check-ubsan That is testing of the upstream code, not of GCC and the libsanitizer copy in GCC. What I'm more interested to hear is whether you've bootstrapped/regtested the gcc tree with this patch on x86_64-*-netbsd*, as per https://gcc.gnu.org/contribute.html I.e. ..../configure ...; make -jN bootstrap; make -jN -k check; ..../contrib/test_summary and from there if there are any */asan/* or */ubsan/* FAILs. > 2017-10-26 Kamil Rytarowski <n54@gmx.com> > > * sanitizer_common/Makefile.am (sanitizer_common_files): Add > sanitizer_platform_limits_netbsd.cc. > * sanitizer_common/Makefile.in: Regenerated. > * configure.tgt: Enable asan and ubsan on x86_64-*-netbsd*. Jakub
On 30.10.2017 08:24, Jakub Jelinek wrote: > On Thu, Oct 26, 2017 at 09:50:43PM +0200, Kamil Rytarowski wrote: >> $ make check-asan >> $ make check-asan-dynamic >> $ make check-ubsan > > That is testing of the upstream code, not of GCC and the libsanitizer > copy in GCC. What I'm more interested to hear is whether > you've bootstrapped/regtested the gcc tree with this patch on > x86_64-*-netbsd*, as per https://gcc.gnu.org/contribute.html > I.e. ..../configure ...; make -jN bootstrap; make -jN -k check; ..../contrib/test_summary > and from there if there are any */asan/* or */ubsan/* FAILs. > I've been executing GCC tests. Some/many tests were hanging and I was killing them after a longer period of time. There were certainly environment issues, like attempts to execute non-existent 'python' (in pkgsrc/NetBSD we version python to python2.7, python3.6 etc). http://netbsd.org/~kamil/gcc/test_summary.log.8-20171022.txt It looks like the tests complains for asan, and nothing complains for ubsan. I expect that the reporting issue in asan/GCC is generating these results. >> 2017-10-26 Kamil Rytarowski <n54@gmx.com> >> >> * sanitizer_common/Makefile.am (sanitizer_common_files): Add >> sanitizer_platform_limits_netbsd.cc. >> * sanitizer_common/Makefile.in: Regenerated. >> * configure.tgt: Enable asan and ubsan on x86_64-*-netbsd*. > > Jakub >
On Mon, Oct 30, 2017 at 09:01:25PM +0100, Kamil Rytarowski wrote: > On 30.10.2017 08:24, Jakub Jelinek wrote: > > On Thu, Oct 26, 2017 at 09:50:43PM +0200, Kamil Rytarowski wrote: > >> $ make check-asan > >> $ make check-asan-dynamic > >> $ make check-ubsan > > > > That is testing of the upstream code, not of GCC and the libsanitizer > > copy in GCC. What I'm more interested to hear is whether > > you've bootstrapped/regtested the gcc tree with this patch on > > x86_64-*-netbsd*, as per https://gcc.gnu.org/contribute.html > > I.e. ..../configure ...; make -jN bootstrap; make -jN -k check; ..../contrib/test_summary > > and from there if there are any */asan/* or */ubsan/* FAILs. > > > > I've been executing GCC tests. > > Some/many tests were hanging and I was killing them after a longer > period of time. There were certainly environment issues, like attempts > to execute non-existent 'python' (in pkgsrc/NetBSD we version python to > python2.7, python3.6 etc). > > http://netbsd.org/~kamil/gcc/test_summary.log.8-20171022.txt That seems that asan pretty much doesn't work at all in GCC for netbsd. A few FAILs might be acceptable, but so many FAILs certainly aren't. The testsuite doesn't use python, at least not for *san testing nor test_summary, so that shouldn't be the problem. If it is asan/ubsan tests that are hanging, that is something that needs to be debugged and understood why it hangs. You should look into ...objdir/gcc/testsuite/{gcc,g++}/{gcc,g++}.log for details on some short/simple tests and see what the problem is. Jakub
On 31.10.2017 14:22, Jakub Jelinek wrote: > On Mon, Oct 30, 2017 at 09:01:25PM +0100, Kamil Rytarowski wrote: >> On 30.10.2017 08:24, Jakub Jelinek wrote: >>> On Thu, Oct 26, 2017 at 09:50:43PM +0200, Kamil Rytarowski wrote: >>>> $ make check-asan >>>> $ make check-asan-dynamic >>>> $ make check-ubsan >>> >>> That is testing of the upstream code, not of GCC and the libsanitizer >>> copy in GCC. What I'm more interested to hear is whether >>> you've bootstrapped/regtested the gcc tree with this patch on >>> x86_64-*-netbsd*, as per https://gcc.gnu.org/contribute.html >>> I.e. ..../configure ...; make -jN bootstrap; make -jN -k check; ..../contrib/test_summary >>> and from there if there are any */asan/* or */ubsan/* FAILs. >>> >> >> I've been executing GCC tests. >> >> Some/many tests were hanging and I was killing them after a longer >> period of time. There were certainly environment issues, like attempts >> to execute non-existent 'python' (in pkgsrc/NetBSD we version python to >> python2.7, python3.6 etc). >> >> http://netbsd.org/~kamil/gcc/test_summary.log.8-20171022.txt > > That seems that asan pretty much doesn't work at all in GCC for netbsd. > A few FAILs might be acceptable, but so many FAILs certainly aren't. > The testsuite doesn't use python, at least not for *san testing nor > test_summary, so that shouldn't be the problem. If it is asan/ubsan tests > that are hanging, that is something that needs to be debugged and understood > why it hangs. > It is similar in LLVM, where it works against statically linked .a files with sanitizers. For .so, I can observe similar information about DEADLYSIGNAL without detailed information. I will try to fix it in LLVM first. I noted that FreeBSD people has similar issues, caused e.g. by the link order of libraries (libthr vs libc).. not sure what's the reason in NetBSD. > You should look into ...objdir/gcc/testsuite/{gcc,g++}/{gcc,g++}.log > for details on some short/simple tests and see what the problem is. > > Jakub > T
On Tue, Oct 31, 2017 at 02:53:26PM +0100, Kamil Rytarowski wrote: > >> http://netbsd.org/~kamil/gcc/test_summary.log.8-20171022.txt > > > > That seems that asan pretty much doesn't work at all in GCC for netbsd. > > A few FAILs might be acceptable, but so many FAILs certainly aren't. > > The testsuite doesn't use python, at least not for *san testing nor > > test_summary, so that shouldn't be the problem. If it is asan/ubsan tests > > that are hanging, that is something that needs to be debugged and understood > > why it hangs. > > > > It is similar in LLVM, where it works against statically linked .a files > with sanitizers. For .so, I can observe similar information about > DEADLYSIGNAL without detailed information. But dynamic linking of libasan or libubsan is the default in gcc, so it needs to work out of the box. Note gcc/config/gnu-user.h has: /* Link -lasan early on the command line. For -static-libasan, don't link it for -shared link, the executable should be compiled with -static-libasan in that case, and for executable link with --{,no-}whole-archive around it to force everything into the executable. And similarly for -ltsan and -llsan. */ #if defined(HAVE_LD_STATIC_DYNAMIC) #undef LIBASAN_EARLY_SPEC #define LIBASAN_EARLY_SPEC "%{!shared:libasan_preinit%O%s} " \ "%{static-libasan:%{!shared:" \ LD_STATIC_OPTION " --whole-archive -lasan --no-whole-archive " \ LD_DYNAMIC_OPTION "}}%{!static-libasan:-lasan}" #undef LIBTSAN_EARLY_SPEC #define LIBTSAN_EARLY_SPEC "%{!shared:libtsan_preinit%O%s} " \ "%{static-libtsan:%{!shared:" \ LD_STATIC_OPTION " --whole-archive -ltsan --no-whole-archive " \ LD_DYNAMIC_OPTION "}}%{!static-libtsan:-ltsan}" #undef LIBLSAN_EARLY_SPEC #define LIBLSAN_EARLY_SPEC "%{!shared:liblsan_preinit%O%s} " \ "%{static-liblsan:%{!shared:" \ LD_STATIC_OPTION " --whole-archive -llsan --no-whole-archive " \ LD_DYNAMIC_OPTION "}}%{!static-liblsan:-llsan}" #endif which might need to be duplicated into gcc/config/netbsd-elf.h. Jakub
On 31.10.2017 15:04, Jakub Jelinek wrote: > On Tue, Oct 31, 2017 at 02:53:26PM +0100, Kamil Rytarowski wrote: >>>> http://netbsd.org/~kamil/gcc/test_summary.log.8-20171022.txt >>> >>> That seems that asan pretty much doesn't work at all in GCC for netbsd. >>> A few FAILs might be acceptable, but so many FAILs certainly aren't. >>> The testsuite doesn't use python, at least not for *san testing nor >>> test_summary, so that shouldn't be the problem. If it is asan/ubsan tests >>> that are hanging, that is something that needs to be debugged and understood >>> why it hangs. >>> >> >> It is similar in LLVM, where it works against statically linked .a files >> with sanitizers. For .so, I can observe similar information about >> DEADLYSIGNAL without detailed information. > > But dynamic linking of libasan or libubsan is the default in gcc, so > it needs to work out of the box. > Note gcc/config/gnu-user.h has: > /* Link -lasan early on the command line. For -static-libasan, don't link > it for -shared link, the executable should be compiled with -static-libasan > in that case, and for executable link with --{,no-}whole-archive around > it to force everything into the executable. And similarly for -ltsan > and -llsan. */ > #if defined(HAVE_LD_STATIC_DYNAMIC) > #undef LIBASAN_EARLY_SPEC > #define LIBASAN_EARLY_SPEC "%{!shared:libasan_preinit%O%s} " \ > "%{static-libasan:%{!shared:" \ > LD_STATIC_OPTION " --whole-archive -lasan --no-whole-archive " \ > LD_DYNAMIC_OPTION "}}%{!static-libasan:-lasan}" > #undef LIBTSAN_EARLY_SPEC > #define LIBTSAN_EARLY_SPEC "%{!shared:libtsan_preinit%O%s} " \ > "%{static-libtsan:%{!shared:" \ > LD_STATIC_OPTION " --whole-archive -ltsan --no-whole-archive " \ > LD_DYNAMIC_OPTION "}}%{!static-libtsan:-ltsan}" > #undef LIBLSAN_EARLY_SPEC > #define LIBLSAN_EARLY_SPEC "%{!shared:liblsan_preinit%O%s} " \ > "%{static-liblsan:%{!shared:" \ > LD_STATIC_OPTION " --whole-archive -llsan --no-whole-archive " \ > LD_DYNAMIC_OPTION "}}%{!static-liblsan:-llsan}" > #endif > > which might need to be duplicated into gcc/config/netbsd-elf.h. > > Jakub > I'm giving it a try. I took the asan part and skipped "%{!shared:libasan_preinit%O%s} ". If I understand this correctly, it attempts to use the ELF section with preinit property in order to bootstrap asan quickly. The preinit sections are not enabled on NetBSD/amd64. From my understanding, there is a design choice in NetBSD to not include extensional sections unless they are requested by ABI. $NetBSD$ --- ./gcc/config/netbsd-elf.h.orig 2017-01-01 12:07:43.000000000 +0000 +++ ./gcc/config/netbsd-elf.h @@ -85,3 +85,16 @@ along with GCC; see the file COPYING3. #ifdef HAVE_LD_AS_NEEDED #define USE_LD_AS_NEEDED 1 #endif + +/* Link -lasan early on the command line. For -static-libasan, don't link + it for -shared link, the executable should be compiled with -static-libasan + in that case, and for executable link with --{,no-}whole-archive around + it to force everything into the executable. And similarly for -ltsan + and -llsan. */ +#if defined(HAVE_LD_STATIC_DYNAMIC) +#undef LIBASAN_EARLY_SPEC +#define LIBASAN_EARLY_SPEC \ + "%{static-libasan:%{!shared:" \ + LD_STATIC_OPTION " --whole-archive -lasan --no-whole-archive " \ + LD_DYNAMIC_OPTION "}}%{!static-libasan:-lasan}" +#endif
On Tue, Oct 31, 2017 at 07:28:23PM +0100, Kamil Rytarowski wrote: > I'm giving it a try. I took the asan part and skipped > "%{!shared:libasan_preinit%O%s} ". If I understand this correctly, it > attempts to use the ELF section with preinit property in order to > bootstrap asan quickly. The preinit sections are not enabled on > NetBSD/amd64. From my understanding, there is a design choice in NetBSD > to not include extensional sections unless they are requested by ABI. ?? SHT_PREINIT_ARRAY/DT_PREINIT_ARRAY/DT_PREINIT_ARRAYSZ is not any kind of extension, it is an integral part of the ELF gABI: http://www.sco.com/developers/gabi/latest/ch5.dynamic.html#dynamic_section And that is quite essential for proper asan behavior, because the library interposes a lot of functions and if they are invoked before the library is initialized, they crash (of course better would be to fix the library not to rely on that and initialize the minimal stuff needed for interposition if they are called before the initialization, but that is unlikely to happen upstream). Jakub
On 31.10.2017 19:45, Jakub Jelinek wrote: > On Tue, Oct 31, 2017 at 07:28:23PM +0100, Kamil Rytarowski wrote: >> I'm giving it a try. I took the asan part and skipped >> "%{!shared:libasan_preinit%O%s} ". If I understand this correctly, it >> attempts to use the ELF section with preinit property in order to >> bootstrap asan quickly. The preinit sections are not enabled on >> NetBSD/amd64. From my understanding, there is a design choice in NetBSD >> to not include extensional sections unless they are requested by ABI. > > ?? SHT_PREINIT_ARRAY/DT_PREINIT_ARRAY/DT_PREINIT_ARRAYSZ is not any > kind of extension, it is an integral part of the ELF gABI: > http://www.sco.com/developers/gabi/latest/ch5.dynamic.html#dynamic_section > And that is quite essential for proper asan behavior, because the library > interposes a lot of functions and if they are invoked before the library > is initialized, they crash (of course better would be to fix the library > not to rely on that and initialize the minimal stuff needed for > interposition if they are called before the initialization, but that is > unlikely to happen upstream). > > Jakub > Right now this is only Linux-specific at least in asan/LLVM. // We can use .preinit_array section on Linux to call sanitizer initialization // functions very early in the process startup (unless PIC macro is defined). // FIXME: do we have anything like this on Mac? #if SANITIZER_LINUX && !SANITIZER_ANDROID && !defined(PIC) # define SANITIZER_CAN_USE_PREINIT_ARRAY 1 #else # define SANITIZER_CAN_USE_PREINIT_ARRAY 0 #endif -- lib/sanitizer_common/sanitizer_internal_defs.h NetBSD needs to use different ways to initialize, like through interception of a call and during this stage bootstrap initialization bits. The tricky part is that we cannot initialize a sanitizer before sufficient libc+libpthread bootstrap and this is my current obstacle with tsan. Specifying new LIBASAN_EARLY_SPEC does not fix the "AddressSanitizer can not provide additional info." problem.
================================================================= ==20441==ERROR: AddressSanitizer: SEGV on unknown address 0x0ff07fff7cf0 (pc 0x000000400a8f bp 0x7f7fffffe7f0 sp 0x7f7fffffe770 T0) ==20441==The signal is caused by a WRITE memory access. #0 0x400a8e in main (/tmp/a+0x400a8e) #1 0x40090a in ___start (/tmp/a+0x40090a) AddressSanitizer can not provide additional info. SUMMARY: AddressSanitizer: SEGV (/tmp/a+0x400a8e) in main ==20441==ABORTING There is lack of additional info in asan when used with .so. This bug is not a show-stopper because a user still can get backtrace under debugger in the point of detected failure. This bug will be fixed in upstream LLVM sources and merged back to GCC in future merges from LLVM. 2017-10-26 Kamil Rytarowski <n54@gmx.com> * sanitizer_common/Makefile.am (sanitizer_common_files): Add sanitizer_platform_limits_netbsd.cc. * sanitizer_common/Makefile.in: Regenerated. * configure.tgt: Enable asan and ubsan on x86_64-*-netbsd*. --- libsanitizer/ChangeLog | 7 +++++++ libsanitizer/configure.tgt | 4 ++++ libsanitizer/sanitizer_common/Makefile.am | 2 +- libsanitizer/sanitizer_common/Makefile.in | 5 ++++- 4 files changed, 16 insertions(+), 2 deletions(-) diff --git a/libsanitizer/ChangeLog b/libsanitizer/ChangeLog index 63e71317cbf..097230ac5cf 100644 --- a/libsanitizer/ChangeLog +++ b/libsanitizer/ChangeLog @@ -1,3 +1,10 @@ +2017-10-26 Kamil Rytarowski <n54@gmx.com> + + * sanitizer_common/Makefile.am (sanitizer_common_files): Add + sanitizer_platform_limits_netbsd.cc. + * sanitizer_common/Makefile.in: Regenerated. + * configure.tgt: Enable asan and ubsan on x86_64-*-netbsd*. + 2017-10-20 Jakub Jelinek <jakub@redhat.com> PR sanitizer/82595 diff --git a/libsanitizer/configure.tgt b/libsanitizer/configure.tgt index 573e3b482e9..4c1f8e0bb27 100644 --- a/libsanitizer/configure.tgt +++ b/libsanitizer/configure.tgt @@ -55,6 +55,10 @@ case "${target}" in x86_64-*-darwin[1]* | i?86-*-darwin[1]*) TSAN_SUPPORTED=no ;; + x86_64-*-netbsd*) + TSAN_SUPPORTED=no + LSAN_SUPPORTED=no + ;; *) UNSUPPORTED=1 ;; diff --git a/libsanitizer/sanitizer_common/Makefile.am b/libsanitizer/sanitizer_common/Makefile.am index adaab4cee54..70563eded36 100644 --- a/libsanitizer/sanitizer_common/Makefile.am +++ b/libsanitizer/sanitizer_common/Makefile.am @@ -41,6 +41,7 @@ sanitizer_common_files = \ sanitizer_persistent_allocator.cc \ sanitizer_platform_limits_linux.cc \ sanitizer_platform_limits_posix.cc \ + sanitizer_platform_limits_netbsd.cc \ sanitizer_posix.cc \ sanitizer_posix_libcdep.cc \ sanitizer_printf.cc \ @@ -114,4 +115,3 @@ AM_MAKEFLAGS = \ MAKEOVERRIDES= ## ################################################################ - diff --git a/libsanitizer/sanitizer_common/Makefile.in b/libsanitizer/sanitizer_common/Makefile.in index b2acc5caf56..f05c181f0b1 100644 --- a/libsanitizer/sanitizer_common/Makefile.in +++ b/libsanitizer/sanitizer_common/Makefile.in @@ -91,7 +91,8 @@ am__objects_1 = sancov_flags.lo sanitizer_allocator.lo \ sanitizer_mac.lo sanitizer_mac_libcdep.lo \ sanitizer_persistent_allocator.lo \ sanitizer_platform_limits_linux.lo \ - sanitizer_platform_limits_posix.lo sanitizer_posix.lo \ + sanitizer_platform_limits_posix.lo \ + sanitizer_platform_limits_netbsd.lo sanitizer_posix.lo \ sanitizer_posix_libcdep.lo sanitizer_printf.lo \ sanitizer_procmaps_common.lo sanitizer_procmaps_freebsd.lo \ sanitizer_procmaps_linux.lo sanitizer_procmaps_mac.lo \ @@ -323,6 +324,7 @@ sanitizer_common_files = \ sanitizer_persistent_allocator.cc \ sanitizer_platform_limits_linux.cc \ sanitizer_platform_limits_posix.cc \ + sanitizer_platform_limits_netbsd.cc \ sanitizer_posix.cc \ sanitizer_posix_libcdep.cc \ sanitizer_printf.cc \ @@ -468,6 +470,7 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sanitizer_mac_libcdep.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sanitizer_persistent_allocator.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sanitizer_platform_limits_linux.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sanitizer_platform_limits_netbsd.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sanitizer_platform_limits_posix.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sanitizer_posix.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/sanitizer_posix_libcdep.Plo@am__quote@