(
meta: &mut ParserMetadata,
id: usize,
fun: FunctionDecl,
args: &[Type],
vars: &[bool],
tok: Option<Token>,
)
| 192 | } |
| 193 | |
| 194 | pub fn handle_function_parameters( |
| 195 | meta: &mut ParserMetadata, |
| 196 | id: usize, |
| 197 | fun: FunctionDecl, |
| 198 | args: &[Type], |
| 199 | vars: &[bool], |
| 200 | tok: Option<Token>, |
| 201 | ) -> Result<(Type, usize), Failure> { |
| 202 | // Check if the function arguments that are references are passed as variables and not as values |
| 203 | for (index, (arg, var)) in izip!(fun.args.iter(), vars.iter()).enumerate() { |
| 204 | let is_ref = arg.is_ref; |
| 205 | let arg_name = &arg.name; |
| 206 | if is_ref && !var { |
| 207 | let fun_name = &fun.name; |
| 208 | let ordinal = ordinal_number(index); |
| 209 | return error!(meta, tok, format!("Cannot pass {ordinal} argument '{arg_name}' as a reference to the function '{fun_name}' because it is not a variable")); |
| 210 | } |
| 211 | } |
| 212 | |
| 213 | // On first invocation, run first-pass with declared types (or Generic) to emit correct warnings. |
| 214 | if !meta.fun_cache.is_first_pass_done(id) { |
| 215 | let declared_types: Vec<Type> = fun.args.iter().map(|arg| arg.kind.clone()).collect(); |
| 216 | // We set persist to false, because we don't want to cache the function instance |
| 217 | let _ = meta.with_first_pass_ctx(true, |meta| { |
| 218 | run_function_with_args(meta, fun.clone(), &declared_types, tok.clone(), false) |
| 219 | }); |
| 220 | meta.fun_cache.set_first_pass_done(id); |
| 221 | } |
| 222 | |
| 223 | // If the function was previously called with the same arguments, return the cached variant |
| 224 | let result = match meta |
| 225 | .fun_cache |
| 226 | .get_instances(id) |
| 227 | .unwrap() |
| 228 | .iter() |
| 229 | .find(|fun| fun.args == args) |
| 230 | { |
| 231 | Some(fun) => Ok((fun.returns.clone(), fun.variant_id)), |
| 232 | None => Ok(run_function_with_args( |
| 233 | meta, |
| 234 | fun, |
| 235 | args, |
| 236 | tok, |
| 237 | !meta.first_pass_ctx, |
| 238 | )?), |
| 239 | }; |
| 240 | |
| 241 | result |
| 242 | } |
| 243 | |
| 244 | fn handle_similar_function(meta: &ParserMetadata, name: &str) -> Option<String> { |
| 245 | let vars = Vec::from_iter(meta.get_fun_names()); |
no test coverage detected