X-Git-Url: https://git.tokkee.org/?a=blobdiff_plain;f=builtin-pack-objects.c;h=3824ee33acb2f984419ab79c2f3ecc306d3e5ea5;hb=755b99d81539461645088085ea033a3b36152da5;hp=41e1e74533d64e999ec1e564e15b8dea29e4c9c6;hpb=ccbb3d17ace70be9d986368d3df795f5961e9683;p=git.git diff --git a/builtin-pack-objects.c b/builtin-pack-objects.c index 41e1e7453..3824ee33a 100644 --- a/builtin-pack-objects.c +++ b/builtin-pack-objects.c @@ -12,10 +12,13 @@ #include "diff.h" #include "revision.h" #include "list-objects.h" -#include -#include -static const char pack_usage[] = "git-pack-objects [-q] [--no-reuse-delta] [--delta-base-offset] [--non-empty] [--local] [--incremental] [--window=N] [--depth=N] [--revs [--unpacked | --all]*] [--stdout | base-name] len) + avail = len; + sha1write(f, in, avail); + offset += avail; + len -= avail; + } +} + +static int check_loose_inflate(unsigned char *data, unsigned long len, unsigned long expect) { z_stream stream; unsigned char fakebuf[4096]; @@ -320,7 +368,7 @@ static int revalidate_loose_object(struct object_entry *entry, return -1; map += used; mapsize -= used; - return check_inflate(map, mapsize, size); + return check_loose_inflate(map, mapsize, size); } static unsigned long write_object(struct sha1file *f, @@ -413,6 +461,8 @@ static unsigned long write_object(struct sha1file *f, } else { struct packed_git *p = entry->in_pack; + struct pack_window *w_curs = NULL; + unsigned long offset; if (entry->delta) { obj_type = (allow_ofs_delta && entry->delta->offset) ? @@ -434,16 +484,14 @@ static unsigned long write_object(struct sha1file *f, hdrlen += 20; } - use_packed_git(p); - buf = (char *) p->pack_base - + entry->in_pack_offset - + entry->in_pack_header_size; + offset = entry->in_pack_offset + entry->in_pack_header_size; datalen = find_packed_object_size(p, entry->in_pack_offset) - entry->in_pack_header_size; - if (!pack_to_stdout && check_inflate(buf, datalen, entry->size)) + if (!pack_to_stdout && check_pack_inflate(p, &w_curs, + offset, datalen, entry->size)) die("corrupt delta in pack %s", sha1_to_hex(entry->sha1)); - sha1write(f, buf, datalen); - unuse_packed_git(p); + copy_pack_data(f, p, &w_curs, offset, datalen); + unuse_pack(&w_curs); reused++; } if (entry->delta) @@ -475,15 +523,15 @@ static void write_pack_file(void) unsigned long offset; struct pack_header hdr; unsigned last_percent = 999; - int do_progress = 0; + int do_progress = progress; - if (!base_name) + if (!base_name) { f = sha1fd(1, ""); - else { + do_progress >>= 1; + } + else f = sha1create("%s-%s.%s", base_name, sha1_to_hex(object_list_sha1), "pack"); - do_progress = progress; - } if (do_progress) fprintf(stderr, "Writing %d objects.\n", nr_result); @@ -509,6 +557,8 @@ static void write_pack_file(void) if (do_progress) fputc('\n', stderr); done: + if (written != nr_result) + die("wrote %d objects while expecting %d", written, nr_result); sha1close(f, pack_file_sha1, 1); } @@ -519,7 +569,7 @@ static void write_index_file(void) sha1_to_hex(object_list_sha1), "idx"); struct object_entry **list = sorted_by_sha; struct object_entry **last = list + nr_result; - unsigned int array[256]; + uint32_t array[256]; /* * Write the first-level table (the list is sorted, @@ -537,7 +587,7 @@ static void write_index_file(void) array[i] = htonl(next - sorted_by_sha); list = next; } - sha1write(f, array, 256 * sizeof(int)); + sha1write(f, array, 256 * 4); /* * Write the actual SHA1 entries.. @@ -545,7 +595,7 @@ static void write_index_file(void) list = sorted_by_sha; for (i = 0; i < nr_result; i++) { struct object_entry *entry = *list++; - unsigned int offset = htonl(entry->offset); + uint32_t offset = htonl(entry->offset); sha1write(f, &offset, 4); sha1write(f, entry->sha1, 20); } @@ -932,22 +982,19 @@ static void check_object(struct object_entry *entry) if (entry->in_pack && !entry->preferred_base) { struct packed_git *p = entry->in_pack; + struct pack_window *w_curs = NULL; unsigned long left = p->pack_size - entry->in_pack_offset; unsigned long size, used; unsigned char *buf; struct object_entry *base_entry = NULL; - use_packed_git(p); - buf = p->pack_base; - buf += entry->in_pack_offset; + buf = use_pack(p, &w_curs, entry->in_pack_offset, NULL); /* We want in_pack_type even if we do not reuse delta. * There is no point not reusing non-delta representations. */ used = unpack_object_header_gently(buf, left, &entry->in_pack_type, &size); - if (!used || left - used <= 20) - die("corrupt pack for %s", sha1_to_hex(entry->sha1)); /* Check if it is delta, and the base is also an object * we are going to pack. If so we will reuse the existing @@ -956,21 +1003,26 @@ static void check_object(struct object_entry *entry) if (!no_reuse_delta) { unsigned char c, *base_name; unsigned long ofs; + unsigned long used_0; /* there is at least 20 bytes left in the pack */ switch (entry->in_pack_type) { case OBJ_REF_DELTA: - base_name = buf + used; + base_name = use_pack(p, &w_curs, + entry->in_pack_offset + used, NULL); used += 20; break; case OBJ_OFS_DELTA: - c = buf[used++]; + buf = use_pack(p, &w_curs, + entry->in_pack_offset + used, NULL); + used_0 = 0; + c = buf[used_0++]; ofs = c & 127; while (c & 128) { ofs += 1; if (!ofs || ofs & ~(~0UL >> 7)) die("delta base offset overflow in pack for %s", sha1_to_hex(entry->sha1)); - c = buf[used++]; + c = buf[used_0++]; ofs = (ofs << 7) + (c & 127); } if (ofs >= entry->in_pack_offset) @@ -978,6 +1030,7 @@ static void check_object(struct object_entry *entry) sha1_to_hex(entry->sha1)); ofs = entry->in_pack_offset - ofs; base_name = find_packed_object_name(p, ofs); + used += used_0; break; default: base_name = NULL; @@ -985,7 +1038,7 @@ static void check_object(struct object_entry *entry) if (base_name) base_entry = locate_object_entry(base_name); } - unuse_packed_git(p); + unuse_pack(&w_curs); entry->in_pack_header_size = used; if (base_entry) { @@ -1171,7 +1224,9 @@ static int try_delta(struct unpacked *trg, struct unpacked *src, * on an earlier try, but only when reusing delta data. */ if (!no_reuse_delta && trg_entry->in_pack && - trg_entry->in_pack == src_entry->in_pack) + trg_entry->in_pack == src_entry->in_pack && + trg_entry->in_pack_type != OBJ_REF_DELTA && + trg_entry->in_pack_type != OBJ_OFS_DELTA) return 0; /* @@ -1520,10 +1575,6 @@ int cmd_pack_objects(int argc, const char **argv, const char *prefix) local = 1; continue; } - if (!strcmp("--progress", arg)) { - progress = 1; - continue; - } if (!strcmp("--incremental", arg)) { incremental = 1; continue; @@ -1546,6 +1597,10 @@ int cmd_pack_objects(int argc, const char **argv, const char *prefix) progress = 1; continue; } + if (!strcmp("--all-progress", arg)) { + progress = 2; + continue; + } if (!strcmp("-q", arg)) { progress = 0; continue; @@ -1568,6 +1623,7 @@ int cmd_pack_objects(int argc, const char **argv, const char *prefix) } if (!strcmp("--unpacked", arg) || !strncmp("--unpacked=", arg, 11) || + !strcmp("--reflog", arg) || !strcmp("--all", arg)) { use_internal_rev_list = 1; if (ARRAY_SIZE(rp_av) - 1 <= rp_ac) @@ -1641,7 +1697,7 @@ int cmd_pack_objects(int argc, const char **argv, const char *prefix) else { if (nr_result) prepare_pack(window, depth); - if (progress && pack_to_stdout) { + if (progress == 1 && pack_to_stdout) { /* the other end usually displays progress itself */ struct itimerval v = {{0,},}; setitimer(ITIMER_REAL, &v, NULL); @@ -1655,7 +1711,7 @@ int cmd_pack_objects(int argc, const char **argv, const char *prefix) } } if (progress) - fprintf(stderr, "Total %d, written %d (delta %d), reused %d (delta %d)\n", - nr_result, written, written_delta, reused, reused_delta); + fprintf(stderr, "Total %d (delta %d), reused %d (delta %d)\n", + written, written_delta, reused, reused_delta); return 0; }