To: vim_dev@googlegroups.com Subject: Patch 8.2.0492 Fcc: outbox From: Bram Moolenaar Mime-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit ------------ Patch 8.2.0492 Problem: Vim9: some error messages not tested. Solution: Add more tests. Remove dead code. Fix uncovered bugs. Files: src/vim9compile.c, src/vim9execute.c, src/testdir/test_vim9_expr.vim, src/testdir/test_vim9_script.vim *** ../vim-8.2.0491/src/vim9compile.c 2020-04-01 16:34:12.555263953 +0200 --- src/vim9compile.c 2020-04-01 21:08:45.834347774 +0200 *************** *** 277,282 **** --- 277,301 ---- return type; } + /* + * Return the type_T for a typval. Only for primitive types. + */ + static type_T * + typval2type(typval_T *tv) + { + if (tv->v_type == VAR_NUMBER) + return &t_number; + if (tv->v_type == VAR_BOOL) + return &t_bool; + if (tv->v_type == VAR_STRING) + return &t_string; + if (tv->v_type == VAR_LIST) // e.g. for v:oldfiles + return &t_list_string; + if (tv->v_type == VAR_DICT) // e.g. for v:completed_item + return &t_dict_any; + return &t_any; + } + ///////////////////////////////////////////////////////////////////// // Following generate_ functions expect the caller to call ga_grow(). *************** *** 1402,1408 **** /* * Parse a type at "arg" and advance over it. ! * Return NULL for failure. */ type_T * parse_type(char_u **arg, garray_T *type_list) --- 1421,1427 ---- /* * Parse a type at "arg" and advance over it. ! * Return &t_any for failure. */ type_T * parse_type(char_u **arg, garray_T *type_list) *************** *** 3462,3468 **** int vimvaridx = -1; int oplen = 0; int heredoc = FALSE; ! type_T *type; lvar_T *lvar; char_u *name; char_u *sp; --- 3481,3487 ---- int vimvaridx = -1; int oplen = 0; int heredoc = FALSE; ! type_T *type = &t_any; lvar_T *lvar; char_u *name; char_u *sp; *************** *** 3532,3537 **** --- 3551,3557 ---- else if (*arg == '$') { dest = dest_env; + type = &t_string; if (is_decl) { semsg(_("E1065: Cannot declare an environment variable: %s"), name); *************** *** 3546,3551 **** --- 3566,3572 ---- goto theend; } dest = dest_reg; + type = &t_string; if (is_decl) { semsg(_("E1066: Cannot declare a register: %s"), name); *************** *** 3563,3568 **** --- 3584,3591 ---- } else if (STRNCMP(arg, "v:", 2) == 0) { + typval_T *vtv; + vimvaridx = find_vim_var(name + 2); if (vimvaridx < 0) { *************** *** 3570,3575 **** --- 3593,3600 ---- goto theend; } dest = dest_vimvar; + vtv = get_vim_var_tv(vimvaridx); + type = typval2type(vtv); if (is_decl) { semsg(_("E1064: Cannot declare a v: variable: %s"), name); *************** *** 3625,3640 **** // parse optional type: "let var: type = expr" p = skipwhite(p + 1); type = parse_type(&p, cctx->ctx_type_list); - if (type == NULL) - goto theend; has_type = TRUE; } ! else if (idx < 0) ! { ! // global and new local default to "any" type ! type = &t_any; ! } ! else { lvar = ((lvar_T *)cctx->ctx_locals.ga_data) + idx; type = lvar->lv_type; --- 3650,3658 ---- // parse optional type: "let var: type = expr" p = skipwhite(p + 1); type = parse_type(&p, cctx->ctx_type_list); has_type = TRUE; } ! else if (idx >= 0) { lvar = ((lvar_T *)cctx->ctx_locals.ga_data) + idx; type = lvar->lv_type; *************** *** 3700,3706 **** } else if (oplen > 0) { ! int r; // for "+=", "*=", "..=" etc. first load the current value if (*op != '=') --- 3718,3726 ---- } else if (oplen > 0) { ! int r; ! type_T *stacktype; ! garray_T *stack; // for "+=", "*=", "..=" etc. first load the current value if (*op != '=') *************** *** 3709,3715 **** { case dest_option: // TODO: check the option exists ! generate_LOAD(cctx, ISN_LOADOPT, 0, name + 1, type); break; case dest_global: generate_LOAD(cctx, ISN_LOADG, 0, name + 2, type); --- 3729,3735 ---- { case dest_option: // TODO: check the option exists ! generate_LOAD(cctx, ISN_LOADOPT, 0, name, type); break; case dest_global: generate_LOAD(cctx, ISN_LOADG, 0, name + 2, type); *************** *** 3746,3757 **** if (r == FAIL) goto theend; if (idx >= 0 && (is_decl || !has_type)) { - garray_T *stack = &cctx->ctx_type_stack; - type_T *stacktype = - ((type_T **)stack->ga_data)[stack->ga_len - 1]; - lvar = ((lvar_T *)cctx->ctx_locals.ga_data) + idx; if (!has_type) { --- 3766,3775 ---- if (r == FAIL) goto theend; + stack = &cctx->ctx_type_stack; + stacktype = ((type_T **)stack->ga_data)[stack->ga_len - 1]; if (idx >= 0 && (is_decl || !has_type)) { lvar = ((lvar_T *)cctx->ctx_locals.ga_data) + idx; if (!has_type) { *************** *** 3767,3772 **** --- 3785,3792 ---- if (check_type(lvar->lv_type, stacktype, TRUE) == FAIL) goto theend; } + else if (*p != '=' && check_type(type, stacktype, TRUE) == FAIL) + goto theend; } else if (cmdidx == CMD_const) { *** ../vim-8.2.0491/src/vim9execute.c 2020-03-31 23:13:05.758568664 +0200 --- src/vim9execute.c 2020-04-01 20:03:38.248837550 +0200 *************** *** 684,689 **** --- 684,691 ---- typval_T optval; char_u *name = iptr->isn_arg.string; + // This is not expected to fail, name is checked during + // compilation: don't set SOURCING_LNUM. if (ga_grow(&ectx.ec_stack, 1) == FAIL) goto failed; if (get_option_tv(&name, &optval, TRUE) == FAIL) *** ../vim-8.2.0491/src/testdir/test_vim9_expr.vim 2020-03-30 22:51:20.647982632 +0200 --- src/testdir/test_vim9_expr.vim 2020-04-01 21:14:42.584993689 +0200 *************** *** 106,111 **** --- 106,113 ---- call CheckDefFailure("let x = 1||2", msg) call CheckDefFailure("let x = 1 ||2", msg) call CheckDefFailure("let x = 1|| 2", msg) + + call CheckDefFailure("let x = 1 || xxx", 'E1001:') endfunc " test && *************** *** 877,883 **** call CheckDefFailure("let x = 123->{x -> x + 5) }", "E451:") call CheckDefFailure("let x = ¬exist", 'E113:') ! call CheckDefExecFailure("&grepprg = [343]", 'E1051:') call CheckDefExecFailure("echo s:doesnt_exist", 'E121:') call CheckDefExecFailure("echo g:doesnt_exist", 'E121:') --- 879,885 ---- call CheckDefFailure("let x = 123->{x -> x + 5) }", "E451:") call CheckDefFailure("let x = ¬exist", 'E113:') ! call CheckDefFailure("&grepprg = [343]", 'E1013:') call CheckDefExecFailure("echo s:doesnt_exist", 'E121:') call CheckDefExecFailure("echo g:doesnt_exist", 'E121:') *** ../vim-8.2.0491/src/testdir/test_vim9_script.vim 2020-03-31 23:13:05.758568664 +0200 --- src/testdir/test_vim9_script.vim 2020-04-01 21:11:24.597743408 +0200 *************** *** 31,36 **** --- 31,38 ---- let s:appendToMe = 'xxx' let s:addToMe = 111 let g:existing = 'yes' + let g:inc_counter = 1 + let $SOME_ENV_VAR = 'some' def Test_assignment() let bool1: bool = true *************** *** 94,99 **** --- 96,122 ---- assert_equal(333, s:addToMe) s:newVar = 'new' assert_equal('new', s:newVar) + + set ts=7 + &ts += 1 + assert_equal(8, &ts) + call CheckDefFailure(['¬ex += 3'], 'E113:') + call CheckDefFailure(['&ts ..= "xxx"'], 'E1019:') + call CheckDefFailure(['&path += 3'], 'E1013:') + + g:inc_counter += 1 + assert_equal(2, g:inc_counter) + + $SOME_ENV_VAR ..= 'more' + assert_equal('somemore', $SOME_ENV_VAR) + call CheckDefFailure(['$SOME_ENV_VAR += "more"'], 'E1013:') + call CheckDefFailure(['$SOME_ENV_VAR += 123'], 'E1013:') + + @a = 'areg' + @a ..= 'add' + assert_equal('aregadd', @a) + call CheckDefFailure(['@a += "more"'], 'E1013:') + call CheckDefFailure(['@a += 123'], 'E1013:') enddef func Test_assignment_failure() *** ../vim-8.2.0491/src/version.c 2020-04-01 19:22:06.522507242 +0200 --- src/version.c 2020-04-01 19:41:59.413491024 +0200 *************** *** 740,741 **** --- 740,743 ---- { /* Add new patch number below this line */ + /**/ + 492, /**/ -- An indication you must be a manager: You feel sorry for Dilbert's boss. /// Bram Moolenaar -- Bram@Moolenaar.net -- http://www.Moolenaar.net \\\ /// sponsor Vim, vote for features -- http://www.Vim.org/sponsor/ \\\ \\\ an exciting new programming language -- http://www.Zimbu.org /// \\\ help me help AIDS victims -- http://ICCF-Holland.org ///