summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBram Moolenaar <Bram@vim.org>2022-09-11 15:14:05 +0100
committerBram Moolenaar <Bram@vim.org>2022-09-11 15:14:05 +0100
commit9510d22463055f56548ff461ccbc54caa1ba1a2f (patch)
tree5c084eccddd0a17e08c4bba2d5fec6d4cc969144
parentcce82a55b8105560a2ef724999c856966337b48e (diff)
downloadvim-git-9.0.0444.tar.gz
patch 9.0.0444: trying to declare g:variable gives confusing errorv9.0.0444
Problem: Trying to declare g:variable gives confusing error. Solution: Give a better error message. (closes #11108)
-rw-r--r--src/errors.h2
-rw-r--r--src/eval.c6
-rw-r--r--src/evalvars.c15
-rw-r--r--src/ex_docmd.c4
-rw-r--r--src/proto/evalvars.pro1
-rw-r--r--src/testdir/test_vim9_assign.vim32
-rw-r--r--src/testdir/test_vim9_cmd.vim4
-rw-r--r--src/testdir/test_vim9_script.vim5
-rw-r--r--src/version.c2
9 files changed, 51 insertions, 20 deletions
diff --git a/src/errors.h b/src/errors.h
index d1cf4b457..5f0fdcb8a 100644
--- a/src/errors.h
+++ b/src/errors.h
@@ -3335,4 +3335,6 @@ EXTERN char e_script_variable_was_deleted[]
INIT(= N_("E1302: Script variable was deleted"));
EXTERN char e_custom_list_completion_function_does_not_return_list_but_str[]
INIT(= N_("E1303: Custom list completion function does not return a List but a %s"));
+EXTERN char e_cannot_use_type_with_this_variable_str[]
+ INIT(= N_("E1304: Cannot use type with this variable: %s"));
#endif
diff --git a/src/eval.c b/src/eval.c
index f208ab100..5d93b7e50 100644
--- a/src/eval.c
+++ b/src/eval.c
@@ -1031,12 +1031,16 @@ get_lval(
{
char_u *tp = skipwhite(p + 1);
+ if (is_scoped_variable(name))
+ {
+ semsg(_(e_cannot_use_type_with_this_variable_str), name);
+ return NULL;
+ }
if (tp == p + 1 && !quiet)
{
semsg(_(e_white_space_required_after_str_str), ":", p);
return NULL;
}
-
if (!SCRIPT_ID_VALID(current_sctx.sc_sid))
{
semsg(_(e_using_type_not_in_script_context_str), p);
diff --git a/src/evalvars.c b/src/evalvars.c
index facafc7dd..7de785bc4 100644
--- a/src/evalvars.c
+++ b/src/evalvars.c
@@ -603,6 +603,18 @@ list_script_vars(int *first)
}
/*
+ * Return TRUE if "name" starts with "g:", "w:", "t:" or "b:".
+ * But only when an identifier character follows.
+ */
+ int
+is_scoped_variable(char_u *name)
+{
+ return vim_strchr((char_u *)"gwbt", name[0]) != NULL
+ && name[1] == ':'
+ && eval_isnamec(name[2]);
+}
+
+/*
* Evaluate one Vim expression {expr} in string "p" and append the
* resulting string to "gap". "p" points to the opening "{".
* When "evaluate" is FALSE only skip over the expression.
@@ -3679,8 +3691,7 @@ set_var_const(
vim9_declare_error(name);
goto failed;
}
- if ((flags & ASSIGN_FOR_LOOP) && name[1] == ':'
- && vim_strchr((char_u *)"gwbt", name[0]) != NULL)
+ if ((flags & ASSIGN_FOR_LOOP) && is_scoped_variable(name))
// Do not make g:var, w:var, b:var or t:var final.
flags &= ~ASSIGN_FINAL;
diff --git a/src/ex_docmd.c b/src/ex_docmd.c
index 0024c99c6..0e5e1db5e 100644
--- a/src/ex_docmd.c
+++ b/src/ex_docmd.c
@@ -3761,11 +3761,11 @@ find_ex_command(
}
}
- // Recognize using a type for a w:, b:, t: or g: variable:
+ // Recognize trying to use a type for a w:, b:, t: or g: variable:
// "w:varname: number = 123".
if (eap->cmd[1] == ':' && *p == ':')
{
- eap->cmdidx = CMD_eval;
+ eap->cmdidx = CMD_var;
return eap->cmd;
}
}
diff --git a/src/proto/evalvars.pro b/src/proto/evalvars.pro
index 253af6de6..b8b005342 100644
--- a/src/proto/evalvars.pro
+++ b/src/proto/evalvars.pro
@@ -13,6 +13,7 @@ list_T *eval_spell_expr(char_u *badword, char_u *expr);
int get_spellword(list_T *list, char_u **pp);
void prepare_vimvar(int idx, typval_T *save_tv);
void restore_vimvar(int idx, typval_T *save_tv);
+int is_scoped_variable(char_u *name);
char_u *eval_one_expr_in_str(char_u *p, garray_T *gap, int evaluate);
list_T *heredoc_get(exarg_T *eap, char_u *cmd, int script_get, int vim9compile);
void ex_var(exarg_T *eap);
diff --git a/src/testdir/test_vim9_assign.vim b/src/testdir/test_vim9_assign.vim
index 58dde3f1f..11d7425e6 100644
--- a/src/testdir/test_vim9_assign.vim
+++ b/src/testdir/test_vim9_assign.vim
@@ -1597,13 +1597,31 @@ def Test_assignment_failure()
v9.CheckDefFailure(['var name: dict<number'], 'E1009:')
v9.CheckDefFailure(['w:foo: number = 10'],
- 'E488: Trailing characters: : number = 1')
+ 'E1016: Cannot declare a window variable: w:foo')
v9.CheckDefFailure(['t:foo: bool = true'],
- 'E488: Trailing characters: : bool = true')
+ 'E1016: Cannot declare a tab variable: t:foo')
v9.CheckDefFailure(['b:foo: string = "x"'],
- 'E488: Trailing characters: : string = "x"')
+ 'E1016: Cannot declare a buffer variable: b:foo')
v9.CheckDefFailure(['g:foo: number = 123'],
- 'E488: Trailing characters: : number = 123')
+ 'E1016: Cannot declare a global variable: g:foo')
+
+ v9.CheckScriptFailure(['vim9script', 'w:foo: number = 123'],
+ 'E1304: Cannot use type with this variable: w:foo:')
+ v9.CheckScriptFailure(['vim9script', 't:foo: number = 123'],
+ 'E1304: Cannot use type with this variable: t:foo:')
+ v9.CheckScriptFailure(['vim9script', 'b:foo: number = 123'],
+ 'E1304: Cannot use type with this variable: b:foo:')
+ v9.CheckScriptFailure(['vim9script', 'g:foo: number = 123'],
+ 'E1304: Cannot use type with this variable: g:foo:')
+
+ v9.CheckScriptFailure(['vim9script', 'const w:FOO: number = 123'],
+ 'E1304: Cannot use type with this variable: w:FOO:')
+ v9.CheckScriptFailure(['vim9script', 'const t:FOO: number = 123'],
+ 'E1304: Cannot use type with this variable: t:FOO:')
+ v9.CheckScriptFailure(['vim9script', 'const b:FOO: number = 123'],
+ 'E1304: Cannot use type with this variable: b:FOO:')
+ v9.CheckScriptFailure(['vim9script', 'const g:FOO: number = 123'],
+ 'E1304: Cannot use type with this variable: g:FOO:')
enddef
def Test_assign_list()
@@ -1959,8 +1977,6 @@ def Test_var_declaration()
FLIST[0] = 11
assert_equal([11], FLIST)
- const g:FOO: number = 321
- assert_equal(321, g:FOO)
const g:FOOS = 'gfoos'
assert_equal('gfoos', g:FOOS)
final g:FLIST = [2]
@@ -1975,8 +1991,6 @@ def Test_var_declaration()
assert_equal(123, g:globConst)
assert_true(islocked('g:globConst'))
- const w:FOO: number = 46
- assert_equal(46, w:FOO)
const w:FOOS = 'wfoos'
assert_equal('wfoos', w:FOOS)
final w:FLIST = [3]
@@ -2015,10 +2029,8 @@ def Test_var_declaration()
unlet g:var_prefixed
unlet g:other_var
unlet g:globConst
- unlet g:FOO
unlet g:FOOS
unlet g:FLIST
- unlet w:FOO
unlet w:FOOS
unlet w:FLIST
enddef
diff --git a/src/testdir/test_vim9_cmd.vim b/src/testdir/test_vim9_cmd.vim
index 636769d3a..80b78205a 100644
--- a/src/testdir/test_vim9_cmd.vim
+++ b/src/testdir/test_vim9_cmd.vim
@@ -1936,7 +1936,7 @@ def Test_var_not_cmd()
var lines =<< trim END
g:notexist:cmd
END
- v9.CheckDefAndScriptFailure(lines, ['E488: Trailing characters: :cmd', 'E121: Undefined variable: g:notexist'], 1)
+ v9.CheckDefAndScriptFailure(lines, ['E1016: Cannot declare a global variable: g:notexist', "E1069: White space required after ':'"], 1)
lines =<< trim END
g-pat-cmd
@@ -1950,7 +1950,7 @@ def Test_var_not_cmd()
lines =<< trim END
s:notexist:repl
END
- v9.CheckDefAndScriptFailure(lines, ['E488: Trailing characters: :repl', 'E1268:'], 1)
+ v9.CheckDefAndScriptFailure(lines, ['E1101: Cannot declare a script variable in a function: s:notexist', "E1069: White space required after ':'"], 1)
lines =<< trim END
notexist:repl
diff --git a/src/testdir/test_vim9_script.vim b/src/testdir/test_vim9_script.vim
index aeee14329..f746ca178 100644
--- a/src/testdir/test_vim9_script.vim
+++ b/src/testdir/test_vim9_script.vim
@@ -4241,13 +4241,12 @@ func Test_misplaced_type()
endfunc
def Run_Test_misplaced_type()
- writefile(['let g:somevar = "asdf"'], 'XTest_misplaced_type')
+ writefile(['let g:somevar = "asdf"'], 'XTest_misplaced_type', 'D')
var buf = g:RunVimInTerminal('-S XTest_misplaced_type', {'rows': 6})
- term_sendkeys(buf, ":vim9cmd echo islocked('g:somevar: string')\<CR>")
+ term_sendkeys(buf, ":vim9cmd echo islocked('somevar: string')\<CR>")
g:VerifyScreenDump(buf, 'Test_misplaced_type', {})
g:StopVimInTerminal(buf)
- delete('XTest_misplaced_type')
enddef
" Ensure echo doesn't crash when stringifying empty variables.
diff --git a/src/version.c b/src/version.c
index 26c1697c3..8fee9776e 100644
--- a/src/version.c
+++ b/src/version.c
@@ -704,6 +704,8 @@ static char *(features[]) =
static int included_patches[] =
{ /* Add new patch number below this line */
/**/
+ 444,
+/**/
443,
/**/
442,