<div dir="auto">Awesome! Thanks for this!</div><div class="gmail_extra"><br><div class="gmail_quote">On Oct 11, 2017 6:44 PM, "Justin Bogner via llvm-commits" <<a href="mailto:llvm-commits@lists.llvm.org">llvm-commits@lists.llvm.org</a>> wrote:<br type="attribution"><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Author: bogner<br>
Date: Wed Oct 11 18:44:24 2017<br>
New Revision: 315544<br>
<br>
URL: <a href="http://llvm.org/viewvc/llvm-project?rev=315544&view=rev" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-<wbr>project?rev=315544&view=rev</a><br>
Log:<br>
docs: Add some information about Fuzzing LLVM itself<br>
<br>
This splits some content out of the libFuzzer docs and adds a fair<br>
amount of detail about the fuzzers in LLVM.<br>
<br>
Added:<br>
    llvm/trunk/docs/FuzzingLLVM.<wbr>rst<br>
Modified:<br>
    llvm/trunk/docs/LibFuzzer.rst<br>
    llvm/trunk/docs/index.rst<br>
<br>
Added: llvm/trunk/docs/FuzzingLLVM.<wbr>rst<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/FuzzingLLVM.rst?rev=315544&view=auto" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-<wbr>project/llvm/trunk/docs/<wbr>FuzzingLLVM.rst?rev=315544&<wbr>view=auto</a><br>
==============================<wbr>==============================<wbr>==================<br>
--- llvm/trunk/docs/FuzzingLLVM.<wbr>rst (added)<br>
+++ llvm/trunk/docs/FuzzingLLVM.<wbr>rst Wed Oct 11 18:44:24 2017<br>
@@ -0,0 +1,221 @@<br>
+=============================<wbr>===<br>
+Fuzzing LLVM libraries and tools<br>
+=============================<wbr>===<br>
+<br>
+.. contents::<br>
+   :local:<br>
+   :depth: 2<br>
+<br>
+Introduction<br>
+============<br>
+<br>
+The LLVM tree includes a number of fuzzers for various components. These are<br>
+built on top of :doc:`LibFuzzer <LibFuzzer>`.<br>
+<br>
+<br>
+Available Fuzzers<br>
+=================<br>
+<br>
+clang-fuzzer<br>
+------------<br>
+<br>
+A |generic fuzzer| that tries to compile textual input as C++ code. Some of the<br>
+bugs this fuzzer has reported are `on bugzilla <<a href="https://llvm.org/pr23057" rel="noreferrer" target="_blank">https://llvm.org/pr23057</a>>`__<br>
+and `on OSS Fuzz's tracker<br>
+<<a href="https://bugs.chromium.org/p/oss-fuzz/issues/list?q=proj-llvm+clang-fuzzer" rel="noreferrer" target="_blank">https://bugs.chromium.org/p/<wbr>oss-fuzz/issues/list?q=proj-<wbr>llvm+clang-fuzzer</a>>`__.<br>
+<br>
+clang-proto-fuzzer<br>
+------------------<br>
+<br>
+A |protobuf fuzzer| that compiles valid C++ programs generated from a protobuf<br>
+class that describes a subset of the C++ language.<br>
+<br>
+This fuzzer accepts clang command line options after `ignore_remaining_args=1`.<br>
+For example, the following command will fuzz clang with a higher optimization<br>
+level:<br>
+<br>
+.. code-block:: shell<br>
+<br>
+   % bin/clang-proto-fuzzer <corpus-dir> -ignore_remaining_args=1 -O3<br>
+<br>
+clang-format-fuzzer<br>
+-------------------<br>
+<br>
+A |generic fuzzer| that runs clang-format_ on C++ text fragments. Some of the<br>
+bugs this fuzzer has reported are `on bugzilla <<a href="https://llvm.org/pr23052" rel="noreferrer" target="_blank">https://llvm.org/pr23052</a>>`__<br>
+and `on OSS Fuzz's tracker<br>
+<<a href="https://bugs.chromium.org/p/oss-fuzz/issues/list?q=proj-llvm+clang-format-fuzzer`__" rel="noreferrer" target="_blank">https://bugs.chromium.org/p/<wbr>oss-fuzz/issues/list?q=proj-<wbr>llvm+clang-format-fuzzer`__</a>.<br>
+<br>
+.. _clang-format: <a href="https://clang.llvm.org/docs/ClangFormat.html" rel="noreferrer" target="_blank">https://clang.llvm.org/docs/<wbr>ClangFormat.html</a><br>
+<br>
+llvm-as-fuzzer<br>
+--------------<br>
+<br>
+A |generic fuzzer| that tries to parse text as :doc:`LLVM assembly <LangRef>`.<br>
+Some of the bugs this fuzzer has reported are `on bugzilla<br>
+<<a href="https://llvm.org/pr24639" rel="noreferrer" target="_blank">https://llvm.org/pr24639</a>>`__<br>
+<br>
+llvm-dwarfdump-fuzzer<br>
+---------------------<br>
+<br>
+A |generic fuzzer| that interprets inputs as object files and runs<br>
+:doc:`llvm-dwarfdump <CommandGuide/llvm-dwarfdump>` on them. Some of the bugs<br>
+this fuzzer has reported are `on OSS Fuzz's tracker<br>
+<<a href="https://bugs.chromium.org/p/oss-fuzz/issues/list?q=proj-llvm+llvm-dwarfdump-fuzzer`__" rel="noreferrer" target="_blank">https://bugs.chromium.org/p/<wbr>oss-fuzz/issues/list?q=proj-<wbr>llvm+llvm-dwarfdump-fuzzer`__</a>.<br>
+<br>
+llvm-isel-fuzzer<br>
+----------------<br>
+<br>
+A |LLVM IR fuzzer| aimed at finding bugs in instruction selection.<br>
+<br>
+This fuzzer accepts flags after `ignore_remaining_args=1`. The flags match<br>
+those of :doc:`llc <CommandGuide/llc>` and the triple is required. For example,<br>
+the following command would fuzz AArch64 with :doc:`GlobalISel`:<br>
+<br>
+.. code-block:: shell<br>
+<br>
+   % bin/llvm-isel-fuzzer <corpus-dir> -ignore_remaining_args=1 -mtriple aarch64 -global-isel -O0<br>
+<br>
+llvm-mc-assemble-fuzzer<br>
+-----------------------<br>
+<br>
+A |generic fuzzer| that fuzzes the MC layer's assemblers by treating inputs as<br>
+target specific assembly.<br>
+<br>
+Note that this fuzzer has an unusual command line interface which is not fully<br>
+compatible with all of libFuzzer's features. Fuzzer arguments must be passed<br>
+after ``--fuzzer-args``, and any ``llc`` flags must use two dashes. For<br>
+example, to fuzz the AArch64 assembler you might use the following command:<br>
+<br>
+.. code-block:: console<br>
+<br>
+  llvm-mc-fuzzer --triple=aarch64-linux-gnu --fuzzer-args -max_len=4<br>
+<br>
+This scheme will likely change in the future.<br>
+<br>
+llvm-mc-disassemble-fuzzer<br>
+--------------------------<br>
+<br>
+A |generic fuzzer| that fuzzes the MC layer's disassemblers by treating inputs<br>
+as assembled binary data.<br>
+<br>
+Note that this fuzzer has an unusual command line interface which is not fully<br>
+compatible with all of libFuzzer's features. See the notes above about<br>
+``llvm-mc-assemble-fuzzer`` for details.<br>
+<br>
+<br>
+.. |generic fuzzer| replace:: :ref:`generic fuzzer <fuzzing-llvm-generic>`<br>
+.. |protobuf fuzzer|<br>
+   replace:: :ref:`libprotobuf-mutator based fuzzer <fuzzing-llvm-protobuf>`<br>
+.. |LLVM IR fuzzer|<br>
+   replace:: :ref:`structured LLVM IR fuzzer <fuzzing-llvm-ir>`<br>
+<br>
+<br>
+Mutators and Input Generators<br>
+=============================<br>
+<br>
+The inputs for a fuzz target are generated via random mutations of a<br>
+:ref:`corpus <libfuzzer-corpus>`. There are a few options for the kinds of<br>
+mutations that a fuzzer in LLVM might want.<br>
+<br>
+.. _fuzzing-llvm-generic:<br>
+<br>
+Generic Random Fuzzing<br>
+----------------------<br>
+<br>
+The most basic form of input mutation is to use the built in mutators of<br>
+LibFuzzer. These simply treat the input corpus as a bag of bits and make random<br>
+mutations. This type of fuzzer is good for stressing the surface layers of a<br>
+program, and is good at testing things like lexers, parsers, or binary<br>
+protocols.<br>
+<br>
+Some of the in-tree fuzzers that use this type of mutator are `clang-fuzzer`_,<br>
+`clang-format-fuzzer`_, `llvm-as-fuzzer`_, `llvm-dwarfdump-fuzzer`_,<br>
+`llvm-mc-assemble-fuzzer`_, and `llvm-mc-disassemble-fuzzer`_.<br>
+<br>
+.. _fuzzing-llvm-protobuf:<br>
+<br>
+Structured Fuzzing using ``libprotobuf-mutator``<br>
+-----------------------------<wbr>-------------------<br>
+<br>
+We can use libprotobuf-mutator_ in order to perform structured fuzzing and<br>
+stress deeper layers of programs. This works by defining a protobuf class that<br>
+translates arbitrary data into structurally interesting input. Specifically, we<br>
+use this to work with a subset of the C++ language and perform mutations that<br>
+produce valid C++ programs in order to exercise parts of clang that are more<br>
+interesting than parser error handling.<br>
+<br>
+To build this kind of fuzzer you need `protobuf`_ and its dependencies<br>
+installed, and you need to specify some extra flags when configuring the build<br>
+with :doc:`CMake <CMake>`. For example, `clang-proto-fuzzer`_ can be enabled by<br>
+adding ``-DCLANG_ENABLE_PROTO_FUZZER=<wbr>ON`` to the flags described in<br>
+:ref:`building-fuzzers`.<br>
+<br>
+The only in-tree fuzzer that uses ``libprotobuf-mutator`` today is<br>
+`clang-proto-fuzzer`_.<br>
+<br>
+.. _libprotobuf-mutator: <a href="https://github.com/google/libprotobuf-mutator" rel="noreferrer" target="_blank">https://github.com/google/<wbr>libprotobuf-mutator</a><br>
+.. _protobuf: <a href="https://github.com/google/protobuf" rel="noreferrer" target="_blank">https://github.com/google/<wbr>protobuf</a><br>
+<br>
+.. _fuzzing-llvm-ir:<br>
+<br>
+Structured Fuzzing of LLVM IR<br>
+-----------------------------<br>
+<br>
+We also use a more direct form of structured fuzzing for fuzzers that take<br>
+:doc:`LLVM IR <LangRef>` as input. This is achieved through the ``FuzzMutate``<br>
+library, which was `discussed at EuroLLVM 2017`_.<br>
+<br>
+The ``FuzzMutate`` library is used to structurally fuzz backends in<br>
+`llvm-isel-fuzzer`_.<br>
+<br>
+.. _discussed at EuroLLVM 2017: <a href="https://www.youtube.com/watch?v=UBbQ_s6hNgg" rel="noreferrer" target="_blank">https://www.youtube.com/watch?<wbr>v=UBbQ_s6hNgg</a><br>
+<br>
+<br>
+Building and Running<br>
+====================<br>
+<br>
+.. _building-fuzzers:<br>
+<br>
+Configuring LLVM to Build Fuzzers<br>
+-----------------------------<wbr>----<br>
+<br>
+Fuzzers will be built and linked to libFuzzer by default as long as you build<br>
+LLVM with sanitizer coverage enabled. You would typically also enable at least<br>
+one sanitizer for the fuzzers to be particularly likely, so the most common way<br>
+to build the fuzzers is by adding the following two flags to your CMake<br>
+invocation: ``-DLLVM_USE_SANITIZER=Address -DLLVM_USE_SANITIZE_COVERAGE=<wbr>On``.<br>
+<br>
+.. note:: If you have ``compiler-rt`` checked out in an LLVM tree when building<br>
+          with sanitizers, you'll want to specify ``-DLLVM_BUILD_RUNTIME=Off``<br>
+          to avoid building the sanitizers themselves with sanitizers enabled.<br>
+<br>
+Continuously Running and Finding Bugs<br>
+-----------------------------<wbr>--------<br>
+<br>
+There used to be a public buildbot running LLVM fuzzers continuously, and while<br>
+this did find issues, it didn't have a very good way to report problems in an<br>
+actionable way. Because of this, we're moving towards using `OSS Fuzz`_ more<br>
+instead.<br>
+<br>
+<a href="https://github.com/google/oss-fuzz/blob/master/projects/llvm/project.yaml" rel="noreferrer" target="_blank">https://github.com/google/<wbr>oss-fuzz/blob/master/projects/<wbr>llvm/project.yaml</a><br>
+<a href="https://bugs.chromium.org/p/oss-fuzz/issues/list?q=Proj-llvm" rel="noreferrer" target="_blank">https://bugs.chromium.org/p/<wbr>oss-fuzz/issues/list?q=Proj-<wbr>llvm</a><br>
+<br>
+.. _OSS Fuzz: <a href="https://github.com/google/oss-fuzz" rel="noreferrer" target="_blank">https://github.com/google/oss-<wbr>fuzz</a><br>
+<br>
+<br>
+Utilities for Writing Fuzzers<br>
+=============================<br>
+<br>
+There are some utilities available for writing fuzzers in LLVM.<br>
+<br>
+Some helpers for handling the command line interface are available in<br>
+``include/llvm/FuzzMutate/<wbr>FuzzerCLI.h``, including functions to parse command<br>
+line options in a consistent way and to implement standalone main functions so<br>
+your fuzzer can be built and tested when not built against libFuzzer.<br>
+<br>
+There is also some handling of the CMake config for fuzzers, where you should<br>
+use the ``add_llvm_fuzzer`` to set up fuzzer targets. This function works<br>
+similarly to functions such as ``add_llvm_tool``, but they take care of linking<br>
+to LibFuzzer when appropriate and can be passed the ``DUMMY_MAIN`` argument to<br>
+enable standalone testing.<br>
<br>
Modified: llvm/trunk/docs/LibFuzzer.rst<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/LibFuzzer.rst?rev=315544&r1=315543&r2=315544&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-<wbr>project/llvm/trunk/docs/<wbr>LibFuzzer.rst?rev=315544&r1=<wbr>315543&r2=315544&view=diff</a><br>
==============================<wbr>==============================<wbr>==================<br>
--- llvm/trunk/docs/LibFuzzer.rst (original)<br>
+++ llvm/trunk/docs/LibFuzzer.rst Wed Oct 11 18:44:24 2017<br>
@@ -42,10 +42,10 @@ This installs the Clang binary as<br>
 ``./third_party/llvm-build/<wbr>Release+Asserts/bin/clang``)<br>
