Mercurial > vim
comparison src/vim9compile.c @ 21576:f4252efe370e v8.2.1338
patch 8.2.1338: Vim9: assigning to script-local variable doesn't check type
Commit: https://github.com/vim/vim/commit/8e4c8c853e3ffbd9258f89180692879ec6bce72b
Author: Bram Moolenaar <Bram@vim.org>
Date: Sat Aug 1 15:38:38 2020 +0200
patch 8.2.1338: Vim9: assigning to script-local variable doesn't check type
Problem: Vim9: assigning to script-local variable doesn't check type.
Solution: Use the type. (issue https://github.com/vim/vim/issues/6591)
author | Bram Moolenaar <Bram@vim.org> |
---|---|
date | Sat, 01 Aug 2020 15:45:06 +0200 |
parents | 30a997217524 |
children | 7417cb54cb24 |
comparison
equal
deleted
inserted
replaced
21575:69d8fbc507a1 | 21576:f4252efe370e |
---|---|
5068 char_u *p; | 5068 char_u *p; |
5069 char_u *end = arg; | 5069 char_u *end = arg; |
5070 char_u *ret = NULL; | 5070 char_u *ret = NULL; |
5071 int var_count = 0; | 5071 int var_count = 0; |
5072 int var_idx; | 5072 int var_idx; |
5073 int scriptvar_sid = 0; | |
5074 int scriptvar_idx = -1; | |
5073 int semicolon = 0; | 5075 int semicolon = 0; |
5074 garray_T *instr = &cctx->ctx_instr; | 5076 garray_T *instr = &cctx->ctx_instr; |
5075 garray_T *stack = &cctx->ctx_type_stack; | 5077 garray_T *stack = &cctx->ctx_type_stack; |
5076 char_u *op; | 5078 char_u *op; |
5077 int oplen = 0; | 5079 int oplen = 0; |
5331 goto theend; | 5333 goto theend; |
5332 } | 5334 } |
5333 } | 5335 } |
5334 else | 5336 else |
5335 { | 5337 { |
5336 int idx; | 5338 int idx; |
5339 imported_T *import = NULL; | |
5337 | 5340 |
5338 for (idx = 0; reserved[idx] != NULL; ++idx) | 5341 for (idx = 0; reserved[idx] != NULL; ++idx) |
5339 if (STRCMP(reserved[idx], name) == 0) | 5342 if (STRCMP(reserved[idx], name) == 0) |
5340 { | 5343 { |
5341 semsg(_("E1034: Cannot use reserved name %s"), name); | 5344 semsg(_("E1034: Cannot use reserved name %s"), name); |
5372 goto theend; | 5375 goto theend; |
5373 } | 5376 } |
5374 } | 5377 } |
5375 else if ((varlen > 1 && STRNCMP(var_start, "s:", 2) == 0) | 5378 else if ((varlen > 1 && STRNCMP(var_start, "s:", 2) == 0) |
5376 || lookup_script(var_start, varlen) == OK | 5379 || lookup_script(var_start, varlen) == OK |
5377 || find_imported(var_start, varlen, cctx) != NULL) | 5380 || (import = find_imported(var_start, varlen, cctx)) |
5381 != NULL) | |
5378 { | 5382 { |
5379 dest = dest_script; | 5383 char_u *rawname = name + (name[1] == ':' ? 2 : 0); |
5384 | |
5380 if (is_decl) | 5385 if (is_decl) |
5381 { | 5386 { |
5382 if ((varlen > 1 && STRNCMP(var_start, "s:", 2) == 0)) | 5387 if ((varlen > 1 && STRNCMP(var_start, "s:", 2) == 0)) |
5383 semsg(_("E1101: Cannot declare a script variable in a function: %s"), | 5388 semsg(_("E1101: Cannot declare a script variable in a function: %s"), |
5384 name); | 5389 name); |
5385 else | 5390 else |
5386 semsg(_("E1054: Variable already declared in the script: %s"), | 5391 semsg(_("E1054: Variable already declared in the script: %s"), |
5387 name); | 5392 name); |
5388 goto theend; | 5393 goto theend; |
5394 } | |
5395 dest = dest_script; | |
5396 | |
5397 // existing script-local variables should have a type | |
5398 scriptvar_sid = current_sctx.sc_sid; | |
5399 if (import != NULL) | |
5400 scriptvar_sid = import->imp_sid; | |
5401 scriptvar_idx = get_script_item_idx(scriptvar_sid, | |
5402 rawname, TRUE); | |
5403 if (scriptvar_idx >= 0) | |
5404 { | |
5405 scriptitem_T *si = SCRIPT_ITEM(scriptvar_sid); | |
5406 svar_T *sv = ((svar_T *)si->sn_var_vals.ga_data) | |
5407 + scriptvar_idx; | |
5408 type = sv->sv_type; | |
5389 } | 5409 } |
5390 } | 5410 } |
5391 else if (name[1] == ':' && name[2] != NUL) | 5411 else if (name[1] == ':' && name[2] != NUL) |
5392 { | 5412 { |
5393 semsg(_("E1082: Cannot use a namespaced variable: %s"), | 5413 semsg(_("E1082: Cannot use a namespaced variable: %s"), |
5764 case dest_vimvar: | 5784 case dest_vimvar: |
5765 generate_STORE(cctx, ISN_STOREV, vimvaridx, NULL); | 5785 generate_STORE(cctx, ISN_STOREV, vimvaridx, NULL); |
5766 break; | 5786 break; |
5767 case dest_script: | 5787 case dest_script: |
5768 { | 5788 { |
5769 char_u *rawname = name + (name[1] == ':' ? 2 : 0); | 5789 if (scriptvar_idx < 0) |
5770 imported_T *import = NULL; | |
5771 int sid = current_sctx.sc_sid; | |
5772 int idx; | |
5773 | |
5774 if (name[1] != ':') | |
5775 { | |
5776 import = find_imported(name, 0, cctx); | |
5777 if (import != NULL) | |
5778 sid = import->imp_sid; | |
5779 } | |
5780 | |
5781 idx = get_script_item_idx(sid, rawname, TRUE); | |
5782 // TODO: specific type | |
5783 if (idx < 0) | |
5784 { | 5790 { |
5785 char_u *name_s = name; | 5791 char_u *name_s = name; |
5786 | 5792 |
5787 // Include s: in the name for store_var() | 5793 // Include s: in the name for store_var() |
5788 if (name[1] != ':') | 5794 if (name[1] != ':') |
5794 name_s = name; | 5800 name_s = name; |
5795 else | 5801 else |
5796 vim_snprintf((char *)name_s, len, | 5802 vim_snprintf((char *)name_s, len, |
5797 "s:%s", name); | 5803 "s:%s", name); |
5798 } | 5804 } |
5799 generate_OLDSCRIPT(cctx, ISN_STORES, name_s, sid, | 5805 generate_OLDSCRIPT(cctx, ISN_STORES, name_s, |
5800 &t_any); | 5806 scriptvar_sid, type); |
5801 if (name_s != name) | 5807 if (name_s != name) |
5802 vim_free(name_s); | 5808 vim_free(name_s); |
5803 } | 5809 } |
5804 else | 5810 else |
5805 generate_VIM9SCRIPT(cctx, ISN_STORESCRIPT, | 5811 generate_VIM9SCRIPT(cctx, ISN_STORESCRIPT, |
5806 sid, idx, &t_any); | 5812 scriptvar_sid, scriptvar_idx, type); |
5807 } | 5813 } |
5808 break; | 5814 break; |
5809 case dest_local: | 5815 case dest_local: |
5810 if (lvar != NULL) | 5816 if (lvar != NULL) |
5811 { | 5817 { |