Create SharedTextureMemory from D3D12 resource Adds support for creating SharedTextureMemory from a D3D12Resource without the need for a shared handle - through a new SharedTextureMemoryD3D12ResourceDescriptor. Change-Id: Ib9ad171eb1e0892c11dbe1524d7dce792dfdc92c Bug: 425864542 Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/268055 Reviewed-by: Rafael Cintron <rafael.cintron@microsoft.com> Commit-Queue: Sahir Vellani <sahir.vellani@microsoft.com> Reviewed-by: Kai Ninomiya <kainino@chromium.org>
diff --git a/include/dawn/native/D3D12Backend.h b/include/dawn/native/D3D12Backend.h index b5ef2d6..753f056 100644 --- a/include/dawn/native/D3D12Backend.h +++ b/include/dawn/native/D3D12Backend.h
@@ -86,6 +86,17 @@ constexpr static uint32_t kRequiredAlignment = D3D12_DEFAULT_RESOURCE_PLACEMENT_ALIGNMENT; }; +// May be chained on SharedTextureMemoryDescriptor. +struct DAWN_NATIVE_EXPORT SharedTextureMemoryD3D12ResourceDescriptor : wgpu::ChainedStruct { + SharedTextureMemoryD3D12ResourceDescriptor() { + sType = static_cast<wgpu::SType>(WGPUSType_SharedTextureMemoryD3D12ResourceDescriptor); + } + + // This ID3D12Resource object must be created from the same ID3D12Device used in the + // WGPUDevice. + Microsoft::WRL::ComPtr<ID3D12Resource> resource; +}; + } // namespace dawn::native::d3d12 #endif // INCLUDE_DAWN_NATIVE_D3D12BACKEND_H_
diff --git a/src/dawn/dawn.json b/src/dawn/dawn.json index 5d66333..bee511e 100644 --- a/src/dawn/dawn.json +++ b/src/dawn/dawn.json
@@ -2453,7 +2453,8 @@ {"value": 57, "name": "dawn device allocator control", "tags": ["dawn"]}, {"value": 58, "name": "chromium experimental bindless", "tags": ["dawn"]}, {"value": 59, "name": "adapter properties WGPU", "tags": ["dawn"]}, - {"value": 60, "name": "shared buffer memory D3D12 shared memory file mapping handle", "tags": ["dawn"]} + {"value": 60, "name": "shared buffer memory D3D12 shared memory file mapping handle", "tags": ["dawn"]}, + {"value": 61, "name": "shared texture memory D3D12 resource", "tags": ["dawn", "native"]} ] }, "filter mode": { @@ -3973,7 +3974,9 @@ {"value": 77, "name": "texel buffer binding layout", "tags": ["dawn"]}, {"value": 78, "name": "shared texture memory metal end access state", "tags": ["dawn", "native"]}, {"value": 79, "name": "adapter properties WGPU", "tags": ["dawn"]}, - {"value": 80, "name": "shared buffer memory D3D12 shared memory file mapping handle descriptor", "tags": ["dawn", "native"]} + {"value": 80, "name": "shared buffer memory D3D12 shared memory file mapping handle descriptor", "tags": ["dawn", "native"]}, + {"value": 81, "name": "shared texture memory D3D12 resource descriptor", "tags": ["dawn", "native"]} + ] }, "texture": {
diff --git a/src/dawn/native/ChainUtilsImpl.inl b/src/dawn/native/ChainUtilsImpl.inl index 8c54c56..b28b49a 100644 --- a/src/dawn/native/ChainUtilsImpl.inl +++ b/src/dawn/native/ChainUtilsImpl.inl
@@ -44,6 +44,7 @@ namespace d3d12 { struct SharedBufferMemoryD3D12ResourceDescriptor; struct SharedBufferMemoryD3D12SharedMemoryFileHandleDescriptor; +struct SharedTextureMemoryD3D12ResourceDescriptor; } namespace opengl { @@ -89,9 +90,14 @@ wgpu::SType(WGPUSType_SharedTextureMemoryD3D11Texture2DDescriptor); template <> +constexpr inline wgpu::SType STypeForImpl<d3d12::SharedTextureMemoryD3D12ResourceDescriptor> = + wgpu::SType(WGPUSType_SharedTextureMemoryD3D12ResourceDescriptor); + +template <> struct AdditionalExtensions<SharedTextureMemoryDescriptor> { using List = - AdditionalExtensionsList<const d3d11::SharedTextureMemoryD3D11Texture2DDescriptor*>; + AdditionalExtensionsList<const d3d11::SharedTextureMemoryD3D11Texture2DDescriptor*, + const d3d12::SharedTextureMemoryD3D12ResourceDescriptor*>; }; template <>
diff --git a/src/dawn/native/Features.cpp b/src/dawn/native/Features.cpp index 488380f..494de28 100644 --- a/src/dawn/native/Features.cpp +++ b/src/dawn/native/Features.cpp
@@ -442,6 +442,10 @@ {Feature::SharedBufferMemoryD3D12SharedMemoryFileMappingHandle, {"Supports importing a shared memory file mapping handle as shared buffer memory.", "https://dawn.googlesource.com/dawn/+/refs/heads/main/docs/dawn/features/shared_buffer.md", + FeatureInfo::FeatureState::Experimental}}, + {Feature::SharedTextureMemoryD3D12Resource, + {"Support importing ID3D12Resource as shared texture memory.", + "https://dawn.googlesource.com/dawn/+/refs/heads/main/docs/dawn/features/shared_texture.md", FeatureInfo::FeatureState::Experimental}}}; } // anonymous namespace
diff --git a/src/dawn/native/d3d12/DeviceD3D12.cpp b/src/dawn/native/d3d12/DeviceD3D12.cpp index 7909de0..df1d8f3 100644 --- a/src/dawn/native/d3d12/DeviceD3D12.cpp +++ b/src/dawn/native/d3d12/DeviceD3D12.cpp
@@ -491,7 +491,8 @@ wgpu::SType type; DAWN_TRY_ASSIGN( - type, (unpacked.ValidateBranches<Branch<SharedTextureMemoryDXGISharedHandleDescriptor>>())); + type, (unpacked.ValidateBranches<Branch<SharedTextureMemoryDXGISharedHandleDescriptor>, + Branch<SharedTextureMemoryD3D12ResourceDescriptor>>())); switch (type) { case wgpu::SType::SharedTextureMemoryDXGISharedHandleDescriptor: @@ -501,6 +502,13 @@ return SharedTextureMemory::Create( this, descriptor->label, unpacked.Get<SharedTextureMemoryDXGISharedHandleDescriptor>()); + case wgpu::SType::SharedTextureMemoryD3D12ResourceDescriptor: + DAWN_INVALID_IF(!HasFeature(Feature::SharedTextureMemoryD3D12Resource), + "%s is not enabled.", + wgpu::FeatureName::SharedTextureMemoryD3D12Resource); + return SharedTextureMemory::Create( + this, descriptor->label, + unpacked.Get<SharedTextureMemoryD3D12ResourceDescriptor>()); default: DAWN_UNREACHABLE(); }
diff --git a/src/dawn/native/d3d12/PhysicalDeviceD3D12.cpp b/src/dawn/native/d3d12/PhysicalDeviceD3D12.cpp index be3cfee..315012b 100644 --- a/src/dawn/native/d3d12/PhysicalDeviceD3D12.cpp +++ b/src/dawn/native/d3d12/PhysicalDeviceD3D12.cpp
@@ -212,6 +212,7 @@ } EnableFeature(Feature::SharedTextureMemoryDXGISharedHandle); + EnableFeature(Feature::SharedTextureMemoryD3D12Resource); EnableFeature(Feature::SharedFenceDXGISharedHandle); if (SupportsBufferMapExtendedUsages()) {
diff --git a/src/dawn/native/d3d12/SharedTextureMemoryD3D12.cpp b/src/dawn/native/d3d12/SharedTextureMemoryD3D12.cpp index 8a5ec77..5b7eb4f 100644 --- a/src/dawn/native/d3d12/SharedTextureMemoryD3D12.cpp +++ b/src/dawn/native/d3d12/SharedTextureMemoryD3D12.cpp
@@ -30,6 +30,7 @@ #include <utility> #include "dawn/native/ChainUtils.h" +#include "dawn/native/D3D12Backend.h" #include "dawn/native/d3d/D3DError.h" #include "dawn/native/d3d/KeyedMutex.h" #include "dawn/native/d3d/UtilsD3D.h" @@ -49,7 +50,35 @@ Ref<d3d::KeyedMutex> keyedMutex; DAWN_TRY(device->ImportSharedHandleResource(descriptor->handle, descriptor->useKeyedMutex, d3d12Resource, keyedMutex)); + return CreateSharedTextureMemoryFromD3D12Resource(device, label, d3d12Resource, keyedMutex); +} +// static +ResultOrError<Ref<SharedTextureMemory>> SharedTextureMemory::Create( + Device* device, + StringView label, + const SharedTextureMemoryD3D12ResourceDescriptor* descriptor) { + DAWN_INVALID_IF(descriptor->resource == nullptr, "D3D12Resource is missing."); + ComPtr<ID3D12Resource> d3d12Resource = descriptor->resource; + return CreateSharedTextureMemoryFromD3D12Resource(device, label, d3d12Resource, nullptr); +} + +SharedTextureMemory::SharedTextureMemory(Device* device, + StringView label, + SharedTextureMemoryProperties properties, + ComPtr<ID3D12Resource> resource, + Ref<d3d::KeyedMutex> keyedMutex) + : d3d::SharedTextureMemory(device, label, properties), + mResource(std::move(resource)), + mKeyedMutex(std::move(keyedMutex)) {} + +// static +ResultOrError<Ref<SharedTextureMemory>> +SharedTextureMemory::CreateSharedTextureMemoryFromD3D12Resource( + Device* device, + StringView label, + ComPtr<ID3D12Resource> d3d12Resource, + Ref<d3d::KeyedMutex> keyedMutex) { D3D12_RESOURCE_DESC desc = d3d12Resource->GetDesc(); DAWN_INVALID_IF(desc.Dimension != D3D12_RESOURCE_DIMENSION_TEXTURE2D, "Resource dimension (%d) was not Texture2D", desc.Dimension); @@ -98,15 +127,6 @@ return result; } -SharedTextureMemory::SharedTextureMemory(Device* device, - StringView label, - SharedTextureMemoryProperties properties, - ComPtr<ID3D12Resource> resource, - Ref<d3d::KeyedMutex> keyedMutex) - : d3d::SharedTextureMemory(device, label, properties), - mResource(std::move(resource)), - mKeyedMutex(std::move(keyedMutex)) {} - void SharedTextureMemory::DestroyImpl() { ToBackend(GetDevice())->ReferenceUntilUnused(std::move(mResource)); mKeyedMutex = nullptr;
diff --git a/src/dawn/native/d3d12/SharedTextureMemoryD3D12.h b/src/dawn/native/d3d12/SharedTextureMemoryD3D12.h index 2ab48ea..eb96cdb 100644 --- a/src/dawn/native/d3d12/SharedTextureMemoryD3D12.h +++ b/src/dawn/native/d3d12/SharedTextureMemoryD3D12.h
@@ -39,6 +39,7 @@ namespace d3d12 { class Device; +struct SharedTextureMemoryD3D12ResourceDescriptor; class SharedTextureMemory final : public d3d::SharedTextureMemory { public: @@ -47,6 +48,11 @@ StringView label, const SharedTextureMemoryDXGISharedHandleDescriptor* descriptor); + static ResultOrError<Ref<SharedTextureMemory>> Create( + Device* device, + StringView label, + const SharedTextureMemoryD3D12ResourceDescriptor* descriptor); + ID3D12Resource* GetD3DResource() const; d3d::KeyedMutex* GetKeyedMutex() const; @@ -58,6 +64,12 @@ ComPtr<ID3D12Resource> resource, Ref<d3d::KeyedMutex> keyedMutex); + static ResultOrError<Ref<SharedTextureMemory>> CreateSharedTextureMemoryFromD3D12Resource( + Device* device, + StringView label, + ComPtr<ID3D12Resource> d3d12Resource, + Ref<d3d::KeyedMutex> keyedMutex); + void DestroyImpl() override; ResultOrError<Ref<TextureBase>> CreateTextureImpl(
diff --git a/src/dawn/node/binding/Converter.cpp b/src/dawn/node/binding/Converter.cpp index 2468e79..2efe08d 100644 --- a/src/dawn/node/binding/Converter.cpp +++ b/src/dawn/node/binding/Converter.cpp
@@ -1752,6 +1752,7 @@ case wgpu::FeatureName::ChromiumExperimentalBindless: case wgpu::FeatureName::AdapterPropertiesWGPU: case wgpu::FeatureName::SharedBufferMemoryD3D12SharedMemoryFileMappingHandle: + case wgpu::FeatureName::SharedTextureMemoryD3D12Resource: return false; } return false;
diff --git a/src/dawn/tests/BUILD.gn b/src/dawn/tests/BUILD.gn index a5b23cf..d3d4275 100644 --- a/src/dawn/tests/BUILD.gn +++ b/src/dawn/tests/BUILD.gn
@@ -834,6 +834,7 @@ sources += [ "white_box/SharedBufferMemoryTests_win.cpp", "white_box/SharedTextureMemoryTests_win.cpp", + "white_box/SharedTextureMemoryTests_win_d3d12.cpp", ] }
diff --git a/src/dawn/tests/end2end/ArchTierLimitsExhaustive.cpp b/src/dawn/tests/end2end/ArchTierLimitsExhaustive.cpp index cf8e1d0..ac272dc 100644 --- a/src/dawn/tests/end2end/ArchTierLimitsExhaustive.cpp +++ b/src/dawn/tests/end2end/ArchTierLimitsExhaustive.cpp
@@ -368,6 +368,7 @@ ChromiumExperimentalBindless, AdapterPropertiesWGPU, SharedBufferMemoryD3D12SharedMemoryFileMappingHandle, + SharedTextureMemoryD3D12Resource, }; @@ -392,61 +393,61 @@ }; // AMD -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0 }, "Metal_AMD_Radeon_Pro_5300M"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0 }, "Metal_AMD_Radeon_Pro_555X"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0 }, "Metal_AMD_Radeon_Pro_560X"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0 }, "Metal_AMD_Radeon_Pro_5300M"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0 }, "Metal_AMD_Radeon_Pro_555X"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, 0, 1, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0 }, "Metal_AMD_Radeon_Pro_560X"); // Apple -AddDevice({1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0 }, "Metal_Apple_M2"); +AddDevice({1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0 }, "Metal_Apple_M2"); // ARM // Intel -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0 }, "D3D11_Intel_R__UHD_Graphics_630"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 1 }, "D3D12_Intel_R__UHD_Graphics_630"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 1 }, "D3D12_Intel_R__UHD_Graphics_630"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 0, 0, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0 }, "Metal_Intel_R__UHD_Graphics_630"); -AddDevice({0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, "OpenGLES_ANGLE__Intel__Intel_R__UHD_Graphics_630__0x00009BC5__Direct3D11_vs_5_0_ps_5_0__D3D11_31_0_101_2127__compat"); -AddDevice({1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0 }, "Vulkan_Intel_R__UHD_Graphics_630"); -AddDevice({1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0 }, "Vulkan_Intel_R__UHD_Graphics_630__CML_GT2"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0 }, "D3D11_Intel_R__UHD_Graphics_770"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0 }, "D3D11_Intel_R__UHD_Graphics_770"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 1 }, "D3D12_Intel_R__UHD_Graphics_770"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 1 }, "D3D12_Intel_R__UHD_Graphics_770"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 1 }, "D3D12_Intel_R__UHD_Graphics_770"); -AddDevice({0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, "OpenGLES_ANGLE__Intel__Intel_R__UHD_Graphics_770__0x00004680__Direct3D11_vs_5_0_ps_5_0__D3D11_31_0_101_5333__compat"); -AddDevice({0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, "OpenGLES_ANGLE__Intel__Intel_R__UHD_Graphics_770__0x00004680__Direct3D11_vs_5_0_ps_5_0__D3D11_31_0_101_5333__compat"); -AddDevice({1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0 }, "Vulkan_Intel_R__UHD_Graphics_770"); -AddDevice({1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0 }, "Vulkan_Intel_R__UHD_Graphics_770__ADL_S_GT1"); -AddDevice({1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0 }, "Vulkan_Intel_R__Iris_R__Xe_Graphics__TGL_GT2"); -AddDevice({1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0 }, "Vulkan_Intel_R__Iris_R__Xe_Graphics__TGL_GT2"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0 }, "D3D11_Intel_R__UHD_Graphics_630"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 1, 1 }, "D3D12_Intel_R__UHD_Graphics_630"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 1, 1 }, "D3D12_Intel_R__UHD_Graphics_630"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 0, 0, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0 }, "Metal_Intel_R__UHD_Graphics_630"); +AddDevice({0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, "OpenGLES_ANGLE__Intel__Intel_R__UHD_Graphics_630__0x00009BC5__Direct3D11_vs_5_0_ps_5_0__D3D11_31_0_101_2127__compat"); +AddDevice({1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0 }, "Vulkan_Intel_R__UHD_Graphics_630"); +AddDevice({1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0 }, "Vulkan_Intel_R__UHD_Graphics_630__CML_GT2"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0 }, "D3D11_Intel_R__UHD_Graphics_770"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0 }, "D3D11_Intel_R__UHD_Graphics_770"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 1, 1 }, "D3D12_Intel_R__UHD_Graphics_770"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 1, 1 }, "D3D12_Intel_R__UHD_Graphics_770"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 1, 1 }, "D3D12_Intel_R__UHD_Graphics_770"); +AddDevice({0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, "OpenGLES_ANGLE__Intel__Intel_R__UHD_Graphics_770__0x00004680__Direct3D11_vs_5_0_ps_5_0__D3D11_31_0_101_5333__compat"); +AddDevice({0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, "OpenGLES_ANGLE__Intel__Intel_R__UHD_Graphics_770__0x00004680__Direct3D11_vs_5_0_ps_5_0__D3D11_31_0_101_5333__compat"); +AddDevice({1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0 }, "Vulkan_Intel_R__UHD_Graphics_770"); +AddDevice({1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0 }, "Vulkan_Intel_R__UHD_Graphics_770__ADL_S_GT1"); +AddDevice({1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0 }, "Vulkan_Intel_R__Iris_R__Xe_Graphics__TGL_GT2"); +AddDevice({1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0 }, "Vulkan_Intel_R__Iris_R__Xe_Graphics__TGL_GT2"); // llvmpipe -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0 }, "Vulkan_llvmpipe__LLVM_19_1_7__256_bits"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0 }, "Vulkan_llvmpipe__LLVM_19_1_7__256_bits"); // Microsoft -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0 }, "D3D11_Microsoft_Basic_Render_Driver_Integrated_GPU"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 1 }, "D3D12_Microsoft_Basic_Render_Driver_Integrated_GPU"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 1 }, "D3D12_Microsoft_Basic_Render_Driver_Integrated_GPU"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0 }, "D3D11_Microsoft_Basic_Render_Driver_Integrated_GPU"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 1, 1 }, "D3D12_Microsoft_Basic_Render_Driver_Integrated_GPU"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 1, 1 }, "D3D12_Microsoft_Basic_Render_Driver_Integrated_GPU"); // NVIDIA -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0 }, "D3D11_NVIDIA_GeForce_GTX_1660"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0 }, "D3D12_NVIDIA_GeForce_GTX_1660"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0 }, "D3D12_NVIDIA_GeForce_GTX_1660"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0 }, "Vulkan_GeForce_GTX_1660"); -AddDevice({0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, "OpenGLES_ANGLE__NVIDIA__NVIDIA_GeForce_GTX_1660__0x00002184__Direct3D11_vs_5_0_ps_5_0__D3D11_31_0_15_4601__compat"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0 }, "Vulkan_NVIDIA_GeForce_GTX_1660"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0 }, "Vulkan_NVIDIA_GeForce_GTX_1660"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0 }, "Vulkan_NVIDIA_GeForce_GTX_1660"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0 }, "D3D11_NVIDIA_GeForce_GTX_1660"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 1 }, "D3D12_NVIDIA_GeForce_GTX_1660"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 1 }, "D3D12_NVIDIA_GeForce_GTX_1660"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0 }, "Vulkan_GeForce_GTX_1660"); +AddDevice({0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, "OpenGLES_ANGLE__NVIDIA__NVIDIA_GeForce_GTX_1660__0x00002184__Direct3D11_vs_5_0_ps_5_0__D3D11_31_0_15_4601__compat"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0 }, "Vulkan_NVIDIA_GeForce_GTX_1660"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0 }, "Vulkan_NVIDIA_GeForce_GTX_1660"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0 }, "Vulkan_NVIDIA_GeForce_GTX_1660"); // Qualcomm -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0 }, "D3D11_Qualcomm_R__Adreno_TM__X1_85_GPU"); -AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0 }, "D3D12_Qualcomm_R__Adreno_TM__X1_85_GPU"); -AddDevice({1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0 }, "Vulkan_Qualcomm_R__Adreno_TM__X1_85_GPU"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0 }, "D3D11_Qualcomm_R__Adreno_TM__X1_85_GPU"); +AddDevice({1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0 }, "D3D12_Qualcomm_R__Adreno_TM__X1_85_GPU"); +AddDevice({1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0 }, "Vulkan_Qualcomm_R__Adreno_TM__X1_85_GPU"); // SwiftShader -AddDevice({0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0 }, "OpenGLES_ANGLE__Google__Vulkan_1_3_0__SwiftShader_Device__Subzero___0x0000C0DE____SwiftShader_driver_5_0_0__compat"); -AddDevice({0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0 }, "OpenGLES_ANGLE__Google__Vulkan_1_3_0__SwiftShader_Device__Subzero___0x0000C0DE____SwiftShader_driver_5_0_0__compat"); +AddDevice({0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0 }, "OpenGLES_ANGLE__Google__Vulkan_1_3_0__SwiftShader_Device__Subzero___0x0000C0DE____SwiftShader_driver_5_0_0__compat"); +AddDevice({0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0 }, "OpenGLES_ANGLE__Google__Vulkan_1_3_0__SwiftShader_Device__Subzero___0x0000C0DE____SwiftShader_driver_5_0_0__compat"); auto supported_features = this->GetSupportedFeatures();
diff --git a/src/dawn/tests/white_box/SharedTextureMemoryTests_win.cpp b/src/dawn/tests/white_box/SharedTextureMemoryTests_win.cpp index 02576f8..faed01a 100644 --- a/src/dawn/tests/white_box/SharedTextureMemoryTests_win.cpp +++ b/src/dawn/tests/white_box/SharedTextureMemoryTests_win.cpp
@@ -389,6 +389,8 @@ // Test that it is an error to import a shared fence without enabling the feature. TEST_P(SharedTextureMemoryNoFeatureTests, SharedFenceImportWithoutFeature) { + DAWN_TEST_UNSUPPORTED_IF(IsD3D12()); + auto backend = static_cast<Backend*>(GetParam().mBackend); DAWN_TEST_UNSUPPORTED_IF(!backend->HasFenceSupport(device)); @@ -418,6 +420,8 @@ // Test that a shared handle can be imported, and then exported. TEST_P(SharedTextureMemoryTests, SharedFenceSuccessfulImportExport) { + DAWN_TEST_UNSUPPORTED_IF(IsD3D12()); + auto backend = static_cast<Backend*>(GetParam().mBackend); DAWN_TEST_UNSUPPORTED_IF(!backend->HasFenceSupport(device)); @@ -507,6 +511,8 @@ // Test exporting info from a shared fence with no chained struct. // It should be valid and the fence type is exported. TEST_P(SharedTextureMemoryTests, SharedFenceExportInfoNoChainedStruct) { + DAWN_TEST_UNSUPPORTED_IF(IsD3D12()); + auto backend = static_cast<Backend*>(GetParam().mBackend); DAWN_TEST_UNSUPPORTED_IF(!backend->HasFenceSupport(device)); @@ -543,6 +549,8 @@ // Test exporting info from a shared fence with an invalid chained struct. // It should not be valid, but the fence type should still be exported. TEST_P(SharedTextureMemoryTests, SharedFenceExportInfoInvalidChainedStruct) { + DAWN_TEST_UNSUPPORTED_IF(IsD3D12()); + auto backend = static_cast<Backend*>(GetParam().mBackend); DAWN_TEST_UNSUPPORTED_IF(!backend->HasFenceSupport(device));
diff --git a/src/dawn/tests/white_box/SharedTextureMemoryTests_win_d3d12.cpp b/src/dawn/tests/white_box/SharedTextureMemoryTests_win_d3d12.cpp new file mode 100644 index 0000000..80f1133 --- /dev/null +++ b/src/dawn/tests/white_box/SharedTextureMemoryTests_win_d3d12.cpp
@@ -0,0 +1,460 @@ +// Copyright 2025 The Dawn & Tint Authors +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are met: +// +// 1. Redistributions of source code must retain the above copyright notice, this +// list of conditions and the following disclaimer. +// +// 2. Redistributions in binary form must reproduce the above copyright notice, +// this list of conditions and the following disclaimer in the documentation +// and/or other materials provided with the distribution. +// +// 3. Neither the name of the copyright holder nor the names of its +// contributors may be used to endorse or promote products derived from +// this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +// DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE +// FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR +// SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, +// OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +#include <d3d12.h> +#include <dxgi1_4.h> +#include <webgpu/webgpu_cpp.h> +#include <wrl/client.h> + +#include <memory> +#include <sstream> +#include <string> +#include <utility> +#include <vector> + +#include "dawn/native/D3D12Backend.h" +#include "dawn/native/D3DBackend.h" +#include "dawn/native/DawnNative.h" +#include "dawn/tests/white_box/SharedTextureMemoryTests.h" + +namespace dawn { +namespace { + +using Microsoft::WRL::ComPtr; + +enum class Mode { + // TODO(crbug.com/454827192): Add tests for shared handle to D3D12Resources. + // DXGISharedHandle, + D3D12Resource, +}; + +// Backend for testing SharedTextureMemory backed by D3D12 resources. This test +// setup is adapted from SharedTextureMemoryTests_win.cpp. +class BackendD3D12 : public SharedTextureMemoryTestBackend { + public: + template <Mode kMode> + static BackendD3D12* GetInstance() { + static BackendD3D12 b(kMode); + return &b; + } + + std::string Name() const override { + std::ostringstream ss; + switch (mMode) { + case Mode::D3D12Resource: { + ss << "D3D12Resource"; + } break; + } + + return ss.str(); + } + + bool SupportsConcurrentRead() const override { return true; } + + ComPtr<ID3D12Device> MakeD3D12Device(const wgpu::Device& device) { + ComPtr<ID3D12Device> d3d12Device = native::d3d12::GetD3D12Device(device.Get()); + return d3d12Device; + } + + std::vector<wgpu::FeatureName> RequiredFeatures(const wgpu::Adapter& adapter) const override { + std::vector<wgpu::FeatureName> features; + if (adapter.HasFeature(wgpu::FeatureName::SharedFenceDXGISharedHandle)) { + features.push_back(wgpu::FeatureName::SharedFenceDXGISharedHandle); + } + + switch (mMode) { + case Mode::D3D12Resource: { + features.push_back(wgpu::FeatureName::SharedTextureMemoryD3D12Resource); + break; + } + } + + return features; + } + + bool UseSharedHandle() const { return false; } + + std::string LabelName(DXGI_FORMAT format, size_t size) const { + std::stringstream ss; + ss << "format 0x" << std::hex << format << " size " << size << "x" << size; + return ss.str(); + } + + wgpu::SharedTextureMemory CreateSharedTextureMemory(const wgpu::Device& device, + int layerCount) override { + ComPtr<ID3D12Device> d3d12Device = MakeD3D12Device(device); + + // Create a DX12 resource. + D3D12_RESOURCE_DESC texDesc = {}; + texDesc.Dimension = D3D12_RESOURCE_DIMENSION_TEXTURE2D; + texDesc.Alignment = 0; + texDesc.Width = 16; + texDesc.Height = 16; + texDesc.DepthOrArraySize = layerCount; + texDesc.MipLevels = 1; + texDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; + texDesc.SampleDesc.Count = 1; + texDesc.SampleDesc.Quality = 0; + texDesc.Layout = D3D12_TEXTURE_LAYOUT_UNKNOWN; + texDesc.Flags = D3D12_RESOURCE_FLAG_ALLOW_RENDER_TARGET | + D3D12_RESOURCE_FLAG_ALLOW_UNORDERED_ACCESS | + D3D12_RESOURCE_FLAG_ALLOW_SIMULTANEOUS_ACCESS; + + D3D12_HEAP_PROPERTIES heapProps = {}; + heapProps.Type = D3D12_HEAP_TYPE_DEFAULT; + heapProps.CPUPageProperty = D3D12_CPU_PAGE_PROPERTY_UNKNOWN; + heapProps.MemoryPoolPreference = D3D12_MEMORY_POOL_UNKNOWN; + heapProps.CreationNodeMask = 0; + heapProps.VisibleNodeMask = 0; + + D3D12_CLEAR_VALUE clearValue = {}; + clearValue.Format = texDesc.Format; + clearValue.Color[0] = 0.0f; + clearValue.Color[1] = 0.0f; + clearValue.Color[2] = 0.0f; + clearValue.Color[3] = 0.0f; + + ComPtr<ID3D12Resource> d3d12Resource; + HRESULT hr = d3d12Device->CreateCommittedResource( + &heapProps, D3D12_HEAP_FLAG_NONE, &texDesc, D3D12_RESOURCE_STATE_COMMON, &clearValue, + IID_PPV_ARGS(&d3d12Resource)); + DAWN_ASSERT(hr == S_OK); + + switch (mMode) { + case Mode::D3D12Resource: { + wgpu::SharedTextureMemoryDescriptor desc; + native::d3d12::SharedTextureMemoryD3D12ResourceDescriptor bufferDesc; + bufferDesc.resource = d3d12Resource.Get(); + desc.nextInChain = &bufferDesc; + desc.label = "D3D12Resource Texture"; + return device.ImportSharedTextureMemory(&desc); + } + } + } + + std::vector<std::vector<wgpu::SharedTextureMemory>> CreatePerDeviceSharedTextureMemories( + const std::vector<wgpu::Device>& devices, + int layerCount) override { + std::vector<std::vector<wgpu::SharedTextureMemory>> memories; + ComPtr<ID3D12Device> d3d12Device = MakeD3D12Device(devices[0]); + + // Check for D3D12 NV12 sharing support. + bool supportsNV12Sharing = false; + D3D12_FEATURE_DATA_D3D12_OPTIONS4 opts4 = {}; + d3d12Device->CheckFeatureSupport(D3D12_FEATURE_D3D12_OPTIONS4, &opts4, sizeof(opts4)); + if (opts4.SharedResourceCompatibilityTier >= D3D12_SHARED_RESOURCE_COMPATIBILITY_TIER_2) { + supportsNV12Sharing = true; + } + + struct D3DFormat { + DXGI_FORMAT format; + wgpu::FeatureName requiredFeature = wgpu::FeatureName(0u); + }; + std::vector<D3DFormat> formats = {{ + {DXGI_FORMAT_R16G16B16A16_FLOAT}, + {DXGI_FORMAT_R16G16_FLOAT}, + {DXGI_FORMAT_R16_FLOAT}, + {DXGI_FORMAT_R8G8B8A8_UNORM}, + {DXGI_FORMAT_B8G8R8A8_UNORM}, + {DXGI_FORMAT_R10G10B10A2_UNORM}, + {DXGI_FORMAT_R16G16_UNORM, wgpu::FeatureName::Unorm16TextureFormats}, + {DXGI_FORMAT_R16_UNORM, wgpu::FeatureName::Unorm16TextureFormats}, + {DXGI_FORMAT_R8G8_UNORM}, + {DXGI_FORMAT_R8_UNORM}, + }}; + + if (supportsNV12Sharing) { + formats.push_back({DXGI_FORMAT_NV12}); + } + + for (auto f : formats) { + for (uint32_t size : {4, 64}) { + // Create a DX12 resource. + D3D12_RESOURCE_DESC texDesc = {}; + texDesc.Dimension = D3D12_RESOURCE_DIMENSION_TEXTURE2D; + texDesc.Alignment = 0; + texDesc.Width = size; + texDesc.Height = size; + texDesc.DepthOrArraySize = layerCount; + texDesc.MipLevels = 1; + texDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; + texDesc.SampleDesc.Count = 1; + texDesc.SampleDesc.Quality = 0; + texDesc.Layout = D3D12_TEXTURE_LAYOUT_UNKNOWN; + texDesc.Flags = D3D12_RESOURCE_FLAG_ALLOW_RENDER_TARGET | + D3D12_RESOURCE_FLAG_ALLOW_UNORDERED_ACCESS | + D3D12_RESOURCE_FLAG_ALLOW_SIMULTANEOUS_ACCESS; + + D3D12_HEAP_PROPERTIES heapProps = {}; + heapProps.Type = D3D12_HEAP_TYPE_DEFAULT; + heapProps.CPUPageProperty = D3D12_CPU_PAGE_PROPERTY_UNKNOWN; + heapProps.MemoryPoolPreference = D3D12_MEMORY_POOL_UNKNOWN; + heapProps.CreationNodeMask = 0; + heapProps.VisibleNodeMask = 0; + + D3D12_CLEAR_VALUE clearValue = {}; + clearValue.Format = texDesc.Format; + clearValue.Color[0] = 0.0f; + clearValue.Color[1] = 0.0f; + clearValue.Color[2] = 0.0f; + clearValue.Color[3] = 0.0f; + + ComPtr<ID3D12Resource> d3d12Resource; + HRESULT hr = d3d12Device->CreateCommittedResource( + &heapProps, D3D12_HEAP_FLAG_NONE, &texDesc, D3D12_RESOURCE_STATE_COMMON, + &clearValue, IID_PPV_ARGS(&d3d12Resource)); + DAWN_ASSERT(hr == S_OK); + + std::vector<wgpu::SharedTextureMemory> perDeviceMemories; + switch (mMode) { + case Mode::D3D12Resource: { + wgpu::SharedTextureMemoryDescriptor desc; + native::d3d12::SharedTextureMemoryD3D12ResourceDescriptor bufferDesc; + bufferDesc.resource = d3d12Resource.Get(); + desc.nextInChain = &bufferDesc; + std::string label = LabelName(f.format, size); + desc.label = label.c_str(); + + for (auto& deviceObj : devices) { + if (f.requiredFeature != wgpu::FeatureName(0u) && + !deviceObj.HasFeature(f.requiredFeature)) { + continue; + } + perDeviceMemories.push_back(deviceObj.ImportSharedTextureMemory(&desc)); + } + break; + } + } + if (!perDeviceMemories.empty()) { + memories.push_back(std::move(perDeviceMemories)); + } + } + } + return memories; + } + + private: + explicit BackendD3D12(Mode mode) : mMode(mode) {} + + const Mode mMode; +}; + +// Test that it is an error to import a shared fence without enabling the feature (D3D12 fence +// path). +TEST_P(SharedTextureMemoryNoFeatureTests, SharedFenceImportWithoutFeatureD3D12) { + DAWN_TEST_UNSUPPORTED_IF(!IsD3D12()); + auto backend = static_cast<BackendD3D12*>(GetParam().mBackend); + ComPtr<ID3D12Device> d3d12Device = backend->MakeD3D12Device(device); + + // Create a shareable D3D12 fence. + ComPtr<ID3D12Fence> d3d12Fence; + HRESULT hr = d3d12Device->CreateFence(0, D3D12_FENCE_FLAG_SHARED, IID_PPV_ARGS(&d3d12Fence)); + ASSERT_EQ(hr, S_OK); + + // Create a shared handle for the fence. + HANDLE fenceSharedHandle = nullptr; + hr = d3d12Device->CreateSharedHandle(d3d12Fence.Get(), nullptr, GENERIC_ALL, nullptr, + &fenceSharedHandle); + ASSERT_EQ(hr, S_OK); + + // Attempt to import without the feature enabled; should be a device error. + wgpu::SharedFenceDXGISharedHandleDescriptor sharedHandleDesc; + sharedHandleDesc.handle = fenceSharedHandle; + + wgpu::SharedFenceDescriptor fenceDesc; + fenceDesc.nextInChain = &sharedHandleDesc; + + ASSERT_DEVICE_ERROR_MSG(wgpu::SharedFence fence = device.ImportSharedFence(&fenceDesc), + testing::HasSubstr("is not enabled")); + + ::CloseHandle(fenceSharedHandle); +} + +// Test that a shared handle can be imported, and then exported, using a D3D12 fence. +TEST_P(SharedTextureMemoryTests, SharedFenceSuccessfulImportExportD3D12) { + DAWN_TEST_UNSUPPORTED_IF(!IsD3D12()); + auto backend = static_cast<BackendD3D12*>(GetParam().mBackend); + ComPtr<ID3D12Device> d3d12Device = backend->MakeD3D12Device(device); + + // Create a D3D12 fence that can be shared. + ComPtr<ID3D12Fence> d3d12Fence; + HRESULT hr = d3d12Device->CreateFence(0, D3D12_FENCE_FLAG_SHARED, IID_PPV_ARGS(&d3d12Fence)); + ASSERT_EQ(hr, S_OK); + + // Export a shared handle for the fence. + HANDLE fenceSharedHandle = nullptr; + hr = d3d12Device->CreateSharedHandle(d3d12Fence.Get(), nullptr, GENERIC_ALL, nullptr, + &fenceSharedHandle); + ASSERT_EQ(hr, S_OK); + + // Import into Dawn as a shared fence. + wgpu::SharedFenceDXGISharedHandleDescriptor sharedHandleDesc; + sharedHandleDesc.handle = fenceSharedHandle; + + wgpu::SharedFenceDescriptor fenceDesc; + fenceDesc.nextInChain = &sharedHandleDesc; + + wgpu::SharedFence fence = device.ImportSharedFence(&fenceDesc); + + // We can close our local HANDLE after import (ownership transferred / duplicated internally). + ::CloseHandle(fenceSharedHandle); + + // Export info back out. + wgpu::SharedFenceDXGISharedHandleExportInfo sharedHandleInfo; + wgpu::SharedFenceExportInfo exportInfo; + exportInfo.nextInChain = &sharedHandleInfo; + fence.ExportInfo(&exportInfo); + + EXPECT_EQ(exportInfo.type, wgpu::SharedFenceType::DXGISharedHandle); + + // Open the exported handle again as a second D3D12 fence object. + ComPtr<ID3D12Fence> d3d12Fence2; + hr = d3d12Device->OpenSharedHandle(sharedHandleInfo.handle, IID_PPV_ARGS(&d3d12Fence2)); + ASSERT_EQ(hr, S_OK); + + // Verify both fence objects report the same initial completed value. + uint64_t fenceValue = d3d12Fence->GetCompletedValue(); + EXPECT_EQ(fenceValue, d3d12Fence2->GetCompletedValue()); + + // Create a command queue to signal the fence. + D3D12_COMMAND_QUEUE_DESC queueDesc = {}; + queueDesc.Type = D3D12_COMMAND_LIST_TYPE_DIRECT; + queueDesc.Priority = D3D12_COMMAND_QUEUE_PRIORITY_NORMAL; + queueDesc.Flags = D3D12_COMMAND_QUEUE_FLAG_NONE; + queueDesc.NodeMask = 0; + + ComPtr<ID3D12CommandQueue> queue; + hr = d3d12Device->CreateCommandQueue(&queueDesc, IID_PPV_ARGS(&queue)); + ASSERT_EQ(hr, S_OK); + + // Signal the fence to a new value. + hr = queue->Signal(d3d12Fence.Get(), fenceValue + 1); + ASSERT_EQ(hr, S_OK); + + // Wait on the fence via event. + HANDLE ev = ::CreateEvent(nullptr, TRUE, FALSE, TEXT("FenceCompleteD3D12")); + ASSERT_NE(ev, (HANDLE) nullptr); + hr = d3d12Fence->SetEventOnCompletion(fenceValue + 1, ev); + ASSERT_EQ(hr, S_OK); + ::WaitForSingleObject(ev, INFINITE); + ::CloseHandle(ev); + + // Both fence objects should now report the updated value. + EXPECT_EQ(fenceValue + 1, d3d12Fence->GetCompletedValue()); + EXPECT_EQ(fenceValue + 1, d3d12Fence2->GetCompletedValue()); +} + +// Test exporting info from a shared fence created from a D3D12 fence with no chained struct. +// It should be valid and the fence type is exported. +TEST_P(SharedTextureMemoryTests, SharedFenceExportInfoNoChainedStructD3D12) { + DAWN_TEST_UNSUPPORTED_IF(!IsD3D12()); + auto backend = static_cast<BackendD3D12*>(GetParam().mBackend); + ComPtr<ID3D12Device> d3d12Device = backend->MakeD3D12Device(device); + + // Create a shareable D3D12 fence. + ComPtr<ID3D12Fence> d3d12Fence; + HRESULT hr = d3d12Device->CreateFence(0, D3D12_FENCE_FLAG_SHARED, IID_PPV_ARGS(&d3d12Fence)); + ASSERT_EQ(hr, S_OK); + + // Create a shared handle for the fence. + HANDLE fenceSharedHandle = nullptr; + hr = d3d12Device->CreateSharedHandle(d3d12Fence.Get(), nullptr, GENERIC_ALL, nullptr, + &fenceSharedHandle); + ASSERT_EQ(hr, S_OK); + + // Import into Dawn. + wgpu::SharedFenceDXGISharedHandleDescriptor sharedHandleDesc; + sharedHandleDesc.handle = fenceSharedHandle; + + wgpu::SharedFenceDescriptor fenceDesc; + fenceDesc.nextInChain = &sharedHandleDesc; + + wgpu::SharedFence fence = device.ImportSharedFence(&fenceDesc); + + // Close our local handle after import. + ::CloseHandle(fenceSharedHandle); + + // Export info with no chained struct. + wgpu::SharedFenceExportInfo exportInfo; + exportInfo.nextInChain = nullptr; + + fence.ExportInfo(&exportInfo); + EXPECT_EQ(exportInfo.type, wgpu::SharedFenceType::DXGISharedHandle); +} + +// Test exporting info from a shared fence created from a D3D12 fence with an invalid chained +// struct. It should trigger a device error, but the fence type would still be known internally. +TEST_P(SharedTextureMemoryTests, SharedFenceExportInfoInvalidChainedStructD3D12) { + DAWN_TEST_UNSUPPORTED_IF(!IsD3D12()); + auto backend = static_cast<BackendD3D12*>(GetParam().mBackend); + ComPtr<ID3D12Device> d3d12Device = backend->MakeD3D12Device(device); + + // Create a shareable D3D12 fence. + ComPtr<ID3D12Fence> d3d12Fence; + HRESULT hr = d3d12Device->CreateFence(0, D3D12_FENCE_FLAG_SHARED, IID_PPV_ARGS(&d3d12Fence)); + ASSERT_EQ(hr, S_OK); + + // Create a shared handle for the fence. + HANDLE fenceSharedHandle = nullptr; + hr = d3d12Device->CreateSharedHandle(d3d12Fence.Get(), nullptr, GENERIC_ALL, nullptr, + &fenceSharedHandle); + ASSERT_EQ(hr, S_OK); + + // Import into Dawn. + wgpu::SharedFenceDXGISharedHandleDescriptor sharedHandleDesc; + sharedHandleDesc.handle = fenceSharedHandle; + + wgpu::SharedFenceDescriptor fenceDesc; + fenceDesc.nextInChain = &sharedHandleDesc; + + wgpu::SharedFence fence = device.ImportSharedFence(&fenceDesc); + + // Close our local handle after import. + ::CloseHandle(fenceSharedHandle); + + // Provide an invalid chained struct to ExportInfo. + wgpu::ChainedStructOut otherStruct; + wgpu::SharedFenceExportInfo exportInfo; + exportInfo.nextInChain = &otherStruct; + + ASSERT_DEVICE_ERROR(fence.ExportInfo(&exportInfo)); +} + +DAWN_INSTANTIATE_PREFIXED_TEST_P(D3D12, + SharedTextureMemoryNoFeatureTests, + {D3D12Backend()}, + {BackendD3D12::GetInstance<Mode::D3D12Resource>()}, + {1}); + +DAWN_INSTANTIATE_PREFIXED_TEST_P(D3D12, + SharedTextureMemoryTests, + {D3D12Backend()}, + {BackendD3D12::GetInstance<Mode::D3D12Resource>()}, + {1}); + +} // anonymous namespace +} // namespace dawn
diff --git a/src/dawn/wire/SupportedFeatures.cpp b/src/dawn/wire/SupportedFeatures.cpp index d079c8ed..dfff2f3 100644 --- a/src/dawn/wire/SupportedFeatures.cpp +++ b/src/dawn/wire/SupportedFeatures.cpp
@@ -56,6 +56,7 @@ case WGPUFeatureName_SharedTextureMemoryZirconHandle: case WGPUFeatureName_SharedTextureMemoryDXGISharedHandle: case WGPUFeatureName_SharedTextureMemoryD3D11Texture2D: + case WGPUFeatureName_SharedTextureMemoryD3D12Resource: case WGPUFeatureName_SharedTextureMemoryIOSurface: case WGPUFeatureName_SharedTextureMemoryEGLImage: case WGPUFeatureName_SharedFenceVkSemaphoreOpaqueFD: