Skip to content

Commit 7b4a856

Browse files

File tree

9 files changed

+220
-50
lines changed

9 files changed

+220
-50
lines changed
 

‎src/hotspot/share/cds/heapShared.cpp

+69
Original file line numberDiff line numberDiff line change
@@ -161,6 +161,14 @@ GrowableArrayCHeap<oop, mtClassShared>* HeapShared::_trace = nullptr;
161161
GrowableArrayCHeap<const char*, mtClassShared>* HeapShared::_context = nullptr;
162162
OopHandle HeapShared::_roots;
163163
OopHandle HeapShared::_scratch_basic_type_mirrors[T_VOID+1];
164+
165+
OopHandle HeapShared::_scratch_null_ptr_exception_instance;
166+
OopHandle HeapShared::_scratch_arithmetic_exception_instance;
167+
OopHandle HeapShared::_scratch_virtual_machine_error_instance;
168+
OopHandle HeapShared::_scratch_array_index_oob_exception_instance;
169+
OopHandle HeapShared::_scratch_array_store_exception_instance;
170+
OopHandle HeapShared::_scratch_class_cast_exception_instance;
171+
164172
MetaspaceObjToOopHandleTable* HeapShared::_scratch_java_mirror_table = nullptr;
165173
MetaspaceObjToOopHandleTable* HeapShared::_scratch_references_table = nullptr;
166174
ClassLoaderData* HeapShared::_saved_java_platform_loader_data = nullptr;
@@ -465,6 +473,27 @@ void HeapShared::init_scratch_objects(TRAPS) {
465473
_scratch_references_table = new (mtClass)MetaspaceObjToOopHandleTable();
466474
}
467475

476+
void HeapShared::init_scratch_exceptions(TRAPS) {
477+
oop instance = nullptr;
478+
479+
instance = java_lang_Throwable::create_exception_instance(vmSymbols::java_lang_NullPointerException(), CHECK);
480+
_scratch_null_ptr_exception_instance = OopHandle(Universe::vm_global(), instance);
481+
482+
instance = java_lang_Throwable::create_exception_instance(vmSymbols::java_lang_ArithmeticException(), CHECK);
483+
_scratch_arithmetic_exception_instance = OopHandle(Universe::vm_global(), instance);
484+
485+
instance = java_lang_Throwable::create_exception_instance(vmSymbols::java_lang_VirtualMachineError(), CHECK);
486+
_scratch_virtual_machine_error_instance = OopHandle(Universe::vm_global(), instance);
487+
488+
instance = java_lang_Throwable::create_exception_instance(vmSymbols::java_lang_ArrayIndexOutOfBoundsException(), CHECK);
489+
_scratch_array_index_oob_exception_instance = OopHandle(Universe::vm_global(), instance);
490+
491+
instance = java_lang_Throwable::create_exception_instance(vmSymbols::java_lang_ArrayStoreException(), CHECK);
492+
_scratch_array_store_exception_instance = OopHandle(Universe::vm_global(), instance);
493+
494+
instance = java_lang_Throwable::create_exception_instance(vmSymbols::java_lang_ClassCastException(), CHECK);
495+
_scratch_class_cast_exception_instance = OopHandle(Universe::vm_global(), instance);
496+
}
468497
// Given java_mirror that represents a (primitive or reference) type T,
469498
// return the "scratch" version that represents the same type T.
470499
// Note that if java_mirror will be returned if it's already a
@@ -646,6 +675,45 @@ void HeapShared::archive_strings() {
646675
StringTable::set_shared_strings_array_index(append_root(shared_strings_array));
647676
}
648677

