test_done
fi
+# Verify that the filesystem delivers events to the daemon.
+# On some configurations (e.g., overlayfs with older kernels),
+# inotify watches succeed but events are never delivered. The
+# cookie wait will time out and the daemon logs a trace message.
+#
+# Use "timeout" (if available) to guard each step against hangs.
+maybe_timeout () {
+ if type timeout >/dev/null 2>&1
+ then
+ timeout "$@"
+ else
+ shift
+ "$@"
+ fi
+}
+verify_fsmonitor_works () {
+ git init test_fsmonitor_smoke || return 1
+
+ GIT_TRACE_FSMONITOR="$PWD/smoke.trace" &&
+ export GIT_TRACE_FSMONITOR &&
+ maybe_timeout 30 \
+ git -C test_fsmonitor_smoke fsmonitor--daemon start \
+ --start-timeout=10
+ ret=$?
+ unset GIT_TRACE_FSMONITOR
+ if test $ret -ne 0
+ then
+ rm -rf test_fsmonitor_smoke smoke.trace
+ return 1
+ fi
+
+ maybe_timeout 10 \
+ test-tool -C test_fsmonitor_smoke fsmonitor-client query \
+ --token 0 >/dev/null 2>&1
+ maybe_timeout 5 \
+ git -C test_fsmonitor_smoke fsmonitor--daemon stop 2>/dev/null
+ ! grep -q "cookie_wait timed out" "$PWD/smoke.trace" 2>/dev/null
+ ret=$?
+ rm -rf test_fsmonitor_smoke smoke.trace
+ return $ret
+}
+
+if ! verify_fsmonitor_works
+then
+ skip_all="filesystem does not deliver fsmonitor events (container/overlayfs?)"
+ test_done
+fi
+
stop_daemon_delete_repo () {
r=$1 &&
- test_might_fail git -C $r fsmonitor--daemon stop &&
+ test_might_fail maybe_timeout 30 \
+ git -C $r fsmonitor--daemon stop 2>/dev/null
rm -rf $1
}
export GIT_TEST_FSMONITOR_TOKEN
fi &&
- git $r fsmonitor--daemon start &&
+ git $r fsmonitor--daemon start --start-timeout=10 &&
git $r fsmonitor--daemon status
)
}
grep "^event: dir1$" .git/trace
'
+test_expect_success 'rapid nested directory creation' '
+ test_when_finished "git fsmonitor--daemon stop; rm -rf rapid" &&
+
+ start_daemon --tf "$PWD/.git/trace" &&
+
+ # Rapidly create nested directories to exercise race conditions
+ # where directory watches may be added concurrently during
+ # event processing and recursive scanning.
+ for i in $(test_seq 1 20)
+ do
+ mkdir -p "rapid/nested/dir$i/subdir/deep" || return 1
+ done &&
+
+ # Give the daemon time to process all events
+ sleep 1 &&
+
+ test-tool fsmonitor-client query --token 0 &&
+
+ # Verify daemon is still running (did not crash)
+ git fsmonitor--daemon status
+'
+
# The next few test cases exercise the token-resync code. When filesystem
# drops events (because of filesystem velocity or because the daemon isn't
# polling fast enough), we need to discard the cached data (relative to the
start_git_in_background () {
git "$@" &
git_pid=$!
- git_pgid=$(ps -o pgid= -p $git_pid)
+ git_pgid=$(ps -o pgid= -p $git_pid 2>/dev/null ||
+ awk '{print $5}' /proc/$git_pid/stat 2>/dev/null) &&
+ git_pgid="${git_pgid## }" &&
+ git_pgid="${git_pgid%% }"
nr_tries_left=10
while true
do
fi
sleep 1
nr_tries_left=$(($nr_tries_left - 1))
- done >/dev/null 2>&1 &
+ done >/dev/null 2>&1 3>&- 4>&- 5>&- 6>&- 7>&- &
watchdog_pid=$!
wait $git_pid
}
stop_git () {
- while kill -0 -- -$git_pgid
+ test -n "$git_pgid" || return 0
+ while kill -0 -- -$git_pgid 2>/dev/null
do
- kill -- -$git_pgid
+ kill -- -$git_pgid 2>/dev/null
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" &&
+ test_when_finished "set +m; stop_git; rm -rf cloned super sub" &&
create_super super &&
create_sub sub &&