Skip to content

Commit

Permalink
checker: fix index expr that left is if expr (fix #22654) (#22661)
Browse files Browse the repository at this point in the history
  • Loading branch information
yuyi98 authored Oct 27, 2024
1 parent d7d88b9 commit e59115e
Show file tree
Hide file tree
Showing 5 changed files with 41 additions and 2 deletions.
7 changes: 7 additions & 0 deletions vlib/v/checker/checker.v
Original file line number Diff line number Diff line change
Expand Up @@ -1006,6 +1006,13 @@ fn (mut c Checker) fail_if_immutable(mut expr ast.Expr) (string, token.Pos) {
ast.InfixExpr {
return '', expr.pos
}
ast.IfExpr {
for mut branch in expr.branches {
mut last_expr := (branch.stmts.last() as ast.ExprStmt).expr
c.fail_if_immutable(mut last_expr)
}
return '', expr.pos
}
else {
if !expr.is_pure_literal() {
c.error('unexpected expression `${expr.type_name()}`', expr.pos())
Expand Down
14 changes: 14 additions & 0 deletions vlib/v/checker/tests/immutable_array_in_if_expr_index.out
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
vlib/v/checker/tests/immutable_array_in_if_expr_index.vv:4:13: error: `array_a` is immutable, declare it with `mut` to make it mutable
2 | array_a := [1, 2, 3]
3 | array_b := [4, 5, 6]
4 | (if true { array_a } else { array_b })[0] = 999
| ~~~~~~~
5 | println(array_a)
6 | }
vlib/v/checker/tests/immutable_array_in_if_expr_index.vv:4:30: error: `array_b` is immutable, declare it with `mut` to make it mutable
2 | array_a := [1, 2, 3]
3 | array_b := [4, 5, 6]
4 | (if true { array_a } else { array_b })[0] = 999
| ~~~~~~~
5 | println(array_a)
6 | }
6 changes: 6 additions & 0 deletions vlib/v/checker/tests/immutable_array_in_if_expr_index.vv
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
fn main() {
array_a := [1, 2, 3]
array_b := [4, 5, 6]
(if true { array_a } else { array_b })[0] = 999
println(array_a)
}
4 changes: 2 additions & 2 deletions vlib/v/gen/c/if.v
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,8 @@ module c
import v.ast

fn (mut g Gen) need_tmp_var_in_if(node ast.IfExpr) bool {
if node.is_expr && g.inside_ternary == 0 {
if g.is_autofree || node.typ.has_option_or_result() || node.is_comptime {
if node.is_expr && (g.inside_ternary == 0 || g.is_assign_lhs) {
if g.is_autofree || node.typ.has_option_or_result() || node.is_comptime || g.is_assign_lhs {
return true
}
for branch in node.branches {
Expand Down
12 changes: 12 additions & 0 deletions vlib/v/tests/indexexpr_with_if_expr_test.v
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
fn test_indexexpr_with_if_expr() {
mut array_a := [1, 2, 3]
mut array_b := [4, 5, 6]

(if true {
array_a
} else {
array_b
})[0] = 999
println(array_a)
assert array_a == [999, 2, 3]
}

0 comments on commit e59115e

Please sign in to comment.