diff --git a/src/backends/dx/DXRuntime/UpdateTileTracker.cpp b/src/backends/dx/DXRuntime/UpdateTileTracker.cpp index 25853482e..7dfb7e3f0 100644 --- a/src/backends/dx/DXRuntime/UpdateTileTracker.cpp +++ b/src/backends/dx/DXRuntime/UpdateTileTracker.cpp @@ -9,11 +9,10 @@ void UpdateTileTracker::record( D3D12_TILE_RANGE_FLAGS RangeFlag, UINT HeapRangeStartOffset, UINT RangeTileCount) { - std::pair key{ - heap, - resource}; - auto iter = map.emplace(key); - auto &v = iter.value(); + auto iter = map.try_emplace(resource); + auto &heap_map = iter.first->second; + auto heap_iter = heap_map.update_tiles.try_emplace(heap); + auto &v = heap_iter.first->second; v.ResourceRegionStartCoordinates.emplace_back(ResourceRegionStartCoordinate); v.ResourceRegionSizes.emplace_back(ResourceRegionSize); v.RangeFlags.emplace_back(RangeFlag); @@ -24,39 +23,52 @@ void UpdateTileTracker::update( ID3D12CommandQueue *queue, D3D12_TILE_MAPPING_FLAGS Flags) { for (auto &kv : map) { - queue->UpdateTileMappings( - kv.first.second, - kv.second.ResourceRegionStartCoordinates.size(), - kv.second.ResourceRegionStartCoordinates.data(), - kv.second.ResourceRegionSizes.data(), - kv.first.first, kv.second.RangeFlags.size(), - kv.second.RangeFlags.data(), - kv.second.HeapRangeStartOffsets.data(), - kv.second.RangeTileCounts.data(), - Flags); - } - for (auto &kv : disp_map) { - queue->UpdateTileMappings( - kv.first, - kv.second.ResourceRegionStartCoordinates.size(), - kv.second.ResourceRegionStartCoordinates.data(), - kv.second.ResourceRegionSizes.data(), - nullptr, - 1, - vstd::get_rval_ptr(D3D12_TILE_RANGE_FLAG_NULL), - nullptr, - nullptr, - Flags); + if (!kv.second.ResourceRegionSizes.empty()) { + if (kv.second.update_tiles.empty()) { + queue->UpdateTileMappings( + kv.first, + kv.second.ResourceRegionStartCoordinates.size(), + kv.second.ResourceRegionStartCoordinates.data(), + kv.second.ResourceRegionSizes.data(), + nullptr, + 1, + vstd::get_rval_ptr(D3D12_TILE_RANGE_FLAG_NULL), + nullptr, + nullptr, + Flags); + } else { + auto &first_tile = kv.second.update_tiles.begin()->second; + vstd::push_back_all(first_tile.ResourceRegionStartCoordinates, vstd::span{kv.second.ResourceRegionStartCoordinates}); + vstd::push_back_all(first_tile.ResourceRegionSizes, vstd::span{kv.second.ResourceRegionSizes}); + vstd::push_back_all(first_tile.RangeFlags, kv.second.ResourceRegionSizes.size(), D3D12_TILE_RANGE_FLAG_NULL); + vstd::push_back_all(first_tile.HeapRangeStartOffsets, kv.second.ResourceRegionSizes.size(), 0); + vstd::push_back_func(first_tile.RangeTileCounts, kv.second.ResourceRegionSizes.size(), [&](size_t i) { + auto &size = first_tile.ResourceRegionSizes[i]; + return size.Width * static_cast(size.Height) * static_cast(size.Depth); + }); + } + } + for (auto &tile : kv.second.update_tiles) { + queue->UpdateTileMappings( + kv.first, + tile.second.ResourceRegionStartCoordinates.size(), + tile.second.ResourceRegionStartCoordinates.data(), + tile.second.ResourceRegionSizes.data(), + tile.first, tile.second.RangeFlags.size(), + tile.second.RangeFlags.data(), + tile.second.HeapRangeStartOffsets.data(), + tile.second.RangeTileCounts.data(), + Flags); + } } map.clear(); - disp_map.clear(); } void UpdateTileTracker::deallocate( ID3D12Resource *resource, D3D12_TILED_RESOURCE_COORDINATE const &ResourceRegionStartCoordinate, D3D12_TILE_REGION_SIZE const &ResourceRegionSize) { - auto iter = disp_map.emplace(resource); - auto &v = iter.value(); + auto iter = map.try_emplace(resource); + auto &v = iter.first->second; v.ResourceRegionStartCoordinates.emplace_back(ResourceRegionStartCoordinate); v.ResourceRegionSizes.emplace_back(ResourceRegionSize); } diff --git a/src/backends/dx/DXRuntime/UpdateTileTracker.h b/src/backends/dx/DXRuntime/UpdateTileTracker.h index a31aed670..92dbd2b74 100644 --- a/src/backends/dx/DXRuntime/UpdateTileTracker.h +++ b/src/backends/dx/DXRuntime/UpdateTileTracker.h @@ -4,18 +4,18 @@ namespace lc::dx { class UpdateTileTracker { struct UpdateTileCommand { - vstd::fixed_vectorResourceRegionStartCoordinates; - vstd::fixed_vectorResourceRegionSizes; - vstd::fixed_vectorRangeFlags; - vstd::fixed_vectorHeapRangeStartOffsets; - vstd::fixed_vectorRangeTileCounts; + vstd::fixed_vector ResourceRegionStartCoordinates; + vstd::fixed_vector ResourceRegionSizes; + vstd::fixed_vector RangeFlags; + vstd::fixed_vector HeapRangeStartOffsets; + vstd::fixed_vector RangeTileCounts; }; - struct DisposeTileTracker { - vstd::fixed_vectorResourceRegionStartCoordinates; - vstd::fixed_vectorResourceRegionSizes; + struct AllTileTracker { + vstd::unordered_map update_tiles; + vstd::fixed_vector ResourceRegionStartCoordinates; + vstd::fixed_vector ResourceRegionSizes; }; - vstd::HashMap, UpdateTileCommand> map; - vstd::HashMap disp_map; + vstd::unordered_map map; public: void record( ID3D12Heap *heap, @@ -33,4 +33,4 @@ class UpdateTileTracker { ID3D12CommandQueue *queue, D3D12_TILE_MAPPING_FLAGS Flags); }; -}// namespace lcdx \ No newline at end of file +}// namespace lc::dx \ No newline at end of file