Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to make AddressSanitizer not stop after one error (and other issues)

I'm running OS X, 10.8.5; I've installed llvm 3.4 via homebrew (clang version 3.4 (tags/RELEASE_34/final) ), and I'm building with -fsanitize=address. I can get asan working with simple demo programs, but when building against our codebase, I have several problems (although I'd really just like an answer to #1):

  1. 3rd party libraries are generating asan errors, and asan is terminating my app on the first occurrence. I would think that there would be some kind of (runtime/compile-time) option to tell asan to keep going after finding an error. Specifically, I see this:

    bash-3.2$ ASAN_SYMBOLIZER_PATH=/usr/local/Cellar/llvm34/3.4/lib/llvm-3.4/bin/llvm-symbolizer ./unit_test
    Start testing of PathTrieTest
    Config: Using QTest library 4.8.2, Qt 4.8.2
    PASS   : PathTrieTest::initTestCase()
    PASS   : PathTrieTest::pathTrieNodeTest()
    =================================================================
    ==76647==ERROR: AddressSanitizer: heap-buffer-overflow on address 0x61600019e588 at pc 0x10891ddd3 bp 0x11312ba90 sp 0x11312ba58
    WRITE of size 48830 at 0x61600019e588 thread T3
        #0 0x10891ddd2 in wrap_readdir_r (/usr/local/lib/llvm-3.4/lib/clang/3.4/lib/darwin/libclang_rt.asan_osx_dynamic.dylib+0x11dd2)
        #1 0x10ac23571 in QFileSystemIterator::advance(QFileSystemEntry&, QFileSystemMetaData&) (/Volumes/ToolChain/qt-4.8/lib/QtCore.framework/Versions/4/QtCore+0xef571)
        #2 0x10abd86d3 in QDirIteratorPrivate::advance() (/Volumes/ToolChain/qt-4.8/lib/QtCore.framework/Versions/4/QtCore+0xa46d3)
        #3 0x10abd7a7f in QDirIteratorPrivate::QDirIteratorPrivate(QFileSystemEntry const&, QStringList const&, QFlags<QDir::Filter>, QFlags<QDirIterator::IteratorFlag>, bool) (/Volumes/ToolChain/qt-4.8/lib/QtCore.framework/Versions/4/QtCore+0xa3a7f)
        #4 0x10abd8b68 in QDirIterator::QDirIterator(QDir const&, QFlags<QDirIterator::IteratorFlag>) (/Volumes/ToolChain/qt-4.8/lib/QtCore.framework/Versions/4/QtCore+0xa4b68)
        #5 0x10abd7609 in QDirPrivate::initFileLists(QDir const&) const (/Volumes/ToolChain/qt-4.8/lib/QtCore.framework/Versions/4/QtCore+0xa3609)
        #6 0x10abd5394 in QDir::count() const (/Volumes/ToolChain/qt-4.8/lib/QtCore.framework/Versions/4/QtCore+0xa1394)
        #7 0x1084c205d in get_count(QFileInfo&) /Users/stebro/dev_vm/ui/ui/fsinfoprovider.cpp:36
    ...
    

    This error doesn't cause the app to terminate when it's running unsanitized.

  2. I can't get code to link when using the -fsanitize=undefined (or -fsanitize=address,undefined) options. I am including the -fsanitize=undefined line on both my compile & link commands, but I get link errors such as:

        Undefined symbols for architecture x86_64:
          "typeinfo for __cxxabiv1::__class_type_info", referenced from:
              __ubsan::checkDynamicType(void*, void*, unsigned long) in libclang_rt.ubsan_osx.a(ubsan_type_hash.o)
              isDerivedFromAtOffset(__cxxabiv1::__class_type_info const*, __cxxabiv1::__class_type_info const*, long) in libclang_rt.ubsan_osx.a(ubsan_type_hash.o)
              findBaseAtOffset(__cxxabiv1::__class_type_info const*, long) in libclang_rt.ubsan_osx.a(ubsan_type_hash.o)
        "typeinfo for __cxxabiv1::__si_class_type_info", referenced from:
              isDerivedFromAtOffset(__cxxabiv1::__class_type_info const*, __cxxabiv1::__class_type_info const*, long) in libclang_rt.ubsan_osx.a(ubsan_type_hash.o)
              findBaseAtOffset(__cxxabiv1::__class_type_info const*, long) in libclang_rt.ubsan_osx.a(ubsan_type_hash.o)
        "typeinfo for __cxxabiv1::__vmi_class_type_info", referenced from:
              isDerivedFromAtOffset(__cxxabiv1::__class_type_info const*, __cxxabiv1::__class_type_info const*, long) in libclang_rt.ubsan_osx.a(ubsan_type_hash.o)
              findBaseAtOffset(__cxxabiv1::__class_type_info const*, long) in libclang_rt.ubsan_osx.a(ubsan_type_hash.o)
    
  3. I can't get blacklists to work, and -mllvm -asan-globals=0 or -mllvm -asan-stack=0 doesn't seem to work like I'd expect. For example, the latter don't suppress the generation of the error listed in #1 above, and creating a blacklist that looks like the one below doesn't suppress the errors either:

    fun:QDirPrivate::initFileLists
    fun:get_count
    fun:*opendir2*
    
  4. Finally, executables generated with these asan options cause lldb to crash. I'm using the lldb shipped with XCode 5 tools; there was no lldb deployed with the homebew llvm package, and I can't figure out how to build it. The build instructions enter link description here have a dead link that points to the source you're supposed to use; pulling the source directly from the svn repository, using:

    svn co http://llvm.org/svn/llvm-project/lldb/tags/RELEASE_34/final lldb
    

    results in code that doesn't compile (errors provided upon request).

