From 2bb426ce4a9cf890edafec5916bb6db8a0523975 Mon Sep 17 00:00:00 2001 From: zeertzjq Date: Wed, 6 May 2026 08:19:30 +0800 Subject: [PATCH] vim-patch:9.2.0443: GUI: cancelling save dialog overwrites or discards unnamed buffer (#39617) Problem: When closing gvim with an unsaved unnamed buffer, choosing "Yes" in the "Save changes?" dialog and then "Cancel" in the file selection dialog either silently writes the buffer to a file named "Untitled" (overwriting any existing file with that name) or discards the buffer altogether (vibs29, after v9.1.0265). Solution: In dialog_changed(), if browse_save_fname() leaves the buffer without a file name, treat it as a cancel and return without saving. Also stop clearing the modified flag in the restore path on write failure, so the unsaved changes are kept and the caller (e.g. gui_shell_closed()) can also cancel the close. Pre-fill the file dialog with "Untitled" to match the preceding "Save changes to ..." prompt. Add a test for the write-failure path (Hirohito Higashi). fixes: vim/vim#20132 closes: vim/vim#20143 https://github.com/vim/vim/commit/cf947e7ef09fc8a63f447b54b107585b8f3b7abe Co-authored-by: Hirohito Higashi --- src/nvim/ex_cmds2.c | 3 +-- test/old/testdir/test_buffer.vim | 22 ++++++++++++++++++++++ 2 files changed, 23 insertions(+), 2 deletions(-) diff --git a/src/nvim/ex_cmds2.c b/src/nvim/ex_cmds2.c index 22dd51b249..cfd71a114e 100644 --- a/src/nvim/ex_cmds2.c +++ b/src/nvim/ex_cmds2.c @@ -223,12 +223,11 @@ void dialog_changed(buf_T *buf, bool checkall) } } - // restore to empty when write failed + // restore to empty when write failed or was cancelled if (empty_bufname) { buf->b_fname = NULL; XFREE_CLEAR(buf->b_ffname); XFREE_CLEAR(buf->b_sfname); - unchanged(buf, true, false); } } else if (ret == VIM_NO) { unchanged(buf, true, false); diff --git a/test/old/testdir/test_buffer.vim b/test/old/testdir/test_buffer.vim index 997a952a14..e71907ff39 100644 --- a/test/old/testdir/test_buffer.vim +++ b/test/old/testdir/test_buffer.vim @@ -344,6 +344,28 @@ func Test_goto_buf_with_confirm() close! endfunc +" Test for issue #20132: when saving an unnamed buffer fails the modified +" flag must be kept, otherwise the buffer is silently discarded. +func Test_dialog_changed_keep_modified_on_write_fail() + CheckUnix + CheckNotGui + CheckFeature dialog_con + CheckNotFeature dialog_con_gui + CheckNotRoot + + call writefile(['existing'], 'Untitled', 'D') + call setfperm('Untitled', 'r--r--r--') + + new + call setline(1, 'test') + call feedkeys('y', 'L') + silent! confirm bdel + call assert_true(&modified) + call assert_equal(['existing'], readfile('Untitled')) + + bw! +endfunc + " Test for splitting buffer with 'switchbuf' func Test_buffer_switchbuf() new Xswitchbuf