cgen: fix closure code gen with if statement in definition (#12028)
parent
cb149bfa00
commit
60ecbec8ea
|
@ -425,20 +425,17 @@ fn (mut g Gen) gen_anon_fn(mut node ast.AnonFn) {
|
|||
return
|
||||
}
|
||||
// it may be possible to optimize `memdup` out if the closure never leaves current scope
|
||||
ctx_var := g.new_tmp_var()
|
||||
cur_line := g.go_before_stmt(0)
|
||||
ctx_struct := closure_ctx_struct(node.decl)
|
||||
g.writeln('$ctx_struct* $ctx_var = ($ctx_struct*) memdup(&($ctx_struct){')
|
||||
// TODO in case of an assignment, this should only call "__closure_set_data" and "__closure_set_function" (and free the former data)
|
||||
g.write('__closure_create($node.decl.name, ${node.decl.params.len + 1}, ')
|
||||
g.writeln('($ctx_struct*) memdup(&($ctx_struct){')
|
||||
g.indent++
|
||||
for var in node.inherited_vars {
|
||||
g.writeln('.$var.name = $var.name,')
|
||||
}
|
||||
g.indent--
|
||||
g.writeln('}, sizeof($ctx_struct));')
|
||||
g.write('}, sizeof($ctx_struct)))')
|
||||
g.empty_line = false
|
||||
g.write(cur_line)
|
||||
// TODO in case of an assignment, this should only call "__closure_set_data" and "__closure_set_function" (and free the former data)
|
||||
g.write('__closure_create($node.decl.name, ${node.decl.params.len + 1}, $ctx_var)')
|
||||
}
|
||||
|
||||
fn (mut g Gen) gen_anon_fn_decl(mut node ast.AnonFn) {
|
||||
|
|
|
@ -151,3 +151,20 @@ fn test_go_call_closure() {
|
|||
assert <-ch == 15
|
||||
}
|
||||
*/
|
||||
|
||||
fn test_closures_with_ifstmt() {
|
||||
a := 1
|
||||
f := fn [a] (x int) int {
|
||||
if a > x { return 1
|
||||
} else { return -1
|
||||
}
|
||||
}
|
||||
g := fn [a] () int {
|
||||
if true {
|
||||
return 1
|
||||
}
|
||||
return 0
|
||||
}
|
||||
assert f(0) == 1
|
||||
assert g() == 1
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue