Map any userspace program to the exact kernel code it exercises.
sudo ./vock.bin --vmlinux vmlinux /bin/ip addr show
# → kerncov.log + coverage.htmlvock is written in Rust — a full port of the original C/Python, with no C
remaining and libc as the only crate dependency. make produces ./vock.bin
and the mode/kcov.so LD_PRELOAD coverage shim.
Status. All four selftests pass on x86_64. selftest 1 (KCOV) covers
KCOV+vmlinux and KCOV+BTF across all three syscall backends (ptrace, sud,
ebpf), with --syzlang, --ordered and --filter reporting. selftest 3
(crypto) passes; selftest 4 reproduces a real KASAN use-after-free from the
bundled sample. selftest 2 (HW trace) traces with Intel PT on bare metal
(--on host, root or perf_event_paranoid ≤ 1). The sud backend
traces up to and including the target's execve (the LD_PRELOAD re-injection
that keeps tracing past exec is not yet ported). HW trace (Intel PT / AMD LBR /
CoreSight) is ported and builds; arm64 and AMD are validated in follow-up work.
vock execprog is a syz-execprog-style executor: it replays a program
with -repeat/-procs and can attribute KCOV coverage to each call. An
unmodified syzbot reproducer works, including the &(0x7f…) memory layout,
resource wiring and 13 of the syz_* pseudo-syscalls; the rest return ENOSYS
and are named on startup. execprog -stress mutates the program and loops it,
mirroring syz-execprog -stress.
vock fuzz is not implemented and prints a notice explaining why:
coverage-guided mutation needs an edge signal that is not wired in yet. See
FUZZ.md.
Toolchain (Rust, via rustup):
curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | shOptional runtime helpers:
sudo apt install binutils # addr2line, nm — source-annotated reports
sudo apt install clang # only to build test kernels in `vock selftest`Or build a package (see Build):
./debian/get-vendor.sh && dpkg-buildpackage -us -uc -b
sudo apt install ../vock_0.1.0-1_*.debBuild:
git clone https://github.com/yskzalloc/vock && cd vock
make # wraps `cargo build --release`; places ./vock.bin and mode/kcov.soWorks on any kernel — no CONFIG_KCOV needed:
# Full branch coverage (needs vmlinux for TNT decoding)
sudo ./vock.bin --vmlinux /boot/vmlinux-$(uname -r) /bin/ip addr show
# → kerncov.log + coverage.html
# Function-entry only (no vmlinux)
sudo ./vock.bin /bin/ip addr show
# → kerncov.logIf not running as root — the kernel only forbids kernel profiling at
perf_event_paranoid >= 2, so 1 is enough:
echo 1 | sudo tee /proc/sys/kernel/perf_event_paranoid
./vock.bin --vmlinux vmlinux /bin/ip addr showPer-task kernel coverage including remote (softirqs, workqueues):
sudo ./vock.bin --mode kcov /bin/ip addr show
# → kerncov.log (local + remote) + coverage.htmlTracks coverage across fork() and pthread_create() — each child gets its own KCOV instance (local-<TID>.log).
sudo ./vock.bin --syscall /bin/ls /tmp
# → kerncov.log + trace.log
sudo ./vock.bin --syzlang /bin/ip addr show
# → kerncov.log + trace.log + trace.syz (for syz-trace2syz)Replay a program, or use it as a seed and loop mutated variants (-stress):
sudo ./vock.bin --syzlang /bin/ip addr show # capture a program
./vock.bin execprog -stress -procs=8 trace.syz # mutate + execute in a loop
sudo ./vock.bin execprog trace.syz # replay a saved programSee FUZZ.md for details and current limitations.
vock integrates with virtme-ng for testing custom kernels in lightweight VMs. This is useful for running vock against kernels with specific configs (KCOV, debug info) without rebooting your host.
Install virtme-ng:
python3 -m venv venv-virtme
source venv-virtme/bin/activate
pip3 install git+https://github.com/arighi/virtme-ng.gitBuild a kernel with KCOV and run vock inside it:
cd /path/to/linux
vng --configitem CONFIG_KCOV=y --configitem CONFIG_KCOV_INSTRUMENT_ALL=y --build LLVM=-21
vng --rw -- /path/to/vock --mode kcov --vmlinux vmlinux /bin/ip addr showAMD LBR works inside KVM guests. Build a kernel without KCOV to verify HW-only coverage:
cd /path/to/linux
vng --configitem CONFIG_KCOV=n --configitem CONFIG_PERF_EVENTS=y --build LLVM=-21
vng --rw -- /path/to/vock --mode hw --vmlinux vmlinux /bin/ip addr showNote: Intel PT requires host passthrough and is typically unavailable in guests. Use --on host for Intel PT testing.
Each feature requires specific kernel configs:
Works on stock distro kernels — only needs:
CONFIG_PERF_EVENTS=y
CONFIG_KCOV=y
CONFIG_KCOV_INSTRUMENT_ALL=y
CONFIG_BPF_SYSCALL=y
CONFIG_DEBUG_INFO_BTF=y
CONFIG_DEBUG_INFO=y
CONFIG_DEBUG_INFO_DWARF5=y
CONFIG_DEBUG_INFO_BTF=y
CONFIG_IKCONFIG=y
CONFIG_IKCONFIG_PROC=y
CONFIG_CRYPTO_XTS=y
CONFIG_CRYPTO_USER=y
CONFIG_CRYPTO_USER_API_SKCIPHER=y
| Mode | Flag | Coverage Level | Kernel Requirement |
|---|---|---|---|
| Intel PT | --mode hw (default) |
Branch (with vmlinux) or function-entry | CONFIG_PERF_EVENTS=y |
| AMD LBR | --mode hw (auto) |
Function-entry, works in VMs | CONFIG_PERF_EVENTS=y |
| CoreSight | --mode hw (auto) |
Function-entry | CONFIG_PERF_EVENTS=y, CONFIG_CORESIGHT=y |
| KCOV | --mode kcov |
Branch (per-task + remote) | CONFIG_KCOV=y, CONFIG_KCOV_INSTRUMENT_ALL=y |
| Backend | Flag | Requirement |
|---|---|---|
| ptrace | --syscall ptrace (default) |
Any kernel |
| SUD | --syscall sud |
Kernel ≥ 5.11, x86_64, mmap_min_addr=0 |
| eBPF | --syscall ebpf |
CONFIG_BPF_SYSCALL=y, CONFIG_DEBUG_INFO_BTF=y |
SUD setup:
echo 0 | sudo tee /proc/sys/vm/mmap_min_addr| Feature | Intel x86_64 | ARM64 | AMD x86_64 |
|---|---|---|---|
| Intel PT (full branch) | ✓ | — | — |
| AMD LBR (function-entry) | — | — | ✓ |
| CoreSight | — | ✓ | — |
| KCOV | ✓ | ✓ | ✓ |
| Syscall tracking | ✓ | ✓ | ✓ |
# 1. What kernel code does the target reach?
sudo ./vock.bin --vmlinux vmlinux /bin/ip addr show
# → kerncov.log (5000+ kernel PCs)
# 2. Get syscall trace for syzkaller
sudo ./vock.bin --syzlang /bin/ip addr show
# → trace.syz
# 3. Feed to syzkaller
syz-trace2syz -file trace.syz
# → syzkaller corpusFour tests (see SELFTEST.md for details):
./vock.bin selftest 1 --on vng-kvm # KCOV + all syscall engines + reporting (VM)
sudo ./vock.bin selftest 2 --on host # HW trace, auto-selected for the host CPU
./vock.bin selftest 3 --on vng-kvm # --filter + xts(aes) crypto coverage (VM)
./vock.bin selftest 4 --on vng-kvm # KASAN bug hunt: loop a sample repro ≤30 min
./vock.bin selftest --on vng-kvm # all four
./vock.bin selftest --help # all optionsTest 2 detects the host CPU and runs the matching engine — Intel PT or AMD LBR
on x86_64, CoreSight on arm64. Intel PT and CoreSight need --on host (and
either root or perf_event_paranoid ≤ 1); AMD LBR also works under --on vng-kvm.
| File | Description |
|---|---|
kerncov.log |
Merged kernel coverage (all per-TID logs combined) |
local-<TID>.log |
Per-task KCOV coverage (direct syscall paths) |
remote-<TID>.log |
Per-task remote coverage (softirqs, workqueues) |
remote_coverage.log |
Remote coverage collected by the parent |
kerncov_prog1.<N> |
Per-call coverage from execprog -cover |
kerncov_prog1.extra |
Background coverage belonging to no single call |
coverage.html |
Source-annotated coverage report |
coverage-<TID>.html |
Per-thread report from --ordered |
trace.log |
Strace-format syscall log |
trace.syz |
Syzlang format (for syz-trace2syz) |
All coverage logs carry PreviousInstructionPC-shifted PCs, syzkaller's
convention — see FUZZ.md → PC convention.
make # or: cargo build --releasevock is a Cargo workspace with two members at the repo root:
| Directory | Produces | What it is |
|---|---|---|
vock/ |
target/release/vock → ./vock.bin |
The vock binary |
kcov-preload/ |
target/release/libkcov_preload.so → mode/kcov.so |
The LD_PRELOAD coverage shim |
make builds both and copies the artifacts into place. The binary is
./vock.bin, not ./vock, because the crate directory at the repo root is
already named vock/ — a file of the same name cannot coexist with it.
The only build dependency is a Rust toolchain; the sole crate dependency is
libc. There is no build.rs, no bindgen, and no C to compile — a CC=...
argument is accepted and ignored for backwards compatibility.
At runtime vock finds its shim by checking $VOCK_KCOV_SO, then
<dir of the binary>/mode/kcov.so (the build tree), then the packaged
locations such as /usr/lib/vock/kcov.so. So the same binary works from a
build tree and from an installed package.
./debian/get-vendor.sh # vendor deps so the build works offline
dpkg-buildpackage -us -uc -b # → ../vock_0.1.0-1_<arch>.debInstalls /usr/bin/vock, /usr/lib/vock/kcov.so and vock(1). See
debian/README.Debian for the privileges each mode needs.
See LICENSE.
