Fuzzing

mohitmishra786/low-level-dev-skills/skills/runtimes/fuzzing

作者 mohitmishra786bdc58472fa9f無授權條款253 個星標收錄於 2026年10月9日更新於 2026年10月9日儲存庫3 個月前更新

Fuzzing skill for automated input-driven bug finding in C/C++. Use when setting up libFuzzer or AFL++ fuzz targets, defining fuzz entry points around parsing or I/O boundaries, integrating fuzzing into CI, managing corpora, or combining fuzzing with sanitizers. Activates on queries about libFuzzer, AFL, afl-fuzz, fuzz targets, corpus management, coverage-guided fuzzing, or OSS-Fuzz integration.

AI 產生的概覽

指導使用 libFuzzer、AFL++、Atheris 與 OSS-Fuzz,為 C/C++ 及 Python 目標建立覆蓋率導向的模糊測試。

功能
此技能引導代理撰寫模糊測試目標、搭配 sanitizer 建置、執行並重現當機、管理語料庫,以及將模糊測試整合進 CI。內容涵蓋 libFuzzer、AFL++(含持久模式)、Python 的 Atheris、結構感知變異器、字典檔、資料流追蹤與 OSS-Fuzz 整合。它產出的是說明與程式碼範本,而非可執行指令碼。
適用情境
適用於為解析器、反序列化器或其他輸入驅動程式碼建立或執行模糊測試時。也適合關於模糊測試進入點、語料庫管理、sanitizer 建置或重現模糊測試所發現當機的問題。
執行需求
需要安裝含 Clang 的 C/C++ 工具鏈(libFuzzer 與 sanitizer)或 AFL++,選用時需要 Python 與 atheris 套件、Zig、GDB,以及 OSS-Fuzz 基礎設施的存取權。不附指令碼,僅為說明文件,並含一份參考文件。

Fuzzing

Purpose

Guide agents through setting up and running coverage-guided fuzz testing: libFuzzer (in-process) and AFL++ (fork-based), with sanitizer integration and CI pipeline setup.

Triggers

  • "How do I fuzz-test my parser/deserializer?"
  • "What is a fuzz target / how do I write one?"
  • "How do I set up libFuzzer?"
  • "How do I use AFL++ on my program?"
  • "How do I run fuzzing in CI?"
  • "Fuzzer found a crash — how do I reproduce it?"

Workflow

1. Write a fuzz target (libFuzzer)

A fuzz target is a function that accepts arbitrary bytes and exercises the code under test.

c
// fuzz_parser.c#include <stdint.h>#include <stddef.h>#include "myparser.h"
// Entry point called by libFuzzer with random dataint LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) {    // Must not abort/exit on invalid input (that's expected)    // Must not read outside [data, data+size)
    MyParser *p = parser_create();    if (p) {        parser_feed(p, (const char *)data, size);        parser_destroy(p);    }    return 0;  // Always return 0 (non-zero means discard input)}

Key rules:

  • Never call abort(), exit(), or use global state that persists across calls
  • Handle all inputs gracefully (crash = bug found)
  • Keep the target fast: the fuzzer calls it millions of times

2. Build with libFuzzer

bash
# Clang (libFuzzer is built into Clang)clang -fsanitize=fuzzer,address -g -O1 \    fuzz_parser.c myparser.c -o fuzz_parser
# With UBSan tooclang -fsanitize=fuzzer,address,undefined -g -O1 \    fuzz_parser.c myparser.c -o fuzz_parser

-fsanitize=fuzzer links libFuzzer and provides main(). Do not provide your own main() in the fuzz target.

3. Run libFuzzer

bash
# Create corpus directorymkdir -p corpus
# Seed with known-good inputs (greatly accelerates coverage)cp tests/inputs/* corpus/
# Run the fuzzer./fuzz_parser corpus/ -max_len=65536 -timeout=10
# Run for a time limit./fuzz_parser corpus/ -max_total_time=3600
# Run with specific number of jobs (parallel)./fuzz_parser corpus/ -jobs=4 -workers=4
# Minimise a corpus (remove redundant inputs)./fuzz_parser -merge=1 corpus_min/ corpus/

Common flags:

FlagDefaultEffect
-max_len=N4096Max input size in bytes
-timeout=N1200Kill if single run takes > N seconds
-max_total_time=N0 (forever)Total fuzzing time
-runs=N-1 (infinite)Total number of runs
-dict=filenoneDictionary of interesting tokens
-jobs=N1Parallel jobs (each writes its own log)
-merge=1offMerge mode: minimise corpus

4. Reproduce a crash

libFuzzer writes crash inputs to files named crash-<hash>, oom-<hash>, timeout-<hash>.

bash
# Reproduce./fuzz_parser crash-abc123
# Debug with GDBgdb ./fuzz_parser(gdb) run crash-abc123

5. AFL++ setup

AFL++ is a fork-based fuzzer that works on arbitrary programs (not just those with a fuzz entry point).

bash
# Installapt install afl++     # or build from source
# Instrument the targetCC=afl-clang-fast CXX=afl-clang-fast++ \  cmake -S . -B build-afl -DCMAKE_BUILD_TYPE=Debugcmake --build build-afl
# Or compile directlyafl-clang-fast -g -O1 -o prog_afl main.c myparser.c
# Create input corpusmkdir -p afl-input afl-outputecho "hello" > afl-input/seed1
# Runafl-fuzz -i afl-input -o afl-output -- ./prog_afl @@# @@ is replaced with the input file path# For stdin-based programs: remove @@afl-fuzz -i afl-input -o afl-output -- ./prog_afl

