1
0
Fork 0
forked from hanez/xtc

Phase 19: measure graph scaling and guard capacity and contention behavior

This commit is contained in:
Johannes Findeisen 2026-10-27 06:35:15 +01:00
commit 6b85f28add
9 changed files with 639 additions and 3 deletions

View file

@ -33,3 +33,59 @@ the API cannot enforce an extension's memory budget. There is no CPU overload
scheduler, disk streaming, latency compensation or callback allocator audit of
arbitrary third-party code. High-density interactive projects, physical devices,
long-duration stereo/recording and live server termination remain unqualified.
## Phase 19 matrix, capacity and contention checks
`make benchmark` records 24 warmed graph cases: 2/16/64/256 nodes, mono/stereo,
44.1k/31, 48k/128 and 96k/1024. Each reports control-thread compile time separately
from 300 process calls, mean/p99/max, block deadline, mean load, and paired graph
buffer bytes. Timing, sorting, allocation and logging happen outside processing.
Metered gain chains test graph scaling; they do not represent expensive plugins.
The checked-in `performance-baseline.json` records CPU/compiler/flags/kernel and
all measurements. Copy a new run only after reviewing changes and conditions.
```sh
make benchmark test-performance test-scale test-stress
make benchmark-compare BENCHMARK_MAX_REGRESSION=1.5
# Select a baseline from this same host/compiler/flags:
make benchmark-compare BENCHMARK_BASELINE=/path/to/performance.json
```
Comparison rejects mismatched CPU/architecture/compiler/flags or missing cases.
It fails if mean time exceeds both the ratio budget and a 1 microsecond absolute
noise allowance. p99/max are reported for investigation, not universally gated.
Repeat surprising results under comparable load; do not silently replace the
baseline to make a regression disappear. Scheduling, clocks, thermal state and
shared-machine contention still affect results. No real-time scheduling/pinning
or external profiler is required. CPU-pressure runs are correctness checks, not
comparable timing baselines. Tests/benchmark outputs live below BUILD_DIR.
Initial matrix (Threadripper 1920X, GCC 16.2.1, -O2, 300 blocks): 256-node stereo
48k/128 mean 353.214 us, p99 396.495 us, load .132; 96k/1024 mean 2478.520 us,
p99 3092.434 us, load .232. The full JSON is the evidence. These met the local
investigation target of mean load <.5 for ordinary graph chains; this is a
host-specific development target, not a supported maximum CPU or latency promise.
The mixed 64-node/4096-note workload measured 340–357 us before removing unused
live-controller processing and 313 us after (mean over 2000 blocks); p99 varied
with system load. The measured hot-path change skips live voices/controller ramps
when neither is active and avoids finished-ramp calls. Exact CC/odd-block tests
continue to pass. No other graph optimization was justified by this measurement.
`test-scale` constructs all 64 tracks, 1024 clips, 1024 automation points and
4096 notes, compiles a standalone 256-node metered graph, renders stereo odd-sized
blocks and rejects capacity excesses. Project/GUI graphs remain capped at 64
nodes. `test-stress` runs publication, allocation/retirement, capacity and optional
GUI/timer/redraw tests while two ordinary CPU workers compete; subprocesses have
timeouts and workers are always terminated. Existing callback guards verify no
host allocation/free/loading/unloading. This does not qualify arbitrary plugins.
Callback work is bounded by documented node/frame/clip/note/event/point capacities.
Exceeding model/plan/mailbox capacities returns CAPACITY transactionally; invalid
or overlarge processing buffers are silenced and reported, JACK xruns are counted.
There is no CPU scheduler or preemption inside a DSP callback: an expensive trusted
plugin can miss a deadline or hang. Automated LADSPA lanes currently use run(1)
and bounded per-sample lane searches and may be costly; they are excluded from
the gain-chain baseline. Large WAV memory limits remain those in AUDIO_FILES.md.
Physical-device endurance, CPU-overload sound quality and a full GUI latency
benchmark remain unqualified.