Skip to content

Commit

Permalink
fsmonitor OSX: fix hangs for submodules
Browse files Browse the repository at this point in the history
fsmonitor_classify_path_absolute() expects state->path_gitdir_watch.buf
has no trailing '/' or '.' For a submodule, fsmonitor_run_daemon() sets
the value with trailing "/." (as repo_get_git_dir(the_repository) on
Darwin returns ".") so that fsmonitor_classify_path_absolute() returns
IS_OUTSIDE_CONE.

In this case, fsevent_callback() doesn't update cookie_list so that
fsmonitor_publish() does nothing and with_lock__mark_cookies_seen() is
not invoked.

As with_lock__wait_for_cookie() infinitely waits for state->cookies_cond
that with_lock__mark_cookies_seen() should unlock, the whole daemon
hangs.

Remove trailing "/." from state->path_gitdir_watch.buf for submodules
and add a corresponding test in t7527-builtin-fsmonitor.sh. The test is
disabled for MINGW because hangs treated with this patch occur only for
Darwin and there is no simple way to terminate the win32 fsmonitor
daemon that hangs.

Suggested-by: Johannes Schindelin <[email protected]>
Suggested-by: Junio C Hamano <[email protected]>
Signed-off-by: Koji Nakamaru <[email protected]>
Signed-off-by: Junio C Hamano <[email protected]>
  • Loading branch information
KojiNakamaru authored and gitster committed Oct 4, 2024
1 parent 3857aae commit 435a690
Show file tree
Hide file tree
Showing 2 changed files with 52 additions and 0 deletions.
1 change: 1 addition & 0 deletions builtin/fsmonitor--daemon.c
Original file line number Diff line number Diff line change
Expand Up @@ -1314,6 +1314,7 @@ static int fsmonitor_run_daemon(void)
strbuf_reset(&state.path_gitdir_watch);
strbuf_addstr(&state.path_gitdir_watch,
absolute_path(repo_get_git_dir(the_repository)));
strbuf_strip_suffix(&state.path_gitdir_watch, "/.");
state.nr_paths_watching = 2;
}

Expand Down
51 changes: 51 additions & 0 deletions t/t7527-builtin-fsmonitor.sh
Original file line number Diff line number Diff line change
Expand Up @@ -907,6 +907,57 @@ test_expect_success "submodule absorbgitdirs implicitly starts daemon" '
test_subcommand git fsmonitor--daemon start <super-sub.trace
'

start_git_in_background () {
git "$@" &
git_pid=$!
git_pgid=$(ps -o pgid= -p $git_pid)
nr_tries_left=10
while true
do
if test $nr_tries_left -eq 0
then
kill -- -$git_pgid
exit 1
fi
sleep 1
nr_tries_left=$(($nr_tries_left - 1))
done >/dev/null 2>&1 &
watchdog_pid=$!
wait $git_pid
}

stop_git () {
while kill -0 -- -$git_pgid
do
kill -- -$git_pgid
sleep 1
done
}

stop_watchdog () {
while kill -0 $watchdog_pid
do
kill $watchdog_pid
sleep 1
done
}

test_expect_success !MINGW "submodule implicitly starts daemon by pull" '
test_atexit "stop_watchdog" &&
test_when_finished "stop_git; rm -rf cloned super sub" &&
create_super super &&
create_sub sub &&
git -C super submodule add ../sub ./dir_1/dir_2/sub &&
git -C super commit -m "add sub" &&
git clone --recurse-submodules super cloned &&
git -C cloned/dir_1/dir_2/sub config core.fsmonitor true &&
set -m &&
start_git_in_background -C cloned pull --recurse-submodules
'

# On a case-insensitive file system, confirm that the daemon
# notices when the .git directory is moved/renamed/deleted
# regardless of how it is spelled in the FS event.
Expand Down

0 comments on commit 435a690

Please sign in to comment.