diff options
| author | Michael Sullivan <sully@msully.net> | 2011-06-29 18:44:38 -0700 |
|---|---|---|
| committer | Michael Sullivan <sully@msully.net> | 2011-07-14 18:45:01 -0500 |
| commit | 759317ca8bf3d2997b5a0973679d9c7bae063e15 (patch) | |
| tree | d0ce70066269d4c7699784bdac68e9dbe17e72e6 /src/comp | |
| parent | 0957525cc67abd582cecf82486c9955268b3a9ec (diff) | |
| download | rust-759317ca8bf3d2997b5a0973679d9c7bae063e15.tar.gz rust-759317ca8bf3d2997b5a0973679d9c7bae063e15.zip | |
Factor out closure construction from trans_for_each.
Diffstat (limited to 'src/comp')
| -rw-r--r-- | src/comp/middle/trans.rs | 38 |
1 files changed, 24 insertions, 14 deletions
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. |
