Mercurial > hg > truffle
diff src/cpu/x86/vm/c1_Runtime1_x86.cpp @ 1434:72cfb36c6bb2
* enabled all jtt tests
* added proxy that counts jni calls
* honor hotspot stackshadowpages
* constant pool caching
* monitor enter/exit
* arithmetic stubs (frem, drem, ...)
* create stack values for debug info
* some doc
author | Lukas Stadler <lukas.stadler@oracle.com> |
---|---|
date | Thu, 30 Sep 2010 17:19:48 -0700 |
parents | abc670a709dc |
children | 8cfe3537a0d3 |
line wrap: on
line diff
--- a/src/cpu/x86/vm/c1_Runtime1_x86.cpp Thu Sep 16 19:42:20 2010 -0700 +++ b/src/cpu/x86/vm/c1_Runtime1_x86.cpp Thu Sep 30 17:19:48 2010 -0700 @@ -1830,94 +1830,203 @@ break; #endif // !SERIALGC - case c1x_unwind_exception_call_id: + case c1x_unwind_exception_call_id: { + // remove the frame from the stack + __ movptr(rsp, rbp); + __ pop(rbp); + // exception_oop is passed using ordinary java calling conventions + __ movptr(rax, j_rarg0); + + Label nonNullExceptionOop; + __ testptr(rax, rax); + __ jcc(Assembler::notZero, nonNullExceptionOop); { - // remove the frame from the stack - __ movptr(rsp, rbp); - __ pop(rbp); - // exception_oop is passed using ordinary java calling conventions - __ movptr(rax, j_rarg0); + __ enter(); + oop_maps = new OopMapSet(); + OopMap* oop_map = save_live_registers(sasm, 0); + int call_offset = __ call_RT(rax, noreg, (address)c1x_create_null_exception, 0); + oop_maps->add_gc_map(call_offset, oop_map); + __ leave(); + } + __ bind(nonNullExceptionOop); - Label nonNullExceptionOop; - __ testptr(rax, rax); - __ jcc(Assembler::notZero, nonNullExceptionOop); - { - __ enter(); - oop_maps = new OopMapSet(); - OopMap* oop_map = save_live_registers(sasm, 0); - int call_offset = __ call_RT(rax, noreg, (address)c1x_create_null_exception, 0); - oop_maps->add_gc_map(call_offset, oop_map); - __ leave(); - } - __ bind(nonNullExceptionOop); + __ set_info("unwind_exception", dont_gc_arguments); + // note: no stubframe since we are about to leave the current + // activation and we are calling a leaf VM function only. + generate_unwind_exception(sasm); + __ should_not_reach_here(); + break; + } - __ set_info("unwind_exception", dont_gc_arguments); - // note: no stubframe since we are about to leave the current - // activation and we are calling a leaf VM function only. - generate_unwind_exception(sasm); - __ should_not_reach_here(); + case c1x_handle_exception_id: { + StubFrame f(sasm, "c1x_handle_exception", dont_gc_arguments); + oop_maps = new OopMapSet(); + OopMap* oop_map = save_live_registers(sasm, 1, false); + c1x_generate_handle_exception(sasm, oop_maps, oop_map); + break; + } + + case c1x_global_implicit_null_id: { + __ push(rax); + __ push(rax); + // move saved fp to make space for the inserted return address + __ get_thread(rax); + __ movptr(rax, Address(rax, JavaThread::saved_exception_pc_offset())); + __ movptr(Address(rsp, HeapWordSize), rax); + __ pop(rax); + + { StubFrame f(sasm, "c1x_global_implicit_null_id", dont_gc_arguments); + oop_maps = generate_exception_throw(sasm, CAST_FROM_FN_PTR(address, throw_null_pointer_exception), false); } break; + } - case c1x_handle_exception_id: - { StubFrame f(sasm, "c1x_handle_exception", dont_gc_arguments); - oop_maps = new OopMapSet(); - OopMap* oop_map = save_live_registers(sasm, 1, false); - c1x_generate_handle_exception(sasm, oop_maps, oop_map); + case c1x_throw_div0_exception_id: { + __ push(rax); + __ push(rax); + // move saved fp to make space for the inserted return address + __ get_thread(rax); + __ movptr(rax, Address(rax, JavaThread::saved_exception_pc_offset())); + __ movptr(Address(rsp, HeapWordSize), rax); + __ pop(rax); + + { StubFrame f(sasm, "throw_div0_exception", dont_gc_arguments); + oop_maps = generate_exception_throw(sasm, CAST_FROM_FN_PTR(address, throw_div0_exception), false); } break; + } - case c1x_global_implicit_null_id: - { - __ push(rax); - __ push(rax); - // move saved fp to make space for the inserted return address - __ get_thread(rax); - __ movptr(rax, Address(rax, JavaThread::saved_exception_pc_offset())); - __ movptr(Address(rsp, HeapWordSize), rax); - __ pop(rax); + case c1x_slow_subtype_check_id: { + Label success; + Label miss; + + // TODO this should really be within the XirSnippets + __ check_klass_subtype_fast_path(j_rarg0, j_rarg1, j_rarg2, &success, &miss, NULL); + __ check_klass_subtype_slow_path(j_rarg0, j_rarg1, j_rarg2, j_rarg3, NULL, &miss); + + // fallthrough on success: + __ bind(success); + __ movptr(rax, 1); + __ ret(0); + + __ bind(miss); + __ movptr(rax, NULL_WORD); + __ ret(0); + break; + } - { StubFrame f(sasm, "c1x_global_implicit_null_id", dont_gc_arguments); - oop_maps = generate_exception_throw(sasm, CAST_FROM_FN_PTR(address, throw_null_pointer_exception), false); - } + case c1x_arithmetic_frem_id: { + __ subptr(rsp, 8); + __ movflt(Address(rsp, 0), xmm1); + __ fld_s(Address(rsp, 0)); + __ movflt(Address(rsp, 0), xmm0); + __ fld_s(Address(rsp, 0)); + Label L; + __ bind(L); + __ fprem(); + __ fwait(); + __ fnstsw_ax(); + __ testl(rax, 0x400); + __ jcc(Assembler::notZero, L); + __ fxch(1); + __ fpop(); + __ fstp_s(Address(rsp, 0)); + __ movflt(xmm0, Address(rsp, 0)); + __ addptr(rsp, 8); + __ ret(0); + break; + } + case c1x_arithmetic_drem_id: { + __ subptr(rsp, 8); + __ movdbl(Address(rsp, 0), xmm1); + __ fld_d(Address(rsp, 0)); + __ movdbl(Address(rsp, 0), xmm0); + __ fld_d(Address(rsp, 0)); + Label L; + __ bind(L); + __ fprem(); + __ fwait(); + __ fnstsw_ax(); + __ testl(rax, 0x400); + __ jcc(Assembler::notZero, L); + __ fxch(1); + __ fpop(); + __ fstp_d(Address(rsp, 0)); + __ movdbl(xmm0, Address(rsp, 0)); + __ addptr(rsp, 8); + __ ret(0); + break; + } + case c1x_monitorenter_id: { + Label slow_case; + + Register obj = j_rarg0; + Register lock = j_rarg1; + + Register scratch1 = rax; + Register scratch2 = rbx; + + // copied from LIR_Assembler::emit_lock + if (UseFastLocking) { + assert(BasicLock::displaced_header_offset_in_bytes() == 0, "lock_reg must point to the displaced header"); + __ lock_object(scratch1, obj, lock, scratch2, slow_case); + __ ret(0); } - break; - case c1x_throw_div0_exception_id: + __ bind(slow_case); { - __ push(rax); - __ push(rax); - // move saved fp to make space for the inserted return address - __ get_thread(rax); - __ movptr(rax, Address(rax, JavaThread::saved_exception_pc_offset())); - __ movptr(Address(rsp, HeapWordSize), rax); - __ pop(rax); + StubFrame f(sasm, "c1x_monitorenter", dont_gc_arguments); + OopMap* map = save_live_registers(sasm, 1, save_fpu_registers); + + // Called with store_parameter and not C abi + int call_offset = __ call_RT(noreg, noreg, CAST_FROM_FN_PTR(address, monitorenter), obj, lock); + + oop_maps = new OopMapSet(); + oop_maps->add_gc_map(call_offset, map); + restore_live_registers(sasm, save_fpu_registers); + } + __ ret(0); + break; + } + case c1x_monitorexit_id: { + Label slow_case; - { StubFrame f(sasm, "throw_div0_exception", dont_gc_arguments); - oop_maps = generate_exception_throw(sasm, CAST_FROM_FN_PTR(address, throw_div0_exception), false); - } + Register obj = j_rarg0; + Register lock = j_rarg1; + + // needed in rax later on... + Register lock2 = rax; + __ mov(lock2, lock); + Register scratch1 = rbx; + + // copied from LIR_Assembler::emit_lock + if (UseFastLocking) { + assert(BasicLock::displaced_header_offset_in_bytes() == 0, "lock_reg must point to the displaced header"); + __ unlock_object(scratch1, obj, lock2, slow_case); + __ ret(0); } - break; - case c1x_slow_subtype_check_id: + __ bind(slow_case); { - Label success; - Label miss; + StubFrame f(sasm, "c1x_monitorexit", dont_gc_arguments); + OopMap* map = save_live_registers(sasm, 2, save_fpu_registers); - // TODO this should really be within the XirSnippets - __ check_klass_subtype_fast_path(j_rarg0, j_rarg1, j_rarg2, &success, &miss, NULL); - __ check_klass_subtype_slow_path(j_rarg0, j_rarg1, j_rarg2, j_rarg3, NULL, &miss); + // note: really a leaf routine but must setup last java sp + // => use call_RT for now (speed can be improved by + // doing last java sp setup manually) + int call_offset = __ call_RT(noreg, noreg, CAST_FROM_FN_PTR(address, monitorexit), lock); - // fallthrough on success: - __ bind(success); - __ movptr(rax, 1); - __ ret(0); + oop_maps = new OopMapSet(); + oop_maps->add_gc_map(call_offset, map); + restore_live_registers(sasm, save_fpu_registers); + } + __ ret(0); + break; + } - __ bind(miss); - __ movptr(rax, NULL_WORD); - __ ret(0); - } - break; + + + default: { StubFrame f(sasm, "unimplemented entry", dont_gc_arguments); __ movptr(rax, (int)id);