From 74722e3d16aaa40902387a00af77de98c174b723 Mon Sep 17 00:00:00 2001 From: Derrick Stolee Date: Mon, 21 Oct 2024 16:08:41 -0400 Subject: [PATCH] path-walk: add 'edge_aggressive' option Signed-off-by: Derrick Stolee --- Documentation/technical/api-path-walk.txt | 8 ++++++++ builtin/pack-objects.c | 3 ++- path-walk.c | 22 ++++++++++++++++++++++ path-walk.h | 7 +++++++ t/t5500-fetch-pack.sh | 13 +------------ 5 files changed, 40 insertions(+), 13 deletions(-) diff --git a/Documentation/technical/api-path-walk.txt b/Documentation/technical/api-path-walk.txt index 83bfe3d665e9fb..c25e7ede6a9652 100644 --- a/Documentation/technical/api-path-walk.txt +++ b/Documentation/technical/api-path-walk.txt @@ -65,6 +65,14 @@ better off using the revision walk API instead. the revision walk so that the walk emits commits marked with the `UNINTERESTING` flag. +`edge_aggressive`:: + For performance reasons, usually only the boundary commits are + explored to find UNINITERESTING objects. However, in the case of + shallow clones it can be helpful to mark all trees and blobs + reachable from UNINTERESTING tip commits as UNINTERESTING. This + matches the behavior of `--objects-edge-aggressive` in the + revision API. + `pl`:: This pattern list pointer allows focusing the path-walk search to a set of patterns, only emitting paths that match the given diff --git a/builtin/pack-objects.c b/builtin/pack-objects.c index 224c39caa40f11..43e10631653fb8 100644 --- a/builtin/pack-objects.c +++ b/builtin/pack-objects.c @@ -201,6 +201,7 @@ static int keep_unreachable, unpack_unreachable, include_tag; static timestamp_t unpack_unreachable_expiration; static int pack_loose_unreachable; static int cruft; +int shallow = 0; static timestamp_t cruft_expiration; static int local; static int have_non_local_packs; @@ -4438,6 +4439,7 @@ static void get_object_list_path_walk(struct rev_info *revs) * base objects. */ info.prune_all_uninteresting = sparse; + info.edge_aggressive = shallow; if (walk_objects_by_path(&info)) die(_("failed to pack objects via path-walk")); @@ -4627,7 +4629,6 @@ int cmd_pack_objects(int argc, struct repository *repo UNUSED) { int use_internal_rev_list = 0; - int shallow = 0; int all_progress_implied = 0; struct strvec rp = STRVEC_INIT; int rev_list_unpacked = 0, rev_list_all = 0, rev_list_reflog = 0; diff --git a/path-walk.c b/path-walk.c index c0be95922c1615..ca1a0da4fccb6a 100644 --- a/path-walk.c +++ b/path-walk.c @@ -280,6 +280,28 @@ int walk_objects_by_path(struct path_walk_info *info) if (prepare_revision_walk(info->revs)) die(_("failed to setup revision walk")); + if (info->edge_aggressive) { + for (struct commit_list *list = info->revs->commits; + list; + list = list->next) { + struct commit *commit = list->item; + if (commit->object.flags & UNINTERESTING) { + struct tree *t = repo_get_commit_tree(info->revs->repo, commit); + mark_tree_uninteresting(info->revs->repo, t); + if (!(commit->object.flags & SHOWN)) + commit->object.flags |= SHOWN; + } + } + for (size_t i = 0; i < info->revs->cmdline.nr; i++) { + struct object *obj = info->revs->cmdline.rev[i].item; + struct commit *commit = (struct commit *)obj; + if (obj->type != OBJ_COMMIT || !(obj->flags & UNINTERESTING)) + continue; + mark_tree_uninteresting(info->revs->repo, + repo_get_commit_tree(info->revs->repo, commit)); + } + } + info->revs->blob_objects = info->revs->tree_objects = 0; if (info->tags) { diff --git a/path-walk.h b/path-walk.h index 090cda3b5cf8f4..6f23f16c6fb084 100644 --- a/path-walk.h +++ b/path-walk.h @@ -48,6 +48,13 @@ struct path_walk_info { */ int prune_all_uninteresting; + /** + * When 'edge_aggressive' is set, then the revision walk will use + * the '--object-edge-aggressive' option to mark even more objects + * as uniniteresting. + */ + int edge_aggressive; + /** * Specify a sparse-checkout definition to match our paths to. Do not * walk outside of this sparse definition. If the patterns are in diff --git a/t/t5500-fetch-pack.sh b/t/t5500-fetch-pack.sh index 32746678e3b629..c29d6c4adc0666 100755 --- a/t/t5500-fetch-pack.sh +++ b/t/t5500-fetch-pack.sh @@ -464,17 +464,6 @@ test_expect_success 'fetch in shallow repo unreachable shallow objects' ' ) ' -# At the moment, the --path-walk option may provide more objects -# when combined with --shallow than the --no-path-walk option. -if test_bool_env GIT_TEST_PACK_PATH_WALK false -then - EXPECTED_SHALLOW_OBJECTS=3 && - export EXPECTED_SHALLOW_OBJECTS -else - EXPECTED_SHALLOW_OBJECTS=1 && - export EXPECTED_SHALLOW_OBJECTS -fi - test_expect_success 'fetch creating new shallow root' ' ( git clone "file://$(pwd)/." shallow10 && @@ -483,7 +472,7 @@ test_expect_success 'fetch creating new shallow root' ' git fetch --depth=1 --progress 2>actual && # This should fetch only the empty commit, no tree or # blob objects - test_grep "remote: Total $EXPECTED_SHALLOW_OBJECTS" actual + test_grep "remote: Total 1" actual ) '