AVPlumber · Mixer cookbook

6. Browser frames go back one per new frame

Browsers run Chromium's ordinary capture. The compositor samples each captured buffer in place, and finished frames go back one per new frame so Chromium's capture pool stops allocating.

Updated 15 October 2026 at 159d0182, which removed the fixed-pool export Electron and the mixer's copy on import. These pages describe that code and named workload settings; they do not assert what every deployment runs.

One path: ordinary capture, sampled in place

Stock Electron with the GBM shim, in the Docker image and in a direct npm install. Chromium copies each painted frame into a buffer of its capture pool and lends it to dma-browser, which sends it to the mixer as a DMA-BUF. The importer maps the buffer and the compositor samples it there; the mixer makes no copy of its own.

Setting Effect
browser_frame_queue 9 (the window's ringSize) Bounds the frames a window has sent and the mixer has not yet acknowledged; it does not bound Chromium's allocations.
return_queue 3 Finished frames wait in the receiver and go back one per new frame, so the pool gets one buffer back for each it lends and stops destroying and allocating buffers.
Imports: the queue plus three, idle for 10 s Each window keeps its recycling buffers registered; a registration unused for ten seconds is released, and the start releases the startup's unused ones before going on air.

No copy on import, no fixed pool

On the 192-input L4 show (15 October 2026), Chromium's ordinary capture sampled in place ran with the browser uncapped, no missed deadline and no repeated browser frame. That run's browser was the export build with the feature off, and its importers had the fixed-pool settings (no return queue, nine registrations that never expire); the settings above are the ordinary ones the fixed pool had replaced. The same show with the mixer copying each browser frame on import stalled the whole GPU within a minute. That copy and the fixed-pool export Electron it was built for are gone: the browser image runs stock Electron, and the importer only maps Chromium's capture buffers.

Ring size is not compositor latency, and a bounded queue does not guarantee no source repeats. Keep both import-churn and on-air delivery counters.

Measured scope

The moving-window transition checks on the limits page were taken on the removed fixed pool with a copy on import; they are not a measurement of this path.

Implementation