From feb3ca4d28c753c89c5a83d2b3fb5f5f4cac1350 Mon Sep 17 00:00:00 2001 From: Panos <25664832+mechpanos@users.noreply.github.com> Date: Tue, 8 Sep 2026 11:58:33 +0300 Subject: [PATCH] perf: split the arena patch's post-work into its three steps MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit With the selection-filter rebuild gone, a drawn point costs 98 ms and `prepare` is 93 % of it: wire 73.0ms arena-patch wires=236961 gpu_instances=405551 wire-cull 5.1ms face3d-upload 3.9ms text-upload 3.0ms resident-patch 1.0ms changes=1 draw-depth-patch 0.0ms `arena-base ok=true patch=Some(16) changes=1` — the arena patches incrementally, one entity, and still takes 73 ms. The patch itself is careful; the three steps that follow it are not, and all three are O(resident set) rather than O(changes): partition_wires(&vp_wires, …) 236 961 wires, every frame upload_block_wires(…instanced…) 10 719 placements rebuilt upload_circles/ellipses_from_instances `arena-post partition= blocks= curves=` says which dominates. Guessing between three plausible candidates is what the earlier rounds of this work paid for repeatedly. Co-Authored-By: Claude Opus 5 --- src/scene/view/render.rs | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/src/scene/view/render.rs b/src/scene/view/render.rs index b25fb4810..faf1a165b 100644 --- a/src/scene/view/render.rs +++ b/src/scene/view/render.rs @@ -839,8 +839,15 @@ impl shader::Primitive for Primitive { gpus.extend(arena.wire_gpus()); } inner.gpu_wires = std::sync::Arc::new(gpus); + // A one-entity patch costs 73 ms in this block, and the + // three steps below are all O(resident set) rather than + // O(changes). Which of them dominates decides the fix. + let t_part = _perf.then(iced::time::Instant::now); let partitioned = wire_arena::partition_wires(&vp_wires, &draw_depths); + let part_ms = t_part + .map_or(0.0, |t| t.elapsed().as_secs_f64() * 1000.0); + let t_blk = _perf.then(iced::time::Instant::now); inner.gpu_block_wires = std::sync::Arc::new( inner.upload_block_wires( device, @@ -850,6 +857,9 @@ impl shader::Primitive for Primitive { &mut pipeline.block_geometry, ), ); + let blk_ms = t_blk + .map_or(0.0, |t| t.elapsed().as_secs_f64() * 1000.0); + let t_curve = _perf.then(iced::time::Instant::now); inner.gpu_circles = std::sync::Arc::new( inner.upload_circles_from_instances( device, @@ -864,6 +874,17 @@ impl shader::Primitive for Primitive { &partitioned.ellipse_instances, ), ); + if _perf { + crate::perf_record!( + "[perf] arena-post partition={part_ms:.1}ms blocks={blk_ms:.1}ms \ +curves={:.1}ms wires={} instanced={} circles={} ellipses={}", + t_curve.map_or(0.0, |t| t.elapsed().as_secs_f64() * 1000.0), + vp_wires.len(), + partitioned.instanced.len(), + partitioned.circle_instances.len(), + partitioned.ellipse_instances.len(), + ); + } if _patched { wire_arena::patch_handle_index( &mut inner.wire_handle_index,