@@ -692,25 +692,27 @@ void VM_PopulateDumpSharedSpace::doit() {
692
692
_map_info->header ()->set_class_location_config (cl_config);
693
693
}
694
694
695
- class CollectCLDClosure : public CLDClosure {
696
- GrowableArray<ClassLoaderData*> _loaded_cld;
697
- GrowableArray<OopHandle> _loaded_cld_handles; // keep the CLDs alive
698
- Thread* _current_thread;
695
+ class CollectClassesForLinking : public KlassClosure {
696
+ GrowableArray<OopHandle> _mirrors;
697
+
699
698
public:
700
- CollectCLDClosure (Thread* thread) : _current_thread(thread) {}
701
- ~CollectCLDClosure () {
702
- for (int i = 0 ; i < _loaded_cld_handles.length (); i++) {
703
- _loaded_cld_handles.at (i).release (Universe::vm_global ());
699
+ ~CollectClassesForLinking () {
700
+ for (int i = 0 ; i < _mirrors.length (); i++) {
701
+ _mirrors.at (i).release (Universe::vm_global ());
704
702
}
705
703
}
704
+
706
705
void do_cld (ClassLoaderData* cld) {
707
706
assert (cld->is_alive (), " must be" );
708
- _loaded_cld.append (cld);
709
- _loaded_cld_handles.append (OopHandle (Universe::vm_global (), cld->holder ()));
710
707
}
711
708
712
- int nof_cld () const { return _loaded_cld.length (); }
713
- ClassLoaderData* cld_at (int index) { return _loaded_cld.at (index ); }
709
+ void do_klass (Klass* k) {
710
+ if (k->is_instance_klass ()) {
711
+ _mirrors.append (OopHandle (Universe::vm_global (), k->java_mirror ()));
712
+ }
713
+ }
714
+
715
+ const GrowableArray<OopHandle>* mirrors () const { return &_mirrors; }
714
716
};
715
717
716
718
// Check if we can eagerly link this class at dump time, so we can avoid the
@@ -751,28 +753,26 @@ void MetaspaceShared::link_shared_classes(bool jcmd_request, TRAPS) {
751
753
LambdaFormInvokers::regenerate_holder_classes (CHECK);
752
754
}
753
755
754
- // Collect all loaded ClassLoaderData.
755
- CollectCLDClosure collect_cld (THREAD);
756
- {
757
- // ClassLoaderDataGraph::loaded_cld_do requires ClassLoaderDataGraph_lock.
758
- // We cannot link the classes while holding this lock (or else we may run into deadlock).
759
- // Therefore, we need to first collect all the CLDs, and then link their classes after
760
- // releasing the lock.
761
- MutexLocker lock (ClassLoaderDataGraph_lock);
762
- ClassLoaderDataGraph::loaded_cld_do (&collect_cld);
763
- }
764
756
765
757
while (true ) {
758
+ CollectClassesForLinking collect_classes;
759
+ {
760
+ // ClassLoaderDataGraph::loaded_classes_do_keepalive() requires ClassLoaderDataGraph_lock.
761
+ // We cannot link the classes while holding this lock (or else we may run into deadlock).
762
+ // Therefore, we need to first collect all the classes, keeping them alive by
763
+ // holding onto their java_mirrors in global OopHandles. We then link the classes after
764
+ // releasing the lock.
765
+ MutexLocker lock (ClassLoaderDataGraph_lock);
766
+ ClassLoaderDataGraph::loaded_classes_do_keepalive (&collect_classes);
767
+ }
768
+
766
769
bool has_linked = false ;
767
- for (int i = 0 ; i < collect_cld.nof_cld (); i++) {
768
- ClassLoaderData* cld = collect_cld.cld_at (i);
769
- for (Klass* klass = cld->klasses (); klass != nullptr ; klass = klass->next_link ()) {
770
- if (klass->is_instance_klass ()) {
771
- InstanceKlass* ik = InstanceKlass::cast (klass);
772
- if (may_be_eagerly_linked (ik)) {
773
- has_linked |= link_class_for_cds (ik, CHECK);
774
- }
775
- }
770
+ const GrowableArray<OopHandle>* mirrors = collect_classes.mirrors ();
771
+ for (int i = 0 ; i < mirrors->length (); i++) {
772
+ OopHandle mirror = mirrors->at (i);
773
+ InstanceKlass* ik = InstanceKlass::cast (java_lang_Class::as_Klass (mirror.resolve ()));
774
+ if (may_be_eagerly_linked (ik)) {
775
+ has_linked |= link_class_for_cds (ik, CHECK);
776
776
}
777
777
}
778
778
0 commit comments