diff options
Diffstat (limited to 'builtin/fast-export.c')
-rw-r--r-- | builtin/fast-export.c | 33 |
1 files changed, 20 insertions, 13 deletions
diff --git a/builtin/fast-export.c b/builtin/fast-export.c index ad9d0c46e8..725c0a7dca 100644 --- a/builtin/fast-export.c +++ b/builtin/fast-export.c @@ -113,12 +113,13 @@ static void show_progress(void) printf("progress %d objects\n", counter); } -static void handle_object(const unsigned char *sha1) +static void export_blob(const unsigned char *sha1) { unsigned long size; enum object_type type; char *buf; struct object *object; + int eaten; if (no_data) return; @@ -126,16 +127,18 @@ static void handle_object(const unsigned char *sha1) if (is_null_sha1(sha1)) return; - object = parse_object(sha1); - if (!object) - die ("Could not read blob %s", sha1_to_hex(sha1)); - - if (object->flags & SHOWN) + object = lookup_object(sha1); + if (object && object->flags & SHOWN) return; buf = read_sha1_file(sha1, &type, &size); if (!buf) die ("Could not read blob %s", sha1_to_hex(sha1)); + if (check_sha1_signature(sha1, buf, size, typename(type)) < 0) + die("sha1 mismatch in blob %s", sha1_to_hex(sha1)); + object = parse_object_buffer(sha1, type, size, buf, &eaten); + if (!object) + die("Could not read blob %s", sha1_to_hex(sha1)); mark_next_object(object); @@ -147,7 +150,8 @@ static void handle_object(const unsigned char *sha1) show_progress(); object->flags |= SHOWN; - free(buf); + if (!eaten) + free(buf); } static int depth_first(const void *a_, const void *b_) @@ -312,7 +316,7 @@ static void handle_commit(struct commit *commit, struct rev_info *rev) /* Export the referenced blobs, and remember the marks. */ for (i = 0; i < diff_queued_diff.nr; i++) if (!S_ISGITLINK(diff_queued_diff.queue[i]->two->mode)) - handle_object(diff_queued_diff.queue[i]->two->sha1); + export_blob(diff_queued_diff.queue[i]->two->sha1); mark_next_object(&commit->object); if (!is_encoding_utf8(encoding)) @@ -512,7 +516,7 @@ static void get_tags_and_duplicates(struct rev_cmdline_info *info, commit = (struct commit *)tag; break; case OBJ_BLOB: - handle_object(tag->object.sha1); + export_blob(tag->object.sha1); continue; default: /* OBJ_TAG (nested tags) is already handled */ warning("Tag points to object of unexpected type %s, skipping.", @@ -614,9 +618,12 @@ static void import_marks(char *input_file) || *mark_end != ' ' || get_sha1(mark_end + 1, sha1)) die("corrupt mark line: %s", line); + if (last_idnum < mark) + last_idnum = mark; + object = parse_object(sha1); if (!object) - die ("Could not read blob %s", sha1_to_hex(sha1)); + continue; if (object->flags & SHOWN) error("Object %s already has a mark", sha1_to_hex(sha1)); @@ -626,8 +633,6 @@ static void import_marks(char *input_file) continue; mark_object(object, mark); - if (last_idnum < mark) - last_idnum = mark; object->flags |= SHOWN; } @@ -641,6 +646,7 @@ int cmd_fast_export(int argc, const char **argv, const char *prefix) struct string_list extra_refs = STRING_LIST_INIT_NODUP; struct commit *commit; char *export_filename = NULL, *import_filename = NULL; + uint32_t lastimportid; struct option options[] = { OPT_INTEGER(0, "progress", &progress, N_("show progress after <n> objects")), @@ -684,6 +690,7 @@ int cmd_fast_export(int argc, const char **argv, const char *prefix) if (import_filename) import_marks(import_filename); + lastimportid = last_idnum; if (import_filename && revs.prune_data.nr) full_tree = 1; @@ -706,7 +713,7 @@ int cmd_fast_export(int argc, const char **argv, const char *prefix) handle_tags_and_duplicates(&extra_refs); - if (export_filename) + if (export_filename && lastimportid != last_idnum) export_marks(export_filename); if (use_done_feature) |