< prev index next >

src/hotspot/cpu/x86/stubGenerator_x86_32.cpp

Print this page

 412     { Label L;
 413       __ testptr(exception_oop, exception_oop);
 414       __ jcc(Assembler::notEqual, L);
 415       __ stop("StubRoutines::forward exception: no pending exception (2)");
 416       __ bind(L);
 417     }
 418 #endif
 419 
 420     // Verify that there is really a valid exception in RAX.
 421     __ verify_oop(exception_oop);
 422 
 423     // continue at exception handler (return address removed)
 424     // rax: exception
 425     // rbx: exception handler
 426     // rdx: throwing pc
 427     __ jmp(handler_addr);
 428 
 429     return start;
 430   }
 431 
 432 
 433   //----------------------------------------------------------------------------------------------------
 434   // Implementation of int32_t atomic_xchg(int32_t exchange_value, volatile int32_t* dest)
 435   // used by Atomic::xchg(volatile int32_t* dest, int32_t exchange_value)
 436   //
 437   // xchg exists as far back as 8086, lock needed for MP only
 438   // Stack layout immediately after call:
 439   //
 440   // 0 [ret addr ] <--- rsp
 441   // 1 [  ex     ]
 442   // 2 [  dest   ]
 443   //
 444   // Result:   *dest <- ex, return (old *dest)
 445   //
 446   // Note: win32 does not currently use this code
 447 
 448   address generate_atomic_xchg() {
 449     StubCodeMark mark(this, "StubRoutines", "atomic_xchg");
 450     address start = __ pc();
 451 
 452     __ push(rdx);
 453     Address exchange(rsp, 2 * wordSize);
 454     Address dest_addr(rsp, 3 * wordSize);
 455     __ movl(rax, exchange);
 456     __ movptr(rdx, dest_addr);
 457     __ xchgl(rax, Address(rdx, 0));
 458     __ pop(rdx);
 459     __ ret(0);
 460 
 461     return start;
 462   }
 463 
 464   //----------------------------------------------------------------------------------------------------
 465   // Support for void verify_mxcsr()
 466   //
 467   // This routine is used with -Xcheck:jni to verify that native
 468   // JNI code does not return to Java code without restoring the
 469   // MXCSR register to our expected state.
 470 
 471 
 472   address generate_verify_mxcsr() {
 473     StubCodeMark mark(this, "StubRoutines", "verify_mxcsr");
 474     address start = __ pc();
 475 
 476     const Address mxcsr_save(rsp, 0);
 477 
 478     if (CheckJNICalls && UseSSE > 0 ) {
 479       Label ok_ret;
 480       ExternalAddress mxcsr_std(StubRoutines::addr_mxcsr_std());
 481       __ push(rax);
 482       __ subptr(rsp, wordSize);      // allocate a temp location
 483       __ stmxcsr(mxcsr_save);

3780     StubRoutines::_fpu_subnormal_bias2[2]= 0x7bff;
3781   }
3782 
3783   //---------------------------------------------------------------------------
3784   // Initialization
3785 
3786   void generate_initial() {
3787     // Generates all stubs and initializes the entry points
3788 
3789     //------------------------------------------------------------------------------------------------------------------------
3790     // entry points that exist in all platforms
3791     // Note: This is code that could be shared among different platforms - however the benefit seems to be smaller than
3792     //       the disadvantage of having a much more complicated generator structure. See also comment in stubRoutines.hpp.
3793     StubRoutines::_forward_exception_entry      = generate_forward_exception();
3794 
3795     StubRoutines::_call_stub_entry              =
3796       generate_call_stub(StubRoutines::_call_stub_return_address);
3797     // is referenced by megamorphic call
3798     StubRoutines::_catch_exception_entry        = generate_catch_exception();
3799 
3800     // These are currently used by Solaris/Intel
3801     StubRoutines::_atomic_xchg_entry            = generate_atomic_xchg();
3802 
3803     // platform dependent
3804     create_control_words();
3805 
3806     StubRoutines::x86::_verify_mxcsr_entry                 = generate_verify_mxcsr();
3807     StubRoutines::x86::_verify_fpu_cntrl_wrd_entry         = generate_verify_fpu_cntrl_wrd();
3808     StubRoutines::_d2i_wrapper                              = generate_d2i_wrapper(T_INT,
3809                                                                                    CAST_FROM_FN_PTR(address, SharedRuntime::d2i));
3810     StubRoutines::_d2l_wrapper                              = generate_d2i_wrapper(T_LONG,
3811                                                                                    CAST_FROM_FN_PTR(address, SharedRuntime::d2l));
3812 
3813     // Build this early so it's available for the interpreter
3814     StubRoutines::_throw_StackOverflowError_entry          = generate_throw_exception("StackOverflowError throw_exception",
3815                                                                                       CAST_FROM_FN_PTR(address, SharedRuntime::throw_StackOverflowError));
3816     StubRoutines::_throw_delayed_StackOverflowError_entry  = generate_throw_exception("delayed StackOverflowError throw_exception",
3817                                                                                       CAST_FROM_FN_PTR(address, SharedRuntime::throw_delayed_StackOverflowError));
3818 
3819     if (UseCRC32Intrinsics) {
3820       // set table address before stub generation which use it
3821       StubRoutines::_crc_table_adr = (address)StubRoutines::x86::_crc_table;
3822       StubRoutines::_updateBytesCRC32 = generate_updateBytesCRC32();

 412     { Label L;
 413       __ testptr(exception_oop, exception_oop);
 414       __ jcc(Assembler::notEqual, L);
 415       __ stop("StubRoutines::forward exception: no pending exception (2)");
 416       __ bind(L);
 417     }
 418 #endif
 419 
 420     // Verify that there is really a valid exception in RAX.
 421     __ verify_oop(exception_oop);
 422 
 423     // continue at exception handler (return address removed)
 424     // rax: exception
 425     // rbx: exception handler
 426     // rdx: throwing pc
 427     __ jmp(handler_addr);
 428 
 429     return start;
 430   }
 431 
































 432   //----------------------------------------------------------------------------------------------------
 433   // Support for void verify_mxcsr()
 434   //
 435   // This routine is used with -Xcheck:jni to verify that native
 436   // JNI code does not return to Java code without restoring the
 437   // MXCSR register to our expected state.
 438 
 439 
 440   address generate_verify_mxcsr() {
 441     StubCodeMark mark(this, "StubRoutines", "verify_mxcsr");
 442     address start = __ pc();
 443 
 444     const Address mxcsr_save(rsp, 0);
 445 
 446     if (CheckJNICalls && UseSSE > 0 ) {
 447       Label ok_ret;
 448       ExternalAddress mxcsr_std(StubRoutines::addr_mxcsr_std());
 449       __ push(rax);
 450       __ subptr(rsp, wordSize);      // allocate a temp location
 451       __ stmxcsr(mxcsr_save);

3748     StubRoutines::_fpu_subnormal_bias2[2]= 0x7bff;
3749   }
3750 
3751   //---------------------------------------------------------------------------
3752   // Initialization
3753 
3754   void generate_initial() {
3755     // Generates all stubs and initializes the entry points
3756 
3757     //------------------------------------------------------------------------------------------------------------------------
3758     // entry points that exist in all platforms
3759     // Note: This is code that could be shared among different platforms - however the benefit seems to be smaller than
3760     //       the disadvantage of having a much more complicated generator structure. See also comment in stubRoutines.hpp.
3761     StubRoutines::_forward_exception_entry      = generate_forward_exception();
3762 
3763     StubRoutines::_call_stub_entry              =
3764       generate_call_stub(StubRoutines::_call_stub_return_address);
3765     // is referenced by megamorphic call
3766     StubRoutines::_catch_exception_entry        = generate_catch_exception();
3767 



3768     // platform dependent
3769     create_control_words();
3770 
3771     StubRoutines::x86::_verify_mxcsr_entry                 = generate_verify_mxcsr();
3772     StubRoutines::x86::_verify_fpu_cntrl_wrd_entry         = generate_verify_fpu_cntrl_wrd();
3773     StubRoutines::_d2i_wrapper                              = generate_d2i_wrapper(T_INT,
3774                                                                                    CAST_FROM_FN_PTR(address, SharedRuntime::d2i));
3775     StubRoutines::_d2l_wrapper                              = generate_d2i_wrapper(T_LONG,
3776                                                                                    CAST_FROM_FN_PTR(address, SharedRuntime::d2l));
3777 
3778     // Build this early so it's available for the interpreter
3779     StubRoutines::_throw_StackOverflowError_entry          = generate_throw_exception("StackOverflowError throw_exception",
3780                                                                                       CAST_FROM_FN_PTR(address, SharedRuntime::throw_StackOverflowError));
3781     StubRoutines::_throw_delayed_StackOverflowError_entry  = generate_throw_exception("delayed StackOverflowError throw_exception",
3782                                                                                       CAST_FROM_FN_PTR(address, SharedRuntime::throw_delayed_StackOverflowError));
3783 
3784     if (UseCRC32Intrinsics) {
3785       // set table address before stub generation which use it
3786       StubRoutines::_crc_table_adr = (address)StubRoutines::x86::_crc_table;
3787       StubRoutines::_updateBytesCRC32 = generate_updateBytesCRC32();
< prev index next >