68 assert(__ pc() - base <= to_interp_stub_size(), "wrong stub size"); 69 70 // Update current stubs pointer and restore code_end. 71 __ end_a_stub(); 72 return base; 73 } 74 #undef __ 75 76 int CompiledStaticCall::to_interp_stub_size() { 77 // This doesn't need to be accurate but it must be larger or equal to 78 // the real size of the stub. 79 return (NativeMovConstReg::instruction_size + // sethi/setlo; 80 NativeJump::instruction_size); // sethi; jmp; nop 81 } 82 83 // Relocation entries for call stub, compiled java to interpreter. 84 int CompiledStaticCall::reloc_to_interp_stub() { 85 return 10; // 4 in emit_java_to_interp + 1 in Java_Static_Call 86 } 87 88 void CompiledStaticCall::set_to_interpreted(methodHandle callee, address entry) { 89 address stub = find_stub(); 90 guarantee(stub != NULL, "stub not found"); 91 92 if (TraceICs) { 93 ResourceMark rm; 94 tty->print_cr("CompiledStaticCall@" INTPTR_FORMAT ": set_to_interpreted %s", 95 p2i(instruction_address()), 96 callee->name_and_sig_as_C_string()); 97 } 98 99 // Creation also verifies the object. 100 NativeMovConstReg* method_holder = nativeMovConstReg_at(stub); 101 NativeJump* jump = nativeJump_at(method_holder->next_instruction_address()); 102 103 #ifdef ASSERT 104 // read the value once 105 intptr_t data = method_holder->data(); 106 address destination = jump->jump_destination(); 107 assert(data == 0 || data == (intptr_t)callee(), 108 "a) MT-unsafe modification of inline cache"); 109 assert(destination == (address)-1 || destination == entry, 110 "b) MT-unsafe modification of inline cache"); 111 #endif 112 113 // Update stub. 114 method_holder->set_data((intptr_t)callee()); 115 jump->set_jump_destination(entry); 116 117 // Update jump to call. 118 set_destination_mt_safe(stub); 119 } 120 121 void CompiledStaticCall::set_stub_to_clean(static_stub_Relocation* static_stub) { 122 assert (CompiledIC_lock->is_locked() || SafepointSynchronize::is_at_safepoint(), "mt unsafe call"); 123 // Reset stub. 124 address stub = static_stub->addr(); 125 assert(stub != NULL, "stub not found"); 126 // Creation also verifies the object. 127 NativeMovConstReg* method_holder = nativeMovConstReg_at(stub); 128 NativeJump* jump = nativeJump_at(method_holder->next_instruction_address()); 129 method_holder->set_data(0); 130 jump->set_jump_destination((address)-1); 131 } 132 133 //----------------------------------------------------------------------------- 134 // Non-product mode code 135 #ifndef PRODUCT 136 137 void CompiledStaticCall::verify() { 138 // Verify call. 139 NativeCall::verify(); 140 if (os::is_MP()) { 141 verify_alignment(); 142 } 143 144 // Verify stub. 145 address stub = find_stub(); 146 assert(stub != NULL, "no stub found for static call"); 147 // Creation also verifies the object. 148 NativeMovConstReg* method_holder = nativeMovConstReg_at(stub); 149 NativeJump* jump = nativeJump_at(method_holder->next_instruction_address()); 150 151 // Verify state. 152 assert(is_clean() || is_call_to_compiled() || is_call_to_interpreted(), "sanity check"); 153 } 154 155 #endif // !PRODUCT | 68 assert(__ pc() - base <= to_interp_stub_size(), "wrong stub size"); 69 70 // Update current stubs pointer and restore code_end. 71 __ end_a_stub(); 72 return base; 73 } 74 #undef __ 75 76 int CompiledStaticCall::to_interp_stub_size() { 77 // This doesn't need to be accurate but it must be larger or equal to 78 // the real size of the stub. 79 return (NativeMovConstReg::instruction_size + // sethi/setlo; 80 NativeJump::instruction_size); // sethi; jmp; nop 81 } 82 83 // Relocation entries for call stub, compiled java to interpreter. 84 int CompiledStaticCall::reloc_to_interp_stub() { 85 return 10; // 4 in emit_java_to_interp + 1 in Java_Static_Call 86 } 87 88 void CompiledDirectStaticCall::set_to_interpreted(const methodHandle& callee, address entry) { 89 address stub = find_stub(/*is_aot*/ false); 90 guarantee(stub != NULL, "stub not found"); 91 92 if (TraceICs) { 93 ResourceMark rm; 94 tty->print_cr("CompiledDirectStaticCall@" INTPTR_FORMAT ": set_to_interpreted %s", 95 p2i(instruction_address()), 96 callee->name_and_sig_as_C_string()); 97 } 98 99 // Creation also verifies the object. 100 NativeMovConstReg* method_holder = nativeMovConstReg_at(stub); 101 NativeJump* jump = nativeJump_at(method_holder->next_instruction_address()); 102 103 #ifdef ASSERT 104 // read the value once 105 intptr_t data = method_holder->data(); 106 address destination = jump->jump_destination(); 107 assert(data == 0 || data == (intptr_t)callee(), 108 "a) MT-unsafe modification of inline cache"); 109 assert(destination == (address)-1 || destination == entry, 110 "b) MT-unsafe modification of inline cache"); 111 #endif 112 113 // Update stub. 114 method_holder->set_data((intptr_t)callee()); 115 jump->set_jump_destination(entry); 116 117 // Update jump to call. 118 set_destination_mt_safe(stub); 119 } 120 121 void CompiledDirectStaticCall::set_stub_to_clean(static_stub_Relocation* static_stub) { 122 assert (CompiledIC_lock->is_locked() || SafepointSynchronize::is_at_safepoint(), "mt unsafe call"); 123 // Reset stub. 124 address stub = static_stub->addr(); 125 assert(stub != NULL, "stub not found"); 126 // Creation also verifies the object. 127 NativeMovConstReg* method_holder = nativeMovConstReg_at(stub); 128 NativeJump* jump = nativeJump_at(method_holder->next_instruction_address()); 129 method_holder->set_data(0); 130 jump->set_jump_destination((address)-1); 131 } 132 133 //----------------------------------------------------------------------------- 134 // Non-product mode code 135 #ifndef PRODUCT 136 137 void CompiledDirectStaticCall::verify() { 138 // Verify call. 139 _call->verify(); 140 if (os::is_MP()) { 141 _call->verify_alignment(); 142 } 143 144 // Verify stub. 145 address stub = find_stub(/*is_aot*/ false); 146 assert(stub != NULL, "no stub found for static call"); 147 // Creation also verifies the object. 148 NativeMovConstReg* method_holder = nativeMovConstReg_at(stub); 149 NativeJump* jump = nativeJump_at(method_holder->next_instruction_address()); 150 151 // Verify state. 152 assert(is_clean() || is_call_to_compiled() || is_call_to_interpreted(), "sanity check"); 153 } 154 155 #endif // !PRODUCT |