perf(buffer): reuse staging via a per-frame-in-flight ring in UploadDeviceLocal (#120) #139
No reviewers
Labels
No milestone
No project
No assignees
1 participant
Notifications
Due date
No due date set.
Dependencies
No dependencies set.
Reference
Catcrafts/Crafter.Graphics!139
Loading…
Add table
Add a link
Reference in a new issue
No description provided.
Delete branch "claude/issue-120"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Problem
On non-ReBAR hardware the staged branch of
VulkanBuffer::UploadDeviceLocal(interfaces/Crafter.Graphics-VulkanBuffer.cppm:281-300) didCreate(create+getreq+alloc+map) +DeferredClear(later free) per call.Mesh::Refit/RecordProceduralBuildhit this every frame for deforming meshes — a full device-memory alloc/free cycle per mesh per frame, on exactly the hardware the staged path targets.Fix
A persistent per-buffer staging ring sized to a high-water mark, reallocated only on growth (via
Resize, which defers the outgrown allocation) — mirroring the TLAS instance/metadata high-water reuse.Why a ring and not a single shared buffer
The
vkCmdCopyBufferstill reads the staging buffer after the call returns (the reason the old code usedDeferredClear). With frames pipelinedframesInFlightdeep, overwriting one shared staging buffer next frame would clobber data the previous frame's copy is still reading. Indexing byframeCounter % framesInFlightgives each in-flight frame its own slot; a slot is rewritten only afterframesInFlightframes have elapsed — the exact window after which single-queue submission order (the same guarantee the #101 deletion queue relies on) ensures that copy has completed.No ReBAR/UMA regression
The ring is grown lazily, on first entry into the staged branch. ReBAR/UMA hardware always takes the direct-write
ifbranch and never touches the ring, so it never constructs a staging allocation it doesn't use — a runtime no-op there, a straight upgrade on non-resizable-BAR machines.Testing
crafter-build test— 21 passed. Directly relevant:BLASBuildOptions— exercises the staged Build→Refit path (the ring's core reuse case) with zero validation errors.DeferredDeletion,MeshDecompressStagingRelease,TLASHighWaterMark,VulkanBufferResizeReuse.Backend/invisible change — no screenshot.
Resolves #120