When prepare_cmd() fails for, e.g., pager process setup, child_process_clear() frees the memory in pager_process.args, but .argv was pointed to pager_process.args.v earlier in start_command(), so it's now a dangling pointer. setup_pager() is then called a second time, from cmd_log_init_finish() in this case, and any further operations using its .argv, e.g. strvec_*, will use the dangling pointer and eventually crash. According to trivial tests, setup_pager() is not called twice if the first call is successful. This patch makes sure that pager_process is properly initialized on setup_pager(). Add a test to catch possible regressions. Reproducer: $ git config pager.show INVALID_PAGER $ git show $VALID_COMMIT error: cannot run INVALID_PAGER: No such file or directory [1] 3619 segmentation fault (core dumped) git show $VALID_COMMIT Signed-off-by: Enzo Matsumiya <ematsumiya@xxxxxxx> --- Changes to v2: - move child_process_init() to setup_pager(), as other callers of child_process_clear() might've not expected .argv to change - add a test case with the reproducer of the original bug Changes to v1: * Implement all of Jeff's suggestions: - remove double frees to .argv - discard the idea of falling back to DEFAULT_PAGER - replace memset() in child_process_clear() by child_process_init() - update/improve commit message pager.c | 2 ++ t/t7006-pager.sh | 5 +++++ 2 files changed, 7 insertions(+) diff --git a/pager.c b/pager.c index 52f27a6765c8..d93304527d62 100644 --- a/pager.c +++ b/pager.c @@ -124,6 +124,8 @@ void setup_pager(void) setenv("GIT_PAGER_IN_USE", "true", 1); + child_process_init(&pager_process); + /* spawn the pager */ prepare_pager_args(&pager_process, pager); pager_process.in = -1; diff --git a/t/t7006-pager.sh b/t/t7006-pager.sh index 0e7cf75435ec..0be9bcba49a8 100755 --- a/t/t7006-pager.sh +++ b/t/t7006-pager.sh @@ -786,4 +786,9 @@ test_expect_success TTY 'git returns SIGPIPE on propagated signals from pager' ' test_path_is_file pager-used ' +test_expect_success TTY 'handle attempt to run an invalid pager' ' + test_config pager.show invalid-pager && + test_terminal git show +' + test_done -- 2.33.1