Compare commits

...

9 Commits

Author SHA1 Message Date
Bram Moolenaar
df2c2988bb patch 8.2.2425: cursor on invalid line with range and :substitute
Problem:    Cursor on invalid line with range and :substitute.
Solution:   Do not move the cursor when skipping commands. (closes #3434)
2021-01-28 20:18:08 +01:00
Bram Moolenaar
97202d9516 patch 8.2.2424: some tests are known to cause an error with ASAN
Problem:    Some tests are known to cause an error with ASAN.
Solution:   Add CheckNotAsan.
2021-01-28 18:34:35 +01:00
Bram Moolenaar
61015162ba patch 8.2.2423: missing error message
Problem:    Missing error message.
Solution:   Add the error message.
2021-01-28 17:56:09 +01:00
Bram Moolenaar
1d859e2421 patch 8.2.2422: crash when deleting with line number out of range
Problem:    Crash when deleting with line number out of range. (Houyunsong)
Solution:   Avoid using a negative line number.
2021-01-28 17:24:58 +01:00
Bram Moolenaar
5ed58c7b70 patch 8.2.2421: double free when using autocommand with "argdel"
Problem:    Double free when using autocommand with "argdel". (Houyunsong)
Solution:   Add the arglist_locked flag.
2021-01-28 14:24:55 +01:00
Bram Moolenaar
9a046fd08b patch 8.2.2420: too many problems with using all autocommand events
Problem:    Too many problems with using all autocommand events.
Solution:   Disallow defining an autocommand for all events.
2021-01-28 13:47:59 +01:00
Bram Moolenaar
d697ddea14 patch 8.2.2419: autocmd test was failing on MS-Windows with GUI
Problem:    Autocmd test was failing on MS-Windows with GUI.
Solution:   Remove stray feedkeys().
2021-01-28 12:08:35 +01:00
Bram Moolenaar
2e6cdb91e8 patch 8.2.2418: color not changed if ModeMsg highlight is set in InsertEnter
Problem:    Color not changed if ModeMsg highlight is set in InsertEnter
            autocmd event. (Paul Swanson)
Solution:   Call highlight_changed() after triggering InsertEnter.
            (closes #7751)
2021-01-28 11:07:44 +01:00
Bram Moolenaar
3e492c2d5f patch 8.2.2417: condition stack values may be used when not set
Problem:    Condition stack values may be used when not set.
Solution:   Clear cs_script_var_len and cs_block_id just in case they get used
            later. (issue #7733)
2021-01-27 21:37:13 +01:00
16 changed files with 159 additions and 66 deletions

View File

@@ -17,12 +17,29 @@
#define AL_ADD 2
#define AL_DEL 3
// This flag is set whenever the argument list is being changed and calling a
// function that might trigger an autocommand.
static int arglist_locked = FALSE;
static int
check_arglist_locked(void)
{
if (arglist_locked)
{
emsg(_(e_cannot_change_arglist_recursively));
return FAIL;
}
return OK;
}
/*
* Clear an argument list: free all file names and reset it to zero entries.
*/
void
alist_clear(alist_T *al)
{
if (check_arglist_locked() == FAIL)
return;
while (--al->al_ga.ga_len >= 0)
vim_free(AARGLIST(al)[al->al_ga.ga_len].ae_fname);
ga_clear(&al->al_ga);
@@ -126,14 +143,9 @@ alist_set(
int fnum_len)
{
int i;
static int recursive = 0;
if (recursive)
{
emsg(_(e_au_recursive));
if (check_arglist_locked() == FAIL)
return;
}
++recursive;
alist_clear(al);
if (ga_grow(&al->al_ga, count) == OK)
@@ -152,7 +164,11 @@ alist_set(
// May set buffer name of a buffer previously used for the
// argument list, so that it's re-used by alist_add.
if (fnum_list != NULL && i < fnum_len)
{
arglist_locked = TRUE;
buf_set_name(fnum_list[i], files[i]);
arglist_locked = FALSE;
}
alist_add(al, files[i], use_curbuf ? 2 : 1);
ui_breakcheck();
@@ -163,8 +179,6 @@ alist_set(
FreeWild(count, files);
if (al == &global_alist)
arg_had_last = FALSE;
--recursive;
}
/*
@@ -179,6 +193,10 @@ alist_add(
{
if (fname == NULL) // don't add NULL file names
return;
if (check_arglist_locked() == FAIL)
return;
arglist_locked = TRUE;
#ifdef BACKSLASH_IN_FILENAME
slash_adjust(fname);
#endif
@@ -187,6 +205,8 @@ alist_add(
AARGLIST(al)[al->al_ga.ga_len].ae_fnum =
buflist_add(fname, BLN_LISTED | (set_fnum == 2 ? BLN_CURBUF : 0));
++al->al_ga.ga_len;
arglist_locked = FALSE;
}
#if defined(BACKSLASH_IN_FILENAME) || defined(PROTO)
@@ -334,7 +354,8 @@ alist_add_list(
int i;
int old_argcount = ARGCOUNT;
if (ga_grow(&ALIST(curwin)->al_ga, count) == OK)
if (check_arglist_locked() != FAIL
&& ga_grow(&ALIST(curwin)->al_ga, count) == OK)
{
if (after < 0)
after = 0;
@@ -343,6 +364,7 @@ alist_add_list(
if (after < ARGCOUNT)
mch_memmove(&(ARGLIST[after + count]), &(ARGLIST[after]),
(ARGCOUNT - after) * sizeof(aentry_T));
arglist_locked = TRUE;
for (i = 0; i < count; ++i)
{
int flags = BLN_LISTED | (will_edit ? BLN_CURBUF : 0);
@@ -350,6 +372,7 @@ alist_add_list(
ARGLIST[after + i].ae_fname = files[i];
ARGLIST[after + i].ae_fnum = buflist_add(files[i], flags);
}
arglist_locked = FALSE;
ALIST(curwin)->al_ga.ga_len += count;
if (old_argcount > 0 && curwin->w_arg_idx >= after)
curwin->w_arg_idx += count;
@@ -382,6 +405,9 @@ do_arglist(
int match;
int arg_escaped = TRUE;
if (check_arglist_locked() == FAIL)
return FAIL;
// Set default argument for ":argadd" command.
if (what == AL_ADD && *str == NUL)
{
@@ -776,6 +802,9 @@ ex_argdelete(exarg_T *eap)
int i;
int n;
if (check_arglist_locked() == FAIL)
return;
if (eap->addr_count > 0 || *eap->arg == NUL)
{
// ":argdel" works like ":.argdel"

View File

@@ -956,11 +956,14 @@ do_autocmd(char_u *arg_in, int forceit)
last_group = AUGROUP_ERROR; // for listing the group name
if (*arg == '*' || *arg == NUL || *arg == '|')
{
for (event = (event_T)0; (int)event < (int)NUM_EVENTS;
event = (event_T)((int)event + 1))
if (do_autocmd_event(event, pat,
once, nested, cmd, forceit, group) == FAIL)
break;
if (!forceit && *cmd != NUL)
emsg(_(e_cannot_define_autocommands_for_all_events));
else
for (event = (event_T)0; (int)event < (int)NUM_EVENTS;
event = (event_T)((int)event + 1))
if (do_autocmd_event(event, pat,
once, nested, cmd, forceit, group) == FAIL)
break;
}
else
{

View File

@@ -196,6 +196,10 @@ edit(
#endif
ins_apply_autocmds(EVENT_INSERTENTER);
// Check for changed highlighting, e.g. for ModeMsg.
if (need_highlight_changed)
highlight_changed();
// Make sure the cursor didn't move. Do call check_cursor_col() in
// case the text was modified. Since Insert mode was not started yet
// a call to check_cursor_col() may move the cursor, especially with

View File

@@ -345,3 +345,7 @@ EXTERN char e_invalid_operation_for_bool[]
INIT(= N_("E1153: Invalid operation for bool"));
EXTERN char e_divide_by_zero[]
INIT(= N_("E1154: Divide by zero"));
EXTERN char e_cannot_define_autocommands_for_all_events[]
INIT(= N_("E1155: Cannot define autocommands for ALL events"));
EXTERN char e_cannot_change_arglist_recursively[]
INIT(= N_("E1156: Cannot change the argument list recursively"));

View File

@@ -3747,6 +3747,8 @@ ex_substitute(exarg_T *eap)
{
linenr_T joined_lines_count;
if (eap->skip)
return;
curwin->w_cursor.lnum = eap->line1;
if (*cmd == 'l')
eap->flags = EXFLAG_LIST;

View File

@@ -920,6 +920,13 @@ enter_block(cstack_T *cstack)
cstack->cs_block_id[cstack->cs_idx] = ++si->sn_last_block_id;
si->sn_current_block_id = si->sn_last_block_id;
}
else
{
// Just in case in_vim9script() does not return the same value when the
// block ends.
cstack->cs_script_var_len[cstack->cs_idx] = 0;
cstack->cs_block_id[cstack->cs_idx] = 0;
}
}
static void

View File

@@ -630,7 +630,7 @@ getcount:
}
else
ca.count0 = ca.count0 * 10 + (c - '0');
if (ca.count0 < 0) // got too large!
if (ca.count0 < 0) // overflow
ca.count0 = 999999999L;
#ifdef FEAT_EVAL
// Set v:count here, when called from main() and not a stuffed
@@ -701,6 +701,8 @@ getcount:
ca.count0 *= ca.opcount;
else
ca.count0 = ca.opcount;
if (ca.count0 < 0) // overflow
ca.count0 = 999999999L;
}
/*
@@ -4775,6 +4777,8 @@ nv_percent(cmdarg_T *cap)
else
curwin->w_cursor.lnum = (curbuf->b_ml.ml_line_count *
cap->count0 + 99L) / 100L;
if (curwin->w_cursor.lnum < 1)
curwin->w_cursor.lnum = 1;
if (curwin->w_cursor.lnum > curbuf->b_ml.ml_line_count)
curwin->w_cursor.lnum = curbuf->b_ml.ml_line_count;
beginline(BL_SOL | BL_FIX);

View File

@@ -183,4 +183,12 @@ func s:CheckIPv6Loopback()
return v:false
endfunc
" Command to check for not running under ASAN
command CheckNotAsan call CheckNotAsan()
func CheckNotAsan()
if execute('version') =~# '-fsanitize=[a-z,]*\<address\>'
throw 'Skipped: does not work with ASAN'
endif
endfunc
" vim: shiftwidth=2 sts=2 expandtab

View File

@@ -173,6 +173,12 @@ func Test_autocmd_bufunload_with_tabnext()
quit
endfunc
func Test_argdelete_in_next()
au BufNew,BufEnter,BufLeave,BufWinEnter * argdel
call assert_fails('next a b', 'E1156:')
au! BufNew,BufEnter,BufLeave,BufWinEnter *
endfunc
func Test_autocmd_bufwinleave_with_tabfirst()
tabedit
augroup sample
@@ -214,7 +220,6 @@ func Test_autocmd_bufunload_avoiding_SEGV_02()
normal! i1
call assert_fails('edit a.txt', 'E517:')
call feedkeys("\<CR>")
autocmd! test_autocmd_bufunload
augroup! test_autocmd_bufunload
@@ -503,14 +508,6 @@ endfunc
" Using :blast and :ball for many events caused a crash, because b_nwindows was
" not incremented correctly.
func Test_autocmd_blast_badd()
" The system() here causes SetChangeMarks() to fail, when run in the GUI
" under Windows. No idea why. Happens with any external command, not
" related to the actual test.
" TODO: find the cause
if has('win32')
throw 'Skipped: calling system() causes problems'
endif
let content =<< trim [CODE]
au BufNew,BufAdd,BufWinEnter,BufEnter,BufLeave,BufWinLeave,BufUnload,VimEnter foo* blast
edit foo1
@@ -1836,20 +1833,9 @@ func Test_TextYankPost()
bwipe!
endfunc
func Test_nocatch_wipe_all_buffers()
" Real nasty autocommand: wipe all buffers on any event.
au * * bwipe *
call assert_fails('next x', ['E94:', 'E937:'])
bwipe
au!
endfunc
func Test_nocatch_wipe_dummy_buffer()
CheckFeature quickfix
" Nasty autocommand: wipe buffer on any event.
au * x bwipe
call assert_fails('lv½ /x', 'E937:')
au!
func Test_autocommand_all_events()
call assert_fails('au * * bwipe', 'E1155:')
call assert_fails('au * x bwipe', 'E1155:')
endfunc
function s:Before_test_dirchanged()

View File

@@ -68,6 +68,11 @@ func Test_for_invalid()
call assert_fails("for x in 99", 'E714:')
call assert_fails("for x in 'asdf'", 'E714:')
call assert_fails("for x in {'a': 9}", 'E714:')
if 0
/1/5/2/s/\n
endif
redraw
endfunc
func Test_readfile_binary()

View File

@@ -206,4 +206,23 @@ func Test_ex_mode_with_global()
call delete('Xexmodescript')
endfunc
func Test_ex_mode_count_overflow()
" The multiplication causes an integer overflow
CheckNotAsan
" this used to cause a crash
let lines =<< trim END
call feedkeys("\<Esc>Q\<CR>")
v9|9silent! vi|333333233333y32333333%O
call writefile(['done'], 'Xdidexmode')
qall!
END
call writefile(lines, 'Xexmodescript')
call assert_equal(1, RunVim([], [], '-e -s -S Xexmodescript -c qa'))
call assert_equal(['done'], readfile('Xdidexmode'))
call delete('Xdidexmode')
call delete('Xexmodescript')
endfunc
" vim: shiftwidth=2 sts=2 expandtab

View File

@@ -562,27 +562,33 @@ func Test_completefunc_error()
call setline(1, ['', 'abcd', ''])
call assert_fails('exe "normal 2G$a\<C-X>\<C-U>"', 'E578:')
" Jump to a different window from the complete function
" TODO: The following test causes an ASAN failure. Once this issue is
" addressed, enable the following test.
"func! CompleteFunc(findstart, base)
" if a:findstart == 1
" return col('.') - 1
" endif
" wincmd p
" return ['a', 'b']
"endfunc
"set completefunc=CompleteFunc
"new
"call assert_fails('exe "normal a\<C-X>\<C-U>"', 'E839:')
"close!
set completefunc&
delfunc CompleteFunc
delfunc CompleteFunc2
close!
endfunc
func Test_completefunc_error_not_asan()
" The following test causes an ASAN failure.
CheckNotAsan
" Jump to a different window from the complete function
func! CompleteFunc(findstart, base)
if a:findstart == 1
return col('.') - 1
endif
wincmd p
return ['a', 'b']
endfunc
set completefunc=CompleteFunc
new
call assert_fails('exe "normal a\<C-X>\<C-U>"', 'E839:')
close!
set completefunc&
delfunc CompleteFunc
endfunc
" Test for returning non-string values from 'completefunc'
func Test_completefunc_invalid_data()
new

View File

@@ -4,11 +4,9 @@ source check.vim
CheckFeature terminal
CheckNotGui
if execute('version') =~# '-fsanitize=[a-z,]*\<address\>'
" Skip tests on Travis CI ASAN build because it's difficult to estimate
" memory usage.
throw 'Skipped: does not work with ASAN'
endif
" Skip tests on Travis CI ASAN build because it's difficult to estimate memory
" usage.
CheckNotAsan
source shared.vim

View File

@@ -3833,7 +3833,7 @@ func Test_lbuffer_crash()
sv Xtest
augroup QF_Test
au!
au * * bw
au QuickFixCmdPre,QuickFixCmdPost,BufEnter,BufLeave * bw
augroup END
lbuffer
augroup QF_Test
@@ -3845,7 +3845,7 @@ endfunc
func Test_lexpr_crash()
augroup QF_Test
au!
au * * call setloclist(0, [], 'f')
au QuickFixCmdPre,QuickFixCmdPost,BufEnter,BufLeave * call setloclist(0, [], 'f')
augroup END
lexpr ""
augroup QF_Test
@@ -3880,7 +3880,7 @@ func Test_lvimgrep_crash()
sv Xtest
augroup QF_Test
au!
au * * call setloclist(0, [], 'f')
au QuickFixCmdPre,QuickFixCmdPost,BufEnter,BufLeave * call setloclist(0, [], 'f')
augroup END
lvimgrep quickfix test_quickfix.vim
augroup QF_Test
@@ -4215,7 +4215,7 @@ func Test_lbuffer_with_bwipe()
new
new
augroup nasty
au * * bwipe
au QuickFixCmdPre,QuickFixCmdPost,BufEnter,BufLeave * bwipe
augroup END
lbuffer
augroup nasty
@@ -4228,9 +4228,9 @@ endfunc
func Xexpr_acmd_freelist(cchar)
call s:setup_commands(a:cchar)
" This was using freed memory.
" This was using freed memory (but with what events?)
augroup nasty
au * * call g:Xsetlist([], 'f')
au QuickFixCmdPre,QuickFixCmdPost,BufEnter,BufLeave * call g:Xsetlist([], 'f')
augroup END
Xexpr "x"
augroup nasty

View File

@@ -567,8 +567,8 @@ endfunc
func Test_access_freed_mem()
call assert_equal(&columns, winwidth(0))
" This was accessing freed memory
au * 0 vs xxx
" This was accessing freed memory (but with what events?)
au BufEnter,BufLeave,WinEnter,WinLeave 0 vs xxx
arg 0
argadd
call assert_fails("all", "E242:")

View File

@@ -750,6 +750,24 @@ static char *(features[]) =
static int included_patches[] =
{ /* Add new patch number below this line */
/**/
2425,
/**/
2424,
/**/
2423,
/**/
2422,
/**/
2421,
/**/
2420,
/**/
2419,
/**/
2418,
/**/
2417,
/**/
2416,
/**/