diff options
Diffstat (limited to 'upload-pack.c')
-rw-r--r-- | upload-pack.c | 73 |
1 files changed, 14 insertions, 59 deletions
diff --git a/upload-pack.c b/upload-pack.c index 82b393ec31..5dc317c3b4 100644 --- a/upload-pack.c +++ b/upload-pack.c @@ -24,13 +24,14 @@ #include "quote.h" #include "upload-pack.h" #include "serve.h" +#include "commit-graph.h" +#include "commit-reach.h" /* Remember to update object flag allocation in object.h */ #define THEY_HAVE (1u << 11) #define OUR_REF (1u << 12) #define WANTED (1u << 13) #define COMMON_KNOWN (1u << 14) -#define REACHABLE (1u << 15) #define SHALLOW (1u << 16) #define NOT_SHALLOW (1u << 17) @@ -337,64 +338,16 @@ static int got_oid(const char *hex, struct object_id *oid) return 0; } -static int reachable(struct commit *want) -{ - struct prio_queue work = { compare_commits_by_commit_date }; - - prio_queue_put(&work, want); - while (work.nr) { - struct commit_list *list; - struct commit *commit = prio_queue_get(&work); - - if (commit->object.flags & THEY_HAVE) { - want->object.flags |= COMMON_KNOWN; - break; - } - if (!commit->object.parsed) - parse_object(the_repository, &commit->object.oid); - if (commit->object.flags & REACHABLE) - continue; - commit->object.flags |= REACHABLE; - if (commit->date < oldest_have) - continue; - for (list = commit->parents; list; list = list->next) { - struct commit *parent = list->item; - if (!(parent->object.flags & REACHABLE)) - prio_queue_put(&work, parent); - } - } - want->object.flags |= REACHABLE; - clear_commit_marks(want, REACHABLE); - clear_prio_queue(&work); - return (want->object.flags & COMMON_KNOWN); -} - static int ok_to_give_up(void) { - int i; + uint32_t min_generation = GENERATION_NUMBER_ZERO; if (!have_obj.nr) return 0; - for (i = 0; i < want_obj.nr; i++) { - struct object *want = want_obj.objects[i].item; - - if (want->flags & COMMON_KNOWN) - continue; - want = deref_tag(the_repository, want, "a want line", 0); - if (!want || want->type != OBJ_COMMIT) { - /* no way to tell if this is reachable by - * looking at the ancestry chain alone, so - * leave a note to ourselves not to worry about - * this object anymore. - */ - want_obj.objects[i].item->flags |= COMMON_KNOWN; - continue; - } - if (!reachable((struct commit *)want)) - return 0; - } - return 1; + return can_all_from_reach_with_flag(&want_obj, THEY_HAVE, + COMMON_KNOWN, oldest_have, + min_generation); } static int get_common_commits(void) @@ -491,6 +444,7 @@ static int do_reachable_revlist(struct child_process *cmd, struct object *o; char namebuf[GIT_MAX_HEXSZ + 2]; /* ^ + hash + LF */ int i; + const unsigned hexsz = the_hash_algo->hexsz; cmd->argv = argv; cmd->git_cmd = 1; @@ -509,7 +463,7 @@ static int do_reachable_revlist(struct child_process *cmd, goto error; namebuf[0] = '^'; - namebuf[GIT_SHA1_HEXSZ + 1] = '\n'; + namebuf[hexsz + 1] = '\n'; for (i = get_max_object_index(); 0 < i; ) { o = get_indexed_object(--i); if (!o) @@ -518,11 +472,11 @@ static int do_reachable_revlist(struct child_process *cmd, o->flags &= ~TMP_MARK; if (!is_our_ref(o)) continue; - memcpy(namebuf + 1, oid_to_hex(&o->oid), GIT_SHA1_HEXSZ); - if (write_in_full(cmd->in, namebuf, GIT_SHA1_HEXSZ + 2) < 0) + memcpy(namebuf + 1, oid_to_hex(&o->oid), hexsz); + if (write_in_full(cmd->in, namebuf, hexsz + 2) < 0) goto error; } - namebuf[GIT_SHA1_HEXSZ] = '\n'; + namebuf[hexsz] = '\n'; for (i = 0; i < src->nr; i++) { o = src->objects[i].item; if (is_our_ref(o)) { @@ -532,8 +486,8 @@ static int do_reachable_revlist(struct child_process *cmd, } if (reachable && o->type == OBJ_COMMIT) o->flags |= TMP_MARK; - memcpy(namebuf, oid_to_hex(&o->oid), GIT_SHA1_HEXSZ); - if (write_in_full(cmd->in, namebuf, GIT_SHA1_HEXSZ + 1) < 0) + memcpy(namebuf, oid_to_hex(&o->oid), hexsz); + if (write_in_full(cmd->in, namebuf, hexsz + 1) < 0) goto error; } close(cmd->in); @@ -740,6 +694,7 @@ static void deepen_by_rev_list(int ac, const char **av, { struct commit_list *result; + close_commit_graph(the_repository); result = get_shallow_commits_by_rev_list(ac, av, SHALLOW, NOT_SHALLOW); send_shallow(result); free_commit_list(result); |