Many invocations of for_each_object_in_pack() and
for_each_packed_object() (which invokes the former) subsequently check
at least the type of the packed object, necessitating accessing the
packfile itself. For locality reasons, it is thus better to iterate in
pack order, instead of index order. Teach for_each_object_in_pack() to
iterate in pack order by first creating a reverse index.

This is based off work by Jeff King.

Signed-off-by: Jonathan Tan <jonathanta...@google.com>
---
After writing this patch and looking at it further, I'm not sure if this
is a clear benefit, but here's the patch anyway. In particular,
builtin/fsck.c and builtin/cat-file.c just deal with the OID directly
and does not access the packfile at all (at least at the time of
invoking for_each_packed_object). And revision.c, if we are excluding
promisor objects, parses each packed promisor object, but it seems
possible to avoid doing that (replacing the parse_object() by
lookup_unknown_object() still passes tests).
---
 packfile.c | 10 +++++++---
 1 file changed, 7 insertions(+), 3 deletions(-)

diff --git a/packfile.c b/packfile.c
index 6974903e5..371b64e9b 100644
--- a/packfile.c
+++ b/packfile.c
@@ -15,6 +15,7 @@
 #include "tree-walk.h"
 #include "tree.h"
 #include "object-store.h"
+#include "pack-revindex.h"
 
 char *odb_pack_name(struct strbuf *buf,
                    const unsigned char *sha1,
@@ -1890,14 +1891,17 @@ int for_each_object_in_pack(struct packed_git *p, 
each_packed_object_fn cb, void
        uint32_t i;
        int r = 0;
 
+       load_pack_revindex(p);
+
        for (i = 0; i < p->num_objects; i++) {
+               uint32_t pack_nr = p->revindex[i].nr;
                struct object_id oid;
 
-               if (!nth_packed_object_oid(&oid, p, i))
+               if (!nth_packed_object_oid(&oid, p, pack_nr))
                        return error("unable to get sha1 of object %u in %s",
-                                    i, p->pack_name);
+                                    pack_nr, p->pack_name);
 
-               r = cb(&oid, p, i, data);
+               r = cb(&oid, p, pack_nr, data);
                if (r)
                        break;
        }
-- 
2.18.0.597.ga71716f1ad-goog

Reply via email to