1use crate::enums::subtyping_variance::SubtypingVariance;
3use crate::enums::value::Value;
4use crate::functions::flatten_type_pack::flatten_type_pack_id;
5use crate::functions::get_argument_index::get_argument_index;
6use crate::functions::get_parameter_extents::get_parameter_extents;
7use crate::functions::get_type_pack::get_type_pack_id;
8use crate::functions::is_path_on_argument_list::is_path_on_argument_list;
9use crate::functions::is_variadic_type_pack::is_variadic;
10use crate::functions::should_suppress_errors_type_utils_alt_b::should_suppress_errors_not_null_normalizer_type_pack_id;
11use crate::functions::traverse_for_flattened_pack::traverse_for_flattened_pack;
12use crate::functions::traverse_for_pack_type_path::traverse_for_pack;
13use crate::functions::traverse_type_path_alt_b::traverse as traverse_pack_root;
14use crate::functions::traverse_type_path_alt_c::traverse as traverse_type_root;
15use crate::records::count_mismatch::{CountMismatch, CountMismatchContext};
16use crate::records::function_type::FunctionType;
17use crate::records::generic_type_pack::GenericTypePack;
18use crate::records::internal_error::InternalError;
19use crate::records::normalization_too_complex::NormalizationTooComplex;
20use crate::records::overload_resolver::OverloadResolver;
21use crate::records::subtyping_reasoning::SubtypingReasoning;
22use crate::records::txn_log::TxnLog;
23use crate::records::type_error::TypeError;
24use crate::records::type_pack_mismatch::TypePackMismatch;
25use crate::type_aliases::error_vec::ErrorVec;
26use crate::type_aliases::module_name_type_fwd::ModuleName;
27use crate::type_aliases::type_error_data::TypeErrorData;
28use crate::type_aliases::type_id::TypeId;
29use crate::type_aliases::type_pack_id::TypePackId;
30use luaur_ast::records::ast_expr::AstExpr;
31use luaur_ast::records::location::Location;
32use luaur_common::macros::luau_assert::LUAU_ASSERT;
33
34impl OverloadResolver {
35 pub fn report_errors(
36 &self,
37 errors: &mut ErrorVec,
38 fn_ty: TypeId,
39 fn_location: Location,
40 module_name: &ModuleName,
41 arg_pack: TypePackId,
42 arg_exprs: &[*mut AstExpr],
43 reason: &SubtypingReasoning,
44 ) {
45 let argument_index = get_argument_index(&reason.sub_path, fn_ty);
46
47 let mut arg_location: Location;
48 if let Some(idx) = argument_index {
50 if idx < arg_exprs.len() {
51 arg_location = unsafe { (*arg_exprs[idx]).base.location };
52 } else if !arg_exprs.is_empty() {
53 arg_location = unsafe { (*arg_exprs[arg_exprs.len() - 1]).base.location };
55 } else {
56 arg_location = fn_location;
58 }
59 } else if !arg_exprs.is_empty() {
60 arg_location = unsafe { (*arg_exprs[arg_exprs.len() - 1]).base.location };
61 } else {
62 arg_location = fn_location;
63 }
64
65 let prospective_function = unsafe {
66 (*self.arena).add_type(FunctionType::function_type_new(
67 arg_pack,
68 (*self.builtin_types).anyTypePack,
69 None,
70 false,
71 ))
72 };
73
74 let failed_sub_pack: Option<TypePackId> = traverse_for_pack(
75 prospective_function,
76 &reason.super_path,
77 unsafe { &*self.builtin_types },
78 unsafe { &mut *self.arena },
79 );
80 let failed_super_pack: Option<TypePackId> = traverse_for_pack(
81 fn_ty,
82 &reason.sub_path,
83 unsafe { &*self.builtin_types },
84 unsafe { &mut *self.arena },
85 );
86
87 if let Some(fsp) = failed_super_pack {
88 if unsafe { !get_type_pack_id::<GenericTypePack>(fsp).is_null() } {
89 let given =
90 failed_sub_pack.unwrap_or(unsafe { (*self.builtin_types).emptyTypePack });
91 self.maybe_emplace_error_error_vec_location_module_name_subtyping_reasoning_optional_type_pack_id_optional_type_pack_id(
92 errors as *mut ErrorVec,
93 arg_location,
94 module_name,
95 reason as *const SubtypingReasoning,
96 failed_super_pack,
97 Some(given),
98 );
99 return;
100 }
101 }
102
103 if is_path_on_argument_list(&reason.sub_path) {
105 if failed_super_pack.is_none() {
116 errors.push(TypeError::type_error_location_module_name_type_error_data(
117 fn_location,
118 module_name.clone(),
119 TypeErrorData::InternalError(InternalError::new(
120 "Malformed SubtypingReasoning".to_string(),
121 )),
122 ));
123 return;
124 }
125
126 let required_mapped_args = unsafe {
127 (*self.arena).add_type_pack_t(traverse_for_flattened_pack(
128 fn_ty,
129 &reason.sub_path,
130 &*self.builtin_types,
131 &mut *self.arena,
132 ))
133 };
134 let (params_head, _params_tail) = flatten_type_pack_id(required_mapped_args);
135 let (arg_head, arg_tail) = flatten_type_pack_id(arg_pack);
136
137 let arg_count = arg_head.len();
138 let (_min_params, opt_max_params) =
139 get_parameter_extents(TxnLog::empty(), required_mapped_args, false);
140
141 match should_suppress_errors_not_null_normalizer_type_pack_id(self.normalizer, arg_pack)
142 .error_suppression_value()
143 {
144 Value::Suppress => return,
145 Value::NormalizationFailed => {
146 errors.push(TypeError::type_error_location_module_name_type_error_data(
147 fn_location,
148 module_name.clone(),
149 TypeErrorData::NormalizationTooComplex(NormalizationTooComplex {
150 _unused: None,
151 }),
152 ));
153 return;
154 }
155 Value::DoNotSuppress => {}
156 }
157
158 match should_suppress_errors_not_null_normalizer_type_pack_id(
160 self.normalizer,
161 required_mapped_args,
162 )
163 .error_suppression_value()
164 {
165 Value::Suppress => return,
166 Value::NormalizationFailed => {
167 errors.push(TypeError::type_error_location_module_name_type_error_data(
168 fn_location,
169 module_name.clone(),
170 TypeErrorData::NormalizationTooComplex(NormalizationTooComplex {
171 _unused: None,
172 }),
173 ));
174 return;
175 }
176 Value::DoNotSuppress => {}
177 }
178
179 let is_variadic_flag = match arg_tail {
180 Some(t) => is_variadic(t),
181 None => false,
182 };
183
184 if is_variadic_flag {
185 let given =
189 failed_sub_pack.unwrap_or(unsafe { (*self.builtin_types).emptyTypePack });
190 self.maybe_emplace_error_error_vec_location_module_name_subtyping_reasoning_optional_type_pack_id_optional_type_pack_id(
191 errors as *mut ErrorVec,
192 arg_location,
193 module_name,
194 reason as *const SubtypingReasoning,
195 failed_super_pack,
196 Some(given),
197 );
198 } else {
199 errors.push(TypeError::type_error_location_module_name_type_error_data(
200 fn_location,
201 module_name.clone(),
202 TypeErrorData::CountMismatch(CountMismatch {
203 expected: params_head.len(),
204 maximum: opt_max_params,
205 actual: arg_count,
206 context: CountMismatchContext::Arg,
207 is_variadic: is_variadic_flag,
208 function: alloc::string::String::new(),
209 }),
210 ));
211 }
212
213 return;
214 }
215
216 if let Some(idx) = argument_index {
217 if idx < arg_exprs.len() {
219 arg_location = unsafe { (*arg_exprs[idx]).base.location };
220 } else if !arg_exprs.is_empty() {
221 arg_location = unsafe { (*arg_exprs[arg_exprs.len() - 1]).base.location };
223 } else {
224 arg_location = fn_location;
226 }
227
228 LUAU_ASSERT!(reason.sub_path.components.len() > 1);
230 let mut super_path_tail = reason.super_path.clone();
231 super_path_tail.components.remove(0);
232
233 let failed_sub = traverse_pack_root(
234 arg_pack,
235 &super_path_tail,
236 unsafe { &*self.builtin_types },
237 unsafe { &mut *self.arena },
238 );
239 let failed_super = traverse_type_root(
240 fn_ty,
241 &reason.sub_path,
242 unsafe { &*self.builtin_types },
243 unsafe { &mut *self.arena },
244 );
245
246 self.maybe_emplace_error_error_vec_location_module_name_subtyping_reasoning_optional_type_or_pack_optional_type_or_pack(
247 errors as *mut ErrorVec,
248 arg_location,
249 module_name,
250 reason as *const SubtypingReasoning,
251 failed_super,
252 failed_sub,
253 );
254 return;
255 }
256
257 if let Some(fsp) = failed_sub_pack {
258 if failed_super_pack.is_none()
259 && unsafe { !get_type_pack_id::<GenericTypePack>(fsp).is_null() }
260 {
261 errors.push(TypeError::type_error_location_module_name_type_error_data(
262 arg_location,
263 module_name.clone(),
264 TypeErrorData::TypePackMismatch(TypePackMismatch {
265 wanted_tp: fsp,
266 given_tp: unsafe { (*self.builtin_types).emptyTypePack },
267 reason: alloc::string::String::new(),
268 }),
269 ));
270 }
271 }
272
273 if let (Some(fsp), Some(fsup)) = (failed_sub_pack, failed_super_pack) {
274 if arg_exprs.is_empty() {
278 arg_location = fn_location;
279 } else {
280 arg_location = unsafe { (*arg_exprs[arg_exprs.len() - 1]).base.location };
281 }
282
283 let error_suppression =
284 should_suppress_errors_not_null_normalizer_type_pack_id(self.normalizer, fsp)
285 .or_else(&should_suppress_errors_not_null_normalizer_type_pack_id(
286 self.normalizer,
287 fsup,
288 ));
289 if error_suppression.error_suppression_value() == Value::Suppress {
290 return;
291 }
292
293 match reason.variance {
294 SubtypingVariance::Covariant => {
295 errors.push(TypeError::type_error_location_module_name_type_error_data(
296 arg_location,
297 module_name.clone(),
298 TypeErrorData::TypePackMismatch(TypePackMismatch {
299 wanted_tp: fsp,
300 given_tp: fsup,
301 reason: alloc::string::String::new(),
302 }),
303 ));
304 }
305 SubtypingVariance::Contravariant => {
306 errors.push(TypeError::type_error_location_module_name_type_error_data(
307 arg_location,
308 module_name.clone(),
309 TypeErrorData::TypePackMismatch(TypePackMismatch {
310 wanted_tp: fsup,
311 given_tp: fsp,
312 reason: alloc::string::String::new(),
313 }),
314 ));
315 }
316 SubtypingVariance::Invariant => {
317 errors.push(TypeError::type_error_location_module_name_type_error_data(
318 arg_location,
319 module_name.clone(),
320 TypeErrorData::TypePackMismatch(TypePackMismatch {
321 wanted_tp: fsp,
322 given_tp: fsup,
323 reason: alloc::string::String::new(),
324 }),
325 ));
326 }
327 _ => {
328 LUAU_ASSERT!(false);
329 }
330 }
331 }
332 }
333}