From: Junio C Hamano Date: Wed, 24 Jun 2026 20:21:10 +0000 (-0700) Subject: Merge branch 'ps/odb-source-packed' into jch X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=4793cda5cbea9701b13a780672f8a78ad42bb772;p=thirdparty%2Fgit.git Merge branch 'ps/odb-source-packed' into jch The packed object source has been refactored into a proper struct odb_source. * ps/odb-source-packed: odb/source-packed: drop pointer to "files" parent source midx: refactor interfaces to work on "packed" source odb/source-packed: stub out remaining functions odb/source-packed: wire up `freshen_object()` callback odb/source-packed: wire up `find_abbrev_len()` callback odb/source-packed: wire up `count_objects()` callback odb/source-packed: wire up `for_each_object()` callback odb/source-packed: wire up `read_object_stream()` callback odb/source-packed: wire up `read_object_info()` callback packfile: use higher-level interface to implement `has_object_pack()` odb/source-packed: wire up `reprepare()` callback odb/source-packed: wire up `close()` callback odb/source-packed: start converting to a proper `struct odb_source` odb/source-packed: store pointer to "files" instead of generic source packfile: move packed source into "odb/" subsystem packfile: split out packfile list logic packfile: rename `struct packfile_store` to `odb_source_packed` --- 4793cda5cbea9701b13a780672f8a78ad42bb772 diff --cc odb/source-packed.h index 0000000000,88994098c1..f0724b204c mode 000000,100644..100644 --- a/odb/source-packed.h +++ b/odb/source-packed.h @@@ -1,0 -1,94 +1,94 @@@ + #ifndef ODB_SOURCE_PACKED_H + #define ODB_SOURCE_PACKED_H + + #include "odb/source.h" + #include "packfile-list.h" + #include "strmap.h" + + /* + * A store that manages packfiles for a given object database. + */ + struct odb_source_packed { + struct odb_source base; + + /* + * The list of packfiles in the order in which they have been most + * recently used. + */ + struct packfile_list packs; + + /* + * Cache of packfiles which are marked as "kept", either because there + * is an on-disk ".keep" file or because they are marked as "kept" in + * memory. + * + * Should not be accessed directly, but via + * `packfile_store_get_kept_pack_cache()`. The list of packs gets + * invalidated when the stored flags and the flags passed to + * `packfile_store_get_kept_pack_cache()` mismatch. + */ + struct { + struct packed_git **packs; + unsigned flags; + } kept_cache; + + /* The multi-pack index that belongs to this specific packfile store. */ + struct multi_pack_index *midx; + + /* + * A map of packfile names to packed_git structs for tracking which + * packs have been loaded already. + */ + struct strmap packs_by_path; + + /* + * Whether packfiles have already been populated with this store's + * packs. + */ + bool initialized; + + /* + * Usually, packfiles will be reordered to the front of the `packs` + * list whenever an object is looked up via them. This has the effect + * that packs that contain a lot of accessed objects will be located + * towards the front. + * - * This is usually desireable, but there are exceptions. One exception ++ * This is usually desirable, but there are exceptions. One exception + * is when the looking up multiple objects in a loop for each packfile. + * In that case, we may easily end up with an infinite loop as the + * packfiles get reordered to the front repeatedly. + * + * Setting this field to `true` thus disables these reorderings. + */ + bool skip_mru_updates; + }; + + /* + * Allocate and initialize a new empty packfile store for the given object + * database. + */ + struct odb_source_packed *odb_source_packed_new(struct object_database *odb, + const char *path, + bool local); + + /* + * Cast the given object database source to the packed backend. This will cause + * a BUG in case the source doesn't use this backend. + */ + static inline struct odb_source_packed *odb_source_packed_downcast(struct odb_source *source) + { + if (source->type != ODB_SOURCE_PACKED) + BUG("trying to downcast source of type '%d' to packed", source->type); + return container_of(source, struct odb_source_packed, base); + } + + /* + * Prepare the source by loading packfiles and multi-pack indices for + * all alternates. This becomes a no-op if the source is already prepared. + * + * It shouldn't typically be necessary to call this function directly, as + * functions that access the source know to prepare it. + */ + void odb_source_packed_prepare(struct odb_source_packed *source); + + #endif diff --cc packfile.h index defb6f442c,71a71017ee..2329a69701 --- a/packfile.h +++ b/packfile.h @@@ -454,11 -292,14 +292,15 @@@ off_t nth_packed_object_offset(const st */ off_t find_pack_entry_one(const struct object_id *oid, struct packed_git *); + int packfile_fill_entry(struct packed_git *p, + const struct object_id *oid, + struct pack_entry *e); + int is_pack_valid(struct packed_git *); -void *unpack_entry(struct repository *r, struct packed_git *, off_t, enum object_type *, unsigned long *); +void *unpack_entry(struct repository *r, struct packed_git *, off_t, + enum object_type *, size_t *); unsigned long unpack_object_header_buffer(const unsigned char *buf, unsigned long len, enum object_type *type, size_t *sizep); -unsigned long get_size_from_delta(struct packed_git *, struct pack_window **, off_t); +size_t get_size_from_delta(struct packed_git *, struct pack_window **, off_t); int unpack_object_header(struct packed_git *, struct pack_window **, off_t *, size_t *); off_t get_delta_base(struct packed_git *p, struct pack_window **w_curs, off_t *curpos, enum object_type type,