From bc149a3814c33ee55eaa01fe49c52389d7b31bb2 Mon Sep 17 00:00:00 2001 From: Elijah Taylor Date: Thu, 31 Jan 2013 13:09:48 -0800 Subject: [PATCH] NaCl amd64 codegen fixes - mostly more code fixes to deal with a 64-bit ILP32 machine --- mono/mini/decompose.c | 12 ++++++++---- mono/mini/method-to-ir.c | 12 +++++++++--- mono/mini/mini-amd64.c | 28 +++++++++++++++++++++------- 3 files changed, 38 insertions(+), 14 deletions(-) diff --git a/mono/mini/decompose.c b/mono/mini/decompose.c index 7504a05bea5..93a2535a479 100644 --- a/mono/mini/decompose.c +++ b/mono/mini/decompose.c @@ -326,7 +326,7 @@ mono_decompose_opcode (MonoCompile *cfg, MonoInst *ins) break; case OP_ICONV_TO_OVF_U4: case OP_ICONV_TO_OVF_I4_UN: -#if SIZEOF_REGISTER == 4 +#if SIZEOF_VOID_P == 4 case OP_ICONV_TO_OVF_U: case OP_ICONV_TO_OVF_I_UN: #endif @@ -339,21 +339,21 @@ mono_decompose_opcode (MonoCompile *cfg, MonoInst *ins) case OP_ICONV_TO_U4: case OP_ICONV_TO_OVF_I4: case OP_ICONV_TO_OVF_U4_UN: -#if SIZEOF_REGISTER == 4 +#if SIZEOF_VOID_P == 4 case OP_ICONV_TO_OVF_I: case OP_ICONV_TO_OVF_U_UN: #endif ins->opcode = OP_MOVE; break; case OP_ICONV_TO_I: -#if SIZEOF_REGISTER == 8 +#if SIZEOF_VOID_P == 8 ins->opcode = OP_SEXT_I4; #else ins->opcode = OP_MOVE; #endif break; case OP_ICONV_TO_U: -#if SIZEOF_REGISTER == 8 +#if SIZEOF_VOID_P == 8 ins->opcode = OP_ZEXT_I4; #else ins->opcode = OP_MOVE; @@ -1218,9 +1218,13 @@ mono_decompose_vtype_opts (MonoCompile *cfg) case 2: MONO_EMIT_NEW_STORE_MEMBASE (cfg, OP_STOREI2_MEMBASE_REG, dest->dreg, 0, call2->inst.dreg); break; + case 3: case 4: MONO_EMIT_NEW_STORE_MEMBASE (cfg, OP_STOREI4_MEMBASE_REG, dest->dreg, 0, call2->inst.dreg); break; + case 5: + case 6: + case 7: case 8: #if SIZEOF_REGISTER == 4 /* diff --git a/mono/mini/method-to-ir.c b/mono/mini/method-to-ir.c index 442017d4b56..2b8a72a7ff0 100644 --- a/mono/mini/method-to-ir.c +++ b/mono/mini/method-to-ir.c @@ -157,7 +157,7 @@ static MonoMethodSignature *helper_sig_monitor_enter_exit_trampoline_llvm = NULL #define FREG 'f' #define VREG 'v' #define XREG 'x' -#if SIZEOF_REGISTER == 8 +#if SIZEOF_REGISTER == 8 && SIZEOF_REGISTER == SIZEOF_VOIDP #define LREG IREG #else #define LREG 'l' @@ -12468,6 +12468,7 @@ mono_spill_global_vars (MonoCompile *cfg, gboolean *need_local_opts) ins->dreg = alloc_dreg (cfg, stacktypes [regtype]); +#if SIZEOF_REGISTER != 8 if (regtype == 'l') { NEW_STORE_MEMBASE (cfg, store_ins, OP_STOREI4_MEMBASE_REG, var->inst_basereg, var->inst_offset + MINI_LS_WORD_OFFSET, ins->dreg + 1); mono_bblock_insert_after_ins (bb, ins, store_ins); @@ -12475,7 +12476,9 @@ mono_spill_global_vars (MonoCompile *cfg, gboolean *need_local_opts) mono_bblock_insert_after_ins (bb, ins, store_ins); def_ins = store_ins; } - else { + else +#endif + { g_assert (store_opcode != OP_STOREV_MEMBASE); /* Try to fuse the store into the instruction itself */ @@ -12634,6 +12637,7 @@ mono_spill_global_vars (MonoCompile *cfg, gboolean *need_local_opts) sregs [srcindex] = sreg; //mono_inst_set_src_registers (ins, sregs); +#if SIZEOF_REGISTER != 8 if (regtype == 'l') { NEW_LOAD_MEMBASE (cfg, load_ins, OP_LOADI4_MEMBASE, sreg + 2, var->inst_basereg, var->inst_offset + MINI_MS_WORD_OFFSET); mono_bblock_insert_before_ins (bb, ins, load_ins); @@ -12641,7 +12645,9 @@ mono_spill_global_vars (MonoCompile *cfg, gboolean *need_local_opts) mono_bblock_insert_before_ins (bb, ins, load_ins); use_ins = load_ins; } - else { + else +#endif + { #if SIZEOF_REGISTER == 4 g_assert (load_opcode != OP_LOADI8_MEMBASE); #endif diff --git a/mono/mini/mini-amd64.c b/mono/mini/mini-amd64.c index 656129c3331..9ee27020155 100644 --- a/mono/mini/mini-amd64.c +++ b/mono/mini/mini-amd64.c @@ -999,6 +999,9 @@ get_call_info (MonoGenericSharingContext *gsctx, MonoMemPool *mp, MonoMethodSign break; } /* fall through */ +#if defined( __native_client_codegen__ ) + case MONO_TYPE_TYPEDBYREF: +#endif case MONO_TYPE_VALUETYPE: { guint32 tmp_gr = 0, tmp_fr = 0, tmp_stacksize = 0; @@ -1009,10 +1012,12 @@ get_call_info (MonoGenericSharingContext *gsctx, MonoMemPool *mp, MonoMethodSign } break; } +#if !defined( __native_client_codegen__ ) case MONO_TYPE_TYPEDBYREF: /* Same as a valuetype with size 24 */ cinfo->vtype_retaddr = TRUE; break; +#endif case MONO_TYPE_VOID: break; default: @@ -1116,7 +1121,7 @@ get_call_info (MonoGenericSharingContext *gsctx, MonoMemPool *mp, MonoMethodSign add_valuetype (gsctx, sig, ainfo, sig->params [i], FALSE, &gr, &fr, &stack_size); break; case MONO_TYPE_TYPEDBYREF: -#ifdef HOST_WIN32 +#if defined( HOST_WIN32 ) || defined( __native_client_codegen__ ) add_valuetype (gsctx, sig, ainfo, sig->params [i], FALSE, &gr, &fr, &stack_size); #else stack_size += sizeof (MonoTypedRef); @@ -1657,7 +1662,7 @@ mono_arch_fill_argument_info (MonoCompile *cfg) case ArgInIReg: case ArgInFloatSSEReg: case ArgInDoubleSSEReg: - if ((MONO_TYPE_ISSTRUCT (sig->ret) && !mono_class_from_mono_type (sig->ret)->enumtype) || (sig->ret->type == MONO_TYPE_TYPEDBYREF)) { + if ((MONO_TYPE_ISSTRUCT (sig->ret) && !mono_class_from_mono_type (sig->ret)->enumtype) || ((sig->ret->type == MONO_TYPE_TYPEDBYREF) && cinfo->vtype_retaddr)) { cfg->vret_addr->opcode = OP_REGVAR; cfg->vret_addr->inst_c0 = cinfo->ret.reg; } @@ -1771,7 +1776,7 @@ mono_arch_allocate_vars (MonoCompile *cfg) case ArgInIReg: case ArgInFloatSSEReg: case ArgInDoubleSSEReg: - if ((MONO_TYPE_ISSTRUCT (sig->ret) && !mono_class_from_mono_type (sig->ret)->enumtype) || (sig->ret->type == MONO_TYPE_TYPEDBYREF)) { + if ((MONO_TYPE_ISSTRUCT (sig->ret) && !mono_class_from_mono_type (sig->ret)->enumtype) || ((sig->ret->type == MONO_TYPE_TYPEDBYREF) && cinfo->vtype_retaddr)) { if (cfg->globalra) { cfg->vret_addr->opcode = OP_REGVAR; cfg->vret_addr->inst_c0 = cinfo->ret.reg; @@ -3042,7 +3047,10 @@ emit_call_body (MonoCompile *cfg, guint8 *code, guint32 patch_type, gconstpointe #ifdef MONO_ARCH_NOMAP32BIT near_call = FALSE; #endif - +#if defined(__native_client__) + /* Always use near_call == TRUE for Native Client */ + near_call = TRUE; +#endif /* The 64bit XEN kernel does not honour the MAP_32BIT flag. (#522894) */ if (optimize_for_xen) near_call = FALSE; @@ -4077,6 +4085,12 @@ mono_arch_output_basic_block (MonoCompile *cfg, MonoBasicBlock *bb) amd64_alu_reg_reg (code, X86_CMP, ins->sreg1, ins->sreg2); break; case OP_COMPARE_IMM: +#if defined(__mono_ilp32__) + /* Comparison of pointer immediates should be 4 bytes to avoid sign-extend problems */ + g_assert (amd64_is_imm32 (ins->inst_imm)); + amd64_alu_reg_imm_size (code, X86_CMP, ins->sreg1, ins->inst_imm, 4); + break; +#endif case OP_LCOMPARE_IMM: g_assert (amd64_is_imm32 (ins->inst_imm)); amd64_alu_reg_imm (code, X86_CMP, ins->sreg1, ins->inst_imm); @@ -8127,7 +8141,7 @@ mono_arch_build_imt_thunk (MonoVTable *vtable, MonoDomain *domain, MonoIMTCheckI if (item->check_target_idx || fail_case) { if (!item->compare_done || fail_case) { if (amd64_is_imm32 (item->key)) - amd64_alu_reg_imm (code, X86_CMP, MONO_ARCH_IMT_REG, (guint32)(gssize)item->key); + amd64_alu_reg_imm_size (code, X86_CMP, MONO_ARCH_IMT_REG, (guint32)(gssize)item->key, sizeof(gpointer)); else { amd64_mov_reg_imm (code, MONO_ARCH_IMT_SCRATCH_REG, item->key); amd64_alu_reg_reg (code, X86_CMP, MONO_ARCH_IMT_REG, MONO_ARCH_IMT_SCRATCH_REG); @@ -8153,7 +8167,7 @@ mono_arch_build_imt_thunk (MonoVTable *vtable, MonoDomain *domain, MonoIMTCheckI /* enable the commented code to assert on wrong method */ #if 0 if (amd64_is_imm32 (item->key)) - amd64_alu_reg_imm (code, X86_CMP, MONO_ARCH_IMT_REG, (guint32)(gssize)item->key); + amd64_alu_reg_imm_size (code, X86_CMP, MONO_ARCH_IMT_REG, (guint32)(gssize)item->key, sizeof(gpointer)); else { amd64_mov_reg_imm (code, MONO_ARCH_IMT_SCRATCH_REG, item->key); amd64_alu_reg_reg (code, X86_CMP, MONO_ARCH_IMT_REG, MONO_ARCH_IMT_SCRATCH_REG); @@ -8178,7 +8192,7 @@ mono_arch_build_imt_thunk (MonoVTable *vtable, MonoDomain *domain, MonoIMTCheckI } } else { if (amd64_is_imm32 (item->key)) - amd64_alu_reg_imm (code, X86_CMP, MONO_ARCH_IMT_REG, (guint32)(gssize)item->key); + amd64_alu_reg_imm_size (code, X86_CMP, MONO_ARCH_IMT_REG, (guint32)(gssize)item->key, sizeof (gpointer)); else { amd64_mov_reg_imm (code, MONO_ARCH_IMT_SCRATCH_REG, item->key); amd64_alu_reg_reg (code, X86_CMP, MONO_ARCH_IMT_REG, MONO_ARCH_IMT_SCRATCH_REG); -- 2.25.1