chore: refresco desde el monorepo (pin tawasuyu.git v0.2.0)
1use super::ffi;
2
3#[derive(thiserror::Error, Debug)]
4/// EGL errors
5pub enum Error {
6 /// The requested OpenGL version is not supported
7 #[error("The requested OpenGL version {0:?} is not supported")]
8 OpenGlVersionNotSupported((u8, u8)),
9 /// The EGL implementation does not support creating OpenGL ES contexts
10 #[error("The EGL implementation does not support creating OpenGL ES contexts. Err: {0:?}")]
11 OpenGlesNotSupported(#[source] Option<EGLError>),
12 /// No available pixel format matched the criteria
13 #[error("No available pixel format matched the criteria")]
14 NoAvailablePixelFormat,
15 /// Backend does not match the context type
16 #[error("The expected backend '{0:?}' does not match the runtime")]
17 NonMatchingBackend(&'static str),
18 /// Display creation failed
19 #[error("Display creation failed with error: {0:}")]
20 DisplayCreationError(#[source] EGLError),
21 /// Display query result invalid
22 #[error("Display query result invalid")]
23 DisplayQueryResultInvalid,
24 /// Unable to obtain a valid EGL Display
25 #[error("Unable to obtain a valid EGL Display.")]
26 DisplayNotSupported,
27 /// `eglInitialize` returned an error
28 #[error("Failed to initialize EGL. Err: {0:}")]
29 InitFailed(#[source] EGLError),
30 /// Failed to configure the EGL context
31 #[error("Failed to configure the EGL context")]
32 ConfigFailed(#[source] EGLError),
33 /// Context creation failed as one or more requirements could not be met. Try removing some gl attributes or pixel format requirements
34 #[error("Context creation failed as one or more requirements could not be met. Try removing some gl attributes or pixel format requirements. Err: {0:}")]
35 CreationFailed(#[source] EGLError),
36 /// The required EGL extension is not supported by the underlying EGL implementation
37 #[error("None of the following EGL extensions is supported by the underlying EGL implementation, at least one is required: {0:?}")]
38 EglExtensionNotSupported(&'static [&'static str]),
39 /// Only one EGLDisplay may be bound to a given `WlDisplay` at any time
40 #[error("Only one EGLDisplay may be bound to a given `WlDisplay` at any time")]
41 OtherEGLDisplayAlreadyBound(#[source] EGLError),
42 /// No EGLDisplay is currently bound to this `WlDisplay`
43 #[error("No EGLDisplay is currently bound to this `WlDisplay`")]
44 NoEGLDisplayBound,
45 /// Index of plane is out of bounds for `EGLImage`
46 #[error("Index of plane is out of bounds for `EGLBuffer`")]
47 PlaneIndexOutOfBounds,
48 /// Failed to create `EGLImage` from the buffer
49 #[error("Failed to create `EGLImage` from the buffer")]
50 EGLImageCreationFailed,
51 /// Failed to create `Dmabuf` from the image
52 #[error("Faiedl to create `Dmabuf` from the image")]
53 DmabufExportFailed(#[source] EGLError),
54 /// Failed to query the available `EGLDevice`s
55 #[error("Failed to query the available `EGLDevice`s")]
56 QueryDevices(#[source] EGLError),
57 /// Failed to query device properties
58 #[error("Failed to query the requested device property")]
59 QueryDeviceProperty(#[source] EGLError),
60 /// The device does not have the given property
61 #[error("The device does not have the given property")]
62 EmptyDeviceProperty,
63 /// Waiting on a fence failed
64 #[error("Waiting on a fence failed. Err: {0:}")]
65 WaitFailed(#[source] EGLError),
66}
67
68/// Raw EGL error
69#[derive(thiserror::Error, Debug)]
70pub enum EGLError {
71 /// EGL is not initialized, or could not be initialized, for the specified EGL display connection.
72 #[error(
73 "EGL is not initialized, or could not be initialized, for the specified EGL display connection."
74 )]
75 NotInitialized,
76 /// EGL cannot access a requested resource (for example a context is bound in another thread).
77 #[error("EGL cannot access a requested resource (for example a context is bound in another thread).")]
78 BadAccess,
79 /// EGL failed to allocate resources for the requested operation.
80 #[error("EGL failed to allocate resources for the requested operation.")]
81 BadAlloc,
82 /// An unrecognized attribute or attribute value was passed in the attribute list.
83 #[error("An unrecognized attribute or attribute value was passed in the attribute list.")]
84 BadAttribute,
85 /// An EGLContext argument does not name a valid EGL rendering context.
86 #[error("An EGLContext argument does not name a valid EGL rendering context.")]
87 BadContext,
88 /// An EGLConfig argument does not name a valid EGL frame buffer configuration.
89 #[error("An EGLConfig argument does not name a valid EGL frame buffer configuration.")]
90 BadConfig,
91 /// The current surface of the calling thread is a window, pixel buffer or pixmap that is no longer valid.
92 #[error("The current surface of the calling thread is a window, pixel buffer or pixmap that is no longer valid.")]
93 BadCurrentSurface,
94 /// An EGLDevice argument is not valid for this display.
95 #[error("An EGLDevice argument is not valid for this display.")]
96 BadDevice,
97 /// An EGLDisplay argument does not name a valid EGL display connection.
98 #[error("An EGLDisplay argument does not name a valid EGL display connection.")]
99 BadDisplay,
100 /// An EGLSurface argument does not name a valid surface (window, pixel buffer or pixmap) configured for GL rendering.
101 #[error("An EGLSurface argument does not name a valid surface (window, pixel buffer or pixmap) configured for GL rendering.")]
102 BadSurface,
103 /// Arguments are inconsistent (for example, a valid context requires buffers not supplied by a valid surface).
104 #[error("Arguments are inconsistent (for example, a valid context requires buffers not supplied by a valid surface).")]
105 BadMatch,
106 /// One or more argument values are invalid.
107 #[error("One or more argument values are invalid.")]
108 BadParameter,
109 /// A NativePixmapType argument does not refer to a valid native pixmap.
110 #[error("A NativePixmapType argument does not refer to a valid native pixmap.")]
111 BadNativePixmap,
112 /// A NativeWindowType argument does not refer to a valid native window.
113 #[error("A NativeWindowType argument does not refer to a valid native window.")]
114 BadNativeWindow,
115 /// The EGL operation failed due to temporary unavailability of a requested resource, but the arguments were otherwise valid, and a subsequent attempt may succeed.
116 #[error("The EGL operation failed due to temporary unavailability of a requested resource, but the arguments were otherwise valid, and a subsequent attempt may succeed.")]
117 ResourceBusy,
118 /// A power management event has occurred. The application must destroy all contexts and reinitialise OpenGL ES state and objects to continue rendering.
119 #[error("A power management event has occurred. The application must destroy all contexts and reinitialise OpenGL ES state and objects to continue rendering.")]
120 ContextLost,
121 /// An unknown error
122 #[error("An unknown error ({0:x})")]
123 Unknown(u32),
124}
125
126impl From<u32> for EGLError {
127 #[inline]
128 fn from(value: u32) -> Self {
129 match value {
130 ffi::egl::NOT_INITIALIZED => EGLError::NotInitialized,
131 ffi::egl::BAD_ACCESS => EGLError::BadAccess,
132 ffi::egl::BAD_ALLOC => EGLError::BadAlloc,
133 ffi::egl::BAD_ATTRIBUTE => EGLError::BadAttribute,
134 ffi::egl::BAD_CONTEXT => EGLError::BadContext,
135 ffi::egl::BAD_CURRENT_SURFACE => EGLError::BadCurrentSurface,
136 ffi::egl::BAD_DEVICE_EXT => EGLError::BadDevice,
137 ffi::egl::BAD_DISPLAY => EGLError::BadDisplay,
138 ffi::egl::BAD_SURFACE => EGLError::BadSurface,
139 ffi::egl::BAD_MATCH => EGLError::BadMatch,
140 ffi::egl::BAD_PARAMETER => EGLError::BadParameter,
141 ffi::egl::BAD_NATIVE_PIXMAP => EGLError::BadNativePixmap,
142 ffi::egl::BAD_NATIVE_WINDOW => EGLError::BadNativeWindow,
143 ffi::egl::RESOURCE_BUSY_EXT => EGLError::ResourceBusy,
144 ffi::egl::CONTEXT_LOST => EGLError::ContextLost,
145 x => EGLError::Unknown(x),
146 }
147 }
148}
149
150impl EGLError {
151 #[inline]
152 pub(super) fn from_last_call() -> Option<EGLError> {
153 match unsafe { ffi::egl::GetError() as u32 } {
154 ffi::egl::SUCCESS => None,
155 x => Some(EGLError::from(x)),
156 }
157 }
158}
159
160/// Wraps a raw egl call and returns error codes from `eglGetError()`, only if the result of the
161/// call is different from the `err` value.
162#[inline]
163pub fn wrap_egl_call<R: PartialEq, F: FnOnce() -> R>(call: F, err: R) -> Result<R, EGLError> {
164 let res = call();
165 if res != err {
166 Ok(res)
167 } else {
168 Err(EGLError::from_last_call().unwrap_or_else(|| {
169 tracing::warn!("Erroneous EGL call didn't set EGLError");
170 EGLError::Unknown(0)
171 }))
172 }
173}
174
175/// Wraps a raw egl call and returns error codes from `eglGetError()`, only if the pointer returned
176/// is null.
177#[inline]
178pub fn wrap_egl_call_ptr<R, F: FnOnce() -> *const R>(call: F) -> Result<*const R, EGLError> {
179 let res = call();
180 if !res.is_null() {
181 Ok(res)
182 } else {
183 Err(EGLError::from_last_call().unwrap_or_else(|| {
184 tracing::warn!("Erroneous EGL call didn't set EGLError");
185 EGLError::Unknown(0)
186 }))
187 }
188}
189
190/// Wraps a raw egl call and returns error codes from `eglGetError()`, only if the `EGLBoolean`
191/// returned is `EGL_FALSE`.
192#[inline]
193pub fn wrap_egl_call_bool<F: FnOnce() -> ffi::egl::types::EGLBoolean>(
194 call: F,
195) -> Result<ffi::egl::types::EGLBoolean, EGLError> {
196 wrap_egl_call(call, ffi::egl::FALSE)
197}