AddressSanitizer.rst 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298
  1. ================
  2. AddressSanitizer
  3. ================
  4. .. contents::
  5. :local:
  6. Introduction
  7. ============
  8. AddressSanitizer is a fast memory error detector. It consists of a compiler
  9. instrumentation module and a run-time library. The tool can detect the
  10. following types of bugs:
  11. * Out-of-bounds accesses to heap, stack and globals
  12. * Use-after-free
  13. * Use-after-return (runtime flag `ASAN_OPTIONS=detect_stack_use_after_return=1`)
  14. * Use-after-scope (clang flag `-fsanitize-address-use-after-scope`)
  15. * Double-free, invalid free
  16. * Memory leaks (experimental)
  17. Typical slowdown introduced by AddressSanitizer is **2x**.
  18. How to build
  19. ============
  20. Build LLVM/Clang with `CMake <https://llvm.org/docs/CMake.html>`_.
  21. Usage
  22. =====
  23. Simply compile and link your program with ``-fsanitize=address`` flag. The
  24. AddressSanitizer run-time library should be linked to the final executable, so
  25. make sure to use ``clang`` (not ``ld``) for the final link step. When linking
  26. shared libraries, the AddressSanitizer run-time is not linked, so
  27. ``-Wl,-z,defs`` may cause link errors (don't use it with AddressSanitizer). To
  28. get a reasonable performance add ``-O1`` or higher. To get nicer stack traces
  29. in error messages add ``-fno-omit-frame-pointer``. To get perfect stack traces
  30. you may need to disable inlining (just use ``-O1``) and tail call elimination
  31. (``-fno-optimize-sibling-calls``).
  32. .. code-block:: console
  33. % cat example_UseAfterFree.cc
  34. int main(int argc, char **argv) {
  35. int *array = new int[100];
  36. delete [] array;
  37. return array[argc]; // BOOM
  38. }
  39. # Compile and link
  40. % clang++ -O1 -g -fsanitize=address -fno-omit-frame-pointer example_UseAfterFree.cc
  41. or:
  42. .. code-block:: console
  43. # Compile
  44. % clang++ -O1 -g -fsanitize=address -fno-omit-frame-pointer -c example_UseAfterFree.cc
  45. # Link
  46. % clang++ -g -fsanitize=address example_UseAfterFree.o
  47. If a bug is detected, the program will print an error message to stderr and
  48. exit with a non-zero exit code. AddressSanitizer exits on the first detected error.
  49. This is by design:
  50. * This approach allows AddressSanitizer to produce faster and smaller generated code
  51. (both by ~5%).
  52. * Fixing bugs becomes unavoidable. AddressSanitizer does not produce
  53. false alarms. Once a memory corruption occurs, the program is in an inconsistent
  54. state, which could lead to confusing results and potentially misleading
  55. subsequent reports.
  56. If your process is sandboxed and you are running on OS X 10.10 or earlier, you
  57. will need to set ``DYLD_INSERT_LIBRARIES`` environment variable and point it to
  58. the ASan library that is packaged with the compiler used to build the
  59. executable. (You can find the library by searching for dynamic libraries with
  60. ``asan`` in their name.) If the environment variable is not set, the process will
  61. try to re-exec. Also keep in mind that when moving the executable to another machine,
  62. the ASan library will also need to be copied over.
  63. Symbolizing the Reports
  64. =========================
  65. To make AddressSanitizer symbolize its output
  66. you need to set the ``ASAN_SYMBOLIZER_PATH`` environment variable to point to
  67. the ``llvm-symbolizer`` binary (or make sure ``llvm-symbolizer`` is in your
  68. ``$PATH``):
  69. .. code-block:: console
  70. % ASAN_SYMBOLIZER_PATH=/usr/local/bin/llvm-symbolizer ./a.out
  71. ==9442== ERROR: AddressSanitizer heap-use-after-free on address 0x7f7ddab8c084 at pc 0x403c8c bp 0x7fff87fb82d0 sp 0x7fff87fb82c8
  72. READ of size 4 at 0x7f7ddab8c084 thread T0
  73. #0 0x403c8c in main example_UseAfterFree.cc:4
  74. #1 0x7f7ddabcac4d in __libc_start_main ??:0
  75. 0x7f7ddab8c084 is located 4 bytes inside of 400-byte region [0x7f7ddab8c080,0x7f7ddab8c210)
  76. freed by thread T0 here:
  77. #0 0x404704 in operator delete[](void*) ??:0
  78. #1 0x403c53 in main example_UseAfterFree.cc:4
  79. #2 0x7f7ddabcac4d in __libc_start_main ??:0
  80. previously allocated by thread T0 here:
  81. #0 0x404544 in operator new[](unsigned long) ??:0
  82. #1 0x403c43 in main example_UseAfterFree.cc:2
  83. #2 0x7f7ddabcac4d in __libc_start_main ??:0
  84. ==9442== ABORTING
  85. If that does not work for you (e.g. your process is sandboxed), you can use a
  86. separate script to symbolize the result offline (online symbolization can be
  87. force disabled by setting ``ASAN_OPTIONS=symbolize=0``):
  88. .. code-block:: console
  89. % ASAN_OPTIONS=symbolize=0 ./a.out 2> log
  90. % projects/compiler-rt/lib/asan/scripts/asan_symbolize.py / < log | c++filt
  91. ==9442== ERROR: AddressSanitizer heap-use-after-free on address 0x7f7ddab8c084 at pc 0x403c8c bp 0x7fff87fb82d0 sp 0x7fff87fb82c8
  92. READ of size 4 at 0x7f7ddab8c084 thread T0
  93. #0 0x403c8c in main example_UseAfterFree.cc:4
  94. #1 0x7f7ddabcac4d in __libc_start_main ??:0
  95. ...
  96. Note that on macOS you may need to run ``dsymutil`` on your binary to have the
  97. file\:line info in the AddressSanitizer reports.
  98. Additional Checks
  99. =================
  100. Initialization order checking
  101. -----------------------------
  102. AddressSanitizer can optionally detect dynamic initialization order problems,
  103. when initialization of globals defined in one translation unit uses
  104. globals defined in another translation unit. To enable this check at runtime,
  105. you should set environment variable
  106. ``ASAN_OPTIONS=check_initialization_order=1``.
  107. Note that this option is not supported on macOS.
  108. Memory leak detection
  109. ---------------------
  110. For more information on leak detector in AddressSanitizer, see
  111. :doc:`LeakSanitizer`. The leak detection is turned on by default on Linux,
  112. and can be enabled using ``ASAN_OPTIONS=detect_leaks=1`` on macOS;
  113. however, it is not yet supported on other platforms.
  114. Issue Suppression
  115. =================
  116. AddressSanitizer is not expected to produce false positives. If you see one,
  117. look again; most likely it is a true positive!
  118. Suppressing Reports in External Libraries
  119. -----------------------------------------
  120. Runtime interposition allows AddressSanitizer to find bugs in code that is
  121. not being recompiled. If you run into an issue in external libraries, we
  122. recommend immediately reporting it to the library maintainer so that it
  123. gets addressed. However, you can use the following suppression mechanism
  124. to unblock yourself and continue on with the testing. This suppression
  125. mechanism should only be used for suppressing issues in external code; it
  126. does not work on code recompiled with AddressSanitizer. To suppress errors
  127. in external libraries, set the ``ASAN_OPTIONS`` environment variable to point
  128. to a suppression file. You can either specify the full path to the file or the
  129. path of the file relative to the location of your executable.
  130. .. code-block:: bash
  131. ASAN_OPTIONS=suppressions=MyASan.supp
  132. Use the following format to specify the names of the functions or libraries
  133. you want to suppress. You can see these in the error report. Remember that
  134. the narrower the scope of the suppression, the more bugs you will be able to
  135. catch.
  136. .. code-block:: bash
  137. interceptor_via_fun:NameOfCFunctionToSuppress
  138. interceptor_via_fun:-[ClassName objCMethodToSuppress:]
  139. interceptor_via_lib:NameOfTheLibraryToSuppress
  140. Conditional Compilation with ``__has_feature(address_sanitizer)``
  141. -----------------------------------------------------------------
  142. In some cases one may need to execute different code depending on whether
  143. AddressSanitizer is enabled.
  144. :ref:`\_\_has\_feature <langext-__has_feature-__has_extension>` can be used for
  145. this purpose.
  146. .. code-block:: c
  147. #if defined(__has_feature)
  148. # if __has_feature(address_sanitizer)
  149. // code that builds only under AddressSanitizer
  150. # endif
  151. #endif
  152. Disabling Instrumentation with ``__attribute__((no_sanitize("address")))``
  153. --------------------------------------------------------------------------
  154. Some code should not be instrumented by AddressSanitizer. One may use
  155. the attribute ``__attribute__((no_sanitize("address")))`` (which has
  156. deprecated synonyms `no_sanitize_address` and
  157. `no_address_safety_analysis`) to disable instrumentation of a
  158. particular function. This attribute may not be supported by other
  159. compilers, so we suggest to use it together with
  160. ``__has_feature(address_sanitizer)``.
  161. The same attribute used on a global variable prevents AddressSanitizer
  162. from adding redzones around it and detecting out of bounds accesses.
  163. Suppressing Errors in Recompiled Code (Blacklist)
  164. -------------------------------------------------
  165. AddressSanitizer supports ``src`` and ``fun`` entity types in
  166. :doc:`SanitizerSpecialCaseList`, that can be used to suppress error reports
  167. in the specified source files or functions. Additionally, AddressSanitizer
  168. introduces ``global`` and ``type`` entity types that can be used to
  169. suppress error reports for out-of-bound access to globals with certain
  170. names and types (you may only specify class or struct types).
  171. You may use an ``init`` category to suppress reports about initialization-order
  172. problems happening in certain source files or with certain global variables.
  173. .. code-block:: bash
  174. # Suppress error reports for code in a file or in a function:
  175. src:bad_file.cpp
  176. # Ignore all functions with names containing MyFooBar:
  177. fun:*MyFooBar*
  178. # Disable out-of-bound checks for global:
  179. global:bad_array
  180. # Disable out-of-bound checks for global instances of a given class ...
  181. type:Namespace::BadClassName
  182. # ... or a given struct. Use wildcard to deal with anonymous namespace.
  183. type:Namespace2::*::BadStructName
  184. # Disable initialization-order checks for globals:
  185. global:bad_init_global=init
  186. type:*BadInitClassSubstring*=init
  187. src:bad/init/files/*=init
  188. Suppressing memory leaks
  189. ------------------------
  190. Memory leak reports produced by :doc:`LeakSanitizer` (if it is run as a part
  191. of AddressSanitizer) can be suppressed by a separate file passed as
  192. .. code-block:: bash
  193. LSAN_OPTIONS=suppressions=MyLSan.supp
  194. which contains lines of the form `leak:<pattern>`. Memory leak will be
  195. suppressed if pattern matches any function name, source file name, or
  196. library name in the symbolized stack trace of the leak report. See
  197. `full documentation
  198. <https://github.com/google/sanitizers/wiki/AddressSanitizerLeakSanitizer#suppressions>`_
  199. for more details.
  200. Limitations
  201. ===========
  202. * AddressSanitizer uses more real memory than a native run. Exact overhead
  203. depends on the allocations sizes. The smaller the allocations you make the
  204. bigger the overhead is.
  205. * AddressSanitizer uses more stack memory. We have seen up to 3x increase.
  206. * On 64-bit platforms AddressSanitizer maps (but not reserves) 16+ Terabytes of
  207. virtual address space. This means that tools like ``ulimit`` may not work as
  208. usually expected.
  209. * Static linking of executables is not supported.
  210. Supported Platforms
  211. ===================
  212. AddressSanitizer is supported on:
  213. * Linux i386/x86\_64 (tested on Ubuntu 12.04)
  214. * macOS 10.7 - 10.11 (i386/x86\_64)
  215. * iOS Simulator
  216. * Android ARM
  217. * NetBSD i386/x86\_64
  218. * FreeBSD i386/x86\_64 (tested on FreeBSD 11-current)
  219. * Windows 8.1+ (i386/x86\_64)
  220. Ports to various other platforms are in progress.
  221. Current Status
  222. ==============
  223. AddressSanitizer is fully functional on supported platforms starting from LLVM
  224. 3.1. The test suite is integrated into CMake build and can be run with ``make
  225. check-asan`` command.
  226. The Windows port is functional and is used by Chrome and Firefox, but it is not
  227. as well supported as the other ports.
  228. More Information
  229. ================
  230. `<https://github.com/google/sanitizers/wiki/AddressSanitizer>`_