Mercurial > vim
diff src/vim9execute.c @ 19862:846fbbacce3a v8.2.0487
patch 8.2.0487: Vim9: compiling not sufficiently tested
Commit: https://github.com/vim/vim/commit/bd5da371aafe5a2207065643502f4d1ff6b286c7
Author: Bram Moolenaar <Bram@vim.org>
Date: Tue Mar 31 23:13:10 2020 +0200
patch 8.2.0487: Vim9: compiling not sufficiently tested
Problem: Vim9: compiling not sufficiently tested.
Solution: Add more tests. Fix bug with PCALL.
author | Bram Moolenaar <Bram@vim.org> |
---|---|
date | Tue, 31 Mar 2020 23:15:04 +0200 |
parents | e4ade28bfaf7 |
children | 8a7bede7b138 |
line wrap: on
line diff
--- a/src/vim9execute.c +++ b/src/vim9execute.c @@ -345,7 +345,7 @@ call_by_name(char_u *name, int argcount, static int call_partial(typval_T *tv, int argcount, ectx_T *ectx) { - char_u *name; + char_u *name = NULL; int called_emsg_before = called_emsg; if (tv->v_type == VAR_PARTIAL) @@ -356,9 +356,9 @@ call_partial(typval_T *tv, int argcount, return call_ufunc(pt->pt_func, argcount, ectx, NULL); name = pt->pt_name; } - else + else if (tv->v_type == VAR_FUNC) name = tv->vval.v_string; - if (call_by_name(name, argcount, ectx, NULL) == FAIL) + if (name == NULL || call_by_name(name, argcount, ectx, NULL) == FAIL) { if (called_emsg == called_emsg_before) semsg(_(e_unknownfunc), name); @@ -421,7 +421,6 @@ call_def_function( typval_T *tv; int idx; int ret = FAIL; - dfunc_T *dfunc; int defcount = ufunc->uf_args.ga_len - argc; // Get pointer to item in the stack. @@ -467,13 +466,17 @@ call_def_function( ++ectx.ec_stack.ga_len; } - // Reserve space for local variables. - dfunc = ((dfunc_T *)def_functions.ga_data) + ufunc->uf_dfunc_idx; - for (idx = 0; idx < dfunc->df_varcount; ++idx) - STACK_TV_VAR(idx)->v_type = VAR_UNKNOWN; - ectx.ec_stack.ga_len += dfunc->df_varcount; + { + // Reserve space for local variables. + dfunc_T *dfunc = ((dfunc_T *)def_functions.ga_data) + + ufunc->uf_dfunc_idx; - ectx.ec_instr = dfunc->df_instr; + for (idx = 0; idx < dfunc->df_varcount; ++idx) + STACK_TV_VAR(idx)->v_type = VAR_UNKNOWN; + ectx.ec_stack.ga_len += dfunc->df_varcount; + + ectx.ec_instr = dfunc->df_instr; + } // Decide where to start execution, handles optional arguments. init_instr_idx(ufunc, argc, &ectx); @@ -1022,16 +1025,16 @@ call_def_function( clear_tv(&partial); if (r == FAIL) goto failed; + } + break; - if (pfunc->cpf_top) - { - // Get the funcref from the stack, overwrite with the - // return value. - clear_tv(tv); - --ectx.ec_stack.ga_len; - *STACK_TV_BOT(-1) = *STACK_TV_BOT(0); - } - } + case ISN_PCALL_END: + // PCALL finished, arguments have been consumed and replaced by + // the return value. Now clear the funcref from the stack, + // and move the return value in its place. + --ectx.ec_stack.ga_len; + clear_tv(STACK_TV_BOT(-1)); + *STACK_TV_BOT(-1) = *STACK_TV_BOT(0); break; // call a user defined function or funcref/partial @@ -1078,6 +1081,7 @@ call_def_function( case ISN_FUNCREF: { partial_T *pt = NULL; + dfunc_T *dfunc; pt = ALLOC_CLEAR_ONE(partial_T); if (pt == NULL) @@ -2005,6 +2009,9 @@ ex_disassemble(exarg_T *eap) cpfunc->cpf_top ? " top" : "", cpfunc->cpf_argcount); } break; + case ISN_PCALL_END: + smsg("%4d PCALL end", current); + break; case ISN_RETURN: smsg("%4d RETURN", current); break;