# HG changeset patch # User Bram Moolenaar # Date 1607866203 -3600 # Node ID 4d5d12138b363d04992c61c0450c6b5bf96ca229 # Parent 638099dc139e8a1c40c530a59c22d0fa03a7f678 patch 8.2.2137: Vim9: :echo and :execute give error for empty argument Commit: https://github.com/vim/vim/commit/e4984290870565a2413cca660b0131f4702b7665 Author: Bram Moolenaar Date: Sun Dec 13 14:19:25 2020 +0100 patch 8.2.2137: Vim9: :echo and :execute give error for empty argument Problem: Vim9: :echo and :execute give error for empty argument. Solution: Ignore an empty argument. (closes https://github.com/vim/vim/issues/7468) diff --git a/src/errors.h b/src/errors.h --- a/src/errors.h +++ b/src/errors.h @@ -61,7 +61,7 @@ EXTERN char e_argument_nr_type_mismatch_ INIT(= N_("E1013: Argument %d: type mismatch, expected %s but got %s")); EXTERN char e_invalid_key_str[] INIT(= N_("E1014: Invalid key: %s")); -EXTERN char e_name_expected[] +EXTERN char e_name_expected_str[] INIT(= N_("E1015: Name expected: %s")); EXTERN char e_cannot_declare_a_scope_variable[] INIT(= N_("E1016: Cannot declare a %s variable: %s")); @@ -315,3 +315,5 @@ EXTERN char e_indexable_type_required[] INIT(= N_("E1141: Indexable type required")); EXTERN char e_non_empty_string_required[] INIT(= N_("E1142: Non-empty string required")); +EXTERN char e_empty_expression_str[] + INIT(= N_("E1143: empty expression: \"%s\"")); diff --git a/src/testdir/test_vim9_disassemble.vim b/src/testdir/test_vim9_disassemble.vim --- a/src/testdir/test_vim9_disassemble.vim +++ b/src/testdir/test_vim9_disassemble.vim @@ -15,6 +15,7 @@ let t:tabpagevar = 't' def s:ScriptFuncLoad(arg: string) var local = 1 buffers + echo echo arg echo local echo &lines @@ -43,14 +44,27 @@ def Test_disassemble_load() var res = execute('disass s:ScriptFuncLoad') assert_match('\d*_ScriptFuncLoad.*' .. - 'buffers.*' .. - ' EXEC \+buffers.*' .. - ' LOAD arg\[-1\].*' .. - ' LOAD $0.*' .. - ' LOADOPT &lines.*' .. - ' LOADV v:version.*' .. - ' LOADS s:scriptvar from .*test_vim9_disassemble.vim.*' .. - ' LOADG g:globalvar.*' .. + 'buffers\_s*' .. + '\d\+ EXEC \+buffers\_s*' .. + 'echo\_s*' .. + 'echo arg\_s*' .. + '\d\+ LOAD arg\[-1\]\_s*' .. + '\d\+ ECHO 1\_s*' .. + 'echo local\_s*' .. + '\d\+ LOAD $0\_s*' .. + '\d\+ ECHO 1\_s*' .. + 'echo &lines\_s*' .. + '\d\+ LOADOPT &lines\_s*' .. + '\d\+ ECHO 1\_s*' .. + 'echo v:version\_s*' .. + '\d\+ LOADV v:version\_s*' .. + '\d\+ ECHO 1\_s*' .. + 'echo s:scriptvar\_s*' .. + '\d\+ LOADS s:scriptvar from .*test_vim9_disassemble.vim\_s*' .. + '\d\+ ECHO 1\_s*' .. + 'echo g:globalvar\_s*' .. + '\d\+ LOADG g:globalvar\_s*' .. + '\d\+ ECHO 1\_s*' .. 'echo get(g:, "global")\_s*' .. '\d\+ LOAD g:\_s*' .. '\d\+ PUSHS "global"\_s*' .. diff --git a/src/testdir/test_vim9_script.vim b/src/testdir/test_vim9_script.vim --- a/src/testdir/test_vim9_script.vim +++ b/src/testdir/test_vim9_script.vim @@ -620,7 +620,7 @@ def Test_try_catch_fails() CheckDefFailure(['if 1', 'endtry'], 'E171:') CheckDefFailure(['try', 'echo 1', 'endtry'], 'E1032:') - CheckDefFailure(['throw'], 'E1015:') + CheckDefFailure(['throw'], 'E1143:') CheckDefFailure(['throw xxx'], 'E1001:') enddef @@ -1719,6 +1719,10 @@ def Test_nested_if() enddef def Test_execute_cmd() + # missing argument is ignored + execute + execute # comment + new setline(1, 'default') execute 'setline(1, "execute-string")' @@ -2137,9 +2141,6 @@ def Test_vim9_comment() 'vim9script', 'exe "echo"# something', ], 'E121:') - CheckDefFailure([ - 'exe # comment', - ], 'E1015:') CheckScriptFailure([ 'vim9script', 'exe# something', @@ -2164,7 +2165,7 @@ def Test_vim9_comment() ' throw#comment', 'catch', 'endtry', - ], 'E1015:') + ], 'E1143:') CheckDefFailure([ 'try', ' throw "yes"#comment', diff --git a/src/version.c b/src/version.c --- a/src/version.c +++ b/src/version.c @@ -751,6 +751,8 @@ static char *(features[]) = static int included_patches[] = { /* Add new patch number below this line */ /**/ + 2137, +/**/ 2136, /**/ 2135, diff --git a/src/vim9compile.c b/src/vim9compile.c --- a/src/vim9compile.c +++ b/src/vim9compile.c @@ -3975,7 +3975,10 @@ compile_expr7( if (!eval_isnamec1(**arg)) { - semsg(_(e_name_expected), *arg); + if (ends_excmd(*skipwhite(*arg))) + semsg(_(e_empty_expression_str), *arg); + else + semsg(_(e_name_expected_str), *arg); return FAIL; } @@ -7101,28 +7104,31 @@ compile_throw(char_u *arg, cctx_T *cctx compile_mult_expr(char_u *arg, int cmdidx, cctx_T *cctx) { char_u *p = arg; - char_u *prev; + char_u *prev = arg; int count = 0; for (;;) { + if (ends_excmd2(prev, p)) + break; if (compile_expr0(&p, cctx) == FAIL) return NULL; ++count; prev = p; p = skipwhite(p); - if (ends_excmd2(prev, p)) - break; - } - - if (cmdidx == CMD_echo || cmdidx == CMD_echon) - generate_ECHO(cctx, cmdidx == CMD_echo, count); - else if (cmdidx == CMD_execute) - generate_MULT_EXPR(cctx, ISN_EXECUTE, count); - else if (cmdidx == CMD_echomsg) - generate_MULT_EXPR(cctx, ISN_ECHOMSG, count); - else - generate_MULT_EXPR(cctx, ISN_ECHOERR, count); + } + + if (count > 0) + { + if (cmdidx == CMD_echo || cmdidx == CMD_echon) + generate_ECHO(cctx, cmdidx == CMD_echo, count); + else if (cmdidx == CMD_execute) + generate_MULT_EXPR(cctx, ISN_EXECUTE, count); + else if (cmdidx == CMD_echomsg) + generate_MULT_EXPR(cctx, ISN_ECHOMSG, count); + else + generate_MULT_EXPR(cctx, ISN_ECHOERR, count); + } return p; }