Add dynamic attribute in bind group layout binding
WebGPU remove dynamic-uniform-buffer and dynamic-storage-buffer but add a new attribute in
BindgroupLayoutBinding to record whether a buffer resource is dynamic.
Dawn need to align with this change.
BUG=dawn:180
Change-Id: I873ad2ec75575e72d184f89a6e3698dff6df50d7
Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/8520
Commit-Queue: Corentin Wallez <cwallez@chromium.org>
Reviewed-by: Corentin Wallez <cwallez@chromium.org>
diff --git a/dawn.json b/dawn.json
index cfb0db3..4b1f6e2 100644
--- a/dawn.json
+++ b/dawn.json
@@ -55,7 +55,8 @@
"members": [
{"name": "binding", "type": "uint32_t"},
{"name": "visibility", "type": "shader stage bit"},
- {"name": "type", "type": "binding type"}
+ {"name": "type", "type": "binding type"},
+ {"name": "dynamic", "type": "bool", "default": "false" }
]
},
"bind group layout descriptor": {
@@ -70,11 +71,9 @@
"category": "enum",
"values": [
{"value": 0, "name": "uniform buffer"},
- {"value": 1, "name": "sampler"},
- {"value": 2, "name": "sampled texture"},
- {"value": 3, "name": "storage buffer"},
- {"value": 4, "name": "dynamic uniform buffer"},
- {"value": 5, "name": "dynamic storage buffer"}
+ {"value": 1, "name": "storage buffer"},
+ {"value": 2, "name": "sampler"},
+ {"value": 3, "name": "sampled texture"}
]
},
"blend descriptor": {
diff --git a/examples/Animometer.cpp b/examples/Animometer.cpp
index da68552..a90546c 100644
--- a/examples/Animometer.cpp
+++ b/examples/Animometer.cpp
@@ -111,7 +111,7 @@
})");
dawn::BindGroupLayout bgl = utils::MakeBindGroupLayout(
- device, {{0, dawn::ShaderStageBit::Vertex, dawn::BindingType::DynamicUniformBuffer}});
+ device, {{0, dawn::ShaderStageBit::Vertex, dawn::BindingType::UniformBuffer, true}});
utils::ComboRenderPipelineDescriptor descriptor(device);
descriptor.layout = utils::MakeBasicPipelineLayout(device, &bgl);
diff --git a/src/dawn_native/BindGroup.cpp b/src/dawn_native/BindGroup.cpp
index 93af9bf..a6db7cf 100644
--- a/src/dawn_native/BindGroup.cpp
+++ b/src/dawn_native/BindGroup.cpp
@@ -126,18 +126,23 @@
// Perform binding-type specific validation.
switch (layoutInfo.types[bindingIndex]) {
case dawn::BindingType::UniformBuffer:
- case dawn::BindingType::DynamicUniformBuffer:
DAWN_TRY(ValidateBufferBinding(device, binding, dawn::BufferUsageBit::Uniform));
break;
case dawn::BindingType::StorageBuffer:
- case dawn::BindingType::DynamicStorageBuffer:
DAWN_TRY(ValidateBufferBinding(device, binding, dawn::BufferUsageBit::Storage));
break;
case dawn::BindingType::SampledTexture:
+ if (layoutInfo.dynamic[bindingIndex]) {
+ return DAWN_VALIDATION_ERROR(
+ "SampledTextures are expected to be not dynamic");
+ }
DAWN_TRY(
ValidateTextureBinding(device, binding, dawn::TextureUsageBit::Sampled));
break;
case dawn::BindingType::Sampler:
+ if (layoutInfo.dynamic[bindingIndex]) {
+ return DAWN_VALIDATION_ERROR("Samplers are expected to be not dynamic");
+ }
DAWN_TRY(ValidateSamplerBinding(device, binding));
break;
}
@@ -207,10 +212,7 @@
ASSERT(binding < kMaxBindingsPerGroup);
ASSERT(mLayout->GetBindingInfo().mask[binding]);
ASSERT(mLayout->GetBindingInfo().types[binding] == dawn::BindingType::UniformBuffer ||
- mLayout->GetBindingInfo().types[binding] == dawn::BindingType::StorageBuffer ||
- mLayout->GetBindingInfo().types[binding] ==
- dawn::BindingType::DynamicUniformBuffer ||
- mLayout->GetBindingInfo().types[binding] == dawn::BindingType::DynamicStorageBuffer);
+ mLayout->GetBindingInfo().types[binding] == dawn::BindingType::StorageBuffer);
BufferBase* buffer = static_cast<BufferBase*>(mBindings[binding].Get());
return {buffer, mOffsets[binding], mSizes[binding]};
}
diff --git a/src/dawn_native/BindGroupLayout.cpp b/src/dawn_native/BindGroupLayout.cpp
index 4e94e9f..9dcdce4 100644
--- a/src/dawn_native/BindGroupLayout.cpp
+++ b/src/dawn_native/BindGroupLayout.cpp
@@ -87,8 +87,8 @@
mBindingInfo.visibilities[index] = binding.visibility;
mBindingInfo.types[index] = binding.type;
- if (binding.type == dawn::BindingType::DynamicUniformBuffer ||
- binding.type == dawn::BindingType::DynamicStorageBuffer) {
+ if (binding.dynamic) {
+ mBindingInfo.dynamic.set(index);
mDynamicBufferCount++;
}
diff --git a/src/dawn_native/BindGroupLayout.h b/src/dawn_native/BindGroupLayout.h
index decc68f..c2b5d8c 100644
--- a/src/dawn_native/BindGroupLayout.h
+++ b/src/dawn_native/BindGroupLayout.h
@@ -42,6 +42,7 @@
struct LayoutBindingInfo {
std::array<dawn::ShaderStageBit, kMaxBindingsPerGroup> visibilities;
std::array<dawn::BindingType, kMaxBindingsPerGroup> types;
+ std::bitset<kMaxBindingsPerGroup> dynamic;
std::bitset<kMaxBindingsPerGroup> mask;
};
const LayoutBindingInfo& GetBindingInfo() const;
diff --git a/src/dawn_native/CommandEncoder.cpp b/src/dawn_native/CommandEncoder.cpp
index 4a66f23..f306a01 100644
--- a/src/dawn_native/CommandEncoder.cpp
+++ b/src/dawn_native/CommandEncoder.cpp
@@ -588,14 +588,12 @@
dawn::BindingType type = layoutInfo.types[i];
switch (type) {
- case dawn::BindingType::UniformBuffer:
- case dawn::BindingType::DynamicUniformBuffer: {
+ case dawn::BindingType::UniformBuffer: {
BufferBase* buffer = group->GetBindingAsBufferBinding(i).buffer;
tracker->BufferUsedAs(buffer, dawn::BufferUsageBit::Uniform);
} break;
- case dawn::BindingType::StorageBuffer:
- case dawn::BindingType::DynamicStorageBuffer: {
+ case dawn::BindingType::StorageBuffer: {
BufferBase* buffer = group->GetBindingAsBufferBinding(i).buffer;
tracker->BufferUsedAs(buffer, dawn::BufferUsageBit::Storage);
} break;
diff --git a/src/dawn_native/ShaderModule.cpp b/src/dawn_native/ShaderModule.cpp
index ac025e6..6313eab 100644
--- a/src/dawn_native/ShaderModule.cpp
+++ b/src/dawn_native/ShaderModule.cpp
@@ -66,17 +66,6 @@
return {};
}
- dawn::BindingType NonDynamicBindingType(dawn::BindingType type) {
- switch (type) {
- case dawn::BindingType::DynamicUniformBuffer:
- return dawn::BindingType::UniformBuffer;
- case dawn::BindingType::DynamicStorageBuffer:
- return dawn::BindingType::StorageBuffer;
- default:
- return type;
- }
- }
-
// ShaderModuleBase
ShaderModuleBase::ShaderModuleBase(DeviceBase* device,
@@ -247,9 +236,7 @@
continue;
}
- // DynamicUniformBuffer and DynamicStorageBuffer are uniform buffer and
- // storage buffer in shader. Need to translate them.
- if (NonDynamicBindingType(layoutBindingType) != moduleInfo.type) {
+ if (layoutBindingType != moduleInfo.type) {
return false;
}
diff --git a/src/dawn_native/d3d12/BindGroupD3D12.cpp b/src/dawn_native/d3d12/BindGroupD3D12.cpp
index e81db4d..4c1dbae 100644
--- a/src/dawn_native/d3d12/BindGroupD3D12.cpp
+++ b/src/dawn_native/d3d12/BindGroupD3D12.cpp
@@ -97,10 +97,6 @@
} break;
// TODO(shaobo.yan@intel.com): Implement dynamic buffer offset.
- case dawn::BindingType::DynamicUniformBuffer:
- case dawn::BindingType::DynamicStorageBuffer:
- UNREACHABLE();
- break;
}
}
diff --git a/src/dawn_native/d3d12/BindGroupLayoutD3D12.cpp b/src/dawn_native/d3d12/BindGroupLayoutD3D12.cpp
index f97eebb..ac419ce 100644
--- a/src/dawn_native/d3d12/BindGroupLayoutD3D12.cpp
+++ b/src/dawn_native/d3d12/BindGroupLayoutD3D12.cpp
@@ -38,10 +38,6 @@
mBindingOffsets[binding] = mDescriptorCounts[Sampler]++;
break;
// TODO(shaobo.yan@intel.com): Implement dynamic buffer offset.
- case dawn::BindingType::DynamicUniformBuffer:
- case dawn::BindingType::DynamicStorageBuffer:
- UNREACHABLE();
- break;
}
}
@@ -101,10 +97,6 @@
mBindingOffsets[binding] += descriptorOffsets[Sampler];
break;
// TODO(shaobo.yan@intel.com): Implement dynamic buffer offset.
- case dawn::BindingType::DynamicUniformBuffer:
- case dawn::BindingType::DynamicStorageBuffer:
- UNREACHABLE();
- break;
}
}
}
diff --git a/src/dawn_native/metal/CommandBufferMTL.mm b/src/dawn_native/metal/CommandBufferMTL.mm
index b037285..1970f3e 100644
--- a/src/dawn_native/metal/CommandBufferMTL.mm
+++ b/src/dawn_native/metal/CommandBufferMTL.mm
@@ -235,7 +235,14 @@
case dawn::BindingType::StorageBuffer: {
BufferBinding binding = group->GetBindingAsBufferBinding(bindingIndex);
const id<MTLBuffer> buffer = ToBackend(binding.buffer)->GetMTLBuffer();
- const NSUInteger offset = binding.offset;
+ NSUInteger offset = binding.offset;
+
+ // TODO(shaobo.yan@intel.com): Record bound buffer status to use
+ // setBufferOffset to achieve better performance.
+ if (layout.dynamic[bindingIndex]) {
+ offset += dynamicOffsets[currentDynamicBufferIndex];
+ currentDynamicBufferIndex++;
+ }
if (hasVertStage) {
[render setVertexBuffers:&buffer
@@ -285,34 +292,6 @@
[compute setTexture:textureView->GetMTLTexture() atIndex:computeIndex];
}
} break;
-
- // TODO(shaobo.yan@intel.com): Record bound buffer status to use setBufferOffset
- // to achieve better performance.
- case dawn::BindingType::DynamicUniformBuffer:
- case dawn::BindingType::DynamicStorageBuffer: {
- ASSERT(currentDynamicBufferIndex < dynamicOffsetCount);
- BufferBinding binding = group->GetBindingAsBufferBinding(bindingIndex);
- const id<MTLBuffer> buffer = ToBackend(binding.buffer)->GetMTLBuffer();
- NSUInteger offset =
- binding.offset + dynamicOffsets[currentDynamicBufferIndex];
- currentDynamicBufferIndex += 1;
-
- if (hasVertStage) {
- [render setVertexBuffers:&buffer
- offsets:&offset
- withRange:NSMakeRange(vertIndex, 1)];
- }
- if (hasFragStage) {
- [render setFragmentBuffers:&buffer
- offsets:&offset
- withRange:NSMakeRange(fragIndex, 1)];
- }
- if (hasComputeStage) {
- [compute setBuffers:&buffer
- offsets:&offset
- withRange:NSMakeRange(computeIndex, 1)];
- }
- } break;
}
}
}
diff --git a/src/dawn_native/metal/PipelineLayoutMTL.mm b/src/dawn_native/metal/PipelineLayoutMTL.mm
index 640feca..9912f94 100644
--- a/src/dawn_native/metal/PipelineLayoutMTL.mm
+++ b/src/dawn_native/metal/PipelineLayoutMTL.mm
@@ -42,8 +42,6 @@
switch (groupInfo.types[binding]) {
case dawn::BindingType::UniformBuffer:
case dawn::BindingType::StorageBuffer:
- case dawn::BindingType::DynamicUniformBuffer:
- case dawn::BindingType::DynamicStorageBuffer:
mIndexInfo[stage][group][binding] = bufferIndex;
bufferIndex++;
break;
diff --git a/src/dawn_native/opengl/CommandBufferGL.cpp b/src/dawn_native/opengl/CommandBufferGL.cpp
index c1a3d45..2b064eb 100644
--- a/src/dawn_native/opengl/CommandBufferGL.cpp
+++ b/src/dawn_native/opengl/CommandBufferGL.cpp
@@ -266,11 +266,7 @@
binding.offset, binding.size);
} break;
- // TODO(shaobo.yan@intel.com): Implement dynamic buffer offset.
- case dawn::BindingType::DynamicUniformBuffer:
- case dawn::BindingType::DynamicStorageBuffer:
- UNREACHABLE();
- break;
+ // TODO(shaobo.yan@intel.com): Implement dynamic buffer offset.
}
}
}
diff --git a/src/dawn_native/opengl/PipelineGL.cpp b/src/dawn_native/opengl/PipelineGL.cpp
index 697ab82..645dac2 100644
--- a/src/dawn_native/opengl/PipelineGL.cpp
+++ b/src/dawn_native/opengl/PipelineGL.cpp
@@ -136,10 +136,6 @@
break;
// TODO(shaobo.yan@intel.com): Implement dynamic buffer offset.
- case dawn::BindingType::DynamicUniformBuffer:
- case dawn::BindingType::DynamicStorageBuffer:
- UNREACHABLE();
- break;
}
}
}
diff --git a/src/dawn_native/opengl/PipelineLayoutGL.cpp b/src/dawn_native/opengl/PipelineLayoutGL.cpp
index e646fef..d8278a6 100644
--- a/src/dawn_native/opengl/PipelineLayoutGL.cpp
+++ b/src/dawn_native/opengl/PipelineLayoutGL.cpp
@@ -55,10 +55,6 @@
break;
// TODO(shaobo.yan@intel.com): Implement dynamic buffer offset
- case dawn::BindingType::DynamicUniformBuffer:
- case dawn::BindingType::DynamicStorageBuffer:
- UNREACHABLE();
- break;
}
}
}
diff --git a/src/dawn_native/vulkan/BindGroupLayoutVk.cpp b/src/dawn_native/vulkan/BindGroupLayoutVk.cpp
index 83f5838..fb22153 100644
--- a/src/dawn_native/vulkan/BindGroupLayoutVk.cpp
+++ b/src/dawn_native/vulkan/BindGroupLayoutVk.cpp
@@ -39,20 +39,22 @@
} // anonymous namespace
- VkDescriptorType VulkanDescriptorType(dawn::BindingType type) {
+ VkDescriptorType VulkanDescriptorType(dawn::BindingType type, bool isDynamic) {
switch (type) {
case dawn::BindingType::UniformBuffer:
+ if (isDynamic) {
+ return VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC;
+ }
return VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER;
case dawn::BindingType::Sampler:
return VK_DESCRIPTOR_TYPE_SAMPLER;
case dawn::BindingType::SampledTexture:
return VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE;
case dawn::BindingType::StorageBuffer:
+ if (isDynamic) {
+ return VK_DESCRIPTOR_TYPE_STORAGE_BUFFER_DYNAMIC;
+ }
return VK_DESCRIPTOR_TYPE_STORAGE_BUFFER;
- case dawn::BindingType::DynamicUniformBuffer:
- return VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC;
- case dawn::BindingType::DynamicStorageBuffer:
- return VK_DESCRIPTOR_TYPE_STORAGE_BUFFER_DYNAMIC;
default:
UNREACHABLE();
}
@@ -70,7 +72,8 @@
for (uint32_t bindingIndex : IterateBitSet(info.mask)) {
auto& binding = bindings[numBindings];
binding.binding = bindingIndex;
- binding.descriptorType = VulkanDescriptorType(info.types[bindingIndex]);
+ binding.descriptorType =
+ VulkanDescriptorType(info.types[bindingIndex], info.dynamic[bindingIndex]);
binding.descriptorCount = 1;
binding.stageFlags = VulkanShaderStageFlags(info.visibilities[bindingIndex]);
binding.pImmutableSamplers = nullptr;
@@ -122,14 +125,12 @@
auto ToDescriptorType = [](dawn::BindingType type) -> DescriptorType {
switch (type) {
case dawn::BindingType::UniformBuffer:
- case dawn::BindingType::DynamicUniformBuffer:
return UNIFORM_BUFFER;
case dawn::BindingType::Sampler:
return SAMPLER;
case dawn::BindingType::SampledTexture:
return SAMPLED_IMAGE;
case dawn::BindingType::StorageBuffer:
- case dawn::BindingType::DynamicStorageBuffer:
return STORAGE_BUFFER;
default:
UNREACHABLE();
@@ -145,7 +146,8 @@
if (descriptorTypeIndex[type] == -1) {
descriptorTypeIndex[type] = numSizes;
- result[numSizes].type = VulkanDescriptorType(info.types[bindingIndex]);
+ result[numSizes].type =
+ VulkanDescriptorType(info.types[bindingIndex], info.dynamic[bindingIndex]);
result[numSizes].descriptorCount = 1;
numSizes++;
} else {
diff --git a/src/dawn_native/vulkan/BindGroupLayoutVk.h b/src/dawn_native/vulkan/BindGroupLayoutVk.h
index 6a6d8cd..37cfbc5 100644
--- a/src/dawn_native/vulkan/BindGroupLayoutVk.h
+++ b/src/dawn_native/vulkan/BindGroupLayoutVk.h
@@ -23,7 +23,7 @@
class Device;
- VkDescriptorType VulkanDescriptorType(dawn::BindingType type);
+ VkDescriptorType VulkanDescriptorType(dawn::BindingType type, bool isDynamic);
class BindGroupLayout : public BindGroupLayoutBase {
public:
diff --git a/src/dawn_native/vulkan/BindGroupVk.cpp b/src/dawn_native/vulkan/BindGroupVk.cpp
index a1ef1c7..f321c68 100644
--- a/src/dawn_native/vulkan/BindGroupVk.cpp
+++ b/src/dawn_native/vulkan/BindGroupVk.cpp
@@ -77,13 +77,12 @@
write.dstBinding = bindingIndex;
write.dstArrayElement = 0;
write.descriptorCount = 1;
- write.descriptorType = VulkanDescriptorType(layoutInfo.types[bindingIndex]);
+ write.descriptorType = VulkanDescriptorType(layoutInfo.types[bindingIndex],
+ layoutInfo.dynamic[bindingIndex]);
switch (layoutInfo.types[bindingIndex]) {
case dawn::BindingType::UniformBuffer:
- case dawn::BindingType::StorageBuffer:
- case dawn::BindingType::DynamicUniformBuffer:
- case dawn::BindingType::DynamicStorageBuffer: {
+ case dawn::BindingType::StorageBuffer: {
BufferBinding binding = GetBindingAsBufferBinding(bindingIndex);
writeBufferInfo[numWrites].buffer = ToBackend(binding.buffer)->GetHandle();
diff --git a/src/tests/end2end/DynamicBufferOffsetTests.cpp b/src/tests/end2end/DynamicBufferOffsetTests.cpp
index d880a74..cfb89a0 100644
--- a/src/tests/end2end/DynamicBufferOffsetTests.cpp
+++ b/src/tests/end2end/DynamicBufferOffsetTests.cpp
@@ -47,9 +47,9 @@
mBindGroupLayout = utils::MakeBindGroupLayout(
device, {{0, dawn::ShaderStageBit::Compute | dawn::ShaderStageBit::Fragment,
- dawn::BindingType::DynamicUniformBuffer},
+ dawn::BindingType::UniformBuffer, true},
{1, dawn::ShaderStageBit::Compute | dawn::ShaderStageBit::Fragment,
- dawn::BindingType::DynamicStorageBuffer}});
+ dawn::BindingType::StorageBuffer, true}});
mBindGroup = utils::MakeBindGroup(
device, mBindGroupLayout,
diff --git a/src/tests/unittests/validation/BindGroupValidationTests.cpp b/src/tests/unittests/validation/BindGroupValidationTests.cpp
index bcccdb5..db7dfd1 100644
--- a/src/tests/unittests/validation/BindGroupValidationTests.cpp
+++ b/src/tests/unittests/validation/BindGroupValidationTests.cpp
@@ -456,9 +456,9 @@
void SetUp() override {
mBindGroupLayout = utils::MakeBindGroupLayout(
device, {{0, dawn::ShaderStageBit::Compute | dawn::ShaderStageBit::Fragment,
- dawn::BindingType::DynamicUniformBuffer},
+ dawn::BindingType::UniformBuffer, true},
{1, dawn::ShaderStageBit::Compute | dawn::ShaderStageBit::Fragment,
- dawn::BindingType::DynamicStorageBuffer}});
+ dawn::BindingType::StorageBuffer, true}});
}
dawn::Buffer CreateBuffer(uint64_t bufferSize, dawn::BufferUsageBit usage) {