Mercurial > vim
comparison src/vim9compile.c @ 25547:ec4df0b982da v8.2.3310
patch 8.2.3310: Vim9: unpack assignment does not mention source of type error
Commit: https://github.com/vim/vim/commit/4270d8b7626ff8a7006f6a09c89bc446a3f89d1e
Author: Bram Moolenaar <Bram@vim.org>
Date: Sat Aug 7 16:30:42 2021 +0200
patch 8.2.3310: Vim9: unpack assignment does not mention source of type error
Problem: Vim9: unpack assignment does not mention source of type error.
Solution: Mention the argument number. (closes https://github.com/vim/vim/issues/8719)
author | Bram Moolenaar <Bram@vim.org> |
---|---|
date | Sat, 07 Aug 2021 16:45:03 +0200 |
parents | 2ae1d5a4ae5c |
children | 5ab75ca75d21 |
comparison
equal
deleted
inserted
replaced
25546:465989ba8936 | 25547:ec4df0b982da |
---|---|
1037 * - "actual" is a type that can be "expected" type: add a runtime check; or | 1037 * - "actual" is a type that can be "expected" type: add a runtime check; or |
1038 * - return FAIL. | 1038 * - return FAIL. |
1039 * If "actual_is_const" is TRUE then the type won't change at runtime, do not | 1039 * If "actual_is_const" is TRUE then the type won't change at runtime, do not |
1040 * generate a TYPECHECK. | 1040 * generate a TYPECHECK. |
1041 */ | 1041 */ |
1042 static int | |
1043 need_type_where( | |
1044 type_T *actual, | |
1045 type_T *expected, | |
1046 int offset, | |
1047 where_T where, | |
1048 cctx_T *cctx, | |
1049 int silent, | |
1050 int actual_is_const) | |
1051 { | |
1052 if (expected == &t_bool && actual != &t_bool | |
1053 && (actual->tt_flags & TTFLAG_BOOL_OK)) | |
1054 { | |
1055 // Using "0", "1" or the result of an expression with "&&" or "||" as a | |
1056 // boolean is OK but requires a conversion. | |
1057 generate_2BOOL(cctx, FALSE, offset); | |
1058 return OK; | |
1059 } | |
1060 | |
1061 if (check_type(expected, actual, FALSE, where) == OK) | |
1062 return OK; | |
1063 | |
1064 // If the actual type can be the expected type add a runtime check. | |
1065 // If it's a constant a runtime check makes no sense. | |
1066 if ((!actual_is_const || actual == &t_any) | |
1067 && use_typecheck(actual, expected)) | |
1068 { | |
1069 generate_TYPECHECK(cctx, expected, offset, where.wt_index); | |
1070 return OK; | |
1071 } | |
1072 | |
1073 if (!silent) | |
1074 type_mismatch_where(expected, actual, where); | |
1075 return FAIL; | |
1076 } | |
1077 | |
1042 int | 1078 int |
1043 need_type( | 1079 need_type( |
1044 type_T *actual, | 1080 type_T *actual, |
1045 type_T *expected, | 1081 type_T *expected, |
1046 int offset, | 1082 int offset, |
1049 int silent, | 1085 int silent, |
1050 int actual_is_const) | 1086 int actual_is_const) |
1051 { | 1087 { |
1052 where_T where = WHERE_INIT; | 1088 where_T where = WHERE_INIT; |
1053 | 1089 |
1054 if (expected == &t_bool && actual != &t_bool | |
1055 && (actual->tt_flags & TTFLAG_BOOL_OK)) | |
1056 { | |
1057 // Using "0", "1" or the result of an expression with "&&" or "||" as a | |
1058 // boolean is OK but requires a conversion. | |
1059 generate_2BOOL(cctx, FALSE, offset); | |
1060 return OK; | |
1061 } | |
1062 | |
1063 where.wt_index = arg_idx; | 1090 where.wt_index = arg_idx; |
1064 if (check_type(expected, actual, FALSE, where) == OK) | 1091 return need_type_where(actual, expected, offset, where, |
1065 return OK; | 1092 cctx, silent, actual_is_const); |
1066 | |
1067 // If the actual type can be the expected type add a runtime check. | |
1068 // If it's a constant a runtime check makes no sense. | |
1069 if ((!actual_is_const || actual == &t_any) | |
1070 && use_typecheck(actual, expected)) | |
1071 { | |
1072 generate_TYPECHECK(cctx, expected, offset, arg_idx); | |
1073 return OK; | |
1074 } | |
1075 | |
1076 if (!silent) | |
1077 arg_type_mismatch(expected, actual, arg_idx); | |
1078 return FAIL; | |
1079 } | 1093 } |
1080 | 1094 |
1081 /* | 1095 /* |
1082 * Check that the top of the type stack has a type that can be used as a | 1096 * Check that the top of the type stack has a type that can be used as a |
1083 * condition. Give an error and return FAIL if not. | 1097 * condition. Give an error and return FAIL if not. |
7002 } | 7016 } |
7003 } | 7017 } |
7004 else if (*op == '=') | 7018 else if (*op == '=') |
7005 { | 7019 { |
7006 type_T *use_type = lhs.lhs_lvar->lv_type; | 7020 type_T *use_type = lhs.lhs_lvar->lv_type; |
7021 where_T where = WHERE_INIT; | |
7007 | 7022 |
7008 // Without operator check type here, otherwise below. | 7023 // Without operator check type here, otherwise below. |
7009 // Use the line number of the assignment. | 7024 // Use the line number of the assignment. |
7010 SOURCING_LNUM = start_lnum; | 7025 SOURCING_LNUM = start_lnum; |
7026 where.wt_index = var_count > 0 ? var_idx + 1 : 0; | |
7027 where.wt_variable = var_count > 0; | |
7011 if (lhs.lhs_has_index) | 7028 if (lhs.lhs_has_index) |
7012 use_type = lhs.lhs_member_type; | 7029 use_type = lhs.lhs_member_type; |
7013 if (need_type(rhs_type, use_type, -1, 0, cctx, | 7030 if (need_type_where(rhs_type, use_type, -1, where, |
7014 FALSE, is_const) == FAIL) | 7031 cctx, FALSE, is_const) == FAIL) |
7015 goto theend; | 7032 goto theend; |
7016 } | 7033 } |
7017 } | 7034 } |
7018 else | 7035 else |
7019 { | 7036 { |