This makes `git branch` without -v, --merged, --no-merged, or --contains run about 5 times faster on an uncached repository (4 s intead of 18 s on my linux-2.6 repository with several remotes). Signed-off-by: Anders Kaseorg <andersk@xxxxxxx> --- builtin-branch.c | 33 ++++++++++++++++++++------------- 1 files changed, 20 insertions(+), 13 deletions(-) diff --git a/builtin-branch.c b/builtin-branch.c index 91098ca..7ca2834 100644 --- a/builtin-branch.c +++ b/builtin-branch.c @@ -195,6 +195,7 @@ struct ref_list { struct ref_item *list; struct commit_list *with_commit; int kinds; + int lookup_commits; }; static char *resolve_symref(const char *src, const char *prefix) @@ -215,7 +216,7 @@ static int append_ref(const char *refname, const unsigned char *sha1, int flags, { struct ref_list *ref_list = (struct ref_list*)(cb_data); struct ref_item *newitem; - struct commit *commit; + struct commit *commit = NULL; int kind, i; const char *prefix, *orig_refname = refname; @@ -240,21 +241,25 @@ static int append_ref(const char *refname, const unsigned char *sha1, int flags, if (ARRAY_SIZE(ref_kind) <= i) return 0; - commit = lookup_commit_reference_gently(sha1, 1); - if (!commit) - return error("branch '%s' does not point at a commit", refname); - - /* Filter with with_commit if specified */ - if (!is_descendant_of(commit, ref_list->with_commit)) - return 0; - /* Don't add types the caller doesn't want */ if ((kind & ref_list->kinds) == 0) return 0; - if (merge_filter != NO_FILTER) - add_pending_object(&ref_list->revs, - (struct object *)commit, refname); + + if (ref_list->lookup_commits) { + commit = lookup_commit_reference_gently(sha1, 1); + if (!commit) + return error("branch '%s' does not point at a commit", + refname); + + /* Filter with with_commit if specified */ + if (!is_descendant_of(commit, ref_list->with_commit)) + return 0; + + if (merge_filter != NO_FILTER) + add_pending_object(&ref_list->revs, + (struct object *)commit, refname); + } /* Resize buffer */ if (ref_list->index >= ref_list->alloc) { @@ -426,7 +431,9 @@ static void print_ref_list(int kinds, int detached, int verbose, int abbrev, str ref_list.with_commit = with_commit; if (merge_filter != NO_FILTER) init_revisions(&ref_list.revs, NULL); - for_each_ref(append_ref, &ref_list); + ref_list.lookup_commits = + with_commit || merge_filter != NO_FILTER || verbose; + for_each_rawref(append_ref, &ref_list); if (merge_filter != NO_FILTER) { struct commit *filter; filter = lookup_commit_reference_gently(merge_filter_ref, 0); -- 1.6.3.1 -- To unsubscribe from this list: send the line "unsubscribe git" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html