From 69ae63d4b02b15d47ab90a4bf96880329601f116 Mon Sep 17 00:00:00 2001 From: Graydon Hoare Date: Tue, 12 Oct 2010 16:51:27 -0700 Subject: Fix horribly embarassing signedness bug in backend, plus related regressions. --- src/boot/be/asm.ml | 5 +++-- src/boot/be/il.ml | 6 ++++++ src/boot/be/x86.ml | 5 ++++- src/boot/me/trans.ml | 12 +++++++++--- 4 files changed, 22 insertions(+), 6 deletions(-) (limited to 'src') diff --git a/src/boot/be/asm.ml b/src/boot/be/asm.ml index 4b05e347..939b297c 100644 --- a/src/boot/be/asm.ml +++ b/src/boot/be/asm.ml @@ -590,8 +590,9 @@ and lower_frag | WORD (m,e) -> iflog sess (fun _ -> - log sess "lowering word %s" - (string_of_ty_mach m)); + log sess "lowering word %s with val %s" + (string_of_ty_mach m) + (fmt_to_str fmt_frag frag)); word (bytes_of_ty_mach m) (mach_is_signed m) e | ALIGN_FILE (n, frag) -> diff --git a/src/boot/be/il.ml b/src/boot/be/il.ml index 0888f8e8..9a63576e 100644 --- a/src/boot/be/il.ml +++ b/src/boot/be/il.ml @@ -812,6 +812,12 @@ let umov (dst:cell) (src:operand) : quad' = else unary UMOV dst src ;; +let imov (dst:cell) (src:operand) : quad' = + if (cell_is_nil dst || operand_is_nil src) + then Dead + else unary IMOV dst src +;; + let zero (dst:cell) (count:operand) : quad' = unary ZERO dst count ;; diff --git a/src/boot/be/x86.ml b/src/boot/be/x86.ml index d2d70ea2..c9b13d04 100644 --- a/src/boot/be/x86.ml +++ b/src/boot/be/x86.ml @@ -663,6 +663,7 @@ let emit_c_call let emit = Il.emit e in let mov dst src = emit (Il.umov dst src) in + let imov dst src = emit (Il.imov dst src) in let binary op dst imm = emit (Il.binary op dst (c dst) (immi imm)) in (* rust calls get task as arg0 *) @@ -702,6 +703,8 @@ let emit_c_call mov (r tmp1) arg; mov (word_n (h esp) i) (c (r tmp1)); end + | Il.Imm (_, tm) when mach_is_signed tm -> + imov (word_n (h esp) i) arg | _ -> mov (word_n (h esp) i) arg end @@ -2151,7 +2154,7 @@ let mov (signed:bool) (dst:Il.cell) (src:Il.operand) : Asm.frag = (* rm32 <- imm32 *) | (_, _, Il.Imm (i, _)) when is_rm32 dst || is_r8 dst -> - let t = if signed then TY_u32 else TY_i32 in + let t = if signed then TY_i32 else TY_u32 in insn_rm_r_imm 0xc7 dst slash0 t i | _ -> raise Unrecognized diff --git a/src/boot/me/trans.ml b/src/boot/me/trans.ml index cb0b7c83..67a96030 100644 --- a/src/boot/me/trans.ml +++ b/src/boot/me/trans.ml @@ -316,6 +316,10 @@ let trans_visitor Il.Mem (mem, Il.ScalarTy (Il.ValTy word_bits)) in + let imov (dst:Il.cell) (src:Il.operand) : unit = + emit (Il.imov dst src) + in + let mov (dst:Il.cell) (src:Il.operand) : unit = emit (Il.umov dst src) in @@ -398,8 +402,10 @@ let trans_visitor (in_quad_category "crate_rel -> ptr" (fun _ -> let cell = next_vreg_cell (Il.AddrTy rty) in + let diff = next_vreg_cell (Il.AddrTy rty) in mov cell (Il.Cell (curr_crate_ptr())); - add_to cell rel; + imov diff rel; + add_to cell (Il.Cell diff); cell)) (* @@ -1566,7 +1572,7 @@ let trans_visitor Abi.load_fixup_addr (emitter()) crate_ptr_reg cx.ctxt_crate_fixup Il.OpaqueTy; mov (word_at (fp_imm frame_crate_ptr)) (Il.Cell (crate_ptr_cell)); - mov (word_at (fp_imm frame_fns_disp)) frame_fns + imov (word_at (fp_imm frame_fns_disp)) frame_fns and check_interrupt_flag _ = if cx.ctxt_sess.Session.sess_minimal @@ -2307,7 +2313,7 @@ let trans_visitor else Il.JL in (* Start with assumption lhs < rhs *) - mov result neg_one; + imov result neg_one; let lhs_lt_rhs_jmps = trans_compare ~ty_params ~cjmp ~ty lhs rhs in -- cgit v1.2.3