From 1934e56159c9594bc645dad36a5a8b5354f5cbcb Mon Sep 17 00:00:00 2001 From: Brandon Jones Date: Tue, 14 Sep 2021 00:54:59 +0000 Subject: [PATCH] Disable multiple mip levels for r8/rg8unorm textures on Metal Bug: dawn:1071 Change-Id: I2cc9173f0dff325e4bb2583bb27a98bbaaa61531 Reviewed-on: https://dawn-review.googlesource.com/c/dawn/+/63462 Commit-Queue: Brandon Jones Reviewed-by: Corentin Wallez --- src/dawn_native/Texture.cpp | 8 ++++++++ src/dawn_native/Toggles.cpp | 5 +++++ src/dawn_native/Toggles.h | 1 + src/dawn_native/metal/DeviceMTL.mm | 10 +++++++++- src/tests/end2end/CopyTests.cpp | 5 +++++ src/tests/end2end/NonzeroTextureCreationTests.cpp | 6 ++++++ 6 files changed, 34 insertions(+), 1 deletion(-) diff --git a/src/dawn_native/Texture.cpp b/src/dawn_native/Texture.cpp index 889d706c7e..21e378b67e 100644 --- a/src/dawn_native/Texture.cpp +++ b/src/dawn_native/Texture.cpp @@ -311,6 +311,14 @@ namespace dawn_native { "disabled on Metal."); } + if (device->IsToggleEnabled(Toggle::DisableR8RG8Mipmaps) && descriptor->mipLevelCount > 1 && + (descriptor->format == wgpu::TextureFormat::R8Unorm || + descriptor->format == wgpu::TextureFormat::RG8Unorm)) { + return DAWN_VALIDATION_ERROR( + "https://crbug.com/dawn/1071: r8unorm and rg8unorm textures with more than one mip " + "level are disabled on Metal."); + } + return {}; } diff --git a/src/dawn_native/Toggles.cpp b/src/dawn_native/Toggles.cpp index 7c40fe7c1a..6b35aeb9f6 100644 --- a/src/dawn_native/Toggles.cpp +++ b/src/dawn_native/Toggles.cpp @@ -217,6 +217,11 @@ namespace dawn_native { "Enables calls to SetLabel to be forwarded to backend-specific APIs that label " "objects.", "https://crbug.com/dawn/840"}}, + {Toggle::DisableR8RG8Mipmaps, + {"disable_r8_rg8_mipmaps", + "Disables mipmaps for r8unorm and rg8unorm textures, which are known on some drivers " + "to not clear correctly.", + "https://crbug.com/dawn/1071"}}, // Dummy comment to separate the }} so it is clearer what to copy-paste to add a toggle. }}; } // anonymous namespace diff --git a/src/dawn_native/Toggles.h b/src/dawn_native/Toggles.h index 668086fcaa..eccfb21bb7 100644 --- a/src/dawn_native/Toggles.h +++ b/src/dawn_native/Toggles.h @@ -59,6 +59,7 @@ namespace dawn_native { DisableWorkgroupInit, DisableSymbolRenaming, UseUserDefinedLabelsInBackend, + DisableR8RG8Mipmaps, EnumCount, InvalidEnum = EnumCount, diff --git a/src/dawn_native/metal/DeviceMTL.mm b/src/dawn_native/metal/DeviceMTL.mm index 348f5db312..c24916d117 100644 --- a/src/dawn_native/metal/DeviceMTL.mm +++ b/src/dawn_native/metal/DeviceMTL.mm @@ -199,13 +199,21 @@ namespace dawn_native { namespace metal { // TODO(crbug.com/dawn/846): tighten this workaround when the driver bug is fixed. SetToggle(Toggle::AlwaysResolveIntoZeroLevelAndLayer, true); + const PCIInfo& pciInfo = GetAdapter()->GetPCIInfo(); + // TODO(crbug.com/dawn/847): Use MTLStorageModeShared instead of MTLStorageModePrivate when // creating MTLCounterSampleBuffer in QuerySet on Intel platforms, otherwise it fails to // create the buffer. Change to use MTLStorageModePrivate when the bug is fixed. if (@available(macOS 10.15, iOS 14.0, *)) { - bool useSharedMode = gpu_info::IsIntel(this->GetAdapter()->GetPCIInfo().vendorId); + bool useSharedMode = gpu_info::IsIntel(pciInfo.vendorId); SetToggle(Toggle::MetalUseSharedModeForCounterSampleBuffer, useSharedMode); } + + // TODO(crbug.com/dawn/1071): r8unorm and rg8unorm textures with multiple mip levels don't + // clear properly on Intel Macs. + if (gpu_info::IsIntel(pciInfo.vendorId)) { + SetToggle(Toggle::DisableR8RG8Mipmaps, true); + } } ResultOrError> Device::CreateBindGroupImpl( diff --git a/src/tests/end2end/CopyTests.cpp b/src/tests/end2end/CopyTests.cpp index 43bc5caea2..f0750a1108 100644 --- a/src/tests/end2end/CopyTests.cpp +++ b/src/tests/end2end/CopyTests.cpp @@ -2120,6 +2120,11 @@ TEST_P(CopyTests_T2T, CopyFromNonZeroMipLevelWithTexelBlockSizeLessThan4Bytes) { continue; } + if (HasToggleEnabled("disable_r8_rg8_mipmaps") && + (format == wgpu::TextureFormat::R8Unorm || format == wgpu::TextureFormat::RG8Unorm)) { + continue; + } + for (uint32_t textureLayer : kTestTextureLayer) { const wgpu::Extent3D kUploadSize = {4u, 4u, textureLayer}; diff --git a/src/tests/end2end/NonzeroTextureCreationTests.cpp b/src/tests/end2end/NonzeroTextureCreationTests.cpp index 783c3ecd69..6040562591 100644 --- a/src/tests/end2end/NonzeroTextureCreationTests.cpp +++ b/src/tests/end2end/NonzeroTextureCreationTests.cpp @@ -104,6 +104,12 @@ namespace { GetParam().mFormat == wgpu::TextureFormat::Depth24PlusStencil8) && IsMetal() && IsIntel() && GetParam().mMip != 0); + // TODO(crbug.com/dawn/1071): Implement a workaround on Intel/Metal backends. + DAWN_SUPPRESS_TEST_IF((GetParam().mFormat == wgpu::TextureFormat::R8Unorm || + GetParam().mFormat == wgpu::TextureFormat::RG8Unorm) && + GetParam().mMipCount > 1 && + HasToggleEnabled("disable_r8_rg8_mipmaps")); + // Copies from depth textures not fully supported on the OpenGL backend right now. DAWN_SUPPRESS_TEST_IF(GetParam().mFormat == wgpu::TextureFormat::Depth32Float && (IsOpenGL() || IsOpenGLES()));