profile → benchmark → analyze → optimize ↻
- Tune the host with different profiles.
- Profile live binaries without re-compiling.
- Benchmark assembly snippets, functions and regions of any binary with hardware performance counters and CPU state control.
- Compare data via central limit theorem and null-hypothesis tests.
- Analyze machine code together with measured data.
- Optimize binaries with measured-data-guided, address-preserving passes.
- View/Plot in the terminal, via interactive mode or jupyter notebooks.
| Name | Description |
|---|---|
| CLI reference | Command line options, configuration |
| Python API | Architecture, synopsis |
| Code Markers | Zero-instruction code (C, C++, Rust, Zig) markers |
| Skills | The Human–Agent performance engineering loop |
| Studies | Top-down Microarchitecture Analysis Method studies: retiring, bad-speculation, frontend-bound, backend-bound |
| How it works | Symbolic exploration, data synthesis, JIT harness, CPU control (cache/branch/...), code patching, hardware counters |
- x86-64 Linux, kernel 6.x+
- Python 3.11+ (see pyproject.toml)
- linux-perf and user-space rdpmc access (see Setup)
pip install git+https://github.com/perf-labs/perf.gitSee Development.
echo 2 | sudo tee /sys/devices/{cpu_core,cpu_atom}/rdpmcThis enables user-space RDPMC hardware counters without syscalls on the hot path.
This is not required for duration_time (Time-Stamp Counter).
# info
perf system info
# tune
perf system tune --dry-run
perf system tune --profile=latency
perf system tune --profile=throughput
perf system tune --profile=latency --profile.aslr=true
# profile
perf profile -t hot_begin..hot_end -e cycles -o profile.json -- ./a.out
# benchmark
perf benchmark 'imul eax, 0' -m latency -e cycles
perf benchmark snippet.s:label
perf benchmark a.out:func -e 'topdown-*'
perf benchmark a.out:0x401000..0x401020
perf benchmark a.out:func -m throughput -e cycles,instructions
perf benchmark a.out:hot_begin..hot_end # see code markers
perf benchmark /usr/bin/tree:main -m latency -- /path/to/folder
perf benchmark a.out:func --data.rdi=15
perf benchmark a.out:func --config.branch=predictable
perf benchmark a.out:func --config.dcache=cold -e cache-misses,cycles
perf benchmark 'mov rax, [rdi]' --data.rdi=0x42000000000 --data[0x42000000000]=123
# compare
perf benchmark clang.out:func_v1 --output data/
perf benchmark gcc.out:func_v2 --output data/
perf compare --baseline func_v1 -- data/
# analyze
perf analyze a.out:func --filter 'latency > 4'
perf analyze a.out:func -e 'index,assembly,data*'
perf analyze a.out:func -e assembly | llvm-mca
perf analyze a.out:func --filter '15 in `data.rdi`'
perf analyze a.out:func -- perf.data profile.json
# optimize
perf optimize a.out --output b.out -- data/
perf optimize a.out --output b.out --opt peephole,branch
perf optimize a.out --output b.out --opt layout --config.layout.align=64 -- data/
perf optimize a.out --filter hot --output b.out -- data/
# view/plot
perf benchmark a.out:func | perf view
perf benchmark a.out:func | perf plot
perf plot -e instructions/cycles -- perf.dataSee CLI reference.
import perf
df = perf.benchmark(target=["a.out", "func"], mode=["latency"])
df.duration_time.describe()
df = perf.benchmark(asm="mov eax, 42", mode=["latency"], event=["cycles"])
df.cycles.plot()
df = perf.benchmark(target=["/usr/bin/tree", "main"], mode=["latency"])
json = perf.to_json(df)
df = perf.profile(cmd=["./a.out"], event=["cycles"], target=[("hot_begin", "hot_end")])
perf.plot(df, type=["ecdf"])
df = perf.analyze(target=["a.out", "func"], event=["assembly"])
print(df)
df = perf.optimize(target="a.out", output="b.out", config={"passes": ["peephole", "branch"])
print(df)
df = perf.compare(df, baseline="base", filter='mode == "latency"')
print(df)See Python API.
@software{perflabs2026perf,
author = {{perf-labs}},
title = {{perf}: Profile, Benchmark, Analyze, Optimize},
year = {2026},
url = {https://github.com/perf-labs/perf}
}See REFERENCES.md.