From e7025982129e79b42cb9e04666aa2962aebad645 Mon Sep 17 00:00:00 2001 From: Benson Joeris Date: Wed, 12 Jun 2019 11:18:44 -0400 Subject: [PATCH] Vulkan: `ImgRefs` now uses `ImageInfo`. Also added some additional `ImgRefs` tests for 3d images. Change-Id: I36805ef5135207e691a1c27e6b4fd0903bb8a4f3 --- renderdoc/driver/vulkan/imgrefs_tests.cpp | 115 ++++++++++++++++------ renderdoc/driver/vulkan/vk_resources.cpp | 12 +-- renderdoc/driver/vulkan/vk_resources.h | 68 ++++++------- 3 files changed, 127 insertions(+), 68 deletions(-) diff --git a/renderdoc/driver/vulkan/imgrefs_tests.cpp b/renderdoc/driver/vulkan/imgrefs_tests.cpp index 8f115ecb4..393aac50c 100644 --- a/renderdoc/driver/vulkan/imgrefs_tests.cpp +++ b/renderdoc/driver/vulkan/imgrefs_tests.cpp @@ -37,63 +37,63 @@ TEST_CASE("Test ImgRefs type", "[imgrefs]") { SECTION("unsplit") { - ImgRefs imgRefs(VK_IMAGE_TYPE_2D, VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT, 11, - 17, {100, 100, 1}); + ImgRefs imgRefs( + ImageInfo(VK_IMAGE_TYPE_2D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 1}, 11, 17, 1)); CHECK(imgRefs.SubresourceIndex(VK_IMAGE_ASPECT_STENCIL_BIT, 2, 5) == 0); }; SECTION("split aspect") { - ImgRefs imgRefs(VK_IMAGE_TYPE_2D, VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT, 11, - 17, {100, 100, 1}); + ImgRefs imgRefs( + ImageInfo(VK_IMAGE_TYPE_2D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 1}, 11, 17, 1)); imgRefs.Split(true, false, false); CHECK(imgRefs.SubresourceIndex(VK_IMAGE_ASPECT_STENCIL_BIT, 2, 5) == 1); }; SECTION("split levels") { - ImgRefs imgRefs(VK_IMAGE_TYPE_2D, VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT, 11, - 17, {100, 100, 1}); + ImgRefs imgRefs( + ImageInfo(VK_IMAGE_TYPE_2D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 1}, 11, 17, 1)); imgRefs.Split(false, true, false); CHECK(imgRefs.SubresourceIndex(VK_IMAGE_ASPECT_STENCIL_BIT, 2, 5) == 2); }; SECTION("split layers") { - ImgRefs imgRefs(VK_IMAGE_TYPE_2D, VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT, 11, - 17, {100, 100, 1}); + ImgRefs imgRefs( + ImageInfo(VK_IMAGE_TYPE_2D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 1}, 11, 17, 1)); imgRefs.Split(false, false, true); CHECK(imgRefs.SubresourceIndex(VK_IMAGE_ASPECT_STENCIL_BIT, 2, 5) == 5); }; SECTION("split aspect and levels") { - ImgRefs imgRefs(VK_IMAGE_TYPE_2D, VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT, 11, - 17, {100, 100, 1}); + ImgRefs imgRefs( + ImageInfo(VK_IMAGE_TYPE_2D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 1}, 11, 17, 1)); imgRefs.Split(true, true, false); CHECK(imgRefs.SubresourceIndex(VK_IMAGE_ASPECT_STENCIL_BIT, 2, 5) == 11 + 2); }; SECTION("split aspect and layers") { - ImgRefs imgRefs(VK_IMAGE_TYPE_2D, VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT, 11, - 17, {100, 100, 1}); + ImgRefs imgRefs( + ImageInfo(VK_IMAGE_TYPE_2D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 1}, 11, 17, 1)); imgRefs.Split(true, false, true); CHECK(imgRefs.SubresourceIndex(VK_IMAGE_ASPECT_STENCIL_BIT, 2, 5) == 17 + 5); }; SECTION("split levels and layers") { - ImgRefs imgRefs(VK_IMAGE_TYPE_2D, VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT, 11, - 17, {100, 100, 1}); + ImgRefs imgRefs( + ImageInfo(VK_IMAGE_TYPE_2D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 1}, 11, 17, 1)); imgRefs.Split(false, true, true); CHECK(imgRefs.SubresourceIndex(VK_IMAGE_ASPECT_STENCIL_BIT, 2, 5) == 2 * 17 + 5); }; SECTION("split aspect and levels and layers") { - ImgRefs imgRefs(VK_IMAGE_TYPE_2D, VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT, 11, - 17, {100, 100, 1}); + ImgRefs imgRefs( + ImageInfo(VK_IMAGE_TYPE_2D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 1}, 11, 17, 1)); imgRefs.Split(true, true, true); CHECK(imgRefs.SubresourceIndex(VK_IMAGE_ASPECT_STENCIL_BIT, 2, 5) == 11 * 17 + 2 * 17 + 5); }; SECTION("update unsplit") { - ImgRefs imgRefs(VK_IMAGE_TYPE_2D, VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT, 11, - 17, {100, 100, 1}); + ImgRefs imgRefs( + ImageInfo(VK_IMAGE_TYPE_2D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 1}, 11, 17, 1)); ImageRange range; imgRefs.Update(range, eFrameRef_Read); std::vector expected = {eFrameRef_Read}; @@ -101,8 +101,8 @@ TEST_CASE("Test ImgRefs type", "[imgrefs]") }; SECTION("update split aspect") { - ImgRefs imgRefs(VK_IMAGE_TYPE_2D, VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT, 11, - 17, {100, 100, 1}); + ImgRefs imgRefs( + ImageInfo(VK_IMAGE_TYPE_2D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 1}, 11, 17, 1)); ImageRange range; range.aspectMask = VK_IMAGE_ASPECT_STENCIL_BIT; imgRefs.Update(range, eFrameRef_Read); @@ -111,8 +111,8 @@ TEST_CASE("Test ImgRefs type", "[imgrefs]") }; SECTION("update split levels") { - ImgRefs imgRefs(VK_IMAGE_TYPE_2D, VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT, 11, - 17, {100, 100, 1}); + ImgRefs imgRefs( + ImageInfo(VK_IMAGE_TYPE_2D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 1}, 11, 17, 1)); ImageRange range; range.baseMipLevel = 1; range.levelCount = 3; @@ -125,8 +125,8 @@ TEST_CASE("Test ImgRefs type", "[imgrefs]") }; SECTION("update split layers") { - ImgRefs imgRefs(VK_IMAGE_TYPE_2D, VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT, 11, - 17, {100, 100, 1}); + ImgRefs imgRefs( + ImageInfo(VK_IMAGE_TYPE_2D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 1}, 11, 17, 1)); ImageRange range; range.baseArrayLayer = 7; imgRefs.Update(range, eFrameRef_Read); @@ -139,8 +139,8 @@ TEST_CASE("Test ImgRefs type", "[imgrefs]") }; SECTION("update split aspect then levels") { - ImgRefs imgRefs(VK_IMAGE_TYPE_2D, VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT, 11, - 17, {100, 100, 1}); + ImgRefs imgRefs( + ImageInfo(VK_IMAGE_TYPE_2D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 1}, 11, 17, 1)); ImageRange range0; range0.aspectMask = VK_IMAGE_ASPECT_STENCIL_BIT; imgRefs.Update(range0, eFrameRef_Read); @@ -162,8 +162,7 @@ TEST_CASE("Test ImgRefs type", "[imgrefs]") } SECTION("update split layers then aspects and levels") { - ImgRefs imgRefs(VK_IMAGE_TYPE_2D, VK_IMAGE_ASPECT_DEPTH_BIT | VK_IMAGE_ASPECT_STENCIL_BIT, 7, 5, - {100, 100, 1}); + ImgRefs imgRefs(ImageInfo(VK_IMAGE_TYPE_2D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 1}, 7, 5, 1)); ImageRange range0; range0.baseArrayLayer = 1; range0.layerCount = 2; @@ -209,6 +208,66 @@ TEST_CASE("Test ImgRefs type", "[imgrefs]") }; CHECK(imgRefs.rangeRefs == expected); } + SECTION("update 3D image default view") + { + ImgRefs imgRefs(ImageInfo(VK_IMAGE_TYPE_3D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 5}, 11, 1, 1)); + ImageRange range; + range.layerCount = 1; + imgRefs.Update(range, eFrameRef_Read); + std::vector expected = {eFrameRef_Read}; + CHECK(imgRefs.rangeRefs == expected); + } + SECTION("update 3D image 3D view") + { + ImgRefs imgRefs(ImageInfo(VK_IMAGE_TYPE_3D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 5}, 11, 1, 1)); + ImageRange range; + range.layerCount = 1; + range.viewType = VK_IMAGE_VIEW_TYPE_3D; + imgRefs.Update(range, eFrameRef_Read); + std::vector expected = {eFrameRef_Read}; + CHECK(imgRefs.rangeRefs == expected); + } + SECTION("update 3D image 2D view") + { + ImgRefs imgRefs(ImageInfo(VK_IMAGE_TYPE_3D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 5}, 11, 1, 1)); + ImageRange range; + range.layerCount = 1; + range.viewType = VK_IMAGE_VIEW_TYPE_2D; + imgRefs.Update(range, eFrameRef_Read); + std::vector expected = {eFrameRef_Read, eFrameRef_None, eFrameRef_None, + eFrameRef_None, eFrameRef_None}; + CHECK(imgRefs.rangeRefs == expected); + } + SECTION("update 3D image 2D array view") + { + ImgRefs imgRefs(ImageInfo(VK_IMAGE_TYPE_3D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 5}, 11, 1, 1)); + ImageRange range; + range.baseArrayLayer = 1; + range.layerCount = 2; + range.viewType = VK_IMAGE_VIEW_TYPE_2D_ARRAY; + imgRefs.Update(range, eFrameRef_Read); + std::vector expected = {eFrameRef_None, eFrameRef_Read, eFrameRef_Read, + eFrameRef_None, eFrameRef_None}; + CHECK(imgRefs.rangeRefs == expected); + } + SECTION("update 3D image 2D array view full") + { + ImgRefs imgRefs(ImageInfo(VK_IMAGE_TYPE_3D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 5}, 11, 1, 1)); + ImageRange range; + range.viewType = VK_IMAGE_VIEW_TYPE_2D_ARRAY; + imgRefs.Update(range, eFrameRef_Read); + std::vector expected = {eFrameRef_Read}; + CHECK(imgRefs.rangeRefs == expected); + } + SECTION("update 3D image 3D view full") + { + ImgRefs imgRefs(ImageInfo(VK_IMAGE_TYPE_3D, VK_FORMAT_D16_UNORM_S8_UINT, {100, 100, 5}, 11, 1, 1)); + ImageRange range; + range.viewType = VK_IMAGE_VIEW_TYPE_3D; + imgRefs.Update(range, eFrameRef_Read); + std::vector expected = {eFrameRef_Read}; + CHECK(imgRefs.rangeRefs == expected); + } }; #endif // ENABLED(ENABLE_UNIT_TESTS) diff --git a/renderdoc/driver/vulkan/vk_resources.cpp b/renderdoc/driver/vulkan/vk_resources.cpp index 66fd69171..e8518b4ed 100644 --- a/renderdoc/driver/vulkan/vk_resources.cpp +++ b/renderdoc/driver/vulkan/vk_resources.cpp @@ -2952,12 +2952,12 @@ int ImgRefs::SubresourceIndex(int aspectIndex, int level, int layer) const aspectIndex = 0; int splitLevelCount = 1; if(areLevelsSplit) - splitLevelCount = levelCount; + splitLevelCount = imageInfo.levelCount; else level = 0; int splitLayerCount = 1; if(areLayersSplit) - splitLayerCount = layerCount; + splitLayerCount = imageInfo.layerCount; else layer = 0; return (aspectIndex * splitLevelCount + level) * splitLayerCount + layer; @@ -2971,11 +2971,11 @@ void ImgRefs::Split(bool splitAspects, bool splitLevels, bool splitLayers) newSplitAspectCount = GetAspectCount(); } - int oldSplitLevelCount = areLevelsSplit ? levelCount : 1; - int newSplitLevelCount = splitLevels ? levelCount : oldSplitLevelCount; + int oldSplitLevelCount = areLevelsSplit ? imageInfo.levelCount : 1; + int newSplitLevelCount = splitLevels ? imageInfo.levelCount : oldSplitLevelCount; - int oldSplitLayerCount = areLayersSplit ? layerCount : 1; - int newSplitLayerCount = splitLayers ? layerCount : oldSplitLayerCount; + int oldSplitLayerCount = areLayersSplit ? imageInfo.layerCount : 1; + int newSplitLayerCount = splitLayers ? imageInfo.layerCount : oldSplitLayerCount; int newSize = newSplitAspectCount * newSplitLevelCount * newSplitLayerCount; if(newSize == (int)rangeRefs.size()) diff --git a/renderdoc/driver/vulkan/vk_resources.h b/renderdoc/driver/vulkan/vk_resources.h index 133fb07f4..0f8fc451d 100644 --- a/renderdoc/driver/vulkan/vk_resources.h +++ b/renderdoc/driver/vulkan/vk_resources.h @@ -888,6 +888,16 @@ struct ImageInfo VkFormat format = VK_FORMAT_UNDEFINED; VkImageType imageType = VK_IMAGE_TYPE_MAX_ENUM; ImageInfo() {} + ImageInfo(VkImageType imageType, VkFormat format, VkExtent3D extent, int levelCount, + int layerCount, int sampleCount) + : imageType(imageType), + format(format), + extent(extent), + levelCount(levelCount), + layerCount(layerCount), + sampleCount(sampleCount) + { + } ImageInfo(const VkImageCreateInfo &ci) : layerCount(ci.arrayLayers), levelCount(ci.mipLevels), @@ -1073,15 +1083,14 @@ struct ImageRange typedef BitFlagIterator ImageAspectFlagIter; +VkImageAspectFlags FormatImageAspects(VkFormat fmt); + struct ImgRefs { std::vector rangeRefs; - WrappedVkRes *initializedLiveRes; - VkImageType type; + WrappedVkRes *initializedLiveRes = NULL; + ImageInfo imageInfo; VkImageAspectFlags aspectMask; - int levelCount; - int layerCount; - VkExtent3D extent; bool areAspectsSplit = false; bool areLevelsSplit = false; @@ -1090,19 +1099,14 @@ struct ImgRefs int GetAspectCount() const; ImgRefs() : initializedLiveRes(NULL) {} - inline ImgRefs(VkImageType type, VkImageAspectFlags aspectMask, int levelCount, int layerCount, - VkExtent3D extent) + inline ImgRefs(const ImageInfo &imageInfo) : rangeRefs(1, eFrameRef_None), - initializedLiveRes(NULL), - type(type), - aspectMask(aspectMask), - levelCount(levelCount), - layerCount(layerCount), - extent(extent) + imageInfo(imageInfo), + aspectMask(FormatImageAspects(imageInfo.format)) { - if(type == VK_IMAGE_TYPE_3D) + if(imageInfo.imageType == VK_IMAGE_TYPE_3D) // Depth slices of 3D views are treated as array layers - layerCount = extent.depth; + this->imageInfo.layerCount = imageInfo.extent.depth; } int SubresourceIndex(VkImageAspectFlagBits aspect, int level, int layer) const; int SubresourceIndex(int aspectIndex, int level, int layer) const; @@ -1129,10 +1133,10 @@ struct ImgRefs template FrameRefType ImgRefs::Update(ImageRange range, FrameRefType refType, Compose comp) { - range.extent.width = RDCMIN(range.extent.width, extent.width - range.offset.x); - range.extent.height = RDCMIN(range.extent.height, extent.height - range.offset.y); + range.extent.width = RDCMIN(range.extent.width, imageInfo.extent.width - range.offset.x); + range.extent.height = RDCMIN(range.extent.height, imageInfo.extent.height - range.offset.y); - if(type == VK_IMAGE_TYPE_3D && range.viewType != VK_IMAGE_VIEW_TYPE_2D && + if(imageInfo.imageType == VK_IMAGE_TYPE_3D && range.viewType != VK_IMAGE_VIEW_TYPE_2D && range.viewType != VK_IMAGE_VIEW_TYPE_2D_ARRAY) { // The Vulkan spec allows 2D `VkImageView`s of 3D `VkImage`s--the depth slices of the images are @@ -1144,21 +1148,21 @@ FrameRefType ImgRefs::Update(ImageRange range, FrameRefType refType, Compose com // view). When a 3D image is accessed without a 2D view, we need to translate the Z axis into // array layer indices. - range.extent.depth = RDCMIN(range.extent.depth, extent.depth - range.offset.z); + range.extent.depth = RDCMIN(range.extent.depth, imageInfo.extent.depth - range.offset.z); range.baseArrayLayer = range.offset.z; range.layerCount = range.extent.depth; } else if(range.layerCount == VK_REMAINING_ARRAY_LAYERS) { - range.layerCount = layerCount - range.baseArrayLayer; + range.layerCount = imageInfo.layerCount - range.baseArrayLayer; } if(range.levelCount == VK_REMAINING_MIP_LEVELS) - range.levelCount = levelCount - range.baseMipLevel; + range.levelCount = imageInfo.levelCount - range.baseMipLevel; if(refType == eFrameRef_CompleteWrite && - (range.offset.x != 0 || range.offset.y != 0 || range.extent.width != extent.width || - range.extent.height != extent.height)) + (range.offset.x != 0 || range.offset.y != 0 || range.extent.width != imageInfo.extent.width || + range.extent.height != imageInfo.extent.height)) // Complete write, but only to part of the image. // We don't track writes at the pixel level, so turn this into a partial write refType = eFrameRef_PartialWrite; @@ -1176,8 +1180,8 @@ FrameRefType ImgRefs::Update(ImageRange range, FrameRefType refType, Compose com } Split(range.aspectMask != aspectMask, - range.baseMipLevel != 0 || (int)range.levelCount != levelCount, - range.baseArrayLayer != 0 || (int)range.layerCount != layerCount); + range.baseMipLevel != 0 || (int)range.levelCount != imageInfo.levelCount, + range.baseArrayLayer != 0 || (int)range.layerCount != imageInfo.layerCount); std::vector splitAspects; if(areAspectsSplit) @@ -1197,7 +1201,7 @@ FrameRefType ImgRefs::Update(ImageRange range, FrameRefType refType, Compose com int levelEnd = 1; if(areLevelsSplit) { - splitLevelCount = levelCount; + splitLevelCount = imageInfo.levelCount; levelEnd = (int)(range.baseMipLevel + range.levelCount); } @@ -1205,7 +1209,7 @@ FrameRefType ImgRefs::Update(ImageRange range, FrameRefType refType, Compose com int layerEnd = 1; if(areLayersSplit) { - splitLayerCount = layerCount; + splitLayerCount = imageInfo.layerCount; layerEnd = (int)(range.baseArrayLayer + range.layerCount); } @@ -1237,9 +1241,9 @@ FrameRefType ImgRefs::Merge(const ImgRefs &other, Compose comp) if(areAspectsSplit) splitAspectCount = GetAspectCount(); - int splitLevelCount = areLevelsSplit ? levelCount : 1; + int splitLevelCount = areLevelsSplit ? imageInfo.levelCount : 1; - int splitLayerCount = areLayersSplit ? layerCount : 1; + int splitLayerCount = areLayersSplit ? imageInfo.layerCount : 1; FrameRefType maxRefType = eFrameRef_None; for(int aspectIndex = 0; aspectIndex < splitAspectCount; ++aspectIndex) @@ -1627,11 +1631,7 @@ FrameRefType MarkImageReferenced(std::map &imgRefs, Resourc auto refs = imgRefs.find(img); if(refs == imgRefs.end()) { - refs = imgRefs - .insert(std::make_pair( - img, ImgRefs(imageInfo.imageType, FormatImageAspects(imageInfo.format), - imageInfo.levelCount, imageInfo.layerCount, imageInfo.extent))) - .first; + refs = imgRefs.insert(std::make_pair(img, ImgRefs(imageInfo))).first; } return refs->second.Update(range, refType, comp); }