Merge pull request 'perf(mesh): dirty-range vertex upload for deforming-mesh Refit (#119)' (#138) from claude/issue-119 into master
This commit is contained in:
commit
e3edb87c0f
5 changed files with 199 additions and 8 deletions
|
|
@ -157,6 +157,42 @@ int main() {
|
|||
Check(tri.blasAddr == triAddrBefore,
|
||||
"Refit kept the same blasAddr (instances stay valid)");
|
||||
|
||||
// Dirty-range refit (issue #119): move only a sub-window of the vertices
|
||||
// and pass it as [offset, count). The ranged upload patches just those
|
||||
// vertices in place; the UPDATE must still keep the same AS handle /
|
||||
// blasAddr, and the validation layer (checked at the end) is the real proof
|
||||
// that the ranged host-write / flush / barrier — and the staged variant
|
||||
// below — are spec-correct. The untouched vertices retain their last values
|
||||
// in the device buffer, so the refit BLAS is over the full deformed cube.
|
||||
{
|
||||
// Full array of moved positions; we declare only the back half [4,8)
|
||||
// as the dirty window, so only those 4 vertices are re-uploaded.
|
||||
auto verts = CubeVerts(2.0f);
|
||||
auto idx = CubeIndices();
|
||||
VkCommandBuffer cmd = BeginCmd();
|
||||
tri.Refit(verts, idx, /*dirtyVertexOffset*/ 4, /*dirtyVertexCount*/ 4, cmd);
|
||||
SubmitWait(cmd);
|
||||
}
|
||||
Check(tri.accelerationStructure == triHandleBefore,
|
||||
"dirty-range Refit kept the same AS handle (in-place UPDATE, #119)");
|
||||
Check(tri.blasAddr == triAddrBefore,
|
||||
"dirty-range Refit kept the same blasAddr (#119)");
|
||||
|
||||
// A dirty-range refit on a mesh whose counts changed must still fall back
|
||||
// to a full rebuild (the dirty window is irrelevant on that path) and
|
||||
// succeed — same robustness as the full-span Refit fallback.
|
||||
{
|
||||
auto verts = CubeVerts(1.0f);
|
||||
verts.push_back({2.0f, 2.0f, 2.0f}); // count change → topology change
|
||||
auto idx = CubeIndices();
|
||||
idx.insert(idx.end(), {0u, 1u, 8u});
|
||||
VkCommandBuffer cmd = BeginCmd();
|
||||
tri.Refit(verts, idx, /*dirtyVertexOffset*/ 8, /*dirtyVertexCount*/ 1, cmd);
|
||||
SubmitWait(cmd);
|
||||
}
|
||||
Check(tri.blasAddr != 0 && tri.builtPrimitiveCount == 13,
|
||||
"dirty-range Refit with a count change rebuilt the BLAS (13 prims, #119)");
|
||||
|
||||
// ── Triangle BLAS: fast-build, no update → flags reflect the choice. ─
|
||||
Mesh triFast;
|
||||
{
|
||||
|
|
@ -340,6 +376,19 @@ int main() {
|
|||
Check(staged.accelerationStructure == stagedHandle,
|
||||
"staged-upload Refit kept the same AS handle (in-place UPDATE, #73)");
|
||||
|
||||
// Dirty-range refit on the staged path (#119): the ranged upload must
|
||||
// take the stage-a-sub-slice + vkCmdCopyBuffer-at-offset path (the
|
||||
// buffer is pure DEVICE_LOCAL), keep the AS handle, and stay
|
||||
// validation-clean. Only the front half [0,4) is declared dirty.
|
||||
{
|
||||
auto verts3 = CubeVerts(2.0f);
|
||||
VkCommandBuffer cmd = BeginCmd();
|
||||
staged.Refit(verts3, idx, /*dirtyVertexOffset*/ 0, /*dirtyVertexCount*/ 4, cmd);
|
||||
SubmitWait(cmd);
|
||||
}
|
||||
Check(staged.accelerationStructure == stagedHandle,
|
||||
"staged-upload dirty-range Refit kept the same AS handle (#119)");
|
||||
|
||||
Device::directWriteBudget = savedBudget;
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue