aboutsummaryrefslogtreecommitdiff
path: root/src/boot
diff options
context:
space:
mode:
authorGraydon Hoare <[email protected]>2010-10-13 15:53:38 -0700
committerGraydon Hoare <[email protected]>2010-10-13 15:53:38 -0700
commit52c2a1549c2dda91d147d20edd62f6465b90d9e4 (patch)
tree00e93fcc2a7b2c348c2beaec5c85391943b6c089 /src/boot
parentUse "friendly" types throughout the typechecker (diff)
downloadrust-52c2a1549c2dda91d147d20edd62f6465b90d9e4.tar.xz
rust-52c2a1549c2dda91d147d20edd62f6465b90d9e4.zip
Fetch typarams from the outermost item frame, when inside an iter-block. One less crash in rustc.
Diffstat (limited to 'src/boot')
-rw-r--r--src/boot/me/semant.ml8
-rw-r--r--src/boot/me/trans.ml80
2 files changed, 58 insertions, 30 deletions
diff --git a/src/boot/me/semant.ml b/src/boot/me/semant.ml
index c8b3b45e..8ff439e8 100644
--- a/src/boot/me/semant.ml
+++ b/src/boot/me/semant.ml
@@ -495,12 +495,18 @@ let get_callsz (cx:ctxt) (id:node_id) : size =
else bugi cx id "missing callsz"
;;
+let get_loop_outermost_fn (cx:ctxt) (id:node_id) : node_id =
+ match Hashtbl.find cx.ctxt_all_defns id with
+ DEFN_loop_body fnid -> fnid
+ | _ -> bugi cx id "get_loop_outermost_fn on non-loop"
+;;
+
let rec n_item_ty_params (cx:ctxt) (id:node_id) : int =
match Hashtbl.find cx.ctxt_all_defns id with
DEFN_item i -> Array.length i.Ast.decl_params
| DEFN_obj_fn (oid,_) -> n_item_ty_params cx oid
| DEFN_obj_drop oid -> n_item_ty_params cx oid
- | DEFN_loop_body fid -> n_item_ty_params cx fid
+ | DEFN_loop_body _ -> 0
| _ -> bugi cx id "n_item_ty_params on non-item"
;;
diff --git a/src/boot/me/trans.ml b/src/boot/me/trans.ml
index 67a96030..edbfd06e 100644
--- a/src/boot/me/trans.ml
+++ b/src/boot/me/trans.ml
@@ -624,10 +624,61 @@ let trans_visitor
Abi.iterator_args_elt_outer_frame_ptr
in
+ (*
+ * Within a for-each block, calculate the fp of an enclosing for-each block
+ * or the enclosing function by chasing static links.
+ *)
+ let get_nth_outer_frame_ptr (diff:int) : Il.cell =
+ (* All for-each block frames have the same args. *)
+ let block_args_rty = current_fn_args_rty None in
+ let current_fp = Il.Reg (abi.Abi.abi_fp_reg, Il.AddrTy Il.OpaqueTy) in
+ let rec out (n:int) (fp:Il.cell) : Il.cell =
+ if n == 0
+ then fp
+ else
+ let args = fp_to_args fp block_args_rty in
+ let iter_args = get_element_ptr args Abi.calltup_elt_iterator_args in
+ let outer_fp =
+ get_element_ptr iter_args Abi.iterator_args_elt_outer_frame_ptr
+ in
+ out (n - 1) outer_fp
+ in
+ out diff current_fp
+ in
+
+ let curr_stmt_depth _ =
+ if (Stack.is_empty curr_stmt)
+ then None
+ else
+ Some
+ (get_stmt_depth cx (Stack.top curr_stmt))
+ in
+
let get_ty_params_of_current_frame _ : Il.cell =
let fnid = current_fn() in
let n_ty_params = n_item_ty_params cx fnid in
+ let local _ =
get_ty_params_of_frame fnid abi.Abi.abi_fp_reg n_ty_params
+ in
+ if Hashtbl.mem cx.ctxt_block_is_loop_body fnid
+ then
+ begin
+ let outermost_fnid = get_loop_outermost_fn cx fnid in
+ match curr_stmt_depth() with
+ None -> local()
+ | Some depth ->
+ iflog (fun _ ->
+ annotate "loading outermost frame ty params");
+ let (outermost_fp, _) =
+ force_to_reg (Il.Cell (get_nth_outer_frame_ptr depth))
+ in
+ get_ty_params_of_frame
+ outermost_fnid
+ outermost_fp
+ (n_item_ty_params cx outermost_fnid)
+ end
+ else
+ local()
in
let get_ty_param_in_current_frame (param_idx:int) : Il.cell =
@@ -872,35 +923,6 @@ let trans_visitor
Il.Mem (mem, (pointee_type ptr))
in
- (*
- * Within a for-each block, calculate the fp of an enclosing for-each block
- * or the enclosing function by chasing static links.
- *)
- let get_nth_outer_frame_ptr (diff:int) : Il.cell =
- (* All for-each block frames have the same args. *)
- let block_args_rty = current_fn_args_rty None in
- let current_fp = Il.Reg (abi.Abi.abi_fp_reg, Il.AddrTy Il.OpaqueTy) in
- let rec out (n:int) (fp:Il.cell) : Il.cell =
- if n == 0
- then fp
- else
- let args = fp_to_args fp block_args_rty in
- let iter_args = get_element_ptr args Abi.calltup_elt_iterator_args in
- let outer_fp =
- get_element_ptr iter_args Abi.iterator_args_elt_outer_frame_ptr
- in
- out (n - 1) outer_fp
- in
- out diff current_fp
- in
-
- let curr_stmt_depth _ =
- if (Stack.is_empty curr_stmt)
- then None
- else
- Some
- (get_stmt_depth cx (Stack.top curr_stmt))
- in
let cell_of_block_slot
?access_depth:(access_depth=curr_stmt_depth())