< prev index next >

src/hotspot/share/classfile/moduleEntry.cpp

Print this page

 14  *
 15  * You should have received a copy of the GNU General Public License version
 16  * 2 along with this work; if not, write to the Free Software Foundation,
 17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 18  *
 19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 20  * or visit www.oracle.com if you need additional information or have any
 21  * questions.
 22  *
 23  */
 24 
 25 #include "cds/aotClassLocation.hpp"
 26 #include "cds/archiveBuilder.hpp"
 27 #include "cds/archiveUtils.hpp"
 28 #include "cds/cdsConfig.hpp"
 29 #include "cds/heapShared.hpp"
 30 #include "classfile/classLoader.hpp"
 31 #include "classfile/classLoaderData.inline.hpp"
 32 #include "classfile/javaClasses.inline.hpp"
 33 #include "classfile/moduleEntry.hpp"

 34 #include "classfile/systemDictionary.hpp"
 35 #include "jni.h"
 36 #include "logging/log.hpp"
 37 #include "logging/logStream.hpp"
 38 #include "memory/resourceArea.hpp"
 39 #include "memory/universe.hpp"
 40 #include "oops/oopHandle.inline.hpp"
 41 #include "oops/symbol.hpp"
 42 #include "runtime/handles.inline.hpp"
 43 #include "runtime/safepoint.hpp"
 44 #include "utilities/events.hpp"
 45 #include "utilities/growableArray.hpp"
 46 #include "utilities/ostream.hpp"
 47 #include "utilities/quickSort.hpp"
 48 #include "utilities/resourceHash.hpp"
 49 
 50 ModuleEntry* ModuleEntryTable::_javabase_module = nullptr;
 51 
 52 oop ModuleEntry::module() const { return _module.resolve(); }
 53 

