Validate SetVertexBuffers' slot is less than kMaxVertexBuffers

Bug: chromium:1034808
Change-Id: Ibad70a7cd7b4e30b5b885e9373cc40db16768c72
Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/14840
Reviewed-by: Austin Eng <enga@chromium.org>
Reviewed-by: Kai Ninomiya <kainino@chromium.org>
Commit-Queue: Corentin Wallez <cwallez@chromium.org>
This commit is contained in:
Corentin Wallez 2020-01-06 19:36:07 +00:00 committed by Commit Bot service account
parent 87d3138158
commit 96f79f6db5
2 changed files with 59 additions and 12 deletions

View File

@ -139,6 +139,10 @@ namespace dawn_native {
mEncodingContext->TryEncode(this, [&](CommandAllocator* allocator) -> MaybeError { mEncodingContext->TryEncode(this, [&](CommandAllocator* allocator) -> MaybeError {
DAWN_TRY(GetDevice()->ValidateObject(buffer)); DAWN_TRY(GetDevice()->ValidateObject(buffer));
if (slot >= kMaxVertexBuffers) {
return DAWN_VALIDATION_ERROR("Vertex buffer slot out of bounds");
}
SetVertexBufferCmd* cmd = SetVertexBufferCmd* cmd =
allocator->Allocate<SetVertexBufferCmd>(Command::SetVertexBuffer); allocator->Allocate<SetVertexBufferCmd>(Command::SetVertexBuffer);
cmd->slot = slot; cmd->slot = slot;

View File

@ -16,6 +16,7 @@
#include "tests/unittests/validation/ValidationTest.h" #include "tests/unittests/validation/ValidationTest.h"
#include "utils/ComboRenderBundleEncoderDescriptor.h"
#include "utils/ComboRenderPipelineDescriptor.h" #include "utils/ComboRenderPipelineDescriptor.h"
#include "utils/WGPUHelpers.h" #include "utils/WGPUHelpers.h"
@ -86,14 +87,14 @@ class VertexBufferValidationTest : public ValidationTest {
TEST_F(VertexBufferValidationTest, VertexBuffersInheritedBetweenPipelines) { TEST_F(VertexBufferValidationTest, VertexBuffersInheritedBetweenPipelines) {
DummyRenderPass renderPass(device); DummyRenderPass renderPass(device);
auto vsModule2 = MakeVertexShader(2); wgpu::ShaderModule vsModule2 = MakeVertexShader(2);
auto vsModule1 = MakeVertexShader(1); wgpu::ShaderModule vsModule1 = MakeVertexShader(1);
auto pipeline2 = MakeRenderPipeline(vsModule2, 2); wgpu::RenderPipeline pipeline2 = MakeRenderPipeline(vsModule2, 2);
auto pipeline1 = MakeRenderPipeline(vsModule1, 1); wgpu::RenderPipeline pipeline1 = MakeRenderPipeline(vsModule1, 1);
auto vertexBuffer1 = MakeVertexBuffer(); wgpu::Buffer vertexBuffer1 = MakeVertexBuffer();
auto vertexBuffer2 = MakeVertexBuffer(); wgpu::Buffer vertexBuffer2 = MakeVertexBuffer();
// Check failure when vertex buffer is not set // Check failure when vertex buffer is not set
wgpu::CommandEncoder encoder = device.CreateCommandEncoder(); wgpu::CommandEncoder encoder = device.CreateCommandEncoder();
@ -122,14 +123,14 @@ TEST_F(VertexBufferValidationTest, VertexBuffersInheritedBetweenPipelines) {
TEST_F(VertexBufferValidationTest, VertexBuffersNotInheritedBetweenRendePasses) { TEST_F(VertexBufferValidationTest, VertexBuffersNotInheritedBetweenRendePasses) {
DummyRenderPass renderPass(device); DummyRenderPass renderPass(device);
auto vsModule2 = MakeVertexShader(2); wgpu::ShaderModule vsModule2 = MakeVertexShader(2);
auto vsModule1 = MakeVertexShader(1); wgpu::ShaderModule vsModule1 = MakeVertexShader(1);
auto pipeline2 = MakeRenderPipeline(vsModule2, 2); wgpu::RenderPipeline pipeline2 = MakeRenderPipeline(vsModule2, 2);
auto pipeline1 = MakeRenderPipeline(vsModule1, 1); wgpu::RenderPipeline pipeline1 = MakeRenderPipeline(vsModule1, 1);
auto vertexBuffer1 = MakeVertexBuffer(); wgpu::Buffer vertexBuffer1 = MakeVertexBuffer();
auto vertexBuffer2 = MakeVertexBuffer(); wgpu::Buffer vertexBuffer2 = MakeVertexBuffer();
// Check success when vertex buffer is set for each render pass // Check success when vertex buffer is set for each render pass
wgpu::CommandEncoder encoder = device.CreateCommandEncoder(); wgpu::CommandEncoder encoder = device.CreateCommandEncoder();
@ -168,3 +169,45 @@ TEST_F(VertexBufferValidationTest, VertexBuffersNotInheritedBetweenRendePasses)
} }
ASSERT_DEVICE_ERROR(encoder.Finish()); ASSERT_DEVICE_ERROR(encoder.Finish());
} }
TEST_F(VertexBufferValidationTest, VertexBufferSlotValidation) {
wgpu::Buffer buffer = MakeVertexBuffer();
DummyRenderPass renderPass(device);
// Control case: using the last vertex buffer slot in render passes is ok.
{
wgpu::CommandEncoder encoder = device.CreateCommandEncoder();
wgpu::RenderPassEncoder pass = encoder.BeginRenderPass(&renderPass);
pass.SetVertexBuffer(kMaxVertexBuffers - 1, buffer, 0);
pass.EndPass();
encoder.Finish();
}
// Error case: using past the last vertex buffer slot in render pass fails.
{
wgpu::CommandEncoder encoder = device.CreateCommandEncoder();
wgpu::RenderPassEncoder pass = encoder.BeginRenderPass(&renderPass);
pass.SetVertexBuffer(kMaxVertexBuffers, buffer, 0);
pass.EndPass();
ASSERT_DEVICE_ERROR(encoder.Finish());
}
utils::ComboRenderBundleEncoderDescriptor renderBundleDesc = {};
renderBundleDesc.colorFormatsCount = 1;
renderBundleDesc.cColorFormats[0] = wgpu::TextureFormat::RGBA8Unorm;
// Control case: using the last vertex buffer slot in render bundles is ok.
{
wgpu::RenderBundleEncoder encoder = device.CreateRenderBundleEncoder(&renderBundleDesc);
encoder.SetVertexBuffer(kMaxVertexBuffers - 1, buffer, 0);
encoder.Finish();
}
// Error case: using past the last vertex buffer slot in render bundle fails.
{
wgpu::RenderBundleEncoder encoder = device.CreateRenderBundleEncoder(&renderBundleDesc);
encoder.SetVertexBuffer(kMaxVertexBuffers, buffer, 0);
ASSERT_DEVICE_ERROR(encoder.Finish());
}
}