Thread (158 messages) 158 messages, 3 authors, 2025-10-16
STALE264d

[PATCH 31/49] builtin/repack.c: remove ref snapshotting from builtin

From: Taylor Blau <hidden>
Date: 2025-09-28 22:09:13
Subsystem: kernel build + files below scripts/ (unless maintained elsewhere), the rest · Maintainers: Nathan Chancellor, Nicolas Schier, Linus Torvalds

When writing a MIDX, 'git repack' takes a snapshot of the repository's
references and writes the result out to a file, which it then passes to
'git multi-pack-index write' via the '--refs-snapshot'.

This is done in order to make bitmap selections with respect to what we
are packing, thus avoiding a race where an incoming reference update
causes us to try and write a bitmap for a commit not present in the
MIDX.

Extract this functionality out into a new repack-midx.c compilation
unit, and expose the necessary functions via the repack.h API.

Signed-off-by: Taylor Blau <redacted>
---
 Makefile         |  1 +
 builtin/repack.c | 68 ------------------------------------------
 meson.build      |  1 +
 repack-midx.c    | 77 ++++++++++++++++++++++++++++++++++++++++++++++++
 repack.h         |  4 +++
 5 files changed, 83 insertions(+), 68 deletions(-)
 create mode 100644 repack-midx.c
diff --git a/Makefile b/Makefile
index a6da12a326..3360743afb 100644
--- a/Makefile
+++ b/Makefile
@@ -1138,6 +1138,7 @@ LIB_OBJS += refspec.o
 LIB_OBJS += remote.o
 LIB_OBJS += repack.o
 LIB_OBJS += repack-geometry.o
+LIB_OBJS += repack-midx.o
 LIB_OBJS += repack-promisor.o
 LIB_OBJS += replace-object.o
 LIB_OBJS += repo-settings.o
diff --git a/builtin/repack.c b/builtin/repack.c
index b49e2dab9a..5a1f1cb562 100644
--- a/builtin/repack.c
+++ b/builtin/repack.c
@@ -178,74 +178,6 @@ static int midx_has_unknown_packs(char **midx_pack_names,
 	return 0;
 }
 