433     ls.print("Stored in archive: ");
434     archived_entry->print(&ls);
435   }
436   return archived_entry;
437 }
438 
439 bool ModuleEntry::has_been_archived() {
440   assert(!ArchiveBuilder::current()->is_in_buffer_space(this), "must be called on original ModuleEntry");
441   return _archive_modules_entries->contains(this);
442 }
443 
444 ModuleEntry* ModuleEntry::get_archived_entry(ModuleEntry* orig_entry) {
445   ModuleEntry** ptr = _archive_modules_entries->get(orig_entry);
446   assert(ptr != nullptr && *ptr != nullptr, "must have been allocated");
447   return *ptr;
448 }
449 
450 // This function is used to archive ModuleEntry::_reads and PackageEntry::_qualified_exports.
451 // GrowableArray cannot be directly archived, as it needs to be expandable at runtime.
452 // Write it out as an Array, and convert it back to GrowableArray at runtime.
453 Array<ModuleEntry*>* ModuleEntry::write_growable_array(GrowableArray<ModuleEntry*>* array) {
454   Array<ModuleEntry*>* archived_array = nullptr;
455   int length = (array == nullptr) ? 0 : array->length();







456   if (length > 0) {
457     archived_array = ArchiveBuilder::new_ro_array<ModuleEntry*>(length);
458     for (int i = 0; i < length; i++) {
459       ModuleEntry* archived_entry = get_archived_entry(array->at(i));
460       archived_array->at_put(i, archived_entry);
461       ArchivePtrMarker::mark_pointer((address*)archived_array->adr_at(i));
462     }
463   }
464 
465   return archived_array;
466 }
467 
468 GrowableArray<ModuleEntry*>* ModuleEntry::restore_growable_array(Array<ModuleEntry*>* archived_array) {
469   GrowableArray<ModuleEntry*>* array = nullptr;
470   int length = (archived_array == nullptr) ? 0 : archived_array->length();
471   if (length > 0) {
472     array = new (mtModule) GrowableArray<ModuleEntry*>(length, mtModule);
473     for (int i = 0; i < length; i++) {
474       ModuleEntry* archived_entry = archived_array->at(i);
475       array->append(archived_entry);
476     }
477   }
478 
479   return array;
480 }
481 
482 void ModuleEntry::iterate_symbols(MetaspaceClosure* closure) {
483   closure->push(&_name);
484   closure->push(&_version);
485   closure->push(&_location);
486 }
487 
488 void ModuleEntry::init_as_archived_entry() {
489   set_archived_reads(write_growable_array(reads()));
490 
491   _loader_data = nullptr;  // re-init at runtime
492   _shared_path_index = AOTClassLocationConfig::dumptime()->get_module_shared_path_index(_location);
493   if (name() != nullptr) {
494     _name = ArchiveBuilder::get_buffered_symbol(_name);
495     ArchivePtrMarker::mark_pointer((address*)&_name);
496   }
497   if (_version != nullptr) {
498     _version = ArchiveBuilder::get_buffered_symbol(_version);
499   }
500   if (_location != nullptr) {
501     _location = ArchiveBuilder::get_buffered_symbol(_location);
502   }
503   JFR_ONLY(set_trace_id(0);) // re-init at runtime
504 
505   ArchivePtrMarker::mark_pointer((address*)&_reads);
506   ArchivePtrMarker::mark_pointer((address*)&_version);
507   ArchivePtrMarker::mark_pointer((address*)&_location);
508 }
509 
510 #ifndef PRODUCT
511 void ModuleEntry::verify_archived_module_entries() {
512   assert(_num_archived_module_entries == _num_inited_module_entries,
513          "%d ModuleEntries have been archived but %d of them have been properly initialized with archived java.lang.Module objects",
514          _num_archived_module_entries, _num_inited_module_entries);
515 }
516 #endif // PRODUCT
517 
518 void ModuleEntry::load_from_archive(ClassLoaderData* loader_data) {
519   assert(CDSConfig::is_using_archive(), "runtime only");
520   set_loader_data(loader_data);
521   set_reads(restore_growable_array(archived_reads()));
522   JFR_ONLY(INIT_ID(this);)
523 }
524 
525 void ModuleEntry::restore_archived_oops(ClassLoaderData* loader_data) {
526   assert(CDSConfig::is_using_archive(), "runtime only");
527   Handle module_handle(Thread::current(), HeapShared::get_root(_archived_module_index, /*clear=*/true));
528   assert(module_handle.not_null(), "huh");
529   set_module(loader_data->add_handle(module_handle));
530 
531   // This was cleared to zero during dump time -- we didn't save the value
532   // because it may be affected by archive relocation.
533   java_lang_Module::set_module_entry(module_handle(), this);
534 
535   assert(java_lang_Module::loader(module_handle()) == loader_data->class_loader(),
536          "must be set in dump time");
537 
538   if (log_is_enabled(Info, cds, module)) {
539     ResourceMark rm;
540     LogStream ls(Log(cds, module)::info());
541     ls.print("Restored from archive: ");
542     print(&ls);
543   }
544 }
545 
546 void ModuleEntry::clear_archived_oops() {
547   assert(CDSConfig::is_using_archive(), "runtime only");
548   HeapShared::clear_root(_archived_module_index);
549 }
550 
551 static int compare_module_by_name(ModuleEntry* a, ModuleEntry* b) {
552   assert(a == b || a->name() != b->name(), "no duplicated names");
553   return a->name()->fast_compare(b->name());
554 }
555 
556 void ModuleEntryTable::iterate_symbols(MetaspaceClosure* closure) {
557   auto syms = [&] (const SymbolHandle& key, ModuleEntry*& m) {
558       m->iterate_symbols(closure);
559   };
560   _table.iterate_all(syms);
561 }
562 
563 Array<ModuleEntry*>* ModuleEntryTable::allocate_archived_entries() {
564   Array<ModuleEntry*>* archived_modules = ArchiveBuilder::new_rw_array<ModuleEntry*>(_table.number_of_entries());
565   int n = 0;
566   auto grab = [&] (const SymbolHandle& key, ModuleEntry*& m) {
567     archived_modules->at_put(n++, m);

572     // Always allocate in the same order to produce deterministic archive.
573     QuickSort::sort(archived_modules->data(), n, compare_module_by_name);
574   }
575   for (int i = 0; i < n; i++) {
576     archived_modules->at_put(i, archived_modules->at(i)->allocate_archived_entry());
577     ArchivePtrMarker::mark_pointer((address*)archived_modules->adr_at(i));
578   }
579   return archived_modules;
580 }
581 
582 void ModuleEntryTable::init_archived_entries(Array<ModuleEntry*>* archived_modules) {
583   assert(CDSConfig::is_dumping_full_module_graph(), "sanity");
584   for (int i = 0; i < archived_modules->length(); i++) {
585     ModuleEntry* archived_entry = archived_modules->at(i);
586     archived_entry->init_as_archived_entry();
587   }
588 }
589 
590 void ModuleEntryTable::load_archived_entries(ClassLoaderData* loader_data,
591                                              Array<ModuleEntry*>* archived_modules) {
592   assert(CDSConfig::is_using_archive(), "runtime only");
593 
594   for (int i = 0; i < archived_modules->length(); i++) {
595     ModuleEntry* archived_entry = archived_modules->at(i);
596     archived_entry->load_from_archive(loader_data);
597     _table.put(archived_entry->name(), archived_entry);
598   }
599 }
600 
601 void ModuleEntryTable::restore_archived_oops(ClassLoaderData* loader_data, Array<ModuleEntry*>* archived_modules) {
602   assert(CDSConfig::is_using_archive(), "runtime only");
603   for (int i = 0; i < archived_modules->length(); i++) {
604     ModuleEntry* archived_entry = archived_modules->at(i);
605     archived_entry->restore_archived_oops(loader_data);
606   }
607 }
608 #endif // INCLUDE_CDS_JAVA_HEAP
609 
610 // Create an entry in the class loader's module_entry_table.  It is the
611 // caller's responsibility to ensure that the entry has not already been
612 // created.
613 ModuleEntry* ModuleEntryTable::locked_create_entry(Handle module_handle,
614                                                    bool is_open,
615                                                    Symbol* module_name,
616                                                    Symbol* module_version,
617                                                    Symbol* module_location,
618                                                    ClassLoaderData* loader_data) {
619   assert(module_name != nullptr, "ModuleEntryTable locked_create_entry should never be called for unnamed module.");
620   assert(Module_lock->owned_by_self(), "should have the Module_lock");
621   assert(lookup_only(module_name) == nullptr, "Module already exists");
622   ModuleEntry* entry = new ModuleEntry(module_handle, is_open, module_name,

 14  *
 15  * You should have received a copy of the GNU General Public License version
 16  * 2 along with this work; if not, write to the Free Software Foundation,
 17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 18  *
 19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 20  * or visit www.oracle.com if you need additional information or have any
 21  * questions.
 22  *
 23  */
 24 
 25 #include "cds/aotClassLocation.hpp"
 26 #include "cds/archiveBuilder.hpp"
 27 #include "cds/archiveUtils.hpp"
 28 #include "cds/cdsConfig.hpp"
 29 #include "cds/heapShared.hpp"
 30 #include "classfile/classLoader.hpp"
 31 #include "classfile/classLoaderData.inline.hpp"
 32 #include "classfile/javaClasses.inline.hpp"
 33 #include "classfile/moduleEntry.hpp"
 34 #include "classfile/modules.hpp"
 35 #include "classfile/systemDictionary.hpp"
 36 #include "jni.h"
 37 #include "logging/log.hpp"
 38 #include "logging/logStream.hpp"
 39 #include "memory/resourceArea.hpp"
 40 #include "memory/universe.hpp"
 41 #include "oops/oopHandle.inline.hpp"
 42 #include "oops/symbol.hpp"
 43 #include "runtime/handles.inline.hpp"
 44 #include "runtime/safepoint.hpp"
 45 #include "utilities/events.hpp"
 46 #include "utilities/growableArray.hpp"
 47 #include "utilities/ostream.hpp"
 48 #include "utilities/quickSort.hpp"
 49 #include "utilities/resourceHash.hpp"
 50 
 51 ModuleEntry* ModuleEntryTable::_javabase_module = nullptr;
 52 
 53 oop ModuleEntry::module() const { return _module.resolve(); }
 54 

434     ls.print("Stored in archive: ");
435     archived_entry->print(&ls);
436   }
437   return archived_entry;
438 }
439 
440 bool ModuleEntry::has_been_archived() {
441   assert(!ArchiveBuilder::current()->is_in_buffer_space(this), "must be called on original ModuleEntry");
442   return _archive_modules_entries->contains(this);
443 }
444 
445 ModuleEntry* ModuleEntry::get_archived_entry(ModuleEntry* orig_entry) {
446   ModuleEntry** ptr = _archive_modules_entries->get(orig_entry);
447   assert(ptr != nullptr && *ptr != nullptr, "must have been allocated");
448   return *ptr;
449 }
450 
451 // This function is used to archive ModuleEntry::_reads and PackageEntry::_qualified_exports.
452 // GrowableArray cannot be directly archived, as it needs to be expandable at runtime.
453 // Write it out as an Array, and convert it back to GrowableArray at runtime.
454 Array<ModuleEntry*>* ModuleEntry::write_growable_array(ModuleEntry* module, GrowableArray<ModuleEntry*>* array) {
455   Array<ModuleEntry*>* archived_array = nullptr;
456   int length = (array == nullptr) ? 0 : array->length();
457   if (module->is_named()) {
458     if (Modules::is_dynamic_proxy_module(module)) {
459       // This is a dynamically generated module. Its opens and exports will be
460       // restored at runtime in the Java code. See comments in ArchivedData::restore().
461       return nullptr;
462     }
463   }
464   if (length > 0) {
465     archived_array = ArchiveBuilder::new_ro_array<ModuleEntry*>(length);
466     for (int i = 0; i < length; i++) {
467       ModuleEntry* archived_entry = get_archived_entry(array->at(i));
468       archived_array->at_put(i, archived_entry);
469       ArchivePtrMarker::mark_pointer((address*)archived_array->adr_at(i));
470     }
471   }
472 
473   return archived_array;
474 }
475 
476 GrowableArray<ModuleEntry*>* ModuleEntry::restore_growable_array(Array<ModuleEntry*>* archived_array) {
477   GrowableArray<ModuleEntry*>* array = nullptr;
478   int length = (archived_array == nullptr) ? 0 : archived_array->length();
479   if (length > 0) {
480     array = new (mtModule) GrowableArray<ModuleEntry*>(length, mtModule);
481     for (int i = 0; i < length; i++) {
482       ModuleEntry* archived_entry = archived_array->at(i);
483       array->append(archived_entry);
484     }
485   }
486 
487   return array;
488 }
489 
490 void ModuleEntry::iterate_symbols(MetaspaceClosure* closure) {
491   closure->push(&_name);
492   closure->push(&_version);
493   closure->push(&_location);
494 }
495 
496 void ModuleEntry::init_as_archived_entry() {
497   set_archived_reads(write_growable_array(this, reads()));
498 
499   _loader_data = nullptr;  // re-init at runtime
500   _shared_path_index = AOTClassLocationConfig::dumptime()->get_module_shared_path_index(_location);
501   if (name() != nullptr) {
502     _name = ArchiveBuilder::get_buffered_symbol(_name);
503     ArchivePtrMarker::mark_pointer((address*)&_name);
504   }
505   if (_version != nullptr) {
506     _version = ArchiveBuilder::get_buffered_symbol(_version);
507   }
508   if (_location != nullptr) {
509     _location = ArchiveBuilder::get_buffered_symbol(_location);
510   }
511   JFR_ONLY(set_trace_id(0);) // re-init at runtime
512 
513   ArchivePtrMarker::mark_pointer((address*)&_reads);
514   ArchivePtrMarker::mark_pointer((address*)&_version);
515   ArchivePtrMarker::mark_pointer((address*)&_location);
516 }
517 
518 #ifndef PRODUCT
519 void ModuleEntry::verify_archived_module_entries() {
520   assert(_num_archived_module_entries == _num_inited_module_entries,
521          "%d ModuleEntries have been archived but %d of them have been properly initialized with archived java.lang.Module objects",
522          _num_archived_module_entries, _num_inited_module_entries);
523 }
524 #endif // PRODUCT
525 
526 void ModuleEntry::load_from_archive(ClassLoaderData* loader_data) {
527   assert(CDSConfig::is_using_full_module_graph(), "runtime only");
528   set_loader_data(loader_data);
529   set_reads(restore_growable_array(archived_reads()));
530   JFR_ONLY(INIT_ID(this);)
531 }
532 
533 void ModuleEntry::restore_archived_oops(ClassLoaderData* loader_data) {
534   assert(CDSConfig::is_using_full_module_graph(), "runtime only");
535   Handle module_handle(Thread::current(), HeapShared::get_root(_archived_module_index, /*clear=*/true));
536   assert(module_handle.not_null(), "huh");
537   set_module(loader_data->add_handle(module_handle));
538 
539   // This was cleared to zero during dump time -- we didn't save the value
540   // because it may be affected by archive relocation.
541   java_lang_Module::set_module_entry(module_handle(), this);
542 
543   assert(java_lang_Module::loader(module_handle()) == loader_data->class_loader(),
544          "must be set in dump time");
545 
546   if (log_is_enabled(Info, cds, module)) {
547     ResourceMark rm;
548     LogStream ls(Log(cds, module)::info());
549     ls.print("Restored from archive: ");
550     print(&ls);
551   }
552 }
553 
554 void ModuleEntry::clear_archived_oops() {
555   assert(CDSConfig::is_using_archive() && !CDSConfig::is_using_full_module_graph(), "runtime only");
556   HeapShared::clear_root(_archived_module_index);
557 }
558 
559 static int compare_module_by_name(ModuleEntry* a, ModuleEntry* b) {
560   assert(a == b || a->name() != b->name(), "no duplicated names");
561   return a->name()->fast_compare(b->name());
562 }
563 
564 void ModuleEntryTable::iterate_symbols(MetaspaceClosure* closure) {
565   auto syms = [&] (const SymbolHandle& key, ModuleEntry*& m) {
566       m->iterate_symbols(closure);
567   };
568   _table.iterate_all(syms);
569 }
570 
571 Array<ModuleEntry*>* ModuleEntryTable::allocate_archived_entries() {
572   Array<ModuleEntry*>* archived_modules = ArchiveBuilder::new_rw_array<ModuleEntry*>(_table.number_of_entries());
573   int n = 0;
574   auto grab = [&] (const SymbolHandle& key, ModuleEntry*& m) {
575     archived_modules->at_put(n++, m);

580     // Always allocate in the same order to produce deterministic archive.
581     QuickSort::sort(archived_modules->data(), n, compare_module_by_name);
582   }
583   for (int i = 0; i < n; i++) {
584     archived_modules->at_put(i, archived_modules->at(i)->allocate_archived_entry());
585     ArchivePtrMarker::mark_pointer((address*)archived_modules->adr_at(i));
586   }
587   return archived_modules;
588 }
589 
590 void ModuleEntryTable::init_archived_entries(Array<ModuleEntry*>* archived_modules) {
591   assert(CDSConfig::is_dumping_full_module_graph(), "sanity");
592   for (int i = 0; i < archived_modules->length(); i++) {
593     ModuleEntry* archived_entry = archived_modules->at(i);
594     archived_entry->init_as_archived_entry();
595   }
596 }
597 
598 void ModuleEntryTable::load_archived_entries(ClassLoaderData* loader_data,
599                                              Array<ModuleEntry*>* archived_modules) {
600   assert(CDSConfig::is_using_full_module_graph(), "runtime only");
601 
602   for (int i = 0; i < archived_modules->length(); i++) {
603     ModuleEntry* archived_entry = archived_modules->at(i);
604     archived_entry->load_from_archive(loader_data);
605     _table.put(archived_entry->name(), archived_entry);
606   }
607 }
608 
609 void ModuleEntryTable::restore_archived_oops(ClassLoaderData* loader_data, Array<ModuleEntry*>* archived_modules) {
610   assert(CDSConfig::is_using_full_module_graph(), "runtime only");
611   for (int i = 0; i < archived_modules->length(); i++) {
612     ModuleEntry* archived_entry = archived_modules->at(i);
613     archived_entry->restore_archived_oops(loader_data);
614   }
615 }
616 #endif // INCLUDE_CDS_JAVA_HEAP
617 
618 // Create an entry in the class loader's module_entry_table.  It is the
619 // caller's responsibility to ensure that the entry has not already been
620 // created.
621 ModuleEntry* ModuleEntryTable::locked_create_entry(Handle module_handle,
622                                                    bool is_open,
623                                                    Symbol* module_name,
624                                                    Symbol* module_version,
625                                                    Symbol* module_location,
626                                                    ClassLoaderData* loader_data) {
627   assert(module_name != nullptr, "ModuleEntryTable locked_create_entry should never be called for unnamed module.");
628   assert(Module_lock->owned_by_self(), "should have the Module_lock");
629   assert(lookup_only(module_name) == nullptr, "Module already exists");
630   ModuleEntry* entry = new ModuleEntry(module_handle, is_open, module_name,
< prev index next >