mirror of
https://github.com/servo/servo.git
synced 2025-08-06 06:00:15 +01:00
webgpu: Implement ShaderCompilationInfo (#32642)
* ShaderCompilationInfo * expectations * Handle CompilationInfo promise in GPUShaderModule * Fix my english
This commit is contained in:
parent
bd0a5eb4b7
commit
c0105de82b
9 changed files with 22103 additions and 682 deletions
|
@ -25,11 +25,54 @@ use wgc::pipeline::{ComputePipelineDescriptor, RenderPipelineDescriptor};
|
|||
use wgc::resource::{
|
||||
BufferDescriptor, SamplerDescriptor, TextureDescriptor, TextureViewDescriptor,
|
||||
};
|
||||
use wgpu_core::pipeline::CreateShaderModuleError;
|
||||
pub use {wgpu_core as wgc, wgpu_types as wgt};
|
||||
|
||||
use crate::identity::*;
|
||||
use crate::{Error, ErrorFilter, PopError, WebGPU, PRESENTATION_BUFFER_COUNT};
|
||||
|
||||
#[derive(Clone, Debug, Default, Deserialize, Serialize)]
|
||||
pub struct ShaderCompilationInfo {
|
||||
pub line_number: u64,
|
||||
pub line_pos: u64,
|
||||
pub offset: u64,
|
||||
pub length: u64,
|
||||
pub message: String,
|
||||
}
|
||||
|
||||
impl ShaderCompilationInfo {
|
||||
pub fn from(error: &CreateShaderModuleError, source: &str) -> Self {
|
||||
let location = match error {
|
||||
CreateShaderModuleError::Parsing(e) => e.inner.location(source),
|
||||
CreateShaderModuleError::Validation(e) => e.inner.location(source),
|
||||
_ => None,
|
||||
};
|
||||
|
||||
if let Some(location) = location {
|
||||
// Naga reports locations in UTF-8 code units, but spec requires location in UTF-16 code units
|
||||
// Based on https://searchfox.org/mozilla-central/rev/5b037d9c6ecdb0729f39ad519f0b867d80a92aad/gfx/wgpu_bindings/src/server.rs#353
|
||||
fn len_utf16(s: &str) -> u64 {
|
||||
s.chars().map(|c| c.len_utf16() as u64).sum()
|
||||
}
|
||||
let start = location.offset as usize;
|
||||
let end = start + location.length as usize;
|
||||
let line_start = source[0..start].rfind('\n').map(|pos| pos + 1).unwrap_or(0);
|
||||
Self {
|
||||
line_number: location.line_number as u64,
|
||||
line_pos: len_utf16(&source[line_start..start]) + 1,
|
||||
offset: len_utf16(&source[0..start]),
|
||||
length: len_utf16(&source[start..end]),
|
||||
message: error.to_string(),
|
||||
}
|
||||
} else {
|
||||
Self {
|
||||
message: error.to_string(),
|
||||
..Default::default()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, Deserialize, Serialize)]
|
||||
#[allow(clippy::large_enum_variant)]
|
||||
pub enum WebGPUResponse {
|
||||
|
@ -48,6 +91,7 @@ pub enum WebGPUResponse {
|
|||
BufferMapAsync(IpcSharedMemory),
|
||||
SubmittedWorkDone,
|
||||
PoppedErrorScope(Result<Option<Error>, PopError>),
|
||||
CompilationInfo(Option<ShaderCompilationInfo>),
|
||||
}
|
||||
|
||||
pub type WebGPUResponseResult = Result<WebGPUResponse, String>;
|
||||
|
@ -145,6 +189,7 @@ pub enum WebGPURequest {
|
|||
program_id: id::ShaderModuleId,
|
||||
program: String,
|
||||
label: Option<String>,
|
||||
sender: IpcSender<Option<WebGPUResponseResult>>,
|
||||
},
|
||||
CreateSwapChain {
|
||||
device_id: id::DeviceId,
|
||||
|
|
|
@ -4,6 +4,7 @@
|
|||
|
||||
//! Data and main loop of WebGPU thread.
|
||||
|
||||
use std::borrow::Cow;
|
||||
use std::collections::HashMap;
|
||||
use std::slice;
|
||||
use std::sync::{Arc, Mutex};
|
||||
|
@ -437,17 +438,24 @@ impl WGPU {
|
|||
program_id,
|
||||
program,
|
||||
label,
|
||||
sender,
|
||||
} => {
|
||||
let global = &self.global;
|
||||
let source = wgpu_core::pipeline::ShaderModuleSource::Wgsl(
|
||||
crate::Cow::Owned(program),
|
||||
);
|
||||
let source =
|
||||
wgpu_core::pipeline::ShaderModuleSource::Wgsl(Cow::Borrowed(&program));
|
||||
let desc = ShaderModuleDescriptor {
|
||||
label: label.map(|s| s.into()),
|
||||
shader_bound_checks: wgt::ShaderBoundChecks::default(),
|
||||
};
|
||||
let (_, error) = gfx_select!(program_id =>
|
||||
global.device_create_shader_module(device_id, &desc, source, Some(program_id)));
|
||||
if let Err(e) = sender.send(Some(Ok(WebGPUResponse::CompilationInfo(
|
||||
error
|
||||
.as_ref()
|
||||
.map(|e| crate::ShaderCompilationInfo::from(e, &program)),
|
||||
)))) {
|
||||
warn!("Failed to send WebGPUResponse::CompilationInfo {e:?}");
|
||||
}
|
||||
self.maybe_dispatch_wgpu_error(device_id, error);
|
||||
},
|
||||
WebGPURequest::CreateSwapChain {
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue