summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/globals.h202
-rw-r--r--src/structs.h9
-rw-r--r--src/testdir/test_vim9_func.vim16
-rw-r--r--src/version.c2
-rw-r--r--src/vim9execute.c23
-rw-r--r--src/vim9type.c22
6 files changed, 158 insertions, 116 deletions
diff --git a/src/globals.h b/src/globals.h
index e38b471657..3c401a290f 100644
--- a/src/globals.h
+++ b/src/globals.h
@@ -430,107 +430,111 @@ EXTERN int garbage_collect_at_exit INIT(= FALSE);
#define t_number_bool (static_types[14])
#define t_const_number_bool (static_types[15])
-#define t_float (static_types[16])
-#define t_const_float (static_types[17])
+// t_number_float - number that can be used as a float
+#define t_number_float (static_types[16])
+#define t_const_number_float (static_types[17])
-#define t_string (static_types[18])
-#define t_const_string (static_types[19])
+#define t_float (static_types[18])
+#define t_const_float (static_types[19])
-#define t_blob (static_types[20])
-#define t_const_blob (static_types[21])
+#define t_string (static_types[20])
+#define t_const_string (static_types[21])
-#define t_blob_null (static_types[22])
-#define t_const_blob_null (static_types[23])
+#define t_blob (static_types[22])
+#define t_const_blob (static_types[23])
-#define t_job (static_types[24])
-#define t_const_job (static_types[25])
+#define t_blob_null (static_types[24])
+#define t_const_blob_null (static_types[25])
-#define t_channel (static_types[26])
-#define t_const_channel (static_types[27])
+#define t_job (static_types[26])
+#define t_const_job (static_types[27])
+
+#define t_channel (static_types[28])
+#define t_const_channel (static_types[29])
// t_number_or_string - Special value used for @#.
-#define t_number_or_string (static_types[28])
-#define t_const_number_or_string (static_types[29])
+#define t_number_or_string (static_types[30])
+#define t_const_number_or_string (static_types[31])
// t_func_unknown - function with any arguments and no or unknown return value
-#define t_func_unknown (static_types[30])
-#define t_const_func_unknown (static_types[31])
+#define t_func_unknown (static_types[32])
+#define t_const_func_unknown (static_types[33])
// t_func_void - function with any arguments and no return value
-#define t_func_void (static_types[32])
-#define t_const_func_void (static_types[33])
+#define t_func_void (static_types[34])
+#define t_const_func_void (static_types[35])
-#define t_func_any (static_types[34])
-#define t_const_func_any (static_types[35])
+#define t_func_any (static_types[36])
+#define t_const_func_any (static_types[37])
-#define t_func_number (static_types[36])
-#define t_const_func_number (static_types[37])
+#define t_func_number (static_types[38])
+#define t_const_func_number (static_types[39])
-#define t_func_string (static_types[38])
-#define t_const_func_string (static_types[39])
+#define t_func_string (static_types[40])
+#define t_const_func_string (static_types[41])
-#define t_func_bool (static_types[40])
-#define t_const_func_bool (static_types[41])
+#define t_func_bool (static_types[42])
+#define t_const_func_bool (static_types[43])
// t_func_0_void - function without arguments and nor return value
-#define t_func_0_void (static_types[42])
-#define t_const_func_0_void (static_types[43])
+#define t_func_0_void (static_types[44])
+#define t_const_func_0_void (static_types[45])
-#define t_func_0_any (static_types[44])
-#define t_const_func_0_any (static_types[45])
+#define t_func_0_any (static_types[46])
+#define t_const_func_0_any (static_types[47])
-#define t_func_0_number (static_types[46])
-#define t_const_func_0_number (static_types[47])
+#define t_func_0_number (static_types[48])
+#define t_const_func_0_number (static_types[49])
-#define t_func_0_string (static_types[48])
-#define t_const_func_0_string (static_types[49])
+#define t_func_0_string (static_types[50])
+#define t_const_func_0_string (static_types[51])
-#define t_list_any (static_types[50])
-#define t_const_list_any (static_types[51])
+#define t_list_any (static_types[52])
+#define t_const_list_any (static_types[53])
-#define t_dict_any (static_types[52])
-#define t_const_dict_any (static_types[53])
+#define t_dict_any (static_types[54])
+#define t_const_dict_any (static_types[55])
-#define t_list_empty (static_types[54])
-#define t_const_list_empty (static_types[55])
+#define t_list_empty (static_types[56])
+#define t_const_list_empty (static_types[57])
-#define t_dict_empty (static_types[56])
-#define t_const_dict_empty (static_types[57])
+#define t_dict_empty (static_types[58])
+#define t_const_dict_empty (static_types[59])
-#define t_list_bool (static_types[58])
-#define t_const_list_bool (static_types[59])
+#define t_list_bool (static_types[60])
+#define t_const_list_bool (static_types[61])
-#define t_list_number (static_types[60])
-#define t_const_list_number (static_types[61])
+#define t_list_number (static_types[62])
+#define t_const_list_number (static_types[63])
-#define t_list_string (static_types[62])
-#define t_const_list_string (static_types[63])
+#define t_list_string (static_types[64])
+#define t_const_list_string (static_types[65])
-#define t_list_job (static_types[64])
-#define t_const_list_job (static_types[65])
+#define t_list_job (static_types[66])
+#define t_const_list_job (static_types[67])
-#define t_list_dict_any (static_types[66])
-#define t_const_list_dict_any (static_types[67])
+#define t_list_dict_any (static_types[68])
+#define t_const_list_dict_any (static_types[69])
-#define t_list_list_any (static_types[68])
-#define t_const_list_list_any (static_types[69])
+#define t_list_list_any (static_types[70])
+#define t_const_list_list_any (static_types[71])
-#define t_list_list_string (static_types[70])
-#define t_const_list_list_string (static_types[71])
+#define t_list_list_string (static_types[72])
+#define t_const_list_list_string (static_types[73])
-#define t_dict_bool (static_types[72])
-#define t_const_dict_bool (static_types[73])
+#define t_dict_bool (static_types[74])
+#define t_const_dict_bool (static_types[75])
-#define t_dict_number (static_types[74])
-#define t_const_dict_number (static_types[75])
+#define t_dict_number (static_types[76])
+#define t_const_dict_number (static_types[77])
-#define t_dict_string (static_types[76])
-#define t_const_dict_string (static_types[77])
+#define t_dict_string (static_types[78])
+#define t_const_dict_string (static_types[79])
-#define t_super (static_types[78])
-#define t_const_super (static_types[79])
+#define t_super (static_types[80])
+#define t_const_super (static_types[81])
-EXTERN type_T static_types[80]
+EXTERN type_T static_types[82]
#ifdef DO_INIT
= {
// 0: t_unknown
@@ -565,131 +569,135 @@ EXTERN type_T static_types[80]
{VAR_NUMBER, 0, 0, TTFLAG_STATIC|TTFLAG_BOOL_OK, NULL, NULL},
{VAR_NUMBER, 0, 0, TTFLAG_STATIC|TTFLAG_BOOL_OK|TTFLAG_CONST, NULL, NULL},
- // 16: t_float
+ // 16: t_number_float
+ {VAR_NUMBER, 0, 0, TTFLAG_STATIC|TTFLAG_FLOAT_OK, NULL, NULL},
+ {VAR_NUMBER, 0, 0, TTFLAG_STATIC|TTFLAG_FLOAT_OK|TTFLAG_CONST, NULL, NULL},
+
+ // 18: t_float
{VAR_FLOAT, 0, 0, TTFLAG_STATIC, NULL, NULL},
{VAR_FLOAT, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, NULL, NULL},
- // 18: t_string
+ // 20: t_string
{VAR_STRING, 0, 0, TTFLAG_STATIC, NULL, NULL},
{VAR_STRING, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, NULL, NULL},
- // 20: t_blob
+ // 22: t_blob
{VAR_BLOB, 0, 0, TTFLAG_STATIC, NULL, NULL},
{VAR_BLOB, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, NULL, NULL},
- // 22: t_blob_null
+ // 24: t_blob_null
{VAR_BLOB, 0, 0, TTFLAG_STATIC, &t_void, NULL},
{VAR_BLOB, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_void, NULL},
- // 24: t_job
+ // 26: t_job
{VAR_JOB, 0, 0, TTFLAG_STATIC, NULL, NULL},
{VAR_JOB, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, NULL, NULL},
- // 26: t_channel
+ // 28: t_channel
{VAR_CHANNEL, 0, 0, TTFLAG_STATIC, NULL, NULL},
{VAR_CHANNEL, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, NULL, NULL},
- // 28: t_number_or_string
+ // 30: t_number_or_string
{VAR_STRING, 0, 0, TTFLAG_STATIC, NULL, NULL},
{VAR_STRING, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, NULL, NULL},
- // 30: t_func_unknown
+ // 32: t_func_unknown
{VAR_FUNC, -1, -1, TTFLAG_STATIC, &t_unknown, NULL},
{VAR_FUNC, -1, -1, TTFLAG_STATIC|TTFLAG_CONST, &t_unknown, NULL},
- // 32: t_func_void
+ // 34: t_func_void
{VAR_FUNC, -1, 0, TTFLAG_STATIC, &t_void, NULL},
{VAR_FUNC, -1, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_void, NULL},
- // 34: t_func_any
+ // 36: t_func_any
{VAR_FUNC, -1, 0, TTFLAG_STATIC, &t_any, NULL},
{VAR_FUNC, -1, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_any, NULL},
- // 36: t_func_number
+ // 38: t_func_number
{VAR_FUNC, -1, 0, TTFLAG_STATIC, &t_number, NULL},
{VAR_FUNC, -1, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_number, NULL},
- // 38: t_func_string
+ // 40: t_func_string
{VAR_FUNC, -1, 0, TTFLAG_STATIC, &t_string, NULL},
{VAR_FUNC, -1, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_string, NULL},
- // 40: t_func_bool
+ // 42: t_func_bool
{VAR_FUNC, -1, 0, TTFLAG_STATIC, &t_bool, NULL},
{VAR_FUNC, -1, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_bool, NULL},
- // 42: t_func_0_void
+ // 44: t_func_0_void
{VAR_FUNC, 0, 0, TTFLAG_STATIC, &t_void, NULL},
{VAR_FUNC, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_void, NULL},
- // 44: t_func_0_any
+ // 46: t_func_0_any
{VAR_FUNC, 0, 0, TTFLAG_STATIC, &t_any, NULL},
{VAR_FUNC, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_any, NULL},
- // 46: t_func_0_number
+ // 48: t_func_0_number
{VAR_FUNC, 0, 0, TTFLAG_STATIC, &t_number, NULL},
{VAR_FUNC, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_number, NULL},
- // 48: t_func_0_string
+ // 50: t_func_0_string
{VAR_FUNC, 0, 0, TTFLAG_STATIC, &t_string, NULL},
{VAR_FUNC, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_string, NULL},
- // 50: t_list_any
+ // 52: t_list_any
{VAR_LIST, 0, 0, TTFLAG_STATIC, &t_any, NULL},
{VAR_LIST, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_any, NULL},
- // 52: t_dict_any
+ // 54: t_dict_any
{VAR_DICT, 0, 0, TTFLAG_STATIC, &t_any, NULL},
{VAR_DICT, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_any, NULL},
- // 54: t_list_empty
+ // 56: t_list_empty
{VAR_LIST, 0, 0, TTFLAG_STATIC, &t_unknown, NULL},
{VAR_LIST, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_unknown, NULL},
- // 56: t_dict_empty
+ // 58: t_dict_empty
{VAR_DICT, 0, 0, TTFLAG_STATIC, &t_unknown, NULL},
{VAR_DICT, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_unknown, NULL},
- // 58: t_list_bool
+ // 60: t_list_bool
{VAR_LIST, 0, 0, TTFLAG_STATIC, &t_bool, NULL},
{VAR_LIST, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_bool, NULL},
- // 60: t_list_number
+ // 62: t_list_number
{VAR_LIST, 0, 0, TTFLAG_STATIC, &t_number, NULL},
{VAR_LIST, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_number, NULL},
- // 62: t_list_string
+ // 64: t_list_string
{VAR_LIST, 0, 0, TTFLAG_STATIC, &t_string, NULL},
{VAR_LIST, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_string, NULL},
- // 64: t_list_job
+ // 66: t_list_job
{VAR_LIST, 0, 0, TTFLAG_STATIC, &t_job, NULL},
{VAR_LIST, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_job, NULL},
- // 66: t_list_dict_any
+ // 68: t_list_dict_any
{VAR_LIST, 0, 0, TTFLAG_STATIC, &t_dict_any, NULL},
{VAR_LIST, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_dict_any, NULL},
- // 68: t_list_list_any
+ // 70: t_list_list_any
{VAR_LIST, 0, 0, TTFLAG_STATIC, &t_list_any, NULL},
{VAR_LIST, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_list_any, NULL},
- // 70: t_list_list_string
+ // 72: t_list_list_string
{VAR_LIST, 0, 0, TTFLAG_STATIC, &t_list_string, NULL},
{VAR_LIST, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_list_string, NULL},
- // 72: t_dict_bool
+ // 74: t_dict_bool
{VAR_DICT, 0, 0, TTFLAG_STATIC, &t_bool, NULL},
{VAR_DICT, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_bool, NULL},
- // 74: t_dict_number
+ // 76: t_dict_number
{VAR_DICT, 0, 0, TTFLAG_STATIC, &t_number, NULL},
{VAR_DICT, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_number, NULL},
- // 76: t_dict_string
+ // 78: t_dict_string
{VAR_DICT, 0, 0, TTFLAG_STATIC, &t_string, NULL},
{VAR_DICT, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_string, NULL},
- // 78: t_super (VAR_CLASS with tt_member set to &t_bool
+ // 80: t_super (VAR_CLASS with tt_member set to &t_bool
{VAR_CLASS, 0, 0, TTFLAG_STATIC, &t_bool, NULL},
{VAR_CLASS, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_bool, NULL},
}
diff --git a/src/structs.h b/src/structs.h
index a015dec49f..3b5a233f63 100644
--- a/src/structs.h
+++ b/src/structs.h
@@ -1462,10 +1462,11 @@ typedef struct {
#define TTFLAG_VARARGS 0x01 // func args ends with "..."
#define TTFLAG_BOOL_OK 0x02 // can be converted to bool
-#define TTFLAG_NUMBER_OK 0x04 // tt_type is VAR_FLOAT, VAR_NUMBER is OK
-#define TTFLAG_STATIC 0x08 // one of the static types, e.g. t_any
-#define TTFLAG_CONST 0x10 // cannot be changed
-#define TTFLAG_SUPER 0x20 // object from "super".
+#define TTFLAG_FLOAT_OK 0x04 // number can be used/converted to float
+#define TTFLAG_NUMBER_OK 0x08 // number can be used for a float
+#define TTFLAG_STATIC 0x10 // one of the static types, e.g. t_any
+#define TTFLAG_CONST 0x20 // cannot be changed
+#define TTFLAG_SUPER 0x40 // object from "super".
typedef enum {
ACCESS_PRIVATE, // read/write only inside th class
diff --git a/src/testdir/test_vim9_func.vim b/src/testdir/test_vim9_func.vim
index bf8b705ed5..44a8d4b106 100644
--- a/src/testdir/test_vim9_func.vim
+++ b/src/testdir/test_vim9_func.vim
@@ -727,6 +727,18 @@ def Test_call_default_args()
v9.CheckScriptSuccess(lines)
enddef
+def Test_convert_number_to_float()
+ var lines =<< trim END
+ vim9script
+ def Foo(a: float, b: float): float
+ return a + b
+ enddef
+
+ assert_equal(5.3, Foo(3.3, 2))
+ END
+ v9.CheckScriptSuccess(lines)
+enddef
+
def s:FuncWithComment( # comment
a: number, #comment
b: bool, # comment
@@ -4311,10 +4323,10 @@ def Test_lambda_argument_type_check()
return sum
enddef
- const ml = [3.0, 2, 7]
+ const ml = [3.0, 2, '7']
echo Scan(ml)->Sum()
END
- v9.CheckScriptFailure(lines, 'E1013: Argument 1: type mismatch, expected float but got number')
+ v9.CheckScriptFailure(lines, 'E1013: Argument 1: type mismatch, expected float but got string')
enddef
def Test_multiple_funcref()
diff --git a/src/version.c b/src/version.c
index f15061adc2..29c788d2b4 100644
--- a/src/version.c
+++ b/src/version.c
@@ -696,6 +696,8 @@ static char *(features[]) =
static int included_patches[] =
{ /* Add new patch number below this line */
/**/
+ 1224,
+/**/
1223,
/**/
1222,
diff --git a/src/vim9execute.c b/src/vim9execute.c
index d0dbefc43b..57f875de35 100644
--- a/src/vim9execute.c
+++ b/src/vim9execute.c
@@ -5822,12 +5822,25 @@ call_def_function(
}
else
{
- if (ufunc->uf_arg_types != NULL && idx < ufunc->uf_args.ga_len
- && check_typval_arg_type(
- ufunc->uf_arg_types[idx], tv,
+ int done = FALSE;
+ if (ufunc->uf_arg_types != NULL && idx < ufunc->uf_args.ga_len)
+ {
+ type_T *expected = ufunc->uf_arg_types[idx];
+ if (expected->tt_type == VAR_FLOAT && tv->v_type == VAR_NUMBER)
+ {
+ // When a float is expected and a number was given, convert
+ // the value.
+ STACK_TV_BOT(0)->v_type = VAR_FLOAT;
+ STACK_TV_BOT(0)->v_lock = 0;
+ STACK_TV_BOT(0)->vval.v_float = tv->vval.v_number;
+ done = TRUE;
+ }
+ else if (check_typval_arg_type(expected, tv,
NULL, argv_idx + 1) == FAIL)
- goto failed_early;
- copy_tv(tv, STACK_TV_BOT(0));
+ goto failed_early;
+ }
+ if (!done)
+ copy_tv(tv, STACK_TV_BOT(0));
}
++ectx.ec_stack.ga_len;
}
diff --git a/src/vim9type.c b/src/vim9type.c
index 08dabd1c22..61853956e8 100644
--- a/src/vim9type.c
+++ b/src/vim9type.c
@@ -628,12 +628,17 @@ typval2type(typval_T *tv, int copyID, garray_T *type_gap, int flags)
{
type_T *type = typval2type_int(tv, copyID, type_gap, flags);
- if (type != NULL && type != &t_bool
- && (tv->v_type == VAR_NUMBER
+ if (type != NULL)
+ {
+ if (type != &t_bool && (tv->v_type == VAR_NUMBER
&& (tv->vval.v_number == 0 || tv->vval.v_number == 1)))
- // Number 0 and 1 and expression with "&&" or "||" can also be used for
- // bool.
- type = &t_number_bool;
+ // Number 0 and 1 and expression with "&&" or "||" can also be used
+ // for bool.
+ type = &t_number_bool;
+ else if (type != &t_float && tv->v_type == VAR_NUMBER)
+ // A number can also be used for float.
+ type = &t_number_float;
+ }
return type;
}
@@ -821,9 +826,10 @@ check_type_maybe(
// Using number 0 or 1 for bool is OK.
return OK;
if (expected->tt_type == VAR_FLOAT
- && (expected->tt_flags & TTFLAG_NUMBER_OK)
- && actual->tt_type == VAR_NUMBER)
- // Using number where float is expected is OK here.
+ && actual->tt_type == VAR_NUMBER
+ && ((expected->tt_flags & TTFLAG_NUMBER_OK)
+ || (actual->tt_flags & TTFLAG_FLOAT_OK)))
+ // Using a number where a float is expected is OK here.
return OK;
if (give_msg)
type_mismatch_where(expected, actual, where);