6. AFL++ with persistent mode (faster)

Persistent mode avoids fork() per input — much faster for library fuzzing:

c
// In your harness:#include "myparser.h"
int main(int argc, char **argv) {    while (__AFL_LOOP(1000)) {        // Read input        unsigned char *buf = NULL;        ssize_t len = read(0, &buf, MAX_SIZE);  // or use afl_custom_mutator        parser_feed((char*)buf, len);        free(buf);    }    return 0;}

7. Corpus management

bash
# AFL++ corpus minimisationafl-cmin -i afl-output/default/queue -o corpus_min -- ./prog_afl @@
# Merge libFuzzer corpora from multiple runs./fuzz_parser -merge=1 merged_corpus/ run1_corpus/ run2_corpus/
# Show coverage (libFuzzer)./fuzz_parser corpus/ -runs=0 -print_coverage=1

8. CI integration

yaml
# GitHub Actions example- name: Build fuzz targets  run: |    clang -fsanitize=fuzzer,address,undefined -g -O1 \      fuzz_parser.c myparser.c -o fuzz_parser
- name: Short fuzz run (regression check)  run: |    ./fuzz_parser corpus/ -max_total_time=60 -error_exitcode=1    # Also run known crash inputs if any:    ls known_crashes/ 2>/dev/null | xargs -I{} ./fuzz_parser known_crashes/{}

For long-duration fuzzing, use OSS-Fuzz or ClusterFuzz infrastructure.

9. Structure-aware fuzzing (libFuzzer)

c
// Custom mutator hook — preserve format invariantssize_t LLVMFuzzerCustomMutator(uint8_t *Data, size_t Size,                               size_t MaxSize, unsigned int Seed) {    // Delegate to default mutator then fix up structure    Size = LLVMFuzzerMutate(Data, Size, MaxSize);    if (Size >= 4)        fix_checksum(Data, Size);    return Size;}
// Register custom crossover for structured inputsextern "C" size_t LLVMFuzzerCustomCrossOver(    const uint8_t *Data1, size_t Size1,    const uint8_t *Data2, size_t Size2,    uint8_t *Out, size_t MaxOutSize, unsigned int Seed);

Use when naive bit-flipping breaks checksums/headers before reaching deep code paths.

10. Atheris (Python fuzzing)

python
import atherisimport sys
with atheris.instrument_imports():    import myparser
def TestOneInput(data: bytes) -> None:    fdp = atheris.FuzzedDataProvider(data)    try:        myparser.parse(fdp.ConsumeString(sys.maxsize))    except myparser.ParseError:        pass
if __name__ == "__main__":    atheris.Setup(sys.argv, TestOneInput)    atheris.Fuzz()
bash
pip install atherispython fuzz_myparser.py corpus/ -max_total_time=300

11. Dataflow tracing

bash
# Track tainted bytes through execution (LLVM dataflow sanitizer + libFuzzer)clang -fsanitize=fuzzer,dataflow -g -O1 fuzz.c target.c -o fuzzLIBFUZZER_DATAFLOW_TRACE=1 ./fuzz corpus/

Produces traces showing which input bytes influenced branches — guides dictionary and structure-aware mutators.

12. OSS-Fuzz integration

OSS-Fuzz workflow├── Add project/ in google/oss-fuzz repo (Dockerfile + build.sh)├── Fuzz targets linked with -fsanitize=fuzzer,address├── ClusterFuzz runs continuously on GCE└── Crash reproducers uploaded to issue tracker
dockerfile
# project/Dockerfile (minimal)FROM gcr.io/oss-fuzz-base/base-builderRUN git clone --depth 1 https://github.com/you/yourprojectWORKDIR yourprojectCOPY build.sh $SRC/
bash
# Local OSS-Fuzz repropython infra/helper.py build_image yourprojectpython infra/helper.py build_fuzzers yourprojectpython infra/helper.py run_fuzzer yourproject fuzz_target

13. Zig fuzz testing

bash
# Zig 0.11+ built-in fuzzingzig build test --fuzz
# fuzz target in build.zig# .root_module.fuzz_tests = &.{#     .{ .name = "parser", .path = "src/fuzz/parser.zig" },# };

Zig fuzz integrates with zig test and sanitizer builds for native targets.

14. Dictionary files

Dictionaries contain interesting tokens to guide mutation:

bash
# parser.dictkw1="<"kw2=">"kw3="</"kw4='="'kw5="\x00"kw6="\xff\xfe"
bash
./fuzz_parser corpus/ -dict=parser.dict

References

For fuzz target templates, corpus seed examples, and OSS-Fuzz integration guidance, see references/targets.md [blocked].

Related skills

  • Use skills/runtimes/sanitizers to add ASan/UBSan to fuzz builds
  • Use skills/compilers/clang for Clang-specific libFuzzer flags
  • Use skills/debuggers/gdb to debug crash inputs found by the fuzzer
  • Use skills/zig/zig-testing for Zig build test --fuzz workflows
  • Use skills/security/kernel-security for kernel fuzzing with syzkaller

來源與署名

來源:mohitmishra786/low-level-dev-skills位於skills/runtimes/fuzzing提交bdc5847

授權條款: 無授權條款

內容歸原作者所有。SourceWeft 從公開儲存庫中收錄這些內容。

檢舉或申請下架