Skip to content

Commit 48bbc95

Browse files
committed
8371388: [BACKOUT] JDK-8365047: Remove exception handler stub code in C2
Reviewed-by: chagedorn, epeter
1 parent 205a163 commit 48bbc95

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

41 files changed

+301
-353
lines changed

src/hotspot/cpu/aarch64/aarch64.ad

Lines changed: 28 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
//
22
// Copyright (c) 2003, 2025, Oracle and/or its affiliates. All rights reserved.
33
// Copyright (c) 2014, 2024, Red Hat, Inc. All rights reserved.
4-
// Copyright 2025 Arm Limited and/or its affiliates.
54
// DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
65
//
76
// This code is free software; you can redistribute it and/or modify it
@@ -1195,10 +1194,15 @@ class HandlerImpl {
11951194

11961195
public:
11971196

1197+
static int emit_exception_handler(C2_MacroAssembler *masm);
11981198
static int emit_deopt_handler(C2_MacroAssembler* masm);
11991199

1200+
static uint size_exception_handler() {
1201+
return MacroAssembler::far_codestub_branch_size();
1202+
}
1203+
12001204
static uint size_deopt_handler() {
1201-
// count one branch instruction and one far call instruction sequence
1205+
// count one adr and one far branch instruction
12021206
return NativeInstruction::instruction_size + MacroAssembler::far_codestub_branch_size();
12031207
}
12041208
};
@@ -2257,6 +2261,25 @@ uint MachUEPNode::size(PhaseRegAlloc* ra_) const
22572261

22582262
//=============================================================================
22592263

2264+
// Emit exception handler code.
2265+
int HandlerImpl::emit_exception_handler(C2_MacroAssembler* masm)
2266+
{
2267+
// mov rscratch1 #exception_blob_entry_point
2268+
// br rscratch1
2269+
// Note that the code buffer's insts_mark is always relative to insts.
2270+
// That's why we must use the macroassembler to generate a handler.
2271+
address base = __ start_a_stub(size_exception_handler());
2272+
if (base == nullptr) {
2273+
ciEnv::current()->record_failure("CodeCache is full");
2274+
return 0; // CodeBuffer::expand failed
2275+
}
2276+
int offset = __ offset();
2277+
__ far_jump(RuntimeAddress(OptoRuntime::exception_blob()->entry_point()));
2278+
assert(__ offset() - offset <= (int) size_exception_handler(), "overflow");
2279+
__ end_a_stub();
2280+
return offset;
2281+
}
2282+
22602283
// Emit deopt handler code.
22612284
int HandlerImpl::emit_deopt_handler(C2_MacroAssembler* masm)
22622285
{
@@ -2267,18 +2290,14 @@ int HandlerImpl::emit_deopt_handler(C2_MacroAssembler* masm)
22672290
ciEnv::current()->record_failure("CodeCache is full");
22682291
return 0; // CodeBuffer::expand failed
22692292
}
2270-
22712293
int offset = __ offset();
2272-
Label start;
2273-
__ bind(start);
2274-
__ far_call(RuntimeAddress(SharedRuntime::deopt_blob()->unpack()));
22752294

2276-
int entry_offset = __ offset();
2277-
__ b(start);
2295+
__ adr(lr, __ pc());
2296+
__ far_jump(RuntimeAddress(SharedRuntime::deopt_blob()->unpack()));
22782297

22792298
assert(__ offset() - offset == (int) size_deopt_handler(), "overflow");
22802299
__ end_a_stub();
2281-
return entry_offset;
2300+
return offset;
22822301
}
22832302

22842303
// REQUIRED MATCHER CODE

src/hotspot/cpu/aarch64/c1_LIRAssembler_aarch64.cpp

Lines changed: 3 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -449,18 +449,12 @@ int LIR_Assembler::emit_deopt_handler() {
449449

450450
int offset = code_offset();
451451

452-
Label start;
453-
__ bind(start);
454-
455-
__ far_call(RuntimeAddress(SharedRuntime::deopt_blob()->unpack()));
456-
457-
int entry_offset = __ offset();
458-
__ b(start);
459-
452+
__ adr(lr, pc());
453+
__ far_jump(RuntimeAddress(SharedRuntime::deopt_blob()->unpack()));
460454
guarantee(code_offset() - offset <= deopt_handler_size(), "overflow");
461455
__ end_a_stub();
462456

463-
return entry_offset;
457+
return offset;
464458
}
465459

