Show More
@@ -212,3 +212,41 pub(crate) unsafe fn proxy_index_extract | |||
|
212 | 212 | }; |
|
213 | 213 | Ok(py_shared.inner) |
|
214 | 214 | } |
|
215 | ||
|
216 | /// Error propagation for an [`UnsafePyLeaked`] wrapping a [`Result`] | |
|
217 | /// | |
|
218 | /// TODO (will consider when implementing UnsafePyLeaked in PyO3): | |
|
219 | /// It would be nice for UnsafePyLeaked to provide this directly as a variant | |
|
220 | /// of the `map` method with a signature such as: | |
|
221 | /// | |
|
222 | /// ``` | |
|
223 | /// unsafe fn map_or_err(&self, | |
|
224 | /// py: Python, | |
|
225 | /// f: impl FnOnce(T) -> Result(U, E), | |
|
226 | /// convert_err: impl FnOnce(E) -> PyErr) | |
|
227 | /// ``` | |
|
228 | /// | |
|
229 | /// This would spare users of the `cpython` crate the additional `unsafe` deref | |
|
230 | /// to inspect the error and return it outside `UnsafePyLeaked`, and the | |
|
231 | /// subsequent unwrapping that this function performs. | |
|
232 | #[allow(dead_code)] | |
|
233 | pub(crate) fn py_leaked_or_map_err<T, E: std::fmt::Debug + Copy>( | |
|
234 | py: cpython::Python, | |
|
235 | leaked: cpython::UnsafePyLeaked<Result<T, E>>, | |
|
236 | convert_err: impl FnOnce(E) -> PyErr, | |
|
237 | ) -> PyResult<cpython::UnsafePyLeaked<T>> { | |
|
238 | // Safety: we don't leak the "faked" reference out of `UnsafePyLeaked` | |
|
239 | if let Err(e) = *unsafe { | |
|
240 | leaked | |
|
241 | .try_borrow(py) | |
|
242 | .map_err(|e| from_cpython_pyerr(py, e))? | |
|
243 | } { | |
|
244 | return Err(convert_err(e)); | |
|
245 | } | |
|
246 | // Safety: we don't leak the "faked" reference out of `UnsafePyLeaked` | |
|
247 | Ok(unsafe { | |
|
248 | leaked.map(py, |res| { | |
|
249 | res.expect("Error case should have already be treated") | |
|
250 | }) | |
|
251 | }) | |
|
252 | } |
General Comments 0
You need to be logged in to leave comments.
Login now