vim-patch:8.2.4609: :unhide does not check for failing to close a window

Problem:    :unhide does not check for failing to close a window.
Solution:   When closing a window fails continue with the next one.  Do not
            try closing the autocmd window. (closes vim/vim#9984)

6f2465d336

Co-authored-by: Bram Moolenaar <Bram@vim.org>
(cherry picked from commit 6c4ef7eca6)
This commit is contained in:
zeertzjq 2023-09-23 10:33:52 +08:00 committed by github-actions[bot]
parent 94246472e3
commit b3b30dbaf7
3 changed files with 27 additions and 10 deletions

View File

@ -1482,7 +1482,6 @@ void aucmd_restbuf(aco_save_T *aco)
if (aco->use_aucmd_win_idx >= 0) { if (aco->use_aucmd_win_idx >= 0) {
win_T *awp = aucmd_win[aco->use_aucmd_win_idx].auc_win; win_T *awp = aucmd_win[aco->use_aucmd_win_idx].auc_win;
curbuf->b_nwindows--;
// Find "awp", it can't be closed, but it may be in another tab page. // Find "awp", it can't be closed, but it may be in another tab page.
// Do not trigger autocommands here. // Do not trigger autocommands here.
block_autocmds(); block_autocmds();
@ -1498,7 +1497,7 @@ void aucmd_restbuf(aco_save_T *aco)
} }
} }
win_found: win_found:
; curbuf->b_nwindows--;
const bool save_stop_insert_mode = stop_insert_mode; const bool save_stop_insert_mode = stop_insert_mode;
// May need to stop Insert mode if we were in a prompt buffer. // May need to stop Insert mode if we were in a prompt buffer.
leaving_window(curwin); leaving_window(curwin);

View File

@ -3619,12 +3619,15 @@ void ex_buffer_all(exarg_T *eap)
: wp->w_width != Columns) : wp->w_width != Columns)
|| (had_tab > 0 && wp != firstwin)) || (had_tab > 0 && wp != firstwin))
&& !ONE_WINDOW && !ONE_WINDOW
&& !(wp->w_closing && !(wp->w_closing || wp->w_buffer->b_locked > 0)
|| wp->w_buffer->b_locked > 0)) { && !is_aucmd_win(wp)) {
win_close(wp, false, false); if (win_close(wp, false, false) == FAIL) {
wpnext = firstwin; // just in case an autocommand does break;
// something strange with windows }
tpnext = first_tabpage; // start all over... // Just in case an autocommand does something strange with
// windows: start all over...
wpnext = firstwin;
tpnext = first_tabpage;
open_wins = 0; open_wins = 0;
} else { } else {
open_wins++; open_wins++;
@ -3644,7 +3647,7 @@ void ex_buffer_all(exarg_T *eap)
// //
// Don't execute Win/Buf Enter/Leave autocommands here. // Don't execute Win/Buf Enter/Leave autocommands here.
autocmd_no_enter++; autocmd_no_enter++;
win_enter(lastwin, false); win_enter(lastwin_nofloating(), false);
autocmd_no_leave++; autocmd_no_leave++;
for (buf = firstbuf; buf != NULL && open_wins < count; buf = buf->b_next) { for (buf = firstbuf; buf != NULL && open_wins < count; buf = buf->b_next) {
// Check if this buffer needs a window // Check if this buffer needs a window
@ -3736,7 +3739,7 @@ void ex_buffer_all(exarg_T *eap)
// Close superfluous windows. // Close superfluous windows.
for (wp = lastwin; open_wins > count;) { for (wp = lastwin; open_wins > count;) {
r = (buf_hide(wp->w_buffer) || !bufIsChanged(wp->w_buffer) r = (buf_hide(wp->w_buffer) || !bufIsChanged(wp->w_buffer)
|| autowrite(wp->w_buffer, false) == OK); || autowrite(wp->w_buffer, false) == OK) && !is_aucmd_win(wp);
if (!win_valid(wp)) { if (!win_valid(wp)) {
// BufWrite Autocommands made the window invalid, start over // BufWrite Autocommands made the window invalid, start over
wp = lastwin; wp = lastwin;

View File

@ -4,6 +4,7 @@ source shared.vim
source check.vim source check.vim
source term_util.vim source term_util.vim
source screendump.vim source screendump.vim
source vim9.vim
source load.vim source load.vim
func s:cleanup_buffers() abort func s:cleanup_buffers() abort
@ -3416,6 +3417,20 @@ func Test_autocmd_vimgrep()
augroup END augroup END
endfunc endfunc
func Test_closing_autocmd_window()
let lines =<< trim END
edit Xa.txt
tabnew Xb.txt
autocmd BufEnter Xa.txt unhide 1
doautoall BufEnter
END
call CheckScriptFailure(lines, 'E814:')
au! BufEnter
only!
bwipe Xa.txt
bwipe Xb.txt
endfunc
func Test_bufwipeout_changes_window() func Test_bufwipeout_changes_window()
" This should not crash, but we don't have any expectations about what " This should not crash, but we don't have any expectations about what
" happens, changing window in BufWipeout has unpredictable results. " happens, changing window in BufWipeout has unpredictable results.