<br>
 The libFuzzer code resides in the LLVM repository, and requires a recent Clang<br>
-compiler to build (and is used to `fuzz various parts of LLVM itself`_).<br>
-However the fuzzer itself does not (and should not) depend on any part of LLVM<br>
-infrastructure and can be used for other projects without requiring the rest<br>
-of LLVM.<br>
+compiler to build (and is used to :doc:`fuzz various parts of LLVM itself<br>
+<FuzzingLLVM>`).  However the fuzzer itself does not (and should not) depend on<br>
+any part of LLVM infrastructure and can be used for other projects without<br>
+requiring the rest of LLVM.<br>
<br>
<br>
 Getting Started<br>
@@ -137,6 +137,8 @@ Finally, link with ``libFuzzer.a``::<br>
<br>
   clang -fsanitize-coverage=trace-pc-<wbr>guard -fsanitize=address your_lib.cc fuzz_target.cc libFuzzer.a -o my_fuzzer<br>
<br>
+.. _libfuzzer-corpus:<br>
+<br>
 Corpus<br>
 ------<br>
<br>
@@ -627,66 +629,6 @@ which was configured with ``-DLIBFUZZER_<br>
     ninja check-fuzzer<br>
<br>
<br>
-Fuzzing components of LLVM<br>
-==========================<br>
-.. contents::<br>
-   :local:<br>
-   :depth: 1<br>
-<br>
-To build any of the LLVM fuzz targets use the build instructions above.<br>
-<br>
-clang-format-fuzzer<br>
--------------------<br>
-The inputs are random pieces of C++-like text.<br>
-<br>
-.. code-block:: console<br>
-<br>
-    ninja clang-format-fuzzer<br>
-    mkdir CORPUS_DIR<br>
-    ./bin/clang-format-fuzzer CORPUS_DIR<br>
-<br>
-Optionally build other kinds of binaries (ASan+Debug, MSan, UBSan, etc).<br>
-<br>
-Tracking bug: <a href="https://llvm.org/bugs/show_bug.cgi?id=23052" rel="noreferrer" target="_blank">https://llvm.org/bugs/show_<wbr>bug.cgi?id=23052</a><br>
-<br>
-clang-fuzzer<br>
-------------<br>
-<br>
-The behavior is very similar to ``clang-format-fuzzer``.<br>
-<br>
-Tracking bug: <a href="https://llvm.org/bugs/show_bug.cgi?id=23057" rel="noreferrer" target="_blank">https://llvm.org/bugs/show_<wbr>bug.cgi?id=23057</a><br>
-<br>
-llvm-as-fuzzer<br>
---------------<br>
-<br>
-Tracking bug: <a href="https://llvm.org/bugs/show_bug.cgi?id=24639" rel="noreferrer" target="_blank">https://llvm.org/bugs/show_<wbr>bug.cgi?id=24639</a><br>
-<br>
-llvm-mc-fuzzer<br>
---------------<br>
-<br>
-This tool fuzzes the MC layer. Currently it is only able to fuzz the<br>
-disassembler but it is hoped that assembly, and round-trip verification will be<br>
-added in future.<br>
-<br>
-When run in dissassembly mode, the inputs are opcodes to be disassembled. The<br>
-fuzzer will consume as many instructions as possible and will stop when it<br>
-finds an invalid instruction or runs out of data.<br>
-<br>
-Please note that the command line interface differs slightly from that of other<br>
-fuzzers. The fuzzer arguments should follow ``--fuzzer-args`` and should have<br>
-a single dash, while other arguments control the operation mode and target in a<br>
-similar manner to ``llvm-mc`` and should have two dashes. For example:<br>
-<br>
-.. code-block:: console<br>
-<br>
-  llvm-mc-fuzzer --triple=aarch64-linux-gnu --disassemble --fuzzer-args -max_len=4 -jobs=10<br>
-<br>
-Buildbot<br>
---------<br>
-<br>
-A buildbot continuously runs the above fuzzers for LLVM components, with results<br>
-shown at <a href="http://lab.llvm.org:8011/builders/sanitizer-x86_64-linux-fuzzer" rel="noreferrer" target="_blank">http://lab.llvm.org:8011/<wbr>builders/sanitizer-x86_64-<wbr>linux-fuzzer</a> .<br>
-<br>
 FAQ<br>
 =========================<br>
