coverage-analysis
Originally fromtrailofbits/skills
SKILL.md
Coverage Analysis
Coverage analysis for understanding which parts of code are exercised during fuzzing.
Overview
Code coverage during fuzzing serves two critical purposes:
- Assessing harness effectiveness: Which parts are actually executed by fuzzing harnesses
- Tracking fuzzing progress: How coverage changes when updating harnesses or fuzzers
When to Apply
Apply this technique when:
- Starting a new fuzzing campaign to establish a baseline
- Fuzzer appears to plateau without finding new paths
- After harness modifications to verify improvements
- When migrating between different fuzzers
- Identifying areas requiring dictionary entries or seed inputs
- Debugging why certain code paths aren't reached
Skip this technique when:
- Fuzzing campaign is actively finding crashes
- Coverage infrastructure isn't set up yet
- Fuzzer's internal coverage metrics are sufficient
Quick Reference
| Task | Command/Pattern |
|---|---|
| LLVM coverage (C/C++) | -fprofile-instr-generate -fcoverage-mapping |
| GCC coverage | -ftest-coverage -fprofile-arcs |
| cargo-fuzz coverage (Rust) | cargo +nightly fuzz coverage <target> |
| Generate LLVM profile | llvm-profdata merge -sparse file.profraw -o file.profdata |
| LLVM coverage report | llvm-cov report ./binary -instr-profile=file.profdata |
| LLVM HTML report | llvm-cov show ./binary -instr-profile=file.profdata -format=html -output-dir html/ |
| gcovr HTML report | gcovr --html-details -o coverage.html |
Ideal Coverage Workflow
[Fuzzing Campaign]
|
v
[Generate Corpus]
|
v
[Coverage Analysis]
|
+---> Coverage Increased? --> Continue fuzzing
|
+---> Coverage Decreased? --> Fix harness or investigate changes
|
+---> Coverage Plateaued? --> Add dictionary entries or seed inputs
Rust: cargo-fuzz Coverage
# Install prerequisites
rustup toolchain install nightly --component llvm-tools-preview
cargo install cargo-binutils rustfilt
# Generate coverage data
cargo +nightly fuzz coverage fuzz_target_1
# Create HTML report script
cat <<'EOF' > ./generate_html
#!/bin/sh
FUZZ_TARGET="$1"
shift
SRC_FILTER="$@"
TARGET=$(rustc -vV | sed -n 's|host: ||p')
cargo +nightly cov -- show -Xdemangler=rustfilt \
"target/$TARGET/coverage/$TARGET/release/$FUZZ_TARGET" \
-instr-profile="fuzz/coverage/$FUZZ_TARGET/coverage.profdata" \
-show-line-counts-or-regions -show-instantiations \
-format=html -o fuzz_html/ $SRC_FILTER
EOF
chmod +x ./generate_html
# Generate report
./generate_html fuzz_target_1 src/lib.rs
C/C++: LLVM Coverage
# Build with coverage instrumentation
clang++ -fprofile-instr-generate -fcoverage-mapping \
-O2 -DNO_MAIN \
main.cc harness.cc execute-rt.cc -o fuzz_exec
# Execute on corpus
LLVM_PROFILE_FILE=fuzz.profraw ./fuzz_exec corpus/
# Process and generate report
llvm-profdata merge -sparse fuzz.profraw -o fuzz.profdata
llvm-cov show ./fuzz_exec \
-instr-profile=fuzz.profdata \
-ignore-filename-regex='harness.cc|execute-rt.cc' \
-format=html -output-dir fuzz_html/
Common Patterns
Identifying Magic Values
Coverage reveals:
// Coverage shows this block is never executed
if (buf == 0x7F454C46) { // ELF magic number
// start parsing buf
}
Solution: Add magic values to dictionary file:
# magic.dict
"\x7F\x45\x4C\x46"
Anti-Patterns
| Anti-Pattern | Problem | Correct Approach |
|---|---|---|
| Using fuzzer-reported coverage for comparisons | Different fuzzers calculate coverage differently | Use dedicated coverage tools |
| Generating coverage with -O3 | Optimizations eliminate code | Use -O2 or -O0 |
| Not filtering harness code | Harness inflates numbers | Use -ignore-filename-regex |
| Ignoring crashing inputs | Crashes prevent coverage generation | Fix crashes first or use process forking |
Tips
| Tip | Why It Helps |
|---|---|
Use LLVM 18+ with -show-directory-coverage |
Organizes large reports by directory |
| Export to lcov format for better HTML | llvm-cov export -format=lcov + genhtml |
| Compare coverage across campaigns | Store .profdata files with timestamps |
| Filter harness code from reports | Focus on SUT coverage only |
| Automate coverage in CI/CD | Generate reports after scheduled fuzzing runs |
Attribution
Based on trailofbits/skills coverage-analysis skill - 45+ installs.
Weekly Installs
3
Repository
5dlabs/ctoFirst Seen
Jan 24, 2026
Installed on
claude-code2
windsurf1
trae1
opencode1
codex1
antigravity1