fix(rendering): wait all frame fences before freeing shared descriptor sets

deferAfterFrameFence only waits for one frame slot's fence, but shared
resources (material descriptor sets, vertex/index buffers) are bound by
both in-flight frames' command buffers. On AMD RADV this caused
vkFreeDescriptorSets errors and eventual SIGSEGV.

Add deferAfterAllFrameFences: queues to every frame slot with a shared
counter so cleanup runs exactly once, after the last slot is fenced.
Use it for WMO, terrain, water, and character model shared resources.
Per-frame bone sets keep using deferAfterFrameFence (already correct).

Also fix character renderer vertex format: R8G8B8A8_UINT -> _SINT to
match shader's ivec4 input (RADV validation rejects the mismatch).
This commit is contained in:
Kelsi 2026-04-03 19:48:43 -07:00
parent def821055b
commit 3ac8c4d95f
6 changed files with 31 additions and 10 deletions

View file

@ -1972,7 +1972,7 @@ void WMORenderer::destroyGroupGPU(GroupResources& group, bool defer) {
}
VkDescriptorPool pool = materialDescPool_;
vkCtx_->deferAfterFrameFence([device, allocator, pool, vb, vbAlloc, ib, ibAlloc,
vkCtx_->deferAfterAllFrameFences([device, allocator, pool, vb, vbAlloc, ib, ibAlloc,
mats = std::move(mats)]() {
if (vb) vmaDestroyBuffer(allocator, vb, vbAlloc);
if (ib) vmaDestroyBuffer(allocator, ib, ibAlloc);