Ensure we pick the right gpu card in the example backend (#6557)

This commit is contained in:
Arjo Chakravarty 2024-12-12 17:50:45 +08:00 committed by GitHub
parent 28a3e97dde
commit ef996e6139
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
2 changed files with 113 additions and 31 deletions

View File

@ -279,37 +279,14 @@ impl ExampleContext {
gles_minor_version,
});
surface.pre_adapter(&instance, window);
let adapter = wgpu::util::initialize_adapter_from_env_or_default(&instance, surface.get())
.await
.expect("No suitable GPU adapters found on the system!");
let adapter_info = adapter.get_info();
log::info!("Using {} ({:?})", adapter_info.name, adapter_info.backend);
let optional_features = E::optional_features();
let required_features = E::required_features();
let adapter_features = adapter.features();
assert!(
adapter_features.contains(required_features),
"Adapter does not support required features for this example: {:?}",
required_features - adapter_features
);
let required_downlevel_capabilities = E::required_downlevel_capabilities();
let downlevel_capabilities = adapter.get_downlevel_capabilities();
assert!(
downlevel_capabilities.shader_model >= required_downlevel_capabilities.shader_model,
"Adapter does not support the minimum shader model required to run this example: {:?}",
required_downlevel_capabilities.shader_model
);
assert!(
downlevel_capabilities
.flags
.contains(required_downlevel_capabilities.flags),
"Adapter does not support the downlevel capabilities required to run this example: {:?}",
required_downlevel_capabilities.flags - downlevel_capabilities.flags
);
let adapter = get_adapter_with_capabilities_or_from_env(
&instance,
&E::required_features(),
&E::required_downlevel_capabilities(),
&surface.get(),
)
.await;
// Make sure we use the texture resolution limits from the adapter, so we can support images the size of the surface.
let needed_limits = E::required_limits().using_resolution(adapter.limits());
@ -318,7 +295,8 @@ impl ExampleContext {
.request_device(
&wgpu::DeviceDescriptor {
label: None,
required_features: (optional_features & adapter_features) | required_features,
required_features: (E::optional_features() & adapter.features())
| E::required_features(),
required_limits: needed_limits,
memory_hints: wgpu::MemoryHints::MemoryUsage,
},
@ -514,6 +492,8 @@ pub fn parse_url_query_string<'a>(query: &'a str, search_key: &str) -> Option<&'
#[cfg(test)]
pub use wgpu_test::image::ComparisonType;
use crate::utils::get_adapter_with_capabilities_or_from_env;
#[cfg(test)]
#[derive(Clone)]
pub struct ExampleTestParams<E> {

View File

@ -156,3 +156,105 @@ fn create_output_image_element(document: &web_sys::Document) -> web_sys::HtmlIma
log::info!("Created new output target image: {:?}", &new_image);
new_image
}
#[cfg(not(target_arch = "wasm32"))]
/// If the environment variable `WGPU_ADAPTER_NAME` is set, this function will attempt to
/// initialize the adapter with that name. If it is not set, it will attempt to initialize
/// the adapter which supports the required features.
pub(crate) async fn get_adapter_with_capabilities_or_from_env(
instance: &wgpu::Instance,
required_features: &wgpu::Features,
required_downlevel_capabilities: &wgpu::DownlevelCapabilities,
surface: &Option<&wgpu::Surface<'_>>,
) -> wgpu::Adapter {
use wgpu::Backends;
if std::env::var("WGPU_ADAPTER_NAME").is_ok() {
let adapter = wgpu::util::initialize_adapter_from_env_or_default(instance, *surface)
.await
.expect("No suitable GPU adapters found on the system!");
let adapter_info = adapter.get_info();
log::info!("Using {} ({:?})", adapter_info.name, adapter_info.backend);
let adapter_features = adapter.features();
assert!(
adapter_features.contains(*required_features),
"Adapter does not support required features for this example: {:?}",
*required_features - adapter_features
);
let downlevel_capabilities = adapter.get_downlevel_capabilities();
assert!(
downlevel_capabilities.shader_model >= required_downlevel_capabilities.shader_model,
"Adapter does not support the minimum shader model required to run this example: {:?}",
required_downlevel_capabilities.shader_model
);
assert!(
downlevel_capabilities
.flags
.contains(required_downlevel_capabilities.flags),
"Adapter does not support the downlevel capabilities required to run this example: {:?}",
required_downlevel_capabilities.flags - downlevel_capabilities.flags
);
adapter
} else {
let adapters = instance.enumerate_adapters(Backends::all());
let mut chosen_adapter = None;
for adapter in adapters {
if let Some(surface) = surface {
if !adapter.is_surface_supported(surface) {
continue;
}
}
let required_features = *required_features;
let adapter_features = adapter.features();
if !adapter_features.contains(required_features) {
continue;
} else {
chosen_adapter = Some(adapter);
break;
}
}
chosen_adapter.expect("No suitable GPU adapters found on the system!")
}
}
#[cfg(target_arch = "wasm32")]
pub(crate) async fn get_adapter_with_capabilities_or_from_env(
instance: &wgpu::Instance,
required_features: &wgpu::Features,
required_downlevel_capabilities: &wgpu::DownlevelCapabilities,
surface: &Option<&wgpu::Surface<'_>>,
) -> wgpu::Adapter {
let adapter = wgpu::util::initialize_adapter_from_env_or_default(instance, *surface)
.await
.expect("No suitable GPU adapters found on the system!");
let adapter_info = adapter.get_info();
log::info!("Using {} ({:?})", adapter_info.name, adapter_info.backend);
let adapter_features = adapter.features();
assert!(
adapter_features.contains(*required_features),
"Adapter does not support required features for this example: {:?}",
*required_features - adapter_features
);
let downlevel_capabilities = adapter.get_downlevel_capabilities();
assert!(
downlevel_capabilities.shader_model >= required_downlevel_capabilities.shader_model,
"Adapter does not support the minimum shader model required to run this example: {:?}",
required_downlevel_capabilities.shader_model
);
assert!(
downlevel_capabilities
.flags
.contains(required_downlevel_capabilities.flags),
"Adapter does not support the downlevel capabilities required to run this example: {:?}",
required_downlevel_capabilities.flags - downlevel_capabilities.flags
);
adapter
}