patch 9.2.0182: autocmds may leave windows with w_locked set

Problem:  autocmds that switch windows may cause them to remain with
          w_locked set, preventing them from being closed longer than
          intended.
Solution: Unset w_locked in the window where it was set (Sean Dewar).

closes: #19716

Signed-off-by: Sean Dewar <6256228+seandewar@users.noreply.github.com>
Signed-off-by: Christian Brabandt <cb@256bit.org>
This commit is contained in:
Sean Dewar
2026-03-16 21:54:28 +00:00
committed by Christian Brabandt
parent 955d28799b
commit bae31c35bb
4 changed files with 38 additions and 10 deletions
+11 -7
View File
@@ -193,12 +193,14 @@ alist_add(
char_u *fname,
int set_fnum) // 1: set buffer number; 2: re-use curbuf
{
win_T *wp = curwin;
if (fname == NULL) // don't add NULL file names
return;
if (check_arglist_locked() == FAIL)
return;
arglist_locked = TRUE;
curwin->w_locked = TRUE;
wp->w_locked = TRUE;
#ifdef BACKSLASH_IN_FILENAME
slash_adjust(fname);
@@ -210,7 +212,7 @@ alist_add(
++al->al_ga.ga_len;
arglist_locked = FALSE;
curwin->w_locked = FALSE;
wp->w_locked = FALSE;
}
#if defined(BACKSLASH_IN_FILENAME)
@@ -361,6 +363,8 @@ alist_add_list(
if (check_arglist_locked() != FAIL
&& GA_GROW_OK(&ALIST(curwin)->al_ga, count))
{
win_T *wp = curwin;
if (after < 0)
after = 0;
if (after > ARGCOUNT)
@@ -369,7 +373,7 @@ alist_add_list(
mch_memmove(&(ARGLIST[after + count]), &(ARGLIST[after]),
(ARGCOUNT - after) * sizeof(aentry_T));
arglist_locked = TRUE;
curwin->w_locked = TRUE;
wp->w_locked = TRUE;
for (i = 0; i < count; ++i)
{
int flags = BLN_LISTED | (will_edit ? BLN_CURBUF : 0);
@@ -378,10 +382,10 @@ alist_add_list(
ARGLIST[after + i].ae_fnum = buflist_add(files[i], flags);
}
arglist_locked = FALSE;
curwin->w_locked = FALSE;
ALIST(curwin)->al_ga.ga_len += count;
if (old_argcount > 0 && curwin->w_arg_idx >= after)
curwin->w_arg_idx += count;
wp->w_locked = FALSE;
ALIST(wp)->al_ga.ga_len += count;
if (old_argcount > 0 && wp->w_arg_idx >= after)
wp->w_arg_idx += count;
return;
}
+5 -3
View File
@@ -3730,14 +3730,16 @@ term_after_channel_closed(term_T *term)
aucmd_prepbuf(&aco, term->tl_buffer);
if (curbuf == term->tl_buffer)
{
win_T *wp = curwin;
// Avoid closing the window if we temporarily use it.
if (is_aucmd_win(curwin))
if (is_aucmd_win(wp))
do_set_w_locked = TRUE;
if (do_set_w_locked)
curwin->w_locked = TRUE;
wp->w_locked = TRUE;
do_bufdel(DOBUF_WIPE, (char_u *)"", 1, fnum, fnum, FALSE);
if (do_set_w_locked)
curwin->w_locked = FALSE;
wp->w_locked = FALSE;
aucmd_restbuf(&aco);
}
#ifdef FEAT_PROP_POPUP
+20
View File
@@ -798,4 +798,24 @@ func Test_crash_arglist_uaf2()
au! BufAdd
endfunc
func Test_arglist_w_locked_unlock()
au BufAdd * split
args a
call assert_equal(2, winnr('$'))
wincmd p
quit
call assert_equal(1, winnr('$'))
argedit b
call assert_equal(2, winnr('$'))
wincmd p
quit
call assert_equal(1, winnr('$'))
%argd
%bw!
au! BufAdd
endfunc
" vim: shiftwidth=2 sts=2 expandtab
+2
View File
@@ -734,6 +734,8 @@ static char *(features[]) =
static int included_patches[] =
{ /* Add new patch number below this line */
/**/
182,
/**/
181,
/**/