commit-graph: replace packed_oid_list with oid_array

Our custom packed_oid_list data structure is really just an oid_array in disguise. Let's switch to using the generic structure, which shortens and simplifies the code slightly. There's one slightly awkward part: in the old code we copied a hash straight from the mmap'd on-disk data into the final object_id. And now we'll copy to a temporary oid, which we'll then pass to oid_array_append(). But this is an operation we have to do all over the commit-graph code already, since it mostly uses object_id structs internally. I also measured "git commit-graph --append", which triggers this code path, and it showed no difference. Signed-off-by: Jeff King <peff@peff.net> Signed-off-by: Junio C Hamano <gitster@pobox.com>

Jeff King committed Dec 7, 2020 at 14:11 UTC a5f1c448998fba5f5a1b00e1b9a779176ec665a6
1 file changed +15 -47
commit-graph.c
+15 -47
@@ -936,17 +936,11 @@ struct packed_commit_list {
936 int alloc;
937 };
938
939 -struct packed_oid_list {
940 - struct object_id *list;
941 - int nr;
942 - int alloc;
943 -};
944 -
939 struct write_commit_graph_context {
940 struct repository *r;
941 struct object_directory *odb;
942 char *graph_name;
949 - struct packed_oid_list oids;
943 + struct oid_array oids;
944 struct packed_commit_list commits;
945 int num_extra_edges;
946 unsigned long approx_nr_objects;
@@ -1240,13 +1234,6 @@ static int write_graph_chunk_bloom_data(struct hashfile *f,
1234 return 0;
1235 }
1236
1243 -static int oid_compare(const void *_a, const void *_b)
1244 -{
1245 - const struct object_id *a = (const struct object_id *)_a;
1246 - const struct object_id *b = (const struct object_id *)_b;
1247 - return oidcmp(a, b);
1248 -}
1249 -
1237 static int add_packed_commits(const struct object_id *oid,
1238 struct packed_git *pack,
1239 uint32_t pos,
@@ -1267,10 +1254,7 @@ static int add_packed_commits(const struct object_id *oid,
1254 if (type != OBJ_COMMIT)
1255 return 0;
1256
1270 - ALLOC_GROW(ctx->oids.list, ctx->oids.nr + 1, ctx->oids.alloc);
1271 - oidcpy(&(ctx->oids.list[ctx->oids.nr]), oid);
1272 - ctx->oids.nr++;
1273 -
1257 + oid_array_append(&ctx->oids, oid);
1258 set_commit_pos(ctx->r, oid);
1259
1260 return 0;
@@ -1281,9 +1265,7 @@ static void add_missing_parents(struct write_commit_graph_context *ctx, struct c
1265 struct commit_list *parent;
1266 for (parent = commit->parents; parent; parent = parent->next) {
1267 if (!(parent->item->object.flags & REACHABLE)) {
1284 - ALLOC_GROW(ctx->oids.list, ctx->oids.nr + 1, ctx->oids.alloc);
1285 - oidcpy(&ctx->oids.list[ctx->oids.nr], &(parent->item->object.oid));
1286 - ctx->oids.nr++;
1268 + oid_array_append(&ctx->oids, &parent->item->object.oid);
1269 parent->item->object.flags |= REACHABLE;
1270 }
1271 }
@@ -1302,7 +1284,7 @@ static void close_reachable(struct write_commit_graph_context *ctx)
1284 ctx->oids.nr);
1285 for (i = 0; i < ctx->oids.nr; i++) {
1286 display_progress(ctx->progress, i + 1);
1305 - commit = lookup_commit(ctx->r, &ctx->oids.list[i]);
1287 + commit = lookup_commit(ctx->r, &ctx->oids.oid[i]);
1288 if (commit)
1289 commit->object.flags |= REACHABLE;
1290 }
@@ -1319,7 +1301,7 @@ static void close_reachable(struct write_commit_graph_context *ctx)
1301 0);
1302 for (i = 0; i < ctx->oids.nr; i++) {
1303 display_progress(ctx->progress, i + 1);
1322 - commit = lookup_commit(ctx->r, &ctx->oids.list[i]);
1304 + commit = lookup_commit(ctx->r, &ctx->oids.oid[i]);
1305
1306 if (!commit)
1307 continue;
@@ -1339,7 +1321,7 @@ static void close_reachable(struct write_commit_graph_context *ctx)
1321 ctx->oids.nr);
1322 for (i = 0; i < ctx->oids.nr; i++) {
1323 display_progress(ctx->progress, i + 1);
1342 - commit = lookup_commit(ctx->r, &ctx->oids.list[i]);
1324 + commit = lookup_commit(ctx->r, &ctx->oids.oid[i]);
1325
1326 if (commit)
1327 commit->object.flags &= ~REACHABLE;
@@ -1567,9 +1549,7 @@ static int fill_oids_from_commits(struct write_commit_graph_context *ctx,
1549
1550 oidset_iter_init(commits, &iter);
1551 while ((oid = oidset_iter_next(&iter))) {
1570 - ALLOC_GROW(ctx->oids.list, ctx->oids.nr + 1, ctx->oids.alloc);
1571 - oidcpy(&ctx->oids.list[ctx->oids.nr], oid);
1572 - ctx->oids.nr++;
1552 + oid_array_append(&ctx->oids, oid);
1553 }
1554
1555 return 0;
@@ -1599,16 +1579,14 @@ static void copy_oids_to_commits(struct write_commit_graph_context *ctx)
1579 ctx->progress = start_delayed_progress(
1580 _("Finding extra edges in commit graph"),
1581 ctx->oids.nr);
1602 - QSORT(ctx->oids.list, ctx->oids.nr, oid_compare);
1603 - for (i = 0; i < ctx->oids.nr; i++) {
1582 + oid_array_sort(&ctx->oids);
1583 + for (i = 0; i < ctx->oids.nr; i = oid_array_next_unique(&ctx->oids, i)) {
1584 unsigned int num_parents;
1585
1586 display_progress(ctx->progress, i + 1);
1607 - if (i > 0 && oideq(&ctx->oids.list[i - 1], &ctx->oids.list[i]))
1608 - continue;
1587
1588 ALLOC_GROW(ctx->commits.list, ctx->commits.nr + 1, ctx->commits.alloc);
1611 - ctx->commits.list[ctx->commits.nr] = lookup_commit(ctx->r, &ctx->oids.list[i]);
1589 + ctx->commits.list[ctx->commits.nr] = lookup_commit(ctx->r, &ctx->oids.oid[i]);
1590
1591 if (ctx->split && flags != COMMIT_GRAPH_SPLIT_REPLACE &&
1592 commit_graph_position(ctx->commits.list[ctx->commits.nr]) != COMMIT_NOT_FROM_GRAPH)
@@ -2199,26 +2177,16 @@ int write_commit_graph(struct object_directory *odb,
2177 }
2178
2179 ctx->approx_nr_objects = approximate_object_count();
2202 - ctx->oids.alloc = ctx->approx_nr_objects / 32;
2180
2204 - if (ctx->split && opts && ctx->oids.alloc > opts->max_commits)
2205 - ctx->oids.alloc = opts->max_commits;
2206 -
2207 - if (ctx->append) {
2181 + if (ctx->append)
2182 prepare_commit_graph_one(ctx->r, ctx->odb);
2209 - if (ctx->r->objects->commit_graph)
2210 - ctx->oids.alloc += ctx->r->objects->commit_graph->num_commits;
2211 - }
2212 -
2213 - if (ctx->oids.alloc < 1024)
2214 - ctx->oids.alloc = 1024;
2215 - ALLOC_ARRAY(ctx->oids.list, ctx->oids.alloc);
2183
2184 if (ctx->append && ctx->r->objects->commit_graph) {
2185 struct commit_graph *g = ctx->r->objects->commit_graph;
2186 for (i = 0; i < g->num_commits; i++) {
2220 - const unsigned char *hash = g->chunk_oid_lookup + g->hash_len * i;
2221 - hashcpy(ctx->oids.list[ctx->oids.nr++].hash, hash);
2187 + struct object_id oid;
2188 + hashcpy(oid.hash, g->chunk_oid_lookup + g->hash_len * i);
2189 + oid_array_append(&ctx->oids, &oid);
2190 }
2191 }
2192
@@ -2274,7 +2242,7 @@ int write_commit_graph(struct object_directory *odb,
2242 cleanup:
2243 free(ctx->graph_name);
2244 free(ctx->commits.list);
2277 - free(ctx->oids.list);
2245 + oid_array_clear(&ctx->oids);
2246
2247 if (ctx->commit_graph_filenames_after) {
2248 for (i = 0; i < ctx->num_commit_graphs_after; i++) {