git/list[1] front-page[2] threads[3] people[4] search[5] about
 

Re: [RFC PATCH 0/3] grep: don'\''t add subrepos to in-memory alternates

From
Ævar Arnfjörð Bjarmason <avarab@gmail.com>
Date
Sep 27, 2021, 17:30 UTC
Message-ID
<87zgryylfx.fsf@evledraar.gmail.com>
In-Reply-To
<296230071f2cabda213b2a5f6f435f9308718569.1632754555.git.matheus.bernardino@usp.br>
On Mon, Sep 27 2021, Matheus Tavares wrote:
Show 179 quoted lines
> On Mon, Sep 27, 2021 at 9:09 AM Ævar Arnfjörð Bjarmason <avarab@gmail.com> wrote:
>>
>>
>> On Mon, Aug 16 2021, Jonathan Tan wrote:
>>
>> > Record the repository whenever an OID grep source is created, and teach
>> > the worker threads to explicitly provide the repository when accessing
>> > objects.
>> > [...]
>> > diff --git a/grep.h b/grep.h
>> > index 480b3f5bba..128007db65 100644
>> > --- a/grep.h
>> > +++ b/grep.h
>> > @@ -120,7 +120,20 @@ struct grep_opt {
>> >       struct grep_pat *header_list;
>> >       struct grep_pat **header_tail;
>> >       struct grep_expr *pattern_expression;
>> > +
>> > +     /*
>> > +      * NEEDSWORK: See if we can remove this field, because the repository
>> > +      * should probably be per-source. That is, grep.c functions using this
>> > +      * field should probably start using "repo" in "struct grep_source"
>> > +      * instead.
>> > +      *
>> > +      * This is potentially the cause of at least one bug - "git grep"
>> > +      * ignoring the textconv attributes from submodules. See [1] for more
>> > +      * information.
>> > +      * [1] https://lore.kernel.org/git/CAHd-oW5iEQarYVxEXoTG-ua2zdoybTrSjCBKtO0YT292fm0NQQ@mail.gmail.com/
>> > +      */
>> >       struct repository *repo;
>> > +
>>
>> I ran into this comment and read the linked E-Mail, and then the
>> downthread
>> https://lore.kernel.org/git/CAHd-oW6uG1fap-T4UF17bJmjoHAqWCDq9KbY+_8a3cEnnfATxg@mail.gmail.com/;
>>
>> Given Matheus's "I've somehow missed this guard and the..." there I'm
>> not quite sure what/if we should be doing here & what this comment is
>> recommending? I.e. do we still need to adjust the call chains as noted
>> in the E-Mail the comment links to, or not?
>
> I think we should still adjust the call chains, yes. The downthread
> message you mentioned is kind of a tangent about performance, where
> Junio helped me understand something I had previously missed in the
> code, regarding the persistence of the attributes stack.
>
> But the issue that started the thread was about a correctness problem:
> the superproject textconv attributes are being used on submodules'
> files when running `git grep` with `--recurse-submodules --textconv`.
> The three cases to consider are:
>
> - .gitattributes from the working tree
> - .gitattributes from the index
> - .git/info/attributes
>
> On all these cases, the superproject attributes are being used on the
> submodule. Additionally, if the superproject does not define any
> attribute, the submodule attributes are being ignored in all cases
> except by the first one (but that is only because the code sees the
> .gitattributes file on the submodule as if it were a "regular"
> subdirectory of the surperproject. So the submodule's .gitattribures
> takes higher precedence when evaluating the attributes for files in
> that directory).
>
> Another issue is that the textconv cache is always saved to (and read
> from) the superproject gitdir, even for submodules' files.
>
> Here are some test cases that demonstrate these issues:
>
> -- snipsnap --
> diff --git a/t/t7814-grep-recurse-submodules.sh b/t/t7814-grep-recurse-submodules.sh
> index 3172f5b936..d01a3bc5d8 100755
> --- a/t/t7814-grep-recurse-submodules.sh
> +++ b/t/t7814-grep-recurse-submodules.sh
> @@ -441,4 +441,104 @@ test_expect_success 'grep --recurse-submodules with --cached ignores worktree mo
>  	test_must_fail git grep --recurse-submodules --cached "A modified line in submodule" >actual 2>&1 &&
>  	test_must_be_empty actual
>  '
> +
> +test_expect_failure 'grep --textconv: superproject .gitattributes does not affect submodules' '
> +	reset_and_clean &&
> +	test_config_global diff.d2x.textconv "sed -e \"s/d/x/\"" &&
> +	echo "a diff=d2x" >.gitattributes &&
> +
> +	cat >expect <<-\EOF &&
> +	a:(1|2)x(3|4)
> +	EOF
> +	git grep --textconv --recurse-submodules x >actual &&
> +	test_cmp expect actual
> +'
> +
> +test_expect_failure 'grep --textconv: superproject .gitattributes (from index) does not affect submodules' '
> +	reset_and_clean &&
> +	test_config_global diff.d2x.textconv "sed -e \"s/d/x/\"" &&
> +	echo "a diff=d2x" >.gitattributes &&
> +	git add .gitattributes &&
> +	rm .gitattributes &&
> +
> +	cat >expect <<-\EOF &&
> +	a:(1|2)x(3|4)
> +	EOF
> +	git grep --textconv --recurse-submodules x >actual &&
> +	test_cmp expect actual
> +'
> +
> +test_expect_failure 'grep --textconv: superproject .git/info/attributes does not affect submodules' '
> +	reset_and_clean &&
> +	test_config_global diff.d2x.textconv "sed -e \"s/d/x/\"" &&
> +	super_attr="$(git rev-parse --path-format=relative --git-path info/attributes)" &&
> +	test_when_finished rm -f "$super_attr" &&
> +	echo "a diff=d2x" >"$super_attr" &&
> +
> +	cat >expect <<-\EOF &&
> +	a:(1|2)x(3|4)
> +	EOF
> +	git grep --textconv --recurse-submodules x >actual &&
> +	test_cmp expect actual
> +'
> +
> +test_expect_success 'grep --textconv corectly reads submodule .gitattributes' '
> +	reset_and_clean &&
> +	test_config_global diff.d2x.textconv "sed -e \"s/d/x/\"" &&
> +	echo "a diff=d2x" >submodule/.gitattributes &&
> +
> +	cat >expect <<-\EOF &&
> +	submodule/a:(1|2)x(3|4)
> +	EOF
> +	git grep --textconv --recurse-submodules x >actual &&
> +	test_cmp expect actual
> +'
> +
> +test_expect_failure 'grep --textconv corectly reads submodule .gitattributes (from index)' '
> +	reset_and_clean &&
> +	test_config_global diff.d2x.textconv "sed -e \"s/d/x/\"" &&
> +	echo "a diff=d2x" >submodule/.gitattributes &&
> +	git -C submodule add .gitattributes &&
> +	rm submodule/.gitattributes &&
> +
> +	cat >expect <<-\EOF &&
> +	submodule/a:(1|2)x(3|4)
> +	EOF
> +	git grep --textconv --recurse-submodules x >actual &&
> +	test_cmp expect actual
> +'
> +
> +test_expect_failure 'grep --textconv corectly reads submodule .git/info/attributes' '
> +	reset_and_clean &&
> +	test_config_global diff.d2x.textconv "sed -e \"s/d/x/\"" &&
> +
> +	# Workaround: we use --path-format=relative because the absolute path
> +	# contains whitespaces and that seems to confuse test_when_finished
> +	#
> +	submodule_attr="submodule/$(git -C submodule rev-parse --path-format=relative --git-path info/attributes)" &&
> +	test_when_finished rm -f "$submodule_attr" &&
> +	echo "a diff=d2x" >"$submodule_attr" &&
> +
> +	cat >expect <<-\EOF &&
> +	submodule/a:(1|2)x(3|4)
> +	EOF
> +	git grep --textconv --recurse-submodules x >actual &&
> +	test_cmp expect actual
> +'
> +
> +test_expect_failure 'grep saves textconv cache in the appropriated repository' '
> +	reset_and_clean &&
> +	test_config_global diff.d2x_cached.textconv "sed -e \"s/d/x/\"" &&
> +	test_config_global diff.d2x_cached.cachetextconv true &&
> +	echo "a diff=d2x_cached" >submodule/.gitattributes &&
> +
> +	# Note: we only read/write to the textconv cache when grepping from an
> +	# OID as the working tree file might have modifications. That is why
> +	# we use --cached here.
> +	#
> +	git grep --textconv --cached --recurse-submodules x &&
> +	test_path_is_missing "$(git rev-parse --git-path refs/notes/textconv/d2x_cached)" &&
> +	test_path_is_file "$(git -C submodule rev-parse --git-path refs/notes/textconv/d2x_cached)"
> +'
> +
>  test_done

Thanks! I think it would be very good to have these tests in-tree along with an updated comment pointing to them.

Previous: Matheus TavaresNext: Jonathan Tan
Message 65 of 71 in “In grep, no adding submodule ODB as alternates”
  1. 0/7 In grep, no adding submodule ODB as alternatesJonathan Tan, Aug 10, 2021
  2. 4/7 grep: read submodule entry with explicit repoJonathan Tan, Aug 10, 2021
  3. Emily ShafferAug 11, 2021
  4. Jonathan TanAug 13, 2021
  5. 3/7 grep: typesafe versions of grep_source_initJonathan Tan, Aug 10, 2021
  6. Junio C HamanoAug 10, 2021
  7. Emily ShafferAug 11, 2021
  8. Ramsay JonesAug 11, 2021
  9. Jonathan TanAug 13, 2021
  10. Matheus Tavares BernardinoAug 11, 2021
  11. Junio C HamanoAug 12, 2021
  12. Jonathan TanAug 13, 2021
  13. 2/7 grep: use submodule-ODB-as-alternate lazy-additionJonathan Tan, Aug 10, 2021
  14. Emily ShafferAug 11, 2021
  15. Jonathan TanAug 13, 2021
  16. 1/7 submodule: lazily add submodule ODBs as alternatesJonathan Tan, Aug 10, 2021
  17. Junio C HamanoAug 10, 2021
  18. Jonathan TanAug 13, 2021
  19. Emily ShafferAug 11, 2021
  20. Jonathan TanAug 13, 2021
  21. 5/7 grep: allocate subrepos on heapJonathan Tan, Aug 10, 2021
  22. Emily ShafferAug 11, 2021
  23. Jonathan TanAug 13, 2021
  24. 6/7 grep: add repository to OID grep sourcesJonathan Tan, Aug 10, 2021
  25. Emily ShafferAug 11, 2021
  26. Jonathan TanAug 13, 2021
  27. Matheus Tavares BernardinoAug 11, 2021
  28. Jonathan TanAug 13, 2021
  29. 7/7 t7814: show lack of alternate ODB-addingJonathan Tan, Aug 10, 2021
  30. Emily ShafferAug 11, 2021
  31. Matheus Tavares BernardinoAug 11, 2021
  32. Jonathan TanAug 13, 2021
  33. Emily ShafferAug 11, 2021
  34. Josh SteadmonAug 11, 2021
  35. 0/8 In grep, no adding submodule ODB as alternatesJonathan Tan, Aug 13, 2021
  36. 2/8 grep: use submodule-ODB-as-alternate lazy-additionJonathan Tan, Aug 13, 2021
  37. 1/8 submodule: lazily add submodule ODBs as alternatesJonathan Tan, Aug 13, 2021
  38. 3/8 grep: typesafe versions of grep_source_initJonathan Tan, Aug 13, 2021
  39. Matheus Tavares BernardinoAug 16, 2021
  40. 4/8 grep: read submodule entry with explicit repoJonathan Tan, Aug 13, 2021
  41. 5/8 grep: allocate subrepos on heapJonathan Tan, Aug 13, 2021
  42. Junio C HamanoAug 13, 2021
  43. Jonathan TanAug 16, 2021
  44. 6/8 grep: add repository to OID grep sourcesJonathan Tan, Aug 13, 2021
  45. Matheus Tavares BernardinoAug 16, 2021
  46. Jonathan TanAug 16, 2021
  47. 7/8 submodule-config: pass repo upon blob config readJonathan Tan, Aug 13, 2021
  48. Matheus Tavares BernardinoAug 16, 2021
  49. Matheus Tavares BernardinoAug 16, 2021
  50. Jonathan TanAug 16, 2021
  51. Matheus Tavares BernardinoAug 16, 2021
  52. Jonathan TanAug 16, 2021
  53. Jonathan TanAug 16, 2021
  54. 8/8 t7814: show lack of alternate ODB-addingJonathan Tan, Aug 13, 2021
  55. Matheus Tavares BernardinoAug 16, 2021
  56. 0/8 In grep, no adding submodule ODB as alternatesJonathan Tan, Aug 16, 2021
  57. 1/8 submodule: lazily add submodule ODBs as alternatesJonathan Tan, Aug 16, 2021
  58. 2/8 grep: use submodule-ODB-as-alternate lazy-additionJonathan Tan, Aug 16, 2021
  59. 3/8 grep: typesafe versions of grep_source_initJonathan Tan, Aug 16, 2021
  60. 4/8 grep: read submodule entry with explicit repoJonathan Tan, Aug 16, 2021
  61. 5/8 grep: allocate subrepos on heapJonathan Tan, Aug 16, 2021
  62. 6/8 grep: add repository to OID grep sourcesJonathan Tan, Aug 16, 2021
  63. Ævar Arnfjörð BjarmasonSep 27, 2021
  64. Matheus TavaresSep 27, 2021
  65. Ævar Arnfjörð BjarmasonSep 27, 2021
  66. 7/8 submodule-config: pass repo upon blob config readJonathan Tan, Aug 16, 2021
  67. 8/8 t7814: show lack of alternate ODB-addingJonathan Tan, Aug 16, 2021
  68. Matheus Tavares BernardinoAug 17, 2021
  69. Junio C HamanoSep 8, 2021
  70. Matheus Tavares BernardinoSep 8, 2021
  71. Junio C HamanoSep 8, 2021

Read the whole thread, see it on lore, or plain text.

$ cat FOOTERMessages come from the public archive at lore.kernel.org/git, fetched every hour. The front page is chosen and written each morning by an AI editor and can be wrong; the threads themselves are the record. About and API. For agents: an MCP server at https://gitlist.dev/mcp, and any thread, story or person page as Markdown by adding .md to its URL (or sending Accept: text/markdown). Details in /llms.txt.