diff --git a/odb.c b/odb.c index cf6e7938c0..1d6538163b 100644 --- a/odb.c +++ b/odb.c @@ -989,11 +989,33 @@ int odb_write_object_ext(struct object_database *odb, const void *buf, unsigned long len, enum object_type type, struct object_id *oid, - struct object_id *compat_oid, + const struct object_id *compat_oid_in, enum odb_write_object_flags flags) { + const struct git_hash_algo *compat = odb->repo->compat_hash_algo; + struct object_id compat_oid, *compat_oid_p = NULL; + + if (compat) { + const struct git_hash_algo *algo = odb->repo->hash_algo; + + if (compat_oid_in) { + oidcpy(&compat_oid, compat_oid_in); + } else if (type == OBJ_BLOB) { + hash_object_file(compat, buf, len, type, &compat_oid); + } else { + struct strbuf converted = STRBUF_INIT; + convert_object_file(odb->repo, &converted, algo, compat, + buf, len, type, 0); + hash_object_file(compat, converted.buf, converted.len, + type, &compat_oid); + strbuf_release(&converted); + } + + compat_oid_p = &compat_oid; + } + return odb_source_write_object(odb->sources, buf, len, type, - oid, compat_oid, flags); + oid, compat_oid_p, flags); } int odb_write_object_stream(struct object_database *odb, diff --git a/odb.h b/odb.h index 94754643d2..066560113e 100644 --- a/odb.h +++ b/odb.h @@ -585,9 +585,11 @@ enum odb_write_object_flags { /* * Write an object into the object database. The object is being written into - * the local alternate of the repository. If provided, the converted object ID - * as well as the compatibility object ID are written to the respective - * pointers. + * the local alternate of the repository. If provided, the object ID of the + * final object is written into `oid`. + * + * If the caller provides a `compat_oid`, then this compatibility object hash + * will be stored instead of computing the compatibility hash ad-hoc. * * Returns 0 on success, a negative error code otherwise. */ @@ -595,7 +597,7 @@ int odb_write_object_ext(struct object_database *odb, const void *buf, unsigned long len, enum object_type type, struct object_id *oid, - struct object_id *compat_oid, + const struct object_id *compat_oid, enum odb_write_object_flags flags); static inline int odb_write_object(struct object_database *odb, diff --git a/odb/source-files.c b/odb/source-files.c index 4138758511..3d9f5eca32 100644 --- a/odb/source-files.c +++ b/odb/source-files.c @@ -163,7 +163,7 @@ static int odb_source_files_write_object(struct odb_source *source, const void *buf, size_t len, enum object_type type, struct object_id *oid, - struct object_id *compat_oid, + const struct object_id *compat_oid, enum odb_write_object_flags flags) { struct odb_source_files *files = odb_source_files_downcast(source); diff --git a/odb/source-inmemory.c b/odb/source-inmemory.c index e47bfd8fcc..e727aba427 100644 --- a/odb/source-inmemory.c +++ b/odb/source-inmemory.c @@ -231,7 +231,7 @@ static int odb_source_inmemory_write_object(struct odb_source *source, const void *buf, size_t len, enum object_type type, struct object_id *oid, - struct object_id *compat_oid UNUSED, + const struct object_id *compat_oid UNUSED, enum odb_write_object_flags flags UNUSED) { struct odb_source_inmemory *inmemory = odb_source_inmemory_downcast(source); diff --git a/odb/source-loose.c b/odb/source-loose.c index 3f7d04a56e..ca223109cd 100644 --- a/odb/source-loose.c +++ b/odb/source-loose.c @@ -585,32 +585,14 @@ static int odb_source_loose_freshen_object(struct odb_source *source, static int odb_source_loose_write_object(struct odb_source *source, const void *buf, size_t len, enum object_type type, struct object_id *oid, - struct object_id *compat_oid_in, + const struct object_id *compat_oid, enum odb_write_object_flags flags) { struct odb_source_loose *loose = odb_source_loose_downcast(source); const struct git_hash_algo *algo = source->odb->repo->hash_algo; - const struct git_hash_algo *compat = source->odb->repo->compat_hash_algo; - struct object_id compat_oid; char hdr[MAX_HEADER_LEN]; size_t hdrlen = sizeof(hdr); - /* Generate compat_oid */ - if (compat) { - if (compat_oid_in) - oidcpy(&compat_oid, compat_oid_in); - else if (type == OBJ_BLOB) - hash_object_file(compat, buf, len, type, &compat_oid); - else { - struct strbuf converted = STRBUF_INIT; - convert_object_file(source->odb->repo, &converted, algo, compat, - buf, len, type, 0); - hash_object_file(compat, converted.buf, converted.len, - type, &compat_oid); - strbuf_release(&converted); - } - } - /* Normally if we have it in the pack then we do not bother writing * it out into .git/objects/??/?{38} file. */ @@ -619,8 +601,8 @@ static int odb_source_loose_write_object(struct odb_source *source, return 0; if (write_loose_object(loose, oid, hdr, hdrlen, buf, len, 0, flags)) return -1; - if (compat) - return repo_add_loose_object_map(loose, oid, &compat_oid); + if (compat_oid) + return repo_add_loose_object_map(loose, oid, compat_oid); return 0; } diff --git a/odb/source-packed.c b/odb/source-packed.c index 8d9ce197cc..af0d533375 100644 --- a/odb/source-packed.c +++ b/odb/source-packed.c @@ -530,7 +530,7 @@ static int odb_source_packed_write_object(struct odb_source *source UNUSED, size_t len UNUSED, enum object_type type UNUSED, struct object_id *oid UNUSED, - struct object_id *compat_oid UNUSED, + const struct object_id *compat_oid UNUSED, unsigned flags UNUSED) { return error("packed backend cannot write objects"); diff --git a/odb/source.h b/odb/source.h index cd63dba91f..b3c1ca3a66 100644 --- a/odb/source.h +++ b/odb/source.h @@ -207,7 +207,7 @@ struct odb_source { const void *buf, size_t len, enum object_type type, struct object_id *oid, - struct object_id *compat_oid, + const struct object_id *compat_oid, enum odb_write_object_flags flags); /* @@ -417,7 +417,7 @@ static inline int odb_source_write_object(struct odb_source *source, const void *buf, unsigned long len, enum object_type type, struct object_id *oid, - struct object_id *compat_oid, + const struct object_id *compat_oid, enum odb_write_object_flags flags) { return source->write_object(source, buf, len, type, oid,