X-Git-Url: http://wien.tomnetworks.com/gitweb/?a=blobdiff_plain;f=src%2Fvm%2Fjit%2Fi386%2Fasmpart.S;h=b9be6e191288c242139bfc018248b49e875043d0;hb=d62d56aa9150bb2156dac82966795fdcbd7562e0;hp=f90743898e81527ed13abd67f48decff826cb6c2;hpb=ad92477479aeed17382996ab43a7ca0dfab2ba93;p=cacao.git diff --git a/src/vm/jit/i386/asmpart.S b/src/vm/jit/i386/asmpart.S index f90743898..b9be6e191 100644 --- a/src/vm/jit/i386/asmpart.S +++ b/src/vm/jit/i386/asmpart.S @@ -1,9 +1,7 @@ /* src/vm/jit/i386/asmpart.S - Java-C interface functions for i386 - 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 + Copyright (C) 1996-2005, 2006, 2007, 2008 + CACAOVM - Verein zur Foerderung der freien virtuellen Maschine CACAO This file is part of CACAO. @@ -22,132 +20,78 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. - Contact: cacao@cacaojvm.org - - Authors: Andreas Krall - Reinhard Grafl - Christian Thalinger - - Changes: Joseph Wenninger - - $Id: asmpart.S 4357 2006-01-22 23:33:38Z twisti $ - */ #include "config.h" -#include "vm/jit/abi.h" +#include "md-asm.h" + +#include "vm/jit/i386/arch.h" #include "vm/jit/i386/md-abi.h" -#include "vm/jit/i386/md-asm.h" -#include "vm/jit/i386/offsets.h" +#include "vm/jit/abi-asm.h" #include "vm/jit/methodheader.h" .text -/* exported functions and variables *******************************************/ +/* export functions ***********************************************************/ - .globl asm_calljavafunction - .globl asm_calljavafunction_int + .globl asm_md_init - .globl asm_calljavafunction2 - .globl asm_calljavafunction2int - .globl asm_calljavafunction2long - .globl asm_calljavafunction2float - .globl asm_calljavafunction2double + .globl asm_vm_call_method + .globl asm_vm_call_method_int + .globl asm_vm_call_method_long + .globl asm_vm_call_method_float + .globl asm_vm_call_method_double + .globl asm_vm_call_method_exception_handler + .globl asm_vm_call_method_end - .globl asm_call_jit_compiler .globl asm_handle_nat_exception .globl asm_handle_exception - .globl asm_wrapper_patcher + .globl asm_abstractmethoderror .globl asm_builtin_f2i .globl asm_builtin_f2l .globl asm_builtin_d2i .globl asm_builtin_d2l - .globl asm_perform_threadswitch - .globl asm_initialize_thread_stack - .globl asm_switchstackandcall - .globl asm_criticalsections - .globl asm_getclassvalues_atomic - - -/********************* function asm_calljavafunction *************************** -* * -* This function calls a Java-method (which possibly needs compilation) * -* with up to 4 address parameters. * -* * -* This functions calls the JIT-compiler which eventually translates the * -* method into machine code. * -* * -* C-prototype: * -* javaobject_header *asm_calljavamethod (methodinfo *m, * -* void *arg1, void *arg2, void *arg3, void *arg4); * -* * -*******************************************************************************/ - - .align 8 + .globl asm_compare_and_swap + .globl asm_memory_barrier - .long 0 /* catch type all */ - .long calljava_xhandler /* handler pc */ - .long calljava_xhandler /* end pc */ - .long asm_calljavafunction /* start pc */ - .long 1 /* extable size */ - .long 0 /* line number table start */ - .long 0 /* line number table size */ - .long 0 /* fltsave */ - .long 0 /* intsave */ - .long 0 /* isleaf */ - .long 0 /* IsSync */ - .long 0 /* frame size */ - .long 0 /* method pointer (pointer to name) */ +#if defined(ENABLE_ESCAPE_CHECK) + .globl asm_escape_check +#endif -asm_calljavafunction: -asm_calljavafunction_int: - push bp /* allocate stack space */ - mov sp,bp - push %ebx /* save registers */ - push %esi - push %edi +/* asm_md_init ***************************************************************** - sub $(4*4),sp /* 4 adress parameters * 4 Bytes */ - mov 5*4(bp),itmp1 /* copy adress parameters to new block*/ - mov itmp1,3*4(sp) - - mov 5*4(bp),itmp1 - mov itmp1,2*4(sp) + Initialize machine dependent stuff. - mov 4*4(bp),itmp1 - mov itmp1,1*4(sp) + See: http://www.srware.com/linux_numerics.txt - mov 3*4(bp),itmp1 - mov itmp1,0*4(sp) - - mov 2*4(bp),itmp1 /* move function pointer to %eax */ + This puts the X86 FPU in 64-bit precision mode. The default under + Linux is to use 80-bit mode, which produces subtle differences from + FreeBSD and other systems, eg, (int)(1000*atof("0.3")) is 300 in + 64-bit mode, 299 in 80-bit mode. - lea asm_call_jit_compiler,itmp3 - call *itmp3 /* call JIT compiler */ + Fixes: http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=350729 -L_asm_calljavafunction_return: - add $(4*4),sp - pop %edi /* restore registers */ - pop %esi - pop %ebx - leave - ret +*******************************************************************************/ -calljava_xhandler: - push xptr /* pass exception pointer */ - call builtin_throw_exception +asm_md_init: + sub $4,sp /* allocate space for the FPU state */ + fnstcw (sp) /* get the FPU state */ + mov (sp),%eax + and $0xfcff,%ax /* remove the extended mode flag */ + or $0x0200,%ax /* put the double mode flag */ + mov %eax,(sp) /* store new FPU state */ + fldcw (sp) /* setup new FPU state */ add $4,sp - xor v0,v0 /* return NULL */ - jmp L_asm_calljavafunction_return + ret /********************* function asm_calljavafunction *************************** @@ -159,215 +103,85 @@ calljava_xhandler: * method into machine code. * * * * C-prototype: * -* javaobject_header *asm_calljavafunction2(methodinfo *m, * +* javaobject_header *asm_vm_call_method(methodinfo *m, * * u4 count, u4 size, void *callblock); * * * *******************************************************************************/ .align 8 - .long 0 /* catch type all */ - .long calljava_xhandler2 /* handler pc */ - .long calljava_xhandler2 /* end pc */ - .long asm_calljavafunction2 /* start pc */ - .long 1 /* extable size */ - .long 0 /* line number table start */ - .long 0 /* line number table size */ .long 0 /* fltsave */ .long 0 /* intsave */ .long 0 /* isleaf */ - .long 0 /* IsSync */ .long 0 /* frame size */ - .long 0 /* method pointer (pointer to name) */ - -asm_calljavafunction2: -asm_calljavafunction2int: -asm_calljavafunction2long: -asm_calljavafunction2float: -asm_calljavafunction2double: - push %ebp - mov %esp,%ebp /* save stackptr */ - - push %ebx /* save registers */ - push %esi - push %edi - - mov 20(%ebp),%eax /* pointer to arg block (4(push)+4(return)+4+4+4)*/ - mov 12(%ebp),%ecx /* arg count (4(push)+4(return)+4 */ - - xor %esi,%esi /* clear stackframe size (MUST be */ - /* before args check, may be zero!!!) */ - test %ecx,%ecx /* maybe we have no args */ - jle calljava_copydone - - mov %ecx,%edx /* calculate stack size */ - mov %eax,%edi /* save pointer to arg block */ - -calljava_calcstacksize: - mov offjniitemtype(%eax),%ebx - test $1,%ebx /* two word type? */ - jz calljava_onewordtype - add $4,%esi /* add 1 slot to stackframe size */ - -calljava_onewordtype: - add $4,%esi /* add 1 slot to stackframe size */ - sub $1,%edx - test %edx,%edx /* any args left? */ - jz calljava_setstack - add $sizejniblock,%eax /* goto next argument block */ - jmp calljava_calcstacksize - -calljava_setstack: - mov %edi,%eax /* restore pointer to arg block */ - sub %esi,%esp /* create stackframe for arguments */ - mov %esp,%edi /* move stackpointer into temp variable */ - -calljava_copyloop: - mov offjniitem(%eax),%edx /* copy 4 Byte of Argument */ - mov %edx,(%edi) - add $4,%edi /* increase sp to next argument */ - mov offjniitemtype(%eax),%ebx /* type -> ebx */ - test $1,%ebx /* Two Word Type? */ - jz calljava_copynext - - mov offjniitem+4(%eax),%edx /* copy upper 4 Byte of 2 Word Type */ - mov %edx,(%edi) - add $4,%edi /* increase sp to next argument */ - -calljava_copynext: - sub $1,%ecx /* are there any args left? */ - test %ecx,%ecx - jle calljava_copydone - - add $sizejniblock,%eax /* goto next argument block */ - jmp calljava_copyloop - -calljava_copydone: - mov 8(%ebp),%eax /* move function pointer to %eax */ - - lea asm_call_jit_compiler,itmp3 + .long 0 /* codeinfo pointer */ + +asm_vm_call_method: +asm_vm_call_method_int: +asm_vm_call_method_long: +asm_vm_call_method_float: +asm_vm_call_method_double: + push bp + mov sp,bp /* save stack pointer */ + sub $(4*4),sp /* create stackframe */ + and $0xfffffff0,sp /* align stack to 16-byte */ + + mov t0,0*4(sp) /* save registers */ + mov s1,1*4(sp) + mov s2,2*4(sp) + + mov sp,s1 /* save stack pointer */ + + mov 3*4(bp),t0 /* address of data structure */ + mov 4*4(bp),itmp1 /* number of stack arguments */ + + cmp $0,itmp1 + je L_asm_vm_call_method_stack_copy_done + + mov itmp1,itmp2 + add $1,itmp2 /* keep stack 16-byte aligned */ + and $0xfffffffe,itmp2 + shl $3,itmp2 /* calculate stack size */ + sub itmp2,sp /* create stack frame */ + mov sp,itmp2 /* temporary stack pointer */ + +L_asm_vm_call_method_stack_copy_loop: + mov 0(t0),itmp3 /* load argument */ + mov itmp3,0(itmp2) /* store argument on stack */ + mov 4(t0),itmp3 + mov itmp3,4(itmp2) + + sub $1,itmp1 /* subtract 1 argument */ + add $8,t0 /* set address of next argument */ + add $8,itmp2 /* increase SP */ + + cmp $0,itmp1 + jg L_asm_vm_call_method_stack_copy_loop + +L_asm_vm_call_method_stack_copy_done: + lea (2*4-256)(bp),mptr /* We subtract 256 to force the next */ + /* move instruction to have a 32-bit */ + /* offset. */ + + mov (0*4+256)(mptr),itmp3 /* method call as in Java */ call *itmp3 /* call JIT compiler */ -L_asm_calljavafunction2_return: - add %esi,%esp /* remove arg stack frame */ - pop %edi /* restore registers */ - pop %esi - pop %ebx +L_asm_vm_call_method_return: + mov s1,sp /* restore stackpointer */ + + mov 0*4(sp),t0 /* restore registers */ + mov 1*4(sp),s1 + mov 2*4(sp),s2 + leave ret -calljava_xhandler2: +asm_vm_call_method_exception_handler: push xptr /* pass exception pointer */ call builtin_throw_exception add $4,sp - xor v0,v0 /* return NULL */ - jmp L_asm_calljavafunction2_return - - -/****************** function asm_call_jit_compiler ***************************** -* * -* invokes the compiler for untranslated JavaVM methods. * -* * -* Register R0 contains a pointer to the method info structure (prepared * -* by createcompilerstub). Using the return address in R26 and the * -* offset in the LDA instruction or using the value in methodptr R28 the * -* patching address for storing the method address can be computed: * -* * -* method address was either loaded using * -* * -* i386_mov_imm_reg(a, REG_ITMP2) ; invokestatic/special * -* i386_call_reg(REG_ITMP2) * -* * -* or * -* * -* i386_mov_membase_reg(REG_SP, 0, REG_ITMP1) ; invokevirtual/interface * -* i386_mov_membase_reg(REG_ITMP1, OFFSET(, vftbl), REG_ITMP2) * -* i386_mov_membase_reg(REG_ITMP2, OFFSET(vftbl, table[0]) + \ * -* sizeof(methodptr) * m->vftblindex, REG_ITMP1) * -* i386_call_reg(REG_ITMP1) * -* * -* in the static case the method pointer can be computed using the * -* return address and the lda function following the jmp instruction * -* * -*******************************************************************************/ - -asm_call_jit_compiler: - sub $((4+2)*4+sizestackframeinfo),sp /* create stack frame */ - mov itmp1,(4+0)*4(sp) /* save method pointer */ - - mov (4+2)*4+sizestackframeinfo(sp),itmp3 /* get return address */ - mov -1(itmp3),itmp1b /* get function code */ - cmp $0xd1,itmp1b /* called with `call *REG_ITMP2'? */ - jne L_not_static_special - - sub $6,itmp3 /* calculate address of immediate */ - jmp L_call_jit_compile - -L_not_static_special: - cmp $0xd0,itmp1b /* called with `call *REG_ITMP1' */ - jne L_not_virtual_interface - - sub $6,itmp3 /* calculate address of offset */ - mov (itmp3),itmp3 /* get offset */ - add itmp2,itmp3 /* add base address to get method adr */ - jmp L_call_jit_compile - -L_not_virtual_interface: - xor itmp3,itmp3 /* a call from asm_calljavafunction */ - -L_call_jit_compile: - mov itmp3,(4+1)*4(sp) /* save address for method pointer */ - - mov sp,itmp1 /* create stackframe info */ - add $((4+2)*4),itmp1 - mov itmp1,0*4(sp) /* stackframeinfo pointer */ - movl $0,1*4(sp) /* if pv is NULL, use findmethod */ - mov sp,itmp2 - add $((1+4+2)*4+sizestackframeinfo),itmp2 /* pass java sp */ - mov itmp2,2*4(sp) - mov ((0+4+2)*4+sizestackframeinfo)(sp),itmp3 /* pass java ra */ - mov itmp3,3*4(sp) - call stacktrace_create_inline_stackframeinfo - - mov (4+0)*4(sp),itmp1 /* pass method pointer */ - mov itmp1,0*4(sp) - call jit_compile - mov v0,(4+0)*4(sp) /* save return value */ - - mov sp,itmp1 /* remove stackframe info */ - add $((4+2)*4),itmp1 - mov itmp1,0*4(sp) /* stackframeinfo pointer */ - call stacktrace_remove_stackframeinfo - - mov (4+0)*4(sp),v0 /* restore return value */ - mov (4+1)*4(sp),itmp3 /* restore address for method pointer */ - - add $((4+2)*4+sizestackframeinfo),sp /* remove stack frame */ - - test v0,v0 /* check for exception */ - je L_asm_call_jit_compiler_exception - - test itmp3,itmp3 /* was this a JIT call? */ - je L_call_method - - mov v0,(itmp3) /* save the new method pointer */ - -L_call_method: - jmp *v0 /* ...and now call the new method */ - -L_asm_call_jit_compiler_exception: -#if defined(USE_THREADS) && defined(NATIVE_THREADS) - call builtin_asm_get_exceptionptrptr - mov v0,itmp2 /* v0 == itmp1 */ -#else - lea _exceptionptr,itmp2 -#endif - mov (itmp2),xptr /* get the exception pointer */ - movl $0,(itmp2) /* clear the exception pointer */ - - pop xpc /* get return address */ - sub $2,xpc /* faulting address is ra - 2 */ - jmp asm_handle_exception +asm_vm_call_method_end: + jmp L_asm_vm_call_method_return /* asm_handle_exception ******************************************************** @@ -384,25 +198,26 @@ asm_handle_nat_exception: add $4,sp /* clear return address of native stub*/ asm_handle_exception: - sub $((ARG_CNT+TMP_CNT)*4),sp /* create maybe-leaf stackframe */ +L_asm_handle_exception: /* required for PIC code */ + sub $((ARG_CNT+TMP_CNT+3)*4),sp /* keep stack 16-byte aligned */ SAVE_ARGUMENT_REGISTERS(0) /* we save arg and temp registers in */ SAVE_TEMPORARY_REGISTERS(ARG_CNT) /* case this is a leaf method */ - mov $((ARG_CNT+TMP_CNT)*4),itmp3/* prepare a3 for handle_exception */ + mov $((ARG_CNT+TMP_CNT+3)*4),itmp3 /* prepare a3 for handle_exception */ mov $1,t0 /* set maybe-leaf flag */ L_asm_handle_exception_stack_loop: - sub $(10*4),sp /* create stackframe */ + sub $(12*4),sp /* keep stack 16-byte aligned */ mov xptr,4*4(sp) /* save exception pointer */ mov xpc,5*4(sp) /* save exception pc */ add sp,itmp3 /* calculate Java sp into a3... */ - add $(10*4),itmp3 + add $(12*4),itmp3 mov itmp3,7*4(sp) /* ...and save it */ mov t0,8*4(sp) /* save maybe-leaf flag */ mov xpc,0*4(sp) /* pass exception pc */ - call codegen_findmethod + call methodtree_find mov v0,6*4(sp) /* save data segment pointer */ mov 4*4(sp),itmp3 /* pass exception pointer */ @@ -420,7 +235,7 @@ L_asm_handle_exception_stack_loop: mov v0,xpc /* move handlerpc into xpc */ mov 4*4(sp),xptr /* restore exception pointer */ mov 8*4(sp),t0 /* get maybe-leaf flag */ - add $(10*4),sp /* free stackframe */ + add $(12*4),sp /* free stackframe */ test t0,t0 /* test for maybe-leaf flag */ jz L_asm_handle_exception_no_leaf @@ -428,7 +243,7 @@ L_asm_handle_exception_stack_loop: RESTORE_ARGUMENT_REGISTERS(0) /* if this is a leaf method, we have */ RESTORE_TEMPORARY_REGISTERS(ARG_CNT)/* to restore arg and temp registers */ - add $((ARG_CNT+TMP_CNT)*4),sp /* remove maybe-leaf stackframe */ + add $((ARG_CNT+TMP_CNT+3)*4),sp /* remove maybe-leaf stackframe */ L_asm_handle_exception_no_leaf: jmp *xpc /* jump to exception handler */ @@ -437,12 +252,12 @@ L_asm_handle_exception_not_catched: mov 4*4(sp),xptr /* restore exception pointer */ mov 6*4(sp),itmp3 /* restore data segment pointer */ mov 8*4(sp),t0 /* get maybe-leaf flag */ - add $(10*4),sp /* free stackframe */ + add $(12*4),sp /* free stackframe */ test t0,t0 jz L_asm_handle_exception_no_leaf_stack - add $((ARG_CNT+TMP_CNT)*4),sp /* remove maybe-leaf stackframe */ + add $((ARG_CNT+TMP_CNT+3)*4),sp /* remove maybe-leaf stackframe */ xor t0,t0 /* clear the maybe-leaf flag */ L_asm_handle_exception_no_leaf_stack: @@ -460,11 +275,11 @@ L_asm_handle_exception_no_leaf_stack: cmp $2,itmp1 je int2 - mov -3*4(itmp2),s0 + mov -4-3*8(itmp2),s0 int2: - mov -2*4(itmp2),s1 + mov -4-2*8(itmp2),s1 int1: - mov -1*4(itmp2),s2 + mov -4-1*8(itmp2),s2 shl $2,itmp1 /* multiply by 4 bytes */ sub itmp1,itmp2 @@ -508,70 +323,27 @@ noflt: jmp L_asm_handle_exception_stack_loop -/* asm_wrapper_patcher ********************************************************* - - XXX +/* asm_abstractmethoderror ***************************************************** - Stack layout: - 20 return address - 16 pointer to virtual java_objectheader - 12 last byte of machine code (xmcode) - 8 machine code (which is patched back later) - 4 unresolved field reference - 0 patcher function pointer to call + Creates and throws an AbstractMethodError. *******************************************************************************/ -asm_wrapper_patcher: - 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 */ +asm_abstractmethoderror: + sub $(3*4),sp /* keep stack 16-byte aligned */ + mov sp,itmp1 /* pass java sp */ + add $((1+3)*4),itmp1 mov itmp1,0*4(sp) - mov (0+2+4)*4+sizestackframeinfo(sp),itmp1 /* get function pointer */ - call *itmp1 /* call the patcher function */ - mov v0,1*4(sp) /* save return value */ - - 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)*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)*4+sizestackframeinfo),sp /* remove stack frame, keep ra */ - test itmp3,itmp3 /* exception thrown? */ - jz L_asm_wrapper_patcher_exception - ret /* call new patched code */ - -L_asm_wrapper_patcher_exception: -#if defined(USE_THREADS) && defined(NATIVE_THREADS) - call builtin_asm_get_exceptionptrptr - mov v0,itmp2 -#else - lea _exceptionptr,itmp2 -#endif - mov (itmp2),xptr /* get the exception pointer */ - movl $0,(itmp2) /* clear the exception pointer */ + mov 3*4(sp),itmp2 /* pass exception address */ + sub $2,itmp2 + mov itmp2,1*4(sp) + call exceptions_asm_new_abstractmethoderror + /* exception pointer is return value */ + add $(3*4),sp /* remove stack frame */ - pop xpc /* get and remove return address */ - jmp asm_handle_exception + pop xpc /* get exception address */ + sub $2,xpc /* exception address is ra - 2 */ + jmp L_asm_handle_exception /************************ function asm_builtin_x2x ***************************** @@ -581,179 +353,97 @@ L_asm_wrapper_patcher_exception: *******************************************************************************/ asm_builtin_f2i: - sub $4,%esp + sub $(3*4),%esp fsts (%esp) call builtin_f2i - add $4,%esp + add $(3*4),%esp ret asm_builtin_d2i: - sub $8,%esp + sub $(3*4),%esp fstl (%esp) call builtin_d2i - add $8,%esp + add $(3*4),%esp ret asm_builtin_f2l: - sub $4,%esp + sub $(3*4),%esp fsts (%esp) call builtin_f2l - add $4,%esp + add $(3*4),%esp ret asm_builtin_d2l: - sub $8,%esp + sub $(3*4),%esp fstl (%esp) call builtin_d2l - add $8,%esp + add $(3*4),%esp ret -/******************* function asm_initialize_thread_stack ********************** -* * -* initialized a thread stack * -* (to)->restorePoint = asm_initialize_thread_stack((u1*)(func), (to)->stackEnd)* -* * -*******************************************************************************/ +/* asm_compare_and_swap ******************************************************** + + Does an atomic compare and swap. Required for the lock + implementation. + + Atomically do the following: Check if the location still contains + `oldval`. If so, replace it by `newval` and return `oldval`. + + RETURN VALUE: + the old value at *p + + long compare_and_swap(volatile long *p, long oldval, long newval); -asm_initialize_thread_stack: - mov 8(%esp),%eax /* (to)->stackEnd */ - sub $36,%eax /* 4 bytes * 8 regs + 4 bytes func */ - - xor %edx,%edx - mov %edx,0(%eax) - mov %edx,4(%eax) - mov %edx,8(%eax) - mov %edx,12(%eax) - mov %edx,16(%eax) - mov %edx,20(%eax) - mov %edx,24(%eax) - mov %edx,28(%eax) - - mov 4(%esp),%edx /* save (u1*) (func) */ - mov %edx,32(%eax) - - ret /* return restorepoint in %eax */ - - -/******************* function asm_perform_threadswitch ************************* -* * -* void asm_perform_threadswitch (u1 **from, u1 **to, u1 **stackTop); * -* * -* performs a threadswitch * -* * *******************************************************************************/ -asm_perform_threadswitch: - sub $36,%esp - - mov %eax,0(%esp) - mov %ecx,4(%esp) - mov %edx,8(%esp) - mov %ebx,12(%esp) - mov %esp,16(%esp) - mov %ebp,20(%esp) - mov %esi,24(%esp) - mov %edi,28(%esp) - - mov 36(%esp),%eax /* save current return address */ - mov %eax,32(%esp) - - mov 40(%esp),%eax /* first argument **from */ - mov %esp,0(%eax) - - mov 48(%esp),%eax /* third argument **stackTop */ - mov %esp,0(%eax) - - mov 44(%esp),%eax /* second argument **to */ - mov 0(%eax),%esp /* load new stack pointer */ - - mov 0(%esp),%eax - mov 4(%esp),%ecx - mov 8(%esp),%edx - mov 12(%esp),%ebx - /* skip stack pointer */ - mov 20(%esp),%ebp - mov 24(%esp),%esi - mov 28(%esp),%edi - - add $32,%esp /* leave return address on stack */ +asm_compare_and_swap: + mov 1*4(sp),%ecx /* load p into a register */ + mov 2*4(sp),%eax /* load oldval into return register */ + mov 3*4(sp),%edx /* load newval into a register */ + lock; cmpxchgl %edx,0(%ecx) ret - -/********************* function asm_switchstackandcall ************************* -* * -* int asm_switchstackandcall (void *stack, void *func, void **stacktopsave, * -* void *p); * -* * -* Switches to a new stack, calls a function and switches back. * -* a0 new stack pointer * -* a1 function pointer * -* a2 pointer to variable where stack top should be stored * -* a3 pointer to user data, is passed to the function * -* * + +/* asm_memory_barrier ********************************************************** + + A memory barrier for the Java Memory Model. + *******************************************************************************/ -asm_switchstackandcall: - mov 4(%esp),%edx /* first argument *stack */ - sub $8,%edx /* allocate new stack */ +asm_memory_barrier: + lock; add $0,0(sp) + ret - mov (%esp),%eax /* save return address on new stack */ - mov %eax,(%edx) - mov %esp,4(%edx) /* save old stack pointer on new stack */ +#if defined(ENABLE_ESCAPE_CHECK) +asm_escape_check: + sub $24,%esp - mov 12(%esp),%eax /* third argument **stacktopsave */ - mov %esp,(%eax) /* save old stack pointer to variable */ + mov t0, 4(%esp) + mov itmp1, 8(%esp) + mov itmp2, 12(%esp) + mov itmp3, 16(%esp) - mov 8(%esp),%eax /* load function pointer */ - mov 16(%esp),%ecx /* fourth argument *p */ - - mov %edx,%esp /* switch to new stack */ + mov 28(%esp), itmp1 + mov itmp1, (%esp) - sub $4,%esp - mov %ecx,0(%esp) /* pass pointer */ - call *%eax /* and call function */ - add $4,%esp + call escape_analysis_escape_check - mov (%esp),%edx /* load return address */ - mov 4(%esp),%esp /* switch to old stack */ - mov %edx,(%esp) - ret + mov 4(%esp), t0 + mov 8(%esp), itmp1 + mov 12(%esp), itmp2 + mov 16(%esp), itmp3 - -asm_getclassvalues_atomic: -_crit_restart2: - mov 4(%esp),%ecx /* super */ - mov 8(%esp),%edx /* sub */ -_crit_begin2: - mov offbaseval(%ecx),%eax - mov offdiffval(%ecx),%ecx - mov offbaseval(%edx),%edx -_crit_end2: - push %ebx - mov 16(%esp),%ebx /* out */ - mov %eax,offcast_super_baseval(%ebx) - mov %ecx,offcast_super_diffval(%ebx) - mov %edx,offcast_sub_baseval(%ebx) - pop %ebx + add $24,sp ret +#endif - .data -asm_criticalsections: -#if defined(USE_THREADS) && defined(NATIVE_THREADS) -#if 0 - .long _crit_begin1 - .long _crit_end1 - .long _crit_restart1 -#endif - .long _crit_begin2 - .long _crit_end2 - .long _crit_restart2 -#endif - .long 0 +/* disable exec-stacks ********************************************************/ +#if defined(__linux__) && defined(__ELF__) + .section .note.GNU-stack,"",%progbits +#endif /* * These are local overrides for various environment variables in Emacs. @@ -766,4 +456,5 @@ asm_criticalsections: * c-basic-offset: 4 * tab-width: 4 * End: + * vim:noexpandtab:sw=4:ts=4: */