evidence · 6.3 KiB

README.md

Committed at docs/evidence/card-shell/throw-sampling/README.md. This is what grounds the requirements that cite it.

Open raw source

Preserve throw velocity across repeated millisecond timestamps

The policy previously set velocity to zero whenever two consecutive motion events had the same millisecond timestamp. A valid upward movement followed by another movement or a duplicate endpoint in that timestamp then failed to request close. This is independently reproduced in the actual C policy and the cross-built compositor’s native wlroots input path.

The policy now measures those samples from the preceding distinct timestamp. Coordinates still update on every event. A same-time downward reversal resets the velocity reference conservatively, and motion with no elapsed interval cannot throw. A later stationary sample, slow drag and held release continue to reject close. The 120-pixel displacement, 0.4-pixel/ms speed and 150-ms release-age thresholds are unchanged, as are dispatch-time close deadlines, graceful close/refusal behavior and performance budgets.

Host and native runtime proof

python3 tests/test_card_shell_state.py
TMPDIR=/mnt/MediaVolume/home/jadams nix build .#card-shell \
  --max-jobs 1 --cores 8 --no-link --print-out-paths
python3 tests/card_shell_runtime.py --native-touch --delayed-touch \
  --sway /nix/store/d7pxj3jviq5ghax97hy98fnqlmhbiy0f-sway-unwrapped-riscv64-unknown-linux-gnu-1.12/bin/sway \
  --client /nix/store/6nskh3ldk3ya7mwxbb258qszrxhw2i61-card-composition-probe-client-0.1/bin/card-composition-probe-client \
  --output NEW_HEADLESS_DIRECTORY

All 23 compiled policy cases pass with address/undefined-behavior sanitizers. Two new case groups cover duplicate and advancing same-time endpoints, a zero-duration whole movement, same-time reversal, a later stationary sample, slow movement and held release. The new positive group fails with the original policy from base 4ba9f58a; its other 22 cases pass.

build.json identifies the built package and source hashes. headless.json records 17 compositor runtime checks and eight independent source-timing checks, including repeated-timestamp close and reversal/held-release rejection. This executes the RISC-V compositor under QEMU user emulation with native Wayland clients and wlroots/cursor/seat routing, not a full Linux guest.

For the runtime negative control, substitute the previous timestamp-corrected Sway /nix/store/bggwbi2nx72c494xpjvgyi98yxz3w3c0-sway-unwrapped-riscv64-unknown-linux-gnu-1.12/bin/sway in the same command. It passes the preceding timing checks, then fails waiting for the first same-millisecond motion close request. negative-control.json records that expected exit 1 and the exact runtime-test hash.

Remaining physical gate

This does not establish the cause of the four intermittent upward-throw misses in the RVV comparison. Its input injector’s absolute scheduling deadlines can produce bursts after a delay, but those runs did not retain the individual gesture source timestamps needed for attribution. Three unchanged injected board workload repeats now observe all thirteen interaction checks apiece; see the physical report below. Real-finger acceptance, default-image integration and all failed card cost budgets remain open. The normal image has not changed.

Three physical-board repeats

board/result.json records three unchanged card-shell-acceptance.py runs on normal system gnr36q…, using published fix revision 33962837dd8a6dfc20d2ee944f321d45808b11df and package mp0bqh… from build.json. All 39/39 interaction checks were OBSERVED, including each upward-throw request, refusal, timeout, accepted close and normal-control route. Each run verified the running Sway executable and restored normal shell/seatd. These are injected-input observations, not reviewed new pictures or physical fingers.

The root-only bounded runner is committed as run-board.py. Stage it beside exactly the three published session, acceptance and budget tools; their hashes are in the board result. The actual command, within a transient root service with a 1,800-second outer deadline, was:

python3 /var/lib/k230/card-throw-tools-33962837/run-board.py \
  --board --revision 33962837dd8a6dfc20d2ee944f321d45808b11df \
  --output /var/lib/k230/card-throw-sampling-33962837

Each session had the independent root watchdog, a 540-second compositor limit, and a 480-second acceptance timeout. The three runs retain the same normal kernel, panel, Pixman renderer, configuration, client, 24 drags per card count, and existing benchmark producer. transfer.json records SHA256 verification of the 23 named text files; raw process logs and native pictures were excluded.

All six workload budgets still FAIL. All reports were reconstructed exactly from committed telemetry, excluding only the newly generated report timestamp. comparison.json preserves the per-run summary without a speedup claim.

RepeatCardsFramesFrame CPU p95 / max msTracking p95 ms
1114416.574 / 49.31257.475
1213923.663 / 25.89657.474
2113816.511 / 49.61257.478
2214323.726 / 25.41157.478
3114216.309 / 48.92057.477
3215023.843 / 26.93457.478

The unchanged CPU limits are p95 16.667 ms / max 33.334 ms; tracking p95 is 33.334 ms. Frame CPU and tracking fail in every workload; the other declared input/release/memory metrics pass. Reproduce each complete report with:

python3 tools/card-shell-benchmark.py --board \
  --input docs/evidence/card-shell/throw-sampling/board/run-1/public/telemetry.log \
  --manifest docs/evidence/card-shell/throw-sampling/board/run-1/public/manifest.json \
  --output /tmp/card-throw-repeat-1-budget.json

Exit 1 is expected for the retained budget failure; repeat for runs 2 and 3. normal-restoration.json and its serial record independently check the normal system, shell, seatd, Wi-Fi HTTPS, protected boot/firmware hashes and root layout. Its repeat phase compares against the committed storage baseline; no reboot or flash occurred during this trial, and its boot ID matches the three runs.

Three successful injected repeats support this fix but are not a reliability estimate or a matched before/after board attribution. The previous failures remain committed. Card tasks 4.2, 5.1 and 5.3 stay open: repaint/cadence cost, default-image integration and focused real-finger acceptance still need proof.