From d2e6e605850eccb65b2a07dd99dbd1e3c3aaa19f Mon Sep 17 00:00:00 2001 From: Mehmet Oguz Derin Date: Sat, 19 Apr 2025 03:16:22 +0300 Subject: [PATCH 1/8] Support Sliced 3D for ASTC --- deno_webgpu/webgpu.idl | 1 + deno_webgpu/webidl.rs | 2 + tests/tests/wgpu-gpu/clear_texture.rs | 7 ++- wgpu-core/src/device/resource.rs | 3 ++ wgpu-hal/src/gles/adapter.rs | 1 + wgpu-hal/src/metal/adapter.rs | 3 ++ wgpu-hal/src/metal/mod.rs | 1 + wgpu-hal/src/vulkan/adapter.rs | 61 +++++++++++++++++++++++++++ wgpu-types/src/features.rs | 30 ++++++++++--- wgpu-types/src/lib.rs | 7 +++ wgpu/src/backend/webgpu.rs | 4 ++ 11 files changed, 112 insertions(+), 8 deletions(-) diff --git a/deno_webgpu/webgpu.idl b/deno_webgpu/webgpu.idl index df2aef498f..cb4fff5965 100644 --- a/deno_webgpu/webgpu.idl +++ b/deno_webgpu/webgpu.idl @@ -99,6 +99,7 @@ enum GPUFeatureName { "texture-compression-bc-sliced-3d", "texture-compression-etc2", "texture-compression-astc", + "texture-compression-astc-sliced-3d", "timestamp-query", "indirect-first-instance", "shader-f16", diff --git a/deno_webgpu/webidl.rs b/deno_webgpu/webidl.rs index 97476a7ac3..679f445de2 100644 --- a/deno_webgpu/webidl.rs +++ b/deno_webgpu/webidl.rs @@ -359,6 +359,8 @@ pub enum GPUFeatureName { TextureCompressionEtc2, #[webidl(rename = "texture-compression-astc")] TextureCompressionAstc, + #[webidl(rename = "texture-compression-astc-sliced-3d")] + TextureCompressionAstcSliced3d, #[webidl(rename = "rg11b10ufloat-renderable")] Rg11b10ufloatRenderable, #[webidl(rename = "bgra8unorm-storage")] diff --git a/tests/tests/wgpu-gpu/clear_texture.rs b/tests/tests/wgpu-gpu/clear_texture.rs index 484681130b..0789eedb1c 100644 --- a/tests/tests/wgpu-gpu/clear_texture.rs +++ b/tests/tests/wgpu-gpu/clear_texture.rs @@ -405,9 +405,14 @@ static CLEAR_TEXTURE_COMPRESSED_BCN: GpuTestConfiguration = GpuTestConfiguration static CLEAR_TEXTURE_COMPRESSED_ASTC: GpuTestConfiguration = GpuTestConfiguration::new() .parameters( TestParameters::default() - .features(wgpu::Features::CLEAR_TEXTURE | wgpu::Features::TEXTURE_COMPRESSION_ASTC) + .features( + wgpu::Features::CLEAR_TEXTURE + | wgpu::Features::TEXTURE_COMPRESSION_ASTC + | wgpu::Features::TEXTURE_COMPRESSION_ASTC_SLICED_3D, + ) .limits(wgpu::Limits { max_texture_dimension_2d: wgpu::COPY_BYTES_PER_ROW_ALIGNMENT * 12, + max_texture_dimension_3d: wgpu::COPY_BYTES_PER_ROW_ALIGNMENT * 12, ..wgpu::Limits::downlevel_defaults() }) // https://bugs.chromium.org/p/angleproject/issues/detail?id=7056 diff --git a/wgpu-core/src/device/resource.rs b/wgpu-core/src/device/resource.rs index 7b54a78809..59dfe083ff 100644 --- a/wgpu-core/src/device/resource.rs +++ b/wgpu-core/src/device/resource.rs @@ -958,6 +958,9 @@ impl Device { if desc.format.is_bcn() { self.require_features(wgt::Features::TEXTURE_COMPRESSION_BC_SLICED_3D) .map_err(|error| CreateTextureError::MissingFeatures(desc.format, error))?; + } else if desc.format.is_astc() { + self.require_features(wgt::Features::TEXTURE_COMPRESSION_ASTC_SLICED_3D) + .map_err(|error| CreateTextureError::MissingFeatures(desc.format, error))?; } else { return Err(CreateTextureError::InvalidCompressedDimension( desc.dimension, diff --git a/wgpu-hal/src/gles/adapter.rs b/wgpu-hal/src/gles/adapter.rs index 34725a944d..1325f5c786 100644 --- a/wgpu-hal/src/gles/adapter.rs +++ b/wgpu-hal/src/gles/adapter.rs @@ -531,6 +531,7 @@ impl super::Adapter { .compressed_texture_astc_supports_ldr_profile() { features.insert(wgt::Features::TEXTURE_COMPRESSION_ASTC); + features.insert(wgt::Features::TEXTURE_COMPRESSION_ASTC_3D); } if context .glow_context diff --git a/wgpu-hal/src/metal/adapter.rs b/wgpu-hal/src/metal/adapter.rs index 19719b7a96..2d606cfe8d 100644 --- a/wgpu-hal/src/metal/adapter.rs +++ b/wgpu-hal/src/metal/adapter.rs @@ -664,6 +664,8 @@ impl super::PrivateCapabilities { || Self::supports_any(device, ASTC_PIXEL_FORMAT_FEATURES), // A13(Apple6) M1(Apple7) and later always support HDR ASTC pixel formats format_astc_hdr: family_check && device.supports_family(MTLGPUFamily::Apple6), + // Apple3 and later supports compressed volume texture formats including ASTC Sliced 3D + format_astc_3d: family_check && device.supports_family(MTLGPUFamily::Apple3), format_any8_unorm_srgb_all: Self::supports_any(device, ANY8_UNORM_SRGB_ALL), format_any8_unorm_srgb_no_write: !Self::supports_any(device, ANY8_UNORM_SRGB_ALL) && !os_is_mac, @@ -937,6 +939,7 @@ impl super::PrivateCapabilities { ); features.set(F::TEXTURE_COMPRESSION_ASTC, self.format_astc); features.set(F::TEXTURE_COMPRESSION_ASTC_HDR, self.format_astc_hdr); + features.set(F::TEXTURE_COMPRESSION_ASTC_SLICED_3D, self.format_astc_3d); features.set(F::TEXTURE_COMPRESSION_BC, self.format_bc); features.set(F::TEXTURE_COMPRESSION_BC_SLICED_3D, self.format_bc); // BC guarantees Sliced 3D features.set(F::TEXTURE_COMPRESSION_ETC2, self.format_eac_etc); diff --git a/wgpu-hal/src/metal/mod.rs b/wgpu-hal/src/metal/mod.rs index 08581736ec..17d3477a22 100644 --- a/wgpu-hal/src/metal/mod.rs +++ b/wgpu-hal/src/metal/mod.rs @@ -230,6 +230,7 @@ struct PrivateCapabilities { format_eac_etc: bool, format_astc: bool, format_astc_hdr: bool, + format_astc_3d: bool, format_any8_unorm_srgb_all: bool, format_any8_unorm_srgb_no_write: bool, format_any8_snorm_all: bool, diff --git a/wgpu-hal/src/vulkan/adapter.rs b/wgpu-hal/src/vulkan/adapter.rs index 38a5b80a57..64a08eae66 100644 --- a/wgpu-hal/src/vulkan/adapter.rs +++ b/wgpu-hal/src/vulkan/adapter.rs @@ -715,6 +715,13 @@ impl PhysicalDeviceFeatures { ); } + if self.core.texture_compression_astc_ldr != 0 { + features.set( + F::TEXTURE_COMPRESSION_ASTC_SLICED_3D, + supports_astc_3d(instance, phd), + ); + } + if let Some((ref f16_i8, ref bit16)) = self.shader_float16 { features.set( F::SHADER_F16, @@ -2599,6 +2606,60 @@ fn supports_format( } } +fn supports_astc_3d(instance: &ash::Instance, phd: vk::PhysicalDevice) -> bool { + let mut supports = true; + + let astc_formats = [ + vk::Format::ASTC_4X4_UNORM_BLOCK, + vk::Format::ASTC_4X4_SRGB_BLOCK, + vk::Format::ASTC_5X4_UNORM_BLOCK, + vk::Format::ASTC_5X4_SRGB_BLOCK, + vk::Format::ASTC_5X5_UNORM_BLOCK, + vk::Format::ASTC_5X5_SRGB_BLOCK, + vk::Format::ASTC_6X5_UNORM_BLOCK, + vk::Format::ASTC_6X5_SRGB_BLOCK, + vk::Format::ASTC_6X6_UNORM_BLOCK, + vk::Format::ASTC_6X6_SRGB_BLOCK, + vk::Format::ASTC_8X5_UNORM_BLOCK, + vk::Format::ASTC_8X5_SRGB_BLOCK, + vk::Format::ASTC_8X6_UNORM_BLOCK, + vk::Format::ASTC_8X6_SRGB_BLOCK, + vk::Format::ASTC_8X8_UNORM_BLOCK, + vk::Format::ASTC_8X8_SRGB_BLOCK, + vk::Format::ASTC_10X5_UNORM_BLOCK, + vk::Format::ASTC_10X5_SRGB_BLOCK, + vk::Format::ASTC_10X6_UNORM_BLOCK, + vk::Format::ASTC_10X6_SRGB_BLOCK, + vk::Format::ASTC_10X8_UNORM_BLOCK, + vk::Format::ASTC_10X8_SRGB_BLOCK, + vk::Format::ASTC_10X10_UNORM_BLOCK, + vk::Format::ASTC_10X10_SRGB_BLOCK, + vk::Format::ASTC_12X10_UNORM_BLOCK, + vk::Format::ASTC_12X10_SRGB_BLOCK, + vk::Format::ASTC_12X12_UNORM_BLOCK, + vk::Format::ASTC_12X12_SRGB_BLOCK, + ]; + + for &format in &astc_formats { + let result = unsafe { + instance.get_physical_device_image_format_properties( + phd, + format, + vk::ImageType::TYPE_3D, + vk::ImageTiling::OPTIMAL, + vk::ImageUsageFlags::SAMPLED, + vk::ImageCreateFlags::empty(), + ) + }; + if result.is_err() { + supports = false; + break; + } + } + + supports +} + fn supports_bgra8unorm_storage( instance: &ash::Instance, phd: vk::PhysicalDevice, diff --git a/wgpu-types/src/features.rs b/wgpu-types/src/features.rs index a3bd0498e1..e1ea159a2d 100644 --- a/wgpu-types/src/features.rs +++ b/wgpu-types/src/features.rs @@ -37,25 +37,28 @@ mod webgpu_impl { pub const WEBGPU_FEATURE_TEXTURE_COMPRESSION_ASTC: u64 = 1 << 5; #[doc(hidden)] - pub const WEBGPU_FEATURE_TIMESTAMP_QUERY: u64 = 1 << 6; + pub const WEBGPU_FEATURE_TEXTURE_COMPRESSION_ASTC_SLICED_3D: u64 = 1 << 6; #[doc(hidden)] - pub const WEBGPU_FEATURE_INDIRECT_FIRST_INSTANCE: u64 = 1 << 7; + pub const WEBGPU_FEATURE_TIMESTAMP_QUERY: u64 = 1 << 7; #[doc(hidden)] - pub const WEBGPU_FEATURE_SHADER_F16: u64 = 1 << 8; + pub const WEBGPU_FEATURE_INDIRECT_FIRST_INSTANCE: u64 = 1 << 8; #[doc(hidden)] - pub const WEBGPU_FEATURE_RG11B10UFLOAT_RENDERABLE: u64 = 1 << 9; + pub const WEBGPU_FEATURE_SHADER_F16: u64 = 1 << 9; #[doc(hidden)] - pub const WEBGPU_FEATURE_BGRA8UNORM_STORAGE: u64 = 1 << 10; + pub const WEBGPU_FEATURE_RG11B10UFLOAT_RENDERABLE: u64 = 1 << 10; #[doc(hidden)] - pub const WEBGPU_FEATURE_FLOAT32_FILTERABLE: u64 = 1 << 11; + pub const WEBGPU_FEATURE_BGRA8UNORM_STORAGE: u64 = 1 << 11; #[doc(hidden)] - pub const WEBGPU_FEATURE_DUAL_SOURCE_BLENDING: u64 = 1 << 12; + pub const WEBGPU_FEATURE_FLOAT32_FILTERABLE: u64 = 1 << 12; + + #[doc(hidden)] + pub const WEBGPU_FEATURE_DUAL_SOURCE_BLENDING: u64 = 1 << 13; } macro_rules! bitflags_array_impl { @@ -1301,6 +1304,19 @@ bitflags_array! { /// This is a web and native feature. const TEXTURE_COMPRESSION_ASTC = WEBGPU_FEATURE_TEXTURE_COMPRESSION_ASTC; + + /// Allows the 3d dimension for textures with ASTC compressed formats. + /// + /// This feature must be used in combination with TEXTURE_COMPRESSION_ASTC to enable 3D textures with ASTC compression. + /// It does not enable the ASTC formats by itself. + /// + /// Supported Platforms: + /// - Desktop (some) + /// - Mobile (some) + /// + /// This is a web and native feature. + const TEXTURE_COMPRESSION_ASTC_SLICED_3D = WEBGPU_FEATURE_TEXTURE_COMPRESSION_ASTC_SLICED_3D; + /// Enables use of Timestamp Queries. These queries tell the current gpu timestamp when /// all work before the query is finished. /// diff --git a/wgpu-types/src/lib.rs b/wgpu-types/src/lib.rs index 77b0774346..7d317d3e70 100644 --- a/wgpu-types/src/lib.rs +++ b/wgpu-types/src/lib.rs @@ -2720,6 +2720,13 @@ impl TextureFormat { self.required_features() == Features::TEXTURE_COMPRESSION_BC } + /// Returns `true` for ASTC compressed formats. + #[must_use] + pub fn is_astc(&self) -> bool { + self.required_features() == Features::TEXTURE_COMPRESSION_ASTC + || self.required_features() == Features::TEXTURE_COMPRESSION_ASTC_HDR + } + /// Returns the required features (if any) in order to use the texture. #[must_use] pub fn required_features(&self) -> Features { diff --git a/wgpu/src/backend/webgpu.rs b/wgpu/src/backend/webgpu.rs index 28891170e6..ba0d6967ce 100644 --- a/wgpu/src/backend/webgpu.rs +++ b/wgpu/src/backend/webgpu.rs @@ -733,6 +733,10 @@ const FEATURES_MAPPING: [(wgt::Features, webgpu_sys::GpuFeatureName); 13] = [ wgt::Features::TEXTURE_COMPRESSION_ASTC, webgpu_sys::GpuFeatureName::TextureCompressionAstc, ), + ( + wgt::Features::TEXTURE_COMPRESSION_ASTC_SLICED_3D, + webgpu_sys::GpuFeatureName::TextureCompressionAstcSliced3d, + ), ( wgt::Features::TIMESTAMP_QUERY, webgpu_sys::GpuFeatureName::TimestampQuery, From 4c697aa1a6aef6ae5d23f63bb5085b87362f0d0b Mon Sep 17 00:00:00 2001 From: Mehmet Oguz Derin Date: Sat, 19 Apr 2025 03:19:47 +0300 Subject: [PATCH 2/8] Changelog --- CHANGELOG.md | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 944af45653..5e666acb97 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -44,7 +44,7 @@ Bottom level categories: #### Naga -### Bux Fixes +### Bug Fixes #### Naga @@ -63,6 +63,7 @@ Naga now infers the correct binding layout when a resource appears only in an as #### General +- Add support for the astc-slice-3d feature. By @mehmetoguzderin in [#7577](https://github.com/gfx-rs/wgpu/issues/7577) - Removed `MaintainBase` in favor of using `PollType`. By @waywardmonkeys in [#7508](https://github.com/gfx-rs/wgpu/pull/7508). #### Naga From ab7afd9baad57c10d1b3923deceb1c331853bb33 Mon Sep 17 00:00:00 2001 From: Mehmet Oguz Derin Date: Sat, 19 Apr 2025 03:26:46 +0300 Subject: [PATCH 3/8] Cover in `deno_webgpu` --- deno_webgpu/webidl.rs | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/deno_webgpu/webidl.rs b/deno_webgpu/webidl.rs index 679f445de2..dcc58aaff5 100644 --- a/deno_webgpu/webidl.rs +++ b/deno_webgpu/webidl.rs @@ -453,6 +453,7 @@ pub fn feature_names_to_features(names: Vec) -> wgpu_types::Feat GPUFeatureName::TextureCompressionBcSliced3d => Features::TEXTURE_COMPRESSION_BC_SLICED_3D, GPUFeatureName::TextureCompressionEtc2 => Features::TEXTURE_COMPRESSION_ETC2, GPUFeatureName::TextureCompressionAstc => Features::TEXTURE_COMPRESSION_ASTC, + GPUFeatureName::TextureCompressionAstcSliced3d => Features::TEXTURE_COMPRESSION_ASTC_SLICED_3D, GPUFeatureName::Rg11b10ufloatRenderable => Features::RG11B10UFLOAT_RENDERABLE, GPUFeatureName::Bgra8unormStorage => Features::BGRA8UNORM_STORAGE, GPUFeatureName::Float32Filterable => Features::FLOAT32_FILTERABLE, @@ -531,6 +532,9 @@ pub fn features_to_feature_names(features: wgpu_types::Features) -> HashSet Date: Sat, 19 Apr 2025 03:27:50 +0300 Subject: [PATCH 4/8] Match length for WASM --- wgpu/src/backend/webgpu.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/wgpu/src/backend/webgpu.rs b/wgpu/src/backend/webgpu.rs index ba0d6967ce..cd2fc1007e 100644 --- a/wgpu/src/backend/webgpu.rs +++ b/wgpu/src/backend/webgpu.rs @@ -708,7 +708,7 @@ fn map_map_mode(mode: crate::MapMode) -> u32 { } } -const FEATURES_MAPPING: [(wgt::Features, webgpu_sys::GpuFeatureName); 13] = [ +const FEATURES_MAPPING: [(wgt::Features, webgpu_sys::GpuFeatureName); 14] = [ ( wgt::Features::DEPTH_CLIP_CONTROL, webgpu_sys::GpuFeatureName::DepthClipControl, From 2ad3a26415078fa2c7ab115291416f51966d9965 Mon Sep 17 00:00:00 2001 From: Mehmet Oguz Derin Date: Sat, 19 Apr 2025 03:30:56 +0300 Subject: [PATCH 5/8] Fix spelling of enum --- wgpu-hal/src/gles/adapter.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/wgpu-hal/src/gles/adapter.rs b/wgpu-hal/src/gles/adapter.rs index 1325f5c786..d6e20b8d4c 100644 --- a/wgpu-hal/src/gles/adapter.rs +++ b/wgpu-hal/src/gles/adapter.rs @@ -531,7 +531,7 @@ impl super::Adapter { .compressed_texture_astc_supports_ldr_profile() { features.insert(wgt::Features::TEXTURE_COMPRESSION_ASTC); - features.insert(wgt::Features::TEXTURE_COMPRESSION_ASTC_3D); + features.insert(wgt::Features::TEXTURE_COMPRESSION_ASTC_SLICED_3D); } if context .glow_context From dc52d75238d7f996eb8d3aa8f42f28997652cae0 Mon Sep 17 00:00:00 2001 From: Mehmet Oguz Derin Date: Sun, 27 Apr 2025 22:49:32 +0300 Subject: [PATCH 6/8] Update wgpu-types/src/features.rs Co-authored-by: Andreas Reich --- wgpu-types/src/features.rs | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/wgpu-types/src/features.rs b/wgpu-types/src/features.rs index e1ea159a2d..3d10b75a6b 100644 --- a/wgpu-types/src/features.rs +++ b/wgpu-types/src/features.rs @@ -1311,8 +1311,12 @@ bitflags_array! { /// It does not enable the ASTC formats by itself. /// /// Supported Platforms: - /// - Desktop (some) - /// - Mobile (some) + /// - Vulkan (some) + /// - Metal on Apple3+ + /// - OpenGL/WebGL (some) + /// + /// Not Supported: + /// - DX12 /// /// This is a web and native feature. const TEXTURE_COMPRESSION_ASTC_SLICED_3D = WEBGPU_FEATURE_TEXTURE_COMPRESSION_ASTC_SLICED_3D; From 63798c5e698ce7b7a6d885bd44653f2a7e1c2347 Mon Sep 17 00:00:00 2001 From: Mehmet Oguz Derin Date: Sun, 27 Apr 2025 23:04:35 +0300 Subject: [PATCH 7/8] Adjust support for ASTC sliced 3D --- wgpu-hal/src/gles/adapter.rs | 5 +++++ wgpu-types/src/features.rs | 3 +++ 2 files changed, 8 insertions(+) diff --git a/wgpu-hal/src/gles/adapter.rs b/wgpu-hal/src/gles/adapter.rs index d6e20b8d4c..34052cc66a 100644 --- a/wgpu-hal/src/gles/adapter.rs +++ b/wgpu-hal/src/gles/adapter.rs @@ -544,6 +544,7 @@ impl super::Adapter { #[cfg(any(native, Emscripten))] { features.insert(wgt::Features::TEXTURE_COMPRESSION_ASTC); + features.insert(wgt::Features::TEXTURE_COMPRESSION_ASTC_SLICED_3D); features.insert(wgt::Features::TEXTURE_COMPRESSION_ASTC_HDR); } } else { @@ -551,6 +552,10 @@ impl super::Adapter { wgt::Features::TEXTURE_COMPRESSION_ASTC, extensions.contains("GL_KHR_texture_compression_astc_ldr"), ); + features.set( + wgt::Features::TEXTURE_COMPRESSION_ASTC_SLICED_3D, + extensions.contains("GL_KHR_texture_compression_astc_sliced_3d"), + ); features.set( wgt::Features::TEXTURE_COMPRESSION_ASTC_HDR, extensions.contains("GL_KHR_texture_compression_astc_hdr"), diff --git a/wgpu-types/src/features.rs b/wgpu-types/src/features.rs index 3d10b75a6b..e99e77f809 100644 --- a/wgpu-types/src/features.rs +++ b/wgpu-types/src/features.rs @@ -1297,6 +1297,9 @@ bitflags_array! { /// Support for this feature guarantees availability of [`TextureUsages::COPY_SRC | TextureUsages::COPY_DST | TextureUsages::TEXTURE_BINDING`] for ASTC formats with Unorm/UnormSrgb channel type. /// [`Features::TEXTURE_ADAPTER_SPECIFIC_FORMAT_FEATURES`] may enable additional usages. /// + /// This feature does not guarantee availability of sliced 3d textures for ASTC formats. + /// If available, 3d support can be enabled by TEXTURE_COMPRESSION_ASTC_SLICED_3D feature. + /// /// Supported Platforms: /// - Vulkan on Intel /// - Mobile (some) From f8ae95ab40a7381a6f108fedf5505acea0110520 Mon Sep 17 00:00:00 2001 From: Mehmet Oguz Derin Date: Mon, 28 Apr 2025 10:18:35 +0300 Subject: [PATCH 8/8] Update ASTC sliced 3D feature check to require both base and sliced extensions --- wgpu-hal/src/gles/adapter.rs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/wgpu-hal/src/gles/adapter.rs b/wgpu-hal/src/gles/adapter.rs index 34052cc66a..7332ecd2b9 100644 --- a/wgpu-hal/src/gles/adapter.rs +++ b/wgpu-hal/src/gles/adapter.rs @@ -554,7 +554,8 @@ impl super::Adapter { ); features.set( wgt::Features::TEXTURE_COMPRESSION_ASTC_SLICED_3D, - extensions.contains("GL_KHR_texture_compression_astc_sliced_3d"), + extensions.contains("GL_KHR_texture_compression_astc_ldr") + && extensions.contains("GL_KHR_texture_compression_astc_sliced_3d"), ); features.set( wgt::Features::TEXTURE_COMPRESSION_ASTC_HDR,