AtlatestRenderedmarkdown
Readme

test-shader-limits

The measured proof for the v0.11.3 shader additions, on native and on the web config: a Game of Life stepped entirely on the GPU (a step shader bound with with-shader inside with-render-target, ping-pong between two render targets), colours drawn from vec4 palette[8] and float levels[4] uniform arrays, and a 4x4 texture made from pixels and refilled with update-texture. verify.mjs reads the presented frame on each target and compares every cell against a CPU Life run of the same seed, every strip against the array entries, and every texel against the post-update pattern.

Native arm

Builds against the sigil-graphics checkout two directories up (dev-redirects.sgl). The app needs an X display; use a worker-owned Xvfb, never a real session.

guix shell xorg-server -- Xvfb :91 -screen 0 1400x900x24 +extension GLX -nolisten tcp &
guix shell -m ../../manifest.scm -- sh -c 'CPATH=$GUIX_ENVIRONMENT/include LIBRARY_PATH=$GUIX_ENVIRONMENT/lib sigil deps install --redirects dev-redirects.sgl && sigil build --redirects dev-redirects.sgl'
DISPLAY=:91 guix shell -m ../../manifest.scm imagemagick xdotool -- sh -c 'LD_LIBRARY_PATH=$GUIX_ENVIRONMENT/lib node verify.mjs --native'

The verifier runs build/dev/bin/test-shader-limits, waits for its shader-limits: ready line, captures the window with import -window, and prints one PASS/FAIL line per sub-arm, then GREEN/RED; exit 1 on any FAIL, 2 when a wait ran out or the setup was wrong (TIMED-OUT, SETUP-FAILED). The capture lands at /tmp/test-shader-limits-native.png.

Web arm

Needs binaryen (wasm-opt) for the build and google-chrome plus Node 22 for the verifier (headless Chrome with SwiftShader, driven over the DevTools Protocol, no puppeteer).

guix shell binaryen -- sigil build --redirects dev-redirects.sgl --config web
node verify.mjs --web

Adds two sub-arms: imports (the wasm imports only gl, sigil_wasm_gles3 and wasi) and console (no error entries). The page screenshot lands at /tmp/test-shader-limits-web.png.

Options

  • --grid N, --steps N: the field size (64) and the generations to run (8).
  • --expect-steps N: what the verifier models; different from --steps it must go RED (the assertion-layer control).
  • --rule reaction --steps 4000 --substeps 8 [--grid 128]: the Gray-Scott bonus: u and v packed into 16 bits each across the RGBA8 target (8 bits per quantity freezes the field), the step shader loaded with 'none blending. The field sub-arm then checks that a pattern grew from the three seed squares rather than comparing cells (there is no closed form), and the screenshot shows it.
  • --bench [--grid 512]: run the app in bench mode and print its frame-ms MEAN MAX tick-ms MEAN MAX lines (wall time between frames, and the tick's own step+present CPU time), no verdict.
  • --verbose (web): dump the page console, including sokol's log lines.

Running the app by hand: test-shader-limits [--grid N] [--steps N] [--rule life|reaction] [--substeps N] [--bench] [--hold SECONDS] natively; index.html?grid=N&steps=N&rule=NAME&substeps=N&bench on the web.

What it proves, and what it does not

Every cell of the field is compared, so a wrong neighbour offset, a wrong wrap (the glider crosses both torus edges), a wrong u_resolution inside the pass, a filtered read, or a pass that silently draws nothing all read as a FAIL; the sabotage legs that showed each of those going red are in the task note tasks/sigil-graphics-shader-limits. Frame timing under Xvfb (llvmpipe) and SwiftShader is software rendering on both arms: it bounds the CPU-side cost of a step, not what a phone's GPU will do.

Wayland arm

verify-wl.mjs is the native arm for a Wayland compositor the caller owns (a headless sway); it captures the window through swaymsg and grim instead of xdotool and import, and pins the window to the child's pid.

WAYLAND_DISPLAY=/run/user/$UID/<private>/wayland-1 SWAYSOCK=<its ipc socket> \
  guix shell -m ../../manifest.scm imagemagick grim jq -- \
  sh -c 'LD_LIBRARY_PATH=$GUIX_ENVIRONMENT/lib node verify-wl.mjs --native'

With sigil-desktop 0.10 the binary's NEEDED list is libm and libc only, so guix shell --pure -m <sigil-desktop>/guix/run-wayland.scm -- build/dev/bin/test-shader-limits runs it with no LD_LIBRARY_PATH at all (the runtime libraries resolve through sigil-desktop's dlopen fallback).