466460
void LIR_Assembler::add_debug_info_for_branch(address adr, CodeEmitInfo* info) {

src/hotspot/cpu/aarch64/c1_LIRAssembler_aarch64.hpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,7 @@ friend class ArrayCopyStub;
7171
// CompiledDirectCall::to_trampoline_stub_size()
7272
_call_stub_size = 13 * NativeInstruction::instruction_size,
7373
_exception_handler_size = DEBUG_ONLY(1*K) NOT_DEBUG(175),
74-
_deopt_handler_size = 4 * NativeInstruction::instruction_size
74+
_deopt_handler_size = 7 * NativeInstruction::instruction_size
7575
};
7676

7777
public:

src/hotspot/cpu/aarch64/nativeInst_aarch64.cpp

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -394,6 +394,12 @@ void NativePostCallNop::make_deopt() {
394394
NativeDeoptInstruction::insert(addr_at(0));
395395
}
396396

397+
#ifdef ASSERT
398+
static bool is_movk_to_zr(uint32_t insn) {
399+
return ((insn & 0xffe0001f) == 0xf280001f);
400+
}
401+
#endif
402+
397403
bool NativePostCallNop::patch(int32_t oopmap_slot, int32_t cb_offset) {
398404
if (((oopmap_slot & 0xff) != oopmap_slot) || ((cb_offset & 0xffffff) != cb_offset)) {
399405
return false; // cannot encode

src/hotspot/cpu/aarch64/nativeInst_aarch64.hpp

Lines changed: 6 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -526,24 +526,14 @@ inline NativeLdSt* NativeLdSt_at(address addr) {
526526
// can store an offset from the initial nop to the nmethod.
527527

528528
class NativePostCallNop: public NativeInstruction {
529-
private:
530-
static bool is_movk_to_zr(uint32_t insn) {
531-
return ((insn & 0xffe0001f) == 0xf280001f);
532-
}
533-
534529
public:
535530
bool check() const {
536-
// Check the first instruction is NOP.
537-
if (is_nop()) {
538-
uint32_t insn = *(uint32_t*)addr_at(4);
539-
// Check next instruction is MOVK zr, xx.
540-
// These instructions only ever appear together in a post-call
541-
// NOP, so it's unnecessary to check that the third instruction is
542-
// a MOVK as well.
543-
return is_movk_to_zr(insn);
544-
}
545-
546-
return false;
531+
uint64_t insns = *(uint64_t*)addr_at(0);
532+
// Check for two instructions: nop; movk zr, xx
533+
// These instructions only ever appear together in a post-call
534+
// NOP, so it's unnecessary to check that the third instruction is
535+
// a MOVK as well.
536+
return (insns & 0xffe0001fffffffff) == 0xf280001fd503201f;
547537
}
548538

549539
bool decode(int32_t& oopmap_slot, int32_t& cb_offset) const {

src/hotspot/cpu/aarch64/runtime_aarch64.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -260,6 +260,8 @@ UncommonTrapBlob* OptoRuntime::generate_uncommon_trap_blob() {
260260

261261
//------------------------------generate_exception_blob---------------------------
262262
// creates exception blob at the end
263+
// Using exception blob, this code is jumped from a compiled method.
264+
// (see emit_exception_handler in aarch64.ad file)
263265
//
264266
// Given an exception pc at a call we call into the runtime for the
265267
// handler in this method. This handler might merely restore state

src/hotspot/cpu/arm/arm.ad

Lines changed: 33 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -105,8 +105,14 @@ class HandlerImpl {
105105

106106
public:
107107

108+
static int emit_exception_handler(C2_MacroAssembler *masm);
108109
static int emit_deopt_handler(C2_MacroAssembler* masm);
109110

111+
static uint size_exception_handler() {
112+
return ( 3 * 4 );
113+
}
114+
115+
110116
static uint size_deopt_handler() {
111117
return ( 9 * 4 );
112118
}
@@ -870,6 +876,26 @@ uint MachUEPNode::size(PhaseRegAlloc *ra_) const {
870876

871877
//=============================================================================
872878

879+
// Emit exception handler code.
880+
int HandlerImpl::emit_exception_handler(C2_MacroAssembler* masm) {
881+
address base = __ start_a_stub(size_exception_handler());
882+
if (base == nullptr) {
883+
ciEnv::current()->record_failure("CodeCache is full");
884+
return 0; // CodeBuffer::expand failed
885+
}
886+
887+
int offset = __ offset();
888+
889+
// OK to trash LR, because exception blob will kill it
890+
__ jump(OptoRuntime::exception_blob()->entry_point(), relocInfo::runtime_call_type, LR_tmp);
891+
892+
assert(__ offset() - offset <= (int) size_exception_handler(), "overflow");
893+
894+
__ end_a_stub();
895+
896+
return offset;
897+
}
898+
873899
int HandlerImpl::emit_deopt_handler(C2_MacroAssembler* masm) {
874900
// Can't use any of the current frame's registers as we may have deopted
875901
// at a poll and everything can be live.
@@ -880,26 +906,19 @@ int HandlerImpl::emit_deopt_handler(C2_MacroAssembler* masm) {
880906
}
881907

882908
int offset = __ offset();
909+
address deopt_pc = __ pc();
883910

884-
Label start;
885-
__ bind(start);
886-
911+
__ sub(SP, SP, wordSize); // make room for saved PC
912+
__ push(LR); // save LR that may be live when we get here
913+
__ mov_relative_address(LR, deopt_pc);
914+
__ str(LR, Address(SP, wordSize)); // save deopt PC
915+
__ pop(LR); // restore LR
887916
__ jump(SharedRuntime::deopt_blob()->unpack(), relocInfo::runtime_call_type, noreg);
888917

889-
int entry_offset = __ offset();
890-
address deopt_pc = __ pc();
891-
// Preserve R0 and reserve space for the address of the entry point
892-
__ push(RegisterSet(R0) | RegisterSet(R1));
893-
// Store the entry point address
894-
__ mov_relative_address(R0, deopt_pc);
895-
__ str(R0, Address(SP, wordSize));
896-
__ pop(R0); // restore R0
897-
__ b(start);
898-
899918
assert(__ offset() - offset <= (int) size_deopt_handler(), "overflow");
900919

901920
__ end_a_stub();
902-
return entry_offset;
921+
return offset;
903922
}
904923

905924
bool Matcher::match_rule_supported(int opcode) {

src/hotspot/cpu/arm/c1_LIRAssembler_arm.cpp

Lines changed: 2 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -272,20 +272,14 @@ int LIR_Assembler::emit_deopt_handler() {
272272

273273
int offset = code_offset();
274274

275-
Label start;
276-
__ bind(start);
277-
278-
__ jump(SharedRuntime::deopt_blob()->unpack(), relocInfo::runtime_call_type, noreg);
279-
280-
int entry_offset = __ offset();
281275
__ mov_relative_address(LR, __ pc());
282276
__ push(LR); // stub expects LR to be saved
283-
__ b(start);
277+
__ jump(SharedRuntime::deopt_blob()->unpack(), relocInfo::runtime_call_type, noreg);
284278

285279
assert(code_offset() - offset <= deopt_handler_size(), "overflow");
286280
__ end_a_stub();
287281

288-
return entry_offset;
282+
return offset;
289283
}
290284

291285

src/hotspot/cpu/arm/c1_LIRAssembler_arm.hpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -54,7 +54,7 @@
5454
enum {
5555
_call_stub_size = 16,
5656
_exception_handler_size = PRODUCT_ONLY(68) NOT_PRODUCT(68+60),
57-
_deopt_handler_size = 20
57+
_deopt_handler_size = 16
5858
};
5959

6060
public:

src/hotspot/cpu/arm/runtime_arm.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -182,6 +182,8 @@ UncommonTrapBlob* OptoRuntime::generate_uncommon_trap_blob() {
182182

183183
//------------------------------ generate_exception_blob ---------------------------
184184
// creates exception blob at the end
185+
// Using exception blob, this code is jumped from a compiled method.
186+
// (see emit_exception_handler in sparc.ad file)
185187
//
186188
// Given an exception pc at a call we call into the runtime for the
187189
// handler in this method. This handler might merely restore state

0 commit comments

Comments
 (0)