34 #include "classfile/systemDictionaryShared.hpp" |
34 #include "classfile/systemDictionaryShared.hpp" |
35 #include "code/codeCache.hpp" |
35 #include "code/codeCache.hpp" |
36 #include "gc/shared/gcLocker.hpp" |
36 #include "gc/shared/gcLocker.hpp" |
37 #include "interpreter/bytecodeStream.hpp" |
37 #include "interpreter/bytecodeStream.hpp" |
38 #include "interpreter/bytecodes.hpp" |
38 #include "interpreter/bytecodes.hpp" |
|
39 #include "logging/log.hpp" |
|
40 #include "logging/logMessage.hpp" |
39 #include "memory/filemap.hpp" |
41 #include "memory/filemap.hpp" |
40 #include "memory/metaspace.hpp" |
42 #include "memory/metaspace.hpp" |
41 #include "memory/metaspaceShared.hpp" |
43 #include "memory/metaspaceShared.hpp" |
42 #include "memory/resourceArea.hpp" |
44 #include "memory/resourceArea.hpp" |
43 #include "oops/instanceClassLoaderKlass.hpp" |
45 #include "oops/instanceClassLoaderKlass.hpp" |
328 intptr_t* srcvtable = vtable_of(tmp); |
330 intptr_t* srcvtable = vtable_of(tmp); |
329 intptr_t* dstvtable = info->cloned_vtable(); |
331 intptr_t* dstvtable = info->cloned_vtable(); |
330 |
332 |
331 // We already checked (and, if necessary, adjusted n) when the vtables were allocated, so we are |
333 // We already checked (and, if necessary, adjusted n) when the vtables were allocated, so we are |
332 // safe to do memcpy. |
334 // safe to do memcpy. |
333 if (PrintSharedSpaces) { |
335 log_debug(cds, vtables)("Copying %3d vtable entries for %s", n, name); |
334 tty->print_cr("Copying %3d vtable entries for %s", n, name); |
|
335 } |
|
336 memcpy(dstvtable, srcvtable, sizeof(intptr_t) * n); |
336 memcpy(dstvtable, srcvtable, sizeof(intptr_t) * n); |
337 return dstvtable + n; |
337 return dstvtable + n; |
338 } |
338 } |
339 |
339 |
340 // To determine the size of the vtable for each type, we use the following |
340 // To determine the size of the vtable for each type, we use the following |
381 for (; ; vtable_len++) { |
381 for (; ; vtable_len++) { |
382 if (avtable[vtable_len] != bvtable[vtable_len]) { |
382 if (avtable[vtable_len] != bvtable[vtable_len]) { |
383 break; |
383 break; |
384 } |
384 } |
385 } |
385 } |
386 if (PrintSharedSpaces) { |
386 log_debug(cds, vtables)("Found %3d vtable entries for %s", vtable_len, name); |
387 tty->print_cr("Found %3d vtable entries for %s", vtable_len, name); |
|
388 } |
|
389 |
387 |
390 return vtable_len; |
388 return vtable_len; |
391 } |
389 } |
392 |
390 |
393 #define ALLOC_CPP_VTABLE_CLONE(c) \ |
391 #define ALLOC_CPP_VTABLE_CLONE(c) \ |
626 // To make fmt_stats be a syntactic constant (for format warnings), use #define. |
624 // To make fmt_stats be a syntactic constant (for format warnings), use #define. |
627 #define fmt_stats "%-20s: %8d %10d %5.1f | %8d %10d %5.1f | %8d %10d %5.1f" |
625 #define fmt_stats "%-20s: %8d %10d %5.1f | %8d %10d %5.1f | %8d %10d %5.1f" |
628 const char *sep = "--------------------+---------------------------+---------------------------+--------------------------"; |
626 const char *sep = "--------------------+---------------------------+---------------------------+--------------------------"; |
629 const char *hdr = " ro_cnt ro_bytes % | rw_cnt rw_bytes % | all_cnt all_bytes %"; |
627 const char *hdr = " ro_cnt ro_bytes % | rw_cnt rw_bytes % | all_cnt all_bytes %"; |
630 |
628 |
631 tty->print_cr("Detailed metadata info (rw includes md and mc):"); |
629 ResourceMark rm; |
632 tty->print_cr("%s", hdr); |
630 LogMessage(cds) msg; |
633 tty->print_cr("%s", sep); |
631 stringStream info_stream; |
|
632 |
|
633 info_stream.print_cr("Detailed metadata info (rw includes md and mc):"); |
|
634 info_stream.print_cr("%s", hdr); |
|
635 info_stream.print_cr("%s", sep); |
634 for (int type = 0; type < int(_number_of_types); type ++) { |
636 for (int type = 0; type < int(_number_of_types); type ++) { |
635 const char *name = type_name((Type)type); |
637 const char *name = type_name((Type)type); |
636 int ro_count = _counts[RO][type]; |
638 int ro_count = _counts[RO][type]; |
637 int ro_bytes = _bytes [RO][type]; |
639 int ro_bytes = _bytes [RO][type]; |
638 int rw_count = _counts[RW][type]; |
640 int rw_count = _counts[RW][type]; |
642 |
644 |
643 double ro_perc = 100.0 * double(ro_bytes) / double(ro_all); |
645 double ro_perc = 100.0 * double(ro_bytes) / double(ro_all); |
644 double rw_perc = 100.0 * double(rw_bytes) / double(rw_all); |
646 double rw_perc = 100.0 * double(rw_bytes) / double(rw_all); |
645 double perc = 100.0 * double(bytes) / double(ro_all + rw_all); |
647 double perc = 100.0 * double(bytes) / double(ro_all + rw_all); |
646 |
648 |
647 tty->print_cr(fmt_stats, name, |
649 info_stream.print_cr(fmt_stats, name, |
648 ro_count, ro_bytes, ro_perc, |
650 ro_count, ro_bytes, ro_perc, |
649 rw_count, rw_bytes, rw_perc, |
651 rw_count, rw_bytes, rw_perc, |
650 count, bytes, perc); |
652 count, bytes, perc); |
651 |
653 |
652 all_ro_count += ro_count; |
654 all_ro_count += ro_count; |
653 all_ro_bytes += ro_bytes; |
655 all_ro_bytes += ro_bytes; |
654 all_rw_count += rw_count; |
656 all_rw_count += rw_count; |
655 all_rw_bytes += rw_bytes; |
657 all_rw_bytes += rw_bytes; |
660 |
662 |
661 double all_ro_perc = 100.0 * double(all_ro_bytes) / double(ro_all); |
663 double all_ro_perc = 100.0 * double(all_ro_bytes) / double(ro_all); |
662 double all_rw_perc = 100.0 * double(all_rw_bytes) / double(rw_all); |
664 double all_rw_perc = 100.0 * double(all_rw_bytes) / double(rw_all); |
663 double all_perc = 100.0 * double(all_bytes) / double(ro_all + rw_all); |
665 double all_perc = 100.0 * double(all_bytes) / double(ro_all + rw_all); |
664 |
666 |
665 tty->print_cr("%s", sep); |
667 info_stream.print_cr("%s", sep); |
666 tty->print_cr(fmt_stats, "Total", |
668 info_stream.print_cr(fmt_stats, "Total", |
667 all_ro_count, all_ro_bytes, all_ro_perc, |
669 all_ro_count, all_ro_bytes, all_ro_perc, |
668 all_rw_count, all_rw_bytes, all_rw_perc, |
670 all_rw_count, all_rw_bytes, all_rw_perc, |
669 all_count, all_bytes, all_perc); |
671 all_count, all_bytes, all_perc); |
670 |
672 |
671 assert(all_ro_bytes == ro_all, "everything should have been counted"); |
673 assert(all_ro_bytes == ro_all, "everything should have been counted"); |
672 assert(all_rw_bytes == rw_all, "everything should have been counted"); |
674 assert(all_rw_bytes == rw_all, "everything should have been counted"); |
|
675 |
|
676 msg.info("%s", info_stream.as_string()); |
673 #undef fmt_stats |
677 #undef fmt_stats |
674 } |
678 } |
675 |
679 |
676 // Populate the shared space. |
680 // Populate the shared space. |
677 |
681 |
895 mapinfo->close(); |
899 mapinfo->close(); |
896 |
900 |
897 // Restore the vtable in case we invoke any virtual methods. |
901 // Restore the vtable in case we invoke any virtual methods. |
898 MetaspaceShared::clone_cpp_vtables((intptr_t*)vtbl_list); |
902 MetaspaceShared::clone_cpp_vtables((intptr_t*)vtbl_list); |
899 |
903 |
900 if (PrintSharedSpaces) { |
904 if (log_is_enabled(Info, cds)) { |
901 DumpAllocClosure dac; |
905 DumpAllocClosure dac; |
902 dac.iterate_metaspace(_loader_data->ro_metaspace(), DumpAllocClosure::RO); |
906 dac.iterate_metaspace(_loader_data->ro_metaspace(), DumpAllocClosure::RO); |
903 dac.iterate_metaspace(_loader_data->rw_metaspace(), DumpAllocClosure::RW); |
907 dac.iterate_metaspace(_loader_data->rw_metaspace(), DumpAllocClosure::RW); |
904 |
908 |
905 dac.dump_stats(int(ro_bytes), int(rw_bytes), int(md_bytes), int(mc_bytes)); |
909 dac.dump_stats(int(ro_bytes), int(rw_bytes), int(md_bytes), int(mc_bytes)); |
1062 class_count += preload_and_dump(ExtraSharedClassListFile, class_promote_order, |
1066 class_count += preload_and_dump(ExtraSharedClassListFile, class_promote_order, |
1063 THREAD); |
1067 THREAD); |
1064 } |
1068 } |
1065 tty->print_cr("Loading classes to share: done."); |
1069 tty->print_cr("Loading classes to share: done."); |
1066 |
1070 |
1067 if (PrintSharedSpaces) { |
1071 log_info(cds)("Shared spaces: preloaded %d classes", class_count); |
1068 tty->print_cr("Shared spaces: preloaded %d classes", class_count); |
|
1069 } |
|
1070 |
1072 |
1071 // Rewrite and link classes |
1073 // Rewrite and link classes |
1072 tty->print_cr("Rewriting and linking classes ..."); |
1074 tty->print_cr("Rewriting and linking classes ..."); |
1073 |
1075 |
1074 // Link any classes which got missed. This would happen if we have loaded classes that |
1076 // Link any classes which got missed. This would happen if we have loaded classes that |
1100 while (parser.parse_one_line()) { |
1102 while (parser.parse_one_line()) { |
1101 Klass* klass = ClassLoaderExt::load_one_class(&parser, THREAD); |
1103 Klass* klass = ClassLoaderExt::load_one_class(&parser, THREAD); |
1102 |
1104 |
1103 CLEAR_PENDING_EXCEPTION; |
1105 CLEAR_PENDING_EXCEPTION; |
1104 if (klass != NULL) { |
1106 if (klass != NULL) { |
1105 if (PrintSharedSpaces && Verbose && WizardMode) { |
1107 if (log_is_enabled(Trace, cds)) { |
1106 ResourceMark rm; |
1108 ResourceMark rm; |
1107 tty->print_cr("Shared spaces preloaded: %s", klass->external_name()); |
1109 log_trace(cds)("Shared spaces preloaded: %s", klass->external_name()); |
1108 } |
1110 } |
1109 |
1111 |
1110 InstanceKlass* ik = InstanceKlass::cast(klass); |
1112 InstanceKlass* ik = InstanceKlass::cast(klass); |
1111 |
1113 |
1112 // Should be class load order as per -Xlog:class+preorder |
1114 // Should be class load order as per -Xlog:class+preorder |