diff --git a/libgit2-sys/lib.rs b/libgit2-sys/lib.rs index 383db6c37e..2cc53bf92d 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>; + 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/tree.rs b/src/tree.rs index ae8fe3b4c5..e683257436 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, @@ -126,12 +127,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 as raw::git_treewalk_mode, + treewalk_cb::, + &mut data as *mut _ as *mut c_void + )); Ok(()) } } @@ -599,4 +600,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(); + let e = tree.walk(TreeWalkMode::PreOrder, |_, _| -1).unwrap_err(); + assert_eq!(e.class(), crate::ErrorClass::Callback); + } }