mirror of
https://github.com/vlang/v.git
synced 2023-08-10 21:13:21 +03:00
ast, parser, cgen: fix closure with nested closure variable (#15542)
This commit is contained in:
parent
3af12271fb
commit
02a47f42f3
@ -644,6 +644,7 @@ pub:
|
||||
is_arg bool // fn args should not be autofreed
|
||||
is_auto_deref bool
|
||||
is_inherited bool
|
||||
has_inherited bool
|
||||
pub mut:
|
||||
expr Expr
|
||||
typ Type
|
||||
|
@ -460,7 +460,18 @@ fn (mut g Gen) gen_anon_fn(mut node ast.AnonFn) {
|
||||
g.write('__closure_create($fn_name, ($ctx_struct*) memdup_uncollectable(&($ctx_struct){')
|
||||
g.indent++
|
||||
for var in node.inherited_vars {
|
||||
g.writeln('.$var.name = $var.name,')
|
||||
mut has_inherited := false
|
||||
if obj := node.decl.scope.find(var.name) {
|
||||
if obj is ast.Var {
|
||||
if obj.has_inherited {
|
||||
has_inherited = true
|
||||
g.writeln('.$var.name = $c.closure_ctx->$var.name,')
|
||||
}
|
||||
}
|
||||
}
|
||||
if !has_inherited {
|
||||
g.writeln('.$var.name = $var.name,')
|
||||
}
|
||||
}
|
||||
g.indent--
|
||||
g.write('}, sizeof($ctx_struct)))')
|
||||
|
@ -1042,6 +1042,7 @@ fn (mut p Parser) closure_vars() []ast.Param {
|
||||
...(*var)
|
||||
pos: var_pos
|
||||
is_inherited: true
|
||||
has_inherited: var.is_inherited
|
||||
is_used: false
|
||||
is_changed: false
|
||||
is_mut: is_mut
|
||||
|
2
vlib/v/tests/inout/closure_with_nested_closure_var.out
Normal file
2
vlib/v/tests/inout/closure_with_nested_closure_var.out
Normal file
@ -0,0 +1,2 @@
|
||||
Test1{}, Test(Test1{})
|
||||
Test1{}, Test(Test1{})
|
23
vlib/v/tests/inout/closure_with_nested_closure_var.vv
Normal file
23
vlib/v/tests/inout/closure_with_nested_closure_var.vv
Normal file
@ -0,0 +1,23 @@
|
||||
module main
|
||||
|
||||
interface Test {
|
||||
test(fn (Test))
|
||||
}
|
||||
|
||||
struct Test1 {
|
||||
}
|
||||
|
||||
fn (t Test1) test(f fn (Test)) {
|
||||
f(Test(t))
|
||||
}
|
||||
|
||||
fn main() {
|
||||
t := Test1{}
|
||||
|
||||
t.test(fn [t] (t1 Test) {
|
||||
println('$t, $t1')
|
||||
t.test(fn [t] (t2 Test) {
|
||||
println('$t, $t2')
|
||||
})
|
||||
})
|
||||
}
|
Loading…
Reference in New Issue
Block a user