Add depthSlice to GPURenderPassColorAttachment for 3D texture
- Add new depthSlice to GPURenderPassColorAttachment struct
- Allow 3d texture created as valid RenderAttachment
- Add depthSlice validation in RenderPassDescriptor
Bug: dawn:1020
Change-Id: Iea921aceb9c56809386375c733e1654bd4b82cec
Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/147180
Reviewed-by: Austin Eng <enga@chromium.org>
Reviewed-by: Corentin Wallez <cwallez@chromium.org>
Kokoro: Kokoro <noreply+kokoro@google.com>
Commit-Queue: Hao Li <hao.x.li@intel.com>
diff --git a/dawn.json b/dawn.json
index 1b00ca8..94152e3 100644
--- a/dawn.json
+++ b/dawn.json
@@ -2362,6 +2362,7 @@
"extensible": "in",
"members": [
{"name": "view", "type": "texture view", "optional": true},
+ {"name": "depth slice", "type": "uint32_t", "default": "0"},
{"name": "resolve target", "type": "texture view", "optional": true},
{"name": "load op", "type": "load op"},
{"name": "store op", "type": "store op"},
diff --git a/src/dawn/native/CommandEncoder.cpp b/src/dawn/native/CommandEncoder.cpp
index d7f675c..0ecd3cc 100644
--- a/src/dawn/native/CommandEncoder.cpp
+++ b/src/dawn/native/CommandEncoder.cpp
@@ -242,6 +242,27 @@
return {};
}
+MaybeError ValidateColorAttachmentDepthSlice(const TextureViewBase* attachment,
+ uint32_t depthSlice) {
+ if (attachment->GetDimension() == wgpu::TextureViewDimension::e3D) {
+ const Extent3D& attachmentSize =
+ attachment->GetTexture()->GetMipLevelSingleSubresourceVirtualSize(
+ attachment->GetBaseMipLevel());
+
+ DAWN_INVALID_IF(depthSlice >= attachmentSize.depthOrArrayLayers,
+ "The depth slice index (%u) of 3D %s used as attachment is >= the "
+ "depthOrArrayLayers (%u) of its subresource at mip level (%u).",
+ depthSlice, attachment, attachmentSize.depthOrArrayLayers,
+ attachment->GetBaseMipLevel());
+ } else {
+ DAWN_INVALID_IF(depthSlice != 0,
+ "The depth slice index (%u) of non-3D %s used as attachment is not 0.",
+ depthSlice, attachment);
+ }
+
+ return {};
+}
+
MaybeError ValidateColorAttachmentRenderToSingleSampled(
const DeviceBase* device,
const RenderPassColorAttachment& colorAttachment,
@@ -346,6 +367,7 @@
DAWN_TRY(ValidateResolveTarget(device, colorAttachment, usageValidationMode));
}
+ DAWN_TRY(ValidateColorAttachmentDepthSlice(attachment, colorAttachment.depthSlice));
DAWN_TRY(ValidateAttachmentArrayLayersAndLevelCount(attachment));
DAWN_TRY(ValidateOrSetAttachmentSize(attachment, width, height));
@@ -1030,6 +1052,8 @@
resolveTarget = descriptor->colorAttachments[i].resolveTarget;
cmd->colorAttachments[index].view = colorTarget;
+ cmd->colorAttachments[index].depthSlice =
+ descriptor->colorAttachments[i].depthSlice;
cmd->colorAttachments[index].loadOp = descriptor->colorAttachments[i].loadOp;
cmd->colorAttachments[index].storeOp = descriptor->colorAttachments[i].storeOp;
} else {
diff --git a/src/dawn/native/Commands.h b/src/dawn/native/Commands.h
index 135469a..66e4dc0 100644
--- a/src/dawn/native/Commands.h
+++ b/src/dawn/native/Commands.h
@@ -102,6 +102,7 @@
~RenderPassColorAttachmentInfo();
Ref<TextureViewBase> view;
+ uint32_t depthSlice;
Ref<TextureViewBase> resolveTarget;
wgpu::LoadOp loadOp;
wgpu::StoreOp storeOp;
diff --git a/src/dawn/native/Texture.cpp b/src/dawn/native/Texture.cpp
index b603301..c71430b 100644
--- a/src/dawn/native/Texture.cpp
+++ b/src/dawn/native/Texture.cpp
@@ -317,12 +317,19 @@
"format (%s).",
usage, wgpu::TextureUsage::RenderAttachment, format->format);
- DAWN_INVALID_IF(descriptor->dimension != wgpu::TextureDimension::e2D &&
+ DAWN_INVALID_IF(descriptor->dimension == wgpu::TextureDimension::e1D &&
(usage & wgpu::TextureUsage::RenderAttachment),
"The texture usage (%s) includes %s, which is incompatible with the texture "
"dimension (%s).",
usage, wgpu::TextureUsage::RenderAttachment, descriptor->dimension);
+ DAWN_INVALID_IF(!device->IsToggleEnabled(Toggle::AllowUnsafeAPIs) &&
+ descriptor->dimension == wgpu::TextureDimension::e3D &&
+ (usage & wgpu::TextureUsage::RenderAttachment),
+ "The texture dimension must not be %s for a render attachment if "
+ "allow_unsafe_apis is not enabled. See crbug.com/dawn/1020.",
+ wgpu::TextureDimension::e3D);
+
DAWN_INVALID_IF(
!format->supportsStorageUsage && (usage & wgpu::TextureUsage::StorageBinding),
"The texture usage (%s) includes %s, which is incompatible with the format (%s).", usage,
diff --git a/src/dawn/tests/unittests/validation/RenderPassDescriptorValidationTests.cpp b/src/dawn/tests/unittests/validation/RenderPassDescriptorValidationTests.cpp
index fe23ed7..e15373e 100644
--- a/src/dawn/tests/unittests/validation/RenderPassDescriptorValidationTests.cpp
+++ b/src/dawn/tests/unittests/validation/RenderPassDescriptorValidationTests.cpp
@@ -407,6 +407,67 @@
}
}
+// Depth slice index must be within the depth range of 3D color attachment and must be 0 for non-3D
+// color attachment.
+TEST_F(RenderPassDescriptorValidationTest, TextureViewDepthSliceForColor) {
+ constexpr uint32_t kSize = 8;
+ constexpr uint32_t kDepthOrArrayLayers = 4;
+ constexpr wgpu::TextureFormat kColorFormat = wgpu::TextureFormat::RGBA8Unorm;
+
+ wgpu::Texture colorTexture3D = CreateTexture(device, wgpu::TextureDimension::e3D, kColorFormat,
+ kSize, kSize, kDepthOrArrayLayers, 2);
+
+ wgpu::TextureView colorView2D = Create2DAttachment(device, kSize, kSize, kColorFormat);
+
+ wgpu::TextureViewDescriptor baseDescriptor;
+ baseDescriptor.dimension = wgpu::TextureViewDimension::e3D;
+ baseDescriptor.baseArrayLayer = 0;
+ baseDescriptor.arrayLayerCount = 1;
+ baseDescriptor.baseMipLevel = 0;
+ baseDescriptor.mipLevelCount = 1;
+
+ // Control case: Depth slice index within the depth range of 3D color attachment is valid.
+ {
+ wgpu::TextureView view = colorTexture3D.CreateView(&baseDescriptor);
+ utils::ComboRenderPassDescriptor renderPass({view});
+ renderPass.cColorAttachments[0].depthSlice = kDepthOrArrayLayers - 1;
+ AssertBeginRenderPassSuccess(&renderPass);
+ }
+
+ // Depth slice index out of the depth range of 3D color attachment is invalid.
+ {
+ wgpu::TextureView view = colorTexture3D.CreateView(&baseDescriptor);
+ utils::ComboRenderPassDescriptor renderPass({view});
+ renderPass.cColorAttachments[0].depthSlice = kDepthOrArrayLayers;
+ AssertBeginRenderPassError(&renderPass);
+ }
+
+ // Depth slice index out of the depth range of 3D color attachment with non-zero mip level is
+ // invalid.
+ {
+ wgpu::TextureViewDescriptor descriptor = baseDescriptor;
+ descriptor.baseMipLevel = 1;
+ wgpu::TextureView view = colorTexture3D.CreateView(&descriptor);
+ utils::ComboRenderPassDescriptor renderPass({view});
+ renderPass.cColorAttachments[0].depthSlice = kDepthOrArrayLayers >> 1;
+ AssertBeginRenderPassError(&renderPass);
+ }
+
+ // Control case: Depth slice must be 0 for non-3D color attachment.
+ {
+ utils::ComboRenderPassDescriptor renderPass({colorView2D});
+ renderPass.cColorAttachments[0].depthSlice = 0;
+ AssertBeginRenderPassSuccess(&renderPass);
+ }
+
+ // Non-zero depth slice is invalid for non-3D color attachment.
+ {
+ utils::ComboRenderPassDescriptor renderPass({colorView2D});
+ renderPass.cColorAttachments[0].depthSlice = 1;
+ AssertBeginRenderPassError(&renderPass);
+ }
+}
+
// Check that the render pass depth attachment must have the RenderAttachment usage.
TEST_F(RenderPassDescriptorValidationTest, DepthAttachmentInvalidUsage) {
// Control case: using a texture with RenderAttachment is valid.
diff --git a/src/dawn/tests/unittests/validation/TextureValidationTests.cpp b/src/dawn/tests/unittests/validation/TextureValidationTests.cpp
index 2391ae1..2cb0fc8 100644
--- a/src/dawn/tests/unittests/validation/TextureValidationTests.cpp
+++ b/src/dawn/tests/unittests/validation/TextureValidationTests.cpp
@@ -645,10 +645,10 @@
{wgpu::TextureDimension::e1D, wgpu::TextureDimension::e2D, wgpu::TextureDimension::e3D}};
for (wgpu::TextureDimension dimension : kTextureDimensions) {
descriptor.dimension = dimension;
- if (dimension == wgpu::TextureDimension::e2D) {
- device.CreateTexture(&descriptor);
- } else {
+ if (dimension == wgpu::TextureDimension::e1D) {
ASSERT_DEVICE_ERROR(device.CreateTexture(&descriptor));
+ } else {
+ device.CreateTexture(&descriptor);
}
}
}
diff --git a/webgpu-cts/expectations.txt b/webgpu-cts/expectations.txt
index e920813..f01c390 100644
--- a/webgpu-cts/expectations.txt
+++ b/webgpu-cts/expectations.txt
@@ -620,6 +620,11 @@
crbug.com/dawn/1970 [ android ] webgpu:web_platform,canvas,getCurrentTexture:single_frames:canvasType="onscreen" [ Failure ]
################################################################################
+# 3D texture is allowed to be created with usage RenderAttachment. These tests need to be updated once spec change is landed.
+################################################################################
+crbug.com/dawn/1020 webgpu:api,validation,createTexture:texture_usage:dimension="3d";* [ Failure ]
+
+################################################################################
# untriaged Android failures
################################################################################
crbug.com/dawn/0000 [ nvidia-0x2184 ubuntu ] webgpu:api,validation,texture,bgra8unorm_storage:configure_storage_usage_on_canvas_context_with_bgra8unorm_storage:* [ Failure ]