678+
void HeapShared::archive_exception_instances() {
679+
{
680+
oop m = _scratch_null_ptr_exception_instance.resolve();
681+
bool success = archive_reachable_objects_from(1, _default_subgraph_info, m /*Universe::null_ptr_exception_instance()*/);
682+
assert(success, "sanity");
683+
Universe::set_archived_null_ptr_exception_instance_index(append_root(m));
684+
}
685+
{
686+
oop m = _scratch_arithmetic_exception_instance.resolve();
687+
bool success = archive_reachable_objects_from(1, _default_subgraph_info, m /*Universe::arithmetic_exception_instance()*/);
688+
assert(success, "sanity");
689+
Universe::set_archived_arithmetic_exception_instance_index(append_root(m));
690+
}
691+
{
692+
oop m = _scratch_virtual_machine_error_instance.resolve();
693+
bool success = archive_reachable_objects_from(1, _default_subgraph_info, m /*Universe::virtual_machine_error_instance()*/);
694+
assert(success, "sanity");
695+
Universe::set_archived_virtual_machine_error_instance_index(append_root(m));
696+
}
697+
{
698+
oop m = _scratch_array_index_oob_exception_instance.resolve();
699+
bool success = archive_reachable_objects_from(1, _default_subgraph_info, m /*Universe::array_index_oob_exception_instance()*/);
700+
assert(success, "sanity");
701+
Universe::set_archived_array_index_oob_exception_instance_index(append_root(m));
702+
}
703+
{
704+
oop m = _scratch_array_store_exception_instance.resolve();
705+
bool success = archive_reachable_objects_from(1, _default_subgraph_info, m /*Universe::array_store_exception_instance()*/);
706+
assert(success, "sanity");
707+
Universe::set_archived_array_store_exception_instance_index(append_root(m));
708+
}
709+
{
710+
oop m = _scratch_class_cast_exception_instance.resolve();
711+
bool success = archive_reachable_objects_from(1, _default_subgraph_info, m /*Universe::class_cast_exception_instance()*/);
712+
assert(success, "sanity");
713+
Universe::set_archived_class_cast_exception_instance_index(append_root(m));
714+
}
715+
}
716+
649717
void HeapShared::mark_native_pointers(oop orig_obj) {
650718
if (java_lang_Class::is_instance(orig_obj)) {
651719
ArchiveHeapWriter::mark_native_pointer(orig_obj, java_lang_Class::klass_offset());
@@ -702,6 +770,7 @@ void HeapShared::copy_special_objects() {
702770
init_seen_objects_table();
703771
archive_java_mirrors();
704772
archive_strings();
773+
archive_exception_instances();
705774
delete_seen_objects_table();
706775
}
707776

‎src/hotspot/share/cds/heapShared.hpp

+9
Original file line numberDiff line numberDiff line change
@@ -282,6 +282,13 @@ class HeapShared: AllStatic {
282282
static OopHandle _roots;
283283
static int _permobj_segments;
284284
static OopHandle _scratch_basic_type_mirrors[T_VOID+1];
285+
static OopHandle _scratch_null_ptr_exception_instance;
286+
static OopHandle _scratch_arithmetic_exception_instance;
287+
static OopHandle _scratch_virtual_machine_error_instance;
288+
static OopHandle _scratch_array_index_oob_exception_instance;
289+
static OopHandle _scratch_array_store_exception_instance;
290+
static OopHandle _scratch_class_cast_exception_instance;
291+
285292
static MetaspaceObjToOopHandleTable* _scratch_java_mirror_table;
286293
static MetaspaceObjToOopHandleTable* _scratch_references_table;
287294

@@ -346,6 +353,7 @@ class HeapShared: AllStatic {
346353
static bool can_mirror_be_used_in_subgraph(oop orig_java_mirror);
347354
static void archive_java_mirrors();
348355
static void archive_strings();
356+
static void archive_exception_instances();
349357
static void exit_on_error();
350358
public:
351359
static void reset_archived_object_states(TRAPS);
@@ -409,6 +417,7 @@ class HeapShared: AllStatic {
409417
static objArrayOop scratch_resolved_references(ConstantPool* src);
410418
static void add_scratch_resolved_references(ConstantPool* src, objArrayOop dest) NOT_CDS_JAVA_HEAP_RETURN;
411419
static void init_scratch_objects(TRAPS) NOT_CDS_JAVA_HEAP_RETURN;
420+
static void init_scratch_exceptions(TRAPS) NOT_CDS_JAVA_HEAP_RETURN;
412421
static void init_box_classes(TRAPS) NOT_CDS_JAVA_HEAP_RETURN;
413422
static void restore_loader_data() NOT_CDS_JAVA_HEAP_RETURN;
414423
static bool is_heap_region(int idx) {

‎src/hotspot/share/cds/metaspaceShared.cpp

+1
Original file line numberDiff line numberDiff line change
@@ -1521,6 +1521,7 @@ void MetaspaceShared::initialize_shared_spaces() {
15211521
ArchiveHeapLoader::finish_initialization();
15221522

15231523
CDS_JAVA_HEAP_ONLY(Universe::update_archived_basic_type_mirrors());
1524+
CDS_JAVA_HEAP_ONLY(Universe::update_exception_instances());
15241525

15251526
// Close the mapinfo file
15261527
static_mapinfo->close();

‎src/hotspot/share/ci/ciEnv.cpp

+6-32
Original file line numberDiff line numberDiff line change
@@ -372,29 +372,6 @@ void ciEnv::cache_dtrace_flags() {
372372
_dtrace_alloc_probes = DTraceAllocProbes;
373373
}
374374

375-
// ------------------------------------------------------------------
376-
// helper for lazy exception creation
377-
ciInstance* ciEnv::get_or_create_exception(jobject& handle, Symbol* name) {
378-
VM_ENTRY_MARK;
379-
if (handle == nullptr) {
380-
// Cf. universe.cpp, creation of Universe::_null_ptr_exception_instance.
381-
InstanceKlass* ik = SystemDictionary::find_instance_klass(THREAD, name, Handle(), Handle());
382-
jobject objh = nullptr;
383-
if (ik != nullptr) {
384-
oop obj = ik->allocate_instance(THREAD);
385-
if (!HAS_PENDING_EXCEPTION)
386-
objh = JNIHandles::make_global(Handle(THREAD, obj));
387-
}
388-
if (HAS_PENDING_EXCEPTION) {
389-
CLEAR_PENDING_EXCEPTION;
390-
} else {
391-
handle = objh;
392-
}
393-
}
394-
oop obj = JNIHandles::resolve(handle);
395-
return obj == nullptr? nullptr: get_object(obj)->as_instance();
396-
}
397-
398375
ciInstanceKlass* ciEnv::get_box_klass_for_primitive_type(BasicType type) {
399376
switch (type) {
400377
case T_BOOLEAN: return Boolean_klass();
@@ -414,25 +391,22 @@ ciInstanceKlass* ciEnv::get_box_klass_for_primitive_type(BasicType type) {
414391

415392
ciInstance* ciEnv::ArrayIndexOutOfBoundsException_instance() {
416393
if (_ArrayIndexOutOfBoundsException_instance == nullptr) {
417-
_ArrayIndexOutOfBoundsException_instance
418-
= get_or_create_exception(_ArrayIndexOutOfBoundsException_handle,
419-
vmSymbols::java_lang_ArrayIndexOutOfBoundsException());
394+
VM_ENTRY_MARK;
395+
_ArrayIndexOutOfBoundsException_instance = get_object(Universe::array_index_oob_exception_instance())->as_instance();
420396
}
421397
return _ArrayIndexOutOfBoundsException_instance;
422398
}
423399
ciInstance* ciEnv::ArrayStoreException_instance() {
424400
if (_ArrayStoreException_instance == nullptr) {
425-
_ArrayStoreException_instance
426-
= get_or_create_exception(_ArrayStoreException_handle,
427-
vmSymbols::java_lang_ArrayStoreException());
401+
VM_ENTRY_MARK;
402+
_ArrayStoreException_instance = get_object(Universe::array_store_exception_instance())->as_instance();
428403
}
429404
return _ArrayStoreException_instance;
430405
}
431406
ciInstance* ciEnv::ClassCastException_instance() {
432407
if (_ClassCastException_instance == nullptr) {
433-
_ClassCastException_instance
434-
= get_or_create_exception(_ClassCastException_handle,
435-
vmSymbols::java_lang_ClassCastException());
408+
VM_ENTRY_MARK;
409+
_ClassCastException_instance = get_object(Universe::class_cast_exception_instance())->as_instance();
436410
}
437411
return _ClassCastException_instance;
438412
}

‎src/hotspot/share/ci/ciEnv.hpp

-2
Original file line numberDiff line numberDiff line change
@@ -230,8 +230,6 @@ class ciEnv : StackObj {
230230

231231
ciMethod* get_method_from_handle(Method* method);
232232

233-
ciInstance* get_or_create_exception(jobject& handle, Symbol* name);
234-
235233
// Get a ciMethod representing either an unfound method or
236234
// a method with an unloaded holder. Ensures uniqueness of
237235
// the result.

‎src/hotspot/share/classfile/javaClasses.cpp

+4
Original file line numberDiff line numberDiff line change
@@ -2100,6 +2100,10 @@ void java_lang_Throwable::clear_stacktrace(oop throwable) {
21002100
set_stacktrace(throwable, nullptr);
21012101
}
21022102

2103+
oop java_lang_Throwable::create_exception_instance(Symbol* class_name, TRAPS) {
2104+
Klass* k = SystemDictionary::resolve_or_fail(class_name, true, CHECK_NULL);
2105+
return InstanceKlass::cast(k)->allocate_instance(CHECK_NULL);
2106+
}
21032107

21042108
void java_lang_Throwable::print(oop throwable, outputStream* st) {
21052109
ResourceMark rm;

‎src/hotspot/share/classfile/javaClasses.hpp

+3-1
Original file line numberDiff line numberDiff line change
@@ -619,7 +619,9 @@ class java_lang_Throwable: AllStatic {
619619
// For recreating class initialization error exceptions.
620620
static Handle create_initialization_error(JavaThread* current, Handle throwable);
621621

622-
// Printing
622+
static oop create_exception_instance(Symbol* class_name, TRAPS);
623+
624+
// Printing
623625
static void print(oop throwable, outputStream* st);
624626
static void print_stack_trace(Handle throwable, outputStream* st);
625627
static void java_printStackTrace(Handle throwable, TRAPS);

‎src/hotspot/share/memory/universe.cpp

+92-15
Original file line numberDiff line numberDiff line change
@@ -93,6 +93,13 @@ Klass* Universe::_fillerArrayKlassObj = nullptr;
9393
OopHandle Universe::_basic_type_mirrors[T_VOID+1];
9494
#if INCLUDE_CDS_JAVA_HEAP
9595
int Universe::_archived_basic_type_mirror_indices[T_VOID+1];
96+
97+
int Universe::_archived_null_ptr_exception_instance_index;
98+
int Universe::_archived_arithmetic_exception_instance_index;
99+
int Universe::_archived_virtual_machine_error_instance_index;
100+
int Universe::_archived_array_index_oob_exception_instance_index;
101+
int Universe::_archived_array_store_exception_instance_index;
102+
int Universe::_archived_class_cast_exception_instance_index;
96103
#endif
97104

98105
OopHandle Universe::_main_thread_group;
@@ -129,6 +136,10 @@ OopHandle Universe::_null_ptr_exception_instance;
129136
OopHandle Universe::_arithmetic_exception_instance;
130137
OopHandle Universe::_virtual_machine_error_instance;
131138

139+
OopHandle Universe::_array_index_oob_exception_instance;
140+
OopHandle Universe::_array_store_exception_instance;
141+
OopHandle Universe::_class_cast_exception_instance;
142+
132143
OopHandle Universe::_reference_pending_list;
133144

134145
Array<Klass*>* Universe::_the_array_interfaces_array = nullptr;
@@ -184,6 +195,10 @@ oop Universe::null_ptr_exception_instance() { return _null_ptr_exception_i
184195
oop Universe::arithmetic_exception_instance() { return _arithmetic_exception_instance.resolve(); }
185196
oop Universe::virtual_machine_error_instance() { return _virtual_machine_error_instance.resolve(); }
186197

198+
oop Universe::array_index_oob_exception_instance() { return _array_index_oob_exception_instance.resolve(); }
199+
oop Universe::array_store_exception_instance() { return _array_store_exception_instance.resolve(); }
200+
oop Universe::class_cast_exception_instance() { return _class_cast_exception_instance.resolve(); }
201+
187202
oop Universe::the_null_sentinel() { return _the_null_sentinel.resolve(); }
188203

189204
oop Universe::int_mirror() { return check_mirror(_basic_type_mirrors[T_INT].resolve()); }
@@ -257,6 +272,41 @@ void Universe::update_archived_basic_type_mirrors() {
257272
}
258273
}
259274
}
275+
276+
void Universe::update_exception_instances() {
277+
if (ArchiveHeapLoader::is_in_use()) {
278+
if (_archived_null_ptr_exception_instance_index >= 0) {
279+
oop mirror_oop = HeapShared::get_root(_archived_null_ptr_exception_instance_index);
280+
assert(mirror_oop != nullptr, "must be");
281+
_null_ptr_exception_instance = OopHandle(vm_global(), mirror_oop);
282+
}
283+
if (_archived_arithmetic_exception_instance_index >= 0) {
284+
oop mirror_oop = HeapShared::get_root(_archived_arithmetic_exception_instance_index);
285+
assert(mirror_oop != nullptr, "must be");
286+
_arithmetic_exception_instance = OopHandle(vm_global(), mirror_oop);
287+
}
288+
if (_archived_virtual_machine_error_instance_index >= 0) {
289+
oop mirror_oop = HeapShared::get_root(_archived_virtual_machine_error_instance_index);
290+
assert(mirror_oop != nullptr, "must be");
291+
_virtual_machine_error_instance = OopHandle(vm_global(), mirror_oop);
292+
}
293+
if (_archived_array_index_oob_exception_instance_index >= 0) {
294+
oop mirror_oop = HeapShared::get_root(_archived_array_index_oob_exception_instance_index);
295+
assert(mirror_oop != nullptr, "must be");
296+
_array_index_oob_exception_instance = OopHandle(vm_global(), mirror_oop);
297+
}
298+
if (_archived_array_store_exception_instance_index >= 0) {
299+
oop mirror_oop = HeapShared::get_root(_archived_array_store_exception_instance_index);
300+
assert(mirror_oop != nullptr, "must be");
301+
_array_store_exception_instance = OopHandle(vm_global(), mirror_oop);
302+
}
303+
if (_archived_class_cast_exception_instance_index >= 0) {
304+
oop mirror_oop = HeapShared::get_root(_archived_class_cast_exception_instance_index);
305+
assert(mirror_oop != nullptr, "must be");
306+
_class_cast_exception_instance = OopHandle(vm_global(), mirror_oop);
307+
}
308+
}
309+
}
260310
#endif
261311

262312
void Universe::serialize(SerializeClosure* f) {
@@ -268,6 +318,12 @@ void Universe::serialize(SerializeClosure* f) {
268318
// contents may need to be relocated. _basic_type_mirrors[i] will be
269319
// updated later in Universe::update_archived_basic_type_mirrors().
270320
}
321+
f->do_int(&_archived_null_ptr_exception_instance_index);
322+
f->do_int(&_archived_arithmetic_exception_instance_index);
323+
f->do_int(&_archived_virtual_machine_error_instance_index);
324+
f->do_int(&_archived_array_index_oob_exception_instance_index);
325+
f->do_int(&_archived_array_store_exception_instance_index);
326+
f->do_int(&_archived_class_cast_exception_instance_index);
271327
#endif
272328

273329
f->do_ptr(&_fillerArrayKlassObj);
@@ -1011,29 +1067,50 @@ bool universe_post_init() {
10111067
instance = java_lang_String::create_oop_from_str("Delayed StackOverflowError due to ReservedStackAccess annotated method", CHECK_false);
10121068
Universe::_delayed_stack_overflow_error_message = OopHandle(Universe::vm_global(), instance);
10131069
}
1070+
if (Universe::_null_ptr_exception_instance.is_empty()) {
1071+
instance = java_lang_Throwable::create_exception_instance(vmSymbols::java_lang_NullPointerException(), CHECK_false);
1072+
Universe::_null_ptr_exception_instance = OopHandle(Universe::vm_global(), instance);
1073+
Universe::_archived_null_ptr_exception_instance_index = -1;
1074+
}
1075+
if (Universe::_arithmetic_exception_instance.is_empty()) {
1076+
instance = java_lang_Throwable::create_exception_instance(vmSymbols::java_lang_ArithmeticException(), CHECK_false);
1077+
Universe::_arithmetic_exception_instance = OopHandle(Universe::vm_global(), instance);
1078+
Universe::_archived_arithmetic_exception_instance_index = -1;
1079+
}
1080+
//#ifdef COMPILER1_OR_COMPILER2_PRESENT
1081+
if (Universe::_array_index_oob_exception_instance.is_empty()) {
1082+
instance = java_lang_Throwable::create_exception_instance(vmSymbols::java_lang_ArrayIndexOutOfBoundsException(), CHECK_false);
1083+
Universe::_array_index_oob_exception_instance = OopHandle(Universe::vm_global(), instance);
1084+
Universe::_archived_array_index_oob_exception_instance_index = -1;
1085+
}
1086+
if (Universe::_array_store_exception_instance.is_empty()) {
1087+
instance = java_lang_Throwable::create_exception_instance(vmSymbols::java_lang_ArrayStoreException(), CHECK_false);
1088+
Universe::_array_store_exception_instance = OopHandle(Universe::vm_global(), instance);
1089+
Universe::_archived_array_store_exception_instance_index = -1;
1090+
}
1091+
if (Universe::_class_cast_exception_instance.is_empty()) {
1092+
instance = java_lang_Throwable::create_exception_instance(vmSymbols::java_lang_ClassCastException(), CHECK_false);
1093+
Universe::_class_cast_exception_instance = OopHandle(Universe::vm_global(), instance);
1094+
Universe::_archived_class_cast_exception_instance_index = -1;
1095+
}
1096+
//#endif // COMPILER1_OR_COMPILER2_PRESENT
10141097

1015-
// Setup preallocated NullPointerException
1016-
// (this is currently used for a cheap & dirty solution in compiler exception handling)
1017-
Klass* k = SystemDictionary::resolve_or_fail(vmSymbols::java_lang_NullPointerException(), true, CHECK_false);
1018-
instance = InstanceKlass::cast(k)->allocate_instance(CHECK_false);
1019-
Universe::_null_ptr_exception_instance = OopHandle(Universe::vm_global(), instance);
1020-
1021-
// Setup preallocated ArithmeticException
1022-
// (this is currently used for a cheap & dirty solution in compiler exception handling)
1023-
k = SystemDictionary::resolve_or_fail(vmSymbols::java_lang_ArithmeticException(), true, CHECK_false);
1024-
instance = InstanceKlass::cast(k)->allocate_instance(CHECK_false);
1025-
Universe::_arithmetic_exception_instance = OopHandle(Universe::vm_global(), instance);
1098+
if (DumpSharedSpaces) {
1099+
HeapShared::init_scratch_exceptions(CHECK_false);
1100+
}
10261101

10271102
// Virtual Machine Error for when we get into a situation we can't resolve
1028-
k = vmClasses::VirtualMachineError_klass();
1103+
Klass* k = vmClasses::VirtualMachineError_klass();
10291104
bool linked = InstanceKlass::cast(k)->link_class_or_fail(CHECK_false);
10301105
if (!linked) {
10311106
tty->print_cr("Unable to link/verify VirtualMachineError class");
10321107
return false; // initialization failed
10331108
}
1034-
instance = InstanceKlass::cast(k)->allocate_instance(CHECK_false);
1035-
Universe::_virtual_machine_error_instance = OopHandle(Universe::vm_global(), instance);
1036-
1109+
if (Universe::_virtual_machine_error_instance.is_empty()) {
1110+
instance = java_lang_Throwable::create_exception_instance(vmSymbols::java_lang_VirtualMachineError(), CHECK_false);
1111+
Universe::_virtual_machine_error_instance = OopHandle(Universe::vm_global(), instance);
1112+
Universe::_archived_virtual_machine_error_instance_index = -1;
1113+
}
10371114
Handle msg = java_lang_String::create_from_str("/ by zero", CHECK_false);
10381115
java_lang_Throwable::set_message(Universe::arithmetic_exception_instance(), msg());
10391116

0 commit comments

Comments
 (0)
Please sign in to comment.