< prev index next >

src/share/vm/memory/filemap.cpp

Print this page

        

*** 349,359 **** } size_t len = lseek(fd, 0, SEEK_END); struct FileMapInfo::FileMapHeader::space_info* si = &_header->_space[MetaspaceShared::last_valid_region]; ! if (si->_file_offset >= len || len - si->_file_offset < si->_used) { fail_continue("The shared archive file has been truncated."); return false; } _file_offset += (long)n; --- 349,360 ---- } size_t len = lseek(fd, 0, SEEK_END); struct FileMapInfo::FileMapHeader::space_info* si = &_header->_space[MetaspaceShared::last_valid_region]; ! // The last space might be empty ! if (si->_file_offset > len || len - si->_file_offset < si->_used) { fail_continue("The shared archive file has been truncated."); return false; } _file_offset += (long)n;
*** 441,451 **** " bytes, addr " INTPTR_FORMAT " file offset " SIZE_FORMAT_HEX_W(08), region, size, p2i(base), _file_offset); } else { si->_file_offset = _file_offset; } ! if (MetaspaceShared::is_string_region(region)) { assert((base - (char*)Universe::narrow_oop_base()) % HeapWordSize == 0, "Sanity"); if (base != NULL) { si->_addr._offset = (intx)oopDesc::encode_heap_oop_not_null((oop)base); } else { si->_addr._offset = 0; --- 442,452 ---- " bytes, addr " INTPTR_FORMAT " file offset " SIZE_FORMAT_HEX_W(08), region, size, p2i(base), _file_offset); } else { si->_file_offset = _file_offset; } ! if (MetaspaceShared::is_heap_region(region)) { assert((base - (char*)Universe::narrow_oop_base()) % HeapWordSize == 0, "Sanity"); if (base != NULL) { si->_addr._offset = (intx)oopDesc::encode_heap_oop_not_null((oop)base); } else { si->_addr._offset = 0;
*** 458,537 **** si->_allow_exec = allow_exec; si->_crc = ClassLoader::crc32(0, base, (jint)size); write_bytes_aligned(base, (int)size); } ! // Write the string space. The string space contains one or multiple GC(G1) regions. ! // When the total string space size is smaller than one GC region of the dump time, ! // only one string region is used for shared strings. // ! // If the total string space size is bigger than one GC region, there would be more ! // than one GC regions allocated for shared strings. The first/bottom GC region might // be a partial GC region with the empty portion at the higher address within that region. ! // The non-empty portion of the first region is written into the archive as one string // region. The rest are consecutive full GC regions if they exist, which can be written ! // out in one chunk as another string region. // ! // Here's the mapping from (GrowableArray<MemRegion> *regions) -> (metaspace string regions). ! // + We have 1 or more heap regions: r0, r1, r2 ..... rn ! // + We have 2 metaspace string regions: s0 and s1 // ! // If there's a single heap region (r0), then s0 == r0, and s1 is empty. // Otherwise: // // "X" represented space that's occupied by heap objects. // "_" represented unused spaced in the heap region. // // ! // |r0 | r1 | r2 | ...... | rn | // |XXXXXX|__ |XXXXX|XXXX|XXXXXXXX|XXXX| ! // |<-s0->| |<- s1 ----------------->| // ^^^ // | ! // +-- unmapped space ! void FileMapInfo::write_string_regions(GrowableArray<MemRegion> *regions, ! char** st0_start, char** st0_top, char** st0_end, ! char** st1_start, char** st1_top, char** st1_end) { ! *st0_start = *st0_top = *st0_end = NULL; ! *st1_start = *st1_top = *st1_end = NULL; ! ! assert(MetaspaceShared::max_strings == 2, "this loop doesn't work for any other value"); ! for (int i = MetaspaceShared::first_string; ! i < MetaspaceShared::first_string + MetaspaceShared::max_strings; i++) { char* start = NULL; size_t size = 0; ! int len = regions->length(); ! if (len > 0) { ! if (i == MetaspaceShared::first_string) { ! MemRegion first = regions->first(); ! start = (char*)first.start(); ! size = first.byte_size(); ! *st0_start = start; ! *st0_top = start + size; ! if (len > 1) { ! *st0_end = (char*)regions->at(1).start(); ! } else { ! *st0_end = start + size; ! } } else { ! assert(i == MetaspaceShared::first_string + 1, "must be"); ! if (len > 1) { ! start = (char*)regions->at(1).start(); ! size = (char*)regions->at(len - 1).end() - start; ! *st1_start = start; ! *st1_top = start + size; ! *st1_end = start + size; } ! } ! } ! log_info(cds)("String region %d " INTPTR_FORMAT " - " INTPTR_FORMAT " = " SIZE_FORMAT_W(8) " bytes", i, p2i(start), p2i(start + size), size); write_region(i, start, size, false, false); } } - // Dump bytes to file -- at the current file position. void FileMapInfo::write_bytes(const void* buffer, int nbytes) { if (_file_open) { int n = ::write(_fd, buffer, nbytes); --- 459,529 ---- si->_allow_exec = allow_exec; si->_crc = ClassLoader::crc32(0, base, (jint)size); write_bytes_aligned(base, (int)size); } ! // Write the current archive heap region, which contains one or multiple GC(G1) regions. ! // When current archive heap region size is smaller than one GC region of the dump time, ! // all archive heap data is written out as one region. // ! // If the current archive heap region size is bigger than one GC region, there would be more ! // than one GC regions allocated for archive heap data. The first/bottom GC region might // be a partial GC region with the empty portion at the higher address within that region. ! // The non-empty portion of the first region is written into the archive as one archive // region. The rest are consecutive full GC regions if they exist, which can be written ! // out in one chunk as another archive region. // ! // Here's the mapping from (archive heap regions) -> (GrowableArray<MemRegion> *regions). ! // + We have 1 or more archive heap regions: ah0, ah1, ah2 ..... ahn ! // + We have 2 consolidate heap memory regions: r0 and r1 // ! // If there's a single archive heap region (ah0), then r0 == ah0, and r1 is empty. // Otherwise: // // "X" represented space that's occupied by heap objects. // "_" represented unused spaced in the heap region. // // ! // |ah0 | ah1 | ah2| ...... | ahn | // |XXXXXX|__ |XXXXX|XXXX|XXXXXXXX|XXXX| ! // |<-r0->| |<- r1 ----------------->| // ^^^ // | ! // +-- gap ! void FileMapInfo::write_archive_heap_regions(GrowableArray<MemRegion> *regions, ! int first_region, int max_num_regions, ! char** r0_start, char** r0_top, ! char** r1_start, char** r1_top) { ! int arr_len = regions == NULL ? 0 : regions->length(); ! assert(max_num_regions <= 2, "this loop doesn't work for any other value"); ! assert(arr_len <= max_num_regions, "number of memory regions exceeds maximum"); ! ! *r0_start = *r0_top = NULL; ! *r1_start = *r1_top = NULL; ! ! for (int i = first_region, arr_idx = 0; i < first_region + max_num_regions; i++, arr_idx++) { char* start = NULL; size_t size = 0; ! if (arr_idx < arr_len) { ! start = (char*)regions->at(arr_idx).start(); ! size = regions->at(arr_idx).byte_size(); ! } ! if (i == first_region) { ! *r0_start = start; ! *r0_top = start + size; } else { ! assert(i == first_region + 1, "must be"); ! *r1_start = start; ! *r1_top = start + size; } ! ! log_info(cds)("Archive heap region %d " INTPTR_FORMAT " - " INTPTR_FORMAT " = " SIZE_FORMAT_W(8) " bytes", i, p2i(start), p2i(start + size), size); write_region(i, start, size, false, false); } } // Dump bytes to file -- at the current file position. void FileMapInfo::write_bytes(const void* buffer, int nbytes) { if (_file_open) { int n = ::write(_fd, buffer, nbytes);
*** 639,653 **** return rs; } // Memory map a region in the address space. ! static const char* shared_region_name[] = { "ReadOnly", "ReadWrite", "MiscData", "MiscCode", ! "String1", "String2", "OptionalData" }; char* FileMapInfo::map_region(int i) { ! assert(!MetaspaceShared::is_string_region(i), "sanity"); struct FileMapInfo::FileMapHeader::space_info* si = &_header->_space[i]; size_t used = si->_used; size_t alignment = os::vm_allocation_granularity(); size_t size = align_up(used, alignment); char *requested_addr = _header->region_addr(i); --- 631,645 ---- return rs; } // Memory map a region in the address space. ! static const char* shared_region_name[] = { "MiscData", "ReadWrite", "ReadOnly", "MiscCode", "OptionalData", ! "String1", "String2", "OpenArchive1", "OpenArchive2" }; char* FileMapInfo::map_region(int i) { ! assert(!MetaspaceShared::is_heap_region(i), "sanity"); struct FileMapInfo::FileMapHeader::space_info* si = &_header->_space[i]; size_t used = si->_used; size_t alignment = os::vm_allocation_granularity(); size_t size = align_up(used, alignment); char *requested_addr = _header->region_addr(i);
*** 673,794 **** return base; } static MemRegion *string_ranges = NULL; ! static int num_ranges = 0; ! bool FileMapInfo::map_string_regions() { ! #if INCLUDE_ALL_GCS ! if (UseG1GC && UseCompressedOops && UseCompressedClassPointers) { // Check that all the narrow oop and klass encodings match the archive if (narrow_oop_mode() != Universe::narrow_oop_mode() || narrow_oop_shift() != Universe::narrow_oop_shift() || narrow_klass_base() != Universe::narrow_klass_base() || narrow_klass_shift() != Universe::narrow_klass_shift()) { if (log_is_enabled(Info, cds) && _header->_space[MetaspaceShared::first_string]._used > 0) { ! log_info(cds)("Shared string data from the CDS archive is being ignored. " "The current CompressedOops/CompressedClassPointers encoding differs from " "that archived due to heap size change. The archive was dumped using max heap " "size " UINTX_FORMAT "M.", max_heap_size()/M); } } else { ! string_ranges = new MemRegion[MetaspaceShared::max_strings]; struct FileMapInfo::FileMapHeader::space_info* si; ! for (int i = MetaspaceShared::first_string; ! i < MetaspaceShared::first_string + MetaspaceShared::max_strings; i++) { si = &_header->_space[i]; size_t used = si->_used; if (used > 0) { size_t size = used; char* requested_addr = (char*)((void*)oopDesc::decode_heap_oop_not_null( (narrowOop)si->_addr._offset)); ! string_ranges[num_ranges] = MemRegion((HeapWord*)requested_addr, size / HeapWordSize); ! num_ranges ++; } } ! if (num_ranges == 0) { ! StringTable::ignore_shared_strings(true); ! return true; // no shared string data } // Check that ranges are within the java heap ! if (!G1CollectedHeap::heap()->check_archive_addresses(string_ranges, num_ranges)) { ! fail_continue("Unable to allocate shared string space: range is not " ! "within java heap."); return false; } // allocate from java heap ! if (!G1CollectedHeap::heap()->alloc_archive_regions(string_ranges, num_ranges)) { ! fail_continue("Unable to allocate shared string space: range is " ! "already in use."); return false; } ! // Map the string data. No need to call MemTracker::record_virtual_memory_type() ! // for mapped string regions as they are part of the reserved java heap, which ! // is already recorded. ! for (int i = 0; i < num_ranges; i++) { ! si = &_header->_space[MetaspaceShared::first_string + i]; ! char* addr = (char*)string_ranges[i].start(); char* base = os::map_memory(_fd, _full_path, si->_file_offset, ! addr, string_ranges[i].byte_size(), si->_read_only, si->_allow_exec); if (base == NULL || base != addr) { ! // dealloc the string regions from java heap ! dealloc_string_regions(); ! fail_continue("Unable to map shared string space at required address."); ! return false; ! } } - - if (!verify_string_regions()) { - // dealloc the string regions from java heap - dealloc_string_regions(); - fail_continue("Shared string regions are corrupt"); return false; } - - // the shared string data is mapped successfully - return true; } ! } else { ! if (log_is_enabled(Info, cds) && _header->_space[MetaspaceShared::first_string]._used > 0) { ! log_info(cds)("Shared string data from the CDS archive is being ignored. UseG1GC, " ! "UseCompressedOops and UseCompressedClassPointers are required."); } } ! // if we get here, the shared string data is not mapped ! assert(string_ranges == NULL && num_ranges == 0, "sanity"); ! StringTable::ignore_shared_strings(true); ! #endif return true; } ! bool FileMapInfo::verify_string_regions() { ! for (int i = MetaspaceShared::first_string; ! i < MetaspaceShared::first_string + MetaspaceShared::max_strings; i++) { if (!verify_region_checksum(i)) { return false; } } return true; } ! void FileMapInfo::fixup_string_regions() { ! #if INCLUDE_ALL_GCS // If any string regions were found, call the fill routine to make them parseable. // Note that string_ranges may be non-NULL even if no ranges were found. ! if (num_ranges != 0) { assert(string_ranges != NULL, "Null string_ranges array with non-zero count"); ! G1CollectedHeap::heap()->fill_archive_regions(string_ranges, num_ranges); } - #endif } bool FileMapInfo::verify_region_checksum(int i) { if (!VerifySharedSpaces) { return true; } --- 665,851 ---- return base; } static MemRegion *string_ranges = NULL; ! static MemRegion *open_archive_heap_ranges = NULL; ! static int num_string_ranges = 0; ! static int num_open_archive_heap_ranges = 0; ! ! #if INCLUDE_CDS_JAVA_HEAP ! // ! // Map the string regions and open archive heap regions to the runtime java ! // heap. ! // ! // The archive string regions are mapped near the runtime java heap top. The ! // mapped string regions contain no out-going references to any other java heap ! // regions. GC does not write into the string regions. ! // ! // The open archive heap regions are mapped below the string regions in ! // the runtime java heap. The mapped open archive heap regions may contain ! // out-going references to the string regions or other java heap regions. ! // Objects inside the open archive heap regions may be marked by GC and ! // the references are updated by GC. ! // ! void FileMapInfo::map_heap_regions() { ! if (MetaspaceShared::allow_archive_heap_object()) { // Check that all the narrow oop and klass encodings match the archive if (narrow_oop_mode() != Universe::narrow_oop_mode() || narrow_oop_shift() != Universe::narrow_oop_shift() || narrow_klass_base() != Universe::narrow_klass_base() || narrow_klass_shift() != Universe::narrow_klass_shift()) { if (log_is_enabled(Info, cds) && _header->_space[MetaspaceShared::first_string]._used > 0) { ! log_info(cds)("Cached heap data from the CDS archive is being ignored. " "The current CompressedOops/CompressedClassPointers encoding differs from " "that archived due to heap size change. The archive was dumped using max heap " "size " UINTX_FORMAT "M.", max_heap_size()/M); } } else { ! // First, map string regions as closed archive heap regions. ! // GC does not write into the regions. ! if (map_heap_data(&string_ranges, ! MetaspaceShared::first_string, ! MetaspaceShared::max_strings, ! &num_string_ranges)) { ! StringTable::set_shared_string_mapped(); ! ! // Now, map open_archive heap regions, GC can write into the regions. ! if (map_heap_data(&open_archive_heap_ranges, ! MetaspaceShared::first_open_archive_heap_region, ! MetaspaceShared::max_open_archive_heap_region, ! &num_open_archive_heap_ranges, ! true /* open */)) { ! MetaspaceShared::set_open_archive_heap_region_mapped(); ! } ! } ! } ! } else { ! if (log_is_enabled(Info, cds) && _header->_space[MetaspaceShared::first_string]._used > 0) { ! log_info(cds)("Cached heap data from the CDS archive is being ignored. UseG1GC, " ! "UseCompressedOops and UseCompressedClassPointers are required."); ! } ! } ! ! if (!StringTable::shared_string_mapped()) { ! assert(string_ranges == NULL && num_string_ranges == 0, "sanity"); ! } ! ! if (!MetaspaceShared::open_archive_heap_region_mapped()) { ! assert(open_archive_heap_ranges == NULL && num_open_archive_heap_ranges == 0, "sanity"); ! } ! } ! ! bool FileMapInfo::map_heap_data(MemRegion **mem_regions, int first, ! int max, int* num, bool is_open_archive) { ! MemRegion * regions = new MemRegion[max]; struct FileMapInfo::FileMapHeader::space_info* si; + int region_num = 0; ! for (int i = first; ! i < first + max; i++) { si = &_header->_space[i]; size_t used = si->_used; if (used > 0) { size_t size = used; char* requested_addr = (char*)((void*)oopDesc::decode_heap_oop_not_null( (narrowOop)si->_addr._offset)); ! regions[region_num] = MemRegion((HeapWord*)requested_addr, size / HeapWordSize); ! region_num ++; } } ! if (region_num == 0) { ! return false; // no archived java heap data } // Check that ranges are within the java heap ! if (!G1CollectedHeap::heap()->check_archive_addresses(regions, region_num)) { ! if (log_is_enabled(Info, cds)) { ! log_info(cds)("UseSharedSpaces: Unable to allocate region, " ! "range is not within java heap."); ! } return false; } // allocate from java heap ! if (!G1CollectedHeap::heap()->alloc_archive_regions( ! regions, region_num, is_open_archive)) { ! if (log_is_enabled(Info, cds)) { ! log_info(cds)("UseSharedSpaces: Unable to allocate region, " ! "java heap range is already in use."); ! } return false; } ! // Map the archived heap data. No need to call MemTracker::record_virtual_memory_type() ! // for mapped regions as they are part of the reserved java heap, which is ! // already recorded. ! for (int i = 0; i < region_num; i++) { ! si = &_header->_space[first + i]; ! char* addr = (char*)regions[i].start(); char* base = os::map_memory(_fd, _full_path, si->_file_offset, ! addr, regions[i].byte_size(), si->_read_only, si->_allow_exec); if (base == NULL || base != addr) { ! // dealloc the regions from java heap ! dealloc_archive_heap_regions(regions, region_num); ! if (log_is_enabled(Info, cds)) { ! log_info(cds)("UseSharedSpaces: Unable to map at required address in java heap."); } return false; } } ! ! if (!verify_mapped_heap_regions(first, region_num)) { ! // dealloc the regions from java heap ! dealloc_archive_heap_regions(regions, region_num); ! if (log_is_enabled(Info, cds)) { ! log_info(cds)("UseSharedSpaces: mapped heap regions are corrupt"); } + return false; } ! // the shared heap data is mapped successfully ! *mem_regions = regions; ! *num = region_num; return true; } ! bool FileMapInfo::verify_mapped_heap_regions(int first, int num) { ! for (int i = first; ! i <= first + num; i++) { if (!verify_region_checksum(i)) { return false; } } return true; } ! void FileMapInfo::fixup_mapped_heap_regions() { // If any string regions were found, call the fill routine to make them parseable. // Note that string_ranges may be non-NULL even if no ranges were found. ! if (num_string_ranges != 0) { assert(string_ranges != NULL, "Null string_ranges array with non-zero count"); ! G1CollectedHeap::heap()->fill_archive_regions(string_ranges, num_string_ranges); ! } ! ! // do the same for mapped open archive heap regions ! if (num_open_archive_heap_ranges != 0) { ! assert(open_archive_heap_ranges != NULL, "NULL open_archive_heap_ranges array with non-zero count"); ! G1CollectedHeap::heap()->fill_archive_regions(open_archive_heap_ranges, ! num_open_archive_heap_ranges); ! } ! } ! ! // dealloc the archive regions from java heap ! void FileMapInfo::dealloc_archive_heap_regions(MemRegion* regions, int num) { ! if (num > 0) { ! assert(regions != NULL, "Null archive ranges array with non-zero count"); ! G1CollectedHeap::heap()->dealloc_archive_regions(regions, num); } } + #endif // INCLUDE_CDS_JAVA_HEAP bool FileMapInfo::verify_region_checksum(int i) { if (!VerifySharedSpaces) { return true; }
*** 796,807 **** size_t sz = _header->_space[i]._used; if (sz == 0) { return true; // no data } ! if (MetaspaceShared::is_string_region(i) && StringTable::shared_string_ignored()) { ! return true; // shared string data are not mapped } const char* buf = _header->region_addr(i); int crc = ClassLoader::crc32(0, buf, (jint)sz); if (crc != _header->_space[i]._crc) { fail_continue("Checksum verification failed."); --- 853,867 ---- size_t sz = _header->_space[i]._used; if (sz == 0) { return true; // no data } ! if ((MetaspaceShared::is_string_region(i) && ! !StringTable::shared_string_mapped()) || ! (MetaspaceShared::is_open_archive_heap_region(i) && ! !MetaspaceShared::open_archive_heap_region_mapped())) { ! return true; // archived heap data is not mapped } const char* buf = _header->region_addr(i); int crc = ClassLoader::crc32(0, buf, (jint)sz); if (crc != _header->_space[i]._crc) { fail_continue("Checksum verification failed.");
*** 811,821 **** } // Unmap a memory region in the address space. void FileMapInfo::unmap_region(int i) { ! assert(!MetaspaceShared::is_string_region(i), "sanity"); struct FileMapInfo::FileMapHeader::space_info* si = &_header->_space[i]; size_t used = si->_used; size_t size = align_up(used, os::vm_allocation_granularity()); if (used == 0) { --- 871,881 ---- } // Unmap a memory region in the address space. void FileMapInfo::unmap_region(int i) { ! assert(!MetaspaceShared::is_heap_region(i), "sanity"); struct FileMapInfo::FileMapHeader::space_info* si = &_header->_space[i]; size_t used = si->_used; size_t size = align_up(used, os::vm_allocation_granularity()); if (used == 0) {
*** 826,845 **** if (!os::unmap_memory(addr, size)) { fail_stop("Unable to unmap shared space."); } } - // dealloc the archived string region from java heap - void FileMapInfo::dealloc_string_regions() { - #if INCLUDE_ALL_GCS - if (num_ranges > 0) { - assert(string_ranges != NULL, "Null string_ranges array with non-zero count"); - G1CollectedHeap::heap()->dealloc_archive_regions(string_ranges, num_ranges); - } - #endif - } - void FileMapInfo::assert_mark(bool check) { if (!check) { fail_stop("Mark mismatch while restoring from shared file."); } } --- 886,895 ----
*** 881,893 **** } return true; } char* FileMapInfo::FileMapHeader::region_addr(int idx) { ! if (MetaspaceShared::is_string_region(idx)) { ! return (char*)((void*)oopDesc::decode_heap_oop_not_null( ! (narrowOop)_space[idx]._addr._offset)); } else { return _space[idx]._addr._base; } } --- 931,943 ---- } return true; } char* FileMapInfo::FileMapHeader::region_addr(int idx) { ! if (MetaspaceShared::is_heap_region(idx)) { ! return _space[idx]._used > 0 ? ! (char*)((void*)oopDesc::decode_heap_oop_not_null((narrowOop)_space[idx]._addr._offset)) : NULL; } else { return _space[idx]._addr._base; } }
*** 963,981 **** } return status; } // The following method is provided to see whether a given pointer ! // falls in the mapped shared space. // Param: // p, The given pointer // Return: // True if the p is within the mapped shared space, otherwise, false. bool FileMapInfo::is_in_shared_space(const void* p) { ! for (int i = 0; i < MetaspaceShared::n_regions; i++) { char *base; ! if (MetaspaceShared::is_string_region(i) && _header->_space[i]._used == 0) { continue; } base = _header->region_addr(i); if (p >= base && p < base + _header->_space[i]._used) { return true; --- 1013,1031 ---- } return status; } // The following method is provided to see whether a given pointer ! // falls in the mapped shared metadata space. // Param: // p, The given pointer // Return: // True if the p is within the mapped shared space, otherwise, false. bool FileMapInfo::is_in_shared_space(const void* p) { ! for (int i = 0; i < MetaspaceShared::num_non_heap_spaces; i++) { char *base; ! if (_header->_space[i]._used == 0) { continue; } base = _header->region_addr(i); if (p >= base && p < base + _header->_space[i]._used) { return true;
*** 983,993 **** } return false; } ! // Check if a given address is within one of the shared regions ( ro, rw, mc or md) bool FileMapInfo::is_in_shared_region(const void* p, int idx) { assert(idx == MetaspaceShared::ro || idx == MetaspaceShared::rw || idx == MetaspaceShared::mc || idx == MetaspaceShared::md, "invalid region index"); --- 1033,1043 ---- } return false; } ! // Check if a given address is within one of the shared regions bool FileMapInfo::is_in_shared_region(const void* p, int idx) { assert(idx == MetaspaceShared::ro || idx == MetaspaceShared::rw || idx == MetaspaceShared::mc || idx == MetaspaceShared::md, "invalid region index");
*** 1012,1030 **** // Unmap mapped regions of shared space. void FileMapInfo::stop_sharing_and_unmap(const char* msg) { FileMapInfo *map_info = FileMapInfo::current_info(); if (map_info) { map_info->fail_continue("%s", msg); ! for (int i = 0; i < MetaspaceShared::num_non_strings; i++) { char *addr = map_info->_header->region_addr(i); ! if (addr != NULL && !MetaspaceShared::is_string_region(i)) { map_info->unmap_region(i); map_info->_header->_space[i]._addr._base = NULL; } } ! // Dealloc the string regions only without unmapping. The string regions are part // of the java heap. Unmapping of the heap regions are managed by GC. ! map_info->dealloc_string_regions(); } else if (DumpSharedSpaces) { fail_stop("%s", msg); } } --- 1062,1082 ---- // Unmap mapped regions of shared space. void FileMapInfo::stop_sharing_and_unmap(const char* msg) { FileMapInfo *map_info = FileMapInfo::current_info(); if (map_info) { map_info->fail_continue("%s", msg); ! for (int i = 0; i < MetaspaceShared::num_non_heap_spaces; i++) { char *addr = map_info->_header->region_addr(i); ! if (addr != NULL && !MetaspaceShared::is_heap_region(i)) { map_info->unmap_region(i); map_info->_header->_space[i]._addr._base = NULL; } } ! // Dealloc the archive heap regions only without unmapping. The regions are part // of the java heap. Unmapping of the heap regions are managed by GC. ! map_info->dealloc_archive_heap_regions(open_archive_heap_ranges, ! num_open_archive_heap_ranges); ! map_info->dealloc_archive_heap_regions(string_ranges, num_string_ranges); } else if (DumpSharedSpaces) { fail_stop("%s", msg); } }
< prev index next >