changeset 52534:9af0330788a5

rust-pyo3: new helper for incoming iterables of revisions The pattern to borrow the core `Index` from the index proxy, and using it in `rev_pyiter_collect` is frequent enough in what remains to be converted from `hg-cpython` that it is worth having this direct helper (and it will neatly enclose the unsafety).
author Georges Racinet <georges.racinet@cloudcrane.io>
date Sat, 07 Dec 2024 14:55:42 +0100
parents 6b694bdf752a
children 507fec66014f
files rust/hg-pyo3/src/ancestors.rs rust/hg-pyo3/src/revision.rs
diffstat 2 files changed, 20 insertions(+), 15 deletions(-) [+]
line wrap: on
line diff
--- a/rust/hg-pyo3/src/ancestors.rs	Sat Dec 07 18:54:31 2024 +0100
+++ b/rust/hg-pyo3/src/ancestors.rs	Sat Dec 07 14:55:42 2024 +0100
@@ -19,11 +19,11 @@
 };
 
 use crate::convert_cpython::{
-    proxy_index_extract, proxy_index_py_leak, py_leaked_borrow,
-    py_leaked_borrow_mut, py_leaked_or_map_err,
+    proxy_index_py_leak, py_leaked_borrow, py_leaked_borrow_mut,
+    py_leaked_or_map_err,
 };
 use crate::exceptions::{map_lock_error, GraphError};
-use crate::revision::{rev_pyiter_collect, PyRevision};
+use crate::revision::{rev_pyiter_collect_with_py_index, PyRevision};
 use crate::util::new_submodule;
 use rusthg::revlog::PySharedIndex;
 
@@ -41,12 +41,8 @@
         stoprev: PyRevision,
         inclusive: bool,
     ) -> PyResult<Self> {
-        // Safety: we don't leak the "faked" reference out of
-        // `UnsafePyLeaked`
-        let initvec: Vec<_> = {
-            let borrowed_idx = unsafe { proxy_index_extract(index_proxy)? };
-            rev_pyiter_collect(initrevs, borrowed_idx)?
-        };
+        let initvec: Vec<_> =
+            rev_pyiter_collect_with_py_index(initrevs, index_proxy)?;
         let (py, leaked_idx) = proxy_index_py_leak(index_proxy)?;
         let res_ait = unsafe {
             leaked_idx.map(py, |idx| {
@@ -99,12 +95,8 @@
         inclusive: bool,
     ) -> PyResult<Self> {
         let cloned_proxy = index_proxy.clone().unbind();
-        let initvec: Vec<_> = {
-            // Safety: we don't leak the "faked" reference out of
-            // `UnsafePyLeaked`
-            let borrowed_idx = unsafe { proxy_index_extract(index_proxy)? };
-            rev_pyiter_collect(initrevs, borrowed_idx)?
-        };
+        let initvec: Vec<_> =
+            rev_pyiter_collect_with_py_index(initrevs, index_proxy)?;
         let (py, leaked_idx) = proxy_index_py_leak(index_proxy)?;
         // Safety: we don't leak the "faked" reference out of
         // `UnsafePyLeaked`
--- a/rust/hg-pyo3/src/revision.rs	Sat Dec 07 18:54:31 2024 +0100
+++ b/rust/hg-pyo3/src/revision.rs	Sat Dec 07 14:55:42 2024 +0100
@@ -3,6 +3,7 @@
 use hg::revlog::RevlogIndex;
 use hg::{BaseRevision, Revision, UncheckedRevision};
 
+use crate::convert_cpython::proxy_index_extract;
 use crate::exceptions::GraphError;
 
 /// Revision as exposed to/from the Python layer.
@@ -55,6 +56,18 @@
     })
 }
 
+pub fn rev_pyiter_collect_with_py_index<C>(
+    revs: &Bound<'_, PyAny>,
+    proxy_index: &Bound<'_, PyAny>,
+) -> PyResult<C>
+where
+    C: FromIterator<Revision>,
+{
+    // Safety: we don't leak the "faked" reference out of `UnsafePyLeaked`
+    let borrowed_idx = unsafe { proxy_index_extract(proxy_index)? };
+    rev_pyiter_collect(revs, borrowed_idx)
+}
+
 /// Same as [`rev_pyiter_collect`], giving control on returned errors
 pub fn rev_pyiter_collect_or_else<C, I>(
     revs: &Bound<'_, PyAny>,