Changes: Joseph Wenninger
- $Id: asmpart.S 2947 2005-07-09 12:17:14Z twisti $
+ $Id: asmpart.S 2971 2005-07-10 15:33:54Z twisti $
*/
#define v0 %eax
+#define sp %esp
+
#define itmp1 %eax
#define itmp2 %ecx
#define itmp3 %edx
.globl asm_calljavafunction2double
.globl asm_call_jit_compiler
- .globl asm_handle_builtin_exception
.globl asm_handle_nat_exception
.globl asm_handle_exception
.globl asm_wrapper_patcher
- .globl asm_builtin_arraycheckcast
- .globl asm_builtin_aastore
-
- .globl asm_builtin_ldiv
- .globl asm_builtin_lrem
-
.globl asm_builtin_f2i
.globl asm_builtin_f2l
.globl asm_builtin_d2i
.globl asm_perform_threadswitch
.globl asm_initialize_thread_stack
.globl asm_switchstackandcall
- .globl asm_getcallingmethod
.globl asm_criticalsections
.globl asm_getclassvalues_atomic
- .globl asm_throw_and_handle_exception
- .globl asm_throw_and_handle_hardware_arithmetic_exception
-
- .globl asm_prepare_native_stackinfo
- .globl asm_remove_native_stackinfo
-
/********************* function asm_calljavafunction ***************************
* *
#if defined(USE_THREADS) && defined(NATIVE_THREADS)
call builtin_asm_get_exceptionptrptr
- mov %eax,%ecx
+ mov v0,itmp2
#else
- lea _exceptionptr,%ecx
+ lea _exceptionptr,itmp2
#endif
- mov (%ecx),%eax /* get the exception pointer */
- movl $0,(%ecx) /* clear the exception pointer */
-
- pop %ecx /* delete return address */
- sub $2,%ecx /* faulting address is return adress - 2 */
-
-L_refillinStacktrace: /*a compilation error should cause a stacktrace
- which starts at the method call, which caused
- the compilation of the new function. Until this
- point the trace is invalid anyways, since it is
- not complete. Compared to other runtimes it will
- not be correct either, since we report eg class
- not found errors too early, since we always
- compile methods completely. The native info
- should be moved around the jit call to get
- a more compliant trace for the "exception in
- initializer" case*/
- push %ecx /* store fault adress */
- push %eax /* temporarily save exception pointer*/
- push $0 /* internal function */
- call builtin_asm_get_stackframeinfo
- push %eax /* save location of thread specific stack info head pointer */
- mov (%eax),%ecx /* save old value of pointer*/
- push %ecx
- mov %esp,(%eax) /*store pointer to this structure*/
- mov 12(%esp),%eax /* get the exception pointer again*/
- movl $0,12(%esp) /*java stack begins just above structure*/
- push $0 /*used for the jni_callblock structure*/
- push %eax /*save eax for later */
- /* get fillInStackTrace method*/
- push utf_void__java_lang_Throwable
- push utf_fillInStackTrace
- mov offobjvftbl(%eax),%ecx
- mov offclass(%ecx),%eax
- push %eax
- call class_resolvemethod
- add $12,%esp
- push $0
- push $4 /*TYPE_ADR*/
- push %esp
- push $sizejniblock
- push $1
- push %eax
- call asm_calljavafunction2
- add $24,%esp
-
- /*remove native stack info */
- mov 8(%esp),%ecx
- mov 12(%esp),%eax
- mov %ecx,(%eax)
- mov (%esp),%eax
- add $24,%esp
- pop %ecx
-
+ mov (itmp2),xptr /* get the exception pointer */
+ movl $0,(itmp2) /* clear the exception pointer */
+
+ sub $(5*4+sizestackframeinfo),sp
+ mov xptr,4*4(sp) /* save exception pointer */
+
+ mov sp,itmp1 /* create stackframe info */
+ add $(5*4),itmp1
+ mov itmp1,0*4(sp) /* stackframeinfo pointer */
+ movl $0,1*4(sp) /* if pv is NULL, use findmethod */
+ mov sp,itmp2
+ add $(6*4+sizestackframeinfo),itmp2
+ mov itmp2,2*4(sp)
+ mov (5*4+sizestackframeinfo)(sp),itmp3
+ mov itmp3,3*4(sp)
+ call stacktrace_create_inline_stackframeinfo
+
+ mov 4*4(sp),itmp1 /* fill in stacktrace */
+ mov itmp1,0*4(sp)
+ call stacktrace_call_fillInStackTrace
+ mov sp,itmp1 /* remove stackframe info */
+ add $(5*4),itmp1
+ mov itmp1,0*4(sp) /* stackframeinfo pointer */
+ call stacktrace_remove_stackframeinfo
+
+ mov 4*4(sp),xptr /* restore exception pointer */
+ add $(5*4+sizestackframeinfo),sp
+
+ pop xpc /* delete return address */
+ sub $2,xpc /* faulting address is return adress - 2 */
jmp asm_handle_exception
*******************************************************************************/
asm_wrapper_patcher:
- sub $(2*4),%esp /* create stack frame */
-
- mov itmp1,0*4(%esp) /* save itmp1 and itmp2 */
- mov itmp2,1*4(%esp) /* may be used by some instructions */
-
-#if 0
- /* 3*4 bytes */
- mov 3*4(%esp),itmp1 /* return adress into java code */
- mov %esp,itmp2 /* begin of java stack frame */
- add $(3*4),itmp2
- push itmp1
- push itmp2
- pushl $0 /* internal (invisible) method */
- call asm_prepare_native_stackinfo /* puts additional 2 *4 bytes of
- data onto the stack */
-#endif
-
- mov %esp,itmp1 /* pass stack pointer */
- add $(3*4),itmp1 /* also skip patcher function pointer */
- push itmp1
- mov 3*4(%esp),itmp1 /* get function pointer from stack */
+ sub $((2+4)*4+sizestackframeinfo),sp /* create stack frame */
+
+ mov itmp1,(0+4)*4(sp) /* save itmp1 and itmp2 */
+ mov itmp2,(1+4)*4(sp) /* may be used by some instructions */
+
+ mov sp,itmp1 /* create stackframe info */
+ add $((2+4)*4),itmp1
+ mov itmp1,0*4(sp) /* stackframeinfo pointer */
+ movl $0,1*4(sp) /* if pv is NULL, use findmethod */
+ mov sp,itmp2
+ add $((6+2+4)*4+sizestackframeinfo),itmp2
+ mov itmp2,2*4(sp)
+ mov ((5+2+4)*4+sizestackframeinfo)(sp),itmp3
+ mov itmp3,3*4(sp)
+ call stacktrace_create_inline_stackframeinfo
+
+ mov sp,itmp1 /* pass stack pointer */
+ add $((1+2+4)*4+sizestackframeinfo),itmp1 /* skip function pointer */
+ mov itmp1,0*4(sp)
+ mov (0+2+4)*4+sizestackframeinfo(sp),itmp1 /* get function pointer */
call *itmp1 /* call the patcher function */
- add $4,%esp
- mov v0,itmp3 /* save return value */
+ mov v0,1*4(sp) /* save return value */
-#if 0
- call asm_remove_native_stackinfo /* removes 4* 4 bytes and leaves ret
- into java machine code on stack */
- add $4,%esp /* ret address no longer needed, is still
- on stack a few bytes above */
-#endif
+ mov sp,itmp1 /* remove stackframe info */
+ add $((2+4)*4),itmp1
+ mov itmp1,0*4(sp) /* stackframeinfo pointer */
+ call stacktrace_remove_stackframeinfo
- mov 0*4(%esp),itmp1 /* restore itmp1 and itmp2 */
- mov 1*4(%esp),itmp2 /* may be used by some instructions */
+ mov (0+4)*4(sp),itmp1 /* restore itmp1 and itmp2 */
+ mov (1+4)*4(sp),itmp2 /* may be used by some instructions */
+ mov 1*4(sp),itmp3 /* restore return value */
- add $((5+2)*4),%esp /* remove stack frame, keep ra */
+ add $((5+2+4)*4+sizestackframeinfo),sp /* remove stack frame, keep ra */
test itmp3,itmp3 /* exception thrown? */
jz L_asm_wrapper_patcher_exception
ret /* call new patched code */
jmp asm_handle_exception
-/************************ function asm_builtin_ldiv ****************************
-* *
-* Does null check and calls ldiv or throws an exception *
-* *
-*******************************************************************************/
-
-asm_builtin_ldiv:
- mov 12(%esp),%eax
- or 16(%esp),%eax
- test %eax,%eax /* if (null) throw exception */
- je nb_ldiv
-
- jmp builtin_ldiv
-
-nb_ldiv:
- pop %ecx
- sub $2,%ecx
- jmp asm_throw_and_handle_hardware_arithmetic_exception
-#if 0
- push string_java_lang_ArithmeticException_message
- push string_java_lang_ArithmeticException
- call new_exception_message
- add $(2*4),%esp
-
- pop %ecx /* delete return address */
- sub $2,%ecx /* faulting address is return adress - 2 */
- jmp asm_handle_exception
-#endif
-
-/************************ function asm_builtin_lrem ****************************
-* *
-* Does null check and calls lrem or throws an exception *
-* *
-*******************************************************************************/
-
-asm_builtin_lrem:
- mov 12(%esp),%eax
- or 16(%esp),%eax
- test %eax,%eax /* if (null) throw exception */
- je nb_lrem
-
- jmp builtin_lrem
-
-nb_lrem:
- pop %ecx
- sub $2,%ecx
- jmp asm_throw_and_handle_hardware_arithmetic_exception
-#if 0
- push string_java_lang_ArithmeticException_message
- push string_java_lang_ArithmeticException
- call new_exception_message
- add $(2*4),%esp
-
- pop %ecx /* delete return address */
- sub $2,%ecx /* faulting address is return adress - 2 */
- jmp asm_handle_exception
-#endif
-
/************************ function asm_builtin_x2x *****************************
* *
* Wrapper functions for corner cases *
ret
-/* asm_builtin_arraycheckcast **************************************************
-
- Does the cast check and eventually throws an exception.
-
-*******************************************************************************/
-
-asm_builtin_arraycheckcast:
- sub $8,%esp /* build stack frame (2 * 4 bytes) */
-
- mov 12(%esp),%eax /* first param: 8 (frame) + 4 (return)*/
- mov %eax,(%esp) /* save object pointer */
-
- mov 16(%esp),%eax /* second param: 8 (frame) + 4 (return) + 4*/
- mov %eax,4(%esp)
-
- call builtin_arraycheckcast
-
- test %eax,%eax /* if (false) throw exception */
- je nb_carray_throw
-
- mov 12(%esp),%eax /* return object pointer */
- add $8,%esp
- ret
-
-nb_carray_throw:
- add $8,%esp
- mov string_java_lang_ClassCastException,%eax
- pop %ecx
- sub $2,%ecx
- jmp asm_throw_and_handle_exception
-#if 0
- push string_java_lang_ClassCastException
- call new_exception
- add $(1*4),%esp
-
- add $8,%esp
-
- pop %ecx /* delete return address */
- sub $2,%ecx /* faulting address is return adress - 2 */
- jmp asm_handle_exception
-#endif
-
-
-/******************* function asm_builtin_aastore ******************************
-* *
-* Does the cast check and eventually throws an exception *
-* void asm_builtin_aastore(java_objectarray *a, s4 index, java_objectheader *o)*
-*******************************************************************************/
-
-asm_builtin_aastore:
- sub $12,%esp /* build stack frame (3 * 4 bytes) */
-
- mov 16(%esp),%eax /* 12 (frame) + 4 (return) */
- test %eax,%eax /* if null pointer throw exception */
- je nb_aastore_null
-
- mov offarraysize(%eax),%edx /* load size */
- mov 20(%esp),%ecx /* index (12 + 4 + 4) */
- cmp %edx,%ecx /* do bound check */
- jae nb_aastore_bound /* if out of bounds throw exception */
-
- shl $2,%ecx /* index * 4 */
- add %eax,%ecx /* add index * 4 to arrayref */
-
- mov %ecx,8(%esp) /* save store position */
-
- mov 16(%esp),%eax /* 12 (frame) + 4 (return) */
- mov %eax,(%esp)
-
- mov 24(%esp),%eax /* object is second argument (12+4+4+4) */
- mov %eax,4(%esp)
-
- call builtin_canstore /* builtin_canstore(arrayref,object) */
-
- test %eax,%eax /* if (false) throw exception */
- je nb_aastore_store
-
- mov 24(%esp),%eax
- mov 8(%esp),%ecx
- mov %eax,offobjarrdata(%ecx) /* store objectptr in array */
-
- add $12,%esp
- ret
-
-nb_aastore_null:
- add $12,%esp
- mov string_java_lang_NullPointerException,%eax
- pop %ecx
- sub $2,%ecx
- jmp asm_throw_and_handle_exception
-
-#if 0
- push string_java_lang_NullPointerException
- call new_exception
- add $(1*4),%esp
-
- add $12,%esp
- pop %ecx /* delete return address */
- sub $2,%ecx /* faulting address is return adress - 2 */
- jmp asm_handle_exception
-#endif
-nb_aastore_bound:
- add $12,%esp
- mov %ecx,%eax /* itmp2 contains array index */
- pushl $0 /*directly below return adress*/
- pushl $0 /*internal (invisible) method*/
- call asm_prepare_native_stackinfo /* puts 2*4 bytes onto stack*/
-
- push %eax
- call new_arrayindexoutofboundsexception
- add $(1*4),%esp
-
- call asm_remove_native_stackinfo /*return adress is the first on stack again*/
-
- pop %ecx /* delete return address */
- sub $2,%ecx /* faulting address is return adress - 2 */
- jmp asm_handle_exception
-
-nb_aastore_store:
- add $12,%esp
-
- mov string_java_lang_ArrayStoreException,%eax
- pop %ecx
- sub $2,%ecx
- jmp asm_throw_and_handle_exception
-
-#if 0
- push string_java_lang_ArrayStoreException
- call new_exception
- add $(1*4),%esp
-
- add $12,%esp
- pop %ecx /* delete return address */
- sub $2,%ecx /* faulting address is return adress - 2 */
- jmp asm_handle_exception
-#endif
-
-
/******************* function asm_initialize_thread_stack **********************
* *
* initialized a thread stack *
ret
-asm_throw_and_handle_exception:
- push %ecx
- pushl $0 /* the pushed XPC is directly below the java frame*/
- pushl $0
- call asm_prepare_native_stackinfo /* be aware of the stack effect and calling convention explained below*/
-
- push %eax
- call new_exception
- add $4,%esp /*remove parameter*/
-
- call asm_remove_native_stackinfo /* be aware of the stack effect and calling convention explained below*/
-
- pop %ecx
- jmp asm_handle_exception
- ret /*should never be reached */
-
-asm_throw_and_handle_hardware_arithmetic_exception:
-
- push %ecx
- pushl $0 /* the pushed XPC is directly below the java frame*/
- pushl $0
- call asm_prepare_native_stackinfo /* be aware of the stack effect and calling convention explained below*/
-
- mov string_java_lang_ArithmeticException_message,%eax
- push %eax
- mov string_java_lang_ArithmeticException,%eax
- push %eax
-
- call new_exception_message
- add $8,%esp /*remove parameters */
-
- call asm_remove_native_stackinfo /* be aware of the stack effect and calling convention explained below*/
-
- pop %ecx
- jmp asm_handle_exception
- ret /*should never be reached */
-
-asm_builtin_new2:
-/*optimize a littlebit */
- mov %esp,%eax
-/*DEBUG*/
-/* push %eax
- call i386_native_stub_debug
- pop %eax */
-
- movl 4(%esp),%eax
- mov offclassinit(%eax),%ecx /* get initialized flag */
- test %ecx,%ecx
- jnz L_builtin_new_noinit
-
- mov 4(%esp),%eax /* class pointer, is kept during the asm_prepare... calls */
-
- /* 2 *4 bytes, the return adress is used directy */
- pushl $0 /* the structure is placed directly below the java stackframe*/
- pushl $0 /* builtin (invisible) method */
- call asm_prepare_native_stackinfo /*puts 2*4 additional bytes on stack*/
-#if 0
- sub $16,%esp /* build stack frame (4 * 4 bytes) */
-
- mov 20(%esp),%eax
- mov %eax,(%esp)
-
- call builtin_asm_get_stackframeinfo
- movl $0,12(%esp)
- mov %eax,8(%esp)
- mov (%eax),%ebx
- mov %ebx,4(%esp)
- mov %esp,%ecx
- add $4,%ecx
- mov %ecx,(%eax)
-#endif
- push %eax
- call builtin_new
- add $4,%esp
-
- call asm_remove_native_stackinfo /*first element on stack is return adress again*/
-#if 0
- call
- mov 4(%esp),%ebx
- mov 8(%esp),%ecx
- mov %ebx,(%ecx)
-
- add $16,%esp
-#endif
- jmp L_builtin_new_patch
-
-
-L_builtin_new_noinit:
- mov 4(%esp),%eax
- push %eax
- call builtin_new
- add $4,%esp
- /*jmp L_builtin_new_patch*/
-
-L_builtin_new_patch:
-/*add patching code here */
- lea builtin_new,%edx
- mov (%esp),%ecx
- mov %edx,-6(%ecx) /*patch calling instruction, t directly call builtin_new the next time*/
- ret
-
-
-
-
-
-
asm_getclassvalues_atomic:
_crit_restart2:
mov 4(%esp),%ecx /* super */
.long 0
-
-/************************ function asm_prepare_native_stackinfo ****************************
-* *
-* creates a stackfame for the begin of a native function (either builtin or not ) *
-* expected stack at begin of function *
-* .... *
-* address of the jit call which invokes the native *
-* begin address of stack frame of the java method *
-* method pointer or 0 (for built ins) *
-* return address *
-* *
-* at end of function: *
-* ... *
-* address of the jit call which invokes the native *
-* begin address of stack frame of the java method *
-* method pointer or 0 (for built ins) *
-* address of thread specific top of native list *
-* old value of thread specific head *
-* return address *
-* *
-* .... *
-* This thing is less efficient than the original #define (callerside) *
-* destroyes REG_ITMP2, keeps REG_ITMP1 *
-********************************************************************************************/
-
-
-asm_prepare_native_stackinfo:
- sub $8,%esp
- mov 8(%esp),%ecx
- mov %ecx,(%esp)
- push %eax
- lea builtin_asm_get_stackframeinfo,%ecx
- call *%ecx
- mov %eax, 12(%esp)
- mov (%eax),%ecx
- mov %ecx,8(%esp)
- mov %esp,%ecx
- add $8,%ecx
- mov %ecx,(%eax)
- pop %eax
- ret
-#if 0
-#define PREPARE_NATIVE_STACKINFO \
- i386_push_reg(cd, REG_ITMP1); /*save itmp1, needed by some stubs */ \
- i386_alu_imm_reg(cd, I386_SUB, 2*4, REG_SP); /* build stack frame (2 * 4 bytes), together with previous =3*4 */ \
- i386_mov_imm_reg(cd, (s4) codegen_stubcalled,REG_ITMP1); \
- i386_call_reg(cd, REG_ITMP1); /*call codegen_stubcalled*/ \
- 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_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 */ \
- i386_mov_membase_reg(cd, REG_SP,2*4,REG_ITMP1); /* restore ITMP1, need for some stubs*/ \
- i386_mov_imm_membase(cd, 0,REG_SP, 2*4); /* builtin */
-#endif
-
-
-/************************ function asm_remove _native_stackinfo *******************************************
-* *
-* creates a stackfame for the begin of a native function (either builtin or not) *
-* expected stack at begin of function *
-* address of the jit call which invokes the native *
-* begin address of stack frame of the java method *
-* method pointer or 0 (for built ins) *
-* address thread specific top of native list *
-* old value of thread specific head *
-* return address *
-* *
-* at end of function: *
-* .... *
-* return adresss of the jit call which invokes the native *
-* return address *
-* *
-* REG_ITMP2_XPC = address of the jit call which invokes the native *
-* *
-* *
-* This thing is less efficient than the original #define (callerside), uses ITMP3,uses ITMP3,keeps ITMP1 *
-***********************************************************************************************************/
-
-asm_remove_native_stackinfo:
- mov 4(%esp),%ecx
- mov 8(%esp),%edx
- mov %ecx,(%edx)
- pop %edx
- add $16,%esp
- push %edx
- ret
-
-#if 0
-#define REMOVE_NATIVE_STACKINFO \
- 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, I386_ADD,3*4,REG_SP);
-#endif
-
-
-
-
/*
* These are local overrides for various environment variables in Emacs.
* Please do not remove this and leave it at the end of the file, where
Changes: Joseph Wenninger
Christian Ullrich
- $Id: codegen.c 2860 2005-06-28 18:37:28Z twisti $
+ $Id: codegen.c 2971 2005-07-10 15:33:54Z twisti $
*/
void codegen(methodinfo *m, codegendata *cd, registerdata *rd)
{
- s4 len, s1, s2, s3, d;
+ s4 len, s1, s2, s3, d, off;
ptrint a;
stackptr src;
varinfo *var;
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);
} 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);
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);
} 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);
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);
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);
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) {
+ 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_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) {
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);
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);
+
+ bte = iptr->val.a;
+
+ M_AST(s1, REG_SP, 0 * 4);
+ M_AST(s3, REG_SP, 1 * 4);
+ M_MOV_IMM((ptrint) bte->fp, 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*/
PATCHER_get_putstatic,
(unresolved_field *) iptr->target);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
codegen_addpatchref(cd, cd->mcodeptr,
PATCHER_clinit, fi->class);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
}
PATCHER_get_putstatic,
(unresolved_field *) iptr->target);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
codegen_addpatchref(cd, cd->mcodeptr,
PATCHER_clinit, fi->class);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
}
PATCHER_get_putstatic,
(unresolved_field *) iptr[1].target);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
codegen_addpatchref(cd, cd->mcodeptr,
PATCHER_clinit, fi->class);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
}
PATCHER_getfield,
(unresolved_field *) iptr->target);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
PATCHER_putfield,
(unresolved_field *) iptr->target);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
PATCHER_putfieldconst,
(unresolved_field *) iptr[1].target);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
if (iptr->target) {
codegen_addpatchref(cd, cd->mcodeptr, bte->fp, iptr->target);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
codegen_addpatchref(cd, cd->mcodeptr,
PATCHER_invokestatic_special, um);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
codegen_addpatchref(cd, cd->mcodeptr,
PATCHER_invokevirtual, um);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
codegen_addpatchref(cd, cd->mcodeptr,
PATCHER_invokeinterface, um);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
2 /* test */ + 6 /* jcc */);
if (!super)
- s2 += (showdisassemble ? 5 : 0);
+ s2 += (opt_showdisassemble ? 5 : 0);
/* calculate class checkcast code size */
s3 += 2 /* cmp */ + 6 /* jcc */;
if (!super)
- s3 += (showdisassemble ? 5 : 0);
+ s3 += (opt_showdisassemble ? 5 : 0);
/* 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);
+ 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);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
PATCHER_checkcast_instanceof_interface,
(constant_classref *) iptr->target);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
}
PATCHER_checkcast_class,
(constant_classref *) iptr->target);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
}
}
break;
+ case ICMD_ARRAYCHECKCAST: /* ..., objectref ==> ..., objectref */
+ /* op1: 1... resolved, 0... not resolved */
+
+ var_to_reg_int(s1, src, REG_ITMP1);
+ M_AST(s1, REG_SP, 0 * 4);
+
+ bte = iptr->val.a;
+
+ if (!iptr->op1) {
+ codegen_addpatchref(cd, cd->mcodeptr, bte->fp, iptr->target);
+
+ if (opt_showdisassemble) {
+ M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
+ }
+
+ a = 0;
+
+ } else {
+ a = (ptrint) bte->fp;
+ }
+
+ M_AST_IMM((ptrint) iptr->target, REG_SP, 1 * 4);
+ M_MOV_IMM((ptrint) a, 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);
+ M_INTMOVE(s1, d);
+ store_reg_to_var_int(iptr->dst, d);
+ break;
+
case ICMD_INSTANCEOF: /* ..., objectref ==> ..., intresult */
/* op1: 0 == array, 1 == class */
2 /* test */ + 6 /* jcc */ + 5 /* mov_imm_reg */);
if (!super)
- s2 += (showdisassemble ? 5 : 0);
+ s2 += (opt_showdisassemble ? 5 : 0);
/* calculate class instanceof code size */
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);
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);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
PATCHER_checkcast_instanceof_interface,
(constant_classref *) iptr->target);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
}
PATCHER_instanceof_class,
(constant_classref *) iptr->target);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
}
(functionptr) (ptrint) iptr->target,
iptr->val.a);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
{
- /* generate bound check stubs */
+ /* generate ArrayIndexOutOfBoundsException stubs */
u1 *xcodeptr = NULL;
branchref *bref;
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 */
+ M_INTMOVE(bref->reg, REG_ITMP1); /* 2 bytes */
+
+ M_MOV_IMM(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 */
+ M_AADD_IMM32(bref->branchpos - 6, REG_ITMP2_XPC); /* 6 bytes */
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_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);
+ M_ASUB_IMM(6 * 4 + sizeof(stackframeinfo), REG_SP);
+ M_IST(REG_ITMP1, REG_SP, 4 * 4);
+ M_AST(REG_ITMP2_XPC, REG_SP, 5 * 4);
- /*REMOVE_NATIVE_STACKINFO;*/
- i386_mov_imm_reg(cd,(s4)asm_remove_native_stackinfo,REG_ITMP3);
- i386_call_reg(cd,REG_ITMP3);
+ /* create dynamic stack info */
- 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_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(6 * 4, REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 0 * 4);
+ M_IST_IMM(0, REG_SP, 1 * 4);
+ dseg_adddata(cd, cd->mcodeptr);
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(6 * 4 + sizeof(stackframeinfo), REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 2 * 4);
+ M_AST(REG_ITMP2_XPC, REG_SP, 3 * 4); /* don't use ITMP2 till here */
+ M_MOV_IMM((ptrint) stacktrace_create_inline_stackframeinfo, REG_ITMP3);
+ M_CALL(REG_ITMP3);
+
+ /* create exception */
+
+ M_ALD(REG_ITMP1, REG_SP, 4 * 4);
+ M_AST(REG_ITMP1, REG_SP, 0 * 4);
+ M_MOV_IMM((ptrint) new_arrayindexoutofboundsexception, REG_ITMP3);
+ M_CALL(REG_ITMP3);
+ M_AST(REG_RESULT, REG_SP, 1 * 4);
+
+ /* remove native stackframe info */
+
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(6 * 4, REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 0 * 4);
+ M_MOV_IMM((ptrint) stacktrace_remove_stackframeinfo, REG_ITMP3);
+ M_CALL(REG_ITMP3);
+
+ M_ALD(REG_ITMP1_XPTR, REG_SP, 1 * 4);
+ M_ALD(REG_ITMP2_XPC, REG_SP, 5 * 4);
+ M_AADD_IMM(6 * 4 + sizeof(stackframeinfo), REG_SP);
+
+ M_MOV_IMM((ptrint) asm_handle_exception, REG_ITMP3);
+ M_JMP(REG_ITMP3);
}
}
- /* generate negative array size check stubs */
+ /* generate ArrayStoreException stubs */
xcodeptr = NULL;
- for (bref = cd->xcheckarefs; bref != NULL; bref = bref->next) {
+ for (bref = cd->xstorerefs; 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));
+ xcodeptr - cd->mcodebase - (5 + 6));
continue;
}
MCODECHECK(100);
- i386_mov_imm_reg(cd, 0, REG_ITMP2_XPC); /* 5 bytes */
+ M_MOV_IMM(0, REG_ITMP2_XPC); /* 5 bytes */
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); /* 6 bytes */
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(5 * 4 + sizeof(stackframeinfo), REG_SP);
+ M_AST(REG_ITMP2_XPC, REG_SP, 4 * 4);
+ /* create dynamic stack info */
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4, REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 0 * 4);
+ M_IST_IMM(0, REG_SP, 1 * 4);
+ dseg_adddata(cd, cd->mcodeptr);
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4 + sizeof(stackframeinfo), REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 2 * 4);
+ M_AST(REG_ITMP2_XPC, REG_SP, 3 * 4); /* don't use ITMP2 till here */
+ M_MOV_IMM((ptrint) stacktrace_create_inline_stackframeinfo, REG_ITMP3);
+ M_CALL(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);*/
+ /* create exception */
+ M_MOV_IMM((ptrint) new_arraystoreexception, REG_ITMP3);
+ M_CALL(REG_ITMP3);
+ M_AST(REG_RESULT, REG_SP, 1 * 4);
- /*REMOVE_NATIVE_STACKINFO;*/
- i386_mov_imm_reg(cd,(s4)asm_remove_native_stackinfo,REG_ITMP3);
- i386_call_reg(cd,REG_ITMP3);
+ /* remove native stackframe info */
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4, REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 0 * 4);
+ M_MOV_IMM((ptrint) stacktrace_remove_stackframeinfo, REG_ITMP3);
+ M_CALL(REG_ITMP3);
- i386_pop_reg(cd, REG_ITMP2_XPC);
+ M_ALD(REG_ITMP1_XPTR, REG_SP, 1 * 4);
+ M_ALD(REG_ITMP2_XPC, REG_SP, 4 * 4);
+ M_AADD_IMM(5 * 4 + sizeof(stackframeinfo), 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 cast check stubs */
+ /* generate NegativeArraySizeException stubs */
xcodeptr = NULL;
- for (bref = cd->xcastrefs; bref != NULL; bref = bref->next) {
+ 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));
+ xcodeptr - cd->mcodebase - (5 + 6));
continue;
}
MCODECHECK(100);
- i386_mov_imm_reg(cd, 0, REG_ITMP2_XPC); /* 5 bytes */
+ M_MOV_IMM(0, REG_ITMP2_XPC); /* 5 bytes */
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); /* 6 bytes */
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(5 * 4 + sizeof(stackframeinfo), REG_SP);
+ M_AST(REG_ITMP2_XPC, REG_SP, 4 * 4);
- /*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);
+ /* create dynamic stack info */
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4, REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 0 * 4);
+ M_IST_IMM(0, REG_SP, 1 * 4);
+ dseg_adddata(cd, cd->mcodeptr);
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4 + sizeof(stackframeinfo), REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 2 * 4);
+ M_AST(REG_ITMP2_XPC, REG_SP, 3 * 4); /* don't use ITMP2 till here */
+ M_MOV_IMM((ptrint) stacktrace_create_inline_stackframeinfo, REG_ITMP3);
+ M_CALL(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);*/
+ /* create exception */
+ M_MOV_IMM((ptrint) new_negativearraysizeexception, REG_ITMP3);
+ M_CALL(REG_ITMP3);
+ M_AST(REG_RESULT, REG_SP, 1 * 4);
- /*REMOVE_NATIVE_STACKINFO;*/
- i386_mov_imm_reg(cd,(s4)asm_remove_native_stackinfo,REG_ITMP3);
- i386_call_reg(cd,REG_ITMP3);
+ /* remove native stackframe info */
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4, REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 0 * 4);
+ M_MOV_IMM((ptrint) stacktrace_remove_stackframeinfo, REG_ITMP3);
+ M_CALL(REG_ITMP3);
- i386_pop_reg(cd, REG_ITMP2_XPC);
+ M_ALD(REG_ITMP1_XPTR, REG_SP, 1 * 4);
+ M_ALD(REG_ITMP2_XPC, REG_SP, 4 * 4);
+ M_AADD_IMM(5 * 4 + sizeof(stackframeinfo), REG_SP);
- i386_mov_imm_reg(cd, (u4) 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 divide by zero check stubs */
+ /* generate ClassCastException stubs */
xcodeptr = NULL;
- for (bref = cd->xdivrefs; bref != NULL; bref = bref->next) {
+ 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));
+ xcodeptr - cd->mcodebase - (5 + 6));
continue;
}
MCODECHECK(100);
- i386_mov_imm_reg(cd, 0, REG_ITMP2_XPC); /* 5 bytes */
+ M_MOV_IMM(0, REG_ITMP2_XPC); /* 5 bytes */
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); /* 6 bytes */
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(5 * 4 + sizeof(stackframeinfo), REG_SP);
+ M_AST(REG_ITMP2_XPC, REG_SP, 4 * 4);
- /*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);
+ /* create dynamic stack info */
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4, REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 0 * 4);
+ M_IST_IMM(0, REG_SP, 1 * 4);
+ dseg_adddata(cd, cd->mcodeptr);
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4 + sizeof(stackframeinfo), REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 2 * 4);
+ M_AST(REG_ITMP2_XPC, REG_SP, 3 * 4); /* don't use ITMP2 till here */
+ M_MOV_IMM((ptrint) stacktrace_create_inline_stackframeinfo, REG_ITMP3);
+ M_CALL(REG_ITMP3);
+ /* create exception */
- i386_mov_imm_reg(cd, (u4) new_arithmeticexception, REG_ITMP1);
- i386_call_reg(cd, REG_ITMP1); /* return value is REG_ITMP1_XPTR */
+ M_MOV_IMM((ptrint) new_classcastexception, REG_ITMP3);
+ M_CALL(REG_ITMP3);
+ M_AST(REG_RESULT, REG_SP, 1 * 4);
- /*REMOVE_NATIVE_STACKINFO;*/
- i386_mov_imm_reg(cd,(s4)asm_remove_native_stackinfo,REG_ITMP3);
- i386_call_reg(cd,REG_ITMP3);
+ /* remove native stackframe info */
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4, REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 0 * 4);
+ M_MOV_IMM((ptrint) stacktrace_remove_stackframeinfo, REG_ITMP3);
+ M_CALL(REG_ITMP3);
- i386_pop_reg(cd, REG_ITMP2_XPC);
+ M_ALD(REG_ITMP1_XPTR, REG_SP, 1 * 4);
+ M_ALD(REG_ITMP2_XPC, REG_SP, 4 * 4);
+ M_AADD_IMM(5 * 4 + sizeof(stackframeinfo), 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 exception check stubs */
+ /* generate ArithmeticException stubs */
xcodeptr = NULL;
- for (bref = cd->xexceptionrefs; bref != NULL; bref = bref->next) {
+ for (bref = cd->xdivrefs; bref != NULL; bref = bref->next) {
if ((cd->exceptiontablelength == 0) && (xcodeptr != NULL)) {
- gen_resolvebranch(cd->mcodebase + bref->branchpos,
+ gen_resolvebranch(cd->mcodebase + bref->branchpos,
bref->branchpos,
- xcodeptr - cd->mcodebase - (5 + 5 + 2));
+ xcodeptr - cd->mcodebase - (5 + 6));
continue;
}
bref->branchpos,
cd->mcodeptr - cd->mcodebase);
- MCODECHECK(200);
+ MCODECHECK(100);
- i386_mov_imm_reg(cd, 0, REG_ITMP2_XPC); /* 5 bytes */
+ M_MOV_IMM(0, REG_ITMP2_XPC); /* 5 bytes */
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); /* 6 bytes */
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(5 * 4 + sizeof(stackframeinfo), REG_SP);
+ M_AST(REG_ITMP2_XPC, REG_SP, 4 * 4);
- /*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);
+ /* create dynamic stack info */
-#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)*/
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4, REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 0 * 4);
+ M_IST_IMM(0, REG_SP, 1 * 4);
+ dseg_adddata(cd, cd->mcodeptr);
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4 + sizeof(stackframeinfo), REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 2 * 4);
+ M_AST(REG_ITMP2_XPC, REG_SP, 3 * 4); /* don't use ITMP2 till here */
+ M_MOV_IMM((ptrint) stacktrace_create_inline_stackframeinfo, REG_ITMP3);
+ M_CALL(REG_ITMP3);
- i386_alu_imm_reg(cd, ALU_ADD,6*4,REG_SP);
+ /* create exception */
- i386_pop_reg(cd, REG_ITMP1_XPTR);
- i386_pop_reg(cd, REG_ITMP3); /* just remove the no longer needed 0 from the stack*/
+ M_MOV_IMM((ptrint) new_arithmeticexception, REG_ITMP3);
+ M_CALL(REG_ITMP3);
+ M_AST(REG_RESULT, REG_SP, 1 * 4);
- /*REMOVE_NATIVE_STACKINFO;*/
- i386_mov_imm_reg(cd,(s4)asm_remove_native_stackinfo,REG_ITMP3);
- i386_call_reg(cd,REG_ITMP3);
+ /* remove native stackframe info */
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4, REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 0 * 4);
+ M_MOV_IMM((ptrint) stacktrace_remove_stackframeinfo, REG_ITMP3);
+ M_CALL(REG_ITMP3);
- i386_pop_reg(cd, REG_ITMP2_XPC);
+ M_ALD(REG_ITMP1_XPTR, REG_SP, 1 * 4);
+ M_ALD(REG_ITMP2_XPC, REG_SP, 4 * 4);
+ M_AADD_IMM(5 * 4 + sizeof(stackframeinfo), 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;
if ((cd->exceptiontablelength == 0) && (xcodeptr != NULL)) {
gen_resolvebranch(cd->mcodebase + bref->branchpos,
bref->branchpos,
- xcodeptr - cd->mcodebase - (5 + 5 + 2));
+ xcodeptr - cd->mcodebase - (5 + 6));
continue;
}
MCODECHECK(100);
- i386_mov_imm_reg(cd, 0, REG_ITMP2_XPC); /* 5 bytes */
+ M_MOV_IMM(0, REG_ITMP2_XPC); /* 5 bytes */
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); /* 6 bytes */
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(5 * 4 + sizeof(stackframeinfo), REG_SP);
+ M_AST(REG_ITMP2_XPC, REG_SP, 4 * 4);
- /*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);
+ /* create dynamic stack info */
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4, REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 0 * 4);
+ M_IST_IMM(0, REG_SP, 1 * 4);
+ dseg_adddata(cd, cd->mcodeptr);
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4 + sizeof(stackframeinfo), REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 2 * 4);
+ M_AST(REG_ITMP2_XPC, REG_SP, 3 * 4); /* don't use ITMP2 till here */
+ M_MOV_IMM((ptrint) stacktrace_create_inline_stackframeinfo, REG_ITMP3);
+ M_CALL(REG_ITMP3);
+ /* create exception */
-#if 0
- /* create native call block*/
- i386_alu_imm_reg(cd, ALU_SUB, 3*4, REG_SP); /* build stack frame (4 * 4 bytes) */
+ M_MOV_IMM((ptrint) new_nullpointerexception, REG_ITMP3);
+ M_CALL(REG_ITMP3);
+ M_AST(REG_RESULT, REG_SP, 1 * 4);
+ /* remove stackframe info */
- i386_mov_imm_reg(cd, (s4) codegen_stubcalled,REG_ITMP1);
- i386_call_reg(cd, REG_ITMP1); /*call codegen_stubcalled*/
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4, REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 0 * 4);
+ M_MOV_IMM((ptrint) stacktrace_remove_stackframeinfo, REG_ITMP3);
+ M_CALL(REG_ITMP3);
- 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_ALD(REG_ITMP1_XPTR, REG_SP, 1 * 4);
+ M_ALD(REG_ITMP2_XPC, REG_SP, 4 * 4);
+ M_AADD_IMM(5 * 4 + sizeof(stackframeinfo), REG_SP);
- i386_mov_imm_reg(cd, (u4) new_nullpointerexception, REG_ITMP1);
- i386_call_reg(cd, REG_ITMP1); /* return value is REG_ITMP1_XPTR */
+ M_MOV_IMM((ptrint) asm_handle_exception, REG_ITMP3);
+ M_JMP(REG_ITMP3);
+ }
+ }
- /*REMOVE_NATIVE_STACKINFO;*/
- i386_mov_imm_reg(cd,(s4)asm_remove_native_stackinfo,REG_ITMP3);
- i386_call_reg(cd,REG_ITMP3);
+ /* generate exception check 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 + 6));
+ continue;
+ }
-#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);
+ gen_resolvebranch(cd->mcodebase + bref->branchpos,
+ bref->branchpos,
+ cd->mcodeptr - cd->mcodebase);
+
+ MCODECHECK(200);
+
+ M_MOV_IMM(0, REG_ITMP2_XPC); /* 5 bytes */
+ dseg_adddata(cd, cd->mcodeptr);
+ M_AADD_IMM32(bref->branchpos - 6, REG_ITMP2_XPC); /* 6 bytes */
+
+ if (xcodeptr != NULL) {
+ i386_jmp_imm(cd, (xcodeptr - cd->mcodeptr) - 5);
+
+ } else {
+ xcodeptr = cd->mcodeptr;
+
+ M_ASUB_IMM(5 * 4 + sizeof(stackframeinfo), REG_SP);
+ M_AST(REG_ITMP2_XPC, REG_SP, 4 * 4);
+
+ /* create dynamic stack info */
+
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4, REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 0 * 4);
+ M_IST_IMM(0, REG_SP, 1 * 4);
+ dseg_adddata(cd, cd->mcodeptr);
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4 + sizeof(stackframeinfo), REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 2 * 4);
+ M_AST(REG_ITMP2_XPC, REG_SP, 3 * 4); /* don't use ITMP2 till here */
+ M_MOV_IMM((ptrint) stacktrace_create_inline_stackframeinfo, REG_ITMP3);
+ M_CALL(REG_ITMP3);
+
+#if defined(USE_THREADS) && defined(NATIVE_THREADS)
+ M_MOV_IMM((ptrint) &builtin_get_exceptionptrptr, REG_ITMP1);
+ M_CALL(REG_ITMP1);
+ M_ALD(REG_ITMP3, REG_RESULT, 0);
+ M_AST_IMM(0, REG_RESULT, 0);
+ M_MOV(REG_ITMP3, REG_ITMP1_XPTR);
+#else
+ M_MOV_IMM((ptrint) &_exceptionptr, REG_ITMP3);
+ M_ALD(REG_ITMP1_XPTR, REG_ITMP3, 0);
+ M_AST_IMM(0, REG_ITMP3, 0);
#endif
- i386_pop_reg(cd, REG_ITMP2_XPC);
+ M_AST(REG_ITMP1_XPTR, REG_SP, 1 * 4);
+
+ /* call fillInStackTrace */
+
+ M_AST(REG_ITMP1_XPTR, REG_SP, 0 * 4);
+ M_MOV_IMM((ptrint) stacktrace_call_fillInStackTrace, REG_ITMP3);
+ M_CALL(REG_ITMP3);
+
+ /* remove stackframe info */
- i386_mov_imm_reg(cd, (s4) asm_handle_exception, REG_ITMP3);
- i386_jmp_reg(cd, REG_ITMP3);
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(5 * 4, REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 0 * 4);
+ M_MOV_IMM((ptrint) stacktrace_remove_stackframeinfo, REG_ITMP3);
+ M_CALL(REG_ITMP3);
+
+ M_ALD(REG_ITMP1_XPTR, REG_SP, 1 * 4);
+ M_ALD(REG_ITMP2_XPC, REG_SP, 4 * 4);
+ M_AADD_IMM(5 * 4 + sizeof(stackframeinfo), REG_SP);
+
+ M_MOV_IMM((ptrint) asm_handle_exception, REG_ITMP3);
+ M_JMP(REG_ITMP3);
}
}
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 */
/* 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);
+ M_PUSH_IMM((ptrint) (mcode >> 32));
+ M_PUSH_IMM((ptrint) mcode);
+ M_PUSH_IMM((ptrint) pref->ref);
+ M_PUSH_IMM((ptrint) pref->patcher);
- i386_push_imm(cd, (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);
}
}
}
s4 t;
s4 s1, s2, off;
s4 stackframesize;
- s4 stackframeoffset;
/* set some variables */
/* previous pointer + method info + 4 offset native */
/* already handled by nmd->memuse */
- stackframesize = /* 4 + */ 16;
- stackframeoffset = 4;
+ stackframesize =
+ sizeof(stackframeinfo) / SIZEOF_VOID_P +
+ 4 * 4 + /* 4 arguments (create stackframe) */
+ 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 */
cd->mcodeend = (s4 *) (cd->mcodebase + cd->mcodesize);
- /* if function is static, check for initialized */
+ /* calculate stackframe size for native function */
- if (m->flags & ACC_STATIC) {
- /* already handled by nmd->memuse */
-/* stackframesize += 4; */
- stackframeoffset += 4;
+ M_ASUB_IMM(stackframesize * 4, REG_SP);
- /* if class isn't yet initialized, do it */
- if (!m->class->initialized) {
- codegen_addpatchref(cd, cd->mcodeptr, PATCHER_clinit, m->class);
+ /* if function is static, check for initialized */
- if (showdisassemble) {
- M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
- }
+ if ((m->flags & ACC_STATIC) && !m->class->initialized) {
+ codegen_addpatchref(cd, cd->mcodeptr, PATCHER_clinit, m->class);
+
+ if (opt_showdisassemble) {
+ M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
}
/* 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);
i386_ffree_reg(cd, 6);
i386_ffree_reg(cd, 7);
- /* calculate stackframe size for native function */
-
- stackframesize += nmd->memuse * 4;
- i386_alu_imm_reg(cd, ALU_SUB, stackframesize, REG_SP);
+ /* create dynamic stack info */
- /* CREATE DYNAMIC STACK INFO -- BEGIN*/
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(stackframesize * 4 - sizeof(stackframeinfo), REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 0 * 4);
+ M_IST_IMM(0, REG_SP, 1 * 4);
+ dseg_adddata(cd, cd->mcodeptr);
+ M_MOV(REG_SP, REG_ITMP2);
+ M_AADD_IMM(stackframesize * 4 + SIZEOF_VOID_P, REG_ITMP2);
+ 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) stacktrace_create_native_stackframeinfo, REG_ITMP1);
+ M_CALL(REG_ITMP1);
- 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);
-
- /* CREATE DYNAMIC STACK INFO -- END*/
/* copy arguments into new stackframe */
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);
}
}
}
/* 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);
+ i386_mov_imm_membase(cd, (ptrint) m->class, REG_SP, 1 * 4);
/* put env into first argument */
- i386_mov_imm_membase(cd, (ptrint) &env, REG_SP, 0);
+ i386_mov_imm_membase(cd, (ptrint) &env, REG_SP, 0 * 4);
/* call the native function */
if (f == NULL)
codegen_addpatchref(cd, cd->mcodeptr, PATCHER_resolve_native, m);
- if (showdisassemble) {
+ if (opt_showdisassemble) {
M_NOP; M_NOP; M_NOP; M_NOP; M_NOP;
}
#endif
i386_call_reg(cd, REG_ITMP1);
- /* 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 native stackframe info */
+
+ 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 {
+ /* XXX save float? */
+ }
+
+ M_MOV(REG_SP, REG_ITMP1);
+ M_AADD_IMM(stackframesize * 4 - sizeof(stackframeinfo), REG_ITMP1);
+ M_AST(REG_ITMP1, REG_SP, 0 * 4);
+ M_MOV_IMM((ptrint) stacktrace_remove_stackframeinfo, REG_ITMP1);
+ M_CALL(REG_ITMP1);
- i386_alu_imm_reg(cd, ALU_ADD, stackframesize, 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 {
+ /* XXX save float? */
+ }
if (runverbose) {
}
+ M_AADD_IMM(stackframesize * 4, REG_SP);
+
+
/* check for exception */
#if defined(USE_THREADS) && defined(NATIVE_THREADS)
(void) dseg_addaddress(cd, get_dummyLR()); /* monitorPtr */
off = 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_PUSH(REG_ITMP3);
/* 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);
}
}