<br>
@@ -808,4 +750,4 @@ Trophies<br>
 .. _`value profile`: #value-profile<br>
 .. _`caller-callee pairs`: <a href="http://clang.llvm.org/docs/SanitizerCoverage.html#caller-callee-coverage" rel="noreferrer" target="_blank">http://clang.llvm.org/docs/<wbr>SanitizerCoverage.html#caller-<wbr>callee-coverage</a><br>
 .. _BoringSSL: <a href="https://boringssl.googlesource.com/boringssl/" rel="noreferrer" target="_blank">https://boringssl.<wbr>googlesource.com/boringssl/</a><br>
-.. _`fuzz various parts of LLVM itself`: `Fuzzing components of LLVM`_<br>
+<br>
<br>
Modified: llvm/trunk/docs/index.rst<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/index.rst?rev=315544&r1=315543&r2=315544&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-<wbr>project/llvm/trunk/docs/index.<wbr>rst?rev=315544&r1=315543&r2=<wbr>315544&view=diff</a><br>
==============================<wbr>==============================<wbr>==================<br>
--- llvm/trunk/docs/index.rst (original)<br>
+++ llvm/trunk/docs/index.rst Wed Oct 11 18:44:24 2017<br>
@@ -183,6 +183,7 @@ For developers of applications which use<br>
    ProgrammersManual<br>
    Extensions<br>
    LibFuzzer<br>
+   FuzzingLLVM<br>
    ScudoHardenedAllocator<br>
    OptBisect<br>
<br>
@@ -228,6 +229,9 @@ For developers of applications which use<br>
 :doc:`LibFuzzer`<br>
   A library for writing in-process guided fuzzers.<br>
<br>
+:doc:`FuzzingLLVM`<br>
+  Information on writing and using Fuzzers to find bugs in LLVM.<br>
+<br>
 :doc:`ScudoHardenedAllocator`<br>
   A library that implements a security-hardened `malloc()`.<br>
<br>
<br>
<br>
______________________________<wbr>_________________<br>
llvm-commits mailing list<br>
<a href="mailto:llvm-commits@lists.llvm.org">llvm-commits@lists.llvm.org</a><br>
<a href="http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits" rel="noreferrer" target="_blank">http://lists.llvm.org/cgi-bin/<wbr>mailman/listinfo/llvm-commits</a><br>
</blockquote></div></div>