Files
FluidSimCpp/verification/V8_PIPE_PERFORMANCE.md
2026-10-23 18:29:51 +02:00

3.4 KiB

V8 pipe resolution and performance check

Measured on an Intel Core i5-12600K with GCC 16.2.1, Release (-O3, no fast-math). Each scenario run advances 44,100 frames in pedal mode. Uniform resolution runs rebuild every V8 pipe to the requested cells/m; cell counts are rounded up to whole cells, so short pipes can be slightly denser than the target.

Resolution sweep

Requested cells/m Wall time per simulated second Solver substeps/frame
Existing per-pipe meshes 0.429 s 1.00
20 0.421 s 1.00
30 0.793 s 1.53
33 0.886 s 1.74
35 0.979 s 1.80
36 1.048 s 1.82
40 1.151 s 1.89

Thirty-five cells/m was barely faster than real time on this host; 36 missed real time. The existing per-pipe mesh is substantially faster and remains the default. These are one-second runs at one workload and machine; they do not establish a cross-machine guarantee.

A second sweep held the V8 at 4,500 RPM (loaded mode), a steadier workload:

Requested cells/m Wall time per simulated second
Existing per-pipe meshes 0.424 s
25 0.552 s
30 0.830 s
32 0.951 s
33 0.983 s
34 1.049 s

Thirty-three cells/m only just stayed under real time, while 34 missed. For headroom, 25 cells/m took 0.55 s and 30 cells/m took 0.83 s; the existing per-pipe setting remains much faster.

Run with fluidsim_scenario_benchmark 1 pedal v8 <cells-per-meter>. The optional last argument affects only this benchmark's V8 instance and does not change application mesh defaults.

Pipe threading

The isolated pipe-advance benchmark used the same 35 cells/m V8 mesh and 4,000 steps. It measured 31.6 ms with one worker, 28.2 ms with two, and 23.4 ms with four. This is a 26% reduction in pipe-only time at four workers. Boundary resolution, engine components, and audio remain serial, and the measured gain does not include the extra synchronization needed to parallelize both pipe preparation and advancement in the full solver. Other small scenarios generally lost with worker threads. No threaded solver path was retained.

Run with fluidsim_thread_benchmark 35 to include the V8 mesh. Omitting the argument uses the original per-pipe V8 geometry.

SIMD and allocations

At 30 cells/m, a five-second V8 run averaged 0.646 s per simulated second with compiler vectorization enabled and 0.585 s with GCC vectorization disabled, excluding the first second from each average. State checksums and substep counts matched. This V8 result did not show a SIMD benefit; the project's existing optimization audit found SIMD useful for its other scenarios, so the global setting was left unchanged. A -march=native build did not improve the 33 cells/m run (0.891 s versus 0.886 s portable).

Pipe cell, face, state, wave, and next-state vectors are allocated when a pipe is constructed. Pipe1D::advance reuses those buffers and swaps the cell buffers; it performs no heap allocation per solver substep. Boundaries and component updates also use their setup-time storage. The desktop snapshot path does copy pipe geometry and states into fresh vectors each render frame; that is outside the audio sample update, but could be changed to reuse a persistent snapshot if UI allocation traffic becomes measurable.

An experiment that precomputed per-cell inverse volumes and area-gradient factors did not improve the V8 benchmark and was reverted.