aboutsummaryrefslogtreecommitdiff
path: root/fetch-pack.c
diff options
context:
space:
mode:
authorJunio C Hamano <junkio@cox.net>2005-10-19 18:28:17 -0700
committerJunio C Hamano <junkio@cox.net>2005-10-19 21:04:53 -0700
commit4dab94d52e25b6a53a715613ec5b06b42b240106 (patch)
tree061550ba5e546c9c795b365e1364a159aa264f7c /fetch-pack.c
parent0a8944dd48b97d258240af967dfdfcea4f203b85 (diff)
downloadgit-4dab94d52e25b6a53a715613ec5b06b42b240106.tar.gz
git-4dab94d52e25b6a53a715613ec5b06b42b240106.tar.xz
Do not feed rev-list an invalid SHA1 expression.
The previous round to optimize fetch-pack has a small bug that feeds SHA1^ ("parent commit") before making sure SHA1 is actually a commit (or a tag that eventually dereferences to a commit). Also it did not help culling the known-to-be-common parents if the common one was a merge. Signed-off-by: Junio C Hamano <junkio@cox.net>
Diffstat (limited to 'fetch-pack.c')
-rw-r--r--fetch-pack.c32
1 files changed, 23 insertions, 9 deletions
diff --git a/fetch-pack.c b/fetch-pack.c
index 9dfd072db..4ee91f2ca 100644
--- a/fetch-pack.c
+++ b/fetch-pack.c
@@ -28,22 +28,36 @@ static int find_common(int fd[2], unsigned char *result_sha1,
fetching = 0;
for ( ; refs ; refs = refs->next) {
unsigned char *remote = refs->old_sha1;
+ struct object *o;
/*
- If that object is complete (i.e. it is a descendant of a
- local ref), we don't want it, nor its descendants.
- */
- if (has_sha1_file(remote)
- && parse_object(remote)->flags & COMPLETE) {
- if (rev_command_len + 44 < sizeof(rev_command)) {
+ * If that object is complete (i.e. it is an ancestor of a
+ * local ref), we tell them we have it but do not have to
+ * tell them about its ancestors, which they already know
+ * about.
+ */
+ if (has_sha1_file(remote) &&
+ ((o = parse_object(remote)) != NULL) &&
+ (o->flags & COMPLETE)) {
+ struct commit_list *p;
+ struct commit *commit =
+ (struct commit *) (o = deref_tag(o));
+ if (!o)
+ goto repair;
+ if (o->type != commit_type)
+ continue;
+ p = commit->parents;
+ while (p &&
+ rev_command_len + 44 < sizeof(rev_command)) {
snprintf(rev_command + rev_command_len, 44,
- " ^%s^", sha1_to_hex(remote));
+ " ^%s",
+ sha1_to_hex(p->item->object.sha1));
rev_command_len += 43;
+ p = p->next;
}
-
continue;
}
-
+ repair:
packet_write(fd[1], "want %s\n", sha1_to_hex(remote));
fetching++;
}