Commit 44b374e4 authored by Corentin Wallez's avatar Corentin Wallez Committed by Commit Bot

WebGPU: Make DissociateMailbox take device client ID

Previously it didn't take a device client id, which meant the map
associating shared images to texture reservations in the wire was global
to the WebGPUDecoderImpl. This is incorrect because there is one wire
per device.

This CL adds the missing argument to DissociateMailbox and makes the
associated shared image map a per-device thing. It also adds a
regression test.

Bug: chromium:1059777
Change-Id: Id4db2556dc19f90a13e1af6381f855f7d633e113
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2095123
Commit-Queue: Corentin Wallez <cwallez@chromium.org>
Reviewed-by: default avatarAustin Eng <enga@chromium.org>
Reviewed-by: default avatarKenneth Russell <kbr@chromium.org>
Cr-Commit-Position: refs/heads/master@{#748731}
parent 8f270bff
...@@ -37,11 +37,13 @@ void AssociateMailboxImmediate(GLuint64 device_client_id, ...@@ -37,11 +37,13 @@ void AssociateMailboxImmediate(GLuint64 device_client_id,
} }
} }
void DissociateMailbox(GLuint texture_id, GLuint texture_generation) { void DissociateMailbox(GLuint64 device_client_id,
GLuint texture_id,
GLuint texture_generation) {
webgpu::cmds::DissociateMailbox* c = webgpu::cmds::DissociateMailbox* c =
GetCmdSpace<webgpu::cmds::DissociateMailbox>(); GetCmdSpace<webgpu::cmds::DissociateMailbox>();
if (c) { if (c) {
c->Init(texture_id, texture_generation); c->Init(device_client_id, texture_id, texture_generation);
} }
} }
......
...@@ -20,6 +20,8 @@ void AssociateMailbox(GLuint64 device_client_id, ...@@ -20,6 +20,8 @@ void AssociateMailbox(GLuint64 device_client_id,
GLuint usage, GLuint usage,
const GLbyte* mailbox) override; const GLbyte* mailbox) override;
void DissociateMailbox(GLuint texture_id, GLuint texture_generation) override; void DissociateMailbox(GLuint64 device_client_id,
GLuint texture_id,
GLuint texture_generation) override;
#endif // GPU_COMMAND_BUFFER_CLIENT_WEBGPU_IMPLEMENTATION_AUTOGEN_H_ #endif // GPU_COMMAND_BUFFER_CLIENT_WEBGPU_IMPLEMENTATION_AUTOGEN_H_
...@@ -32,12 +32,14 @@ void WebGPUImplementation::AssociateMailbox(GLuint64 device_client_id, ...@@ -32,12 +32,14 @@ void WebGPUImplementation::AssociateMailbox(GLuint64 device_client_id,
CheckGLError(); CheckGLError();
} }
void WebGPUImplementation::DissociateMailbox(GLuint texture_id, void WebGPUImplementation::DissociateMailbox(GLuint64 device_client_id,
GLuint texture_id,
GLuint texture_generation) { GLuint texture_generation) {
GPU_CLIENT_SINGLE_THREAD_CHECK(); GPU_CLIENT_SINGLE_THREAD_CHECK();
GPU_CLIENT_LOG("[" << GetLogPrefix() << "] wgDissociateMailbox(" << texture_id GPU_CLIENT_LOG("[" << GetLogPrefix() << "] wgDissociateMailbox("
<< ", " << texture_generation << ")"); << device_client_id << ", " << texture_id << ", "
helper_->DissociateMailbox(texture_id, texture_generation); << texture_generation << ")");
helper_->DissociateMailbox(device_client_id, texture_id, texture_generation);
} }
#endif // GPU_COMMAND_BUFFER_CLIENT_WEBGPU_IMPLEMENTATION_IMPL_AUTOGEN_H_ #endif // GPU_COMMAND_BUFFER_CLIENT_WEBGPU_IMPLEMENTATION_IMPL_AUTOGEN_H_
...@@ -34,9 +34,9 @@ TEST_F(WebGPUImplementationTest, DissociateMailbox) { ...@@ -34,9 +34,9 @@ TEST_F(WebGPUImplementationTest, DissociateMailbox) {
cmds::DissociateMailbox cmd; cmds::DissociateMailbox cmd;
}; };
Cmds expected; Cmds expected;
expected.cmd.Init(1, 2); expected.cmd.Init(1, 2, 3);
gl_->DissociateMailbox(1, 2); gl_->DissociateMailbox(1, 2, 3);
EXPECT_EQ(0, memcmp(&expected, commands_, sizeof(expected))); EXPECT_EQ(0, memcmp(&expected, commands_, sizeof(expected)));
} }
#endif // GPU_COMMAND_BUFFER_CLIENT_WEBGPU_IMPLEMENTATION_UNITTEST_AUTOGEN_H_ #endif // GPU_COMMAND_BUFFER_CLIENT_WEBGPU_IMPLEMENTATION_UNITTEST_AUTOGEN_H_
...@@ -19,6 +19,7 @@ virtual void AssociateMailbox(GLuint64 device_client_id, ...@@ -19,6 +19,7 @@ virtual void AssociateMailbox(GLuint64 device_client_id,
GLuint generation, GLuint generation,
GLuint usage, GLuint usage,
const GLbyte* mailbox) = 0; const GLbyte* mailbox) = 0;
virtual void DissociateMailbox(GLuint texture_id, virtual void DissociateMailbox(GLuint64 device_client_id,
GLuint texture_id,
GLuint texture_generation) = 0; GLuint texture_generation) = 0;
#endif // GPU_COMMAND_BUFFER_CLIENT_WEBGPU_INTERFACE_AUTOGEN_H_ #endif // GPU_COMMAND_BUFFER_CLIENT_WEBGPU_INTERFACE_AUTOGEN_H_
...@@ -18,5 +18,7 @@ void AssociateMailbox(GLuint64 device_client_id, ...@@ -18,5 +18,7 @@ void AssociateMailbox(GLuint64 device_client_id,
GLuint generation, GLuint generation,
GLuint usage, GLuint usage,
const GLbyte* mailbox) override; const GLbyte* mailbox) override;
void DissociateMailbox(GLuint texture_id, GLuint texture_generation) override; void DissociateMailbox(GLuint64 device_client_id,
GLuint texture_id,
GLuint texture_generation) override;
#endif // GPU_COMMAND_BUFFER_CLIENT_WEBGPU_INTERFACE_STUB_AUTOGEN_H_ #endif // GPU_COMMAND_BUFFER_CLIENT_WEBGPU_INTERFACE_STUB_AUTOGEN_H_
...@@ -18,6 +18,7 @@ void WebGPUInterfaceStub::AssociateMailbox(GLuint64 /* device_client_id */, ...@@ -18,6 +18,7 @@ void WebGPUInterfaceStub::AssociateMailbox(GLuint64 /* device_client_id */,
GLuint /* generation */, GLuint /* generation */,
GLuint /* usage */, GLuint /* usage */,
const GLbyte* /* mailbox */) {} const GLbyte* /* mailbox */) {}
void WebGPUInterfaceStub::DissociateMailbox(GLuint /* texture_id */, void WebGPUInterfaceStub::DissociateMailbox(GLuint64 /* device_client_id */,
GLuint /* texture_id */,
GLuint /* texture_generation */) {} GLuint /* texture_generation */) {}
#endif // GPU_COMMAND_BUFFER_CLIENT_WEBGPU_INTERFACE_STUB_IMPL_AUTOGEN_H_ #endif // GPU_COMMAND_BUFFER_CLIENT_WEBGPU_INTERFACE_STUB_IMPL_AUTOGEN_H_
...@@ -157,30 +157,50 @@ struct DissociateMailbox { ...@@ -157,30 +157,50 @@ struct DissociateMailbox {
void SetHeader() { header.SetCmd<ValueType>(); } void SetHeader() { header.SetCmd<ValueType>(); }
void Init(GLuint _texture_id, GLuint _texture_generation) { void Init(GLuint64 _device_client_id,
GLuint _texture_id,
GLuint _texture_generation) {
SetHeader(); SetHeader();
gles2::GLES2Util::MapUint64ToTwoUint32(
static_cast<uint64_t>(_device_client_id), &device_client_id_0,
&device_client_id_1);
texture_id = _texture_id; texture_id = _texture_id;
texture_generation = _texture_generation; texture_generation = _texture_generation;
} }
void* Set(void* cmd, GLuint _texture_id, GLuint _texture_generation) { void* Set(void* cmd,
static_cast<ValueType*>(cmd)->Init(_texture_id, _texture_generation); GLuint64 _device_client_id,
GLuint _texture_id,
GLuint _texture_generation) {
static_cast<ValueType*>(cmd)->Init(_device_client_id, _texture_id,
_texture_generation);
return NextCmdAddress<ValueType>(cmd); return NextCmdAddress<ValueType>(cmd);
} }
GLuint64 device_client_id() const volatile {
return static_cast<GLuint64>(gles2::GLES2Util::MapTwoUint32ToUint64(
device_client_id_0, device_client_id_1));
}
gpu::CommandHeader header; gpu::CommandHeader header;
uint32_t device_client_id_0;
uint32_t device_client_id_1;
uint32_t texture_id; uint32_t texture_id;
uint32_t texture_generation; uint32_t texture_generation;
}; };
static_assert(sizeof(DissociateMailbox) == 12, static_assert(sizeof(DissociateMailbox) == 20,
"size of DissociateMailbox should be 12"); "size of DissociateMailbox should be 20");
static_assert(offsetof(DissociateMailbox, header) == 0, static_assert(offsetof(DissociateMailbox, header) == 0,
"offset of DissociateMailbox header should be 0"); "offset of DissociateMailbox header should be 0");
static_assert(offsetof(DissociateMailbox, texture_id) == 4, static_assert(offsetof(DissociateMailbox, device_client_id_0) == 4,
"offset of DissociateMailbox texture_id should be 4"); "offset of DissociateMailbox device_client_id_0 should be 4");
static_assert(offsetof(DissociateMailbox, texture_generation) == 8, static_assert(offsetof(DissociateMailbox, device_client_id_1) == 8,
"offset of DissociateMailbox texture_generation should be 8"); "offset of DissociateMailbox device_client_id_1 should be 8");
static_assert(offsetof(DissociateMailbox, texture_id) == 12,
"offset of DissociateMailbox texture_id should be 12");
static_assert(offsetof(DissociateMailbox, texture_generation) == 16,
"offset of DissociateMailbox texture_generation should be 16");
struct RequestAdapter { struct RequestAdapter {
typedef RequestAdapter ValueType; typedef RequestAdapter ValueType;
......
...@@ -70,13 +70,14 @@ TEST_F(WebGPUFormatTest, AssociateMailboxImmediate) { ...@@ -70,13 +70,14 @@ TEST_F(WebGPUFormatTest, AssociateMailboxImmediate) {
TEST_F(WebGPUFormatTest, DissociateMailbox) { TEST_F(WebGPUFormatTest, DissociateMailbox) {
cmds::DissociateMailbox& cmd = *GetBufferAs<cmds::DissociateMailbox>(); cmds::DissociateMailbox& cmd = *GetBufferAs<cmds::DissociateMailbox>();
void* next_cmd = void* next_cmd = cmd.Set(&cmd, static_cast<GLuint64>(11),
cmd.Set(&cmd, static_cast<GLuint>(11), static_cast<GLuint>(12)); static_cast<GLuint>(12), static_cast<GLuint>(13));
EXPECT_EQ(static_cast<uint32_t>(cmds::DissociateMailbox::kCmdId), EXPECT_EQ(static_cast<uint32_t>(cmds::DissociateMailbox::kCmdId),
cmd.header.command); cmd.header.command);
EXPECT_EQ(sizeof(cmd), cmd.header.size * 4u); EXPECT_EQ(sizeof(cmd), cmd.header.size * 4u);
EXPECT_EQ(static_cast<GLuint>(11), cmd.texture_id); EXPECT_EQ(static_cast<GLuint64>(11), cmd.device_client_id());
EXPECT_EQ(static_cast<GLuint>(12), cmd.texture_generation); EXPECT_EQ(static_cast<GLuint>(12), cmd.texture_id);
EXPECT_EQ(static_cast<GLuint>(13), cmd.texture_generation);
CheckBytesWrittenMatchesExpectedSize(next_cmd, sizeof(cmd)); CheckBytesWrittenMatchesExpectedSize(next_cmd, sizeof(cmd));
} }
......
...@@ -169,10 +169,20 @@ TEST_F(WebGPUDecoderTest, AssociateMailbox) { ...@@ -169,10 +169,20 @@ TEST_F(WebGPUDecoderTest, AssociateMailbox) {
ExecuteImmediateCmd(cmd.cmd, sizeof(bad_mailbox.name))); ExecuteImmediateCmd(cmd.cmd, sizeof(bad_mailbox.name)));
} }
// Error case: device doesn't exist. // Error case: device client id doesn't exist.
{ {
AssociateMailboxCmdStorage cmd; AssociateMailboxCmdStorage cmd;
cmd.cmd.Init(42, 42, 1, 0, WGPUTextureUsage_Sampled, mailbox.name); cmd.cmd.Init(kDeviceClientID + 1, 0, 1, 0, WGPUTextureUsage_Sampled,
mailbox.name);
EXPECT_EQ(error::kInvalidArguments,
ExecuteImmediateCmd(cmd.cmd, sizeof(mailbox.name)));
}
// Error case: device generation is invalid.
{
AssociateMailboxCmdStorage cmd;
cmd.cmd.Init(kDeviceClientID, 42, 1, 0, WGPUTextureUsage_Sampled,
mailbox.name);
EXPECT_EQ(error::kInvalidArguments, EXPECT_EQ(error::kInvalidArguments,
ExecuteImmediateCmd(cmd.cmd, sizeof(mailbox.name))); ExecuteImmediateCmd(cmd.cmd, sizeof(mailbox.name)));
} }
...@@ -229,7 +239,7 @@ TEST_F(WebGPUDecoderTest, AssociateMailbox) { ...@@ -229,7 +239,7 @@ TEST_F(WebGPUDecoderTest, AssociateMailbox) {
// Dissociate the image from the control case to remove its reference. // Dissociate the image from the control case to remove its reference.
{ {
cmds::DissociateMailbox cmd; cmds::DissociateMailbox cmd;
cmd.Init(1, 0); cmd.Init(kDeviceClientID, 1, 0);
EXPECT_EQ(error::kNoError, ExecuteCmd(cmd)); EXPECT_EQ(error::kNoError, ExecuteCmd(cmd));
} }
} }
...@@ -258,14 +268,28 @@ TEST_F(WebGPUDecoderTest, DissociateMailbox) { ...@@ -258,14 +268,28 @@ TEST_F(WebGPUDecoderTest, DissociateMailbox) {
// Error case: wrong texture ID // Error case: wrong texture ID
{ {
cmds::DissociateMailbox cmd; cmds::DissociateMailbox cmd;
cmd.Init(42, 42); cmd.Init(kDeviceClientID, 42, 0);
EXPECT_EQ(error::kInvalidArguments, ExecuteCmd(cmd));
}
// Error case: wrong texture generation
{
cmds::DissociateMailbox cmd;
cmd.Init(kDeviceClientID, 1, 42);
EXPECT_EQ(error::kInvalidArguments, ExecuteCmd(cmd));
}
// Error case: invalid client device ID
{
cmds::DissociateMailbox cmd;
cmd.Init(kDeviceClientID + 1, 1, 0);
EXPECT_EQ(error::kInvalidArguments, ExecuteCmd(cmd)); EXPECT_EQ(error::kInvalidArguments, ExecuteCmd(cmd));
} }
// Success case // Success case
{ {
cmds::DissociateMailbox cmd; cmds::DissociateMailbox cmd;
cmd.Init(1, 0); cmd.Init(kDeviceClientID, 1, 0);
EXPECT_EQ(error::kNoError, ExecuteCmd(cmd)); EXPECT_EQ(error::kNoError, ExecuteCmd(cmd));
} }
} }
......
...@@ -128,7 +128,8 @@ TEST_F(WebGPUMailboxTest, WriteToMailboxThenReadFromIt) { ...@@ -128,7 +128,8 @@ TEST_F(WebGPUMailboxTest, WriteToMailboxThenReadFromIt) {
// Dissociate the mailbox, flushing previous commands first // Dissociate the mailbox, flushing previous commands first
webgpu()->FlushCommands(); webgpu()->FlushCommands();
webgpu()->DissociateMailbox(reservation.id, reservation.generation); webgpu()->DissociateMailbox(device_client_id, reservation.id,
reservation.generation);
} }
// Part 2: Read back the texture using Dawn // Part 2: Read back the texture using Dawn
...@@ -175,7 +176,8 @@ TEST_F(WebGPUMailboxTest, WriteToMailboxThenReadFromIt) { ...@@ -175,7 +176,8 @@ TEST_F(WebGPUMailboxTest, WriteToMailboxThenReadFromIt) {
// Dissociate the mailbox, flushing previous commands first // Dissociate the mailbox, flushing previous commands first
webgpu()->FlushCommands(); webgpu()->FlushCommands();
webgpu()->DissociateMailbox(reservation.id, reservation.generation); webgpu()->DissociateMailbox(device_client_id, reservation.id,
reservation.generation);
// Map the buffer and assert the pixel is the correct value. // Map the buffer and assert the pixel is the correct value.
readback_buffer.MapReadAsync(ToMockBufferMapReadCallback, 0); readback_buffer.MapReadAsync(ToMockBufferMapReadCallback, 0);
...@@ -224,7 +226,8 @@ TEST_F(WebGPUMailboxTest, ErrorWhenUsingTextureAfterDissociate) { ...@@ -224,7 +226,8 @@ TEST_F(WebGPUMailboxTest, ErrorWhenUsingTextureAfterDissociate) {
webgpu()->AssociateMailbox( webgpu()->AssociateMailbox(
device_client_id, 0, reservation.id, reservation.generation, device_client_id, 0, reservation.id, reservation.generation,
WGPUTextureUsage_OutputAttachment, reinterpret_cast<GLbyte*>(&mailbox)); WGPUTextureUsage_OutputAttachment, reinterpret_cast<GLbyte*>(&mailbox));
webgpu()->DissociateMailbox(reservation.id, reservation.generation); webgpu()->DissociateMailbox(device_client_id, reservation.id,
reservation.generation);
// Try using the texture, it should produce a validation error. // Try using the texture, it should produce a validation error.
wgpu::TextureView view = texture.CreateView(); wgpu::TextureView view = texture.CreateView();
...@@ -263,10 +266,10 @@ TEST_F(WebGPUMailboxTest, UseA_UseB_DestroyA_DestroyB) { ...@@ -263,10 +266,10 @@ TEST_F(WebGPUMailboxTest, UseA_UseB_DestroyA_DestroyB) {
// Create a the shared images. // Create a the shared images.
SharedImageInterface* sii = GetSharedImageInterface(); SharedImageInterface* sii = GetSharedImageInterface();
Mailbox mailboxA = sii->CreateSharedImage( Mailbox mailbox_a = sii->CreateSharedImage(
viz::ResourceFormat::RGBA_8888, {1, 1}, gfx::ColorSpace::CreateSRGB(), viz::ResourceFormat::RGBA_8888, {1, 1}, gfx::ColorSpace::CreateSRGB(),
SHARED_IMAGE_USAGE_WEBGPU); SHARED_IMAGE_USAGE_WEBGPU);
Mailbox mailboxB = sii->CreateSharedImage( Mailbox mailbox_b = sii->CreateSharedImage(
viz::ResourceFormat::RGBA_8888, {1, 1}, gfx::ColorSpace::CreateSRGB(), viz::ResourceFormat::RGBA_8888, {1, 1}, gfx::ColorSpace::CreateSRGB(),
SHARED_IMAGE_USAGE_WEBGPU); SHARED_IMAGE_USAGE_WEBGPU);
...@@ -276,21 +279,77 @@ TEST_F(WebGPUMailboxTest, UseA_UseB_DestroyA_DestroyB) { ...@@ -276,21 +279,77 @@ TEST_F(WebGPUMailboxTest, UseA_UseB_DestroyA_DestroyB) {
webgpu::DawnDeviceClientID device_client_id = device_and_id.client_id; webgpu::DawnDeviceClientID device_client_id = device_and_id.client_id;
// Associate both mailboxes // Associate both mailboxes
gpu::webgpu::ReservedTexture reservationA = gpu::webgpu::ReservedTexture reservation_a =
webgpu()->ReserveTexture(device_client_id); webgpu()->ReserveTexture(device_client_id);
webgpu()->AssociateMailbox( webgpu()->AssociateMailbox(
device_client_id, 0, reservationA.id, reservationA.generation, device_client_id, 0, reservation_a.id, reservation_a.generation,
WGPUTextureUsage_OutputAttachment, reinterpret_cast<GLbyte*>(&mailboxA)); WGPUTextureUsage_OutputAttachment, reinterpret_cast<GLbyte*>(&mailbox_a));
gpu::webgpu::ReservedTexture reservationB = gpu::webgpu::ReservedTexture reservation_b =
webgpu()->ReserveTexture(device_client_id); webgpu()->ReserveTexture(device_client_id);
webgpu()->AssociateMailbox( webgpu()->AssociateMailbox(
device_client_id, 0, reservationB.id, reservationB.generation, device_client_id, 0, reservation_b.id, reservation_b.generation,
WGPUTextureUsage_OutputAttachment, reinterpret_cast<GLbyte*>(&mailboxB)); WGPUTextureUsage_OutputAttachment, reinterpret_cast<GLbyte*>(&mailbox_b));
// Dissociate both mailboxes in the same order. // Dissociate both mailboxes in the same order.
webgpu()->DissociateMailbox(reservationA.id, reservationA.generation); webgpu()->DissociateMailbox(device_client_id, reservation_a.id,
webgpu()->DissociateMailbox(reservationB.id, reservationB.generation); reservation_a.generation);
webgpu()->DissociateMailbox(device_client_id, reservation_b.id,
reservation_b.generation);
// Send all the previous commands to the WebGPU decoder.
webgpu()->FlushCommands();
}
// Regression test for a bug where the (id, generation) for associated shared
// images was stored globally instead of per-device. This meant that of two
// devices tried to create shared images with the same (id, generation) (which
// is possible because they can be on different Dawn wires) they would conflict.
TEST_F(WebGPUMailboxTest, AssociateOnTwoDevicesAtTheSameTime) {
if (!WebGPUSupported()) {
LOG(ERROR) << "Test skipped because WebGPU isn't supported";
return;
}
if (!WebGPUSharedImageSupported()) {
LOG(ERROR) << "Test skipped because WebGPUSharedImage isn't supported";
return;
}
// Create a the shared images.
SharedImageInterface* sii = GetSharedImageInterface();
Mailbox mailbox_a = sii->CreateSharedImage(
viz::ResourceFormat::RGBA_8888, {1, 1}, gfx::ColorSpace::CreateSRGB(),
SHARED_IMAGE_USAGE_WEBGPU);
Mailbox mailbox_b = sii->CreateSharedImage(
viz::ResourceFormat::RGBA_8888, {1, 1}, gfx::ColorSpace::CreateSRGB(),
SHARED_IMAGE_USAGE_WEBGPU);
// Two WebGPU devices to associate the shared images to.
DeviceAndClientID device_and_id_a = GetNewDeviceAndClientID();
webgpu::DawnDeviceClientID client_id_a = device_and_id_a.client_id;
DeviceAndClientID device_and_id_b = GetNewDeviceAndClientID();
webgpu::DawnDeviceClientID client_id_b = device_and_id_b.client_id;
// Associate both mailboxes
gpu::webgpu::ReservedTexture reservation_a =
webgpu()->ReserveTexture(client_id_a);
webgpu()->AssociateMailbox(
client_id_a, 0, reservation_a.id, reservation_a.generation,
WGPUTextureUsage_OutputAttachment, reinterpret_cast<GLbyte*>(&mailbox_a));
gpu::webgpu::ReservedTexture reservation_b =
webgpu()->ReserveTexture(client_id_b);
webgpu()->AssociateMailbox(
client_id_b, 0, reservation_b.id, reservation_b.generation,
WGPUTextureUsage_OutputAttachment, reinterpret_cast<GLbyte*>(&mailbox_b));
// Dissociate both mailboxes in the same order.
webgpu()->DissociateMailbox(client_id_a, reservation_a.id,
reservation_a.generation);
webgpu()->DissociateMailbox(client_id_b, reservation_b.id,
reservation_b.generation);
// Send all the previous commands to the WebGPU decoder. // Send all the previous commands to the WebGPU decoder.
webgpu()->FlushCommands(); webgpu()->FlushCommands();
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
// completely ignored. // completely ignored.
GL_APICALL void GL_APIENTRY wgDawnCommands (GLuint64 device_client_id, const char* commands, size_t size); GL_APICALL void GL_APIENTRY wgDawnCommands (GLuint64 device_client_id, const char* commands, size_t size);
GL_APICALL void GL_APIENTRY wgAssociateMailbox (GLuint64 device_client_id, GLuint device_generation, GLuint id, GLuint generation, GLuint usage, const GLbyte* mailbox); GL_APICALL void GL_APIENTRY wgAssociateMailbox (GLuint64 device_client_id, GLuint device_generation, GLuint id, GLuint generation, GLuint usage, const GLbyte* mailbox);
GL_APICALL void GL_APIENTRY wgDissociateMailbox (GLuint texture_id, GLuint texture_generation); GL_APICALL void GL_APIENTRY wgDissociateMailbox (GLuint64 device_client_id, GLuint texture_id, GLuint texture_generation);
GL_APICALL void GL_APIENTRY wgRequestAdapter (GLuint64 request_adapter_serial, EnumClassPowerPreference power_preference = PowerPreference::kDefault); GL_APICALL void GL_APIENTRY wgRequestAdapter (GLuint64 request_adapter_serial, EnumClassPowerPreference power_preference = PowerPreference::kDefault);
GL_APICALL void GL_APIENTRY wgRequestDevice (GLuint64 device_client_id, GLuint adapter_service_id, const char* dawn_request_device_properties, size_t request_device_properties_size); GL_APICALL void GL_APIENTRY wgRequestDevice (GLuint64 device_client_id, GLuint adapter_service_id, const char* dawn_request_device_properties, size_t request_device_properties_size);
GL_APICALL void GL_APIENTRY wgRemoveDevice (GLuint64 device_client_id); GL_APICALL void GL_APIENTRY wgRemoveDevice (GLuint64 device_client_id);
\ No newline at end of file
...@@ -21,7 +21,7 @@ GPUSwapChain::GPUSwapChain(GPUCanvasContext* context, ...@@ -21,7 +21,7 @@ GPUSwapChain::GPUSwapChain(GPUCanvasContext* context,
usage_(AsDawnEnum<WGPUTextureUsage>(descriptor->usage())) { usage_(AsDawnEnum<WGPUTextureUsage>(descriptor->usage())) {
// TODO: Use label from GPUObjectDescriptorBase. // TODO: Use label from GPUObjectDescriptorBase.
swap_buffers_ = base::AdoptRef(new WebGPUSwapBufferProvider( swap_buffers_ = base::AdoptRef(new WebGPUSwapBufferProvider(
this, GetDawnControlClient(), usage_, this, GetDawnControlClient(), device_->GetClientID(), usage_,
AsDawnEnum<WGPUTextureFormat>(descriptor->format()))); AsDawnEnum<WGPUTextureFormat>(descriptor->format())));
} }
...@@ -66,8 +66,8 @@ GPUTexture* GPUSwapChain::getCurrentTexture() { ...@@ -66,8 +66,8 @@ GPUTexture* GPUSwapChain::getCurrentTexture() {
return texture_; return texture_;
} }
WGPUTexture dawn_client_texture = swap_buffers_->GetNewTexture( WGPUTexture dawn_client_texture =
device_->GetClientID(), context_->CanvasSize()); swap_buffers_->GetNewTexture(context_->CanvasSize());
DCHECK(dawn_client_texture); DCHECK(dawn_client_texture);
texture_ = MakeGarbageCollected<GPUTexture>(device_, dawn_client_texture); texture_ = MakeGarbageCollected<GPUTexture>(device_, dawn_client_texture);
return texture_; return texture_;
......
...@@ -29,10 +29,12 @@ viz::ResourceFormat WGPUFormatToViz(WGPUTextureFormat format) { ...@@ -29,10 +29,12 @@ viz::ResourceFormat WGPUFormatToViz(WGPUTextureFormat format) {
WebGPUSwapBufferProvider::WebGPUSwapBufferProvider( WebGPUSwapBufferProvider::WebGPUSwapBufferProvider(
Client* client, Client* client,
scoped_refptr<DawnControlClientHolder> dawn_control_client, scoped_refptr<DawnControlClientHolder> dawn_control_client,
uint64_t device_client_id,
WGPUTextureUsage usage, WGPUTextureUsage usage,
WGPUTextureFormat format) WGPUTextureFormat format)
: dawn_control_client_(dawn_control_client), : dawn_control_client_(dawn_control_client),
client_(client), client_(client),
device_client_id_(device_client_id),
usage_(usage), usage_(usage),
format_(WGPUFormatToViz(format)) { format_(WGPUFormatToViz(format)) {
// Create a layer that will be used by the canvas and will ask for a // Create a layer that will be used by the canvas and will ask for a
...@@ -82,8 +84,7 @@ void WebGPUSwapBufferProvider::Neuter() { ...@@ -82,8 +84,7 @@ void WebGPUSwapBufferProvider::Neuter() {
neutered_ = true; neutered_ = true;
} }
WGPUTexture WebGPUSwapBufferProvider::GetNewTexture(uint64_t device_client_id, WGPUTexture WebGPUSwapBufferProvider::GetNewTexture(const IntSize& size) {
const IntSize& size) {
DCHECK(!current_swap_buffer_ && !dawn_control_client_->IsDestroyed()); DCHECK(!current_swap_buffer_ && !dawn_control_client_->IsDestroyed());
gpu::webgpu::WebGPUInterface* webgpu = dawn_control_client_->GetInterface(); gpu::webgpu::WebGPUInterface* webgpu = dawn_control_client_->GetInterface();
...@@ -110,13 +111,13 @@ WGPUTexture WebGPUSwapBufferProvider::GetNewTexture(uint64_t device_client_id, ...@@ -110,13 +111,13 @@ WGPUTexture WebGPUSwapBufferProvider::GetNewTexture(uint64_t device_client_id,
// Associate the mailbox to a dawn_wire client DawnTexture object // Associate the mailbox to a dawn_wire client DawnTexture object
gpu::webgpu::ReservedTexture reservation = gpu::webgpu::ReservedTexture reservation =
webgpu->ReserveTexture(device_client_id); webgpu->ReserveTexture(device_client_id_);
DCHECK(reservation.texture); DCHECK(reservation.texture);
wire_texture_id_ = reservation.id; wire_texture_id_ = reservation.id;
wire_texture_generation_ = reservation.generation; wire_texture_generation_ = reservation.generation;
webgpu->AssociateMailbox( webgpu->AssociateMailbox(
device_client_id, 0, reservation.id, reservation.generation, usage_, device_client_id_, 0, reservation.id, reservation.generation, usage_,
reinterpret_cast<GLbyte*>(&current_swap_buffer_->mailbox)); reinterpret_cast<GLbyte*>(&current_swap_buffer_->mailbox));
// When the page request a texture it means we'll need to present it on the // When the page request a texture it means we'll need to present it on the
...@@ -144,7 +145,8 @@ bool WebGPUSwapBufferProvider::PrepareTransferableResource( ...@@ -144,7 +145,8 @@ bool WebGPUSwapBufferProvider::PrepareTransferableResource(
// to the texture are errors. // to the texture are errors.
gpu::webgpu::WebGPUInterface* webgpu = dawn_control_client_->GetInterface(); gpu::webgpu::WebGPUInterface* webgpu = dawn_control_client_->GetInterface();
DCHECK_NE(wire_texture_id_, 0u); DCHECK_NE(wire_texture_id_, 0u);
webgpu->DissociateMailbox(wire_texture_id_, wire_texture_generation_); webgpu->DissociateMailbox(device_client_id_, wire_texture_id_,
wire_texture_generation_);
// Make the compositor wait on previous Dawn commands. // Make the compositor wait on previous Dawn commands.
webgpu->GenUnverifiedSyncTokenCHROMIUM( webgpu->GenUnverifiedSyncTokenCHROMIUM(
......
...@@ -35,13 +35,14 @@ class PLATFORM_EXPORT WebGPUSwapBufferProvider ...@@ -35,13 +35,14 @@ class PLATFORM_EXPORT WebGPUSwapBufferProvider
WebGPUSwapBufferProvider( WebGPUSwapBufferProvider(
Client* client, Client* client,
scoped_refptr<DawnControlClientHolder> dawn_control_client, scoped_refptr<DawnControlClientHolder> dawn_control_client,
uint64_t device_client_id,
WGPUTextureUsage usage, WGPUTextureUsage usage,
WGPUTextureFormat format); WGPUTextureFormat format);
~WebGPUSwapBufferProvider() override; ~WebGPUSwapBufferProvider() override;
cc::Layer* CcLayer(); cc::Layer* CcLayer();
void Neuter(); void Neuter();
WGPUTexture GetNewTexture(uint64_t device_client_id, const IntSize& size); WGPUTexture GetNewTexture(const IntSize& size);
// cc::TextureLayerClient implementation. // cc::TextureLayerClient implementation.
bool PrepareTransferableResource( bool PrepareTransferableResource(
...@@ -81,6 +82,7 @@ class PLATFORM_EXPORT WebGPUSwapBufferProvider ...@@ -81,6 +82,7 @@ class PLATFORM_EXPORT WebGPUSwapBufferProvider
scoped_refptr<DawnControlClientHolder> dawn_control_client_; scoped_refptr<DawnControlClientHolder> dawn_control_client_;
Client* client_; Client* client_;
uint64_t device_client_id_;
scoped_refptr<cc::TextureLayer> layer_; scoped_refptr<cc::TextureLayer> layer_;
bool neutered_ = false; bool neutered_ = false;
......
...@@ -58,10 +58,15 @@ class WebGPUSwapBufferProviderForTests : public WebGPUSwapBufferProvider { ...@@ -58,10 +58,15 @@ class WebGPUSwapBufferProviderForTests : public WebGPUSwapBufferProvider {
WebGPUSwapBufferProviderForTests( WebGPUSwapBufferProviderForTests(
bool* alive, bool* alive,
Client* client, Client* client,
uint64_t client_device_id_,
scoped_refptr<DawnControlClientHolder> dawn_control_client, scoped_refptr<DawnControlClientHolder> dawn_control_client,
WGPUTextureUsage usage, WGPUTextureUsage usage,
WGPUTextureFormat format) WGPUTextureFormat format)
: WebGPUSwapBufferProvider(client, dawn_control_client, usage, format), : WebGPUSwapBufferProvider(client,
dawn_control_client,
client_device_id_,
usage,
format),
alive_(alive) {} alive_(alive) {}
~WebGPUSwapBufferProviderForTests() override { *alive_ = false; } ~WebGPUSwapBufferProviderForTests() override { *alive_ = false; }
...@@ -83,13 +88,13 @@ class WebGPUSwapBufferProviderTest : public testing::Test { ...@@ -83,13 +88,13 @@ class WebGPUSwapBufferProviderTest : public testing::Test {
dawn_control_client_ = dawn_control_client_ =
base::MakeRefCounted<DawnControlClientHolder>(std::move(provider)); base::MakeRefCounted<DawnControlClientHolder>(std::move(provider));
static const uint64_t kDeviceClientID = 1;
provider_ = base::MakeRefCounted<WebGPUSwapBufferProviderForTests>( provider_ = base::MakeRefCounted<WebGPUSwapBufferProviderForTests>(
&provider_alive_, &client_, dawn_control_client_, &provider_alive_, &client_, kDeviceClientID, dawn_control_client_,
WGPUTextureUsage_OutputAttachment, WGPUTextureFormat_RGBA8Unorm); WGPUTextureUsage_OutputAttachment, WGPUTextureFormat_RGBA8Unorm);
} }
const static uint64_t kDeviceClientID = 1;
scoped_refptr<DawnControlClientHolder> dawn_control_client_; scoped_refptr<DawnControlClientHolder> dawn_control_client_;
MockWebGPUInterface* webgpu_; MockWebGPUInterface* webgpu_;
viz::TestSharedImageInterface* sii_; viz::TestSharedImageInterface* sii_;
...@@ -119,17 +124,17 @@ TEST_F(WebGPUSwapBufferProviderTest, ...@@ -119,17 +124,17 @@ TEST_F(WebGPUSwapBufferProviderTest,
// Produce resources. // Produce resources.
EXPECT_CALL(*webgpu_, ReserveTexture(_)).WillOnce(Return(reservation1)); EXPECT_CALL(*webgpu_, ReserveTexture(_)).WillOnce(Return(reservation1));
provider_->GetNewTexture(kDeviceClientID, kSize); provider_->GetNewTexture(kSize);
EXPECT_TRUE(provider_->PrepareTransferableResource(nullptr, &resource1, EXPECT_TRUE(provider_->PrepareTransferableResource(nullptr, &resource1,
&release_callback1)); &release_callback1));
EXPECT_CALL(*webgpu_, ReserveTexture(_)).WillOnce(Return(reservation2)); EXPECT_CALL(*webgpu_, ReserveTexture(_)).WillOnce(Return(reservation2));
provider_->GetNewTexture(kDeviceClientID, kSize); provider_->GetNewTexture(kSize);
EXPECT_TRUE(provider_->PrepareTransferableResource(nullptr, &resource2, EXPECT_TRUE(provider_->PrepareTransferableResource(nullptr, &resource2,
&release_callback2)); &release_callback2));
EXPECT_CALL(*webgpu_, ReserveTexture(_)).WillOnce(Return(reservation3)); EXPECT_CALL(*webgpu_, ReserveTexture(_)).WillOnce(Return(reservation3));
provider_->GetNewTexture(kDeviceClientID, kSize); provider_->GetNewTexture(kSize);
EXPECT_TRUE(provider_->PrepareTransferableResource(nullptr, &resource3, EXPECT_TRUE(provider_->PrepareTransferableResource(nullptr, &resource3,
&release_callback3)); &release_callback3));
...@@ -157,7 +162,7 @@ TEST_F(WebGPUSwapBufferProviderTest, VerifyResizingProperlyAffectsResources) { ...@@ -157,7 +162,7 @@ TEST_F(WebGPUSwapBufferProviderTest, VerifyResizingProperlyAffectsResources) {
// Produce one resource of size kSize. // Produce one resource of size kSize.
EXPECT_CALL(*webgpu_, ReserveTexture(_)).WillOnce(Return(reservation)); EXPECT_CALL(*webgpu_, ReserveTexture(_)).WillOnce(Return(reservation));
provider_->GetNewTexture(kDeviceClientID, static_cast<IntSize>(kSize)); provider_->GetNewTexture(static_cast<IntSize>(kSize));
EXPECT_TRUE(provider_->PrepareTransferableResource(nullptr, &resource, EXPECT_TRUE(provider_->PrepareTransferableResource(nullptr, &resource,
&release_callback)); &release_callback));
EXPECT_EQ(static_cast<gfx::Size>(kSize), sii_->MostRecentSize()); EXPECT_EQ(static_cast<gfx::Size>(kSize), sii_->MostRecentSize());
...@@ -165,7 +170,7 @@ TEST_F(WebGPUSwapBufferProviderTest, VerifyResizingProperlyAffectsResources) { ...@@ -165,7 +170,7 @@ TEST_F(WebGPUSwapBufferProviderTest, VerifyResizingProperlyAffectsResources) {
// Produce one resource of size kOtherSize. // Produce one resource of size kOtherSize.
EXPECT_CALL(*webgpu_, ReserveTexture(_)).WillOnce(Return(reservation)); EXPECT_CALL(*webgpu_, ReserveTexture(_)).WillOnce(Return(reservation));
provider_->GetNewTexture(kDeviceClientID, static_cast<IntSize>(kOtherSize)); provider_->GetNewTexture(static_cast<IntSize>(kOtherSize));
EXPECT_TRUE(provider_->PrepareTransferableResource(nullptr, &resource, EXPECT_TRUE(provider_->PrepareTransferableResource(nullptr, &resource,
&release_callback)); &release_callback));
EXPECT_EQ(static_cast<gfx::Size>(kOtherSize), sii_->MostRecentSize()); EXPECT_EQ(static_cast<gfx::Size>(kOtherSize), sii_->MostRecentSize());
...@@ -173,7 +178,7 @@ TEST_F(WebGPUSwapBufferProviderTest, VerifyResizingProperlyAffectsResources) { ...@@ -173,7 +178,7 @@ TEST_F(WebGPUSwapBufferProviderTest, VerifyResizingProperlyAffectsResources) {
// Produce one resource of size kSize again. // Produce one resource of size kSize again.
EXPECT_CALL(*webgpu_, ReserveTexture(_)).WillOnce(Return(reservation)); EXPECT_CALL(*webgpu_, ReserveTexture(_)).WillOnce(Return(reservation));
provider_->GetNewTexture(kDeviceClientID, static_cast<IntSize>(kSize)); provider_->GetNewTexture(static_cast<IntSize>(kSize));
EXPECT_TRUE(provider_->PrepareTransferableResource(nullptr, &resource, EXPECT_TRUE(provider_->PrepareTransferableResource(nullptr, &resource,
&release_callback)); &release_callback));
EXPECT_EQ(static_cast<gfx::Size>(kSize), sii_->MostRecentSize()); EXPECT_EQ(static_cast<gfx::Size>(kSize), sii_->MostRecentSize());
...@@ -191,7 +196,7 @@ TEST_F(WebGPUSwapBufferProviderTest, VerifyInsertAndWaitSyncTokenCorrectly) { ...@@ -191,7 +196,7 @@ TEST_F(WebGPUSwapBufferProviderTest, VerifyInsertAndWaitSyncTokenCorrectly) {
// Produce the first resource, check that WebGPU will wait for the creation of // Produce the first resource, check that WebGPU will wait for the creation of
// the shared image // the shared image
EXPECT_CALL(*webgpu_, ReserveTexture(_)).WillOnce(Return(reservation)); EXPECT_CALL(*webgpu_, ReserveTexture(_)).WillOnce(Return(reservation));
provider_->GetNewTexture(kDeviceClientID, static_cast<IntSize>(kSize)); provider_->GetNewTexture(static_cast<IntSize>(kSize));
EXPECT_EQ(sii_->MostRecentGeneratedToken(), EXPECT_EQ(sii_->MostRecentGeneratedToken(),
webgpu_->most_recent_waited_token); webgpu_->most_recent_waited_token);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment