| aizatsky | 9c8c5b0 | 2016-03-30 22:09:09 | [diff] [blame] | 1 | # libFuzzer Integration Reference |
| aizatsky | 88a677d | 2016-03-18 23:18:24 | [diff] [blame] | 2 | |
| Max Moroz | 9b37075 | 2018-03-20 22:05:32 | [diff] [blame] | 3 | ## Additional Sanitizer Configuration |
| Oliver Chang | d6ead47 | 2017-10-02 19:50:34 | [diff] [blame] | 4 | |
| 5 | ### MSan |
| 6 | |
| Jonathan Metzman | 15e88e7 | 2018-11-16 19:40:13 | [diff] [blame] | 7 | Memory Sanitizer (MSan) in Chromium only supports Ubuntu Precise/Trusty and not |
| 8 | Rodete. |
| 9 | Thus, our [reproduce tool] cannot reproduce bugs found using MSan. |
| 10 | You can try to reproduce them manually by using [these instructions] on how to |
| 11 | run MSan-instrumented code in docker. |
| Oliver Chang | d6ead47 | 2017-10-02 19:50:34 | [diff] [blame] | 12 | |
| 13 | ### UBSan |
| 14 | |
| Abhishek Arya | 9e4a72c | 2017-11-29 16:23:33 | [diff] [blame] | 15 | By default, UBSan does not crash when undefined behavior is detected. |
| 16 | To make it crash, the following option needs to be set in environment: |
| Oliver Chang | d6ead47 | 2017-10-02 19:50:34 | [diff] [blame] | 17 | ```bash |
| 18 | UBSAN_OPTIONS=halt_on_error=1 ./fuzzer <corpus_directory_or_single_testcase_path> |
| Oliver Chang | d6ead47 | 2017-10-02 19:50:34 | [diff] [blame] | 19 | ``` |
| Abhishek Arya | 9e4a72c | 2017-11-29 16:23:33 | [diff] [blame] | 20 | Other useful options are (also used by ClusterFuzz): |
| Oliver Chang | d6ead47 | 2017-10-02 19:50:34 | [diff] [blame] | 21 | ```bash |
| 22 | UBSAN_OPTIONS=symbolize=1:halt_on_error=1:print_stacktrace=1 ./fuzzer <corpus_directory_or_single_testcase_path> |
| 23 | ``` |
| 24 | |
| aizatsky | 62c7a84 | 2016-05-13 19:23:01 | [diff] [blame] | 25 | ## Supported Platforms and Configurations |
| 26 | |
| Oliver Chang | d6ead47 | 2017-10-02 19:50:34 | [diff] [blame] | 27 | ### Builder configurations |
| aizatsky | 62c7a84 | 2016-05-13 19:23:01 | [diff] [blame] | 28 | |
| Jonathan Metzman | 5f37d98 | 2019-01-03 17:39:02 | [diff] [blame] | 29 | The exact GN arguments that are used on our builders can be generated by running |
| 30 | (from Chromium's `src` directory): |
| Oliver Chang | d6ead47 | 2017-10-02 19:50:34 | [diff] [blame] | 31 | |
| 32 | | Builder | Description | |
| 33 | |---------|-------------| |
| Jonathan Metzman | 5f37d98 | 2019-01-03 17:39:02 | [diff] [blame] | 34 | |Linux ASan | `tools/mb/mb.py gen -m chromium.fuzz -b 'Libfuzzer Upload Linux ASan' out/libfuzzer` | |
| 35 | |Linux ASan (x86) | `tools/mb/mb.py gen -m chromium.fuzz -b 'Libfuzzer Upload Linux32 ASan' out/libfuzzer` | |
| 36 | |Linux ASan Debug | `tools/mb/mb.py gen -m chromium.fuzz -b 'Libfuzzer Upload Linux ASan Debug' out/libfuzzer` | |
| Jonathan Metzman | 9c73a7b | 2019-01-27 17:03:38 | [diff] [blame] | 37 | |Linux MSan[*](#MSan) | `tools/mb/mb.py gen -m chromium.fuzz -b 'Libfuzzer Upload Linux MSan' out/libfuzzer` | |
| 38 | |Linux UBSan[*](#UBSan)| `tools/mb/mb.py gen -m chromium.fuzz -b 'Libfuzzer Upload Linux UBSan' out/libfuzzer` | |
| Jonathan Metzman | 5f37d98 | 2019-01-03 17:39:02 | [diff] [blame] | 39 | |Chrome OS ASan | `tools/mb/mb.py gen -m chromium.fuzz -b 'Libfuzzer Upload Chrome OS ASan' out/libfuzzer` | |
| 40 | |Mac ASan | `tools/mb/mb.py gen -m chromium.fuzz -b 'Libfuzzer Upload Mac ASan' out/libfuzzer` | |
| 41 | |Windows ASan | `python tools\mb\mb.py gen -m chromium.fuzz -b "Libfuzzer Upload Windows ASan" out\libfuzzer` | |
| Jonathan Metzman | 9c73a7b | 2019-01-27 17:03:38 | [diff] [blame] | 42 | |Linux ASan V8 ARM Simulator[*](#ARM-and-ARM64)| `tools/mb/mb.py gen -m chromium.fuzz -b 'Libfuzzer Upload Linux32 V8-ARM ASan' out/libfuzzer` | |
| 43 | |Linux ASan V8 ARM64 Simulator[*](#ARM-and-ARM64)| `tools/mb/mb.py gen -m chromium.fuzz -b 'Libfuzzer Upload Linux V8-ARM64 ASan' out/libfuzzer` | |
| 44 | |Linux ASan Debug V8 ARM Simulator[*](#ARM-and-ARM64)| `tools/mb/mb.py gen -m chromium.fuzz -b 'Libfuzzer Upload Linux32 V8-ARM ASan Debug' out/libfuzzer` | |
| 45 | |Linux ASan Debug V8 ARM64 Simulator[*](#ARM-and-ARM64)| `tools/mb/mb.py gen -m chromium.fuzz -b 'Libfuzzer Upload Linux V8-ARM64 ASan Debug' out/libfuzzer` | |
| Oliver Chang | d6ead47 | 2017-10-02 19:50:34 | [diff] [blame] | 46 | |
| 47 | |
| 48 | ### Linux |
| Oliver Chang | 93dae57a | 2017-10-02 16:41:58 | [diff] [blame] | 49 | Linux is fully supported by libFuzzer and ClusterFuzz with following sanitizer |
| aizatsky | 62c7a84 | 2016-05-13 19:23:01 | [diff] [blame] | 50 | configurations: |
| 51 | |
| 52 | | GN Argument | Description | |
| 53 | |--------------|----| |
| 54 | | is_asan=true | enables [Address Sanitizer] to catch problems like buffer overruns. | |
| Oliver Chang | d6ead47 | 2017-10-02 19:50:34 | [diff] [blame] | 55 | | is_msan=true | enables [Memory Sanitizer] to catch problems like uninitialized reads. \[[*](#MSan)\] | |
| 56 | | is_ubsan_security=true | enables [Undefined Behavior Sanitizer] to catch undefined behavior like integer overflow. \[[*](#UBSan)\] | |
| aizatsky | 62c7a84 | 2016-05-13 19:23:01 | [diff] [blame] | 57 | |
| 58 | Configuration example: |
| 59 | |
| 60 | ```bash |
| 61 | # With address sanitizer |
| Jonathan Metzman | df29cec | 2018-10-11 23:12:41 | [diff] [blame] | 62 | gn gen out/libfuzzer '--args=use_libfuzzer=true is_asan=true' --check |
| aizatsky | 62c7a84 | 2016-05-13 19:23:01 | [diff] [blame] | 63 | ``` |
| 64 | |
| Jonathan Metzman | 5f37d98 | 2019-01-03 17:39:02 | [diff] [blame] | 65 | ### Linux x86 (32-bit) |
| 66 | Fuzzing targets built for x86 can discover bugs that are not found by x64 |
| 67 | builds. Linux x86 is supported by libFuzzer with `is_asan` configuration. |
| 68 | |
| 69 | Configuration example: |
| 70 | |
| 71 | ```bash |
| 72 | gn gen out/libfuzzer --args="use_libfuzzer=true is_asan=true host_cpu=\"x86\" target_cpu=\"x86\"" --check |
| 73 | ``` |
| 74 | |
| Jonathan Metzman | f8a8a42 | 2018-11-29 21:45:52 | [diff] [blame] | 75 | ### Chrome OS |
| 76 | Chrome OS is supported by libFuzzer with `is_asan` configuration. |
| 77 | |
| 78 | Configuration example: |
| 79 | |
| 80 | ```bash |
| 81 | gn gen out/libfuzzer '--args=use_libfuzzer=true is_asan=true target_os="chromeos"' --check |
| 82 | ``` |
| 83 | |
| 84 | To do a Chrome OS build on Linux (not just for libFuzzer), your `.gclient` file |
| 85 | must be configured appropriately, see the [Chrome OS build docs] for more |
| 86 | details. |
| 87 | |
| aizatsky | 62c7a84 | 2016-05-13 19:23:01 | [diff] [blame] | 88 | ### Mac |
| 89 | |
| Oliver Chang | 93dae57a | 2017-10-02 16:41:58 | [diff] [blame] | 90 | Mac is supported by libFuzzer with `is_asan` configuration. |
| aizatsky | 62c7a84 | 2016-05-13 19:23:01 | [diff] [blame] | 91 | |
| 92 | Configuration example: |
| 93 | |
| 94 | ```bash |
| Jonathan Metzman | df29cec | 2018-10-11 23:12:41 | [diff] [blame] | 95 | gn gen out/libfuzzer '--args=use_libfuzzer=true is_asan=true mac_deployment_target="10.7"' --check |
| aizatsky | 62c7a84 | 2016-05-13 19:23:01 | [diff] [blame] | 96 | ``` |
| 97 | |
| Jonathan Metzman | df29cec | 2018-10-11 23:12:41 | [diff] [blame] | 98 | ### Windows |
| 99 | |
| 100 | Windows is supported by libFuzzer with `is_asan` configuration. |
| 101 | |
| 102 | Configuration example: |
| 103 | |
| 104 | ```bash |
| Bruce Dawson | 3817e99 | 2018-10-31 23:36:55 | [diff] [blame] | 105 | gn gen out/libfuzzer "--args=use_libfuzzer=true is_asan=true is_debug=false is_component_build=false" --check |
| Jonathan Metzman | df29cec | 2018-10-11 23:12:41 | [diff] [blame] | 106 | ``` |
| 107 | |
| Marijn Kruisselbrink | d0b14c3ef | 2018-12-12 01:33:54 | [diff] [blame] | 108 | On Windows you must use `is_component_build=false` as libFuzzer does not support |
| Jonathan Metzman | df29cec | 2018-10-11 23:12:41 | [diff] [blame] | 109 | component builds on Windows. If you are using `is_asan=true` then you must use |
| 110 | `is_debug=false` as ASan does not support debug builds on Windows. |
| 111 | You may also want to consider using `symbol_level=1` which will reduce build |
| 112 | size by reducing symbol level to the level necessary for libFuzzer (useful |
| 113 | if building many fuzz targets). |
| 114 | |
| Jonathan Metzman | 9c73a7b | 2019-01-27 17:03:38 | [diff] [blame] | 115 | ### ARM and ARM64 |
| 116 | |
| 117 | The V8 ARM and ARM64 simulators are supported by libFuzzer with `is_asan` |
| 118 | configuration. Note that there is nothing special about these builds for non-V8 |
| 119 | fuzz targets. |
| 120 | |
| 121 | ARM configuration example: |
| 122 | |
| 123 | |
| 124 | ```bash |
| 125 | gn gen out/libfuzzer --args="use_libfuzzer=true is_asan=true host_cpu=\"x86\" target_cpu=\"x86\" v8_target_cpu=\"arm\"" --check |
| 126 | ``` |
| 127 | |
| 128 | ARM64 configuration example: |
| 129 | |
| 130 | ```bash |
| 131 | gn gen out/libfuzzer --args="use_libfuzzer=true is_asan=true target_cpu=\"x64\" v8_target_cpu=\"arm64\"" --check |
| 132 | ``` |
| 133 | |
| aizatsky | 88a677d | 2016-03-18 23:18:24 | [diff] [blame] | 134 | ## fuzzer_test GN Template |
| 135 | |
| aizatsky | 9c8c5b0 | 2016-03-30 22:09:09 | [diff] [blame] | 136 | Use `fuzzer_test` to define libFuzzer targets: |
| aizatsky | 88a677d | 2016-03-18 23:18:24 | [diff] [blame] | 137 | |
| 138 | ``` |
| 139 | fuzzer_test("my_fuzzer") { |
| 140 | ... |
| 141 | } |
| 142 | ``` |
| 143 | |
| 144 | Following arguments are supported: |
| 145 | |
| 146 | | Argument | Description | |
| 147 | |----------|-------------| |
| Max Moroz | 9b37075 | 2018-03-20 22:05:32 | [diff] [blame] | 148 | | `sources` | **required** list of fuzzer test source files | |
| 149 | | `deps` | fuzzer dependencies | |
| 150 | | `additional_configs` | additional GN configurations to be used for compilation | |
| 151 | | `dict` | a dictionary file for the fuzzer | |
| 152 | | `libfuzzer_options` | runtime options file for the fuzzer. See [Fuzzer Runtime Options](#Fuzzer-Runtime-Options) | |
| 153 | | `seed_corpus` | single directory containing test inputs, parsed recursively | |
| 154 | | `seed_corpuses` | multiple directories with the same purpose as `seed_corpus` | |
| Jonathan Metzman | 5f37d98 | 2019-01-03 17:39:02 | [diff] [blame] | 155 | | `libs` | additional libraries to link. Same as [libs] for gn targets. | |
| aizatsky | 88a677d | 2016-03-18 23:18:24 | [diff] [blame] | 156 | |
| 157 | |
| 158 | ## Fuzzer Runtime Options |
| 159 | |
| aizatsky | 9c8c5b0 | 2016-03-30 22:09:09 | [diff] [blame] | 160 | There are many different runtime options supported by libFuzzer. Options |
| aizatsky | 88a677d | 2016-03-18 23:18:24 | [diff] [blame] | 161 | are passed as command line arguments: |
| 162 | |
| 163 | ``` |
| 164 | ./fuzzer [-flag1=val1 [-flag2=val2 ...] ] [dir1 [dir2 ...] ] |
| 165 | ``` |
| 166 | |
| 167 | Most common flags are: |
| 168 | |
| 169 | | Flag | Description | |
| 170 | |------|-------------| |
| 171 | | max_len | Maximum length of test input. | |
| 172 | | timeout | Timeout of seconds. Units slower than this value will be reported as bugs. | |
| Brendon Tiszka | 96537005 | 2024-02-05 21:14:58 | [diff] [blame] | 173 | | rss_limit_mb | Memory usage limit in Mb, default 2048. Some Chrome targets, such as Blink, require more than the default to initialize. | |
| aizatsky | 88a677d | 2016-03-18 23:18:24 | [diff] [blame] | 174 | |
| Abhishek Arya | 9e4a72c | 2017-11-29 16:23:33 | [diff] [blame] | 175 | Full list of options can be found at [libFuzzer options] page and by running |
| aizatsky | 88a677d | 2016-03-18 23:18:24 | [diff] [blame] | 176 | the binary with `-help=1`. |
| 177 | |
| mmoroz | 062a4a6 | 2016-04-12 09:02:33 | [diff] [blame] | 178 | To specify these options for ClusterFuzz, list all parameters in |
| 179 | `libfuzzer_options` target attribute: |
| aizatsky | 88a677d | 2016-03-18 23:18:24 | [diff] [blame] | 180 | |
| 181 | ``` |
| mmoroz | 062a4a6 | 2016-04-12 09:02:33 | [diff] [blame] | 182 | fuzzer_test("my_fuzzer") { |
| 183 | ... |
| 184 | libfuzzer_options = [ |
| Max Moroz | c6fce8a | 2019-05-15 15:12:35 | [diff] [blame] | 185 | # Suppress stdout and stderr output (not recommended, as it may silence useful info). |
| 186 | "close_fd_mask=3", |
| mmoroz | 062a4a6 | 2016-04-12 09:02:33 | [diff] [blame] | 187 | ] |
| 188 | } |
| aizatsky | 88a677d | 2016-03-18 23:18:24 | [diff] [blame] | 189 | ``` |
| 190 | |
| Abhishek Arya | 9e4a72c | 2017-11-29 16:23:33 | [diff] [blame] | 191 | [libFuzzer options]: http://llvm.org/docs/LibFuzzer.html#options |
| aizatsky | 62c7a84 | 2016-05-13 19:23:01 | [diff] [blame] | 192 | [Address Sanitizer]: http://clang.llvm.org/docs/AddressSanitizer.html |
| 193 | [Memory Sanitizer]: http://clang.llvm.org/docs/MemorySanitizer.html |
| 194 | [Undefined Behavior Sanitizer]: http://clang.llvm.org/docs/UndefinedBehaviorSanitizer.html |
| Jonathan Metzman | 15e88e7 | 2018-11-16 19:40:13 | [diff] [blame] | 195 | [reproduce tool]: https://github.com/google/clusterfuzz-tools |
| 196 | [these instructions]: https://www.chromium.org/developers/testing/memorysanitizer#TOC-Running-on-other-distros-using-Docker |
| Jonathan Metzman | f8a8a42 | 2018-11-29 21:45:52 | [diff] [blame] | 197 | [Chrome OS build docs]: https://chromium.googlesource.com/chromium/src/+/HEAD/docs/chromeos_build_instructions.md#updating-your-gclient-config |
| Jonathan Metzman | 5f37d98 | 2019-01-03 17:39:02 | [diff] [blame] | 198 | [libs]: https://gn.googlesource.com/gn/+/master/docs/reference.md#libs |