From 28d61f4dfab52f4687236234039a217e612be9f7 Mon Sep 17 00:00:00 2001 From: kbkpbot Date: Sat, 28 Feb 2026 09:18:49 +0800 Subject: [PATCH] checker:fix compiler panic on wrong arg count with or block (#26665) --- vlib/v/checker/fn.v | 15 ++++++++++++--- .../tests/method_call_on_undefined_err.out | 7 ------- .../wrong_arg_count_with_or_block_no_panic.out | 16 ++++++++++++++++ .../wrong_arg_count_with_or_block_no_panic.vv | 15 +++++++++++++++ 4 files changed, 43 insertions(+), 10 deletions(-) create mode 100644 vlib/v/checker/tests/wrong_arg_count_with_or_block_no_panic.out create mode 100644 vlib/v/checker/tests/wrong_arg_count_with_or_block_no_panic.vv diff --git a/vlib/v/checker/fn.v b/vlib/v/checker/fn.v index b1338fc25..616295460 100644 --- a/vlib/v/checker/fn.v +++ b/vlib/v/checker/fn.v @@ -1517,7 +1517,10 @@ fn (mut c Checker) fn_call(mut node ast.CallExpr, mut continue_check &bool) ast. } } } - c.check_expected_arg_count(mut node, func) or { return func.return_type } + c.check_expected_arg_count(mut node, func) or { + node.return_type = func.return_type + return func.return_type + } } // println / eprintln / panic can print anything if args_len > 0 && fn_name in print_everything_fns { @@ -2358,7 +2361,10 @@ fn (mut c Checker) method_call(mut node ast.CallExpr, mut continue_check &bool) node.is_field = true info := field_sym.info as ast.FnType - c.check_expected_arg_count(mut node, info.func) or { return info.func.return_type } + c.check_expected_arg_count(mut node, info.func) or { + node.return_type = info.func.return_type + return info.func.return_type + } node.return_type = info.func.return_type mut earg_types := []ast.Type{} @@ -2546,7 +2552,10 @@ fn (mut c Checker) method_call(mut node ast.CallExpr, mut continue_check &bool) && method.ctdefine_idx != ast.invalid_type_idx { node.should_be_skipped = c.evaluate_once_comptime_if_attribute(mut method.attrs[method.ctdefine_idx]) } - c.check_expected_arg_count(mut node, method) or { return method.return_type } + c.check_expected_arg_count(mut node, method) or { + node.return_type = method.return_type + return method.return_type + } mut exp_arg_typ := ast.no_type // type of 1st arg for special builtin methods mut param_is_mut := false mut no_type_promotion := false diff --git a/vlib/v/checker/tests/method_call_on_undefined_err.out b/vlib/v/checker/tests/method_call_on_undefined_err.out index 6b8f5d36d..27e132e4b 100644 --- a/vlib/v/checker/tests/method_call_on_undefined_err.out +++ b/vlib/v/checker/tests/method_call_on_undefined_err.out @@ -56,10 +56,3 @@ vlib/v/checker/tests/method_call_on_undefined_err.vv:14:13: error: expected 0 ar 16 | exit(1) Details: have (string) want () -vlib/v/checker/tests/method_call_on_undefined_err.vv:14:31: error: unexpected `or` block, the function `foo` does not return an Option or a Result - 12 | - 13 | fn main() { - 14 | res := foo('fe80::1234%ne0') or { - | ~~~~ - 15 | eprintln(err) - 16 | exit(1) diff --git a/vlib/v/checker/tests/wrong_arg_count_with_or_block_no_panic.out b/vlib/v/checker/tests/wrong_arg_count_with_or_block_no_panic.out new file mode 100644 index 000000000..b1078aa54 --- /dev/null +++ b/vlib/v/checker/tests/wrong_arg_count_with_or_block_no_panic.out @@ -0,0 +1,16 @@ +vlib/v/checker/tests/wrong_arg_count_with_or_block_no_panic.vv:9:6: notice: condition is always true + 7 | // Test case: function with no params, called with extra args and or block with if-else + 8 | foo(1, 2, 3) or { + 9 | if true { + | ~~~~ + 10 | println('error') + 11 | } else { +vlib/v/checker/tests/wrong_arg_count_with_or_block_no_panic.vv:8:6: error: expected 0 arguments, but got 3 + 6 | fn main() { + 7 | // Test case: function with no params, called with extra args and or block with if-else + 8 | foo(1, 2, 3) or { + | ~~~~~~~ + 9 | if true { + 10 | println('error') +Details: have (int literal, int literal, int literal) + want () diff --git a/vlib/v/checker/tests/wrong_arg_count_with_or_block_no_panic.vv b/vlib/v/checker/tests/wrong_arg_count_with_or_block_no_panic.vv new file mode 100644 index 000000000..9c60e4b00 --- /dev/null +++ b/vlib/v/checker/tests/wrong_arg_count_with_or_block_no_panic.vv @@ -0,0 +1,15 @@ +// Test that wrong argument count with or block containing if-else +// does not cause compiler panic (issue #26647) +fn foo() ! { +} + +fn main() { + // Test case: function with no params, called with extra args and or block with if-else + foo(1, 2, 3) or { + if true { + println('error') + } else { + println('other') + } + } +} -- 2.39.5