Remove DX11 backend (#4828)

This commit is contained in:
Valaphee The Meerkat 2023-12-06 21:12:46 +01:00 committed by GitHub
parent 12869e36fe
commit a1fafe394f
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
30 changed files with 28 additions and 1297 deletions

View File

@ -31,7 +31,6 @@ Bottom level categories:
- DX12
- Vulkan
- Metal
- DX11
- GLES
- WebGPU
- Emscripten
@ -40,6 +39,10 @@ Bottom level categories:
## Unreleased
### Direct3D 11 backend removal
This backend had no functionality, and with the recent support for GL on Desktop, which allows wgpu to run on older devices, there is no need to keep the backend.
### `WGPU_ALLOW_UNDERLYING_NONCOMPLIANT_ADAPTER` environment variable
This adds a way to allow a Vulkan driver which is non-compliant per VK_KHR_driver_properties to be enumerated. This is intended for testing new Vulkan drivers which are not Vulkan compliant yet.

View File

@ -79,7 +79,6 @@ We have a [wiki](https://github.com/gfx-rs/wgpu/wiki) that serves as a knowledge
| Vulkan | :white_check_mark: | :white_check_mark: | :volcano: | |
| Metal | | | :white_check_mark: | |
| DX12 | :white_check_mark: | | | |
| DX11 | :hammer_and_wrench: | | | |
| OpenGL | :ok: (GL 3.3+) | :ok: (GL ES 3.0+) | :triangular_ruler: | :ok: (WebGL2) |
| WebGPU | | | | :white_check_mark: |
@ -138,7 +137,7 @@ determined by the value of `MINIMUM_RUST_VERSION` in
All testing and example infrastructure share the same set of environment variables that determine which Backend/GPU it will run on.
- `WGPU_ADAPTER_NAME` with a substring of the name of the adapter you want to use (ex. `1080` will match `NVIDIA GeForce 1080ti`).
- `WGPU_BACKEND` with a comma-separated list of the backends you want to use (`vulkan`, `metal`, `dx12`, `dx11`, or `gl`).
- `WGPU_BACKEND` with a comma-separated list of the backends you want to use (`vulkan`, `metal`, `dx12`, or `gl`).
- `WGPU_POWER_PREF` with the power preference to choose when a specific adapter name isn't specified (`high`, `low` or `none`)
- `WGPU_DX12_COMPILER` with the DX12 shader compiler you wish to use (`dxc` or `fxc`, note that `dxc` requires `dxil.dll` and `dxcompiler.dll` to be in the working directory otherwise it will fall back to `fxc`)
- `WGPU_GLES_MINOR_VERSION` with the minor OpenGL ES 3 version number to request (`0`, `1`, `2` or `automatic`).

View File

@ -34,10 +34,10 @@ features = ["trace", "replay", "serde", "strict_asserts", "wgsl", "gles"]
workspace = true
features = ["metal"]
# We want the wgpu-core Direct3D backends on Windows.
# We want the wgpu-core Direct3D backend on Windows.
[target.'cfg(windows)'.dependencies.wgpu-core]
workspace = true
features = ["dx11", "dx12"]
features = ["dx12"]
[target.'cfg(windows)'.dependencies.wgpu-hal]
version = "0.18.0"

View File

@ -33,8 +33,6 @@ mod macros {
wgpu_types::Backend::Metal => $global.$method::<wgpu_core::api::Metal>( $($param),* ),
#[cfg(all(not(target_arch = "wasm32"), windows))]
wgpu_types::Backend::Dx12 => $global.$method::<wgpu_core::api::Dx12>( $($param),* ),
#[cfg(all(not(target_arch = "wasm32"), windows))]
wgpu_types::Backend::Dx11 => $global.$method::<wgpu_core::api::Dx11>( $($param),* ),
#[cfg(any(
all(unix, not(target_os = "macos"), not(target_os = "ios")),
feature = "angle",

Binary file not shown.

Before

Width:  |  Height:  |  Size: 126 KiB

After

Width:  |  Height:  |  Size: 146 KiB

File diff suppressed because one or more lines are too long

View File

@ -33,7 +33,7 @@ features = ["replay"]
[target.'cfg(not(target_arch = "wasm32"))'.dependencies.wgc]
workspace = true
features = ["replay", "raw-window-handle", "strict_asserts", "wgsl", "metal", "dx11", "dx12", "vulkan", "gles"]
features = ["replay", "raw-window-handle", "strict_asserts", "wgsl", "metal", "dx12", "vulkan", "gles"]
[dev-dependencies]
serde.workspace = true

View File

@ -10,4 +10,4 @@ play <trace-dir>
When built with "winit" feature, it's able to replay the workloads that operate on a swapchain. It renders each frame sequentially and then waits for the user to close the window. When built without "winit", it launches in console mode and can replay any trace that doesn't use swapchains.
Note: replaying is currently restricted to the same backend as one used for recording a trace. It is straightforward, however, to just replace the backend in RON since it's serialized as plain text. Valid values are: Vulkan, Metal, Dx12, and Dx11.
Note: replaying is currently restricted to the same backend as one used for recording a trace. It is straightforward, however, to just replace the backend in RON since it's serialized as plain text. Valid values are: Vulkan, Metal, and Dx12.

View File

@ -68,7 +68,6 @@ impl Test<'_> {
wgt::Backend::Vulkan => "Vulkan",
wgt::Backend::Metal => "Metal",
wgt::Backend::Dx12 => "Dx12",
wgt::Backend::Dx11 => "Dx11",
wgt::Backend::Gl => "Gl",
_ => unreachable!(),
};
@ -170,7 +169,6 @@ const BACKENDS: &[wgt::Backend] = &[
wgt::Backend::Vulkan,
wgt::Backend::Metal,
wgt::Backend::Dx12,
wgt::Backend::Dx11,
wgt::Backend::Gl,
];

View File

@ -11,7 +11,7 @@
/// ```
/// # use wgpu_test::*;
/// FailureCase {
/// backends: Some(wgpu::Backends::DX11 | wgpu::Backends::DX12),
/// backends: Some(wgpu::Backends::DX12),
/// vendor: None,
/// adapter: Some("RTX"),
/// driver: None,

View File

@ -38,7 +38,6 @@ resource_log_info = []
metal = ["hal/metal"]
vulkan = ["hal/vulkan"]
gles = ["hal/gles"]
dx11 = ["hal/dx11"]
dx12 = ["hal/dx12"]
# Use static linking for libraries. Disale to manually link. Enabled by default.

View File

@ -35,10 +35,6 @@ impl AnySurface {
if self.downcast_ref::<hal::api::Dx12>().is_some() {
return Backend::Dx12;
}
#[cfg(all(feature = "dx11", windows))]
if self.downcast_ref::<hal::api::Dx11>().is_some() {
return Backend::Dx11;
}
#[cfg(feature = "gles")]
if self.downcast_ref::<hal::api::Gles>().is_some() {
return Backend::Gl;

View File

@ -2178,11 +2178,6 @@ impl<G: GlobalIdentityHandlerFactory> Global<G> {
all_queue_empty =
self.poll_device::<hal::api::Dx12>(force_wait, &mut closures)? && all_queue_empty;
}
#[cfg(all(feature = "dx11", windows))]
{
all_queue_empty =
self.poll_device::<hal::api::Dx11>(force_wait, &mut closures)? && all_queue_empty;
}
#[cfg(feature = "gles")]
{
all_queue_empty =

View File

@ -22,8 +22,6 @@ pub struct GlobalReport {
pub metal: Option<HubReport>,
#[cfg(all(feature = "dx12", windows))]
pub dx12: Option<HubReport>,
#[cfg(all(feature = "dx11", windows))]
pub dx11: Option<HubReport>,
#[cfg(feature = "gles")]
pub gl: Option<HubReport>,
}
@ -40,8 +38,6 @@ impl GlobalReport {
Backend::Metal => self.metal.as_ref().unwrap(),
#[cfg(all(feature = "dx12", windows))]
Backend::Dx12 => self.dx12.as_ref().unwrap(),
#[cfg(all(feature = "dx11", windows))]
Backend::Dx11 => self.dx11.as_ref().unwrap(),
#[cfg(feature = "gles")]
Backend::Gl => self.gl.as_ref().unwrap(),
_ => panic!("HubReport is not supported on this backend"),
@ -132,12 +128,6 @@ impl<G: GlobalIdentityHandlerFactory> Global<G> {
} else {
None
},
#[cfg(all(feature = "dx11", windows))]
dx11: if self.instance.dx11.is_some() {
Some(self.hubs.dx11.generate_report())
} else {
None
},
#[cfg(feature = "gles")]
gl: if self.instance.gl.is_some() {
Some(self.hubs.gl.generate_report())
@ -167,10 +157,6 @@ impl<G: GlobalIdentityHandlerFactory> Drop for Global<G> {
{
self.hubs.dx12.clear(&surfaces_locked, true);
}
#[cfg(all(feature = "dx11", windows))]
{
self.hubs.dx11.clear(&surfaces_locked, true);
}
#[cfg(feature = "gles")]
{
self.hubs.gl.clear(&surfaces_locked, true);

View File

@ -94,27 +94,6 @@ impl HalApi for hal::api::Dx12 {
}
}
#[cfg(all(feature = "dx11", windows))]
impl HalApi for hal::api::Dx11 {
const VARIANT: Backend = Backend::Dx11;
fn create_instance_from_hal(name: &str, hal_instance: Self::Instance) -> Instance {
Instance {
name: name.to_owned(),
dx11: Some(hal_instance),
..Default::default()
}
}
fn instance_as_hal(instance: &Instance) -> Option<&Self::Instance> {
instance.dx11.as_ref()
}
fn hub<G: GlobalIdentityHandlerFactory>(global: &Global<G>) -> &Hub<Self> {
&global.hubs.dx11
}
fn get_surface(surface: &Surface) -> Option<&HalSurface<Self>> {
surface.raw.downcast_ref()
}
}
#[cfg(feature = "gles")]
impl HalApi for hal::api::Gles {
const VARIANT: Backend = Backend::Gl;

View File

@ -308,15 +308,12 @@ pub struct Hubs {
pub(crate) metal: Hub<hal::api::Metal>,
#[cfg(all(feature = "dx12", windows))]
pub(crate) dx12: Hub<hal::api::Dx12>,
#[cfg(all(feature = "dx11", windows))]
pub(crate) dx11: Hub<hal::api::Dx11>,
#[cfg(feature = "gles")]
pub(crate) gl: Hub<hal::api::Gles>,
#[cfg(all(
not(all(feature = "vulkan", not(target_arch = "wasm32"))),
not(all(feature = "metal", any(target_os = "macos", target_os = "ios"))),
not(all(feature = "dx12", windows)),
not(all(feature = "dx11", windows)),
not(feature = "gles"),
))]
pub(crate) empty: Hub<hal::api::Empty>,
@ -331,15 +328,12 @@ impl Hubs {
metal: Hub::new(factory),
#[cfg(all(feature = "dx12", windows))]
dx12: Hub::new(factory),
#[cfg(all(feature = "dx11", windows))]
dx11: Hub::new(factory),
#[cfg(feature = "gles")]
gl: Hub::new(factory),
#[cfg(all(
not(all(feature = "vulkan", not(target_arch = "wasm32"))),
not(all(feature = "metal", any(target_os = "macos", target_os = "ios"))),
not(all(feature = "dx12", windows)),
not(all(feature = "dx11", windows)),
not(feature = "gles"),
))]
empty: Hub::new(factory),

View File

@ -131,8 +131,7 @@ where
1 => Backend::Vulkan,
2 => Backend::Metal,
3 => Backend::Dx12,
4 => Backend::Dx11,
5 => Backend::Gl,
4 => Backend::Gl,
_ => unreachable!(),
}
}
@ -156,13 +155,12 @@ where
fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
let (index, epoch, backend) = self.unzip();
let backend = match backend {
Backend::Empty => "_",
Backend::Vulkan => "vk",
Backend::Metal => "mtl",
Backend::Dx12 => "d3d12",
Backend::Dx11 => "d3d11",
Backend::Gl => "gl",
Backend::BrowserWebGpu => "webgpu",
Backend::Empty => "_",
};
write!(formatter, "Id({index},{epoch},{backend})")?;
Ok(())
@ -280,7 +278,6 @@ fn test_id_backend() {
Backend::Vulkan,
Backend::Metal,
Backend::Dx12,
Backend::Dx11,
Backend::Gl,
] {
let id: Id<()> = Id::zip(1, 0, b);
@ -300,7 +297,6 @@ fn test_id() {
Backend::Vulkan,
Backend::Metal,
Backend::Dx12,
Backend::Dx11,
Backend::Gl,
];
for &i in &indexes {

View File

@ -68,8 +68,6 @@ pub struct Instance {
pub metal: Option<HalInstance<hal::api::Metal>>,
#[cfg(all(feature = "dx12", windows))]
pub dx12: Option<HalInstance<hal::api::Dx12>>,
#[cfg(all(feature = "dx11", windows))]
pub dx11: Option<HalInstance<hal::api::Dx11>>,
#[cfg(feature = "gles")]
pub gl: Option<HalInstance<hal::api::Gles>>,
pub flags: wgt::InstanceFlags,
@ -113,8 +111,6 @@ impl Instance {
metal: init(hal::api::Metal, &instance_desc),
#[cfg(all(feature = "dx12", windows))]
dx12: init(hal::api::Dx12, &instance_desc),
#[cfg(all(feature = "dx11", windows))]
dx11: init(hal::api::Dx11, &instance_desc),
#[cfg(feature = "gles")]
gl: init(hal::api::Gles, &instance_desc),
flags: instance_desc.flags,
@ -144,8 +140,6 @@ impl Instance {
Backend::Metal => destroy(hal::api::Metal, &self.metal, surface.raw),
#[cfg(all(feature = "dx12", windows))]
Backend::Dx12 => destroy(hal::api::Dx12, &self.dx12, surface.raw),
#[cfg(all(feature = "dx11", windows))]
Backend::Dx11 => destroy(hal::api::Dx11, &self.dx11, surface.raw),
#[cfg(feature = "gles")]
Backend::Gl => destroy(hal::api::Gles, &self.gl, surface.raw),
_ => unreachable!(),
@ -531,13 +525,6 @@ impl<G: GlobalIdentityHandlerFactory> Global<G> {
display_handle,
window_handle,
);
#[cfg(all(feature = "dx11", windows))]
init::<hal::api::Dx11>(
&mut hal_surface,
&self.instance.dx11,
display_handle,
window_handle,
);
#[cfg(feature = "gles")]
init::<hal::api::Gles>(
&mut hal_surface,
@ -787,8 +774,6 @@ impl<G: GlobalIdentityHandlerFactory> Global<G> {
unconfigure::<_, hal::api::Metal>(self, &surface.raw, &present);
#[cfg(all(feature = "dx12", windows))]
unconfigure::<_, hal::api::Dx12>(self, &surface.raw, &present);
#[cfg(all(feature = "dx11", windows))]
unconfigure::<_, hal::api::Dx11>(self, &surface.raw, &present);
#[cfg(feature = "gles")]
unconfigure::<_, hal::api::Gles>(self, &surface.raw, &present);
}
@ -849,8 +834,6 @@ impl<G: GlobalIdentityHandlerFactory> Global<G> {
);
#[cfg(all(feature = "dx12", windows))]
self.enumerate(hal::api::Dx12, &self.instance.dx12, &inputs, &mut adapters);
#[cfg(all(feature = "dx11", windows))]
self.enumerate(hal::api::Dx11, &self.instance.dx11, &inputs, &mut adapters);
#[cfg(feature = "gles")]
self.enumerate(hal::api::Gles, &self.instance.gl, &inputs, &mut adapters);
@ -960,15 +943,6 @@ impl<G: GlobalIdentityHandlerFactory> Global<G> {
desc.force_fallback_adapter,
&mut device_types,
);
#[cfg(all(feature = "dx11", windows))]
let (id_dx11, adapters_dx11) = gather(
hal::api::Dx11,
self.instance.dx11.as_ref(),
&inputs,
compatible_surface,
desc.force_fallback_adapter,
&mut device_types,
);
#[cfg(feature = "gles")]
let (id_gl, adapters_gl) = gather(
hal::api::Gles,
@ -1042,10 +1016,6 @@ impl<G: GlobalIdentityHandlerFactory> Global<G> {
if let Some(id) = self.select(&mut selected, id_dx12, adapters_dx12) {
return Ok(id);
}
#[cfg(all(feature = "dx11", windows))]
if let Some(id) = self.select(&mut selected, id_dx11, adapters_dx11) {
return Ok(id);
}
#[cfg(feature = "gles")]
if let Some(id) = self.select(&mut selected, id_gl, adapters_gl) {
return Ok(id);
@ -1076,8 +1046,6 @@ impl<G: GlobalIdentityHandlerFactory> Global<G> {
Backend::Metal => fid.assign(Adapter::new(hal_adapter)),
#[cfg(all(feature = "dx12", windows))]
Backend::Dx12 => fid.assign(Adapter::new(hal_adapter)),
#[cfg(all(feature = "dx11", windows))]
Backend::Dx11 => fid.assign(Adapter::new(hal_adapter)),
#[cfg(feature = "gles")]
Backend::Gl => fid.assign(Adapter::new(hal_adapter)),
_ => unreachable!(),
@ -1283,7 +1251,6 @@ impl<G: GlobalIdentityHandlerFactory> Global<G> {
/// Names:
/// - vulkan = "vulkan" or "vk"
/// - dx12 = "dx12" or "d3d12"
/// - dx11 = "dx11" or "d3d11"
/// - metal = "metal" or "mtl"
/// - gles = "opengl" or "gles" or "gl"
/// - webgpu = "webgpu"
@ -1293,7 +1260,6 @@ pub fn parse_backends_from_comma_list(string: &str) -> Backends {
backends |= match backend.trim() {
"vulkan" | "vk" => Backends::VULKAN,
"dx12" | "d3d12" => Backends::DX12,
"dx11" | "d3d11" => Backends::DX11,
"metal" | "mtl" => Backends::METAL,
"opengl" | "gles" | "gl" => Backends::GL,
"webgpu" => Backends::BROWSER_WEBGPU,

View File

@ -9,7 +9,6 @@
not(all(feature = "vulkan", not(target_arch = "wasm32"))),
not(all(feature = "metal", any(target_os = "macos", target_os = "ios"))),
not(all(feature = "dx12", windows)),
not(all(feature = "dx11", windows)),
not(feature = "gles"),
),
allow(unused, clippy::let_and_return)
@ -217,7 +216,6 @@ macro_rules! define_backend_caller {
define_backend_caller! { gfx_if_vulkan, gfx_if_vulkan_hidden, "vulkan" if all(feature = "vulkan", not(target_arch = "wasm32")) }
define_backend_caller! { gfx_if_metal, gfx_if_metal_hidden, "metal" if all(feature = "metal", any(target_os = "macos", target_os = "ios")) }
define_backend_caller! { gfx_if_dx12, gfx_if_dx12_hidden, "dx12" if all(feature = "dx12", windows) }
define_backend_caller! { gfx_if_dx11, gfx_if_dx11_hidden, "dx11" if all(feature = "dx11", windows) }
define_backend_caller! { gfx_if_gles, gfx_if_gles_hidden, "gles" if feature = "gles" }
/// Dispatch on an [`Id`]'s backend to a backend-generic method.
@ -272,7 +270,6 @@ macro_rules! gfx_select {
wgt::Backend::Vulkan => $crate::gfx_if_vulkan!($global.$method::<$crate::api::Vulkan>( $($param),* )),
wgt::Backend::Metal => $crate::gfx_if_metal!($global.$method::<$crate::api::Metal>( $($param),* )),
wgt::Backend::Dx12 => $crate::gfx_if_dx12!($global.$method::<$crate::api::Dx12>( $($param),* )),
wgt::Backend::Dx11 => $crate::gfx_if_dx11!($global.$method::<$crate::api::Dx11>( $($param),* )),
wgt::Backend::Gl => $crate::gfx_if_gles!($global.$method::<$crate::api::Gles>( $($param),+ )),
other => panic!("Unexpected backend {:?}", other),
}

View File

@ -18,9 +18,9 @@ rust-version = "1.65"
[package.metadata.docs.rs]
# Ideally we would enable all the features.
#
# However the metal features fails to be documented because the docs.rs runner cross compiling under
# However, the metal features fail to be documented because the docs.rs runner cross-compiling under
# x86_64-unknown-linux-gnu and metal-rs cannot compile in that environment at the moment. The same applies
# with the dx11 and dx12 features.
# for the dx12 feature.
features = ["vulkan", "gles", "renderdoc"]
rustdoc-args = ["--cfg", "docsrs"]
targets = [
@ -44,17 +44,6 @@ vulkan = [
"smallvec",
]
gles = ["naga/glsl-out", "glow", "glutin_wgl_sys", "khronos-egl", "libloading"]
dx11 = [
"naga/hlsl-out",
"d3d12",
"libloading",
"winapi/d3d11",
"winapi/std",
"winapi/d3d11_1",
"winapi/d3d11_2",
"winapi/d3d11sdklayers",
"winapi/dxgi1_6",
]
dx12 = [
"naga/hlsl-out",
"d3d12",

View File

@ -1,4 +1,4 @@
#[cfg(all(any(feature = "dx11", feature = "dx12"), windows))]
#[cfg(all(feature = "dx12", windows))]
pub(super) mod dxgi;
#[cfg(all(not(target_arch = "wasm32"), feature = "renderdoc"))]

View File

@ -1,303 +0,0 @@
use std::num::NonZeroU64;
use winapi::um::{d3d11, d3dcommon};
impl crate::Adapter<super::Api> for super::Adapter {
unsafe fn open(
&self,
features: wgt::Features,
limits: &wgt::Limits,
) -> Result<crate::OpenDevice<super::Api>, crate::DeviceError> {
todo!()
}
unsafe fn texture_format_capabilities(
&self,
format: wgt::TextureFormat,
) -> crate::TextureFormatCapabilities {
todo!()
}
unsafe fn surface_capabilities(
&self,
surface: &super::Surface,
) -> Option<crate::SurfaceCapabilities> {
todo!()
}
unsafe fn get_presentation_timestamp(&self) -> wgt::PresentationTimestamp {
todo!()
}
}
impl super::Adapter {
pub(super) fn expose(
instance: &super::library::D3D11Lib,
adapter: d3d12::DxgiAdapter,
) -> Option<crate::ExposedAdapter<super::Api>> {
use d3dcommon::{
D3D_FEATURE_LEVEL_10_0 as FL10_0, D3D_FEATURE_LEVEL_10_1 as FL10_1,
D3D_FEATURE_LEVEL_11_0 as FL11_0, D3D_FEATURE_LEVEL_11_1 as FL11_1,
D3D_FEATURE_LEVEL_9_1 as FL9_1, D3D_FEATURE_LEVEL_9_2 as FL9_2,
D3D_FEATURE_LEVEL_9_3 as FL9_3,
};
let (device, feature_level) = instance.create_device(adapter)?;
//
// Query Features from d3d11
//
let d3d9_features = unsafe {
device.check_feature_support::<d3d11::D3D11_FEATURE_DATA_D3D9_OPTIONS1>(
d3d11::D3D11_FEATURE_D3D9_OPTIONS1,
)
};
let d3d10_features = unsafe {
device.check_feature_support::<d3d11::D3D11_FEATURE_DATA_D3D10_X_HARDWARE_OPTIONS>(
d3d11::D3D11_FEATURE_D3D10_X_HARDWARE_OPTIONS,
)
};
let d3d11_features = unsafe {
device.check_feature_support::<d3d11::D3D11_FEATURE_DATA_D3D11_OPTIONS>(
d3d11::D3D11_FEATURE_D3D11_OPTIONS,
)
};
let d3d11_features1 = unsafe {
device.check_feature_support::<d3d11::D3D11_FEATURE_DATA_D3D11_OPTIONS1>(
d3d11::D3D11_FEATURE_D3D11_OPTIONS1,
)
};
let d3d11_features2 = unsafe {
device.check_feature_support::<d3d11::D3D11_FEATURE_DATA_D3D11_OPTIONS2>(
d3d11::D3D11_FEATURE_D3D11_OPTIONS2,
)
};
let d3d11_features3 = unsafe {
device.check_feature_support::<d3d11::D3D11_FEATURE_DATA_D3D11_OPTIONS3>(
d3d11::D3D11_FEATURE_D3D11_OPTIONS3,
)
};
//
// Fill out features and downlevel features
//
// TODO(cwfitzgerald): Needed downlevel features: 3D dispatch
let mut features = wgt::Features::DEPTH_CLIP_CONTROL
| wgt::Features::PUSH_CONSTANTS
| wgt::Features::POLYGON_MODE_LINE
| wgt::Features::CLEAR_TEXTURE
| wgt::Features::TEXTURE_FORMAT_16BIT_NORM
| wgt::Features::ADDRESS_MODE_CLAMP_TO_ZERO
| wgt::Features::ADDRESS_MODE_CLAMP_TO_BORDER;
let mut downlevel = wgt::DownlevelFlags::BASE_VERTEX
| wgt::DownlevelFlags::READ_ONLY_DEPTH_STENCIL
| wgt::DownlevelFlags::UNRESTRICTED_INDEX_BUFFER
| wgt::DownlevelFlags::UNRESTRICTED_EXTERNAL_TEXTURE_COPIES;
// Features from queries
downlevel.set(
wgt::DownlevelFlags::NON_POWER_OF_TWO_MIPMAPPED_TEXTURES,
d3d9_features.FullNonPow2TextureSupported == 1,
);
downlevel.set(
wgt::DownlevelFlags::COMPUTE_SHADERS,
d3d10_features.ComputeShaders_Plus_RawAndStructuredBuffers_Via_Shader_4_x == 1,
);
// Features from feature level
if feature_level >= FL9_2 {
downlevel |= wgt::DownlevelFlags::INDEPENDENT_BLEND;
// formally FL9_1 supports aniso 2, but we don't support that level of distinction
downlevel |= wgt::DownlevelFlags::ANISOTROPIC_FILTERING;
// this is actually the first FL that supports u32 at all
downlevel |= wgt::DownlevelFlags::FULL_DRAW_INDEX_UINT32;
}
if feature_level >= FL9_3 {
downlevel |= wgt::DownlevelFlags::COMPARISON_SAMPLERS;
}
if feature_level >= FL10_0 {
downlevel |= wgt::DownlevelFlags::FRAGMENT_STORAGE;
downlevel |= wgt::DownlevelFlags::FRAGMENT_WRITABLE_STORAGE;
downlevel |= wgt::DownlevelFlags::DEPTH_BIAS_CLAMP;
downlevel |= wgt::DownlevelFlags::VERTEX_STORAGE;
features |= wgt::Features::DEPTH_CLIP_CONTROL;
features |= wgt::Features::TIMESTAMP_QUERY;
features |= wgt::Features::PIPELINE_STATISTICS_QUERY;
features |= wgt::Features::SHADER_PRIMITIVE_INDEX;
features |= wgt::Features::DEPTH32FLOAT_STENCIL8;
features |= wgt::Features::RG11B10UFLOAT_RENDERABLE;
}
if feature_level >= FL10_1 {
downlevel |= wgt::DownlevelFlags::CUBE_ARRAY_TEXTURES;
downlevel |= wgt::DownlevelFlags::MULTISAMPLED_SHADING;
}
if feature_level >= FL11_0 {
downlevel |= wgt::DownlevelFlags::INDIRECT_EXECUTION;
downlevel |= wgt::DownlevelFlags::WEBGPU_TEXTURE_FORMAT_SUPPORT;
features |= wgt::Features::TEXTURE_COMPRESSION_BC;
}
if feature_level >= FL11_1 {
features |= wgt::Features::VERTEX_WRITABLE_STORAGE;
}
// bgra8unorm-storage is never supported on dx11 according to:
// https://learn.microsoft.com/en-us/windows/win32/direct3ddxgi/format-support-for-direct3d-11-0-feature-level-hardware#dxgi_format_b8g8r8a8_unormfcs-87
// float32-filterable should always be available on dx11
// https://learn.microsoft.com/en-us/windows/win32/direct3ddxgi/format-support-for-direct3d-11-0-feature-level-hardware#dxgi_format_r32g32b32a32_floatfcs-2
features.set(wgt::Features::FLOAT32_FILTERABLE, true);
//
// Fill out limits and alignments
//
let max_texture_dimension_2d = match feature_level {
FL9_1 | FL9_2 => 2048,
FL9_3 => 4096,
FL10_0 | FL10_1 => 8192,
_ => d3d11::D3D11_REQ_TEXTURE2D_U_OR_V_DIMENSION,
};
let max_texture_dimension_3d = match feature_level {
FL9_1..=FL9_3 => 256,
_ => d3d11::D3D11_REQ_TEXTURE3D_U_V_OR_W_DIMENSION,
};
let max_vertex_buffers = match feature_level {
FL9_1..=FL9_3 => 16,
_ => 32,
}
.min(crate::MAX_VERTEX_BUFFERS as u32);
let max_compute_workgroup_storage_size = match feature_level {
FL9_1..=FL9_3 => 0,
FL10_0 | FL10_1 => 4096 * 4, // This doesn't have an equiv SM4 constant :\
_ => d3d11::D3D11_CS_TGSM_REGISTER_COUNT * 4,
};
let max_workgroup_size_xy = match feature_level {
FL9_1..=FL9_3 => 0,
FL10_0 | FL10_1 => d3d11::D3D11_CS_4_X_THREAD_GROUP_MAX_X,
_ => d3d11::D3D11_CS_THREAD_GROUP_MAX_X,
};
let max_workgroup_size_z = match feature_level {
FL9_1..=FL9_3 => 0,
FL10_0 | FL10_1 => 1,
_ => d3d11::D3D11_CS_THREAD_GROUP_MAX_Z,
};
// let max_workgroup_count_z = match feature_level {
// FL9_1..=FL9_3 => 0,
// FL10_0 | FL10_1 => 1,
// _ => d3d11::D3D11_CS_THREAD_GROUP_MAX_Z,
// };
let max_sampled_textures = d3d11::D3D11_COMMONSHADER_INPUT_RESOURCE_REGISTER_COUNT;
let max_samplers = d3d11::D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT;
let max_constant_buffers = d3d11::D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT - 1;
let max_uavs = if device.as_device1().is_some() {
d3d11::D3D11_1_UAV_SLOT_COUNT
} else {
d3d11::D3D11_PS_CS_UAV_REGISTER_COUNT
};
let max_output_registers = d3d11::D3D11_VS_OUTPUT_REGISTER_COMPONENTS;
let max_compute_invocations_per_workgroup =
d3d11::D3D11_CS_THREAD_GROUP_MAX_THREADS_PER_GROUP;
let max_compute_workgroups_per_dimension =
d3d11::D3D11_CS_DISPATCH_MAX_THREAD_GROUPS_PER_DIMENSION;
let limits = wgt::Limits {
max_texture_dimension_1d: max_texture_dimension_2d,
max_texture_dimension_2d,
max_texture_dimension_3d,
max_texture_array_layers: max_texture_dimension_3d,
max_bind_groups: u32::MAX,
max_bindings_per_bind_group: 65535,
max_dynamic_uniform_buffers_per_pipeline_layout: max_constant_buffers,
max_dynamic_storage_buffers_per_pipeline_layout: 0,
max_sampled_textures_per_shader_stage: max_sampled_textures,
max_samplers_per_shader_stage: max_samplers,
max_storage_buffers_per_shader_stage: max_uavs,
max_storage_textures_per_shader_stage: max_uavs,
max_uniform_buffers_per_shader_stage: max_constant_buffers,
max_uniform_buffer_binding_size: 1 << 16,
max_storage_buffer_binding_size: u32::MAX,
max_vertex_buffers,
max_vertex_attributes: max_vertex_buffers,
max_vertex_buffer_array_stride: u32::MAX,
max_push_constant_size: 1 << 16,
min_uniform_buffer_offset_alignment: 256,
min_storage_buffer_offset_alignment: 1,
max_inter_stage_shader_components: max_output_registers,
max_compute_workgroup_storage_size,
max_compute_invocations_per_workgroup,
max_compute_workgroup_size_x: max_workgroup_size_xy,
max_compute_workgroup_size_y: max_workgroup_size_xy,
max_compute_workgroup_size_z: max_workgroup_size_z,
max_compute_workgroups_per_dimension,
// D3D11_BUFFER_DESC represents the buffer size as a 32 bit int.
max_buffer_size: u32::MAX as u64,
max_non_sampler_bindings: u32::MAX,
};
//
// Other capabilities
//
let shader_model = match feature_level {
FL9_1..=FL9_3 => wgt::ShaderModel::Sm2,
FL10_0 | FL10_1 => wgt::ShaderModel::Sm4,
_ => wgt::ShaderModel::Sm5,
};
let device_info = wgt::AdapterInfo {
name: String::new(),
vendor: 0,
device: 0,
device_type: match d3d11_features2.UnifiedMemoryArchitecture {
0 => wgt::DeviceType::DiscreteGpu,
1 => wgt::DeviceType::IntegratedGpu,
_ => unreachable!(),
},
driver: String::new(),
driver_info: String::new(),
backend: wgt::Backend::Dx11,
};
//
// Build up the structs
//
let api_adapter = super::Adapter { device };
let alignments = crate::Alignments {
buffer_copy_offset: NonZeroU64::new(1).unwrap(), // todo
buffer_copy_pitch: NonZeroU64::new(1).unwrap(), // todo
};
let capabilities = crate::Capabilities {
limits,
alignments,
downlevel: wgt::DownlevelCapabilities {
flags: downlevel,
limits: wgt::DownlevelLimits {},
shader_model,
},
};
Some(crate::ExposedAdapter {
adapter: api_adapter,
info: device_info,
features,
capabilities,
})
}
}

View File

@ -1,271 +0,0 @@
impl crate::CommandEncoder<super::Api> for super::CommandEncoder {
unsafe fn begin_encoding(&mut self, label: crate::Label) -> Result<(), crate::DeviceError> {
todo!()
}
unsafe fn discard_encoding(&mut self) {
todo!()
}
unsafe fn end_encoding(&mut self) -> Result<super::CommandBuffer, crate::DeviceError> {
todo!()
}
unsafe fn reset_all<I>(&mut self, command_buffers: I)
where
I: Iterator<Item = super::CommandBuffer>,
{
todo!()
}
unsafe fn transition_buffers<'a, T>(&mut self, barriers: T)
where
T: Iterator<Item = crate::BufferBarrier<'a, super::Api>>,
{
todo!()
}
unsafe fn transition_textures<'a, T>(&mut self, barriers: T)
where
T: Iterator<Item = crate::TextureBarrier<'a, super::Api>>,
{
todo!()
}
unsafe fn clear_buffer(&mut self, buffer: &super::Buffer, range: crate::MemoryRange) {
todo!()
}
unsafe fn copy_buffer_to_buffer<T>(
&mut self,
src: &super::Buffer,
dst: &super::Buffer,
regions: T,
) where
T: Iterator<Item = crate::BufferCopy>,
{
todo!()
}
unsafe fn copy_texture_to_texture<T>(
&mut self,
src: &super::Texture,
src_usage: crate::TextureUses,
dst: &super::Texture,
regions: T,
) where
T: Iterator<Item = crate::TextureCopy>,
{
todo!()
}
unsafe fn copy_buffer_to_texture<T>(
&mut self,
src: &super::Buffer,
dst: &super::Texture,
regions: T,
) where
T: Iterator<Item = crate::BufferTextureCopy>,
{
todo!()
}
unsafe fn copy_texture_to_buffer<T>(
&mut self,
src: &super::Texture,
src_usage: crate::TextureUses,
dst: &super::Buffer,
regions: T,
) where
T: Iterator<Item = crate::BufferTextureCopy>,
{
todo!()
}
unsafe fn set_bind_group(
&mut self,
layout: &super::PipelineLayout,
index: u32,
group: &super::BindGroup,
dynamic_offsets: &[wgt::DynamicOffset],
) {
todo!()
}
unsafe fn set_push_constants(
&mut self,
layout: &super::PipelineLayout,
stages: wgt::ShaderStages,
offset_bytes: u32,
data: &[u32],
) {
todo!()
}
unsafe fn insert_debug_marker(&mut self, label: &str) {
todo!()
}
unsafe fn begin_debug_marker(&mut self, group_label: &str) {
todo!()
}
unsafe fn end_debug_marker(&mut self) {
todo!()
}
unsafe fn begin_query(&mut self, set: &super::QuerySet, index: u32) {
todo!()
}
unsafe fn end_query(&mut self, set: &super::QuerySet, index: u32) {
todo!()
}
unsafe fn write_timestamp(&mut self, set: &super::QuerySet, index: u32) {
todo!()
}
unsafe fn reset_queries(&mut self, set: &super::QuerySet, range: std::ops::Range<u32>) {
todo!()
}
unsafe fn copy_query_results(
&mut self,
set: &super::QuerySet,
range: std::ops::Range<u32>,
buffer: &super::Buffer,
offset: wgt::BufferAddress,
stride: wgt::BufferSize,
) {
todo!()
}
unsafe fn begin_render_pass(&mut self, desc: &crate::RenderPassDescriptor<super::Api>) {
todo!()
}
unsafe fn end_render_pass(&mut self) {
todo!()
}
unsafe fn set_render_pipeline(&mut self, pipeline: &super::RenderPipeline) {
todo!()
}
unsafe fn set_index_buffer<'a>(
&mut self,
binding: crate::BufferBinding<'a, super::Api>,
format: wgt::IndexFormat,
) {
todo!()
}
unsafe fn set_vertex_buffer<'a>(
&mut self,
index: u32,
binding: crate::BufferBinding<'a, super::Api>,
) {
todo!()
}
unsafe fn set_viewport(&mut self, rect: &crate::Rect<f32>, depth_range: std::ops::Range<f32>) {
todo!()
}
unsafe fn set_scissor_rect(&mut self, rect: &crate::Rect<u32>) {
todo!()
}
unsafe fn set_stencil_reference(&mut self, value: u32) {
todo!()
}
unsafe fn set_blend_constants(&mut self, color: &[f32; 4]) {
todo!()
}
unsafe fn draw(
&mut self,
first_vertex: u32,
vertex_count: u32,
first_instance: u32,
instance_count: u32,
) {
todo!()
}
unsafe fn draw_indexed(
&mut self,
first_index: u32,
index_count: u32,
base_vertex: i32,
first_instance: u32,
instance_count: u32,
) {
todo!()
}
unsafe fn draw_indirect(
&mut self,
buffer: &super::Buffer,
offset: wgt::BufferAddress,
draw_count: u32,
) {
todo!()
}
unsafe fn draw_indexed_indirect(
&mut self,
buffer: &super::Buffer,
offset: wgt::BufferAddress,
draw_count: u32,
) {
todo!()
}
unsafe fn draw_indirect_count(
&mut self,
buffer: &super::Buffer,
offset: wgt::BufferAddress,
count_buffer: &super::Buffer,
count_offset: wgt::BufferAddress,
max_count: u32,
) {
todo!()
}
unsafe fn draw_indexed_indirect_count(
&mut self,
buffer: &super::Buffer,
offset: wgt::BufferAddress,
count_buffer: &super::Buffer,
count_offset: wgt::BufferAddress,
max_count: u32,
) {
todo!()
}
unsafe fn begin_compute_pass<'a>(
&mut self,
desc: &crate::ComputePassDescriptor<'a, super::Api>,
) {
todo!()
}
unsafe fn end_compute_pass(&mut self) {
todo!()
}
unsafe fn set_compute_pipeline(&mut self, pipeline: &super::ComputePipeline) {
todo!()
}
unsafe fn dispatch(&mut self, count: [u32; 3]) {
todo!()
}
unsafe fn dispatch_indirect(&mut self, buffer: &super::Buffer, offset: wgt::BufferAddress) {
todo!()
}
}

View File

@ -1,242 +0,0 @@
use std::{ffi::c_void, mem};
use winapi::um::d3d11;
use crate::auxil::dxgi::result::HResult;
impl crate::Device<super::Api> for super::Device {
unsafe fn exit(self, queue: super::Queue) {
todo!()
}
unsafe fn create_buffer(
&self,
desc: &crate::BufferDescriptor,
) -> Result<super::Buffer, crate::DeviceError> {
todo!()
}
unsafe fn destroy_buffer(&self, buffer: super::Buffer) {
todo!()
}
unsafe fn map_buffer(
&self,
buffer: &super::Buffer,
range: crate::MemoryRange,
) -> Result<crate::BufferMapping, crate::DeviceError> {
todo!()
}
unsafe fn unmap_buffer(&self, buffer: &super::Buffer) -> Result<(), crate::DeviceError> {
todo!()
}
unsafe fn flush_mapped_ranges<I>(&self, buffer: &super::Buffer, ranges: I)
where
I: Iterator<Item = crate::MemoryRange>,
{
todo!()
}
unsafe fn invalidate_mapped_ranges<I>(&self, buffer: &super::Buffer, ranges: I)
where
I: Iterator<Item = crate::MemoryRange>,
{
todo!()
}
unsafe fn create_texture(
&self,
desc: &crate::TextureDescriptor,
) -> Result<super::Texture, crate::DeviceError> {
todo!()
}
unsafe fn destroy_texture(&self, texture: super::Texture) {
todo!()
}
unsafe fn create_texture_view(
&self,
texture: &super::Texture,
desc: &crate::TextureViewDescriptor,
) -> Result<super::TextureView, crate::DeviceError> {
todo!()
}
unsafe fn destroy_texture_view(&self, view: super::TextureView) {
todo!()
}
unsafe fn create_sampler(
&self,
desc: &crate::SamplerDescriptor,
) -> Result<super::Sampler, crate::DeviceError> {
todo!()
}
unsafe fn destroy_sampler(&self, sampler: super::Sampler) {
todo!()
}
unsafe fn create_command_encoder(
&self,
desc: &crate::CommandEncoderDescriptor<super::Api>,
) -> Result<super::CommandEncoder, crate::DeviceError> {
todo!()
}
unsafe fn destroy_command_encoder(&self, pool: super::CommandEncoder) {
todo!()
}
unsafe fn create_bind_group_layout(
&self,
desc: &crate::BindGroupLayoutDescriptor,
) -> Result<super::BindGroupLayout, crate::DeviceError> {
todo!()
}
unsafe fn destroy_bind_group_layout(&self, bg_layout: super::BindGroupLayout) {
todo!()
}
unsafe fn create_pipeline_layout(
&self,
desc: &crate::PipelineLayoutDescriptor<super::Api>,
) -> Result<super::PipelineLayout, crate::DeviceError> {
todo!()
}
unsafe fn destroy_pipeline_layout(&self, pipeline_layout: super::PipelineLayout) {
todo!()
}
unsafe fn create_bind_group(
&self,
desc: &crate::BindGroupDescriptor<super::Api>,
) -> Result<super::BindGroup, crate::DeviceError> {
todo!()
}
unsafe fn destroy_bind_group(&self, group: super::BindGroup) {
todo!()
}
unsafe fn create_shader_module(
&self,
desc: &crate::ShaderModuleDescriptor,
shader: crate::ShaderInput,
) -> Result<super::ShaderModule, crate::ShaderError> {
todo!()
}
unsafe fn destroy_shader_module(&self, module: super::ShaderModule) {
todo!()
}
unsafe fn create_render_pipeline(
&self,
desc: &crate::RenderPipelineDescriptor<super::Api>,
) -> Result<super::RenderPipeline, crate::PipelineError> {
todo!()
}
unsafe fn destroy_render_pipeline(&self, pipeline: super::RenderPipeline) {
todo!()
}
unsafe fn create_compute_pipeline(
&self,
desc: &crate::ComputePipelineDescriptor<super::Api>,
) -> Result<super::ComputePipeline, crate::PipelineError> {
todo!()
}
unsafe fn destroy_compute_pipeline(&self, pipeline: super::ComputePipeline) {
todo!()
}
unsafe fn create_query_set(
&self,
desc: &wgt::QuerySetDescriptor<crate::Label>,
) -> Result<super::QuerySet, crate::DeviceError> {
todo!()
}
unsafe fn destroy_query_set(&self, set: super::QuerySet) {
todo!()
}
unsafe fn create_fence(&self) -> Result<super::Fence, crate::DeviceError> {
todo!()
}
unsafe fn destroy_fence(&self, fence: super::Fence) {
todo!()
}
unsafe fn get_fence_value(
&self,
fence: &super::Fence,
) -> Result<crate::FenceValue, crate::DeviceError> {
todo!()
}
unsafe fn wait(
&self,
fence: &super::Fence,
value: crate::FenceValue,
timeout_ms: u32,
) -> Result<bool, crate::DeviceError> {
todo!()
}
unsafe fn start_capture(&self) -> bool {
todo!()
}
unsafe fn stop_capture(&self) {
todo!()
}
}
impl crate::Queue<super::Api> for super::Queue {
unsafe fn submit(
&self,
command_buffers: &[&super::CommandBuffer],
signal_fence: Option<(&mut super::Fence, crate::FenceValue)>,
) -> Result<(), crate::DeviceError> {
todo!()
}
unsafe fn present(
&self,
surface: &super::Surface,
texture: super::SurfaceTexture,
) -> Result<(), crate::SurfaceError> {
todo!()
}
unsafe fn get_timestamp_period(&self) -> f32 {
todo!()
}
}
impl super::D3D11Device {
#[allow(trivial_casts)] // come on
pub unsafe fn check_feature_support<T>(&self, feature: d3d11::D3D11_FEATURE) -> T {
unsafe {
let mut value = mem::zeroed::<T>();
let ret = self.CheckFeatureSupport(
feature,
&mut value as *mut T as *mut c_void,
mem::size_of::<T>() as u32,
);
assert_eq!(ret.into_result(), Ok(()));
value
}
}
}

View File

@ -1,53 +0,0 @@
use crate::auxil;
impl crate::Instance<super::Api> for super::Instance {
unsafe fn init(desc: &crate::InstanceDescriptor) -> Result<Self, crate::InstanceError> {
profiling::scope!("Init DX11 Backend");
let enable_dx11 = match std::env::var("WGPU_UNSTABLE_DX11_BACKEND") {
Ok(string) => string == "1" || string == "true",
Err(_) => false,
};
if !enable_dx11 {
return Err(crate::InstanceError::new(String::from(
"DX11 support is unstable; set WGPU_UNSTABLE_DX11_BACKEND=1 to enable anyway",
)));
}
let lib_d3d11 = super::library::D3D11Lib::new()
.ok_or_else(|| crate::InstanceError::new(String::from("failed to load d3d11.dll")))?;
let (lib_dxgi, factory) = auxil::dxgi::factory::create_factory(
auxil::dxgi::factory::DxgiFactoryType::Factory1,
desc.flags,
)?;
Ok(super::Instance {
lib_d3d11,
lib_dxgi,
factory,
})
}
unsafe fn create_surface(
&self,
display_handle: raw_window_handle::RawDisplayHandle,
window_handle: raw_window_handle::RawWindowHandle,
) -> Result<super::Surface, crate::InstanceError> {
todo!()
}
unsafe fn destroy_surface(&self, surface: super::Surface) {
todo!()
}
unsafe fn enumerate_adapters(&self) -> Vec<crate::ExposedAdapter<super::Api>> {
let adapters = auxil::dxgi::factory::enumerate_adapters(self.factory.clone());
adapters
.into_iter()
.filter_map(|adapter| super::Adapter::expose(&self.lib_d3d11, adapter))
.collect()
}
}

View File

@ -1,142 +0,0 @@
use std::ptr;
use winapi::{
shared::{
dxgi,
minwindef::{HMODULE, UINT},
winerror,
},
um::{d3d11, d3d11_1, d3d11_2, d3dcommon},
};
use crate::auxil::dxgi::result::HResult;
type D3D11CreateDeviceFun = unsafe extern "system" fn(
*mut dxgi::IDXGIAdapter,
d3dcommon::D3D_DRIVER_TYPE,
HMODULE,
UINT,
*const d3dcommon::D3D_FEATURE_LEVEL,
UINT,
UINT,
*mut *mut d3d11::ID3D11Device,
*mut d3dcommon::D3D_FEATURE_LEVEL,
*mut *mut d3d11::ID3D11DeviceContext,
) -> d3d12::HRESULT;
pub(super) struct D3D11Lib {
// We use the os specific symbol to drop the lifetime parameter.
//
// SAFETY: we must ensure this outlives the Library.
d3d11_create_device: libloading::os::windows::Symbol<D3D11CreateDeviceFun>,
lib: libloading::Library,
}
impl D3D11Lib {
pub fn new() -> Option<Self> {
unsafe {
let lib = libloading::Library::new("d3d11.dll").ok()?;
let d3d11_create_device = lib
.get::<D3D11CreateDeviceFun>(b"D3D11CreateDevice")
.ok()?
.into_raw();
Some(Self {
lib,
d3d11_create_device,
})
}
}
pub fn create_device(
&self,
adapter: d3d12::DxgiAdapter,
) -> Option<(super::D3D11Device, d3dcommon::D3D_FEATURE_LEVEL)> {
let feature_levels = [
d3dcommon::D3D_FEATURE_LEVEL_11_1,
d3dcommon::D3D_FEATURE_LEVEL_11_0,
d3dcommon::D3D_FEATURE_LEVEL_10_1,
d3dcommon::D3D_FEATURE_LEVEL_10_0,
d3dcommon::D3D_FEATURE_LEVEL_9_3,
d3dcommon::D3D_FEATURE_LEVEL_9_2,
d3dcommon::D3D_FEATURE_LEVEL_9_1,
];
let mut device = d3d12::ComPtr::<d3d11::ID3D11Device>::null();
let mut feature_level: d3dcommon::D3D_FEATURE_LEVEL = 0;
// We need to try this twice. If the first time fails due to E_INVALIDARG
// we are running on a machine without a D3D11.1 runtime, and need to
// retry without the feature level 11_1 feature level.
//
// Why they thought this was a good API, who knows.
let mut hr = unsafe {
(self.d3d11_create_device)(
adapter.as_mut_ptr() as *mut _,
d3dcommon::D3D_DRIVER_TYPE_UNKNOWN,
ptr::null_mut(), // software implementation DLL???
0, // flags
feature_levels.as_ptr(),
feature_levels.len() as u32,
d3d11::D3D11_SDK_VERSION,
device.mut_self(),
&mut feature_level,
ptr::null_mut(), // device context
)
};
// Try again without FL11_1
if hr == winerror::E_INVALIDARG {
hr = unsafe {
(self.d3d11_create_device)(
adapter.as_mut_ptr() as *mut _,
d3dcommon::D3D_DRIVER_TYPE_UNKNOWN,
ptr::null_mut(), // software implementation DLL???
0, // flags
feature_levels[1..].as_ptr(),
feature_levels[1..].len() as u32,
d3d11::D3D11_SDK_VERSION,
device.mut_self(),
&mut feature_level,
ptr::null_mut(), // device context
)
};
}
// Any errors here are real and we should complain about
if let Err(err) = hr.into_result() {
log::error!("Failed to make a D3D11 device: {}", err);
return None;
}
// We always try to upcast in highest -> lowest order
// Device -> Device2
unsafe {
match device.cast::<d3d11_2::ID3D11Device2>().into_result() {
Ok(device2) => {
return Some((super::D3D11Device::Device2(device2), feature_level));
}
Err(hr) => {
log::warn!("Failed to cast device to ID3D11Device2: {}", hr)
}
}
}
// Device -> Device1
unsafe {
match device.cast::<d3d11_1::ID3D11Device1>().into_result() {
Ok(device1) => {
return Some((super::D3D11Device::Device1(device1), feature_level));
}
Err(hr) => {
log::warn!("Failed to cast device to ID3D11Device1: {}", hr)
}
}
}
Some((super::D3D11Device::Device(device), feature_level))
}
}

View File

@ -1,139 +0,0 @@
#![allow(dead_code)]
#![allow(unused_variables)]
use winapi::um::{d3d11, d3d11_1, d3d11_2};
mod adapter;
mod command;
mod device;
mod instance;
mod library;
#[derive(Clone, Debug)]
pub struct Api;
impl crate::Api for Api {
type Instance = Instance;
type Surface = Surface;
type Adapter = Adapter;
type Device = Device;
type Queue = Queue;
type CommandEncoder = CommandEncoder;
type CommandBuffer = CommandBuffer;
type Buffer = Buffer;
type Texture = Texture;
type SurfaceTexture = SurfaceTexture;
type TextureView = TextureView;
type Sampler = Sampler;
type QuerySet = QuerySet;
type Fence = Fence;
type BindGroupLayout = BindGroupLayout;
type BindGroup = BindGroup;
type PipelineLayout = PipelineLayout;
type ShaderModule = ShaderModule;
type RenderPipeline = RenderPipeline;
type ComputePipeline = ComputePipeline;
}
pub struct Instance {
lib_d3d11: library::D3D11Lib,
lib_dxgi: d3d12::DxgiLib,
factory: d3d12::DxgiFactory,
}
unsafe impl Send for Instance {}
unsafe impl Sync for Instance {}
pub struct Surface {}
pub struct Adapter {
device: D3D11Device,
}
unsafe impl Send for Adapter {}
unsafe impl Sync for Adapter {}
d3d12::weak_com_inheritance_chain! {
#[derive(Debug, Clone, PartialEq)]
enum D3D11Device {
Device(d3d11::ID3D11Device), from_device, as_device, device;
Device1(d3d11_1::ID3D11Device1), from_device1, as_device1, unwrap_device1;
Device2(d3d11_2::ID3D11Device2), from_device2, as_device2, unwrap_device2;
}
}
pub struct Device {}
unsafe impl Send for Device {}
unsafe impl Sync for Device {}
pub struct Queue {}
#[derive(Debug)]
pub struct CommandEncoder {}
#[derive(Debug)]
pub struct CommandBuffer {}
#[derive(Debug)]
pub struct Buffer {}
#[derive(Debug)]
pub struct Texture {}
#[derive(Debug)]
pub struct SurfaceTexture {}
impl std::borrow::Borrow<Texture> for SurfaceTexture {
fn borrow(&self) -> &Texture {
todo!()
}
}
#[derive(Debug)]
pub struct TextureView {}
#[derive(Debug)]
pub struct Sampler {}
#[derive(Debug)]
pub struct QuerySet {}
#[derive(Debug)]
pub struct Fence {}
#[derive(Debug)]
pub struct BindGroupLayout {}
#[derive(Debug)]
pub struct BindGroup {}
#[derive(Debug)]
pub struct PipelineLayout {}
#[derive(Debug)]
pub struct ShaderModule {}
#[derive(Debug)]
pub struct RenderPipeline {}
#[derive(Debug)]
pub struct ComputePipeline {}
impl crate::Surface<Api> for Surface {
unsafe fn configure(
&self,
device: &Device,
config: &crate::SurfaceConfiguration,
) -> Result<(), crate::SurfaceError> {
todo!()
}
unsafe fn unconfigure(&self, device: &Device) {
todo!()
}
unsafe fn acquire_texture(
&self,
_timeout: Option<std::time::Duration>,
) -> Result<Option<crate::AcquiredSurfaceTexture<Api>>, crate::SurfaceError> {
todo!()
}
unsafe fn discard_texture(&self, texture: SurfaceTexture) {
todo!()
}
}

View File

@ -11,7 +11,7 @@
* General design direction is to follow the majority by the following weights:
* - wgpu-core: 1.5
* - primary backends (Vulkan/Metal/DX12): 1.0 each
* - secondary backends (DX11/GLES): 0.5 each
* - secondary backend (GLES): 0.5
*/
#![cfg_attr(docsrs, feature(doc_cfg, doc_auto_cfg))]
@ -51,9 +51,6 @@
clippy::pattern_type_mismatch,
)]
/// DirectX11 API internals.
#[cfg(all(feature = "dx11", windows))]
pub mod dx11;
/// DirectX12 API internals.
#[cfg(all(feature = "dx12", windows))]
pub mod dx12;
@ -71,8 +68,6 @@ pub mod vulkan;
pub mod auxil;
pub mod api {
#[cfg(all(feature = "dx11", windows))]
pub use super::dx11::Api as Dx11;
#[cfg(all(feature = "dx12", windows))]
pub use super::dx12::Api as Dx12;
pub use super::empty::Api as Empty;

View File

@ -102,12 +102,10 @@ pub enum Backend {
Metal = 2,
/// Direct3D-12 (Windows)
Dx12 = 3,
/// Direct3D-11 (Windows)
Dx11 = 4,
/// OpenGL ES-3 (Linux, Android)
Gl = 5,
Gl = 4,
/// WebGPU in the browser
BrowserWebGpu = 6,
BrowserWebGpu = 5,
}
impl Backend {
@ -118,7 +116,6 @@ impl Backend {
Backend::Vulkan => "vulkan",
Backend::Metal => "metal",
Backend::Dx12 => "dx12",
Backend::Dx11 => "dx11",
Backend::Gl => "gl",
Backend::BrowserWebGpu => "webgpu",
}
@ -158,8 +155,6 @@ bitflags::bitflags! {
const METAL = 1 << Backend::Metal as u32;
/// Supported on Windows 10
const DX12 = 1 << Backend::Dx12 as u32;
/// Supported on Windows 7+
const DX11 = 1 << Backend::Dx11 as u32;
/// Supported when targeting the web through webassembly
const BROWSER_WEBGPU = 1 << Backend::BrowserWebGpu as u32;
/// All the apis that wgpu offers first tier of support for.
@ -172,8 +167,8 @@ bitflags::bitflags! {
/// All the apis that wgpu offers second tier of support for. These may
/// be unsupported/still experimental.
///
/// OpenGL + DX11
const SECONDARY = Self::GL.bits() | Self::DX11.bits();
/// OpenGL
const SECONDARY = Self::GL.bits();
}
}
@ -665,7 +660,6 @@ bitflags::bitflags! {
/// - DX12
/// - Vulkan
/// - Metal
/// - DX11 (emulated with uniforms)
/// - OpenGL (emulated with uniforms)
///
/// This is a native only feature.
@ -681,7 +675,6 @@ bitflags::bitflags! {
/// - DX12
/// - Vulkan
/// - Metal
/// - DX11
/// - OpenGL
///
/// This is a native only feature.
@ -693,7 +686,6 @@ bitflags::bitflags! {
/// - DX12
/// - Vulkan
/// - Metal (macOS 10.12+ only)
/// - DX11
/// - OpenGL
///
/// This is a native only feature.
@ -820,7 +812,6 @@ bitflags::bitflags! {
///
/// Supported platforms:
/// - Vulkan
/// - DX11 (feature level 10+)
/// - DX12
/// - Metal (some)
/// - OpenGL (some)
@ -1076,7 +1067,7 @@ pub struct Limits {
/// - Vulkan: 128-256 bytes
/// - DX12: 256 bytes
/// - Metal: 4096 bytes
/// - DX11 & OpenGL don't natively support push constants, and are emulated with uniforms,
/// - OpenGL doesn't natively support push constants, and are emulated with uniforms,
/// so this number is less useful but likely 256.
pub max_push_constant_size: u32,
@ -1421,13 +1412,13 @@ bitflags::bitflags! {
pub struct DownlevelFlags: u32 {
/// The device supports compiling and using compute shaders.
///
/// DX11 on FL10 level hardware, WebGL2, and GLES3.0 devices do not support compute.
/// WebGL2, and GLES3.0 devices do not support compute.
const COMPUTE_SHADERS = 1 << 0;
/// Supports binding storage buffers and textures to fragment shaders.
const FRAGMENT_WRITABLE_STORAGE = 1 << 1;
/// Supports indirect drawing and dispatching.
///
/// DX11 on FL10 level hardware, WebGL2, GLES 3.0, and Metal on Apple1/Apple2 GPUs do not support indirect.
/// WebGL2, GLES 3.0, and Metal on Apple1/Apple2 GPUs do not support indirect.
const INDIRECT_EXECUTION = 1 << 2;
/// Supports non-zero `base_vertex` parameter to direct indexed draw calls.
///
@ -4932,7 +4923,7 @@ pub enum PresentMode {
///
/// No tearing will be observed.
///
/// Supported on DX11/12 on Windows 10, NVidia on Vulkan and Wayland on Vulkan.
/// Supported on DX12 on Windows 10, NVidia on Vulkan and Wayland on Vulkan.
///
/// This is traditionally called "Fast Vsync"
Mailbox = 5,

View File

@ -66,10 +66,10 @@ features = ["raw-window-handle"]
workspace = true
features = ["metal"]
# We want the wgpu-core Direct3D backends and OpenGL (via WGL) on Windows.
# We want the wgpu-core Direct3D backend and OpenGL (via WGL) on Windows.
[target.'cfg(windows)'.dependencies.wgc]
workspace = true
features = ["dx11", "dx12", "gles"]
features = ["dx12", "gles"]
# We want the wgpu-core Vulkan backend on Unix (but not emscripten, macOS, iOS) and Windows.
[target.'cfg(any(windows, all(unix, not(target_os = "emscripten"), not(target_os = "ios"), not(target_os = "macos"))))'.dependencies.wgc]