-struct midx_snapshot_ref_data {
-	struct repository *repo;
-	struct tempfile *f;
-	struct oidset seen;
-	int preferred;
-};
-
-static int midx_snapshot_ref_one(const char *refname UNUSED,
-				 const char *referent UNUSED,
-				 const struct object_id *oid,
-				 int flag UNUSED, void *_data)
-{
-	struct midx_snapshot_ref_data *data = _data;
-	struct object_id peeled;
-
-	if (!peel_iterated_oid(data->repo, oid, &peeled))
-		oid = &peeled;
-
-	if (oidset_insert(&data->seen, oid))
-		return 0; /* already seen */
-
-	if (odb_read_object_info(data->repo->objects, oid, NULL) != OBJ_COMMIT)
-		return 0;
-
-	fprintf(data->f->fp, "%s%s\n", data->preferred ? "+" : "",
-		oid_to_hex(oid));
-
-	return 0;
-}
-
-static void midx_snapshot_refs(struct repository *repo, struct tempfile *f)
-{
-	struct midx_snapshot_ref_data data;
-	const struct string_list *preferred = bitmap_preferred_tips(repo);
-
-	data.repo = repo;
-	data.f = f;
-	data.preferred = 0;
-	oidset_init(&data.seen, 0);
-
-	if (!fdopen_tempfile(f, "w"))
-		 die(_("could not open tempfile %s for writing"),
-		     get_tempfile_path(f));
-
-	if (preferred) {
-		struct string_list_item *item;
-
-		data.preferred = 1;
-		for_each_string_list_item(item, preferred)
-			refs_for_each_ref_in(get_main_ref_store(repo),
-					     item->string,
-					     midx_snapshot_ref_one, &data);
-		data.preferred = 0;
-	}
-
-	refs_for_each_ref(get_main_ref_store(repo),
-			  midx_snapshot_ref_one, &data);
-
-	if (close_tempfile_gently(f)) {
-		int save_errno = errno;
-		delete_tempfile(&f);
-		errno = save_errno;
-		die_errno(_("could not close refs snapshot tempfile"));
-	}
-
-	oidset_clear(&data.seen);
-}
-
 static void midx_included_packs(struct string_list *include,
 				struct existing_packs *existing,
 				char **midx_pack_names,
diff --git a/meson.build b/meson.build
index c929ad6f7e..42171d1851 100644
--- a/meson.build
+++ b/meson.build
@@ -464,6 +464,7 @@ libgit_sources = [
   'remote.c',
   'repack.c',
   'repack-geometry.c',
+  'repack-midx.c',
   'repack-promisor.c',
   'replace-object.c',
   'repo-settings.c',
diff --git a/repack-midx.c b/repack-midx.c
new file mode 100644
index 0000000000..354df729a5
--- /dev/null
+++ b/repack-midx.c
@@ -0,0 +1,77 @@
+#include "git-compat-util.h"
+#include "repack.h"
+#include "hash.h"
+#include "hex.h"
+#include "odb.h"
+#include "oidset.h"
+#include "pack-bitmap.h"
+#include "refs.h"
+#include "tempfile.h"
+
+struct midx_snapshot_ref_data {
+	struct repository *repo;
+	struct tempfile *f;
+	struct oidset seen;
+	int preferred;
+};
+
+static int midx_snapshot_ref_one(const char *refname UNUSED,
+				 const char *referent UNUSED,
+				 const struct object_id *oid,
+				 int flag UNUSED, void *_data)
+{
+	struct midx_snapshot_ref_data *data = _data;
+	struct object_id peeled;
+
+	if (!peel_iterated_oid(data->repo, oid, &peeled))
+		oid = &peeled;
+
+	if (oidset_insert(&data->seen, oid))
+		return 0; /* already seen */
+
+	if (odb_read_object_info(data->repo->objects, oid, NULL) != OBJ_COMMIT)
+		return 0;
+
+	fprintf(data->f->fp, "%s%s\n", data->preferred ? "+" : "",
+		oid_to_hex(oid));
+
+	return 0;
+}
+
+void midx_snapshot_refs(struct repository *repo, struct tempfile *f)
+{
+	struct midx_snapshot_ref_data data;
+	const struct string_list *preferred = bitmap_preferred_tips(repo);
+
+	data.repo = repo;
+	data.f = f;
+	data.preferred = 0;
+	oidset_init(&data.seen, 0);
+
+	if (!fdopen_tempfile(f, "w"))
+		 die(_("could not open tempfile %s for writing"),
+		     get_tempfile_path(f));
+
+	if (preferred) {
+		struct string_list_item *item;
+
+		data.preferred = 1;
+		for_each_string_list_item(item, preferred)
+			refs_for_each_ref_in(get_main_ref_store(repo),
+					     item->string,
+					     midx_snapshot_ref_one, &data);
+		data.preferred = 0;
+	}
+
+	refs_for_each_ref(get_main_ref_store(repo),
+			  midx_snapshot_ref_one, &data);
+
+	if (close_tempfile_gently(f)) {
+		int save_errno = errno;
+		delete_tempfile(&f);
+		errno = save_errno;
+		die_errno(_("could not close refs snapshot tempfile"));
+	}
+
+	oidset_clear(&data.seen);
+}
diff --git a/repack.h b/repack.h
index cea7969ae4..803e129224 100644
--- a/repack.h
+++ b/repack.h
@@ -98,4 +98,8 @@ void pack_geometry_remove_redundant(struct pack_geometry *geometry,
 				    const char *packdir);
 void pack_geometry_release(struct pack_geometry *geometry);
 
+struct tempfile;
+
+void midx_snapshot_refs(struct repository *repo, struct tempfile *f);
+
 #endif /* REPACK_H */
-- 
2.51.0.243.g16eca91f2c0
Keyboard shortcuts
hback out one level
jnext message in thread
kprevious message in thread
ldrill in
Escclose help / fold thread tree
?toggle this help