VelesDB Fuzzing Guide
September 2, 2026 ยท View on GitHub
EPIC-025: Comprehensive fuzzing documentation for VelesDB security testing.
Overview
VelesDB uses cargo-fuzz (libFuzzer) for continuous fuzzing of critical components. This document covers setup, running fuzzers, reproducing crashes, and contributing to fuzzing efforts.
Setup
Prerequisites
# Install Rust nightly (required for cargo-fuzz)
rustup install nightly
# Install cargo-fuzz
cargo install cargo-fuzz
Verify Installation
cd fuzz
cargo +nightly fuzz list
Expected output:
fuzz_velesql_parser
fuzz_distance_metrics
fuzz_snapshot_parser
Fuzz Targets
| Target | Component | Invariants | Priority |
|---|---|---|---|
fuzz_velesql_parser | VelesQL Parser | No panic, valid AST or error | ๐ฅ HIGH |
fuzz_distance_metrics | Distance Calculations | No NaN/panic, bounded output | ๐ฅ HIGH |
fuzz_snapshot_parser | Snapshot Decoder | Roundtrip, no corruption | ๐ MEDIUM |
fuzz_velesql_parser
Tests the VelesQL SQL parser with arbitrary input strings:
- Input: Arbitrary bytes (converted to UTF-8)
- Invariant: Parser must never panic; returns
Ok(AST)orErr(ParseError) - Coverage: SELECT, MATCH, JOIN, ORDER BY, WHERE clauses
cargo +nightly fuzz run fuzz_velesql_parser
fuzz_distance_metrics
Tests SIMD distance calculations with arbitrary vectors:
- Input: Pairs of f32 vectors (arbitrary length and values)
- Invariant: Must handle NaN, Inf, denormals without panic
- Coverage: Cosine, Euclidean, DotProduct, Hamming, Jaccard
cargo +nightly fuzz run fuzz_distance_metrics
fuzz_snapshot_parser
Tests snapshot serialization/deserialization:
- Input: Arbitrary bytes
- Invariant: Decode โ Encode โ Decode must roundtrip (if decode succeeds)
- Coverage: Collection snapshots, metadata, vector data
cargo +nightly fuzz run fuzz_snapshot_parser
Running Fuzzers
Quick Run (1 minute)
cd fuzz
cargo +nightly fuzz run fuzz_velesql_parser -- -max_total_time=60
Long Run (1 hour)
cargo +nightly fuzz run fuzz_velesql_parser -- -max_total_time=3600
Parallel Fuzzing (Multiple Cores)
# Run with 4 workers
cargo +nightly fuzz run fuzz_velesql_parser -- -workers=4 -jobs=4
With Specific Corpus
cargo +nightly fuzz run fuzz_velesql_parser fuzz/corpus/velesql_parser/
Reproducing Crashes
When a crash is found, a crash file is saved to fuzz/artifacts/<target>/.
View Crash Input
xxd fuzz/artifacts/fuzz_velesql_parser/crash-xxx
Reproduce Crash
cargo +nightly fuzz run fuzz_velesql_parser fuzz/artifacts/fuzz_velesql_parser/crash-xxx
Minimize Crash
Minimize the crash input to find the smallest reproducer:
cargo +nightly fuzz tmin fuzz_velesql_parser fuzz/artifacts/fuzz_velesql_parser/crash-xxx
Debug Crash
# With debug symbols
RUST_BACKTRACE=1 cargo +nightly fuzz run fuzz_velesql_parser fuzz/artifacts/fuzz_velesql_parser/crash-xxx
Corpus Management
Versioned Corpus
The corpus directory contains seed inputs that guide fuzzing:
fuzz/
โโโ corpus/
โ โโโ velesql_parser/ # SQL query seeds
โ โ โโโ valid_select_01
โ โ โโโ valid_match_01
โ โ โโโ edge_case_empty
โ โโโ distance_metrics/ # Vector pair seeds
โ โโโ snapshot_parser/ # Binary snapshot seeds
Adding Seeds
Add interesting inputs that exercise different code paths:
# Add a valid query
echo 'SELECT * FROM docs WHERE vector NEAR $v LIMIT 10' > fuzz/corpus/velesql_parser/valid_near_query
# Add edge case
echo '' > fuzz/corpus/velesql_parser/empty_input
Minimizing Corpus
Remove redundant inputs:
cargo +nightly fuzz cmin fuzz_velesql_parser fuzz/corpus/velesql_parser/
CI Integration
GitHub Actions (Optional Nightly Run)
fuzz:
name: Fuzzing (Nightly)
runs-on: ubuntu-latest
if: github.event_name == 'schedule'
steps:
- uses: actions/checkout@v4
- name: Install cargo-fuzz
run: cargo install cargo-fuzz
- name: Run VelesQL parser fuzzer
run: |
cd fuzz
cargo +nightly fuzz run fuzz_velesql_parser -- -max_total_time=300
- name: Upload crashes
if: failure()
uses: actions/upload-artifact@v4
with:
name: fuzz-crashes
path: fuzz/artifacts/
Local Pre-Push Check
# Quick fuzz check before push
cd fuzz
for target in $(cargo +nightly fuzz list); do
cargo +nightly fuzz run $target -- -max_total_time=30 || exit 1
done
Writing New Fuzz Targets
1. Create Fuzz Target
// fuzz/fuzz_targets/fuzz_new_component.rs
#![no_main]
use libfuzzer_sys::fuzz_target;
use arbitrary::Arbitrary;
#[derive(Arbitrary, Debug)]
struct FuzzInput {
data: Vec<u8>,
option: bool,
}
fuzz_target!(|input: FuzzInput| {
// Your component under test
// MUST NOT panic on any input
let _ = your_component::process(&input.data, input.option);
});
2. Add to Cargo.toml
[[bin]]
name = "fuzz_new_component"
path = "fuzz_targets/fuzz_new_component.rs"
test = false
doc = false
bench = false
3. Create Initial Corpus
mkdir -p fuzz/corpus/new_component
echo 'valid input' > fuzz/corpus/new_component/seed_01
4. Document in this Guide
Add entry to the Fuzz Targets table above.
Best Practices
For Fuzz Targets
- No panics: Handle all errors gracefully with
Result - Bounded resources: Use timeouts and size limits
- Deterministic: Same input โ same behavior
- Fast: Each iteration should be < 1ms
For Corpus Seeds
- Diverse: Cover different code paths
- Minimal: Smallest input that exercises a path
- Valid + Invalid: Include both correct and malformed inputs
- Edge cases: Empty, max size, special characters
For CI Integration
- Time-boxed: Always use
-max_total_time - Artifact upload: Preserve crashes for debugging
- Non-blocking: Use
continue-on-error: trueinitially
Reporting Issues
When reporting a fuzzing crash:
- Minimize the crash file
- Check if it's a known issue
- Open issue with:
- Crash file (base64 encoded)
- VelesDB version (
cargo pkgid velesdb-core) - Reproduction command
- Stack trace if available
Template
## Fuzzing Crash Report
**Target**: fuzz_velesql_parser
**Version**: `<output of cargo pkgid velesdb-core>`
**Date**: 2026-01-29
### Reproduction
```bash
cargo +nightly fuzz run fuzz_velesql_parser crash_input.txt
Crash Input (base64)
<base64 encoded crash file>
Stack Trace
thread 'main' panicked at ...
## References
- [cargo-fuzz book](https://rust-fuzz.github.io/book/)
- [libFuzzer documentation](https://llvm.org/docs/LibFuzzer.html)
- [Rust Fuzz Book](https://rust-fuzz.github.io/book/)
- [AFL.rs](https://github.com/rust-fuzz/afl.rs) (alternative fuzzer)
---
*Last updated: 2026-08-13 ยท Applies to: velesdb-core 6.0.0 (introduced: EPIC-025)*