like image 362
Steve Broberg Avatar asked Mar 27 '14 18:03

Steve Broberg


People also ask

How do I turn off AddressSanitizer?

AddressSanitizer can optionally detect stack use after return problems. This is available by default, or explicitly ( -fsanitize-address-use-after-return=runtime ). To disable this check at runtime, set the environment variable ASAN_OPTIONS=detect_stack_use_after_return=0 .

What is AddressSanitizer error?

AddressSanitizer is a fast memory error detector. It consists of a compiler instrumentation module and a run-time library. The tool can detect the following types of bugs: Out-of-bounds accesses to heap, stack and globals. Use-after-free.

How does ASan detect use-after-free?

Additionally, AddressSanitizer can detect use-after-free bugs. A use-after-free bug occurs when a program tries to read or write to memory that has already been freed. This is undefined behavior and can lead to corrupted data, incorrect results, and even program crashes.


2 Answers

You can build your project with -fsanitize=address -fsanitize-recover=address flags, and run with environment variable ASAN_OPTIONS=halt_on_error=0. Source: https://github.com/google/sanitizers/wiki/AddressSanitizer

like image 110
robert Avatar answered Oct 05 '22 15:10

robert


  1. Addressability bugs (especially memory corruptions like the OOB write you've mentioned) are usually severe enough to worry about. Ignoring them can't undo their effects, and the program is very likely to crash in a totally unrelated place after you've skipped a heap corruption. You can try to build your own Clang with checks in readdir_r disabled, but I'd try to fix the error in the first place.
  2. Can you please file a bug with reproduction steps at http://code.google.com/p/address-sanitizer ?
  3. Blacklists only disable addressability checks in the blacklisted functions by not instrumenting them, they do not check the stacks for certain frames. Your particular check occurs in a function interceptor compiled into the runtime library, so you can't even blacklist that. If the error in #1 is in some system library and can't be easily worked around we can look into adding a runtime option to disable the readdir_r checks.
  4. Again, a bug report will be appreciated.
like image 5
Glider Avatar answered Oct 05 '22 15:10

Glider