D3D12: Skip dynamic buffer bindings with None visibility
This was hitting an ASSERT because D3D12 doesn't have an option to set None as the shader visibility. Bug: dawn:448 Change-Id: I3e056e531e7d1bb89da1736bc609bfe97a2fa194 Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/22324 Reviewed-by: Bryan Bernhart <bryan.bernhart@intel.com> Commit-Queue: Austin Eng <enga@chromium.org>
This commit is contained in:
parent
0e3c27de6a
commit
3b7d0858bf
|
@ -230,6 +230,14 @@ namespace dawn_native { namespace d3d12 {
|
||||||
// Dynamic buffer bindings are packed at the beginning of the layout.
|
// Dynamic buffer bindings are packed at the beginning of the layout.
|
||||||
for (BindingIndex bindingIndex = 0; bindingIndex < dynamicOffsetCount;
|
for (BindingIndex bindingIndex = 0; bindingIndex < dynamicOffsetCount;
|
||||||
++bindingIndex) {
|
++bindingIndex) {
|
||||||
|
const BindingInfo& bindingInfo =
|
||||||
|
group->GetLayout()->GetBindingInfo(bindingIndex);
|
||||||
|
if (bindingInfo.visibility == wgpu::ShaderStage::None) {
|
||||||
|
// Skip dynamic buffers that are not visible. D3D12 does not have None
|
||||||
|
// visibility.
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
uint32_t parameterIndex =
|
uint32_t parameterIndex =
|
||||||
pipelineLayout->GetDynamicRootParameterIndex(index, bindingIndex);
|
pipelineLayout->GetDynamicRootParameterIndex(index, bindingIndex);
|
||||||
BufferBinding binding = group->GetBindingAsBufferBinding(bindingIndex);
|
BufferBinding binding = group->GetBindingAsBufferBinding(bindingIndex);
|
||||||
|
@ -241,7 +249,7 @@ namespace dawn_native { namespace d3d12 {
|
||||||
D3D12_GPU_VIRTUAL_ADDRESS bufferLocation =
|
D3D12_GPU_VIRTUAL_ADDRESS bufferLocation =
|
||||||
ToBackend(binding.buffer)->GetVA() + offset;
|
ToBackend(binding.buffer)->GetVA() + offset;
|
||||||
|
|
||||||
switch (group->GetLayout()->GetBindingInfo(bindingIndex).type) {
|
switch (bindingInfo.type) {
|
||||||
case wgpu::BindingType::UniformBuffer:
|
case wgpu::BindingType::UniformBuffer:
|
||||||
if (mInCompute) {
|
if (mInCompute) {
|
||||||
commandList->SetComputeRootConstantBufferView(parameterIndex,
|
commandList->SetComputeRootConstantBufferView(parameterIndex,
|
||||||
|
|
|
@ -136,6 +136,12 @@ namespace dawn_native { namespace d3d12 {
|
||||||
const BindingInfo& bindingInfo =
|
const BindingInfo& bindingInfo =
|
||||||
bindGroupLayout->GetBindingInfo(dynamicBindingIndex);
|
bindGroupLayout->GetBindingInfo(dynamicBindingIndex);
|
||||||
|
|
||||||
|
if (bindingInfo.visibility == wgpu::ShaderStage::None) {
|
||||||
|
// Skip dynamic buffers that are not visible. D3D12 does not have None
|
||||||
|
// visibility.
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
D3D12_ROOT_PARAMETER* rootParameter = &rootParameters[parameterIndex];
|
D3D12_ROOT_PARAMETER* rootParameter = &rootParameters[parameterIndex];
|
||||||
|
|
||||||
// Setup root descriptor.
|
// Setup root descriptor.
|
||||||
|
@ -195,6 +201,8 @@ namespace dawn_native { namespace d3d12 {
|
||||||
ASSERT(group < kMaxBindGroups);
|
ASSERT(group < kMaxBindGroups);
|
||||||
ASSERT(bindingIndex < kMaxBindingsPerGroup);
|
ASSERT(bindingIndex < kMaxBindingsPerGroup);
|
||||||
ASSERT(GetBindGroupLayout(group)->GetBindingInfo(bindingIndex).hasDynamicOffset);
|
ASSERT(GetBindGroupLayout(group)->GetBindingInfo(bindingIndex).hasDynamicOffset);
|
||||||
|
ASSERT(GetBindGroupLayout(group)->GetBindingInfo(bindingIndex).visibility !=
|
||||||
|
wgpu::ShaderStage::None);
|
||||||
return mDynamicRootParameterIndices[group][bindingIndex];
|
return mDynamicRootParameterIndices[group][bindingIndex];
|
||||||
}
|
}
|
||||||
}} // namespace dawn_native::d3d12
|
}} // namespace dawn_native::d3d12
|
||||||
|
|
|
@ -863,6 +863,38 @@ TEST_P(BindGroupTests, BindGroupLayoutVisibilityCanBeNone) {
|
||||||
queue.Submit(1, &commands);
|
queue.Submit(1, &commands);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Regression test for crbug.com/dawn/448 that dynamic buffer bindings can have None visibility.
|
||||||
|
TEST_P(BindGroupTests, DynamicBindingNoneVisibility) {
|
||||||
|
utils::BasicRenderPass renderPass = utils::CreateBasicRenderPass(device, kRTSize, kRTSize);
|
||||||
|
|
||||||
|
wgpu::BindGroupLayoutEntry entry = {0, wgpu::ShaderStage::None,
|
||||||
|
wgpu::BindingType::UniformBuffer, true};
|
||||||
|
wgpu::BindGroupLayoutDescriptor descriptor;
|
||||||
|
descriptor.entryCount = 1;
|
||||||
|
descriptor.entries = &entry;
|
||||||
|
wgpu::BindGroupLayout layout = device.CreateBindGroupLayout(&descriptor);
|
||||||
|
|
||||||
|
wgpu::RenderPipeline pipeline = MakeTestPipeline(renderPass, {}, {layout});
|
||||||
|
|
||||||
|
std::array<float, 4> color = {1, 0, 0, 1};
|
||||||
|
wgpu::Buffer uniformBuffer =
|
||||||
|
utils::CreateBufferFromData(device, &color, sizeof(color), wgpu::BufferUsage::Uniform);
|
||||||
|
wgpu::BindGroup bindGroup =
|
||||||
|
utils::MakeBindGroup(device, layout, {{0, uniformBuffer, 0, sizeof(color)}});
|
||||||
|
|
||||||
|
uint32_t dynamicOffset = 0;
|
||||||
|
|
||||||
|
wgpu::CommandEncoder encoder = device.CreateCommandEncoder();
|
||||||
|
wgpu::RenderPassEncoder pass = encoder.BeginRenderPass(&renderPass.renderPassInfo);
|
||||||
|
pass.SetPipeline(pipeline);
|
||||||
|
pass.SetBindGroup(0, bindGroup, 1, &dynamicOffset);
|
||||||
|
pass.Draw(3);
|
||||||
|
pass.EndPass();
|
||||||
|
|
||||||
|
wgpu::CommandBuffer commands = encoder.Finish();
|
||||||
|
queue.Submit(1, &commands);
|
||||||
|
}
|
||||||
|
|
||||||
// Test that bind group bindings may have unbounded and arbitrary binding numbers
|
// Test that bind group bindings may have unbounded and arbitrary binding numbers
|
||||||
TEST_P(BindGroupTests, ArbitraryBindingNumbers) {
|
TEST_P(BindGroupTests, ArbitraryBindingNumbers) {
|
||||||
utils::BasicRenderPass renderPass = utils::CreateBasicRenderPass(device, kRTSize, kRTSize);
|
utils::BasicRenderPass renderPass = utils::CreateBasicRenderPass(device, kRTSize, kRTSize);
|
||||||
|
|
Loading…
Reference in New Issue