mirror of
https://github.com/gfx-rs/wgpu.git
synced 2025-12-08 21:26:17 +00:00
Completely computerize wgpu-info ascii art (#3546)
This commit is contained in:
parent
6ee0d4c14d
commit
9d6a7a9fe5
1
Cargo.lock
generated
1
Cargo.lock
generated
@ -3112,6 +3112,7 @@ name = "wgpu-info"
|
||||
version = "0.15.0"
|
||||
dependencies = [
|
||||
"env_logger",
|
||||
"num-traits 0.2.15",
|
||||
"wgpu",
|
||||
]
|
||||
|
||||
|
||||
@ -65,6 +65,7 @@ libloading = "0.7"
|
||||
libc = "0.2"
|
||||
log = "0.4"
|
||||
nanorand = { version = "0.7", default-features = false }
|
||||
num-traits = { version = "0.2" }
|
||||
# Opt out of noise's "default-features" to avoid "image" feature as a dependency count optimization.
|
||||
# This will not be required in the next release since it has been removed from the default feature in https://github.com/Razaekel/noise-rs/commit/1af9e1522236b2c584fb9a02150c9c67a5e6bb04#diff-2e9d962a08321605940b5a657135052fbcef87b5e360662bb527c96d9a615542
|
||||
noise = { version = "0.7", default-features = false }
|
||||
|
||||
@ -12,4 +12,5 @@ publish = false
|
||||
|
||||
[dependencies]
|
||||
env_logger.workspace = true
|
||||
num-traits.workspace = true
|
||||
wgpu.workspace = true
|
||||
|
||||
@ -1,11 +1,14 @@
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
mod inner {
|
||||
use std::{
|
||||
fmt::Debug,
|
||||
mem::size_of,
|
||||
process::{exit, Command},
|
||||
time::Instant,
|
||||
};
|
||||
|
||||
use num_traits::FromPrimitive;
|
||||
|
||||
// Lets keep these on one line
|
||||
#[rustfmt::skip]
|
||||
const TEXTURE_FORMAT_LIST: [wgpu::TextureFormat; 114] = [
|
||||
@ -133,6 +136,10 @@ mod inner {
|
||||
let features = adapter.features();
|
||||
let limits = adapter.limits();
|
||||
|
||||
//////////////////
|
||||
// Adapter Info //
|
||||
//////////////////
|
||||
|
||||
println!("Adapter {idx}:");
|
||||
println!("\t Backend: {:?}", info.backend);
|
||||
println!("\t Name: {:?}", info.name);
|
||||
@ -142,15 +149,20 @@ mod inner {
|
||||
println!("\t Driver: {:?}", info.driver);
|
||||
println!("\tDriverInfo: {:?}", info.driver_info);
|
||||
println!("\t Compliant: {:?}", downlevel.is_webgpu_compliant());
|
||||
|
||||
//////////////
|
||||
// Features //
|
||||
//////////////
|
||||
|
||||
println!("\tFeatures:");
|
||||
for i in 0..(size_of::<wgpu::Features>() * 8) {
|
||||
let bit = wgpu::Features::from_bits(1 << i as u64);
|
||||
if let Some(bit) = bit {
|
||||
if wgpu::Features::all().contains(bit) {
|
||||
println!("\t\t{:>63} {}", format!("{bit:?}:"), features.contains(bit));
|
||||
}
|
||||
}
|
||||
}
|
||||
let max_feature_flag_width = wgpu::Features::max_debug_print_width();
|
||||
wgpu::Features::for_valid_bits(|bit, _i| {
|
||||
println!("\t\t{:>width$}: {}", format!("{bit:?}"), features.contains(bit), width = max_feature_flag_width);
|
||||
});
|
||||
|
||||
////////////
|
||||
// Limits //
|
||||
////////////
|
||||
|
||||
println!("\tLimits:");
|
||||
let wgpu::Limits {
|
||||
@ -214,6 +226,10 @@ mod inner {
|
||||
println!("\t\t Max Compute Workgroup Size Z: {max_compute_workgroup_size_z}");
|
||||
println!("\t\t Max Compute Workgroups Per Dimension: {max_compute_workgroups_per_dimension}");
|
||||
|
||||
//////////////////////////
|
||||
// Downlevel Properties //
|
||||
//////////////////////////
|
||||
|
||||
println!("\tDownlevel Properties:");
|
||||
let wgpu::DownlevelCapabilities {
|
||||
shader_model,
|
||||
@ -221,60 +237,69 @@ mod inner {
|
||||
flags,
|
||||
} = downlevel;
|
||||
println!("\t\t Shader Model: {shader_model:?}");
|
||||
for i in 0..(size_of::<wgpu::DownlevelFlags>() * 8) {
|
||||
let bit = wgpu::DownlevelFlags::from_bits(1 << i as u64);
|
||||
if let Some(bit) = bit {
|
||||
if wgpu::DownlevelFlags::all().contains(bit) {
|
||||
println!("\t\t{:>37} {}", format!("{bit:?}:"), flags.contains(bit));
|
||||
}
|
||||
}
|
||||
}
|
||||
let max_downlevel_flag_width = wgpu::DownlevelFlags::max_debug_print_width();
|
||||
wgpu::DownlevelFlags::for_valid_bits(|bit, _i| {
|
||||
println!("\t\t{:>width$}: {}", format!("{bit:?}"), flags.contains(bit), width = max_downlevel_flag_width);
|
||||
});
|
||||
|
||||
println!("\tTexture Format Features: ┌──────────┬──────────┬──────────Allowed┬Usages───────────┬───────────────────┐ ┌────────────┬────────────────┬────────────────┬─────────Feature┬Flags────────────┬─────────────────────┬────────────────────┬───────────┐");
|
||||
////////////////////
|
||||
// Texture Usages //
|
||||
////////////////////
|
||||
|
||||
let max_format_name_size = max_texture_format_name_size();
|
||||
let texture_format_whitespace = " ".repeat(max_format_name_size);
|
||||
|
||||
println!("\n\t Texture Format Allowed Usages:");
|
||||
|
||||
print!("\t\t {texture_format_whitespace}");
|
||||
wgpu::TextureUsages::println_table_header();
|
||||
for format in TEXTURE_FORMAT_LIST {
|
||||
let features = adapter.get_texture_format_features(format);
|
||||
let format_name = match format {
|
||||
wgpu::TextureFormat::Astc { block, channel } => {
|
||||
format!("Astc{block:?}{channel:?}:")
|
||||
let format_name = texture_format_name(format);
|
||||
print!("\t\t{format_name:>0$}", max_format_name_size);
|
||||
wgpu::TextureUsages::for_valid_bits(|bit, _i| {
|
||||
print!(" │ ");
|
||||
if features.allowed_usages.contains(bit) {
|
||||
print!("{bit:?}");
|
||||
}
|
||||
_ => {
|
||||
format!("{format:?}:")
|
||||
else {
|
||||
let length = format!("{bit:?}").len();
|
||||
print!("{}", " ".repeat(length))
|
||||
}
|
||||
};
|
||||
print!("\t\t{format_name:>21}");
|
||||
for i in 0..(size_of::<wgpu::TextureUsages>() * 8) {
|
||||
let bit = wgpu::TextureUsages::from_bits(1 << i as u32);
|
||||
if let Some(bit) = bit {
|
||||
print!(" │ ");
|
||||
if features.allowed_usages.contains(bit) {
|
||||
print!("{bit:?}");
|
||||
}
|
||||
else {
|
||||
let length = format!("{bit:?}").len();
|
||||
print!("{}", " ".repeat(length))
|
||||
}
|
||||
}
|
||||
}
|
||||
print!(" │ │ ");
|
||||
for i in 0..(size_of::<wgpu::TextureFormatFeatureFlags>() * 8) {
|
||||
let bit = wgpu::TextureFormatFeatureFlags::from_bits(1 << i as u32);
|
||||
if let Some(bit) = bit {
|
||||
if i != 0 {
|
||||
print!(" │ ")
|
||||
}
|
||||
if features.flags.contains(bit) {
|
||||
print!("{bit:?}");
|
||||
}
|
||||
else {
|
||||
let length = format!("{bit:?}").len();
|
||||
print!("{}", " ".repeat(length))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
});
|
||||
println!(" │");
|
||||
}
|
||||
println!("\t └──────────┴──────────┴─────────────────┴─────────────────┴───────────────────┘ └────────────┴────────────────┴────────────────┴────────────────┴─────────────────┴─────────────────────┴────────────────────┴───────────┘");
|
||||
print!("\t\t {texture_format_whitespace}");
|
||||
wgpu::TextureUsages::println_table_footer();
|
||||
|
||||
//////////////////////////
|
||||
// Texture Format Flags //
|
||||
//////////////////////////
|
||||
|
||||
println!("\n\t Texture Format Flags:");
|
||||
|
||||
print!("\t\t {texture_format_whitespace}");
|
||||
wgpu::TextureFormatFeatureFlags::println_table_header();
|
||||
|
||||
for format in TEXTURE_FORMAT_LIST {
|
||||
let features = adapter.get_texture_format_features(format);
|
||||
let format_name = texture_format_name(format);
|
||||
|
||||
print!("\t\t{format_name:>0$}", max_format_name_size);
|
||||
wgpu::TextureFormatFeatureFlags::for_valid_bits(|bit, _i| {
|
||||
print!(" │ ");
|
||||
if features.flags.contains(bit) {
|
||||
print!("{bit:?}");
|
||||
}
|
||||
else {
|
||||
let length = format!("{bit:?}").len();
|
||||
print!("{}", " ".repeat(length))
|
||||
}
|
||||
});
|
||||
println!(" │");
|
||||
}
|
||||
print!("\t\t ");
|
||||
wgpu::TextureFormatFeatureFlags::println_table_footer();
|
||||
}
|
||||
|
||||
pub fn main() {
|
||||
@ -341,6 +366,103 @@ mod inner {
|
||||
println!("=========== {adapter_count} adapters PASSED in {all_time:.3}s ===========");
|
||||
}
|
||||
}
|
||||
|
||||
trait Bitflags: Sized + Debug {
|
||||
type Underlying: FromPrimitive;
|
||||
|
||||
fn from_bits(bits: Self::Underlying) -> Option<Self>;
|
||||
|
||||
fn for_valid_bits(mut func: impl FnMut(Self, usize)) {
|
||||
for i in 0..(size_of::<Self>() * 8) {
|
||||
let bit = Self::from_bits(
|
||||
<Self::Underlying as FromPrimitive>::from_u64(1 << i as u64).unwrap(),
|
||||
);
|
||||
if let Some(bit) = bit {
|
||||
func(bit, i)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn max_debug_print_width() -> usize {
|
||||
let mut width = 0;
|
||||
Self::for_valid_bits(|bit, _i| {
|
||||
width = width.max(format!("{bit:?}").len());
|
||||
});
|
||||
width
|
||||
}
|
||||
|
||||
fn println_table_header() {
|
||||
print!("┌─");
|
||||
Self::for_valid_bits(|bit, i| {
|
||||
if i != 0 {
|
||||
print!("─┬─");
|
||||
}
|
||||
let length = format!("{bit:?}").len();
|
||||
print!("{}", "─".repeat(length));
|
||||
});
|
||||
println!("─┐");
|
||||
}
|
||||
|
||||
fn println_table_footer() {
|
||||
print!("└─");
|
||||
Self::for_valid_bits(|bit, i| {
|
||||
if i != 0 {
|
||||
print!("─┴─");
|
||||
}
|
||||
let length = format!("{bit:?}").len();
|
||||
print!("{}", "─".repeat(length));
|
||||
});
|
||||
println!("─┘")
|
||||
}
|
||||
}
|
||||
|
||||
impl Bitflags for wgpu::DownlevelFlags {
|
||||
type Underlying = u32;
|
||||
|
||||
fn from_bits(bits: u32) -> Option<Self> {
|
||||
Self::from_bits(bits)
|
||||
}
|
||||
}
|
||||
impl Bitflags for wgpu::Features {
|
||||
type Underlying = u64;
|
||||
|
||||
fn from_bits(bits: u64) -> Option<Self> {
|
||||
Self::from_bits(bits)
|
||||
}
|
||||
}
|
||||
impl Bitflags for wgpu::TextureUsages {
|
||||
type Underlying = u32;
|
||||
|
||||
fn from_bits(bits: u32) -> Option<Self> {
|
||||
Self::from_bits(bits)
|
||||
}
|
||||
}
|
||||
impl Bitflags for wgpu::TextureFormatFeatureFlags {
|
||||
type Underlying = u32;
|
||||
|
||||
fn from_bits(bits: u32) -> Option<Self> {
|
||||
Self::from_bits(bits)
|
||||
}
|
||||
}
|
||||
|
||||
fn max_texture_format_name_size() -> usize {
|
||||
TEXTURE_FORMAT_LIST
|
||||
.into_iter()
|
||||
.map(|f| texture_format_name(f).len())
|
||||
.max()
|
||||
.unwrap()
|
||||
}
|
||||
|
||||
fn texture_format_name(format: wgpu::TextureFormat) -> String {
|
||||
match format {
|
||||
wgpu::TextureFormat::Astc { block, channel } => {
|
||||
format!("Astc{block:?}{channel:?}:")
|
||||
}
|
||||
_ => {
|
||||
format!("{format:?}:")
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn main() {
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user