Record retained extent-frame progress and remaining layout gap
This commit is contained in:
1 parent
035c7f20e8
commit
32151f7f9f
2 files changed
+83
-17
No files matched your search
+75
-16
@@ -423,7 +423,7 @@ The original proposal was implemented by Claude as `5fcace1` on
|
|||||||
`wip/region-and-placement` in `/home/bob/repos/iris-pr18`. It kept the fraction
|
`wip/region-and-placement` in `/home/bob/repos/iris-pr18`. It kept the fraction
|
||||||
reference stable but failed five layout cases and three draw-count cases.
|
reference stable but failed five layout cases and three draw-count cases.
|
||||||
The first correction is `efb416b`, exact recomposition is `2ed5503`, and the
|
The first correction is `efb416b`, exact recomposition is `2ed5503`, and the
|
||||||
current performance continuation is **`a7307d9`**, pushed to origin's
|
current performance continuation is **`c44bd19`**, pushed to origin's
|
||||||
`wip/region-and-placement`, in the isolated checkout
|
`wip/region-and-placement`, in the isolated checkout
|
||||||
`/home/bob/repos/iris-layout-experiment`; **it is not on PR #18**. The original
|
`/home/bob/repos/iris-layout-experiment`; **it is not on PR #18**. The original
|
||||||
checkout is unchanged. Keep the experiment's build directory separate: Cargo
|
checkout is unchanged. Keep the experiment's build directory separate: Cargo
|
||||||
@@ -517,22 +517,24 @@ regression fails with four draws instead of three when the optimization is
|
|||||||
disabled.
|
disabled.
|
||||||
|
|
||||||
**Still not ready to replace PR #18.** The prototype does substantially more
|
**Still not ready to replace PR #18.** The prototype does substantially more
|
||||||
nested layout work than `e44dea3`, even after removing intermediate placements
|
nested layout work than `e44dea3`, even after retaining extent-relative child
|
||||||
(seed 1, depth 8):
|
frames (seed 1, depth 8):
|
||||||
|
|
||||||
| phase | widget draws at e44dea3 | current | primitive writes at e44dea3 | current |
|
| phase | widget draws at e44dea3 | current | primitive writes at e44dea3 | current |
|
||||||
| --- | ---: | ---: | ---: | ---: |
|
| --- | ---: | ---: | ---: | ---: |
|
||||||
| cold | 369 | 484 | 9635 | 9179 |
|
| cold | 369 | 463 | 9635 | 9179 |
|
||||||
| repaint | 1 | 1 | 1 | 1 |
|
| repaint | 1 | 1 | 1 | 1 |
|
||||||
| many | 157 | 274 | 4721 | 5873 |
|
| many | 157 | 263.1 | 4721 | 5873 |
|
||||||
| size | 16 | 247 | 106 | 5200 |
|
| size | 16 | 240 | 106 | 5200 |
|
||||||
| scroll | 2 | 2 | 0 | 0 |
|
| scroll | 2 | 2 | 0 | 0 |
|
||||||
| resize | 13 | 292 | 0 | 5730 |
|
| resize | 13 | 278 | 0 | 5730 |
|
||||||
|
|
||||||
These are instrumented work counts, not speedups (50 frames per phase except
|
These are instrumented work counts, not speedups (50 frames per phase except
|
||||||
cold, which is one; 578 generated widgets, 191 finally active). Against
|
cold, which is one; 578 generated widgets, 191 finally active). The
|
||||||
`2ed5503`, the changes remove 7 widget draws and 525 primitive writes per size
|
measurement-only change at `7601aa2` removed 7 widget draws and 525
|
||||||
frame, and 8 draws and 525 writes per resize frame.
|
primitive writes per size frame, and 8 draws and 525 writes per resize frame,
|
||||||
|
relative to `2ed5503`. The extent-relative continuation below skips additional
|
||||||
|
container evaluations but does not reduce primitive writes.
|
||||||
|
|
||||||
**Measure cycles as well as instructions** (Bryan, 2026-09-17). The following
|
**Measure cycles as well as instructions** (Bryan, 2026-09-17). The following
|
||||||
are whole-process medians from seven alternating before/after runs of direct,
|
are whole-process medians from seven alternating before/after runs of direct,
|
||||||
@@ -578,7 +580,7 @@ executables under `perf stat -e cycles:u,instructions:u`, seed 1, depth 8,
|
|||||||
All nine samples per side were retained; before/after cycle ranges do not
|
All nine samples per side were retained; before/after cycle ranges do not
|
||||||
overlap. No scans or builds ran during measurement. All instrumented work
|
overlap. No scans or builds ran during measurement. All instrumented work
|
||||||
counters match `7601aa2` on all six phases (50 frames, cold once), including
|
counters match `7601aa2` on all six phases (50 frames, cold once), including
|
||||||
the draw and primitive counts in the table above: this reduces the cost of
|
the primitive counts in the table above: this reduces the cost of
|
||||||
emitting the repeated glyphs, not the repeated layout evaluations themselves.
|
emitting the repeated glyphs, not the repeated layout evaluations themselves.
|
||||||
|
|
||||||
Additional depth-6 fixtures, nine alternating pairs and 4000 frames each:
|
Additional depth-6 fixtures, nine alternating pairs and 4000 frames each:
|
||||||
@@ -602,14 +604,71 @@ saved under 0.8% of instructions and no cycles; special-casing equal endpoint
|
|||||||
fractions in `UiSpan::within` cost 11% cycles and 7% instructions despite still
|
fractions in `UiSpan::within` cost 11% cycles and 7% instructions despite still
|
||||||
inlining. Keep that hot general composition small.
|
inlining. Keep that hot general composition small.
|
||||||
|
|
||||||
|
**Child frames can now follow the extent without evaluating their container.**
|
||||||
|
`widget_within` accepts the same `DrawRegion::{Frame, Extent}` reference as
|
||||||
|
primitives and masks. `Pad` retains its pixel inset in extent coordinates;
|
||||||
|
`Stack` inherits placement for its sizing child and retains extent-relative
|
||||||
|
frames for its other children. Moving the extent replays those requests through
|
||||||
|
`ask_box`, preserving child alignment and region nodes. This extends the existing
|
||||||
|
inherited-child walk rather than adding a separate layout body or a second cache.
|
||||||
|
It stores a region-bearing relation per extent-following child, so retained
|
||||||
|
child records are larger than the old widget-id-only list.
|
||||||
|
|
||||||
|
Two dependencies stay conservative. Fractional endpoints compose before pixel
|
||||||
|
evaluation, so their bounds cannot in general be pulled back through the extent
|
||||||
|
length alone; those frames still depend on raw placement. Reading a child's
|
||||||
|
fractional report also depends on placement because composing that report into
|
||||||
|
the parent's frame can change its value without changing the child's answer.
|
||||||
|
Pixel-inset frame bounds use the existing exact `Holds::through`.
|
||||||
|
|
||||||
|
**Keep the measured slot when repositioning.** A first trial recomputed it from
|
||||||
|
`active.size`, which is the final draw's report. Text measured narrow and placed
|
||||||
|
wider may report a different height at the latter width; the slot is still the
|
||||||
|
one chosen from measurement. Seed 20/depth 4 caught this. The retained slot is
|
||||||
|
now preserved on axes not explicitly assigned by the parent. A small synthetic
|
||||||
|
width-dependent widget pins the same failure without fonts.
|
||||||
|
|
||||||
|
Against `a7307d9`, seed 1/depth 8 skips 21 draws cold, 10.9 per `many` frame,
|
||||||
|
7 per size frame and 14 per resize frame. Repaint, scroll, and all primitive-write
|
||||||
|
counts are unchanged. Nine alternating pairs of direct uninstrumented release
|
||||||
|
executables under `perf stat -e cycles:u,instructions:u`, including setup:
|
||||||
|
|
||||||
|
| phase | median cycles before → after (billions) | median instructions before → after (billions) |
|
||||||
|
| --- | ---: | ---: |
|
||||||
|
| size (2000 frames) | 4.0819 → 4.0714 | 10.4107 → 10.4017 |
|
||||||
|
| resize (2000 frames) | 4.8108 → 4.7237 | 12.1854 → 11.9252 |
|
||||||
|
| many (2000 frames) | 4.7918 → 4.7787 | 12.0925 → 12.0567 |
|
||||||
|
| repaint (1,000,000 frames) | 2.6701 → 2.6851 | 6.0175 → 6.0195 |
|
||||||
|
| scroll (300,000 frames) | 2.6296 → 2.6273 | 6.5025 → 6.5817 |
|
||||||
|
|
||||||
|
Only resize establishes a cycle improvement: **1.8%**, with nonoverlapping sample
|
||||||
|
ranges, and 2.1% fewer instructions. Every other phase's cycle ranges overlap;
|
||||||
|
scroll uses 1.2% more instructions. All samples were retained and no scans or
|
||||||
|
builds ran during measurement. This is a small reduction in work, not closure of
|
||||||
|
the main gap.
|
||||||
|
|
||||||
|
Verification: workspace formatting, clippy with `layout-diagnostics`, tests
|
||||||
|
(104 suite tests, 21 core tests), exact release scans of 2000 seeds/depth 4 and
|
||||||
|
1000/depth 6, the shrinker over 400 trees/depth 5, and a debug scan of 120
|
||||||
|
seeds/depth 4 with assertions enabled.
|
||||||
|
The new no-redraw test checks nested padding/stacks, fixed child
|
||||||
|
alignment, primitives, masks, and region nodes; restoring the old container
|
||||||
|
calls makes it fail with three draws instead of two. Additional tests cover
|
||||||
|
fractional reports and numeric dependencies. All five reference renders match
|
||||||
|
`a7307d9` pixel for pixel at 1920x1200, and the resized 900x1200 `tabs` matches a
|
||||||
|
cold render there. The GPU probe reports Venus on the RX 7900 XT.
|
||||||
|
|
||||||
**The remaining gap has not been established as an unavoidable correctness
|
**The remaining gap has not been established as an unavoidable correctness
|
||||||
cost.** A temporary failure trace of one frame on seed 1, depth 8 counted
|
cost.** Before the extent-relative change, a temporary failure trace of one
|
||||||
39/108 failed reuse attempts in size, 65/151 in resize, and 45/109 in many
|
frame on seed 1, depth 8 counted 39/108 failed reuse attempts in size, 65/151 in resize, and 45/109 in many
|
||||||
where only the raw placement snapshot differed: both numeric frame and extent
|
where only the raw placement snapshot differed: both numeric frame and extent
|
||||||
ranges still held. Containers read that snapshot to construct child positions,
|
ranges still held. Containers read that snapshot to construct child positions,
|
||||||
so discarding the check would be wrong; a way to retain those child positions
|
so discarding the check would be wrong. Padding and stacks now retain their
|
||||||
relative to the extent is the next protocol question. There is also necessary
|
extent-relative child frames, but `Span` still constructs its mixed-reference
|
||||||
width-dependent work: the hot text at widget 199 visits 68 px and 89.53613 px
|
slots from a raw placement read: along the row, child fractions refer to the
|
||||||
|
frame while cursor positions and leftover room refer to the extent. Retaining
|
||||||
|
those expressions without changing their fixed-point evaluation order is the
|
||||||
|
next protocol question. There is also necessary width-dependent work: the hot text at widget 199 visits 68 px and 89.53613 px
|
||||||
and reports different heights (316.80078 and 228.80078). It is evaluated
|
and reports different heights (316.80078 and 228.80078). It is evaluated
|
||||||
repeatedly at those widths, so that fact alone does not justify all the repeats.
|
repeatedly at those widths, so that fact alone does not justify all the repeats.
|
||||||
|
|
||||||
|
|||||||
+8
-1
@@ -879,7 +879,14 @@ prototype has significant container-update costs and is not yet adopted into
|
|||||||
the pinned framework. A container's length query can evaluate the offered extent
|
the pinned framework. A container's length query can evaluate the offered extent
|
||||||
without first placing the child's reported size; the parent's subsequent draw
|
without first placing the child's reported size; the parent's subsequent draw
|
||||||
assigns the final slot using the same `Widget::draw` body. A parent-selected slot
|
assigns the final slot using the same `Widget::draw` body. A parent-selected slot
|
||||||
still honors a fixed child's alignment within that slot.
|
still honors a fixed child's alignment within that slot. Child frames can also
|
||||||
|
retain an extent-relative region through `widget_within(DrawRegion::Extent)`;
|
||||||
|
padding and stacks use this instead of baking the current placement into child
|
||||||
|
coordinates. Pixel insets carry numeric validity through the extent. General
|
||||||
|
fractional endpoints and fractional reports retain conservative placement
|
||||||
|
dependencies; fixed-point composition must not be reassociated to remove them.
|
||||||
|
Retained movement preserves the slot chosen from measurement, even if the final
|
||||||
|
draw reports another size.
|
||||||
|
|
||||||
**A `Span` leaves its children in the offered orthogonal region unless
|
**A `Span` leaves its children in the offered orthogonal region unless
|
||||||
explicitly compacted** (2026-09-12). It still reports the widest orthogonal
|
explicitly compacted** (2026-09-12). It still reports the widest orthogonal
|
||||||
|
|||||||
Reference in new issue
Block a user