X-Git-Url: http://wien.tomnetworks.com/gitweb/?a=blobdiff_plain;f=src%2Fvm%2Fjit%2Fi386%2Fcodegen.c;h=955d3bb8a4770f9054e37e85ad0a03466ebafb6e;hb=2e09f78e835989bbbba929aa9bd60819ff3e6f2a;hp=f9528dd4d28f7400a5c4c5e87f330ee276f087e4;hpb=af362adfdd8741e107c1e2fdbc73b926a1b303bd;p=cacao.git diff --git a/src/vm/jit/i386/codegen.c b/src/vm/jit/i386/codegen.c index f9528dd4d..955d3bb8a 100644 --- a/src/vm/jit/i386/codegen.c +++ b/src/vm/jit/i386/codegen.c @@ -1,9 +1,9 @@ /* src/vm/jit/i386/codegen.c - machine code generator for i386 - Copyright (C) 1996-2005 R. Grafl, A. Krall, C. Kruegel, C. Oates, - R. Obermaisser, M. Platter, M. Probst, S. Ring, E. Steiner, - C. Thalinger, D. Thuernbeck, P. Tomsich, C. Ullrich, J. Wenninger, - Institut f. Computersprachen - TU Wien + Copyright (C) 1996-2005, 2006 R. Grafl, A. Krall, C. Kruegel, + C. Oates, R. Obermaisser, M. Platter, M. Probst, S. Ring, + E. Steiner, C. Thalinger, D. Thuernbeck, P. Tomsich, C. Ullrich, + J. Wenninger, Institut f. Computersprachen - TU Wien This file is part of CACAO. @@ -19,28 +19,33 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software - Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA - 02111-1307, USA. + Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA + 02110-1301, USA. - Contact: cacao@complang.tuwien.ac.at + Contact: cacao@cacaojvm.org Authors: Andreas Krall Christian Thalinger Changes: Joseph Wenninger + Christian Ullrich - $Id: codegen.c 2676 2005-06-13 16:20:32Z twisti $ + $Id: codegen.c 4393 2006-01-31 15:41:22Z twisti $ */ +#include "config.h" + #include #include -#include "config.h" +#include "vm/types.h" #include "vm/jit/i386/md-abi.h" -#include "vm/jit/i386/md-abi.inc" + +#include "vm/jit/i386/codegen.h" +#include "vm/jit/i386/emitfuncs.h" #include "cacao/cacao.h" #include "native/jni.h" @@ -49,38 +54,23 @@ #include "vm/exceptions.h" #include "vm/global.h" #include "vm/loader.h" +#include "vm/options.h" #include "vm/stringlocal.h" -#include "vm/tables.h" #include "vm/utf8.h" #include "vm/jit/asmpart.h" +#include "vm/jit/codegen-common.h" +#include "vm/jit/dseg.h" #include "vm/jit/jit.h" #include "vm/jit/parse.h" #include "vm/jit/patcher.h" #include "vm/jit/reg.h" -#include "vm/jit/i386/codegen.h" -#include "vm/jit/i386/emitfuncs.h" -#include "vm/jit/i386/types.h" -#include "vm/jit/i386/asmoffsets.h" -/******************************************************************************* - - include independent code generation stuff -- include after register - descriptions to avoid extern definitions - -*******************************************************************************/ - -#include "vm/jit/codegen.inc" -#include "vm/jit/reg.inc" -#ifdef LSRA -#ifdef LSRA_USES_REG_RES -#include "vm/jit/i386/icmd_uses_reg_res.inc" +#if defined(ENABLE_LSRA) +# ifdef LSRA_USES_REG_RES +# include "vm/jit/i386/icmd_uses_reg_res.inc" +# endif +# include "vm/jit/allocator/lsra.h" #endif -#include "vm/jit/lsra.inc" -#endif - -void codegen_stubcalled() { - log_text("Stub has been called"); -} /* codegen ********************************************************************* @@ -89,22 +79,27 @@ void codegen_stubcalled() { *******************************************************************************/ -void codegen(methodinfo *m, codegendata *cd, registerdata *rd) +bool codegen(methodinfo *m, codegendata *cd, registerdata *rd) { - s4 len, s1, s2, s3, d; - ptrint a; - stackptr src; - varinfo *var; - basicblock *bptr; - instruction *iptr; - s4 parentargs_base; - u2 currentline; - s4 fpu_st_offset = 0; - methodinfo *lm; /* local methodinfo for ICMD_INVOKE* */ + s4 len, s1, s2, s3, d, off, disp; + s4 parentargs_base; + stackptr src; + varinfo *var; + basicblock *bptr; + instruction *iptr; + exceptiontable *ex; + u2 currentline; + methodinfo *lm; /* local methodinfo for ICMD_INVOKE* */ builtintable_entry *bte; - methoddesc *md; + methoddesc *md; + s4 fpu_st_offset = 0; + + /* prevent compiler warnings */ - exceptiontable *ex; + d = 0; + currentline = 0; + lm = NULL; + bte = NULL; { s4 i, p, t, l; @@ -113,30 +108,33 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) /* space to save used callee saved registers */ - savedregs_num += (rd->savintregcnt - rd->maxsavintreguse); - savedregs_num += 2 * (rd->savfltregcnt - rd->maxsavfltreguse); /* float register are saved on 2 4 Byte stackslots */ + savedregs_num += (INT_SAV_CNT - rd->savintreguse); - parentargs_base = rd->maxmemuse + savedregs_num; + /* float register are saved on 2 4-byte stackslots */ + savedregs_num += (FLT_SAV_CNT - rd->savfltreguse) * 2; + + parentargs_base = rd->memuse + savedregs_num; -#if defined(USE_THREADS) /* space to save argument of monitor_enter */ +#if defined(USE_THREADS) + /* space to save argument of monitor_enter */ - if (checksync && (m->flags & ACC_SYNCHRONIZED)) - parentargs_base++; + if (checksync && (m->flags & ACC_SYNCHRONIZED)) { + /* reserve 2 slots for long/double return values for monitorexit */ + if (IS_2_WORD_TYPE(m->parseddesc->returntype.type)) + parentargs_base += 2; + else + parentargs_base++; + } #endif -/* align Stackframe to 8 Byte */ -/* if ((parentargs_base+1) & 1) */ -/* parentargs_base++; */ - /* create method header */ (void) dseg_addaddress(cd, m); /* MethodPointer */ (void) dseg_adds4(cd, parentargs_base * 4); /* FrameSize */ #if defined(USE_THREADS) - /* IsSync contains the offset relative to the stack pointer for the argument of monitor_exit used in the exception handler. Since the offset could be zero and give a wrong meaning of the flag it is @@ -144,16 +142,14 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) */ if (checksync && (m->flags & ACC_SYNCHRONIZED)) - (void) dseg_adds4(cd, (rd->maxmemuse + 1) * 4); /* IsSync */ + (void) dseg_adds4(cd, (rd->memuse + 1) * 4); /* IsSync */ else - #endif - - (void) dseg_adds4(cd, 0); /* IsSync */ + (void) dseg_adds4(cd, 0); /* IsSync */ - (void) dseg_adds4(cd, m->isleafmethod); /* IsLeaf */ - (void) dseg_adds4(cd, rd->savintregcnt - rd->maxsavintreguse); /* IntSave */ - (void) dseg_adds4(cd, rd->savfltregcnt - rd->maxsavfltreguse); /* FltSave */ + (void) dseg_adds4(cd, m->isleafmethod); /* IsLeaf */ + (void) dseg_adds4(cd, INT_SAV_CNT - rd->savintreguse); /* IntSave */ + (void) dseg_adds4(cd, FLT_SAV_CNT - rd->savfltreguse); /* FltSave */ /* adds a reference for the length of the line number counter. We don't know the size yet, since we evaluate the information during code @@ -172,27 +168,35 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) dseg_addtarget(cd, ex->handler); (void) dseg_addaddress(cd, ex->catchtype.cls); } - /* initialize mcode variables */ cd->mcodeptr = cd->mcodebase; cd->mcodeend = (s4 *) (cd->mcodebase + cd->mcodesize); - MCODECHECK(128 + m->paramcount); - /* create stack frame (if necessary) */ + /* initialize the last patcher pointer */ + + cd->lastmcodeptr = cd->mcodeptr; - if (parentargs_base) { - i386_alu_imm_reg(cd, ALU_SUB, parentargs_base * 4, REG_SP); + /* generate profiling code */ + + if (opt_prof) { + M_MOV_IMM((ptrint) m, REG_ITMP1); + M_IADD_IMM_MEMBASE(1, REG_ITMP1, OFFSET(methodinfo, executioncount)); } + /* create stack frame (if necessary) */ + + if (parentargs_base) + M_ASUB_IMM(parentargs_base * 4, REG_SP); + /* save return address and used callee saved registers */ p = parentargs_base; - for (i = rd->savintregcnt - 1; i >= rd->maxsavintreguse; i--) { - p--; i386_mov_reg_membase(cd, rd->savintregs[i], REG_SP, p * 4); + for (i = INT_SAV_CNT - 1; i >= rd->savintreguse; i--) { + p--; M_AST(rd->savintregs[i], REG_SP, p * 4); } - for (i = rd->savfltregcnt - 1; i >= rd->maxsavfltreguse; i--) { + for (i = FLT_SAV_CNT - 1; i >= rd->savfltreguse; i--) { p-=2; i386_fld_reg(cd, rd->savfltregs[i]); i386_fstpl_membase(cd, REG_SP, p * 4); } @@ -312,7 +316,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) #if defined(USE_THREADS) if (checksync && (m->flags & ACC_SYNCHRONIZED)) { - s1 = rd->maxmemuse; + s1 = rd->memuse; if (m->flags & ACC_STATIC) { i386_mov_imm_reg(cd, (ptrint) m->class, REG_ITMP1); @@ -340,7 +344,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) if (runverbose) { stack_off = 0; - int pa = INT_TMP_CNT * 4 + TRACE_ARGS_NUM * 8 + 4 + 4 + parentargs_base * 4; + s1 = INT_TMP_CNT * 4 + TRACE_ARGS_NUM * 8 + 4 + 4 + parentargs_base * 4; M_ISUB_IMM(INT_TMP_CNT * 4 + TRACE_ARGS_NUM * 8 + 4, REG_SP); @@ -354,20 +358,20 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) if (IS_INT_LNG_TYPE(t)) { if (IS_2_WORD_TYPE(t)) { - i386_mov_membase_reg(cd, REG_SP, pa + stack_off, REG_ITMP1); + i386_mov_membase_reg(cd, REG_SP, s1 + stack_off, REG_ITMP1); i386_mov_reg_membase(cd, REG_ITMP1, REG_SP, p * 8); - i386_mov_membase_reg(cd, REG_SP, pa + stack_off + 4, REG_ITMP1); + i386_mov_membase_reg(cd, REG_SP, s1 + stack_off + 4, REG_ITMP1); i386_mov_reg_membase(cd, REG_ITMP1, REG_SP, p * 8 + 4); } else if (t == TYPE_ADR) { /* } else { */ - i386_mov_membase_reg(cd, REG_SP, pa + stack_off, REG_ITMP1); + i386_mov_membase_reg(cd, REG_SP, s1 + stack_off, REG_ITMP1); i386_mov_reg_membase(cd, REG_ITMP1, REG_SP, p * 8); i386_alu_reg_reg(cd, ALU_XOR, REG_ITMP1, REG_ITMP1); i386_mov_reg_membase(cd, REG_ITMP1, REG_SP, p * 8 + 4); } else { - i386_mov_membase_reg(cd, REG_SP, pa + stack_off, EAX); + i386_mov_membase_reg(cd, REG_SP, s1 + stack_off, EAX); i386_cltd(cd); i386_mov_reg_membase(cd, EAX, REG_SP, p * 8); i386_mov_reg_membase(cd, EDX, REG_SP, p * 8 + 4); @@ -375,13 +379,13 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) } else { if (!IS_2_WORD_TYPE(t)) { - i386_flds_membase(cd, REG_SP, pa + stack_off); + i386_flds_membase(cd, REG_SP, s1 + stack_off); i386_fstps_membase(cd, REG_SP, p * 8); i386_alu_reg_reg(cd, ALU_XOR, REG_ITMP1, REG_ITMP1); i386_mov_reg_membase(cd, REG_ITMP1, REG_SP, p * 8 + 4); } else { - i386_fldl_membase(cd, REG_SP, pa + stack_off); + i386_fldl_membase(cd, REG_SP, s1 + stack_off); i386_fstpl_membase(cd, REG_SP, p * 8); } } @@ -433,7 +437,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) len = bptr->indepth; MCODECHECK(64+len); -#ifdef LSRA +#if defined(ENABLE_LSRA) if (opt_lsra) { while (src != NULL) { len--; @@ -532,7 +536,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) } src = src->prev; } -#ifdef LSRA +#if defined(ENABLE_LSRA) } #endif @@ -581,16 +585,17 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) /* REG_RES Register usage: see lsra.inc icmd_uses_tmp */ /* EAX: NO ECX: NO EDX: NO */ + d = reg_of_var(rd, iptr->dst, REG_ITMP1); if (iptr->dst->flags & INMEMORY) { - i386_mov_imm_membase(cd, iptr->val.i, REG_SP, iptr->dst->regoff * 4); + M_IST_IMM(iptr->val.i, REG_SP, iptr->dst->regoff * 4); } else { if (iptr->val.i == 0) { - i386_alu_reg_reg(cd, ALU_XOR, d, d); + M_CLR(d); } else { - i386_mov_imm_reg(cd, iptr->val.i, d); + M_MOV_IMM(iptr->val.i, d); } } break; @@ -600,10 +605,11 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) /* REG_RES Register usage: see lsra.inc icmd_uses_tmp */ /* EAX: NO ECX: NO EDX: NO */ + d = reg_of_var(rd, iptr->dst, REG_ITMP1); if (iptr->dst->flags & INMEMORY) { - i386_mov_imm_membase(cd, iptr->val.l, REG_SP, iptr->dst->regoff * 4); - i386_mov_imm_membase(cd, iptr->val.l >> 32, REG_SP, iptr->dst->regoff * 4 + 4); + M_IST_IMM(iptr->val.l, REG_SP, iptr->dst->regoff * 4); + M_IST_IMM(iptr->val.l >> 32, REG_SP, iptr->dst->regoff * 4 + 4); } else { log_text("LCONST: longs have to be in memory"); @@ -613,6 +619,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) case ICMD_FCONST: /* ... ==> ..., constant */ /* op1 = 0, val.f = constant */ + /* REG_RES Register usage: see lsra.inc icmd_uses_tmp */ /* EAX: YES ECX: NO EDX: NO */ @@ -637,10 +644,10 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) fpu_st_offset++; } else { - a = dseg_addfloat(cd, iptr->val.f); + disp = dseg_addfloat(cd, iptr->val.f); i386_mov_imm_reg(cd, 0, REG_ITMP1); dseg_adddata(cd, cd->mcodeptr); - i386_flds_membase(cd, REG_ITMP1, a); + i386_flds_membase(cd, REG_ITMP1, disp); fpu_st_offset++; } store_reg_to_var_flt(iptr->dst, d); @@ -648,6 +655,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) case ICMD_DCONST: /* ... ==> ..., constant */ /* op1 = 0, val.d = constant */ + /* REG_RES Register usage: see lsra.inc icmd_uses_tmp */ /* EAX: YES ECX: NO EDX: NO */ @@ -672,10 +680,10 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) fpu_st_offset++; } else { - a = dseg_adddouble(cd, iptr->val.d); + disp = dseg_adddouble(cd, iptr->val.d); i386_mov_imm_reg(cd, 0, REG_ITMP1); dseg_adddata(cd, cd->mcodeptr); - i386_fldl_membase(cd, REG_ITMP1, a); + i386_fldl_membase(cd, REG_ITMP1, disp); fpu_st_offset++; } store_reg_to_var_flt(iptr->dst, d); @@ -683,19 +691,34 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) case ICMD_ACONST: /* ... ==> ..., constant */ /* op1 = 0, val.a = constant */ + /* REG_RES Register usage: see lsra.inc icmd_uses_tmp */ /* EAX: YES ECX: NO EDX: NO */ d = reg_of_var(rd, iptr->dst, REG_ITMP1); - if (iptr->dst->flags & INMEMORY) { - i386_mov_imm_membase(cd, (s4) iptr->val.a, REG_SP, iptr->dst->regoff * 4); + + if ((iptr->target != NULL) && (iptr->val.a == NULL)) { + codegen_addpatchref(cd, cd->mcodeptr, + PATCHER_aconst, + (unresolved_class *) iptr->target, 0); + + if (opt_showdisassemble) { + M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; + } + + M_MOV_IMM((ptrint) iptr->val.a, d); + store_reg_to_var_int(iptr->dst, d); } else { - if ((s4) iptr->val.a == 0) { - i386_alu_reg_reg(cd, ALU_XOR, d, d); + if (iptr->dst->flags & INMEMORY) { + M_AST_IMM((ptrint) iptr->val.a, REG_SP, iptr->dst->regoff * 4); } else { - i386_mov_imm_reg(cd, (s4) iptr->val.a, d); + if ((ptrint) iptr->val.a == 0) { + M_CLR(d); + } else { + M_MOV_IMM((ptrint) iptr->val.a, d); + } } } break; @@ -945,7 +968,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) M_COPY(src->prev, iptr->dst->prev); M_COPY(src->prev->prev, iptr->dst->prev->prev); M_COPY(iptr->dst, iptr->dst->prev->prev->prev); - M_COPY(iptr->dst->prev, iptr->dst->prev->prev->prev); + M_COPY(iptr->dst->prev, iptr->dst->prev->prev->prev->prev); break; case ICMD_DUP2_X2: /* ..., a, b, c, d ==> ..., c, d, a, b, c, d */ @@ -1505,7 +1528,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) case ICMD_IDIV: /* ..., val1, val2 ==> ..., val1 / val2 */ /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: S|YES ECX: S|YES EDX: S|YES OUTPUT: EAX*/ /* Really uses EDX? */ + /* EAX: S|YES ECX: S|YES EDX: S|YES OUTPUT: EAX */ d = reg_of_var(rd, iptr->dst, REG_NULL); var_to_reg_int(s1, src, REG_ITMP2); @@ -1516,8 +1539,10 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) } else { M_INTMOVE(src->prev->regoff, EAX); } - - i386_alu_imm_reg(cd, ALU_CMP, 0x80000000, EAX); /* check as described in jvm spec */ + + /* check as described in jvm spec */ + + i386_alu_imm_reg(cd, ALU_CMP, 0x80000000, EAX); i386_jcc(cd, I386_CC_NE, 3 + 6); i386_alu_imm_reg(cd, ALU_CMP, -1, s1); i386_jcc(cd, I386_CC_E, 1 + 2); @@ -1535,7 +1560,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) case ICMD_IREM: /* ..., val1, val2 ==> ..., val1 % val2 */ /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: S|YES ECX: S|YES EDX: S|YES OUTPUT: EDX*/ + /* EAX: S|YES ECX: S|YES EDX: S|YES OUTPUT: EDX */ d = reg_of_var(rd, iptr->dst, REG_NULL); @@ -1547,8 +1572,10 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) } else { M_INTMOVE(src->prev->regoff, EAX); } - - i386_alu_imm_reg(cd, ALU_CMP, 0x80000000, EAX); /* check as described in jvm spec */ + + /* check as described in jvm spec */ + + i386_alu_imm_reg(cd, ALU_CMP, 0x80000000, EAX); i386_jcc(cd, I386_CC_NE, 2 + 3 + 6); i386_alu_reg_reg(cd, ALU_XOR, EDX, EDX); i386_alu_imm_reg(cd, ALU_CMP, -1, s1); @@ -1568,7 +1595,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) case ICMD_IDIVPOW2: /* ..., value ==> ..., value >> constant */ /* val.i = constant */ /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: YES ECX: NO EDX: NO OUTPUT: REG_NULL*/ + /* EAX: YES ECX: NO EDX: NO OUTPUT: REG_NULL */ /* TODO: optimize for `/ 2' */ var_to_reg_int(s1, src, REG_ITMP1); @@ -1576,46 +1603,19 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) M_INTMOVE(s1, d); i386_test_reg_reg(cd, d, d); - a = 2; - CALCIMMEDIATEBYTES(a, (1 << iptr->val.i) - 1); - i386_jcc(cd, I386_CC_NS, a); + disp = 2; + CALCIMMEDIATEBYTES(disp, (1 << iptr->val.i) - 1); + i386_jcc(cd, I386_CC_NS, disp); i386_alu_imm_reg(cd, ALU_ADD, (1 << iptr->val.i) - 1, d); i386_shift_imm_reg(cd, I386_SAR, iptr->val.i, d); store_reg_to_var_int(iptr->dst, d); break; - case ICMD_LDIVPOW2: /* ..., value ==> ..., value >> constant */ - /* val.i = constant */ - /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: YES ECX: YES EDX: NO OUTPUT: REG_NULL*/ - - d = reg_of_var(rd, iptr->dst, REG_NULL); - if (iptr->dst->flags & INMEMORY) { - if (src->flags & INMEMORY) { - a = 2; - CALCIMMEDIATEBYTES(a, (1 << iptr->val.i) - 1); - a += 3; - i386_mov_membase_reg(cd, REG_SP, src->regoff * 4, REG_ITMP1); - i386_mov_membase_reg(cd, REG_SP, src->regoff * 4 + 4, REG_ITMP2); - - i386_test_reg_reg(cd, REG_ITMP2, REG_ITMP2); - i386_jcc(cd, I386_CC_NS, a); - i386_alu_imm_reg(cd, ALU_ADD, (1 << iptr->val.i) - 1, REG_ITMP1); - i386_alu_imm_reg(cd, ALU_ADC, 0, REG_ITMP2); - i386_shrd_imm_reg_reg(cd, iptr->val.i, REG_ITMP2, REG_ITMP1); - i386_shift_imm_reg(cd, I386_SAR, iptr->val.i, REG_ITMP2); - - i386_mov_reg_membase(cd, REG_ITMP1, REG_SP, iptr->dst->regoff * 4); - i386_mov_reg_membase(cd, REG_ITMP2, REG_SP, iptr->dst->regoff * 4 + 4); - } - } - break; - case ICMD_IREMPOW2: /* ..., value ==> ..., value % constant */ /* val.i = constant */ /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: YES ECX: YES EDX: NO OUTPUT: REG_NULL*/ + /* EAX: YES ECX: YES EDX: NO OUTPUT: REG_NULL */ var_to_reg_int(s1, src, REG_ITMP1); d = reg_of_var(rd, iptr->dst, REG_ITMP2); @@ -1624,17 +1624,17 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) s1 = REG_ITMP1; } - a = 2; - a += 2; - a += 2; - CALCIMMEDIATEBYTES(a, iptr->val.i); - a += 2; + disp = 2; + disp += 2; + disp += 2; + CALCIMMEDIATEBYTES(disp, iptr->val.i); + disp += 2; /* TODO: optimize */ M_INTMOVE(s1, d); i386_alu_imm_reg(cd, ALU_AND, iptr->val.i, d); i386_test_reg_reg(cd, s1, s1); - i386_jcc(cd, I386_CC_GE, a); + i386_jcc(cd, I386_CC_GE, disp); i386_mov_reg_reg(cd, s1, d); i386_neg_reg(cd, d); i386_alu_imm_reg(cd, ALU_AND, iptr->val.i, d); @@ -1657,10 +1657,67 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) store_reg_to_var_int(iptr->dst, d); break; + case ICMD_LDIV: /* ..., val1, val2 ==> ..., val1 / val2 */ + case ICMD_LREM: /* ..., val1, val2 ==> ..., val1 % val2 */ + + d = reg_of_var(rd, iptr->dst, REG_NULL); + M_ILD(REG_ITMP2, REG_SP, src->regoff * 4); + M_OR_MEMBASE(REG_SP, src->regoff * 4 + 4, REG_ITMP2); + M_TEST(REG_ITMP2); + M_BEQ(0); + codegen_addxdivrefs(cd, cd->mcodeptr); + + bte = iptr->val.a; + md = bte->md; + + M_ILD(REG_ITMP1, REG_SP, src->prev->regoff * 4); + M_ILD(REG_ITMP2, REG_SP, src->prev->regoff * 4 + 4); + M_IST(REG_ITMP1, REG_SP, 0 * 4); + M_IST(REG_ITMP2, REG_SP, 0 * 4 + 4); + + M_ILD(REG_ITMP1, REG_SP, src->regoff * 4); + M_ILD(REG_ITMP2, REG_SP, src->regoff * 4 + 4); + M_IST(REG_ITMP1, REG_SP, 2 * 4); + M_IST(REG_ITMP2, REG_SP, 2 * 4 + 4); + + M_MOV_IMM((ptrint) bte->fp, REG_ITMP3); + M_CALL(REG_ITMP3); + + M_IST(REG_RESULT, REG_SP, iptr->dst->regoff * 4); + M_IST(REG_RESULT2, REG_SP, iptr->dst->regoff * 4 + 4); + break; + + case ICMD_LDIVPOW2: /* ..., value ==> ..., value >> constant */ + /* val.i = constant */ + /* REG_RES Register usage: see icmd_uses_reg_res.inc */ + /* EAX: YES ECX: YES EDX: NO OUTPUT: REG_NULL */ + + d = reg_of_var(rd, iptr->dst, REG_NULL); + if (iptr->dst->flags & INMEMORY) { + if (src->flags & INMEMORY) { + disp = 2; + CALCIMMEDIATEBYTES(disp, (1 << iptr->val.i) - 1); + disp += 3; + i386_mov_membase_reg(cd, REG_SP, src->regoff * 4, REG_ITMP1); + i386_mov_membase_reg(cd, REG_SP, src->regoff * 4 + 4, REG_ITMP2); + + i386_test_reg_reg(cd, REG_ITMP2, REG_ITMP2); + i386_jcc(cd, I386_CC_NS, disp); + i386_alu_imm_reg(cd, ALU_ADD, (1 << iptr->val.i) - 1, REG_ITMP1); + i386_alu_imm_reg(cd, ALU_ADC, 0, REG_ITMP2); + i386_shrd_imm_reg_reg(cd, iptr->val.i, REG_ITMP2, REG_ITMP1); + i386_shift_imm_reg(cd, I386_SAR, iptr->val.i, REG_ITMP2); + + i386_mov_reg_membase(cd, REG_ITMP1, REG_SP, iptr->dst->regoff * 4); + i386_mov_reg_membase(cd, REG_ITMP2, REG_SP, iptr->dst->regoff * 4 + 4); + } + } + break; + case ICMD_LREMPOW2: /* ..., value ==> ..., value % constant */ /* val.l = constant */ /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: YES ECX: YES EDX: NO OUTPUT: REG_NULL*/ + /* EAX: YES ECX: YES EDX: NO OUTPUT: REG_NULL */ d = reg_of_var(rd, iptr->dst, REG_NULL); if (iptr->dst->flags & INMEMORY) { @@ -1689,24 +1746,24 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) /* i386_mov_reg_membase(cd, REG_ITMP2, REG_SP, iptr->dst->regoff * 4 + 4); */ /* Alpha algorithm */ - a = 3; - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4); - a += 3; - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4 + 4); + disp = 3; + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4); + disp += 3; + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4 + 4); - a += 2; - a += 3; - a += 2; + disp += 2; + disp += 3; + disp += 2; /* TODO: hmm, don't know if this is always correct */ - a += 2; - CALCIMMEDIATEBYTES(a, iptr->val.l & 0x00000000ffffffff); - a += 2; - CALCIMMEDIATEBYTES(a, iptr->val.l >> 32); + disp += 2; + CALCIMMEDIATEBYTES(disp, iptr->val.l & 0x00000000ffffffff); + disp += 2; + CALCIMMEDIATEBYTES(disp, iptr->val.l >> 32); - a += 2; - a += 3; - a += 2; + disp += 2; + disp += 3; + disp += 2; i386_mov_membase_reg(cd, REG_SP, src->regoff * 4, REG_ITMP1); i386_mov_membase_reg(cd, REG_SP, src->regoff * 4 + 4, REG_ITMP2); @@ -1714,7 +1771,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) i386_alu_imm_reg(cd, ALU_AND, iptr->val.l, REG_ITMP1); i386_alu_imm_reg(cd, ALU_AND, iptr->val.l >> 32, REG_ITMP2); i386_alu_imm_membase(cd, ALU_CMP, 0, REG_SP, src->regoff * 4 + 4); - i386_jcc(cd, I386_CC_GE, a); + i386_jcc(cd, I386_CC_GE, disp); i386_mov_membase_reg(cd, REG_SP, src->regoff * 4, REG_ITMP1); i386_mov_membase_reg(cd, REG_SP, src->regoff * 4 + 4, REG_ITMP2); @@ -2119,17 +2176,16 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) case ICMD_IINC: /* ..., value ==> ..., value + constant */ /* op1 = variable, val.i = constant */ /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: NO ECX: NO EDX: NO OUTPUT: REG_NULL*/ + /* EAX: NO ECX: NO EDX: NO OUTPUT: REG_NULL */ var = &(rd->locals[iptr->op1][TYPE_INT]); - if (var->flags & INMEMORY) { - i386_alu_imm_membase(cd, ALU_ADD, iptr->val.i, REG_SP, var->regoff * 4); - - } else { - /* `inc reg' is slower on p4's (regarding to ia32 */ - /* optimization reference manual and benchmarks) and as fast */ - /* on athlon's. */ - i386_alu_imm_reg(cd, ALU_ADD, iptr->val.i, var->regoff); + if (var->flags & INMEMORY) + M_IADD_IMM_MEMBASE(iptr->val.i, REG_SP, var->regoff * 4); + else { + /* `inc reg' is slower on p4's (regarding to ia32 + optimization reference manual and benchmarks) and + as fast on athlon's. */ + M_IADD_IMM(iptr->val.i, var->regoff); } break; @@ -2360,11 +2416,11 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) fpu_st_offset++; } else { - a = dseg_adds4(cd, 0); + disp = dseg_adds4(cd, 0); i386_mov_imm_reg(cd, 0, REG_ITMP1); dseg_adddata(cd, cd->mcodeptr); - i386_mov_reg_membase(cd, src->regoff, REG_ITMP1, a); - i386_fildl_membase(cd, REG_ITMP1, a); + i386_mov_reg_membase(cd, src->regoff, REG_ITMP1, disp); + i386_fildl_membase(cd, REG_ITMP1, disp); fpu_st_offset++; } store_reg_to_var_flt(iptr->dst, d); @@ -2394,46 +2450,50 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) var_to_reg_flt(s1, src, REG_FTMP1); d = reg_of_var(rd, iptr->dst, REG_NULL); - a = dseg_adds4(cd, 0x0e7f); /* Round to zero, 53-bit mode, exception masked */ i386_mov_imm_reg(cd, 0, REG_ITMP1); dseg_adddata(cd, cd->mcodeptr); - i386_fldcw_membase(cd, REG_ITMP1, a); + + /* Round to zero, 53-bit mode, exception masked */ + disp = dseg_adds4(cd, 0x0e7f); + i386_fldcw_membase(cd, REG_ITMP1, disp); if (iptr->dst->flags & INMEMORY) { i386_fistpl_membase(cd, REG_SP, iptr->dst->regoff * 4); fpu_st_offset--; - a = dseg_adds4(cd, 0x027f); /* Round to nearest, 53-bit mode, exceptions masked */ - i386_fldcw_membase(cd, REG_ITMP1, a); + /* Round to nearest, 53-bit mode, exceptions masked */ + disp = dseg_adds4(cd, 0x027f); + i386_fldcw_membase(cd, REG_ITMP1, disp); i386_alu_imm_membase(cd, ALU_CMP, 0x80000000, REG_SP, iptr->dst->regoff * 4); - a = 3; - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4); - a += 5 + 2 + 3; - CALCOFFSETBYTES(a, REG_SP, iptr->dst->regoff * 4); + disp = 3; + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4); + disp += 5 + 2 + 3; + CALCOFFSETBYTES(disp, REG_SP, iptr->dst->regoff * 4); } else { - a = dseg_adds4(cd, 0); - i386_fistpl_membase(cd, REG_ITMP1, a); + disp = dseg_adds4(cd, 0); + i386_fistpl_membase(cd, REG_ITMP1, disp); fpu_st_offset--; - i386_mov_membase_reg(cd, REG_ITMP1, a, iptr->dst->regoff); + i386_mov_membase_reg(cd, REG_ITMP1, disp, iptr->dst->regoff); - a = dseg_adds4(cd, 0x027f); /* Round to nearest, 53-bit mode, exceptions masked */ - i386_fldcw_membase(cd, REG_ITMP1, a); + /* Round to nearest, 53-bit mode, exceptions masked */ + disp = dseg_adds4(cd, 0x027f); + i386_fldcw_membase(cd, REG_ITMP1, disp); i386_alu_imm_reg(cd, ALU_CMP, 0x80000000, iptr->dst->regoff); - a = 3; - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4); - a += 5 + 2 + ((REG_RESULT == iptr->dst->regoff) ? 0 : 2); + disp = 3; + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4); + disp += 5 + 2 + ((REG_RESULT == iptr->dst->regoff) ? 0 : 2); } - i386_jcc(cd, I386_CC_NE, a); + i386_jcc(cd, I386_CC_NE, disp); /* XXX: change this when we use registers */ i386_flds_membase(cd, REG_SP, src->regoff * 4); - i386_mov_imm_reg(cd, (s4) asm_builtin_f2i, REG_ITMP1); + i386_mov_imm_reg(cd, (ptrint) asm_builtin_f2i, REG_ITMP1); i386_call_reg(cd, REG_ITMP1); if (iptr->dst->flags & INMEMORY) { @@ -2451,46 +2511,50 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) var_to_reg_flt(s1, src, REG_FTMP1); d = reg_of_var(rd, iptr->dst, REG_NULL); - a = dseg_adds4(cd, 0x0e7f); /* Round to zero, 53-bit mode, exception masked */ i386_mov_imm_reg(cd, 0, REG_ITMP1); dseg_adddata(cd, cd->mcodeptr); - i386_fldcw_membase(cd, REG_ITMP1, a); + + /* Round to zero, 53-bit mode, exception masked */ + disp = dseg_adds4(cd, 0x0e7f); + i386_fldcw_membase(cd, REG_ITMP1, disp); if (iptr->dst->flags & INMEMORY) { i386_fistpl_membase(cd, REG_SP, iptr->dst->regoff * 4); fpu_st_offset--; - a = dseg_adds4(cd, 0x027f); /* Round to nearest, 53-bit mode, exceptions masked */ - i386_fldcw_membase(cd, REG_ITMP1, a); + /* Round to nearest, 53-bit mode, exceptions masked */ + disp = dseg_adds4(cd, 0x027f); + i386_fldcw_membase(cd, REG_ITMP1, disp); i386_alu_imm_membase(cd, ALU_CMP, 0x80000000, REG_SP, iptr->dst->regoff * 4); - a = 3; - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4); - a += 5 + 2 + 3; - CALCOFFSETBYTES(a, REG_SP, iptr->dst->regoff * 4); + disp = 3; + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4); + disp += 5 + 2 + 3; + CALCOFFSETBYTES(disp, REG_SP, iptr->dst->regoff * 4); } else { - a = dseg_adds4(cd, 0); - i386_fistpl_membase(cd, REG_ITMP1, a); + disp = dseg_adds4(cd, 0); + i386_fistpl_membase(cd, REG_ITMP1, disp); fpu_st_offset--; - i386_mov_membase_reg(cd, REG_ITMP1, a, iptr->dst->regoff); + i386_mov_membase_reg(cd, REG_ITMP1, disp, iptr->dst->regoff); - a = dseg_adds4(cd, 0x027f); /* Round to nearest, 53-bit mode, exceptions masked */ - i386_fldcw_membase(cd, REG_ITMP1, a); + /* Round to nearest, 53-bit mode, exceptions masked */ + disp = dseg_adds4(cd, 0x027f); + i386_fldcw_membase(cd, REG_ITMP1, disp); i386_alu_imm_reg(cd, ALU_CMP, 0x80000000, iptr->dst->regoff); - a = 3; - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4); - a += 5 + 2 + ((REG_RESULT == iptr->dst->regoff) ? 0 : 2); + disp = 3; + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4); + disp += 5 + 2 + ((REG_RESULT == iptr->dst->regoff) ? 0 : 2); } - i386_jcc(cd, I386_CC_NE, a); + i386_jcc(cd, I386_CC_NE, disp); /* XXX: change this when we use registers */ i386_fldl_membase(cd, REG_SP, src->regoff * 4); - i386_mov_imm_reg(cd, (s4) asm_builtin_d2i, REG_ITMP1); + i386_mov_imm_reg(cd, (ptrint) asm_builtin_d2i, REG_ITMP1); i386_call_reg(cd, REG_ITMP1); if (iptr->dst->flags & INMEMORY) { @@ -2507,44 +2571,47 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) var_to_reg_flt(s1, src, REG_FTMP1); d = reg_of_var(rd, iptr->dst, REG_NULL); - a = dseg_adds4(cd, 0x0e7f); /* Round to zero, 53-bit mode, exception masked */ i386_mov_imm_reg(cd, 0, REG_ITMP1); dseg_adddata(cd, cd->mcodeptr); - i386_fldcw_membase(cd, REG_ITMP1, a); + + /* Round to zero, 53-bit mode, exception masked */ + disp = dseg_adds4(cd, 0x0e7f); + i386_fldcw_membase(cd, REG_ITMP1, disp); if (iptr->dst->flags & INMEMORY) { i386_fistpll_membase(cd, REG_SP, iptr->dst->regoff * 4); fpu_st_offset--; - a = dseg_adds4(cd, 0x027f); /* Round to nearest, 53-bit mode, exceptions masked */ - i386_fldcw_membase(cd, REG_ITMP1, a); + /* Round to nearest, 53-bit mode, exceptions masked */ + disp = dseg_adds4(cd, 0x027f); + i386_fldcw_membase(cd, REG_ITMP1, disp); i386_alu_imm_membase(cd, ALU_CMP, 0x80000000, REG_SP, iptr->dst->regoff * 4 + 4); - a = 6 + 4; - CALCOFFSETBYTES(a, REG_SP, iptr->dst->regoff * 4); - a += 3; - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4); - a += 5 + 2; - a += 3; - CALCOFFSETBYTES(a, REG_SP, iptr->dst->regoff * 4); - a += 3; - CALCOFFSETBYTES(a, REG_SP, iptr->dst->regoff * 4 + 4); + disp = 6 + 4; + CALCOFFSETBYTES(disp, REG_SP, iptr->dst->regoff * 4); + disp += 3; + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4); + disp += 5 + 2; + disp += 3; + CALCOFFSETBYTES(disp, REG_SP, iptr->dst->regoff * 4); + disp += 3; + CALCOFFSETBYTES(disp, REG_SP, iptr->dst->regoff * 4 + 4); - i386_jcc(cd, I386_CC_NE, a); + i386_jcc(cd, I386_CC_NE, disp); i386_alu_imm_membase(cd, ALU_CMP, 0, REG_SP, iptr->dst->regoff * 4); - a = 3; - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4); - a += 5 + 2 + 3; - CALCOFFSETBYTES(a, REG_SP, iptr->dst->regoff * 4); + disp = 3; + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4); + disp += 5 + 2 + 3; + CALCOFFSETBYTES(disp, REG_SP, iptr->dst->regoff * 4); - i386_jcc(cd, I386_CC_NE, a); + i386_jcc(cd, I386_CC_NE, disp); /* XXX: change this when we use registers */ i386_flds_membase(cd, REG_SP, src->regoff * 4); - i386_mov_imm_reg(cd, (s4) asm_builtin_f2l, REG_ITMP1); + i386_mov_imm_reg(cd, (ptrint) asm_builtin_f2l, REG_ITMP1); i386_call_reg(cd, REG_ITMP1); i386_mov_reg_membase(cd, REG_RESULT, REG_SP, iptr->dst->regoff * 4); i386_mov_reg_membase(cd, REG_RESULT2, REG_SP, iptr->dst->regoff * 4 + 4); @@ -2562,44 +2629,47 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) var_to_reg_flt(s1, src, REG_FTMP1); d = reg_of_var(rd, iptr->dst, REG_NULL); - a = dseg_adds4(cd, 0x0e7f); /* Round to zero, 53-bit mode, exception masked */ i386_mov_imm_reg(cd, 0, REG_ITMP1); dseg_adddata(cd, cd->mcodeptr); - i386_fldcw_membase(cd, REG_ITMP1, a); + + /* Round to zero, 53-bit mode, exception masked */ + disp = dseg_adds4(cd, 0x0e7f); + i386_fldcw_membase(cd, REG_ITMP1, disp); if (iptr->dst->flags & INMEMORY) { i386_fistpll_membase(cd, REG_SP, iptr->dst->regoff * 4); fpu_st_offset--; - a = dseg_adds4(cd, 0x027f); /* Round to nearest, 53-bit mode, exceptions masked */ - i386_fldcw_membase(cd, REG_ITMP1, a); + /* Round to nearest, 53-bit mode, exceptions masked */ + disp = dseg_adds4(cd, 0x027f); + i386_fldcw_membase(cd, REG_ITMP1, disp); i386_alu_imm_membase(cd, ALU_CMP, 0x80000000, REG_SP, iptr->dst->regoff * 4 + 4); - a = 6 + 4; - CALCOFFSETBYTES(a, REG_SP, iptr->dst->regoff * 4); - a += 3; - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4); - a += 5 + 2; - a += 3; - CALCOFFSETBYTES(a, REG_SP, iptr->dst->regoff * 4); - a += 3; - CALCOFFSETBYTES(a, REG_SP, iptr->dst->regoff * 4 + 4); + disp = 6 + 4; + CALCOFFSETBYTES(disp, REG_SP, iptr->dst->regoff * 4); + disp += 3; + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4); + disp += 5 + 2; + disp += 3; + CALCOFFSETBYTES(disp, REG_SP, iptr->dst->regoff * 4); + disp += 3; + CALCOFFSETBYTES(disp, REG_SP, iptr->dst->regoff * 4 + 4); - i386_jcc(cd, I386_CC_NE, a); + i386_jcc(cd, I386_CC_NE, disp); i386_alu_imm_membase(cd, ALU_CMP, 0, REG_SP, iptr->dst->regoff * 4); - a = 3; - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4); - a += 5 + 2 + 3; - CALCOFFSETBYTES(a, REG_SP, iptr->dst->regoff * 4); + disp = 3; + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4); + disp += 5 + 2 + 3; + CALCOFFSETBYTES(disp, REG_SP, iptr->dst->regoff * 4); - i386_jcc(cd, I386_CC_NE, a); + i386_jcc(cd, I386_CC_NE, disp); /* XXX: change this when we use registers */ i386_fldl_membase(cd, REG_SP, src->regoff * 4); - i386_mov_imm_reg(cd, (s4) asm_builtin_d2l, REG_ITMP1); + i386_mov_imm_reg(cd, (ptrint) asm_builtin_d2l, REG_ITMP1); i386_call_reg(cd, REG_ITMP1); i386_mov_reg_membase(cd, REG_RESULT, REG_SP, iptr->dst->regoff * 4); i386_mov_reg_membase(cd, REG_RESULT2, REG_SP, iptr->dst->regoff * 4 + 4); @@ -2824,23 +2894,9 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) break; - case ICMD_AASTORE: /* ..., arrayref, index, value ==> ... */ - /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: S|YES ECX: S|YES EDX: S|YES OUTPUT: REG_NULL*/ - - var_to_reg_int(s1, src->prev->prev, REG_ITMP1); - var_to_reg_int(s2, src->prev, REG_ITMP2); - if (iptr->op1 == 0) { - gen_nullptr_check(s1); - gen_bound_check; - } - var_to_reg_int(s3, src, REG_ITMP3); - i386_mov_reg_memindex(cd, s3, OFFSET(java_objectarray, data[0]), s1, s2, 2); - break; - case ICMD_LASTORE: /* ..., arrayref, index, value ==> ... */ /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: S|YES ECX: S|YES EDX: S|YES OUTPUT: REG_NULL*/ + /* EAX: S|YES ECX: S|YES EDX: S|YES OUTPUT: REG_NULL */ var_to_reg_int(s1, src->prev->prev, REG_ITMP1); var_to_reg_int(s2, src->prev, REG_ITMP2); @@ -2947,6 +3003,33 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) i386_movb_reg_memindex(cd, s3, OFFSET(java_bytearray, data[0]), s1, s2, 0); break; + case ICMD_AASTORE: /* ..., arrayref, index, value ==> ... */ + + /* REG_RES Register usage: see icmd_uses_reg_res.inc */ + /* EAX: S|YES ECX: S|YES EDX: S|YES OUTPUT: REG_NULL */ + + var_to_reg_int(s1, src->prev->prev, REG_ITMP1); + var_to_reg_int(s2, src->prev, REG_ITMP2); + if (iptr->op1 == 0) { + gen_nullptr_check(s1); + gen_bound_check; + } + var_to_reg_int(s3, src, REG_ITMP3); + + M_AST(s1, REG_SP, 0 * 4); + M_AST(s3, REG_SP, 1 * 4); + M_MOV_IMM((ptrint) BUILTIN_canstore, REG_ITMP1); + M_CALL(REG_ITMP1); + M_TEST(REG_RESULT); + M_BEQ(0); + codegen_addxstorerefs(cd, cd->mcodeptr); + + var_to_reg_int(s1, src->prev->prev, REG_ITMP1); + var_to_reg_int(s2, src->prev, REG_ITMP2); + var_to_reg_int(s3, src, REG_ITMP3); + i386_mov_reg_memindex(cd, s3, OFFSET(java_objectarray, data[0]), s1, s2, 2); + break; + case ICMD_IASTORECONST: /* ..., arrayref, index ==> ... */ /* REG_RES Register usage: see icmd_uses_reg_res.inc */ /* EAX: S|YES ECX: S|YES EDX: NO OUTPUT: REG_NULL*/ @@ -3033,45 +3116,45 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) /* REG_RES Register usage: see icmd_uses_reg_res.inc */ /* EAX: S|YES ECX: S|YES EDX: S|YES OUTPUT: EAX*/ - if (!iptr->val.a) { + if (iptr->val.a == NULL) { codegen_addpatchref(cd, cd->mcodeptr, PATCHER_get_putstatic, - (unresolved_field *) iptr->target); + (unresolved_field *) iptr->target, 0); - if (showdisassemble) { + if (opt_showdisassemble) { M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; } - a = 0; + disp = 0; } else { fieldinfo *fi = iptr->val.a; - if (!fi->class->initialized) { + if (!CLASS_IS_OR_ALMOST_INITIALIZED(fi->class)) { codegen_addpatchref(cd, cd->mcodeptr, - PATCHER_clinit, fi->class); + PATCHER_clinit, fi->class, 0); - if (showdisassemble) { + if (opt_showdisassemble) { M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; } } - a = (ptrint) &(fi->value); + disp = (ptrint) &(fi->value); } - i386_mov_imm_reg(cd, a, REG_ITMP1); + M_MOV_IMM(disp, REG_ITMP1); switch (iptr->op1) { case TYPE_INT: case TYPE_ADR: d = reg_of_var(rd, iptr->dst, REG_ITMP2); - i386_mov_membase_reg(cd, REG_ITMP1, 0, d); + M_ILD(d, REG_ITMP1, 0); store_reg_to_var_int(iptr->dst, d); break; case TYPE_LNG: d = reg_of_var(rd, iptr->dst, REG_NULL); if (iptr->dst->flags & INMEMORY) { - /* Using both REG_ITMP2 and REG_ITMP3 is faster than only */ - /* using REG_ITMP2 alternating. */ + /* Using both REG_ITMP2 and REG_ITMP3 is faster + than only using REG_ITMP2 alternating. */ i386_mov_membase_reg(cd, REG_ITMP1, 0, REG_ITMP2); i386_mov_membase_reg(cd, REG_ITMP1, 4, REG_ITMP3); i386_mov_reg_membase(cd, REG_ITMP2, REG_SP, iptr->dst->regoff * 4); @@ -3101,43 +3184,43 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) /* REG_RES Register usage: see icmd_uses_reg_res.inc */ /* EAX: S|YES ECX: S|YES EDX: S|YES OUTPUT: REG_NULL*/ - if (!iptr->val.a) { + if (iptr->val.a == NULL) { codegen_addpatchref(cd, cd->mcodeptr, PATCHER_get_putstatic, - (unresolved_field *) iptr->target); + (unresolved_field *) iptr->target, 0); - if (showdisassemble) { + if (opt_showdisassemble) { M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; } - a = 0; + disp = 0; } else { fieldinfo *fi = iptr->val.a; - if (!fi->class->initialized) { + if (!CLASS_IS_OR_ALMOST_INITIALIZED(fi->class)) { codegen_addpatchref(cd, cd->mcodeptr, - PATCHER_clinit, fi->class); + PATCHER_clinit, fi->class, 0); - if (showdisassemble) { + if (opt_showdisassemble) { M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; } } - a = (ptrint) &(fi->value); + disp = (ptrint) &(fi->value); } - i386_mov_imm_reg(cd, a, REG_ITMP1); + M_MOV_IMM(disp, REG_ITMP1); switch (iptr->op1) { case TYPE_INT: case TYPE_ADR: var_to_reg_int(s2, src, REG_ITMP2); - i386_mov_reg_membase(cd, s2, REG_ITMP1, 0); + M_IST(s2, REG_ITMP1, 0); break; case TYPE_LNG: if (src->flags & INMEMORY) { - /* Using both REG_ITMP2 and REG_ITMP3 is faster than only */ - /* using REG_ITMP2 alternating. */ + /* Using both REG_ITMP2 and REG_ITMP3 is faster + than only using REG_ITMP2 alternating. */ s2 = src->regoff; i386_mov_membase_reg(cd, REG_SP, s2 * 4, REG_ITMP2); @@ -3169,33 +3252,33 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) /* REG_RES Register usage: see icmd_uses_reg_res.inc */ /* EAX: S|YES ECX: S|YES EDX: S|YES OUTPUT: REG_NULL*/ - if (!iptr[1].val.a) { + if (iptr[1].val.a == NULL) { codegen_addpatchref(cd, cd->mcodeptr, PATCHER_get_putstatic, - (unresolved_field *) iptr[1].target); + (unresolved_field *) iptr[1].target, 0); - if (showdisassemble) { + if (opt_showdisassemble) { M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; } - a = 0; + disp = 0; } else { fieldinfo *fi = iptr[1].val.a; - if (!fi->class->initialized) { + if (!CLASS_IS_OR_ALMOST_INITIALIZED(fi->class)) { codegen_addpatchref(cd, cd->mcodeptr, - PATCHER_clinit, fi->class); + PATCHER_clinit, fi->class, 0); - if (showdisassemble) { + if (opt_showdisassemble) { M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; } } - a = (ptrint) &(fi->value); + disp = (ptrint) &(fi->value); } - i386_mov_imm_reg(cd, a, REG_ITMP1); + M_MOV_IMM(disp, REG_ITMP1); switch (iptr[1].op1) { case TYPE_INT: case TYPE_FLT: @@ -3218,44 +3301,44 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) var_to_reg_int(s1, src, REG_ITMP1); gen_nullptr_check(s1); - if (!iptr->val.a) { + if (iptr->val.a == NULL) { codegen_addpatchref(cd, cd->mcodeptr, PATCHER_getfield, - (unresolved_field *) iptr->target); + (unresolved_field *) iptr->target, 0); - if (showdisassemble) { + if (opt_showdisassemble) { M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; } - a = 0; + disp = 0; } else { - a = ((fieldinfo *) (iptr->val.a))->offset; + disp = ((fieldinfo *) (iptr->val.a))->offset; } switch (iptr->op1) { case TYPE_INT: case TYPE_ADR: d = reg_of_var(rd, iptr->dst, REG_ITMP2); - i386_mov_membase32_reg(cd, s1, a, d); + i386_mov_membase32_reg(cd, s1, disp, d); store_reg_to_var_int(iptr->dst, d); break; case TYPE_LNG: d = reg_of_var(rd, iptr->dst, REG_NULL); - i386_mov_membase32_reg(cd, s1, a, REG_ITMP2); - i386_mov_membase32_reg(cd, s1, a + 4, REG_ITMP3); + i386_mov_membase32_reg(cd, s1, disp, REG_ITMP2); + i386_mov_membase32_reg(cd, s1, disp + 4, REG_ITMP3); i386_mov_reg_membase(cd, REG_ITMP2, REG_SP, iptr->dst->regoff * 4); i386_mov_reg_membase(cd, REG_ITMP3, REG_SP, iptr->dst->regoff * 4 + 4); break; case TYPE_FLT: d = reg_of_var(rd, iptr->dst, REG_FTMP1); - i386_flds_membase32(cd, s1, a); + i386_flds_membase32(cd, s1, disp); fpu_st_offset++; store_reg_to_var_flt(iptr->dst, d); break; case TYPE_DBL: d = reg_of_var(rd, iptr->dst, REG_FTMP1); - i386_fldl_membase32(cd, s1, a); + i386_fldl_membase32(cd, s1, disp); fpu_st_offset++; store_reg_to_var_flt(iptr->dst, d); break; @@ -3269,49 +3352,50 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) var_to_reg_int(s1, src->prev, REG_ITMP1); gen_nullptr_check(s1); + if ((iptr->op1 == TYPE_INT) || IS_ADR_TYPE(iptr->op1)) { var_to_reg_int(s2, src, REG_ITMP2); } else if (IS_FLT_DBL_TYPE(iptr->op1)) { var_to_reg_flt(s2, src, REG_FTMP2); } - if (!iptr->val.a) { + if (iptr->val.a == NULL) { codegen_addpatchref(cd, cd->mcodeptr, PATCHER_putfield, - (unresolved_field *) iptr->target); + (unresolved_field *) iptr->target, 0); - if (showdisassemble) { + if (opt_showdisassemble) { M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; } - a = 0; + disp = 0; } else { - a = ((fieldinfo *) (iptr->val.a))->offset; + disp = ((fieldinfo *) (iptr->val.a))->offset; } switch (iptr->op1) { case TYPE_INT: case TYPE_ADR: - i386_mov_reg_membase32(cd, s2, s1, a); + i386_mov_reg_membase32(cd, s2, s1, disp); break; case TYPE_LNG: if (src->flags & INMEMORY) { i386_mov_membase32_reg(cd, REG_SP, src->regoff * 4, REG_ITMP2); i386_mov_membase32_reg(cd, REG_SP, src->regoff * 4 + 4, REG_ITMP3); - i386_mov_reg_membase32(cd, REG_ITMP2, s1, a); - i386_mov_reg_membase32(cd, REG_ITMP3, s1, a + 4); + i386_mov_reg_membase32(cd, REG_ITMP2, s1, disp); + i386_mov_reg_membase32(cd, REG_ITMP3, s1, disp + 4); } else { log_text("PUTFIELD: longs have to be in memory"); assert(0); } break; case TYPE_FLT: - i386_fstps_membase32(cd, s1, a); + i386_fstps_membase32(cd, s1, disp); fpu_st_offset--; break; case TYPE_DBL: - i386_fstpl_membase32(cd, s1, a); + i386_fstpl_membase32(cd, s1, disp); fpu_st_offset--; break; } @@ -3327,31 +3411,31 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) var_to_reg_int(s1, src, REG_ITMP1); gen_nullptr_check(s1); - if (!iptr[1].val.a) { + if (iptr[1].val.a == NULL) { codegen_addpatchref(cd, cd->mcodeptr, PATCHER_putfieldconst, - (unresolved_field *) iptr[1].target); + (unresolved_field *) iptr[1].target, 0); - if (showdisassemble) { + if (opt_showdisassemble) { M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; } - a = 0; + disp = 0; } else { - a = ((fieldinfo *) (iptr[1].val.a))->offset; + disp = ((fieldinfo *) (iptr[1].val.a))->offset; } switch (iptr[1].op1) { case TYPE_INT: case TYPE_FLT: case TYPE_ADR: - i386_mov_imm_membase32(cd, iptr->val.i, s1, a); + i386_mov_imm_membase32(cd, iptr->val.i, s1, disp); break; case TYPE_LNG: case TYPE_DBL: - i386_mov_imm_membase32(cd, iptr->val.l, s1, a); - i386_mov_imm_membase32(cd, iptr->val.l >> 32, s1, a + 4); + i386_mov_imm_membase32(cd, iptr->val.l, s1, disp); + i386_mov_imm_membase32(cd, iptr->val.l >> 32, s1, disp + 4); break; } break; @@ -3361,16 +3445,28 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) case ICMD_ATHROW: /* ..., objectref ==> ... (, objectref) */ /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: YES ECX: YES EDX: YES OUTPUT: REG_NULL*/ + /* EAX: YES ECX: YES EDX: YES OUTPUT: REG_NULL */ var_to_reg_int(s1, src, REG_ITMP1); M_INTMOVE(s1, REG_ITMP1_XPTR); - i386_call_imm(cd, 0); /* passing exception pointer */ - i386_pop_reg(cd, REG_ITMP2_XPC); +#ifdef ENABLE_VERIFIER + if (iptr->val.a) { + codegen_addpatchref(cd, cd->mcodeptr, + PATCHER_athrow_areturn, + (unresolved_class *) iptr->val.a, 0); + + if (opt_showdisassemble) { + M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; + } + } +#endif /* ENABLE_VERIFIER */ + + M_CALL_IMM(0); /* passing exception pc */ + M_POP(REG_ITMP2_XPC); - i386_mov_imm_reg(cd, (s4) asm_handle_exception, REG_ITMP3); - i386_jmp_reg(cd, REG_ITMP3); + M_MOV_IMM((ptrint) asm_handle_exception, REG_ITMP3); + M_JMP(REG_ITMP3); break; case ICMD_GOTO: /* ... ==> ... */ @@ -3379,7 +3475,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) /* EAX: YES ECX: YES EDX: YES OUTPUT: REG_NULL*/ i386_jmp_imm(cd, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_JSR: /* ... ==> ... */ @@ -3388,7 +3484,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) /* EAX: YES ECX: YES EDX: YES OUTPUT: REG_NULL*/ i386_call_imm(cd, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_RET: /* ... ==> ... */ @@ -3413,7 +3509,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) i386_test_reg_reg(cd, src->regoff, src->regoff); } i386_jcc(cd, I386_CC_E, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IFNONNULL: /* ..., value ==> ... */ @@ -3428,7 +3524,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) i386_test_reg_reg(cd, src->regoff, src->regoff); } i386_jcc(cd, I386_CC_NE, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IFEQ: /* ..., value ==> ... */ @@ -3443,7 +3539,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) i386_alu_imm_reg(cd, ALU_CMP, iptr->val.i, src->regoff); } i386_jcc(cd, I386_CC_E, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IFLT: /* ..., value ==> ... */ @@ -3458,7 +3554,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) i386_alu_imm_reg(cd, ALU_CMP, iptr->val.i, src->regoff); } i386_jcc(cd, I386_CC_L, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IFLE: /* ..., value ==> ... */ @@ -3473,7 +3569,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) i386_alu_imm_reg(cd, ALU_CMP, iptr->val.i, src->regoff); } i386_jcc(cd, I386_CC_LE, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IFNE: /* ..., value ==> ... */ @@ -3488,7 +3584,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) i386_alu_imm_reg(cd, ALU_CMP, iptr->val.i, src->regoff); } i386_jcc(cd, I386_CC_NE, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IFGT: /* ..., value ==> ... */ @@ -3503,7 +3599,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) i386_alu_imm_reg(cd, ALU_CMP, iptr->val.i, src->regoff); } i386_jcc(cd, I386_CC_G, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IFGE: /* ..., value ==> ... */ @@ -3518,7 +3614,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) i386_alu_imm_reg(cd, ALU_CMP, iptr->val.i, src->regoff); } i386_jcc(cd, I386_CC_GE, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IF_LEQ: /* ..., value ==> ... */ @@ -3541,7 +3637,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) } i386_test_reg_reg(cd, REG_ITMP1, REG_ITMP1); i386_jcc(cd, I386_CC_E, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IF_LLT: /* ..., value ==> ... */ @@ -3552,17 +3648,17 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) if (src->flags & INMEMORY) { i386_alu_imm_membase(cd, ALU_CMP, iptr->val.l >> 32, REG_SP, src->regoff * 4 + 4); i386_jcc(cd, I386_CC_L, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); - a = 3 + 6; - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4); - CALCIMMEDIATEBYTES(a, iptr->val.l); + disp = 3 + 6; + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4); + CALCIMMEDIATEBYTES(disp, iptr->val.l); - i386_jcc(cd, I386_CC_G, a); + i386_jcc(cd, I386_CC_G, disp); i386_alu_imm_membase(cd, ALU_CMP, iptr->val.l, REG_SP, src->regoff * 4); i386_jcc(cd, I386_CC_B, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); } break; @@ -3574,17 +3670,17 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) if (src->flags & INMEMORY) { i386_alu_imm_membase(cd, ALU_CMP, iptr->val.l >> 32, REG_SP, src->regoff * 4 + 4); i386_jcc(cd, I386_CC_L, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); - a = 3 + 6; - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4); - CALCIMMEDIATEBYTES(a, iptr->val.l); + disp = 3 + 6; + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4); + CALCIMMEDIATEBYTES(disp, iptr->val.l); - i386_jcc(cd, I386_CC_G, a); + i386_jcc(cd, I386_CC_G, disp); i386_alu_imm_membase(cd, ALU_CMP, iptr->val.l, REG_SP, src->regoff * 4); i386_jcc(cd, I386_CC_BE, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); } break; @@ -3608,7 +3704,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) } i386_test_reg_reg(cd, REG_ITMP1, REG_ITMP1); i386_jcc(cd, I386_CC_NE, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IF_LGT: /* ..., value ==> ... */ @@ -3619,17 +3715,17 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) if (src->flags & INMEMORY) { i386_alu_imm_membase(cd, ALU_CMP, iptr->val.l >> 32, REG_SP, src->regoff * 4 + 4); i386_jcc(cd, I386_CC_G, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); - a = 3 + 6; - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4); - CALCIMMEDIATEBYTES(a, iptr->val.l); + disp = 3 + 6; + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4); + CALCIMMEDIATEBYTES(disp, iptr->val.l); - i386_jcc(cd, I386_CC_L, a); + i386_jcc(cd, I386_CC_L, disp); i386_alu_imm_membase(cd, ALU_CMP, iptr->val.l, REG_SP, src->regoff * 4); i386_jcc(cd, I386_CC_A, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); } break; @@ -3641,17 +3737,17 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) if (src->flags & INMEMORY) { i386_alu_imm_membase(cd, ALU_CMP, iptr->val.l >> 32, REG_SP, src->regoff * 4 + 4); i386_jcc(cd, I386_CC_G, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); - a = 3 + 6; - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4); - CALCIMMEDIATEBYTES(a, iptr->val.l); + disp = 3 + 6; + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4); + CALCIMMEDIATEBYTES(disp, iptr->val.l); - i386_jcc(cd, I386_CC_L, a); + i386_jcc(cd, I386_CC_L, disp); i386_alu_imm_membase(cd, ALU_CMP, iptr->val.l, REG_SP, src->regoff * 4); i386_jcc(cd, I386_CC_AE, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); } break; @@ -3674,7 +3770,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) i386_alu_reg_reg(cd, ALU_CMP, src->regoff, src->prev->regoff); } i386_jcc(cd, I386_CC_E, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IF_LCMPEQ: /* ..., value, value ==> ... */ @@ -3691,7 +3787,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) i386_test_reg_reg(cd, REG_ITMP1, REG_ITMP1); } i386_jcc(cd, I386_CC_E, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IF_ICMPNE: /* ..., value, value ==> ... */ @@ -3713,7 +3809,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) i386_alu_reg_reg(cd, ALU_CMP, src->regoff, src->prev->regoff); } i386_jcc(cd, I386_CC_NE, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IF_LCMPNE: /* ..., value, value ==> ... */ @@ -3730,7 +3826,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) i386_test_reg_reg(cd, REG_ITMP1, REG_ITMP1); } i386_jcc(cd, I386_CC_NE, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IF_ICMPLT: /* ..., value, value ==> ... */ @@ -3752,7 +3848,7 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) i386_alu_reg_reg(cd, ALU_CMP, src->regoff, src->prev->regoff); } i386_jcc(cd, I386_CC_L, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IF_LCMPLT: /* ..., value, value ==> ... */ @@ -3763,19 +3859,19 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) if ((src->flags & INMEMORY) && (src->prev->flags & INMEMORY)) { i386_mov_membase_reg(cd, REG_SP, src->prev->regoff * 4 + 4, REG_ITMP1); i386_alu_membase_reg(cd, ALU_CMP, REG_SP, src->regoff * 4 + 4, REG_ITMP1); - i386_jcc(cd, I386_CC_L, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + M_BLT(0); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); - a = 3 + 3 + 6; - CALCOFFSETBYTES(a, REG_SP, src->prev->regoff * 4); - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4); + disp = 3 + 3 + 6; + CALCOFFSETBYTES(disp, REG_SP, src->prev->regoff * 4); + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4); - i386_jcc(cd, I386_CC_G, a); + M_BGT(disp); i386_mov_membase_reg(cd, REG_SP, src->prev->regoff * 4, REG_ITMP1); i386_alu_membase_reg(cd, ALU_CMP, REG_SP, src->regoff * 4, REG_ITMP1); i386_jcc(cd, I386_CC_B, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); } break; @@ -3797,8 +3893,8 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) } else { i386_alu_reg_reg(cd, ALU_CMP, src->regoff, src->prev->regoff); } - i386_jcc(cd, I386_CC_G, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + M_BGT(0); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IF_LCMPGT: /* ..., value, value ==> ... */ @@ -3809,19 +3905,19 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) if ((src->flags & INMEMORY) && (src->prev->flags & INMEMORY)) { i386_mov_membase_reg(cd, REG_SP, src->prev->regoff * 4 + 4, REG_ITMP1); i386_alu_membase_reg(cd, ALU_CMP, REG_SP, src->regoff * 4 + 4, REG_ITMP1); - i386_jcc(cd, I386_CC_G, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + M_BGT(0); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); - a = 3 + 3 + 6; - CALCOFFSETBYTES(a, REG_SP, src->prev->regoff * 4); - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4); + disp = 3 + 3 + 6; + CALCOFFSETBYTES(disp, REG_SP, src->prev->regoff * 4); + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4); - i386_jcc(cd, I386_CC_L, a); + M_BLT(disp); i386_mov_membase_reg(cd, REG_SP, src->prev->regoff * 4, REG_ITMP1); i386_alu_membase_reg(cd, ALU_CMP, REG_SP, src->regoff * 4, REG_ITMP1); i386_jcc(cd, I386_CC_A, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); } break; @@ -3843,8 +3939,8 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) } else { i386_alu_reg_reg(cd, ALU_CMP, src->regoff, src->prev->regoff); } - i386_jcc(cd, I386_CC_LE, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + M_BLE(0); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IF_LCMPLE: /* ..., value, value ==> ... */ @@ -3855,19 +3951,19 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) if ((src->flags & INMEMORY) && (src->prev->flags & INMEMORY)) { i386_mov_membase_reg(cd, REG_SP, src->prev->regoff * 4 + 4, REG_ITMP1); i386_alu_membase_reg(cd, ALU_CMP, REG_SP, src->regoff * 4 + 4, REG_ITMP1); - i386_jcc(cd, I386_CC_L, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + M_BLT(0); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); - a = 3 + 3 + 6; - CALCOFFSETBYTES(a, REG_SP, src->prev->regoff * 4); - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4); + disp = 3 + 3 + 6; + CALCOFFSETBYTES(disp, REG_SP, src->prev->regoff * 4); + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4); - i386_jcc(cd, I386_CC_G, a); + M_BGT(disp); i386_mov_membase_reg(cd, REG_SP, src->prev->regoff * 4, REG_ITMP1); i386_alu_membase_reg(cd, ALU_CMP, REG_SP, src->regoff * 4, REG_ITMP1); - i386_jcc(cd, I386_CC_BE, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + M_BBE(0); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); } break; @@ -3889,8 +3985,8 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) } else { i386_alu_reg_reg(cd, ALU_CMP, src->regoff, src->prev->regoff); } - i386_jcc(cd, I386_CC_GE, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + M_BGE(0); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); break; case ICMD_IF_LCMPGE: /* ..., value, value ==> ... */ @@ -3901,19 +3997,19 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) if ((src->flags & INMEMORY) && (src->prev->flags & INMEMORY)) { i386_mov_membase_reg(cd, REG_SP, src->prev->regoff * 4 + 4, REG_ITMP1); i386_alu_membase_reg(cd, ALU_CMP, REG_SP, src->regoff * 4 + 4, REG_ITMP1); - i386_jcc(cd, I386_CC_G, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + M_BGT(0); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); - a = 3 + 3 + 6; - CALCOFFSETBYTES(a, REG_SP, src->prev->regoff * 4); - CALCOFFSETBYTES(a, REG_SP, src->regoff * 4); + disp = 3 + 3 + 6; + CALCOFFSETBYTES(disp, REG_SP, src->prev->regoff * 4); + CALCOFFSETBYTES(disp, REG_SP, src->regoff * 4); - i386_jcc(cd, I386_CC_L, a); + M_BLT(disp); i386_mov_membase_reg(cd, REG_SP, src->prev->regoff * 4, REG_ITMP1); i386_alu_membase_reg(cd, ALU_CMP, REG_SP, src->regoff * 4, REG_ITMP1); - i386_jcc(cd, I386_CC_AE, 0); - codegen_addreference(cd, BlockPtrOfPC(iptr->op1), cd->mcodeptr); + M_BAE(0); + codegen_addreference(cd, (basicblock *) iptr->target, cd->mcodeptr); } break; @@ -3980,13 +4076,11 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) case ICMD_IRETURN: /* ..., retvalue ==> ... */ - case ICMD_ARETURN: /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: YES ECX: YES EDX: YES OUTPUT: REG_NULL*/ + /* EAX: YES ECX: YES EDX: YES OUTPUT: REG_NULL */ var_to_reg_int(s1, src, REG_RESULT); M_INTMOVE(s1, REG_RESULT); - goto nowperformreturn; case ICMD_LRETURN: /* ..., retvalue ==> ... */ @@ -4001,19 +4095,37 @@ void codegen(methodinfo *m, codegendata *cd, registerdata *rd) log_text("LRETURN: longs have to be in memory"); assert(0); } + goto nowperformreturn; + + case ICMD_ARETURN: /* ..., retvalue ==> ... */ + /* REG_RES Register usage: see icmd_uses_reg_res.inc */ + /* EAX: YES ECX: YES EDX: YES OUTPUT: REG_NULL */ + + var_to_reg_int(s1, src, REG_RESULT); + M_INTMOVE(s1, REG_RESULT); + +#ifdef ENABLE_VERIFIER + if (iptr->val.a) { + codegen_addpatchref(cd, cd->mcodeptr, + PATCHER_athrow_areturn, + (unresolved_class *) iptr->val.a, 0); + if (opt_showdisassemble) { + M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; + } + } +#endif /* ENABLE_VERIFIER */ goto nowperformreturn; case ICMD_FRETURN: /* ..., retvalue ==> ... */ - case ICMD_DRETURN: /* ..., retvalue ==> ... */ + case ICMD_DRETURN: /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: YES ECX: YES EDX: YES OUTPUT: REG_NULL*/ + /* EAX: YES ECX: YES EDX: YES OUTPUT: REG_NULL */ var_to_reg_flt(s1, src, REG_FRESULT); /* this may be an early return -- keep the offset correct for the remaining code */ fpu_st_offset--; - goto nowperformreturn; case ICMD_RETURN: /* ... ==> ... */ @@ -4049,62 +4161,63 @@ nowperformreturn: #if defined(USE_THREADS) if (checksync && (m->flags & ACC_SYNCHRONIZED)) { - i386_mov_membase_reg(cd, REG_SP, rd->maxmemuse * 4, REG_ITMP2); + M_ALD(REG_ITMP2, REG_SP, rd->memuse * 4); /* we need to save the proper return value */ switch (iptr->opc) { case ICMD_IRETURN: case ICMD_ARETURN: - i386_mov_reg_membase(cd, REG_RESULT, REG_SP, rd->maxmemuse * 4); + M_IST(REG_RESULT, REG_SP, rd->memuse * 4); break; case ICMD_LRETURN: - i386_mov_reg_membase(cd, REG_RESULT, REG_SP, rd->maxmemuse * 4); - i386_mov_reg_membase(cd, REG_RESULT2, REG_SP, rd->maxmemuse * 4 + 4); + M_IST(REG_RESULT, REG_SP, rd->memuse * 4); + M_IST(REG_RESULT2, REG_SP, rd->memuse * 4 + 4); break; case ICMD_FRETURN: - i386_fsts_membase(cd, REG_SP, rd->maxmemuse * 4); + i386_fstps_membase(cd, REG_SP, rd->memuse * 4); break; case ICMD_DRETURN: - i386_fstl_membase(cd, REG_SP, rd->maxmemuse * 4); + i386_fstpl_membase(cd, REG_SP, rd->memuse * 4); break; } - i386_mov_reg_membase(cd, REG_ITMP2, REG_SP, 0); - i386_mov_imm_reg(cd, (ptrint) BUILTIN_monitorexit, REG_ITMP1); - i386_call_reg(cd, REG_ITMP1); + M_AST(REG_ITMP2, REG_SP, 0); + M_MOV_IMM((ptrint) BUILTIN_monitorexit, REG_ITMP1); + M_CALL(REG_ITMP1); /* and now restore the proper return value */ switch (iptr->opc) { case ICMD_IRETURN: case ICMD_ARETURN: - i386_mov_membase_reg(cd, REG_SP, rd->maxmemuse * 4, REG_RESULT); + M_ILD(REG_RESULT, REG_SP, rd->memuse * 4); break; case ICMD_LRETURN: - i386_mov_membase_reg(cd, REG_SP, rd->maxmemuse * 4, REG_RESULT); - i386_mov_membase_reg(cd, REG_SP, rd->maxmemuse * 4 + 4, REG_RESULT2); + M_ILD(REG_RESULT, REG_SP, rd->memuse * 4); + M_ILD(REG_RESULT2, REG_SP, rd->memuse * 4 + 4); break; case ICMD_FRETURN: - i386_flds_membase(cd, REG_SP, rd->maxmemuse * 4); + i386_flds_membase(cd, REG_SP, rd->memuse * 4); break; case ICMD_DRETURN: - i386_fldl_membase(cd, REG_SP, rd->maxmemuse * 4); + i386_fldl_membase(cd, REG_SP, rd->memuse * 4); break; } } #endif /* restore saved registers */ - for (i = rd->savintregcnt - 1; i >= rd->maxsavintreguse; i--) { - p--; - i386_mov_membase_reg(cd, REG_SP, p * 4, rd->savintregs[i]); + + for (i = INT_SAV_CNT - 1; i >= rd->savintreguse; i--) { + p--; M_ALD(rd->savintregs[i], REG_SP, p * 4); } - for (i = rd->savfltregcnt - 1; i >= rd->maxsavfltreguse; i--) { + + for (i = FLT_SAV_CNT - 1; i >= rd->savfltreguse; i--) { p--; i386_fldl_membase(cd, REG_SP, p * 4); fpu_st_offset++; @@ -4116,10 +4229,10 @@ nowperformreturn: fpu_st_offset--; } - /* deallocate stack */ - if (parentargs_base) { - i386_alu_imm_reg(cd, ALU_ADD, parentargs_base * 4, REG_SP); - } + /* deallocate stack */ + + if (parentargs_base) + M_AADD_IMM(parentargs_base * 4, REG_SP); i386_ret(cd); } @@ -4151,16 +4264,13 @@ nowperformreturn: i386_alu_imm_reg(cd, ALU_CMP, i - 1, REG_ITMP1); i386_jcc(cd, I386_CC_A, 0); - /* codegen_addreference(cd, BlockPtrOfPC(s4ptr[0]), cd->mcodeptr); */ codegen_addreference(cd, (basicblock *) tptr[0], cd->mcodeptr); /* build jump table top down and use address of lowest entry */ - /* s4ptr += 3 + i; */ tptr += i; while (--i >= 0) { - /* dseg_addtarget(cd, BlockPtrOfPC(*--s4ptr)); */ dseg_addtarget(cd, (basicblock *) tptr[0]); --tptr; } @@ -4197,12 +4307,10 @@ nowperformreturn: val = s4ptr[0]; i386_alu_imm_reg(cd, ALU_CMP, val, s1); i386_jcc(cd, I386_CC_E, 0); - /* codegen_addreference(cd, BlockPtrOfPC(s4ptr[1]), cd->mcodeptr); */ codegen_addreference(cd, (basicblock *) tptr[0], cd->mcodeptr); } i386_jmp_imm(cd, 0); - /* codegen_addreference(cd, BlockPtrOfPC(l), cd->mcodeptr); */ tptr = (void **) iptr->target; codegen_addreference(cd, (basicblock *) tptr[0], cd->mcodeptr); @@ -4212,8 +4320,9 @@ nowperformreturn: case ICMD_BUILTIN: /* ..., [arg1, [arg2 ...]] ==> ... */ /* op1 = arg count val.a = builtintable entry */ /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: S|YES ECX: YES EDX: YES OUTPUT: EAX*/ - bte = (builtintable_entry *) iptr->val.a; + /* EAX: S|YES ECX: YES EDX: YES OUTPUT: EAX*/ + + bte = iptr->val.a; md = bte->md; goto gen_method; @@ -4223,20 +4332,21 @@ nowperformreturn: case ICMD_INVOKESPECIAL:/* ..., objectref, [arg1, [arg2 ...]] ==> ... */ case ICMD_INVOKEVIRTUAL:/* op1 = arg count, val.a = method pointer */ case ICMD_INVOKEINTERFACE: + /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: S|YES ECX: YES EDX: YES OUTPUT: EAX*/ + /* EAX: S|YES ECX: YES EDX: YES OUTPUT: EAX */ lm = iptr->val.a; - if (lm) - md = lm->parseddesc; - else { + if (lm == NULL) { unresolved_method *um = iptr->target; md = um->methodref->parseddesc.md; + } else { + md = lm->parseddesc; } gen_method: - s3 = iptr->op1; + s3 = md->paramcount; MCODECHECK((s3 << 1) + 64); @@ -4293,23 +4403,19 @@ gen_method: switch (iptr->opc) { case ICMD_BUILTIN: + disp = (ptrint) bte->fp; d = md->returntype.type; - if (iptr->target) { - codegen_addpatchref(cd, cd->mcodeptr, bte->fp, iptr->target); + M_MOV_IMM(disp, REG_ITMP1); + M_CALL(REG_ITMP1); - if (showdisassemble) { - M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; - } + /* if op1 == true, we need to check for an exception */ - a = 0; - - } else { - a = (ptrint) bte->fp; + if (iptr->op1 == true) { + M_TEST(REG_RESULT); + M_BEQ(0); + codegen_addxexceptionrefs(cd, cd->mcodeptr); } - - i386_mov_imm_reg(cd, a, REG_ITMP1); - i386_call_reg(cd, REG_ITMP1); break; case ICMD_INVOKESPECIAL: @@ -4322,39 +4428,39 @@ gen_method: /* fall through */ case ICMD_INVOKESTATIC: - if (!lm) { + if (lm == NULL) { unresolved_method *um = iptr->target; codegen_addpatchref(cd, cd->mcodeptr, - PATCHER_invokestatic_special, um); + PATCHER_invokestatic_special, um, 0); - if (showdisassemble) { + if (opt_showdisassemble) { M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; } - a = 0; + disp = 0; d = md->returntype.type; } else { - a = (ptrint) lm->stubroutine; + disp = (ptrint) lm->stubroutine; d = lm->parseddesc->returntype.type; } - i386_mov_imm_reg(cd, a, REG_ITMP2); - i386_call_reg(cd, REG_ITMP2); + M_MOV_IMM(disp, REG_ITMP2); + M_CALL(REG_ITMP2); break; case ICMD_INVOKEVIRTUAL: - i386_mov_membase_reg(cd, REG_SP, 0, REG_ITMP1); + M_ALD(REG_ITMP1, REG_SP, 0 * 4); gen_nullptr_check(REG_ITMP1); - if (!lm) { + if (lm == NULL) { unresolved_method *um = iptr->target; codegen_addpatchref(cd, cd->mcodeptr, - PATCHER_invokevirtual, um); + PATCHER_invokevirtual, um, 0); - if (showdisassemble) { + if (opt_showdisassemble) { M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; } @@ -4367,24 +4473,22 @@ gen_method: d = md->returntype.type; } - i386_mov_membase_reg(cd, REG_ITMP1, - OFFSET(java_objectheader, vftbl), - REG_ITMP2); + M_ALD(REG_ITMP2, REG_ITMP1, OFFSET(java_objectheader, vftbl)); i386_mov_membase32_reg(cd, REG_ITMP2, s1, REG_ITMP1); - i386_call_reg(cd, REG_ITMP1); + M_CALL(REG_ITMP1); break; case ICMD_INVOKEINTERFACE: - i386_mov_membase_reg(cd, REG_SP, 0, REG_ITMP1); + M_ALD(REG_ITMP1, REG_SP, 0 * 4); gen_nullptr_check(REG_ITMP1); - if (!lm) { + if (lm == NULL) { unresolved_method *um = iptr->target; codegen_addpatchref(cd, cd->mcodeptr, - PATCHER_invokeinterface, um); + PATCHER_invokeinterface, um, 0); - if (showdisassemble) { + if (opt_showdisassemble) { M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; } @@ -4401,12 +4505,10 @@ gen_method: d = md->returntype.type; } - i386_mov_membase_reg(cd, REG_ITMP1, - OFFSET(java_objectheader, vftbl), - REG_ITMP1); + M_ALD(REG_ITMP1, REG_ITMP1, OFFSET(java_objectheader, vftbl)); i386_mov_membase32_reg(cd, REG_ITMP1, s1, REG_ITMP2); i386_mov_membase32_reg(cd, REG_ITMP2, s2, REG_ITMP1); - i386_call_reg(cd, REG_ITMP1); + M_CALL(REG_ITMP1); break; } @@ -4447,12 +4549,12 @@ gen_method: case ICMD_CHECKCAST: /* ..., objectref ==> ..., objectref */ - /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: YES ECX: I|YES EDX: I|YES OUTPUT: REG_NULL*/ - /* op1: 0 == array, 1 == class */ /* val.a: (classinfo*) superclass */ + /* REG_RES Register usage: see icmd_uses_reg_res.inc */ + /* EAX: YES ECX: I|YES EDX: I|YES OUTPUT: REG_NULL */ + /* superclass is an interface: * * OK if ((sub == NULL) || @@ -4466,189 +4568,217 @@ gen_method: * super->vftbl->diffval)); */ - { - classinfo *super; - vftbl_t *supervftbl; - s4 superindex; + if (iptr->op1 == 1) { + /* object type cast-check */ - super = (classinfo *) iptr->val.a; + classinfo *super; + vftbl_t *supervftbl; + s4 superindex; - if (!super) { - superindex = 0; - supervftbl = NULL; + super = (classinfo *) iptr->val.a; - } else { - superindex = super->index; - supervftbl = super->vftbl; - } + if (!super) { + superindex = 0; + supervftbl = NULL; + + } else { + superindex = super->index; + supervftbl = super->vftbl; + } #if defined(USE_THREADS) && defined(NATIVE_THREADS) - codegen_threadcritrestart(cd, cd->mcodeptr - cd->mcodebase); + codegen_threadcritrestart(cd, cd->mcodeptr - cd->mcodebase); #endif - var_to_reg_int(s1, src, REG_ITMP1); + var_to_reg_int(s1, src, REG_ITMP1); - /* calculate interface checkcast code size */ + /* calculate interface checkcast code size */ - s2 = 2; /* mov_membase_reg */ - CALCOFFSETBYTES(s2, s1, OFFSET(java_objectheader, vftbl)); + s2 = 2; /* mov_membase_reg */ + CALCOFFSETBYTES(s2, s1, OFFSET(java_objectheader, vftbl)); - s2 += (2 + 4 /* mov_membase32_reg */ + 2 + 4 /* sub imm32 */ + - 2 /* test */ + 6 /* jcc */ + 2 + 4 /* mov_membase32_reg */ + - 2 /* test */ + 6 /* jcc */); + s2 += (2 + 4 /* mov_membase32_reg */ + 2 + 4 /* sub imm32 */ + + 2 /* test */ + 6 /* jcc */ + 2 + 4 /* mov_membase32_reg */ + + 2 /* test */ + 6 /* jcc */); - if (!super) - s2 += (showdisassemble ? 5 : 0); + if (!super) + s2 += (opt_showdisassemble ? 5 : 0); - /* calculate class checkcast code size */ + /* calculate class checkcast code size */ - s3 = 2; /* mov_membase_reg */ - CALCOFFSETBYTES(s3, s1, OFFSET(java_objectheader, vftbl)); + s3 = 2; /* mov_membase_reg */ + CALCOFFSETBYTES(s3, s1, OFFSET(java_objectheader, vftbl)); - s3 += 5 /* mov_imm_reg */ + 2 + 4 /* mov_membase32_reg */; + s3 += 5 /* mov_imm_reg */ + 2 + 4 /* mov_membase32_reg */; #if 0 - if (s1 != REG_ITMP1) { - a += 2; - CALCOFFSETBYTES(a, REG_ITMP3, OFFSET(vftbl_t, baseval)); + if (s1 != REG_ITMP1) { + a += 2; + CALCOFFSETBYTES(a, REG_ITMP3, OFFSET(vftbl_t, baseval)); - a += 2; - CALCOFFSETBYTES(a, REG_ITMP3, OFFSET(vftbl_t, diffval)); + a += 2; + CALCOFFSETBYTES(a, REG_ITMP3, OFFSET(vftbl_t, diffval)); - a += 2; + a += 2; - } else + } else #endif - { - s3 += (2 + 4 /* mov_membase32_reg */ + 2 /* sub */ + - 5 /* mov_imm_reg */ + 2 /* mov_membase_reg */); - CALCOFFSETBYTES(s3, REG_ITMP3, OFFSET(vftbl_t, diffval)); - } + { + s3 += (2 + 4 /* mov_membase32_reg */ + 2 /* sub */ + + 5 /* mov_imm_reg */ + 2 /* mov_membase_reg */); + CALCOFFSETBYTES(s3, REG_ITMP3, OFFSET(vftbl_t, diffval)); + } - s3 += 2 /* cmp */ + 6 /* jcc */; + s3 += 2 /* cmp */ + 6 /* jcc */; - if (!super) - s3 += (showdisassemble ? 5 : 0); + if (!super) + s3 += (opt_showdisassemble ? 5 : 0); - /* if class is not resolved, check which code to call */ + /* if class is not resolved, check which code to call */ - if (!super) { - i386_test_reg_reg(cd, s1, s1); - i386_jcc(cd, I386_CC_Z, 5 + (showdisassemble ? 5 : 0) + 6 + 6 + s2 + 5 + s3); + if (!super) { + i386_test_reg_reg(cd, s1, s1); + i386_jcc(cd, I386_CC_Z, 5 + (opt_showdisassemble ? 5 : 0) + 6 + 6 + s2 + 5 + s3); - codegen_addpatchref(cd, cd->mcodeptr, - PATCHER_checkcast_instanceof_flags, - (constant_classref *) iptr->target); + codegen_addpatchref(cd, cd->mcodeptr, + PATCHER_checkcast_instanceof_flags, + (constant_classref *) iptr->target, 0); - if (showdisassemble) { - M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; + if (opt_showdisassemble) { + M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; + } + + i386_mov_imm_reg(cd, 0, REG_ITMP2); /* super->flags */ + i386_alu_imm_reg(cd, ALU_AND, ACC_INTERFACE, REG_ITMP2); + i386_jcc(cd, I386_CC_Z, s2 + 5); } - i386_mov_imm_reg(cd, 0, REG_ITMP2); /* super->flags */ - i386_alu_imm_reg(cd, ALU_AND, ACC_INTERFACE, REG_ITMP2); - i386_jcc(cd, I386_CC_Z, s2 + 5); - } + /* interface checkcast code */ - /* interface checkcast code */ + if (!super || (super->flags & ACC_INTERFACE)) { + if (super) { + i386_test_reg_reg(cd, s1, s1); + i386_jcc(cd, I386_CC_Z, s2); + } - if (!super || (super->flags & ACC_INTERFACE)) { - if (super) { - i386_test_reg_reg(cd, s1, s1); - i386_jcc(cd, I386_CC_Z, s2); - } + i386_mov_membase_reg(cd, s1, + OFFSET(java_objectheader, vftbl), + REG_ITMP2); - i386_mov_membase_reg(cd, s1, - OFFSET(java_objectheader, vftbl), - REG_ITMP2); - - if (!super) { - codegen_addpatchref(cd, cd->mcodeptr, - PATCHER_checkcast_instanceof_interface, - (constant_classref *) iptr->target); + if (!super) { + codegen_addpatchref(cd, cd->mcodeptr, + PATCHER_checkcast_instanceof_interface, + (constant_classref *) iptr->target, 0); - if (showdisassemble) { - M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; + if (opt_showdisassemble) { + M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; + } } - } - i386_mov_membase32_reg(cd, REG_ITMP2, - OFFSET(vftbl_t, interfacetablelength), - REG_ITMP3); - i386_alu_imm32_reg(cd, ALU_SUB, superindex, REG_ITMP3); - i386_test_reg_reg(cd, REG_ITMP3, REG_ITMP3); - i386_jcc(cd, I386_CC_LE, 0); - codegen_addxcastrefs(cd, cd->mcodeptr); - i386_mov_membase32_reg(cd, REG_ITMP2, - OFFSET(vftbl_t, interfacetable[0]) - - superindex * sizeof(methodptr*), - REG_ITMP3); - i386_test_reg_reg(cd, REG_ITMP3, REG_ITMP3); - i386_jcc(cd, I386_CC_E, 0); - codegen_addxcastrefs(cd, cd->mcodeptr); + i386_mov_membase32_reg(cd, REG_ITMP2, + OFFSET(vftbl_t, interfacetablelength), + REG_ITMP3); + i386_alu_imm32_reg(cd, ALU_SUB, superindex, REG_ITMP3); + i386_test_reg_reg(cd, REG_ITMP3, REG_ITMP3); + i386_jcc(cd, I386_CC_LE, 0); + codegen_addxcastrefs(cd, cd->mcodeptr); + i386_mov_membase32_reg(cd, REG_ITMP2, + OFFSET(vftbl_t, interfacetable[0]) - + superindex * sizeof(methodptr*), + REG_ITMP3); + i386_test_reg_reg(cd, REG_ITMP3, REG_ITMP3); + i386_jcc(cd, I386_CC_E, 0); + codegen_addxcastrefs(cd, cd->mcodeptr); - if (!super) - i386_jmp_imm(cd, s3); - } + if (!super) + i386_jmp_imm(cd, s3); + } - /* class checkcast code */ + /* class checkcast code */ - if (!super || !(super->flags & ACC_INTERFACE)) { - if (super) { - i386_test_reg_reg(cd, s1, s1); - i386_jcc(cd, I386_CC_Z, s3); - } + if (!super || !(super->flags & ACC_INTERFACE)) { + if (super) { + i386_test_reg_reg(cd, s1, s1); + i386_jcc(cd, I386_CC_Z, s3); + } - i386_mov_membase_reg(cd, s1, - OFFSET(java_objectheader, vftbl), - REG_ITMP2); + i386_mov_membase_reg(cd, s1, + OFFSET(java_objectheader, vftbl), + REG_ITMP2); - if (!super) { - codegen_addpatchref(cd, cd->mcodeptr, - PATCHER_checkcast_class, - (constant_classref *) iptr->target); + if (!super) { + codegen_addpatchref(cd, cd->mcodeptr, + PATCHER_checkcast_class, + (constant_classref *) iptr->target, 0); - if (showdisassemble) { - M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; + if (opt_showdisassemble) { + M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; + } } - } - i386_mov_imm_reg(cd, (ptrint) supervftbl, REG_ITMP3); + i386_mov_imm_reg(cd, (ptrint) supervftbl, REG_ITMP3); #if defined(USE_THREADS) && defined(NATIVE_THREADS) - codegen_threadcritstart(cd, cd->mcodeptr - cd->mcodebase); + codegen_threadcritstart(cd, cd->mcodeptr - cd->mcodebase); #endif - i386_mov_membase32_reg(cd, REG_ITMP2, - OFFSET(vftbl_t, baseval), - REG_ITMP2); - -/* if (s1 != REG_ITMP1) { */ -/* i386_mov_membase_reg(cd, REG_ITMP3, OFFSET(vftbl_t, baseval), REG_ITMP1); */ -/* i386_mov_membase_reg(cd, REG_ITMP3, OFFSET(vftbl_t, diffval), REG_ITMP3); */ -/* #if defined(USE_THREADS) && defined(NATIVE_THREADS) */ -/* codegen_threadcritstop(cd, cd->mcodeptr - cd->mcodebase); */ -/* #endif */ -/* i386_alu_reg_reg(cd, ALU_SUB, REG_ITMP1, REG_ITMP2); */ - -/* } else { */ - i386_mov_membase32_reg(cd, REG_ITMP3, - OFFSET(vftbl_t, baseval), - REG_ITMP3); - i386_alu_reg_reg(cd, ALU_SUB, REG_ITMP3, REG_ITMP2); - i386_mov_imm_reg(cd, (ptrint) supervftbl, REG_ITMP3); - i386_mov_membase_reg(cd, REG_ITMP3, - OFFSET(vftbl_t, diffval), - REG_ITMP3); + i386_mov_membase32_reg(cd, REG_ITMP2, + OFFSET(vftbl_t, baseval), + REG_ITMP2); + + /* if (s1 != REG_ITMP1) { */ + /* i386_mov_membase_reg(cd, REG_ITMP3, OFFSET(vftbl_t, baseval), REG_ITMP1); */ + /* i386_mov_membase_reg(cd, REG_ITMP3, OFFSET(vftbl_t, diffval), REG_ITMP3); */ + /* #if defined(USE_THREADS) && defined(NATIVE_THREADS) */ + /* codegen_threadcritstop(cd, cd->mcodeptr - cd->mcodebase); */ + /* #endif */ + /* i386_alu_reg_reg(cd, ALU_SUB, REG_ITMP1, REG_ITMP2); */ + + /* } else { */ + i386_mov_membase32_reg(cd, REG_ITMP3, + OFFSET(vftbl_t, baseval), + REG_ITMP3); + i386_alu_reg_reg(cd, ALU_SUB, REG_ITMP3, REG_ITMP2); + i386_mov_imm_reg(cd, (ptrint) supervftbl, REG_ITMP3); + i386_mov_membase_reg(cd, REG_ITMP3, + OFFSET(vftbl_t, diffval), + REG_ITMP3); #if defined(USE_THREADS) && defined(NATIVE_THREADS) - codegen_threadcritstop(cd, cd->mcodeptr - cd->mcodebase); + codegen_threadcritstop(cd, cd->mcodeptr - cd->mcodebase); #endif -/* } */ + /* } */ + + i386_alu_reg_reg(cd, ALU_CMP, REG_ITMP3, REG_ITMP2); + i386_jcc(cd, I386_CC_A, 0); /* (u) REG_ITMP2 > (u) REG_ITMP3 -> jump */ + codegen_addxcastrefs(cd, cd->mcodeptr); + } + d = reg_of_var(rd, iptr->dst, REG_ITMP3); + + } else { + /* array type cast-check */ + + var_to_reg_int(s1, src, REG_ITMP1); + M_AST(s1, REG_SP, 0 * 4); + + if (iptr->val.a == NULL) { + codegen_addpatchref(cd, cd->mcodeptr, + PATCHER_builtin_arraycheckcast, + iptr->target, 0); + + if (opt_showdisassemble) { + M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; + } + } - i386_alu_reg_reg(cd, ALU_CMP, REG_ITMP3, REG_ITMP2); - i386_jcc(cd, I386_CC_A, 0); /* (u) REG_ITMP2 > (u) REG_ITMP3 -> jump */ + M_AST_IMM((ptrint) iptr->val.a, REG_SP, 1 * 4); + M_MOV_IMM((ptrint) BUILTIN_arraycheckcast, REG_ITMP3); + M_CALL(REG_ITMP3); + M_TEST(REG_RESULT); + M_BEQ(0); codegen_addxcastrefs(cd, cd->mcodeptr); + + var_to_reg_int(s1, src, REG_ITMP1); + d = reg_of_var(rd, iptr->dst, s1); } - d = reg_of_var(rd, iptr->dst, REG_ITMP3); M_INTMOVE(s1, d); store_reg_to_var_int(iptr->dst, d); - } break; case ICMD_INSTANCEOF: /* ..., objectref ==> ..., intresult */ @@ -4709,7 +4839,7 @@ gen_method: 2 /* test */ + 6 /* jcc */ + 5 /* mov_imm_reg */); if (!super) - s2 += (showdisassemble ? 5 : 0); + s2 += (opt_showdisassemble ? 5 : 0); /* calculate class instanceof code size */ @@ -4727,7 +4857,7 @@ gen_method: 2 /* alu_reg_reg */ + 6 /* jcc */ + 5 /* mov_imm_reg */); if (!super) - s3 += (showdisassemble ? 5 : 0); + s3 += (opt_showdisassemble ? 5 : 0); i386_alu_reg_reg(cd, ALU_XOR, d, d); @@ -4735,13 +4865,13 @@ gen_method: if (!super) { i386_test_reg_reg(cd, s1, s1); - i386_jcc(cd, I386_CC_Z, 5 + (showdisassemble ? 5 : 0) + 6 + 6 + s2 + 5 + s3); + i386_jcc(cd, I386_CC_Z, 5 + (opt_showdisassemble ? 5 : 0) + 6 + 6 + s2 + 5 + s3); codegen_addpatchref(cd, cd->mcodeptr, PATCHER_checkcast_instanceof_flags, - (constant_classref *) iptr->target); + (constant_classref *) iptr->target, 0); - if (showdisassemble) { + if (opt_showdisassemble) { M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; } @@ -4754,8 +4884,8 @@ gen_method: if (!super || (super->flags & ACC_INTERFACE)) { if (super) { - i386_test_reg_reg(cd, s1, s1); - i386_jcc(cd, I386_CC_Z, s2); + M_TEST(s1); + M_BEQ(s2); } i386_mov_membase_reg(cd, s1, @@ -4765,9 +4895,9 @@ gen_method: if (!super) { codegen_addpatchref(cd, cd->mcodeptr, PATCHER_checkcast_instanceof_interface, - (constant_classref *) iptr->target); + (constant_classref *) iptr->target, 0); - if (showdisassemble) { + if (opt_showdisassemble) { M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; } } @@ -4778,30 +4908,30 @@ gen_method: i386_alu_imm32_reg(cd, ALU_SUB, superindex, REG_ITMP3); i386_test_reg_reg(cd, REG_ITMP3, REG_ITMP3); - a = (2 + 4 /* mov_membase32_reg */ + 2 /* test */ + - 6 /* jcc */ + 5 /* mov_imm_reg */); + disp = (2 + 4 /* mov_membase32_reg */ + 2 /* test */ + + 6 /* jcc */ + 5 /* mov_imm_reg */); - i386_jcc(cd, I386_CC_LE, a); + M_BLE(disp); i386_mov_membase32_reg(cd, REG_ITMP1, OFFSET(vftbl_t, interfacetable[0]) - superindex * sizeof(methodptr*), REG_ITMP1); - i386_test_reg_reg(cd, REG_ITMP1, REG_ITMP1); + M_TEST(REG_ITMP1); /* i386_setcc_reg(cd, I386_CC_A, d); */ /* i386_jcc(cd, I386_CC_BE, 5); */ - i386_jcc(cd, I386_CC_E, 5); - i386_mov_imm_reg(cd, 1, d); + M_BEQ(5); + M_MOV_IMM(1, d); if (!super) - i386_jmp_imm(cd, s3); + M_JMP_IMM(s3); } /* class instanceof code */ if (!super || !(super->flags & ACC_INTERFACE)) { if (super) { - i386_test_reg_reg(cd, s1, s1); - i386_jcc(cd, I386_CC_Z, s3); + M_TEST(s1); + M_BEQ(s3); } i386_mov_membase_reg(cd, s1, @@ -4811,9 +4941,9 @@ gen_method: if (!super) { codegen_addpatchref(cd, cd->mcodeptr, PATCHER_instanceof_class, - (constant_classref *) iptr->target); + (constant_classref *) iptr->target, 0); - if (showdisassemble) { + if (opt_showdisassemble) { M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; } } @@ -4844,100 +4974,70 @@ gen_method: } break; - case ICMD_CHECKASIZE: /* ..., size ==> ..., size */ - /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: NO ECX: NO EDX: NO OUTPUT: REG_NULL*/ - - if (src->flags & INMEMORY) { - i386_alu_imm_membase(cd, ALU_CMP, 0, REG_SP, src->regoff * 4); - - } else { - i386_test_reg_reg(cd, src->regoff, src->regoff); - } - i386_jcc(cd, I386_CC_L, 0); - codegen_addxcheckarefs(cd, cd->mcodeptr); - break; - - case ICMD_CHECKEXCEPTION: /* ... ==> ... */ - /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: YES ECX: NO EDX: NO OUTPUT: REG_NULL*/ - - i386_test_reg_reg(cd, REG_RESULT, REG_RESULT); - i386_jcc(cd, I386_CC_E, 0); - codegen_addxexceptionrefs(cd, cd->mcodeptr); break; case ICMD_MULTIANEWARRAY:/* ..., cnt1, [cnt2, ...] ==> ..., arrayref */ - /* op1 = dimension, val.a = array descriptor */ + /* op1 = dimension, val.a = class */ /* REG_RES Register usage: see icmd_uses_reg_res.inc */ - /* EAX: S|YES ECX: YES EDX: YES OUTPUT: EAX*/ + /* EAX: S|YES ECX: YES EDX: YES OUTPUT: EAX */ /* check for negative sizes and copy sizes to stack if necessary */ MCODECHECK((iptr->op1 << 1) + 64); for (s1 = iptr->op1; --s1 >= 0; src = src->prev) { - if (src->flags & INMEMORY) { - i386_alu_imm_membase(cd, ALU_CMP, 0, REG_SP, src->regoff * 4); - - } else { - i386_test_reg_reg(cd, src->regoff, src->regoff); - } - i386_jcc(cd, I386_CC_L, 0); - codegen_addxcheckarefs(cd, cd->mcodeptr); - - /* - * copy sizes to new stack location, because native function - * builtin_nmultianewarray access them as (int *) - */ - /*i386_mov_membase_reg(cd, REG_SP, src->regoff * 4, REG_ITMP1);*/ - /*i386_mov_reg_membase(cd, REG_ITMP1, REG_SP, -(iptr->op1 - s1) * 4);*/ - /* copy SAVEDVAR sizes to stack */ if (src->varkind != ARGVAR) { if (src->flags & INMEMORY) { - i386_mov_membase_reg(cd, REG_SP, src->regoff * 4, REG_ITMP1); - i386_mov_reg_membase(cd, REG_ITMP1, REG_SP, (s1 +3) * 4); + M_ILD(REG_ITMP1, REG_SP, src->regoff * 4); + M_IST(REG_ITMP1, REG_SP, (s1 + 3) * 4); } else { - i386_mov_reg_membase(cd, src->regoff, REG_SP, (s1 + 3) * 4); + M_IST(src->regoff, REG_SP, (s1 + 3) * 4); } } } /* is a patcher function set? */ - if (iptr->target) { + if (iptr->val.a == NULL) { codegen_addpatchref(cd, cd->mcodeptr, - (functionptr) iptr->target, iptr->val.a); + PATCHER_builtin_multianewarray, + (constant_classref *) iptr->target, 0); - if (showdisassemble) { + if (opt_showdisassemble) { M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; } - a = 0; + disp = 0; } else { - a = (ptrint) iptr->val.a; + disp = (ptrint) iptr->val.a; } /* a0 = dimension count */ - i386_mov_imm_membase(cd, iptr->op1, REG_SP, 0 * 4); + M_IST_IMM(iptr->op1, REG_SP, 0 * 4); /* a1 = arraydescriptor */ - i386_mov_imm_membase(cd, a, REG_SP, 1 * 4); + M_IST_IMM(disp, REG_SP, 1 * 4); /* a2 = pointer to dimensions = stack pointer */ - M_INTMOVE(REG_SP, REG_ITMP1); - i386_alu_imm_reg(cd, ALU_ADD, 3 * 4, REG_ITMP1); - i386_mov_reg_membase(cd, REG_ITMP1, REG_SP, 2 * 4); + M_MOV(REG_SP, REG_ITMP1); + M_AADD_IMM(3 * 4, REG_ITMP1); + M_AST(REG_ITMP1, REG_SP, 2 * 4); - i386_mov_imm_reg(cd, (ptrint) BUILTIN_multianewarray, REG_ITMP1); - i386_call_reg(cd, REG_ITMP1); + M_MOV_IMM((ptrint) BUILTIN_multianewarray, REG_ITMP1); + M_CALL(REG_ITMP1); + + /* check for exception before result assignment */ + + M_TEST(REG_RESULT); + M_BEQ(0); + codegen_addxexceptionrefs(cd, cd->mcodeptr); s1 = reg_of_var(rd, iptr->dst, REG_RESULT); M_INTMOVE(REG_RESULT, s1); @@ -4945,8 +5045,9 @@ gen_method: break; default: - throw_cacao_exception_exit(string_java_lang_InternalError, - "Unknown ICMD %d", iptr->opc); + *exceptionptr = + new_internalerror("Unknown ICMD %d", iptr->opc); + return false; } /* switch */ } /* for instruction */ @@ -4956,7 +5057,7 @@ gen_method: src = bptr->outstack; len = bptr->outdepth; MCODECHECK(64+len); -#ifdef LSRA +#if defined(ENABLE_LSRA) if (!opt_lsra) #endif while (src) { @@ -4997,401 +5098,296 @@ gen_method: } src = src->prev; } + + /* At the end of a basic block we may have to append some nops, + because the patcher stub calling code might be longer than the + actual instruction. So codepatching does not change the + following block unintentionally. */ + + if (cd->mcodeptr < cd->lastmcodeptr) { + while (cd->mcodeptr < cd->lastmcodeptr) { + M_NOP; + } + } + } /* if (bptr -> flags >= BBREACHED) */ } /* for basic block */ - codegen_createlinenumbertable(cd); + dseg_createlinenumbertable(cd); { - /* generate bound check stubs */ - - u1 *xcodeptr = NULL; + u1 *xcodeptr; branchref *bref; - for (bref = cd->xboundrefs; bref != NULL; bref = bref->next) { - gen_resolvebranch(cd->mcodebase + bref->branchpos, - bref->branchpos, - cd->mcodeptr - cd->mcodebase); - - MCODECHECK(100); - - /* move index register into REG_ITMP1 */ - i386_mov_reg_reg(cd, bref->reg, REG_ITMP1); /* 2 bytes */ - - i386_mov_imm_reg(cd, 0, REG_ITMP2_XPC); /* 5 bytes */ - dseg_adddata(cd, cd->mcodeptr); - i386_mov_imm_reg(cd, bref->branchpos - 6, REG_ITMP3); /* 5 bytes */ - i386_alu_reg_reg(cd, ALU_ADD, REG_ITMP3, REG_ITMP2_XPC); /* 2 bytes */ - - if (xcodeptr != NULL) { - i386_jmp_imm(cd, (xcodeptr - cd->mcodeptr) - 5); - - } else { - xcodeptr = cd->mcodeptr; - - i386_push_reg(cd, REG_ITMP2_XPC); - - /*PREPARE_NATIVE_STACKINFO;*/ - i386_push_imm(cd,0); /* the pushed XPC is directly below the java frame*/ - i386_push_imm(cd,0); - i386_mov_imm_reg(cd,(s4)asm_prepare_native_stackinfo,REG_ITMP3); - i386_call_reg(cd,REG_ITMP3); - - i386_alu_imm_reg(cd, ALU_SUB, 1 * 4, REG_SP); - i386_mov_reg_membase(cd, REG_ITMP1, REG_SP, 0 * 4); - i386_mov_imm_reg(cd, (u4) new_arrayindexoutofboundsexception, REG_ITMP1); - i386_call_reg(cd, REG_ITMP1); /* return value is REG_ITMP1_XPTR */ - i386_alu_imm_reg(cd, ALU_ADD, 1 * 4, REG_SP); - - /*REMOVE_NATIVE_STACKINFO;*/ - i386_mov_imm_reg(cd,(s4)asm_remove_native_stackinfo,REG_ITMP3); - i386_call_reg(cd,REG_ITMP3); - - i386_pop_reg(cd, REG_ITMP2_XPC); - - i386_mov_imm_reg(cd, (s4) asm_handle_exception, REG_ITMP3); - i386_jmp_reg(cd, REG_ITMP3); - } - } - - /* generate negative array size check stubs */ + /* generate ArithmeticException stubs */ xcodeptr = NULL; - for (bref = cd->xcheckarefs; bref != NULL; bref = bref->next) { - if ((cd->exceptiontablelength == 0) && (xcodeptr != NULL)) { - gen_resolvebranch(cd->mcodebase + bref->branchpos, - bref->branchpos, - xcodeptr - cd->mcodebase - (5 + 5 + 2)); - continue; - } - + for (bref = cd->xdivrefs; bref != NULL; bref = bref->next) { gen_resolvebranch(cd->mcodebase + bref->branchpos, bref->branchpos, cd->mcodeptr - cd->mcodebase); - MCODECHECK(100); + MCODECHECK(512); - i386_mov_imm_reg(cd, 0, REG_ITMP2_XPC); /* 5 bytes */ + M_MOV_IMM(0, REG_ITMP2_XPC); dseg_adddata(cd, cd->mcodeptr); - i386_mov_imm_reg(cd, bref->branchpos - 6, REG_ITMP1); /* 5 bytes */ - i386_alu_reg_reg(cd, ALU_ADD, REG_ITMP1, REG_ITMP2_XPC); /* 2 bytes */ + M_AADD_IMM32(bref->branchpos - 6, REG_ITMP2_XPC); if (xcodeptr != NULL) { - i386_jmp_imm(cd, (xcodeptr - cd->mcodeptr) - 5); - + M_JMP_IMM((xcodeptr - cd->mcodeptr) - 5); + } else { xcodeptr = cd->mcodeptr; - i386_push_reg(cd, REG_ITMP2_XPC); - - /*PREPARE_NATIVE_STACKINFO;*/ - i386_push_imm(cd,0); /* the pushed XPC is directly below the java frame*/ - i386_push_imm(cd,0); - i386_mov_imm_reg(cd,(s4)asm_prepare_native_stackinfo,REG_ITMP3); - i386_call_reg(cd,REG_ITMP3); - - - - i386_mov_imm_reg(cd, (u4) new_negativearraysizeexception, REG_ITMP1); - i386_call_reg(cd, REG_ITMP1); /* return value is REG_ITMP1_XPTR */ - /*i386_alu_imm_reg(cd, ALU_ADD, 1 * 4, REG_SP);*/ + M_ASUB_IMM(4 * 4, REG_SP); - - /*REMOVE_NATIVE_STACKINFO;*/ - i386_mov_imm_reg(cd,(s4)asm_remove_native_stackinfo,REG_ITMP3); - i386_call_reg(cd,REG_ITMP3); - - - i386_pop_reg(cd, REG_ITMP2_XPC); - - i386_mov_imm_reg(cd, (s4) asm_handle_exception, REG_ITMP3); - i386_jmp_reg(cd, REG_ITMP3); + M_AST_IMM(0, REG_SP, 0 * 4); + dseg_adddata(cd, cd->mcodeptr); + M_MOV(REG_SP, REG_ITMP3); + M_AADD_IMM(4 * 4, REG_ITMP3); + M_AST(REG_ITMP3, REG_SP, 1 * 4); + M_ALD(REG_ITMP3, REG_SP, (4 + parentargs_base) * 4); + M_AST(REG_ITMP3, REG_SP, 2 * 4); + M_AST(REG_ITMP2_XPC, REG_SP, 3 * 4); + + M_MOV_IMM((ptrint) stacktrace_inline_arithmeticexception, + REG_ITMP3); + M_CALL(REG_ITMP3); + + M_ALD(REG_ITMP2_XPC, REG_SP, 3 * 4); + M_AADD_IMM(4 * 4, REG_SP); + + M_MOV_IMM((ptrint) asm_handle_exception, REG_ITMP3); + M_JMP(REG_ITMP3); } } - /* generate cast check stubs */ + /* generate ArrayIndexOutOfBoundsException stubs */ xcodeptr = NULL; - - for (bref = cd->xcastrefs; bref != NULL; bref = bref->next) { - if ((cd->exceptiontablelength == 0) && (xcodeptr != NULL)) { - gen_resolvebranch(cd->mcodebase + bref->branchpos, - bref->branchpos, - xcodeptr - cd->mcodebase - (5 + 5 + 2)); - continue; - } - gen_resolvebranch(cd->mcodebase + bref->branchpos, + for (bref = cd->xboundrefs; bref != NULL; bref = bref->next) { + gen_resolvebranch(cd->mcodebase + bref->branchpos, bref->branchpos, cd->mcodeptr - cd->mcodebase); - MCODECHECK(100); + MCODECHECK(512); + + /* move index register into REG_ITMP1 */ + + M_INTMOVE(bref->reg, REG_ITMP1); - i386_mov_imm_reg(cd, 0, REG_ITMP2_XPC); /* 5 bytes */ + M_MOV_IMM(0, REG_ITMP2_XPC); dseg_adddata(cd, cd->mcodeptr); - i386_mov_imm_reg(cd, bref->branchpos - 6, REG_ITMP1); /* 5 bytes */ - i386_alu_reg_reg(cd, ALU_ADD, REG_ITMP1, REG_ITMP2_XPC); /* 2 bytes */ + M_AADD_IMM32(bref->branchpos - 6, REG_ITMP2_XPC); if (xcodeptr != NULL) { - i386_jmp_imm(cd, (xcodeptr - cd->mcodeptr) - 5); - + M_JMP_IMM((xcodeptr - cd->mcodeptr) - 5); + } else { xcodeptr = cd->mcodeptr; - i386_push_reg(cd, REG_ITMP2_XPC); - - /*PREPARE_NATIVE_STACKINFO;*/ - i386_push_imm(cd,0); /* the pushed XPC is directly below the java frame*/ - i386_push_imm(cd,0); - i386_mov_imm_reg(cd,(s4)asm_prepare_native_stackinfo,REG_ITMP3); - i386_call_reg(cd,REG_ITMP3); - - - i386_mov_imm_reg(cd, (u4) new_classcastexception, REG_ITMP1); - i386_call_reg(cd, REG_ITMP1); /* return value is REG_ITMP1_XPTR */ - /*i386_alu_imm_reg(cd, ALU_ADD, 1 * 4, REG_SP);*/ - + M_ASUB_IMM(5 * 4, REG_SP); - /*REMOVE_NATIVE_STACKINFO;*/ - i386_mov_imm_reg(cd,(s4)asm_remove_native_stackinfo,REG_ITMP3); - i386_call_reg(cd,REG_ITMP3); - - - i386_pop_reg(cd, REG_ITMP2_XPC); - - i386_mov_imm_reg(cd, (u4) asm_handle_exception, REG_ITMP3); - i386_jmp_reg(cd, REG_ITMP3); + M_AST_IMM(0, REG_SP, 0 * 4); + dseg_adddata(cd, cd->mcodeptr); + M_MOV(REG_SP, REG_ITMP3); + M_AADD_IMM(5 * 4, REG_ITMP3); + M_AST(REG_ITMP3, REG_SP, 1 * 4); + M_ALD(REG_ITMP3, REG_SP, (5 + parentargs_base) * 4); + M_AST(REG_ITMP3, REG_SP, 2 * 4); + M_AST(REG_ITMP2_XPC, REG_SP, 3 * 4); + M_AST(REG_ITMP1, REG_SP, 4 * 4); /* don't use REG_ITMP1 till here */ + + M_MOV_IMM((ptrint) stacktrace_inline_arrayindexoutofboundsexception, + REG_ITMP3); + M_CALL(REG_ITMP3); + + M_ALD(REG_ITMP2_XPC, REG_SP, 3 * 4); + M_AADD_IMM(5 * 4, REG_SP); + + M_MOV_IMM((ptrint) asm_handle_exception, REG_ITMP3); + M_JMP(REG_ITMP3); } } - /* generate divide by zero check stubs */ + /* generate ArrayStoreException stubs */ xcodeptr = NULL; - for (bref = cd->xdivrefs; bref != NULL; bref = bref->next) { - if ((cd->exceptiontablelength == 0) && (xcodeptr != NULL)) { - gen_resolvebranch(cd->mcodebase + bref->branchpos, - bref->branchpos, - xcodeptr - cd->mcodebase - (5 + 5 + 2)); - continue; - } - + for (bref = cd->xstorerefs; bref != NULL; bref = bref->next) { gen_resolvebranch(cd->mcodebase + bref->branchpos, bref->branchpos, cd->mcodeptr - cd->mcodebase); - MCODECHECK(100); + MCODECHECK(512); - i386_mov_imm_reg(cd, 0, REG_ITMP2_XPC); /* 5 bytes */ + M_MOV_IMM(0, REG_ITMP2_XPC); dseg_adddata(cd, cd->mcodeptr); - i386_mov_imm_reg(cd, bref->branchpos - 6, REG_ITMP1); /* 5 bytes */ - i386_alu_reg_reg(cd, ALU_ADD, REG_ITMP1, REG_ITMP2_XPC); /* 2 bytes */ + M_AADD_IMM32(bref->branchpos - 6, REG_ITMP2_XPC); if (xcodeptr != NULL) { - i386_jmp_imm(cd, (xcodeptr - cd->mcodeptr) - 5); - + M_JMP_IMM((xcodeptr - cd->mcodeptr) - 5); + } else { xcodeptr = cd->mcodeptr; - i386_push_reg(cd, REG_ITMP2_XPC); + M_ASUB_IMM(4 * 4, REG_SP); - /*PREPARE_NATIVE_STACKINFO;*/ - i386_push_imm(cd,0); /* the pushed XPC is directly below the java frame*/ - i386_push_imm(cd,0); - i386_mov_imm_reg(cd,(s4)asm_prepare_native_stackinfo,REG_ITMP3); - i386_call_reg(cd,REG_ITMP3); - - - - i386_mov_imm_reg(cd, (u4) new_arithmeticexception, REG_ITMP1); - i386_call_reg(cd, REG_ITMP1); /* return value is REG_ITMP1_XPTR */ - - /*REMOVE_NATIVE_STACKINFO;*/ - i386_mov_imm_reg(cd,(s4)asm_remove_native_stackinfo,REG_ITMP3); - i386_call_reg(cd,REG_ITMP3); - - - i386_pop_reg(cd, REG_ITMP2_XPC); - - i386_mov_imm_reg(cd, (s4) asm_handle_exception, REG_ITMP3); - i386_jmp_reg(cd, REG_ITMP3); + M_AST_IMM(0, REG_SP, 0 * 4); + dseg_adddata(cd, cd->mcodeptr); + M_MOV(REG_SP, REG_ITMP3); + M_AADD_IMM(4 * 4, REG_ITMP3); + M_AST(REG_ITMP3, REG_SP, 1 * 4); + M_ALD(REG_ITMP3, REG_SP, (4 + parentargs_base) * 4); + M_AST(REG_ITMP3, REG_SP, 2 * 4); + M_AST(REG_ITMP2_XPC, REG_SP, 3 * 4); + + M_MOV_IMM((ptrint) stacktrace_inline_arraystoreexception, + REG_ITMP3); + M_CALL(REG_ITMP3); + + M_ALD(REG_ITMP2_XPC, REG_SP, 3 * 4); + M_AADD_IMM(4 * 4, REG_SP); + + M_MOV_IMM((ptrint) asm_handle_exception, REG_ITMP3); + M_JMP(REG_ITMP3); } } - /* generate exception check stubs */ + /* generate ClassCastException stubs */ xcodeptr = NULL; - for (bref = cd->xexceptionrefs; bref != NULL; bref = bref->next) { - if ((cd->exceptiontablelength == 0) && (xcodeptr != NULL)) { - gen_resolvebranch(cd->mcodebase + bref->branchpos, - bref->branchpos, - xcodeptr - cd->mcodebase - (5 + 5 + 2)); - continue; - } - + for (bref = cd->xcastrefs; bref != NULL; bref = bref->next) { gen_resolvebranch(cd->mcodebase + bref->branchpos, bref->branchpos, cd->mcodeptr - cd->mcodebase); - MCODECHECK(200); + MCODECHECK(512); - i386_mov_imm_reg(cd, 0, REG_ITMP2_XPC); /* 5 bytes */ + M_MOV_IMM(0, REG_ITMP2_XPC); dseg_adddata(cd, cd->mcodeptr); - i386_mov_imm_reg(cd, bref->branchpos - 6, REG_ITMP1); /* 5 bytes */ - i386_alu_reg_reg(cd, ALU_ADD, REG_ITMP1, REG_ITMP2_XPC); /* 2 bytes */ + M_AADD_IMM32(bref->branchpos - 6, REG_ITMP2_XPC); if (xcodeptr != NULL) { - i386_jmp_imm(cd, (xcodeptr - cd->mcodeptr) - 5); + M_JMP_IMM((xcodeptr - cd->mcodeptr) - 5); } else { xcodeptr = cd->mcodeptr; - i386_push_reg(cd, REG_ITMP2_XPC); - - /*PREPARE_NATIVE_STACKINFO;*/ - i386_push_imm(cd,0); /* the pushed XPC is directly below the java frame*/ - i386_push_imm(cd,0); - i386_mov_imm_reg(cd,(s4)asm_prepare_native_stackinfo,REG_ITMP3); - i386_call_reg(cd,REG_ITMP3); + M_ASUB_IMM(4 * 4, REG_SP); -#if defined(USE_THREADS) && defined(NATIVE_THREADS) - i386_mov_imm_reg(cd, (s4) &builtin_get_exceptionptrptr, REG_ITMP1); - i386_call_reg(cd, REG_ITMP1); - i386_mov_membase_reg(cd, REG_RESULT, 0, REG_ITMP3); - i386_mov_imm_membase(cd, 0, REG_RESULT, 0); - i386_mov_reg_reg(cd, REG_ITMP3, REG_ITMP1_XPTR); -#else - i386_mov_imm_reg(cd, (s4) &_exceptionptr, REG_ITMP3); - i386_mov_membase_reg(cd, REG_ITMP3, 0, REG_ITMP1_XPTR); - i386_mov_imm_membase(cd, 0, REG_ITMP3, 0); -#endif - i386_push_imm(cd, 0); - i386_push_reg(cd, REG_ITMP1_XPTR); - -/*get the fillInStackTrace Method ID. I simulate a native call here, because I do not want to mess around with the -java stack at this point*/ - i386_mov_membase_reg(cd, REG_ITMP1_XPTR, OFFSET(java_objectheader, vftbl), REG_ITMP3); - i386_mov_membase_reg(cd, REG_ITMP3, OFFSET(vftbl_t, class), REG_ITMP1); - i386_push_imm(cd, (u4) utf_void__java_lang_Throwable); - i386_push_imm(cd, (u4) utf_fillInStackTrace); - i386_push_reg(cd, REG_ITMP1); - i386_mov_imm_reg(cd, (s4) class_resolvemethod, REG_ITMP3); - i386_call_reg(cd, REG_ITMP3); -/*cleanup parameters of class_resolvemethod*/ - i386_alu_imm_reg(cd, ALU_ADD,3*4 /*class reference + 2x string reference*/,REG_SP); -/*prepare call to asm_calljavafunction2 */ - i386_push_imm(cd, 0); - i386_push_imm(cd, TYPE_ADR); /* --> call block (TYPE,Exceptionptr), each 8 byte (make this dynamic) (JOWENN)*/ - i386_push_reg(cd, REG_SP); - i386_push_imm(cd, sizeof(jni_callblock)); - i386_push_imm(cd, 1); - i386_push_reg(cd, REG_RESULT); - - i386_mov_imm_reg(cd, (s4) asm_calljavafunction2, REG_ITMP3); - i386_call_reg(cd, REG_ITMP3); - - /* check exceptionptr + fail (JOWENN)*/ - - i386_alu_imm_reg(cd, ALU_ADD,6*4,REG_SP); - - i386_pop_reg(cd, REG_ITMP1_XPTR); - i386_pop_reg(cd, REG_ITMP3); /* just remove the no longer needed 0 from the stack*/ - - /*REMOVE_NATIVE_STACKINFO;*/ - i386_mov_imm_reg(cd,(s4)asm_remove_native_stackinfo,REG_ITMP3); - i386_call_reg(cd,REG_ITMP3); + M_AST_IMM(0, REG_SP, 0 * 4); + dseg_adddata(cd, cd->mcodeptr); + M_MOV(REG_SP, REG_ITMP3); + M_AADD_IMM(4 * 4, REG_ITMP3); + M_AST(REG_ITMP3, REG_SP, 1 * 4); + M_ALD(REG_ITMP3, REG_SP, (4 + parentargs_base) * 4); + M_AST(REG_ITMP3, REG_SP, 2 * 4); + M_AST(REG_ITMP2_XPC, REG_SP, 3 * 4); + M_MOV_IMM((ptrint) stacktrace_inline_classcastexception, REG_ITMP3); + M_CALL(REG_ITMP3); - i386_pop_reg(cd, REG_ITMP2_XPC); + M_ALD(REG_ITMP2_XPC, REG_SP, 3 * 4); + M_AADD_IMM(4 * 4, REG_SP); - i386_mov_imm_reg(cd, (s4) asm_handle_exception, REG_ITMP3); - i386_jmp_reg(cd, REG_ITMP3); + M_MOV_IMM((ptrint) asm_handle_exception, REG_ITMP3); + M_JMP(REG_ITMP3); } } - /* generate null pointer check stubs */ + /* generate NullPointerException stubs */ xcodeptr = NULL; for (bref = cd->xnullrefs; bref != NULL; bref = bref->next) { - if ((cd->exceptiontablelength == 0) && (xcodeptr != NULL)) { - gen_resolvebranch(cd->mcodebase + bref->branchpos, - bref->branchpos, - xcodeptr - cd->mcodebase - (5 + 5 + 2)); - continue; - } - gen_resolvebranch(cd->mcodebase + bref->branchpos, bref->branchpos, cd->mcodeptr - cd->mcodebase); - MCODECHECK(100); + MCODECHECK(512); - i386_mov_imm_reg(cd, 0, REG_ITMP2_XPC); /* 5 bytes */ + M_MOV_IMM(0, REG_ITMP2_XPC); dseg_adddata(cd, cd->mcodeptr); - i386_mov_imm_reg(cd, bref->branchpos - 6, REG_ITMP1); /* 5 bytes */ - i386_alu_reg_reg(cd, ALU_ADD, REG_ITMP1, REG_ITMP2_XPC); /* 2 bytes */ + M_AADD_IMM32(bref->branchpos - 6, REG_ITMP2_XPC); if (xcodeptr != NULL) { - i386_jmp_imm(cd, (xcodeptr - cd->mcodeptr) - 5); + M_JMP_IMM((xcodeptr - cd->mcodeptr) - 5); } else { xcodeptr = cd->mcodeptr; - i386_push_reg(cd, REG_ITMP2_XPC); - - /*PREPARE_NATIVE_STACKINFO;*/ - i386_push_imm(cd,0); /* the pushed XPC is directly below the java frame*/ - i386_push_imm(cd,0); - i386_mov_imm_reg(cd,(s4)asm_prepare_native_stackinfo,REG_ITMP3); - i386_call_reg(cd,REG_ITMP3); - + M_ASUB_IMM(4 * 4, REG_SP); + M_AST_IMM(0, REG_SP, 0 * 4); + dseg_adddata(cd, cd->mcodeptr); + M_MOV(REG_SP, REG_ITMP3); + M_AADD_IMM(4 * 4, REG_ITMP3); + M_AST(REG_ITMP3, REG_SP, 1 * 4); + M_ALD(REG_ITMP3, REG_SP, (4 + parentargs_base) * 4); + M_AST(REG_ITMP3, REG_SP, 2 * 4); + M_AST(REG_ITMP2_XPC, REG_SP, 3 * 4); + + M_MOV_IMM((ptrint) stacktrace_inline_nullpointerexception, + REG_ITMP3); + M_CALL(REG_ITMP3); + + M_ALD(REG_ITMP2_XPC, REG_SP, 3 * 4); + M_AADD_IMM(4 * 4, REG_SP); + + M_MOV_IMM((ptrint) asm_handle_exception, REG_ITMP3); + M_JMP(REG_ITMP3); + } + } -#if 0 - /* create native call block*/ - i386_alu_imm_reg(cd, ALU_SUB, 3*4, REG_SP); /* build stack frame (4 * 4 bytes) */ + /* generate exception check stubs */ + xcodeptr = NULL; + + for (bref = cd->xexceptionrefs; bref != NULL; bref = bref->next) { + gen_resolvebranch(cd->mcodebase + bref->branchpos, + bref->branchpos, + cd->mcodeptr - cd->mcodebase); - i386_mov_imm_reg(cd, (s4) codegen_stubcalled,REG_ITMP1); - i386_call_reg(cd, REG_ITMP1); /*call codegen_stubcalled*/ + MCODECHECK(512); - i386_mov_imm_reg(cd, (s4) builtin_asm_get_stackframeinfo,REG_ITMP1); - i386_call_reg(cd, REG_ITMP1); /*call builtin_asm_get_stackframeinfo*/ - i386_mov_imm_membase(cd, 0,REG_SP, 2*4); /* builtin */ - i386_mov_reg_membase(cd, REG_RESULT,REG_SP,1*4); /* save thread pointer to native call stack*/ - i386_mov_membase_reg(cd, REG_RESULT,0,REG_ITMP2); /* get old value of thread specific native call stack */ - i386_mov_reg_membase(cd, REG_ITMP2,REG_SP,0*4); /* store value on stack */ - i386_mov_reg_membase(cd, REG_SP,REG_RESULT,0); /* store pointer to new stack frame information */ -#endif + M_MOV_IMM(0, REG_ITMP2_XPC); + dseg_adddata(cd, cd->mcodeptr); + M_AADD_IMM32(bref->branchpos - 6, REG_ITMP2_XPC); - i386_mov_imm_reg(cd, (u4) new_nullpointerexception, REG_ITMP1); - i386_call_reg(cd, REG_ITMP1); /* return value is REG_ITMP1_XPTR */ + if (xcodeptr != NULL) { + M_JMP_IMM((xcodeptr - cd->mcodeptr) - 5); + + } else { + xcodeptr = cd->mcodeptr; - /*REMOVE_NATIVE_STACKINFO;*/ - i386_mov_imm_reg(cd,(s4)asm_remove_native_stackinfo,REG_ITMP3); - i386_call_reg(cd,REG_ITMP3); + M_ASUB_IMM(4 * 4, REG_SP); + M_AST_IMM(0, REG_SP, 0 * 4); + dseg_adddata(cd, cd->mcodeptr); + M_MOV(REG_SP, REG_ITMP3); + M_AADD_IMM(4 * 4, REG_ITMP3); + M_AST(REG_ITMP3, REG_SP, 1 * 4); + M_ALD(REG_ITMP3, REG_SP, (4 + parentargs_base) * 4); + M_AST(REG_ITMP3, REG_SP, 2 * 4); + M_AST(REG_ITMP2_XPC, REG_SP, 3 * 4); -#if 0 - /* restore native call stack */ - i386_mov_membase_reg(cd, REG_SP,0,REG_ITMP2); - i386_mov_membase_reg(cd, REG_SP,4,REG_ITMP3); - i386_mov_reg_membase(cd, REG_ITMP2,REG_ITMP3,0); - i386_alu_imm_reg(cd, ALU_ADD,3*4,REG_SP); -#endif + M_MOV_IMM((ptrint) stacktrace_inline_fillInStackTrace, REG_ITMP3); + M_CALL(REG_ITMP3); - i386_pop_reg(cd, REG_ITMP2_XPC); + M_ALD(REG_ITMP2_XPC, REG_SP, 3 * 4); + M_AADD_IMM(4 * 4, REG_SP); - i386_mov_imm_reg(cd, (s4) asm_handle_exception, REG_ITMP3); - i386_jmp_reg(cd, REG_ITMP3); + M_MOV_IMM((ptrint) asm_handle_exception, REG_ITMP3); + M_JMP(REG_ITMP3); } } - /* generate put/getstatic stub call code */ + /* generate code patching stub call code */ { patchref *pref; @@ -5403,7 +5399,7 @@ java stack at this point*/ for (pref = cd->patchrefs; pref != NULL; pref = pref->next) { /* check code segment size */ - MCODECHECK(64); + MCODECHECK(512); /* Get machine code which is patched back in later. A */ /* `call rel32' is 5 bytes long. */ @@ -5411,15 +5407,6 @@ java stack at this point*/ xcodeptr = cd->mcodebase + pref->branchpos; mcode = *((u8 *) xcodeptr); -#if defined(USE_THREADS) && defined(NATIVE_THREADS) - /* create a virtual java_objectheader */ - - *((ptrint *) (cd->mcodeptr + 0)) = 0; /* vftbl */ - *((ptrint *) (cd->mcodeptr + 4)) = (ptrint) get_dummyLR(); /* monitorPtr */ - - cd->mcodeptr += 2 * 4; -#endif - /* patch in `call rel32' to call the following code */ tmpcd->mcodeptr = xcodeptr; /* set dummy mcode pointer */ @@ -5428,27 +5415,35 @@ java stack at this point*/ /* move pointer to java_objectheader onto stack */ #if defined(USE_THREADS) && defined(NATIVE_THREADS) - i386_call_imm(cd, 0); - i386_alu_imm_membase(cd, ALU_SUB, 5 + 2 * 4, REG_SP, 0); + (void) dseg_addaddress(cd, get_dummyLR()); /* monitorPtr */ + off = dseg_addaddress(cd, NULL); /* vftbl */ + + M_MOV_IMM(0, REG_ITMP3); + dseg_adddata(cd, cd->mcodeptr); + M_AADD_IMM(off, REG_ITMP3); + M_PUSH(REG_ITMP3); #else - i386_push_imm(cd, 0); + M_PUSH_IMM(0); #endif /* move machine code bytes and classinfo pointer into registers */ - i386_push_imm(cd, (ptrint) (mcode >> 32)); - i386_push_imm(cd, (ptrint) mcode); - i386_push_imm(cd, (ptrint) pref->ref); - - i386_push_imm(cd, (ptrint) pref->patcher); + M_PUSH_IMM((ptrint) (mcode >> 32)); + M_PUSH_IMM((ptrint) mcode); + M_PUSH_IMM((ptrint) pref->ref); + M_PUSH_IMM((ptrint) pref->patcher); - i386_mov_imm_reg(cd, (ptrint) asm_wrapper_patcher, REG_ITMP3); - i386_jmp_reg(cd, REG_ITMP3); + M_MOV_IMM((ptrint) asm_wrapper_patcher, REG_ITMP3); + M_JMP(REG_ITMP3); } } } codegen_finish(m, cd, (ptrint) (cd->mcodeptr - cd->mcodebase)); + + /* everything's ok */ + + return true; } @@ -5460,7 +5455,7 @@ java stack at this point*/ #define COMPILERSTUB_SIZE 12 -functionptr createcompilerstub(methodinfo *m) +u1 *createcompilerstub(methodinfo *m) { u1 *s; /* memory to hold the stub */ codegendata *cd; @@ -5481,7 +5476,7 @@ functionptr createcompilerstub(methodinfo *m) i386_mov_imm_reg(cd, (ptrint) asm_call_jit_compiler, REG_ITMP3); i386_jmp_reg(cd, REG_ITMP3); -#if defined(STATISTICS) +#if defined(ENABLE_STATISTICS) if (opt_stat) count_cstub_len += COMPILERSTUB_SIZE; #endif @@ -5490,7 +5485,7 @@ functionptr createcompilerstub(methodinfo *m) dump_release(dumpsize); - return (functionptr) (ptrint) s; + return s; } @@ -5506,57 +5501,34 @@ functionptr createcompilerstub(methodinfo *m) static java_objectheader **(*callgetexceptionptrptr)() = builtin_get_exceptionptrptr; #endif -functionptr createnativestub(functionptr f, methodinfo *m, codegendata *cd, - registerdata *rd) +u1 *createnativestub(functionptr f, methodinfo *m, codegendata *cd, + registerdata *rd, methoddesc *nmd) { methoddesc *md; - methoddesc *nmd; s4 nativeparams; + s4 stackframesize; s4 i, j; /* count variables */ s4 t; - s4 s1, s2, off; - s4 stackframesize; - s4 stackframeoffset; + s4 s1, s2, disp; /* set some variables */ - nativeparams = (m->flags & ACC_STATIC) ? 2 : 1; - - /* initial 4 bytes is space for jni env, + 4 byte thread pointer + 4 byte */ - /* previous pointer + method info + 4 offset native */ - /* already handled by nmd->memuse */ - - stackframesize = /* 4 + */ 16; - stackframeoffset = 4; - - - /* create new method descriptor with additional native parameters */ - md = m->parseddesc; - - nmd = (methoddesc *) DMNEW(u1, sizeof(methoddesc) - sizeof(typedesc) + - md->paramcount * sizeof(typedesc) + - nativeparams * sizeof(typedesc)); - - nmd->paramcount = md->paramcount + nativeparams; - - nmd->params = DMNEW(paramdesc, nmd->paramcount); - - nmd->paramtypes[0].type = TYPE_ADR; /* add environment pointer */ - - if (m->flags & ACC_STATIC) - nmd->paramtypes[1].type = TYPE_ADR; /* add class pointer */ - - MCOPY(nmd->paramtypes + nativeparams, md->paramtypes, typedesc, - md->paramcount); + nativeparams = (m->flags & ACC_STATIC) ? 2 : 1; - md_param_alloc(nmd); + /* calculate stackframe size */ + stackframesize = + sizeof(stackframeinfo) / SIZEOF_VOID_P + + sizeof(localref_table) / SIZEOF_VOID_P + + 1 + /* function pointer */ + 4 * 4 + /* 4 arguments (start_native_call) */ + nmd->memuse; /* create method header */ (void) dseg_addaddress(cd, m); /* MethodPointer */ - (void) dseg_adds4(cd, 0 * 8); /* FrameSize */ + (void) dseg_adds4(cd, stackframesize * 4); /* FrameSize */ (void) dseg_adds4(cd, 0); /* IsSync */ (void) dseg_adds4(cd, 0); /* IsLeaf */ (void) dseg_adds4(cd, 0); /* IntSave */ @@ -5564,96 +5536,102 @@ functionptr createnativestub(functionptr f, methodinfo *m, codegendata *cd, (void) dseg_addlinenumbertablesize(cd); (void) dseg_adds4(cd, 0); /* ExTableSize */ - /* initialize mcode variables */ cd->mcodeptr = (u1 *) cd->mcodebase; cd->mcodeend = (s4 *) (cd->mcodebase + cd->mcodesize); + /* generate profiling code */ - /* if function is static, check for initialized */ - - if (m->flags & ACC_STATIC) { - /* already handled by nmd->memuse */ -/* stackframesize += 4; */ - stackframeoffset += 4; - - /* if class isn't yet initialized, do it */ + if (opt_prof) { + M_MOV_IMM((ptrint) m, REG_ITMP1); + M_IADD_IMM_MEMBASE(1, REG_ITMP1, OFFSET(methodinfo, executioncount)); + } - if (!m->class->initialized) { - codegen_addpatchref(cd, cd->mcodeptr, PATCHER_clinit, m->class); + /* calculate stackframe size for native function */ - if (showdisassemble) { - M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; - } - } - } + M_ASUB_IMM(stackframesize * 4, REG_SP); if (runverbose) { s4 p, t; - s4 stack_off = 0; - i386_alu_imm_reg(cd, ALU_SUB, TRACE_ARGS_NUM * 8 + 4, REG_SP); + disp = stackframesize * 4; + + M_ASUB_IMM(TRACE_ARGS_NUM * 8 + 4, REG_SP); for (p = 0; p < md->paramcount && p < TRACE_ARGS_NUM; p++) { t = md->paramtypes[p].type; if (IS_INT_LNG_TYPE(t)) { if (IS_2_WORD_TYPE(t)) { - i386_mov_membase_reg(cd, REG_SP, - 4 + TRACE_ARGS_NUM * 8 + 4 + stack_off, REG_ITMP1); - i386_mov_membase_reg(cd, REG_SP, - 4 + TRACE_ARGS_NUM * 8 + 4 + stack_off + 4, REG_ITMP2); - i386_mov_reg_membase(cd, REG_ITMP1, REG_SP, p * 8); - i386_mov_reg_membase(cd, REG_ITMP2, REG_SP, p * 8 + 4); + M_ILD(REG_ITMP1, REG_SP, + 4 + TRACE_ARGS_NUM * 8 + 4 + disp); + M_ILD(REG_ITMP2, REG_SP, + 4 + TRACE_ARGS_NUM * 8 + 4 + disp + 4); + M_IST(REG_ITMP1, REG_SP, p * 8); + M_IST(REG_ITMP2, REG_SP, p * 8 + 4); } else if (t == TYPE_ADR) { - i386_mov_membase_reg(cd, REG_SP, - 4 + TRACE_ARGS_NUM * 8 + 4 + stack_off, REG_ITMP1); - i386_alu_reg_reg(cd, ALU_XOR, REG_ITMP2, REG_ITMP2); - i386_mov_reg_membase(cd, REG_ITMP1, REG_SP, p * 8); - i386_mov_reg_membase(cd, REG_ITMP2, REG_SP, p * 8 + 4); + M_ALD(REG_ITMP1, REG_SP, + 4 + TRACE_ARGS_NUM * 8 + 4 + disp); + M_CLR(REG_ITMP2); + M_AST(REG_ITMP1, REG_SP, p * 8); + M_AST(REG_ITMP2, REG_SP, p * 8 + 4); } else { - i386_mov_membase_reg(cd, REG_SP, - 4 + TRACE_ARGS_NUM * 8 + 4 + stack_off, EAX); + M_ILD(EAX, REG_SP, 4 + TRACE_ARGS_NUM * 8 + 4 + disp); i386_cltd(cd); - i386_mov_reg_membase(cd, EAX, REG_SP, p * 8); - i386_mov_reg_membase(cd, EDX, REG_SP, p * 8 + 4); + M_IST(EAX, REG_SP, p * 8); + M_IST(EDX, REG_SP, p * 8 + 4); } } else { if (!IS_2_WORD_TYPE(t)) { i386_flds_membase(cd, REG_SP, - 4 + TRACE_ARGS_NUM * 8 + 4 + stack_off); + 4 + TRACE_ARGS_NUM * 8 + 4 + disp); i386_fstps_membase(cd, REG_SP, p * 8); i386_alu_reg_reg(cd, ALU_XOR, REG_ITMP2, REG_ITMP2); - i386_mov_reg_membase(cd, REG_ITMP2, REG_SP, p * 8 + 4); + M_IST(REG_ITMP2, REG_SP, p * 8 + 4); } else { i386_fldl_membase(cd, REG_SP, - 4 + TRACE_ARGS_NUM * 8 + 4 + stack_off); + 4 + TRACE_ARGS_NUM * 8 + 4 + disp); i386_fstpl_membase(cd, REG_SP, p * 8); } } - stack_off += (IS_2_WORD_TYPE(t)) ? 8 : 4; + disp += (IS_2_WORD_TYPE(t)) ? 8 : 4; } - i386_alu_reg_reg(cd, ALU_XOR, REG_ITMP1, REG_ITMP1); + M_CLR(REG_ITMP1); for (p = md->paramcount; p < TRACE_ARGS_NUM; p++) { - i386_mov_reg_membase(cd, REG_ITMP1, REG_SP, p * 8); - i386_mov_reg_membase(cd, REG_ITMP1, REG_SP, p * 8 + 4); + M_IST(REG_ITMP1, REG_SP, p * 8); + M_IST(REG_ITMP1, REG_SP, p * 8 + 4); } - i386_mov_imm_membase(cd, (ptrint) m, REG_SP, TRACE_ARGS_NUM * 8); + M_AST_IMM((ptrint) m, REG_SP, TRACE_ARGS_NUM * 8); - i386_mov_imm_reg(cd, (ptrint) builtin_trace_args, REG_ITMP1); - i386_call_reg(cd, REG_ITMP1); + M_MOV_IMM((ptrint) builtin_trace_args, REG_ITMP1); + M_CALL(REG_ITMP1); - i386_alu_imm_reg(cd, ALU_ADD, TRACE_ARGS_NUM * 8 + 4, REG_SP); + M_AADD_IMM(TRACE_ARGS_NUM * 8 + 4, REG_SP); } + /* get function address (this must happen before the stackframeinfo) */ + +#if !defined(ENABLE_STATICVM) + if (f == NULL) { + codegen_addpatchref(cd, cd->mcodeptr, PATCHER_resolve_native, m, 0); + + if (opt_showdisassemble) { + M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; + } + } +#endif + + M_AST_IMM((ptrint) f, REG_SP, 4 * 4); + /* Mark the whole fpu stack as free for native functions (only for saved */ /* register count == 0). */ + i386_ffree_reg(cd, 0); i386_ffree_reg(cd, 1); i386_ffree_reg(cd, 2); @@ -5663,28 +5641,25 @@ functionptr createnativestub(functionptr f, methodinfo *m, codegendata *cd, i386_ffree_reg(cd, 6); i386_ffree_reg(cd, 7); - /* calculate stackframe size for native function */ + /* prepare data structures for native function call */ - stackframesize += nmd->memuse * 4; + M_MOV(REG_SP, REG_ITMP1); + M_AADD_IMM(stackframesize * 4, REG_ITMP1); - i386_alu_imm_reg(cd, ALU_SUB, stackframesize, REG_SP); + M_AST(REG_ITMP1, REG_SP, 0 * 4); + M_IST_IMM(0, REG_SP, 1 * 4); + dseg_adddata(cd, cd->mcodeptr); - /* CREATE DYNAMIC STACK INFO -- BEGIN*/ + M_MOV(REG_SP, REG_ITMP2); + M_AADD_IMM(stackframesize * 4 + SIZEOF_VOID_P, REG_ITMP2); - i386_mov_imm_membase(cd,0,REG_SP,stackframesize-4); - i386_mov_imm_membase(cd, (ptrint) m, REG_SP,stackframesize-8); - i386_mov_imm_reg(cd, (ptrint) builtin_asm_get_stackframeinfo, REG_ITMP1); - i386_call_reg(cd, REG_ITMP1); - /*save thread specific pointer*/ - i386_mov_reg_membase(cd, REG_RESULT,REG_SP,stackframesize-12); - i386_mov_membase_reg(cd, REG_RESULT,0,REG_ITMP2); - /*save previous value of memory adress pointed to by thread specific pointer*/ - i386_mov_reg_membase(cd, REG_ITMP2,REG_SP,stackframesize-16); - i386_mov_reg_reg(cd, REG_SP,REG_ITMP2); - i386_alu_imm_reg(cd, ALU_ADD,stackframesize-16,REG_ITMP2); - i386_mov_reg_membase(cd, REG_ITMP2,REG_RESULT,0); + M_AST(REG_ITMP2, REG_SP, 2 * 4); + M_ALD(REG_ITMP3, REG_SP, stackframesize * 4); + M_AST(REG_ITMP3, REG_SP, 3 * 4); + M_MOV_IMM((ptrint) codegen_start_native_call, REG_ITMP1); + M_CALL(REG_ITMP1); - /* CREATE DYNAMIC STACK INFO -- END*/ + M_ALD(REG_ITMP3, REG_SP, 4 * 4); /* copy arguments into new stackframe */ @@ -5694,14 +5669,14 @@ functionptr createnativestub(functionptr f, methodinfo *m, codegendata *cd, if (!md->params[i].inmemory) { /* no integer argument registers */ } else { /* float/double in memory can be copied like int/longs */ - s1 = md->params[i].regoff * 4 + stackframesize + (1 * 4); + s1 = (md->params[i].regoff + stackframesize + 1) * 4; s2 = nmd->params[j].regoff * 4; - i386_mov_membase_reg(cd, REG_SP, s1, REG_ITMP1); - i386_mov_reg_membase(cd, REG_ITMP1, REG_SP, s2); + M_ILD(REG_ITMP1, REG_SP, s1); + M_IST(REG_ITMP1, REG_SP, s2); if (IS_2_WORD_TYPE(t)) { - i386_mov_membase_reg(cd, REG_SP, s1 + 4, REG_ITMP1); - i386_mov_reg_membase(cd, REG_ITMP1, REG_SP, s2 + 4); + M_ILD(REG_ITMP1, REG_SP, s1 + 4); + M_IST(REG_ITMP1, REG_SP, s2 + 4); } } } @@ -5709,81 +5684,101 @@ functionptr createnativestub(functionptr f, methodinfo *m, codegendata *cd, /* if function is static, put class into second argument */ if (m->flags & ACC_STATIC) - i386_mov_imm_membase(cd, (ptrint) m->class, REG_SP, 4); + M_AST_IMM((ptrint) m->class, REG_SP, 1 * 4); /* put env into first argument */ - i386_mov_imm_membase(cd, (ptrint) &env, REG_SP, 0); + M_AST_IMM((ptrint) &env, REG_SP, 0 * 4); /* call the native function */ -#if !defined(STATIC_CLASSPATH) - if (f == NULL) - codegen_addpatchref(cd, cd->mcodeptr, PATCHER_resolve_native, m); - - if (showdisassemble) { - M_NOP; M_NOP; M_NOP; M_NOP; M_NOP; - } -#endif + M_CALL(REG_ITMP3); - i386_mov_imm_reg(cd, (ptrint) f, REG_ITMP1); - i386_call_reg(cd, REG_ITMP1); + /* save return value */ + if (IS_INT_LNG_TYPE(md->returntype.type)) { + if (IS_2_WORD_TYPE(md->returntype.type)) + M_IST(REG_RESULT2, REG_SP, 2 * 4); + M_IST(REG_RESULT, REG_SP, 1 * 4); + + } else { + if (IS_2_WORD_TYPE(md->returntype.type)) + i386_fstl_membase(cd, REG_SP, 1 * 4); + else + i386_fsts_membase(cd, REG_SP, 1 * 4); + } - /* REMOVE DYNAMIC STACK INFO -BEGIN */ - i386_push_reg(cd, REG_RESULT2); - i386_mov_membase_reg(cd, REG_SP,stackframesize-12,REG_ITMP2); /*old value*/ - i386_mov_membase_reg(cd, REG_SP,stackframesize-8,REG_RESULT2); /*pointer*/ - i386_mov_reg_membase(cd, REG_ITMP2,REG_RESULT2,0); - i386_pop_reg(cd, REG_RESULT2); - /* REMOVE DYNAMIC STACK INFO -END */ + /* remove data structures for native function call */ - i386_alu_imm_reg(cd, ALU_ADD, stackframesize, REG_SP); + M_MOV(REG_SP, REG_ITMP1); + M_AADD_IMM(stackframesize * 4, REG_ITMP1); + M_AST(REG_ITMP1, REG_SP, 0 * 4); + M_MOV_IMM((ptrint) codegen_finish_native_call, REG_ITMP1); + M_CALL(REG_ITMP1); if (runverbose) { - i386_alu_imm_reg(cd, ALU_SUB, 4 + 8 + 8 + 4, REG_SP); - - i386_mov_imm_membase(cd, (ptrint) m, REG_SP, 0); - - i386_mov_reg_membase(cd, REG_RESULT, REG_SP, 4); - i386_mov_reg_membase(cd, REG_RESULT2, REG_SP, 4 + 4); - - i386_fstl_membase(cd, REG_SP, 4 + 8); - i386_fsts_membase(cd, REG_SP, 4 + 8 + 8); + /* restore return value */ - i386_mov_imm_reg(cd, (ptrint) builtin_displaymethodstop, REG_ITMP1); - i386_call_reg(cd, REG_ITMP1); - - i386_mov_membase_reg(cd, REG_SP, 4, REG_RESULT); - i386_mov_membase_reg(cd, REG_SP, 4 + 4, REG_RESULT2); - - i386_alu_imm_reg(cd, ALU_ADD, 4 + 8 + 8 + 4, REG_SP); - } + if (IS_INT_LNG_TYPE(md->returntype.type)) { + if (IS_2_WORD_TYPE(md->returntype.type)) + M_ILD(REG_RESULT2, REG_SP, 2 * 4); + M_ILD(REG_RESULT, REG_SP, 1 * 4); + + } else { + if (IS_2_WORD_TYPE(md->returntype.type)) + i386_fldl_membase(cd, REG_SP, 1 * 4); + else + i386_flds_membase(cd, REG_SP, 1 * 4); + } + + M_ASUB_IMM(4 + 8 + 8 + 4, REG_SP); + + M_AST_IMM((ptrint) m, REG_SP, 0); + M_IST(REG_RESULT, REG_SP, 4); + M_IST(REG_RESULT2, REG_SP, 4 + 4); + + i386_fstl_membase(cd, REG_SP, 4 + 8); + i386_fsts_membase(cd, REG_SP, 4 + 8 + 8); + + M_MOV_IMM((ptrint) builtin_displaymethodstop, REG_ITMP1); + M_CALL(REG_ITMP1); + + M_AADD_IMM(4 + 8 + 8 + 4, REG_SP); + } /* check for exception */ #if defined(USE_THREADS) && defined(NATIVE_THREADS) - /* we can't use REG_ITMP3 == REG_RESULT2 */ - - i386_push_reg(cd, REG_RESULT); - i386_push_reg(cd, REG_RESULT2); /* i386_call_mem(cd, (ptrint) builtin_get_exceptionptrptr); */ i386_call_mem(cd, (ptrint) &callgetexceptionptrptr); - i386_mov_membase_reg(cd, REG_RESULT, 0, REG_ITMP2); - i386_test_reg_reg(cd, REG_ITMP2, REG_ITMP2); - i386_pop_reg(cd, REG_RESULT2); - i386_pop_reg(cd, REG_RESULT); #else - i386_mov_imm_reg(cd, (ptrint) &_exceptionptr, REG_ITMP2); - i386_mov_membase_reg(cd, REG_ITMP2, 0, REG_ITMP2); - i386_test_reg_reg(cd, REG_ITMP2, REG_ITMP2); + M_MOV_IMM((ptrint) &_exceptionptr, REG_RESULT); #endif - i386_jcc(cd, I386_CC_NE, 1); + /* we can't use REG_ITMP3 == REG_RESULT2 */ + M_ALD(REG_ITMP2, REG_RESULT, 0); + + /* restore return value */ + + if (IS_INT_LNG_TYPE(md->returntype.type)) { + if (IS_2_WORD_TYPE(md->returntype.type)) + M_ILD(REG_RESULT2, REG_SP, 2 * 4); + M_ILD(REG_RESULT, REG_SP, 1 * 4); + + } else { + if (IS_2_WORD_TYPE(md->returntype.type)) + i386_fldl_membase(cd, REG_SP, 1 * 4); + else + i386_flds_membase(cd, REG_SP, 1 * 4); + } + + M_AADD_IMM(stackframesize * 4, REG_SP); - i386_ret(cd); + M_TEST(REG_ITMP2); + M_BNE(1); + M_RET; /* handle exception */ @@ -5794,15 +5789,15 @@ functionptr createnativestub(functionptr f, methodinfo *m, codegendata *cd, i386_mov_imm_membase(cd, 0, REG_RESULT, 0); i386_pop_reg(cd, REG_ITMP1_XPTR); #else - i386_mov_reg_reg(cd, REG_ITMP2, REG_ITMP1_XPTR); - i386_mov_imm_reg(cd, (ptrint) &_exceptionptr, REG_ITMP2); + M_MOV(REG_ITMP2, REG_ITMP1_XPTR); + M_MOV_IMM((ptrint) &_exceptionptr, REG_ITMP2); i386_mov_imm_membase(cd, 0, REG_ITMP2, 0); #endif - i386_mov_membase_reg(cd, REG_SP, 0, REG_ITMP2_XPC); - i386_alu_imm_reg(cd, ALU_SUB, 2, REG_ITMP2_XPC); + M_ALD(REG_ITMP2_XPC, REG_SP, 0); + M_ASUB_IMM(2, REG_ITMP2_XPC); - i386_mov_imm_reg(cd, (ptrint) asm_handle_nat_exception, REG_ITMP3); - i386_jmp_reg(cd, REG_ITMP3); + M_MOV_IMM((ptrint) asm_handle_nat_exception, REG_ITMP3); + M_JMP(REG_ITMP3); /* process patcher calls **************************************************/ @@ -5833,11 +5828,11 @@ functionptr createnativestub(functionptr f, methodinfo *m, codegendata *cd, /* create a virtual java_objectheader */ (void) dseg_addaddress(cd, get_dummyLR()); /* monitorPtr */ - off = dseg_addaddress(cd, NULL); /* vftbl */ + disp = dseg_addaddress(cd, NULL); /* vftbl */ - i386_mov_imm_reg(cd, 0, REG_ITMP3); + M_MOV_IMM(0, REG_ITMP3); dseg_adddata(cd, cd->mcodeptr); - M_AADD_IMM(off, REG_ITMP3); + M_AADD_IMM(disp, REG_ITMP3); M_PUSH(REG_ITMP3); #else M_PUSH_IMM(0); @@ -5845,14 +5840,13 @@ functionptr createnativestub(functionptr f, methodinfo *m, codegendata *cd, /* move machine code bytes and classinfo pointer onto stack */ - i386_push_imm(cd, (ptrint) (mcode >> 32)); - i386_push_imm(cd, (ptrint) mcode); - i386_push_imm(cd, (ptrint) pref->ref); - - i386_push_imm(cd, (ptrint) pref->patcher); + M_PUSH_IMM((ptrint) (mcode >> 32)); + M_PUSH_IMM((ptrint) mcode); + M_PUSH_IMM((ptrint) pref->ref); + M_PUSH_IMM((ptrint) pref->patcher); - i386_mov_imm_reg(cd, (ptrint) asm_wrapper_patcher, REG_ITMP3); - i386_jmp_reg(cd, REG_ITMP3); + M_MOV_IMM((ptrint) asm_wrapper_patcher, REG_ITMP3); + M_JMP(REG_ITMP3); } }