patch 8.2.3996: Vim9: type checking lacks information about declared type
Problem: Vim9: type checking for list and dict lacks information about
declared type.
Solution: Add dv_decl_type and lv_decl_type. Refactor the type stack to
store two types in each entry.
diff --git a/src/vim9compile.c b/src/vim9compile.c
index 026b18f..a243e64 100644
--- a/src/vim9compile.c
+++ b/src/vim9compile.c
@@ -1639,7 +1639,6 @@
int c = var_start[varlen];
int lines_len = cctx->ctx_ufunc->uf_lines.ga_len;
char_u *p = var_start;
- garray_T *stack = &cctx->ctx_type_stack;
int res;
// Evaluate "ll[expr]" of "ll[expr][idx]". End the line with a NUL and
@@ -1657,8 +1656,8 @@
return FAIL;
}
- lhs->lhs_type = stack->ga_len == 0 ? &t_void
- : ((type_T **)stack->ga_data)[stack->ga_len - 1];
+ lhs->lhs_type = cctx->ctx_type_stack.ga_len == 0 ? &t_void
+ : get_type_on_stack(cctx, 0);
// now we can properly check the type
if (rhs_type != NULL && lhs->lhs_type->tt_member != NULL
&& rhs_type != &t_void
@@ -1717,7 +1716,6 @@
cctx_T *cctx)
{
vartype_T dest_type;
- garray_T *stack = &cctx->ctx_type_stack;
int range = FALSE;
if (compile_assign_index(var_start, lhs, &range, cctx) == FAIL)
@@ -1753,12 +1751,12 @@
if (range)
{
- type = ((type_T **)stack->ga_data)[stack->ga_len - 2];
+ type = get_type_on_stack(cctx, 1);
if (need_type(type, &t_number,
-1, 0, cctx, FALSE, FALSE) == FAIL)
return FAIL;
}
- type = ((type_T **)stack->ga_data)[stack->ga_len - 1];
+ type = get_type_on_stack(cctx, 0);
if ((dest_type != VAR_BLOB && type != &t_special)
&& need_type(type, &t_number,
-1, 0, cctx, FALSE, FALSE) == FAIL)
@@ -1837,7 +1835,6 @@
int semicolon = 0;
int did_generate_slice = FALSE;
garray_T *instr = &cctx->ctx_instr;
- garray_T *stack = &cctx->ctx_type_stack;
char_u *op;
int oplen = 0;
int heredoc = FALSE;
@@ -1929,8 +1926,8 @@
int needed_list_len;
int did_check = FALSE;
- stacktype = stack->ga_len == 0 ? &t_void
- : ((type_T **)stack->ga_data)[stack->ga_len - 1];
+ stacktype = cctx->ctx_type_stack.ga_len == 0 ? &t_void
+ : get_type_on_stack(cctx, 0);
if (stacktype->tt_type == VAR_VOID)
{
emsg(_(e_cannot_use_void_value));
@@ -2073,8 +2070,8 @@
goto theend;
}
- rhs_type = stack->ga_len == 0 ? &t_void
- : ((type_T **)stack->ga_data)[stack->ga_len - 1];
+ rhs_type = cctx->ctx_type_stack.ga_len == 0 ? &t_void
+ : get_type_on_stack(cctx, 0);
if (lhs.lhs_lvar != NULL && (is_decl || !lhs.lhs_has_type))
{
if ((rhs_type->tt_type == VAR_FUNC
@@ -2230,7 +2227,7 @@
else
{
expected = lhs.lhs_member_type;
- stacktype = ((type_T **)stack->ga_data)[stack->ga_len - 1];
+ stacktype = get_type_on_stack(cctx, 0);
if (
#ifdef FEAT_FLOAT
// If variable is float operation with number is OK.
@@ -2527,7 +2524,8 @@
cctx.ctx_lnum = -1;
cctx.ctx_outer = outer_cctx;
ga_init2(&cctx.ctx_locals, sizeof(lvar_T), 10);
- ga_init2(&cctx.ctx_type_stack, sizeof(type_T *), 50);
+ // Each entry on the type stack consists of two type pointers.
+ ga_init2(&cctx.ctx_type_stack, sizeof(type2_T), 50);
ga_init2(&cctx.ctx_imports, sizeof(imported_T), 10);
cctx.ctx_type_list = &ufunc->uf_type_list;
ga_init2(&cctx.ctx_instr, sizeof(isn_T), 50);
@@ -2564,7 +2562,6 @@
SOURCING_LNUM = 0; // line number unknown
for (i = 0; i < count; ++i)
{
- garray_T *stack = &cctx.ctx_type_stack;
type_T *val_type;
int arg_idx = first_def_arg + i;
where_T where = WHERE_INIT;
@@ -2588,7 +2585,7 @@
// If no type specified use the type of the default value.
// Otherwise check that the default value type matches the
// specified type.
- val_type = ((type_T **)stack->ga_data)[stack->ga_len - 1];
+ val_type = get_type_on_stack(&cctx, 0);
where.wt_index = arg_idx + 1;
if (ufunc->uf_arg_types[arg_idx] == &t_unknown)
{