From 41d8e0679d56ab634e771c26cb3a4fb16c396a1e Mon Sep 17 00:00:00 2001 From: Ximo Guanter Date: Tue, 19 Nov 2024 08:55:46 -0500 Subject: [PATCH] Propagate errors on Tree::walk --- libgit2-sys/lib.rs | 2 +- src/call.rs | 11 +++++++++++ src/tree.rs | 36 ++++++++++++++++++++---------------- 3 files changed, 32 insertions(+), 17 deletions(-) diff --git a/libgit2-sys/lib.rs b/libgit2-sys/lib.rs index 383db6c37e..54d384afc9 100644 --- a/libgit2-sys/lib.rs +++ b/libgit2-sys/lib.rs @@ -742,7 +742,7 @@ git_enum! { } pub type git_treewalk_cb = - Option c_int>; + *const extern "C" fn(*const c_char, *const git_tree_entry, *mut c_void) -> c_int; pub type git_treebuilder_filter_cb = Option c_int>; diff --git a/src/call.rs b/src/call.rs index a18f05da91..57aaa26dbd 100644 --- a/src/call.rs +++ b/src/call.rs @@ -116,6 +116,17 @@ mod impls { } } + impl Convert for crate::TreeWalkMode { + #[cfg(target_env = "msvc")] + fn convert(&self) -> raw::git_treewalk_mode { + *self as i32 + } + #[cfg(not(target_env = "msvc"))] + fn convert(&self) -> raw::git_treewalk_mode { + *self as u32 + } + } + impl Convert for Direction { fn convert(&self) -> raw::git_direction { match *self { diff --git a/src/tree.rs b/src/tree.rs index ae8fe3b4c5..376ca9aa2d 100644 --- a/src/tree.rs +++ b/src/tree.rs @@ -36,6 +36,7 @@ pub struct TreeIter<'tree> { /// A binary indicator of whether a tree walk should be performed in pre-order /// or post-order. +#[derive(Clone, Copy)] pub enum TreeWalkMode { /// Runs the traversal in pre-order. PreOrder = 0, @@ -60,17 +61,6 @@ impl Into for TreeWalkResult { } } -impl Into for TreeWalkMode { - #[cfg(target_env = "msvc")] - fn into(self) -> raw::git_treewalk_mode { - self as i32 - } - #[cfg(not(target_env = "msvc"))] - fn into(self) -> raw::git_treewalk_mode { - self as u32 - } -} - impl<'repo> Tree<'repo> { /// Get the id (SHA1) of a repository object pub fn id(&self) -> Oid { @@ -126,12 +116,12 @@ impl<'repo> Tree<'repo> { let mut data = TreeWalkCbData { callback: &mut callback, }; - raw::git_tree_walk( + try_call!(raw::git_tree_walk( self.raw(), - mode.into(), - Some(treewalk_cb::), - &mut data as *mut _ as *mut c_void, - ); + mode, + treewalk_cb:: as raw::git_treewalk_cb, + &mut data as *mut _ as *mut c_void + )); Ok(()) } } @@ -599,4 +589,18 @@ mod tests { .unwrap(); assert_eq!(ct, 8); } + + #[test] + fn tree_walk_error() { + let (td, repo) = crate::test::repo_init(); + + setup_repo(&td, &repo); + + let head = repo.head().unwrap(); + let target = head.target().unwrap(); + let commit = repo.find_commit(target).unwrap(); + let tree = repo.find_tree(commit.tree_id()).unwrap(); + + assert!(tree.walk(TreeWalkMode::PreOrder, |_, _| { -1 }).is_err()); + } }