Skip to main content

wgpu_types/
error.rs

1//! Shared types for WebGPU errors. See also:
2//! <https://gpuweb.github.io/gpuweb/#errors-and-debugging>
3
4use alloc::boxed::Box;
5use alloc::string::String;
6use core::{error, fmt};
7
8/// A classification of WebGPU error for implementers of the WebGPU API to use in their own error
9/// layer(s).
10///
11/// Strongly correlates to the [`GPUError`] and [`GPUErrorFilter`] types in the WebGPU API, with an
12/// additional [`Self::DeviceLost`] variant.
13///
14/// [`GPUError`]: https://gpuweb.github.io/gpuweb/#gpuerror
15/// [`GPUErrorFilter`]: https://gpuweb.github.io/gpuweb/#enumdef-gpuerrorfilter
16#[derive(Clone, Copy, Debug, Eq, PartialEq)]
17#[cfg_attr(feature = "serde", derive(serde::Deserialize, serde::Serialize))]
18pub enum ErrorType {
19    /// A [`GPUInternalError`].
20    ///
21    /// [`GPUInternalError`]: https://gpuweb.github.io/gpuweb/#gpuinternalerror
22    Internal,
23    /// A [`GPUOutOfMemoryError`].
24    ///
25    /// [`GPUOutOfMemoryError`]: https://gpuweb.github.io/gpuweb/#gpuoutofmemoryerror
26    OutOfMemory,
27    /// A [`GPUValidationError`].
28    ///
29    /// [`GPUValidationError`]: https://gpuweb.github.io/gpuweb/#gpuvalidationerror
30    Validation,
31    /// Indicates that device loss occurred. In JavaScript, this means the [`GPUDevice.lost`]
32    /// property should be `resolve`d.
33    ///
34    /// [`GPUDevice.lost`]: https://www.w3.org/TR/webgpu/#dom-gpudevice-lost
35    DeviceLost,
36}
37
38/// A trait for querying the [`ErrorType`] classification of an error.
39///
40/// This is intended to be used as a convenience by implementations of WebGPU to classify errors
41/// returned by [`wgpu_core`](crate).
42pub trait WebGpuError: error::Error + 'static {
43    /// Determine the classification of this error as a WebGPU [`ErrorType`].
44    fn webgpu_error_type(&self) -> ErrorType;
45}
46
47/// The callback of [`uncaptured_error`](https://gpuweb.github.io/gpuweb/#eventdef-gpudevice-uncapturederror)
48///
49/// It must be a function with this signature.
50pub trait UncapturedErrorHandler: Fn(Error) + Send + Sync + 'static {}
51impl<T> UncapturedErrorHandler for T where T: Fn(Error) + Send + Sync + 'static {}
52
53/// Kinds of [`Error`]s a [`push_error_scope`](https://gpuweb.github.io/gpuweb/#dom-gpudevice-pusherrorscope) may be configured to catch.
54///
55/// Corresponds to the [`GPUErrorFilter`] type in the WebGPU API.
56///
57/// [`GPUErrorFilter`]: https://gpuweb.github.io/gpuweb/#enumdef-gpuerrorfilter
58#[repr(C)]
59#[derive(Clone, Copy, Debug, Eq, PartialEq, PartialOrd)]
60#[cfg_attr(feature = "serde", derive(serde::Deserialize, serde::Serialize))]
61pub enum ErrorFilter {
62    /// Catch only out-of-memory errors.
63    OutOfMemory,
64    /// Catch only validation errors.
65    Validation,
66    /// Catch only internal errors.
67    Internal,
68}
69static_assertions::assert_impl_all!(ErrorFilter: Send, Sync);
70
71/// Lower level source of the error.
72///
73/// `Send + Sync` varies depending on configuration.
74#[cfg(any(
75    not(target_family = "wasm"),
76    all(
77        feature = "fragile-send-sync-non-atomic-wasm",
78        not(target_feature = "atomics")
79    )
80))]
81#[cfg_attr(docsrs, doc(cfg(all())))]
82pub type ErrorSource = Box<dyn error::Error + Send + Sync + 'static>;
83/// Lower level source of the error.
84///
85/// `Send + Sync` varies depending on configuration.
86#[cfg(not(any(
87    not(target_family = "wasm"),
88    all(
89        feature = "fragile-send-sync-non-atomic-wasm",
90        not(target_feature = "atomics")
91    )
92)))]
93#[cfg_attr(docsrs, doc(cfg(all())))]
94pub type ErrorSource = Box<dyn error::Error + 'static>;
95
96/// Errors resulting from usage of GPU APIs.
97#[derive(Debug)]
98pub enum Error {
99    /// Out of memory.
100    OutOfMemory {
101        /// Lower level source of the error.
102        source: ErrorSource,
103    },
104    /// Validation error, signifying a bug in code or data provided to `wgpu`.
105    Validation {
106        /// Lower level source of the error.
107        source: ErrorSource,
108        /// Description of the validation error.
109        description: String,
110    },
111    /// Internal error. Used for signalling any failures not explicitly expected by WebGPU.
112    ///
113    /// These could be due to internal implementation or system limits being reached.
114    Internal {
115        /// Lower level source of the error.
116        source: ErrorSource,
117        /// Description of the internal GPU error.
118        description: String,
119    },
120}
121
122impl error::Error for Error {
123    fn source(&self) -> Option<&(dyn error::Error + 'static)> {
124        match self {
125            Error::OutOfMemory { source } => Some(source.as_ref()),
126            Error::Validation { source, .. } => Some(source.as_ref()),
127            Error::Internal { source, .. } => Some(source.as_ref()),
128        }
129    }
130}
131
132impl fmt::Display for Error {
133    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
134        match self {
135            Error::OutOfMemory { .. } => f.write_str("Out of Memory"),
136            Error::Validation { description, .. } => f.write_str(description),
137            Error::Internal { description, .. } => f.write_str(description),
138        }
139    }
140}
141
142impl WebGpuError for Error {
143    fn webgpu_error_type(&self) -> ErrorType {
144        match self {
145            Error::OutOfMemory { .. } => ErrorType::OutOfMemory,
146            Error::Validation { .. } => ErrorType::Validation,
147            Error::Internal { .. } => ErrorType::Internal,
148        }
149    }
150}