]> git.ipfire.org Git - thirdparty/git.git/commitdiff
ref-filter: fix stale parsed objects
authorPatrick Steinhardt <ps@pks.im>
Tue, 4 Nov 2025 14:36:13 +0000 (15:36 +0100)
committerJunio C Hamano <gitster@pobox.com>
Tue, 4 Nov 2025 15:32:25 +0000 (07:32 -0800)
In 054f5f457e (ref-filter: parse objects on demand, 2025-10-23) we have
started to skip parsing some objects in case we don't need to access
their values in the first place. This was done by introducing a new
member `struct expand_data::maybe_object` that gets populated on demand
via `get_or_parse_object()`.

This has led to a regression though where the object now gets reused
because we don't reset it properly. The `oi` structure is declared in
global scope, and there is no single place where we reset it before
invoking `get_object()`. The consequence is that the `maybe_object`
member doesn't get reset across calls, so subsequent calls will end up
reusing the same object.

This is only an issue for a subset of retrieved values, as not all of
the infrastructure ends up calling `get_or_parse_object()`. So the
effect is limited, which is probably why the issue wasn't detected
earlier.

Fix the issue by resetting `maybe_object` in `get_object()`.

Reported-by: Junio C Hamano <gitster@pobox.com>
Based-on-patch-by: Jeff King <peff@peff.net>
Signed-off-by: Patrick Steinhardt <ps@pks.im>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
ref-filter.c
t/t7004-tag.sh

index 7cfcd5c35549308dcee9c3654c858f5ebce02a36..d8667c569a18f15ad67270351beb857ffd5b45a7 100644 (file)
@@ -2367,6 +2367,8 @@ static int get_object(struct ref_array_item *ref, int deref,
        int eaten = 0;
        int ret;
 
+       oi->maybe_object = NULL;
+
        if (oi->info.contentp) {
                /* We need to know that to use parse_object_buffer properly */
                oi->info.sizep = &oi->size;
index 10835631ca76444436fb5aef267082fb226b70c6..d1388cfdf45b02eae2bd6ee4b4a4dc315867fe70 100755 (executable)
@@ -2332,4 +2332,24 @@ test_expect_success 'If tag cannot be created then tag message file is not unlin
        test_path_exists .git/TAG_EDITMSG
 '
 
+test_expect_success 'annotated tag version sort' '
+       git tag -a -m "sample 1.0" vsample-1.0 &&
+       git tag -a -m "sample 2.0" vsample-2.0 &&
+       git tag -a -m "sample 10.0" vsample-10.0 &&
+       cat >expect <<-EOF &&
+       vsample-1.0
+       vsample-2.0
+       vsample-10.0
+       EOF
+
+       git tag --list --sort=version:tag vsample-\* >actual &&
+       test_cmp expect actual &&
+
+       # Ensure that we also handle this case alright in the case we have the
+       # peeled values cached e.g. via the packed-refs file.
+       git pack-refs --all &&
+       git tag --list --sort=version:tag vsample-\* &&
+       test_cmp expect actual
+'
+
 test_done