diff --git a/src/hotspot/share/cds/filemap.cpp b/src/hotspot/share/cds/filemap.cpp index 72a7bb021c3..afc45424f7a 100644 --- a/src/hotspot/share/cds/filemap.cpp +++ b/src/hotspot/share/cds/filemap.cpp @@ -2060,6 +2060,20 @@ size_t FileMapInfo::read_bytes(void* buffer, size_t count) { return count; } +// Get the total size in bytes of a read only region +size_t FileMapInfo::readonly_total() { + size_t total = 0; + if (current_info() != nullptr) { + FileMapRegion* r = FileMapInfo::current_info()->region_at(MetaspaceShared::ro); + if (r->read_only()) total += r->used(); + } + if (dynamic_info() != nullptr) { + FileMapRegion* r = FileMapInfo::dynamic_info()->region_at(MetaspaceShared::ro); + if (r->read_only()) total += r->used(); + } + return total; +} + static MemRegion *closed_heap_regions = NULL; static MemRegion *open_heap_regions = NULL; static int num_closed_heap_regions = 0; diff --git a/src/hotspot/share/cds/filemap.hpp b/src/hotspot/share/cds/filemap.hpp index a67274d532a..c71184b82a6 100644 --- a/src/hotspot/share/cds/filemap.hpp +++ b/src/hotspot/share/cds/filemap.hpp @@ -460,6 +460,7 @@ public: void write_bytes(const void* buffer, size_t count); void write_bytes_aligned(const void* buffer, size_t count); size_t read_bytes(void* buffer, size_t count); + static size_t readonly_total(); MapArchiveResult map_regions(int regions[], int num_regions, char* mapped_base_address, ReservedSpace rs); void unmap_regions(int regions[], int num_regions); void map_or_load_heap_regions() NOT_CDS_JAVA_HEAP_RETURN; diff --git a/src/hotspot/share/services/memReporter.cpp b/src/hotspot/share/services/memReporter.cpp index 92dbb801e02..ec1f032fa88 100644 --- a/src/hotspot/share/services/memReporter.cpp +++ b/src/hotspot/share/services/memReporter.cpp @@ -22,6 +22,7 @@ * */ #include "precompiled.hpp" +#include "cds/filemap.hpp" #include "memory/allocation.hpp" #include "memory/metaspace.hpp" #include "memory/metaspaceUtils.hpp" @@ -205,6 +206,13 @@ void MemSummaryReporter::report_summary_of_type(MEMFLAGS flag, const char* scale = current_scale(); out->print("-%26s (", NMTUtil::flag_to_name(flag)); print_total(reserved_amount, committed_amount); +#if INCLUDE_CDS + if (flag == mtClassShared) { + size_t read_only_bytes = FileMapInfo::readonly_total(); + output()->print(", readonly=" SIZE_FORMAT "%s", + amount_in_current_scale(read_only_bytes), scale); + } +#endif out->print_cr(")"); if (flag == mtClass) { diff --git a/test/hotspot/jtreg/runtime/NMT/SummarySanityCheck.java b/test/hotspot/jtreg/runtime/NMT/SummarySanityCheck.java index 099836a12e9..e9576c24faf 100644 --- a/test/hotspot/jtreg/runtime/NMT/SummarySanityCheck.java +++ b/test/hotspot/jtreg/runtime/NMT/SummarySanityCheck.java @@ -64,8 +64,8 @@ public class SummarySanityCheck { long totalCommitted = 0, totalReserved = 0; long totalCommittedSum = 0, totalReservedSum = 0; - // Match '- (reserved=KB, committed=KB) - Pattern mtTypePattern = Pattern.compile("-\\s+(?[\\w\\s]+)\\(reserved=(?\\d+)KB,\\scommitted=(?\\d+)KB\\)"); + // Match '- (reserved=KB, committed=KB) and some times readonly=KB + Pattern mtTypePattern = Pattern.compile("-\\s+(?[\\w\\s]+)\\(reserved=(?\\d+)KB,\\scommitted=(?\\d+)KB((,\\sreadonly=(?\\d+)KB)|)\\)"); // Match 'Total: reserved=KB, committed=KB' Pattern totalMemoryPattern = Pattern.compile("Total\\:\\sreserved=(?\\d+)KB,\\scommitted=(?\\d+)KB"); @@ -85,6 +85,16 @@ public class SummarySanityCheck { long typeCommitted = Long.parseLong(typeMatcher.group("committed")); long typeReserved = Long.parseLong(typeMatcher.group("reserved")); + // Only Shared class space has readonly component + if (lines[i].contains("Shared class space") && typeMatcher.group("readonly") != null) { + long typeReadOnly = Long.parseLong(typeMatcher.group("readonly")); + // Make sure readonly is always less or equal to committed + if (typeReadOnly > typeCommitted) { + throwTestException("Readonly (" + typeReadOnly + ") was more than Committed (" + + typeCommitted + ") for mtType: " + typeMatcher.group("typename")); + } + } + // Make sure reserved is always less or equals if (typeCommitted > typeReserved) { throwTestException("Committed (" + typeCommitted + ") was more than Reserved ("