diff --git a/README.md b/README.md index 823c5d1..4747c77 100644 --- a/README.md +++ b/README.md @@ -11,7 +11,56 @@ no enrolment and no permissions. The rest of this file is the runbook that was delivered with the APKs. -**2026-09-08 (newest): nothing on the transcript is unbounded any more, +**2026-09-09 (newest): the fling. iris APK only** -- rebuilt from ai-app-2 +`42d54ee`; the Compose one is unchanged from 2026-09-08. + +You reported stuttering when flinging that is much harder to notice with +a finger on the scroll. Four things came out of it, and **two of them +were the report rather than the renderer** -- so read the new report +before reading the old numbers against it. + +- **The swapchain wait was being counted as iris's CPU time.** The call + that hands back an image to draw into *blocks* until the compositor + frees one, and it was inside the span the report called `cpu_p50`. An + app comfortably ahead of the display spends most of every frame there, + so a perfectly healthy fling read as several milliseconds of iris being + slow. Each phase now says `build / acquire / submit` separately, and + only `build` is work. +- **Nothing could say a frame was never produced.** `late` counts frames + that *cost* more than a budget -- but a late frame still appears on the + next refresh, while a frame that never happens leaves the previous one + on screen twice, and that is what a stutter is. Every phase now carries + `missed vsyncs`. That is the number to watch. +- **iris asked for its next frame at the end of the frame callback**, and + Android schedules that for the next refresh *after the call* -- so any + frame whose work ran past the boundary registered too late and got the + refresh after it. One frame over budget silently cost a second one. + Your fling phase ran at 103fps on a 120Hz screen, which is the shape + that makes. It asks first now. +- **The fling was advanced on the wall clock, not on the vsync the + callback carries.** Frames are shown on an even cadence whichever clock + computed them, so sampling the coast curve at "whenever the callback got + to run" moves the transcript by an uneven distance every frame -- with + no frame late enough to appear in any percentile. **This is most likely + the thing you were seeing**, and it explains why a finger on the screen + doesn't have it: a drag's positions come from the finger's own + timestamps and never went through that clock. + +Also `opt-level` for the Android build: it was tuned for size (`"s"`), +which costs a renderer its loop vectorisation. At `3`, iris's own +per-frame work over the same warm fling goes from p90 0.15ms / p99 0.42ms +to p90 0.09ms / p99 0.26ms. The APK grows 9.7 -> 11.5 MB; say if you'd +rather have the size. + +**What is worth reporting back**: whether the fling *feels* smoother with +a finger, and the `fling:` block's frame count and `missed vsyncs`. If the +count is near 120 x its seconds and `missed` is small, the loop is fixed; +if `missed` is still large, the cause is elsewhere and the new split says +where. The CPU side is already known not to be it -- a warm fling is p99 +0.26ms of layout, with only one frame in six laying anything out. + + +**2026-09-08: nothing on the transcript is unbounded any more, and both APKs are new.** Rebuilt from ai-app-2 `afbc2ad`. This one has things to look at, unlike the last. diff --git a/iris/build/outputs/apk/release/iris-bench-arm64.apk b/iris/build/outputs/apk/release/iris-bench-arm64.apk index 7a7d707..88ddbd2 100644 Binary files a/iris/build/outputs/apk/release/iris-bench-arm64.apk and b/iris/build/outputs/apk/release/iris-bench-arm64.apk differ