diff --git a/src/comp/middle/trans.rs b/src/comp/middle/trans.rs index bc1d756c8f9..958b9e4cb59 100644 --- a/src/comp/middle/trans.rs +++ b/src/comp/middle/trans.rs @@ -4768,20 +4768,10 @@ fn trans_for_each(&@block_ctxt cx, &@ast::local local, &@ast::expr seq, // Step 3: Call iter passing [lliterbody, llenv], plus other args. alt (seq.node) { case (ast::expr_call(?f, ?args)) { - auto pair = alloca(cx, T_fn_pair(*lcx.ccx, iter_body_llty)); - auto code_cell = - cx.build.GEP(pair, ~[C_int(0), C_int(abi::fn_field_code)]); - cx.build.Store(lliterbody, code_cell); - auto env_cell = - cx.build.GEP(pair, ~[C_int(0), C_int(abi::fn_field_box)]); - auto llenvblobptr = - cx.build.PointerCast(llenvptr, - T_opaque_closure_ptr(*lcx.ccx)); - cx.build.Store(llenvblobptr, env_cell); - // log "lliterbody: " + val_str(lcx.ccx.tn, lliterbody); - - r = trans_call(cx, f, some[ValueRef](cx.build.Load(pair)), args, - seq.id); + auto pair = create_real_fn_pair(cx, iter_body_llty, + lliterbody, llenvptr); + r = trans_call(cx, f, some[ValueRef](cx.build.Load(pair)), + args, seq.id); ret rslt(r.bcx, C_nil()); } } @@ -8714,6 +8704,26 @@ fn create_fn_pair(&@crate_ctxt cx, str ps, TypeRef llfnty, ValueRef llfn, ret gvar; } +// Create a /real/ closure: this is like create_fn_pair, but creates a +// a fn value on the stack with a specified environment (which need not be +// on the stack). +fn create_real_fn_pair(&@block_ctxt cx, TypeRef llfnty, + ValueRef llfn, ValueRef llenvptr) -> ValueRef { + auto lcx = cx.fcx.lcx; + + auto pair = alloca(cx, T_fn_pair(*lcx.ccx, llfnty)); + auto code_cell = + cx.build.GEP(pair, ~[C_int(0), C_int(abi::fn_field_code)]); + cx.build.Store(llfn, code_cell); + auto env_cell = + cx.build.GEP(pair, ~[C_int(0), C_int(abi::fn_field_box)]); + auto llenvblobptr = + cx.build.PointerCast(llenvptr, + T_opaque_closure_ptr(*lcx.ccx)); + cx.build.Store(llenvblobptr, env_cell); + ret pair; +} + fn register_fn_pair(&@crate_ctxt cx, str ps, TypeRef llfnty, ValueRef llfn, ast::node_id id) { // FIXME: We should also hide the unexported pairs in crates.