Skip to content

Conversation

To1ne
Copy link

@To1ne To1ne commented Sep 4, 2025

git-last-modified(1) was recently merged into 'next', but upon use
I've[1] noticed it has a bug:

$ git last-modified
3f3e11118993fe0500b3957ab798e39caaa3952f	.gitignore
3f3e11118993fe0500b3957ab798e39caaa3952f	Makefile
3f3e11118993fe0500b3957ab798e39caaa3952f	builtin.h
3f3e11118993fe0500b3957ab798e39caaa3952f	command-list.txt
3f3e11118993fe0500b3957ab798e39caaa3952f	commit-graph.c
3f3e11118993fe0500b3957ab798e39caaa3952f	git.c
3f3e11118993fe0500b3957ab798e39caaa3952f	meson.build
56072ff0384da5d874fc378d36e089a18f28f1e3	fetch-pack.c
457534d0417d047b943f76a849f256b739894ce9	progress.c
0d8f4ccfe3b13bb5eb95f030dc5fe76efb255397	for-each-ref.h
109c3df14ccf372c2438a470bdfb566265399f0a	combine-diff.c
109c3df14ccf372c2438a470bdfb566265399f0a	diff.c
109c3df14ccf372c2438a470bdfb566265399f0a	diff.h
109c3df14ccf372c2438a470bdfb566265399f0a	dir.c
9e5878fbede57c0499133adf73844261849cd7b2	git-web--browse.sh
b2fb3911eab730a08168c7f85a7935ad5a330b53	config.mak.in
36268b762c4aa6a0d4831f69852b20ab545aff4d	LGPL-2.1
1e58dba142c673c59fbb9d10aeecf62217d4fc9c	aclocal.m4
9517e6b84357252e1882091343661c34d978771e	levenshtein.h
703601d6780c32d33dadf19b2b367f2f79e1e34c	COPYING
BUG: ../builtin/last-modified.c:236: paths remaining beyond boundary in last-modified
zsh: IOT instruction (core dumped)  git last-modified

I didn't see this before but the BUG() statement was only moved up in
the last version of the patch series, and it only comes into trouble
with merge commits.

This series fixes that issue.

This patch is based on 'next' at 1ba7204 (Merge branch
'kh/doc-markup-fixes' into next, 2025-09-03).

git-last-modified(1) was recently merged into 'next', but upon use
I've[1] noticed it has a bug:

    $ git last-modified
    3f3e111	.gitignore
    3f3e111	Makefile
    3f3e111	builtin.h
    3f3e111	command-list.txt
    3f3e111	commit-graph.c
    3f3e111	git.c
    3f3e111	meson.build
    56072ff	fetch-pack.c
    457534d	progress.c
    0d8f4cc	for-each-ref.h
    109c3df	combine-diff.c
    109c3df	diff.c
    109c3df	diff.h
    109c3df	dir.c
    9e5878f	git-web--browse.sh
    b2fb391	config.mak.in
    36268b7	LGPL-2.1
    1e58dba	aclocal.m4
    9517e6b	levenshtein.h
    703601d	COPYING
    BUG: ../builtin/last-modified.c:236: paths remaining beyond boundary in last-modified
    zsh: IOT instruction (core dumped)  git last-modified

I didn't see this before but the BUG() statement was only moved up in
the last version of the patch series, and it only comes into trouble
with merge commits.

This series fixes that issue.

This patch is based on 'next' at 1ba7204 (Merge branch
'kh/doc-markup-fixes' into next, 2025-09-03).

--- b4-submit-tracking ---
# This section is used internally by b4 prep for tracking purposes.
{
  "series": {
    "revision": 1,
    "change-id": "20250902-toon-fix-last-modified-865172060265",
    "prefixes": []
  }
}
Function diff_tree_combined() copies the 'struct diff_options' from the
input 'struct rev_info' to override some flags. One flag was
'recursive', which is set to 1. This has been the case since the
inception of this function in af3feef (diff-tree -c: show a merge
commit a bit more sensibly., 2006-01-24). From that commit there's no
clear indication why recursive is overridden. But it seems to be
incorrect.

Looking at a test case in t4013. The expected test results are in
t/t4013/. And take 'diff.noellipses-diff-tree_-c_--abbrev_master' as an
example:

   $ git diff-tree -c --abbrev master
   59d314ad6f356dd08601a4cd5e530381da3e3c64
   ::100644 100644 100644 cead32e 7289e35 992913c MM	dir/sub
   ::100644 100644 100644 b414108 f4615da 10a8a9f MM	file0
   $

Here we see the expected results include 'dir/sub', while argument
'-r' (for recursive) was not given. So we should expect 'dir' instead.

Stop overriding the 'recursive' flag in diff_tree_combined(). This
changes the expected results for the example above to be:

    $ git diff-tree -c --abbrev master
    59d314ad6f356dd08601a4cd5e530381da3e3c64
    ::040000 040000 040000 65f5c9d f977ed4 0564e02 MM	dir
    ::100644 100644 100644 b414108 f4615da 10a8a9f MM	file0
    $

This also fixes the recently added subcommand git-last-modified(1),
which in some cases (when merges are involved) exited with the error:

    BUG: paths remaining beyond boundary in last-modified

The last-modified machinery uses a hashmap for all the files it wants to
get the last-modified commit for. Through log_tree_commit() the callback
mark_path() is called. Here the incoming path is looked up in the
hashmap, but because the diff-tree machinery internally switched to
recursive (even if the last-modified machinery wasn't) the entry for
'dir' was never expelled from the hashmap, and the BUG() statement was
hit.

Because internally diff-tree no longer runs recursive, this results in a
nice speedup when running `git last-modified` on git.git:

    Benchmark 1: next
      Time (mean ± σ):      6.068 s ±  0.038 s    [User: 5.268 s, System: 0.187 s]
      Range (min … max):    6.007 s …  6.123 s    10 runs

    Benchmark 2: HEAD
      Time (mean ± σ):      3.057 s ±  0.009 s    [User: 2.996 s, System: 0.055 s]
      Range (min … max):    3.047 s …  3.070 s    10 runs

    Summary
      HEAD ran
        1.98 ± 0.01 times faster than next

Besides that, set the flag 'recursive' in submodule.c to 1 because it
calls diff_tree_combined_merge() which no longer enables the flag
itself.

Signed-off-by: Toon Claes <[email protected]>
Copy link

gitgitgadget bot commented Sep 4, 2025

There are issues in commit b0a9f07:
Fix git-last-modified(1)
Commit not signed off

@dscho
Copy link
Member

dscho commented Sep 4, 2025

CI / win+Meson test (4) (pull_request)
CI / win+Meson test (4) (pull_request)Failing after 8m

Isn't it nice that the full log is written to D:\a\git\git\build\meson-logs\testlog.txt? I am sure it felt right at home there, at peace, with nobody touching it before it went into the great abyss when the runner VM was terminated. I guess we will never know what was written into that file.

@To1ne
Copy link
Author

To1ne commented Sep 6, 2025

I know enough. Let's close.

@To1ne To1ne closed this Sep 6, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants