@@ -2704,7 +2704,10 @@ fn trans_args(@block_ctxt cx,
2704
2704
2705
2705
// Arg 0: Output pointer.
2706
2706
auto retty = ty. ty_fn_ret( fn_ty) ;
2707
- auto llretslot = cx. build. Alloca ( type_of( cx. fcx. ccx, retty) ) ;
2707
+ auto llretslot_res = alloc_ty( bcx, retty) ;
2708
+ bcx = llretslot_res. bcx;
2709
+ auto llretslot = llretslot_res. val;
2710
+
2708
2711
alt ( gen) {
2709
2712
case ( some[ generic_info] ( ?g) ) {
2710
2713
lltydescs = g. tydescs;
@@ -2715,30 +2718,30 @@ fn trans_args(@block_ctxt cx,
2715
2718
}
2716
2719
}
2717
2720
if ( ty. type_has_dynamic_size( retty) ) {
2718
- llargs += cx . build. PointerCast ( llretslot, T_typaram_ptr ( ) ) ;
2721
+ llargs += bcx . build. PointerCast ( llretslot, T_typaram_ptr ( ) ) ;
2719
2722
} else if ( ty. count_ty_params( retty) != 0 u) {
2720
2723
// It's possible that the callee has some generic-ness somewhere in
2721
2724
// its return value -- say a method signature within an obj or a fn
2722
2725
// type deep in a structure -- which the caller has a concrete view
2723
2726
// of. If so, cast the caller's view of the restlot to the callee's
2724
2727
// view, for the sake of making a type-compatible call.
2725
2728
llargs += cx. build. PointerCast ( llretslot,
2726
- T_ptr ( type_of( cx . fcx. ccx, retty) ) ) ;
2729
+ T_ptr ( type_of( bcx . fcx. ccx, retty) ) ) ;
2727
2730
} else {
2728
2731
llargs += llretslot;
2729
2732
}
2730
2733
2731
2734
2732
2735
// Arg 1: Task pointer.
2733
- llargs += cx . fcx. lltaskptr;
2736
+ llargs += bcx . fcx. lltaskptr;
2734
2737
2735
2738
// Arg 2: Env (closure-bindings / self-obj)
2736
2739
alt ( llobj) {
2737
2740
case ( some[ ValueRef ] ( ?ob) ) {
2738
2741
// Every object is always found in memory,
2739
2742
// and not-yet-loaded (as part of an lval x.y
2740
2743
// doted method-call).
2741
- llargs += cx . build. Load ( ob) ;
2744
+ llargs += bcx . build. Load ( ob) ;
2742
2745
}
2743
2746
case ( _) {
2744
2747
llargs += llenv;
@@ -2848,25 +2851,32 @@ fn trans_call(@block_ctxt cx, @ast.expr f,
2848
2851
find_scope_cx ( cx) . cleanups += clean ( bind drop_ty ( _, retval, ret_ty) ) ;
2849
2852
}
2850
2853
2854
+ // log "call-result type: " + val_str(retval);
2851
2855
ret res( bcx, retval) ;
2852
2856
}
2853
2857
2854
2858
fn trans_tup ( @block_ctxt cx , vec[ ast. elt] elts ,
2855
2859
& ast. ann ann ) -> result {
2856
- auto t = node_ann_type ( cx. fcx . ccx , ann) ;
2857
- auto llty = type_of ( cx. fcx . ccx , t) ;
2858
- auto tup_val = cx. build . Alloca ( llty) ;
2860
+ auto bcx = cx;
2861
+ auto t = node_ann_type ( bcx. fcx . ccx , ann) ;
2862
+ auto llty = type_of ( bcx. fcx . ccx , t) ;
2863
+ auto tup_res = alloc_ty ( bcx, t) ;
2864
+ auto tup_val = tup_res. val ;
2865
+ bcx = tup_res. bcx ;
2866
+
2859
2867
find_scope_cx ( cx) . cleanups += clean ( bind drop_ty ( _, tup_val, t) ) ;
2860
2868
let int i = 0 ;
2861
- auto r = res ( cx , C_nil ( ) ) ;
2869
+
2862
2870
for ( ast. elt e in elts) {
2863
- auto t = ty. expr_ty( e. expr) ;
2864
- auto src_res = trans_expr( r. bcx, e. expr) ;
2865
- auto dst_elt = r. bcx. build. GEP ( tup_val, vec( C_int ( 0 ) , C_int ( i) ) ) ;
2866
- r = copy_ty( src_res. bcx, INIT , dst_elt, src_res. val, t) ;
2871
+ auto e_ty = ty. expr_ty( e. expr) ;
2872
+ auto src_res = trans_expr( bcx, e. expr) ;
2873
+ bcx = src_res. bcx;
2874
+ auto dst_res = GEP_tup_like ( bcx, t, tup_val, vec( 0 , i) ) ;
2875
+ bcx = dst_res. bcx;
2876
+ bcx = copy_ty( src_res. bcx, INIT , dst_res. val, src_res. val, e_ty) . bcx;
2867
2877
i += 1 ;
2868
2878
}
2869
- ret res( r . bcx, tup_val) ;
2879
+ ret res( bcx, tup_val) ;
2870
2880
}
2871
2881
2872
2882
fn trans_vec( @block_ctxt cx, vec[ @ast. expr] args,
@@ -2891,44 +2901,58 @@ fn trans_vec(@block_ctxt cx, vec[@ast.expr] args,
2891
2901
2892
2902
// FIXME: pass tydesc properly.
2893
2903
auto sub = trans_upcall( bcx, "upcall_new_vec" , vec( data_sz, C_int ( 0 ) ) ) ;
2904
+ bcx = sub. bcx;
2894
2905
2895
2906
auto llty = type_of( bcx. fcx. ccx, t) ;
2896
- auto vec_val = sub . bcx. build. IntToPtr ( sub. val, llty) ;
2907
+ auto vec_val = bcx. build. IntToPtr ( sub. val, llty) ;
2897
2908
find_scope_cx( bcx) . cleanups += clean( bind drop_ty( _, vec_val, t) ) ;
2898
2909
2899
- auto body = sub. bcx. build. GEP ( vec_val, vec( C_int ( 0 ) ,
2900
- C_int ( abi. vec_elt_data) ) ) ;
2910
+ auto body = bcx. build. GEP ( vec_val, vec( C_int ( 0 ) ,
2911
+ C_int ( abi. vec_elt_data) ) ) ;
2912
+
2913
+ auto pseudo_tup_ty =
2914
+ plain_ty( ty. ty_tup( _vec. init_elt[ @ty. t] ( unit_ty,
2915
+ _vec. len[ @ast. expr] ( args) ) ) ) ;
2901
2916
let int i = 0 ;
2917
+
2902
2918
for ( @ast. expr e in args) {
2903
- auto src_res = trans_expr( sub. bcx, e) ;
2904
- auto dst_elt = sub. bcx. build. GEP ( body, vec( C_int ( 0 ) , C_int ( i) ) ) ;
2905
- sub = copy_ty( src_res. bcx, INIT , dst_elt, src_res. val, unit_ty) ;
2919
+ auto src_res = trans_expr( bcx, e) ;
2920
+ bcx = src_res. bcx;
2921
+ auto dst_res = GEP_tup_like ( bcx, pseudo_tup_ty, body, vec( 0 , i) ) ;
2922
+ bcx = dst_res. bcx;
2923
+ bcx = copy_ty( bcx, INIT , dst_res. val, src_res. val, unit_ty) . bcx;
2906
2924
i += 1 ;
2907
2925
}
2908
- auto fill = sub . bcx. build. GEP ( vec_val,
2909
- vec( C_int ( 0 ) , C_int ( abi. vec_elt_fill) ) ) ;
2910
- sub . bcx. build. Store ( data_sz, fill) ;
2926
+ auto fill = bcx. build. GEP ( vec_val,
2927
+ vec( C_int ( 0 ) , C_int ( abi. vec_elt_fill) ) ) ;
2928
+ bcx. build. Store ( data_sz, fill) ;
2911
2929
2912
- ret res( sub . bcx, vec_val) ;
2930
+ ret res( bcx, vec_val) ;
2913
2931
}
2914
2932
2915
2933
fn trans_rec( @block_ctxt cx, vec[ ast. field] fields,
2916
2934
& ast. ann ann) -> result {
2917
- auto t = node_ann_type( cx. fcx. ccx, ann) ;
2918
- auto llty = type_of( cx. fcx. ccx, t) ;
2919
- auto rec_val = cx. build. Alloca ( llty) ;
2935
+
2936
+ auto bcx = cx;
2937
+ auto t = node_ann_type( bcx. fcx. ccx, ann) ;
2938
+ auto llty = type_of( bcx. fcx. ccx, t) ;
2939
+ auto rec_res = alloc_ty( bcx, t) ;
2940
+ auto rec_val = rec_res. val;
2941
+ bcx = rec_res. bcx;
2942
+
2920
2943
find_scope_cx( cx) . cleanups += clean( bind drop_ty( _, rec_val, t) ) ;
2921
2944
let int i = 0 ;
2922
- auto r = res ( cx , C_nil ( ) ) ;
2945
+
2923
2946
for ( ast. field f in fields) {
2924
- auto t = ty. expr_ty( f. expr) ;
2925
- auto src_res = trans_expr( r. bcx, f. expr) ;
2926
- auto dst_elt = r. bcx. build. GEP ( rec_val, vec( C_int( 0 ) , C_int ( i) ) ) ;
2927
- // FIXME: calculate copy init-ness in typestate.
2928
- r = copy_ty( src_res. bcx, INIT, dst_elt, src_res. val, t) ;
2947
+ auto e_ty = ty. expr_ty( f. expr) ;
2948
+ auto src_res = trans_expr( bcx, f. expr) ;
2949
+ bcx = src_res. bcx;
2950
+ auto dst_res = GEP_tup_like ( bcx, t, rec_val, vec( 0 , i) ) ;
2951
+ bcx = dst_res. bcx;
2952
+ bcx = copy_ty( src_res. bcx, INIT, dst_res. val, src_res. val, e_ty) . bcx;
2929
2953
i += 1 ;
2930
2954
}
2931
- ret res( r . bcx, rec_val) ;
2955
+ ret res( bcx, rec_val) ;
2932
2956
}
2933
2957
2934
2958
@@ -3300,8 +3324,7 @@ iter block_locals(&ast.block b) -> @ast.local {
3300
3324
}
3301
3325
}
3302
3326
3303
- fn alloc_local( @block_ctxt cx, @ast. local local) -> result {
3304
- auto t = node_ann_type( cx. fcx. ccx, local. ann) ;
3327
+ fn alloc_ty( @block_ctxt cx, @ty. t t) -> result {
3305
3328
auto val = C_int ( 0 ) ;
3306
3329
auto bcx = cx;
3307
3330
if ( ty. type_has_dynamic_size( t) ) {
@@ -3311,10 +3334,16 @@ fn alloc_local(@block_ctxt cx, @ast.local local) -> result {
3311
3334
} else {
3312
3335
val = bcx. build. Alloca ( type_of( cx. fcx. ccx, t) ) ;
3313
3336
}
3314
- bcx. fcx. lllocals. insert( local. id, val) ;
3315
3337
ret res( bcx, val) ;
3316
3338
}
3317
3339
3340
+ fn alloc_local( @block_ctxt cx, @ast. local local) -> result {
3341
+ auto t = node_ann_type( cx. fcx. ccx, local. ann) ;
3342
+ auto r = alloc_ty( cx, t) ;
3343
+ r. bcx. fcx. lllocals. insert( local. id, r. val) ;
3344
+ ret r;
3345
+ }
3346
+
3318
3347
fn trans_block( @block_ctxt cx, & ast. block b) -> result {
3319
3348
auto bcx = cx;
3320
3349
0 commit comments