From: Ilya Leoshkevich Date: Mon, 13 Feb 2023 16:45:51 +0000 (+0100) Subject: configure: Add --enable-sanitize-memory X-Git-Tag: elfutils-0.189~20 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=3fa98a6f29b0f370e32549ead7eb897c839af980;p=thirdparty%2Felfutils.git configure: Add --enable-sanitize-memory Add support for clang Memory Sanitizer [1], which detects the usage of uninitialized values. While elfutils itself is already checked with valgrind, checking code that depends on elfutils requires elfutils to be built with MSan. MSan is not linked into shared libraries, and is linked into executables statically. Therefore, unlike the other sanitizers, MSan needs to be configured fairly early, since we need to drop -D_FORTIFY_SOURCE [2], -Wl,-z,defs and --no-undefined. Disable a few tests that run for more than 5 minutes due to test files being statically linked with MSan. [1] https://clang.llvm.org/docs/MemorySanitizer.html [2] https://github.com/google/sanitizers/issues/247 Signed-off-by: Ilya Leoshkevich --- diff --git a/configure.ac b/configure.ac index 4efb2a9c4..189519471 100644 --- a/configure.ac +++ b/configure.ac @@ -155,6 +155,29 @@ AC_SUBST([fpie_CFLAGS]) dso_LDFLAGS="-shared" +NO_UNDEFINED=-Wl,--no-undefined +AC_ARG_ENABLE([sanitize-memory], + AS_HELP_STRING([--enable-sanitize-memory], + [Use clang memory sanitizer]), + [use_msan=$enableval], [use_msan=no]) +if test "$use_msan" = yes; then + old_CFLAGS="$CFLAGS" + old_CXXFLAGS="$CXXFLAGS" + old_LDFLAGS="$LDFLAGS" + # -fsanitize=memory is not compatible with -D_FORTIFY_SOURCE, -Wl,-z,defs and --no-undefined + CFLAGS="$CFLAGS -fsanitize=memory -fsanitize-memory-track-origins -D_FORTIFY_SOURCE=0" + CXXFLAGS="$CXXFLAGS -fsanitize=memory -fsanitize-memory-track-origins -D_FORTIFY_SOURCE=0" + LDFLAGS="-shared" + AC_LINK_IFELSE([AC_LANG_SOURCE([int main (int argc, char **argv) { return 0; }])], use_msan=yes, use_msan=no) + AS_IF([test "x$use_msan" == xyes], + ac_cv_zdefs=no NO_UNDEFINED=, + AC_MSG_WARN([clang memory sanitizer not available]) + CFLAGS="$old_CFLAGS" CXXFLAGS="$old_CXXFLAGS") + LDFLAGS="$old_LDFLAGS" +fi +AC_SUBST(NO_UNDEFINED) +AM_CONDITIONAL(USE_MEMORY_SANITIZER, test "$use_msan" = yes) + ZDEFS_LDFLAGS="-Wl,-z,defs" AC_CACHE_CHECK([whether gcc supports $ZDEFS_LDFLAGS], ac_cv_zdefs, [dnl save_LDFLAGS="$LDFLAGS" @@ -894,6 +917,7 @@ AC_MSG_NOTICE([ run all tests under valgrind : ${use_valgrind} gcc undefined behaviour sanitizer : ${use_undefined} gcc address sanitizer : ${use_address} + clang memory sanitizer : ${use_msan} use rpath in tests : ${tests_use_rpath} test biarch : ${utrace_cv_cc_biarch} ]) diff --git a/debuginfod/Makefile.am b/debuginfod/Makefile.am index f27d6e2ea..125be97bb 100644 --- a/debuginfod/Makefile.am +++ b/debuginfod/Makefile.am @@ -102,7 +102,8 @@ endif $(LIBDEBUGINFOD_SONAME): $(srcdir)/libdebuginfod.map $(libdebuginfod_so_LIBS) $(AM_V_CCLD)$(LINK) $(dso_LDFLAGS) -o $@ \ -Wl,--soname,$(LIBDEBUGINFOD_SONAME) \ - -Wl,--version-script,$<,--no-undefined \ + -Wl,--version-script,$< \ + $(NO_UNDEFINED) \ -Wl,--whole-archive $(libdebuginfod_so_LIBS) -Wl,--no-whole-archive \ $(libdebuginfod_so_LDLIBS) @$(textrel_check) diff --git a/libasm/Makefile.am b/libasm/Makefile.am index c2b548115..1e6b63e83 100644 --- a/libasm/Makefile.am +++ b/libasm/Makefile.am @@ -64,7 +64,8 @@ libasm_so_LIBS = libasm_pic.a libasm.so: $(srcdir)/libasm.map $(libasm_so_LIBS) $(libasm_so_DEPS) $(AM_V_CCLD)$(LINK) $(dso_LDFLAGS) -o $@ \ -Wl,--soname,$@.$(VERSION) \ - -Wl,--version-script,$<,--no-undefined \ + -Wl,--version-script,$< \ + $(NO_UNDEFINED) \ -Wl,--whole-archive $(libasm_so_LIBS) -Wl,--no-whole-archive \ $(libasm_so_LDLIBS) @$(textrel_check) diff --git a/libdw/Makefile.am b/libdw/Makefile.am index 1b6fead4b..e548f38c9 100644 --- a/libdw/Makefile.am +++ b/libdw/Makefile.am @@ -114,7 +114,8 @@ libdw_so_LDLIBS = $(libdw_so_DEPS) -ldl -lz $(argp_LDADD) $(fts_LIBS) $(obstack_ libdw.so: $(srcdir)/libdw.map $(libdw_so_LIBS) $(libdw_so_DEPS) $(AM_V_CCLD)$(LINK) $(dso_LDFLAGS) -o $@ \ -Wl,--soname,$@.$(VERSION),--enable-new-dtags \ - -Wl,--version-script,$<,--no-undefined \ + -Wl,--version-script,$< \ + $(NO_UNDEFINED) \ -Wl,--whole-archive $(libdw_so_LIBS) -Wl,--no-whole-archive \ $(libdw_so_LDLIBS) @$(textrel_check) diff --git a/libelf/Makefile.am b/libelf/Makefile.am index 24c25cf8d..aabce43ec 100644 --- a/libelf/Makefile.am +++ b/libelf/Makefile.am @@ -115,7 +115,8 @@ libelf_so_LIBS = libelf_pic.a libelf.so: $(srcdir)/libelf.map $(libelf_so_LIBS) $(libelf_so_DEPS) $(AM_V_CCLD)$(LINK) $(dso_LDFLAGS) -o $@ \ -Wl,--soname,$@.$(VERSION) \ - -Wl,--version-script,$<,--no-undefined \ + -Wl,--version-script,$< \ + $(NO_UNDEFINED) \ -Wl,--whole-archive $(libelf_so_LIBS) -Wl,--no-whole-archive \ $(libelf_so_LDLIBS) @$(textrel_check) diff --git a/tests/Makefile.am b/tests/Makefile.am index efbb4e637..fd58bf849 100644 --- a/tests/Makefile.am +++ b/tests/Makefile.am @@ -88,12 +88,16 @@ endif # test_nlist checks its own symbol table, and expects various symbols # to be in the order as specified in the source file. Explicitly set -# minimal CFLAGS. But add address sanitizer if in use. +# minimal CFLAGS. But add sanitizers if in use. if USE_ADDRESS_SANITIZER EXTRA_NLIST_CFLAGS=-fsanitize=address else +if USE_MEMORY_SANITIZER +EXTRA_NLIST_CFLAGS=-fsanitize=memory -fsanitize-memory-track-origins +else EXTRA_NLIST_CFLAGS= endif +endif test-nlist$(EXEEXT): test-nlist.c $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) \ @@ -225,6 +229,10 @@ if USE_ZSTD_COMPRESS export ELFUTILS_ZSTD = 1 endif +if USE_MEMORY_SANITIZER +export ELFUTILS_MEMORY_SANITIZER = 1 +endif + if DEBUGINFOD check_PROGRAMS += debuginfod_build_id_find # With the dummy delegation doesn't work diff --git a/tests/run-readelf-self.sh b/tests/run-readelf-self.sh index 7ffb35779..f5984597e 100755 --- a/tests/run-readelf-self.sh +++ b/tests/run-readelf-self.sh @@ -17,5 +17,10 @@ . $srcdir/test-subr.sh +if test -n "$ELFUTILS_MEMORY_SANITIZER"; then + echo "binaries linked with memory sanitizer are too big" + exit 77 +fi + # Just makes sure readelf doesn't crash testrun_on_self_quiet ${abs_top_builddir}/src/readelf -a -w diff --git a/tests/run-strip-reloc.sh b/tests/run-strip-reloc.sh index 033ed2785..02e626af9 100755 --- a/tests/run-strip-reloc.sh +++ b/tests/run-strip-reloc.sh @@ -17,6 +17,11 @@ . $srcdir/test-subr.sh +if test -n "$ELFUTILS_MEMORY_SANITIZER"; then + echo "binaries linked with memory sanitizer are too big" + exit 77 +fi + testfiles hello_i386.ko hello_x86_64.ko hello_ppc64.ko hello_s390.ko \ hello_aarch64.ko hello_m68k.ko hello_riscv64.ko hello_csky.ko \ hello_arc_hs4.ko diff --git a/tests/run-varlocs-self.sh b/tests/run-varlocs-self.sh index 5454fc701..760fe4d7e 100755 --- a/tests/run-varlocs-self.sh +++ b/tests/run-varlocs-self.sh @@ -17,6 +17,11 @@ . $srcdir/test-subr.sh +if test -n "$ELFUTILS_MEMORY_SANITIZER"; then + echo "binaries linked with memory sanitizer are too big" + exit 77 +fi + # Make sure varlocs doesn't crash, doesn't trigger self-check/asserts # or leaks running under valgrind. testrun_on_self_exe ${abs_top_builddir}/tests/varlocs -e