Mercurial > hg > truffle
annotate src/share/vm/gc_implementation/parallelScavenge/psParallelCompact.cpp @ 8733:9def4075da6d
8008079: G1: Add nextObject routine to CMBitMapRO and replace nextWord
Summary: Update the task local finger to the start of the next object when marking aborts, in order to avoid the redundant scanning of all 0's when the marking task restarts, if otherwise updating to the next word. In addition, reuse the routine nextObject() in routine iterate().
Reviewed-by: johnc, ysr
Contributed-by: tamao <tao.mao@oracle.com>
author | tamao |
---|---|
date | Tue, 05 Mar 2013 15:36:56 -0800 |
parents | b735136e0d82 |
children | 7b835924c31c |
rev | line source |
---|---|
0 | 1 /* |
4872
aa3d708d67c4
7141200: log some interesting information in ring buffers for crashes
never
parents:
4712
diff
changeset
|
2 * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved. |
0 | 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. |
4 * | |
5 * This code is free software; you can redistribute it and/or modify it | |
6 * under the terms of the GNU General Public License version 2 only, as | |
7 * published by the Free Software Foundation. | |
8 * | |
9 * This code is distributed in the hope that it will be useful, but WITHOUT | |
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | |
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | |
12 * version 2 for more details (a copy is included in the LICENSE file that | |
13 * accompanied this code). | |
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 * | |
1552
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
1489
diff
changeset
|
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA |
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
1489
diff
changeset
|
20 * or visit www.oracle.com if you need additional information or have any |
c18cbe5936b8
6941466: Oracle rebranding changes for Hotspot repositories
trims
parents:
1489
diff
changeset
|
21 * questions. |
0 | 22 * |
23 */ | |
24 | |
1972 | 25 #include "precompiled.hpp" |
26 #include "classfile/symbolTable.hpp" | |
27 #include "classfile/systemDictionary.hpp" | |
28 #include "code/codeCache.hpp" | |
29 #include "gc_implementation/parallelScavenge/gcTaskManager.hpp" | |
30 #include "gc_implementation/parallelScavenge/generationSizer.hpp" | |
31 #include "gc_implementation/parallelScavenge/parallelScavengeHeap.inline.hpp" | |
32 #include "gc_implementation/parallelScavenge/pcTasks.hpp" | |
33 #include "gc_implementation/parallelScavenge/psAdaptiveSizePolicy.hpp" | |
34 #include "gc_implementation/parallelScavenge/psCompactionManager.inline.hpp" | |
35 #include "gc_implementation/parallelScavenge/psMarkSweep.hpp" | |
36 #include "gc_implementation/parallelScavenge/psMarkSweepDecorator.hpp" | |
37 #include "gc_implementation/parallelScavenge/psOldGen.hpp" | |
38 #include "gc_implementation/parallelScavenge/psParallelCompact.hpp" | |
39 #include "gc_implementation/parallelScavenge/psPromotionManager.inline.hpp" | |
40 #include "gc_implementation/parallelScavenge/psScavenge.hpp" | |
41 #include "gc_implementation/parallelScavenge/psYoungGen.hpp" | |
42 #include "gc_implementation/shared/isGCActiveMark.hpp" | |
43 #include "gc_interface/gcCause.hpp" | |
44 #include "memory/gcLocker.inline.hpp" | |
45 #include "memory/referencePolicy.hpp" | |
46 #include "memory/referenceProcessor.hpp" | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
47 #include "oops/methodData.hpp" |
1972 | 48 #include "oops/oop.inline.hpp" |
49 #include "oops/oop.pcgc.inline.hpp" | |
50 #include "runtime/fprofiler.hpp" | |
51 #include "runtime/safepoint.hpp" | |
52 #include "runtime/vmThread.hpp" | |
53 #include "services/management.hpp" | |
54 #include "services/memoryService.hpp" | |
6197 | 55 #include "services/memTracker.hpp" |
1972 | 56 #include "utilities/events.hpp" |
57 #include "utilities/stack.inline.hpp" | |
0 | 58 |
59 #include <math.h> | |
60 | |
61 // All sizes are in HeapWords. | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
62 const size_t ParallelCompactData::Log2RegionSize = 9; // 512 words |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
63 const size_t ParallelCompactData::RegionSize = (size_t)1 << Log2RegionSize; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
64 const size_t ParallelCompactData::RegionSizeBytes = |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
65 RegionSize << LogHeapWordSize; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
66 const size_t ParallelCompactData::RegionSizeOffsetMask = RegionSize - 1; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
67 const size_t ParallelCompactData::RegionAddrOffsetMask = RegionSizeBytes - 1; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
68 const size_t ParallelCompactData::RegionAddrMask = ~RegionAddrOffsetMask; |
0 | 69 |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
70 const ParallelCompactData::RegionData::region_sz_t |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
71 ParallelCompactData::RegionData::dc_shift = 27; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
72 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
73 const ParallelCompactData::RegionData::region_sz_t |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
74 ParallelCompactData::RegionData::dc_mask = ~0U << dc_shift; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
75 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
76 const ParallelCompactData::RegionData::region_sz_t |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
77 ParallelCompactData::RegionData::dc_one = 0x1U << dc_shift; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
78 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
79 const ParallelCompactData::RegionData::region_sz_t |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
80 ParallelCompactData::RegionData::los_mask = ~dc_mask; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
81 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
82 const ParallelCompactData::RegionData::region_sz_t |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
83 ParallelCompactData::RegionData::dc_claimed = 0x8U << dc_shift; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
84 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
85 const ParallelCompactData::RegionData::region_sz_t |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
86 ParallelCompactData::RegionData::dc_completed = 0xcU << dc_shift; |
0 | 87 |
88 SpaceInfo PSParallelCompact::_space_info[PSParallelCompact::last_space_id]; | |
89 bool PSParallelCompact::_print_phases = false; | |
90 | |
91 ReferenceProcessor* PSParallelCompact::_ref_processor = NULL; | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
92 Klass* PSParallelCompact::_updated_int_array_klass_obj = NULL; |
0 | 93 |
94 double PSParallelCompact::_dwl_mean; | |
95 double PSParallelCompact::_dwl_std_dev; | |
96 double PSParallelCompact::_dwl_first_term; | |
97 double PSParallelCompact::_dwl_adjustment; | |
98 #ifdef ASSERT | |
99 bool PSParallelCompact::_dwl_initialized = false; | |
100 #endif // #ifdef ASSERT | |
101 | |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
102 void SplitInfo::record(size_t src_region_idx, size_t partial_obj_size, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
103 HeapWord* destination) |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
104 { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
105 assert(src_region_idx != 0, "invalid src_region_idx"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
106 assert(partial_obj_size != 0, "invalid partial_obj_size argument"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
107 assert(destination != NULL, "invalid destination argument"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
108 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
109 _src_region_idx = src_region_idx; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
110 _partial_obj_size = partial_obj_size; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
111 _destination = destination; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
112 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
113 // These fields may not be updated below, so make sure they're clear. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
114 assert(_dest_region_addr == NULL, "should have been cleared"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
115 assert(_first_src_addr == NULL, "should have been cleared"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
116 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
117 // Determine the number of destination regions for the partial object. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
118 HeapWord* const last_word = destination + partial_obj_size - 1; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
119 const ParallelCompactData& sd = PSParallelCompact::summary_data(); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
120 HeapWord* const beg_region_addr = sd.region_align_down(destination); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
121 HeapWord* const end_region_addr = sd.region_align_down(last_word); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
122 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
123 if (beg_region_addr == end_region_addr) { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
124 // One destination region. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
125 _destination_count = 1; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
126 if (end_region_addr == destination) { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
127 // The destination falls on a region boundary, thus the first word of the |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
128 // partial object will be the first word copied to the destination region. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
129 _dest_region_addr = end_region_addr; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
130 _first_src_addr = sd.region_to_addr(src_region_idx); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
131 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
132 } else { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
133 // Two destination regions. When copied, the partial object will cross a |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
134 // destination region boundary, so a word somewhere within the partial |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
135 // object will be the first word copied to the second destination region. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
136 _destination_count = 2; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
137 _dest_region_addr = end_region_addr; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
138 const size_t ofs = pointer_delta(end_region_addr, destination); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
139 assert(ofs < _partial_obj_size, "sanity"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
140 _first_src_addr = sd.region_to_addr(src_region_idx) + ofs; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
141 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
142 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
143 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
144 void SplitInfo::clear() |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
145 { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
146 _src_region_idx = 0; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
147 _partial_obj_size = 0; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
148 _destination = NULL; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
149 _destination_count = 0; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
150 _dest_region_addr = NULL; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
151 _first_src_addr = NULL; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
152 assert(!is_valid(), "sanity"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
153 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
154 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
155 #ifdef ASSERT |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
156 void SplitInfo::verify_clear() |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
157 { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
158 assert(_src_region_idx == 0, "not clear"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
159 assert(_partial_obj_size == 0, "not clear"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
160 assert(_destination == NULL, "not clear"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
161 assert(_destination_count == 0, "not clear"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
162 assert(_dest_region_addr == NULL, "not clear"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
163 assert(_first_src_addr == NULL, "not clear"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
164 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
165 #endif // #ifdef ASSERT |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
166 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
167 |
0 | 168 #ifndef PRODUCT |
169 const char* PSParallelCompact::space_names[] = { | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
170 "old ", "eden", "from", "to " |
0 | 171 }; |
172 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
173 void PSParallelCompact::print_region_ranges() |
0 | 174 { |
175 tty->print_cr("space bottom top end new_top"); | |
176 tty->print_cr("------ ---------- ---------- ---------- ----------"); | |
177 | |
178 for (unsigned int id = 0; id < last_space_id; ++id) { | |
179 const MutableSpace* space = _space_info[id].space(); | |
180 tty->print_cr("%u %s " | |
264
15dd2594d08e
6718283: existing uses of *_FORMAT_W() were broken by 6521491
jcoomes
parents:
263
diff
changeset
|
181 SIZE_FORMAT_W(10) " " SIZE_FORMAT_W(10) " " |
15dd2594d08e
6718283: existing uses of *_FORMAT_W() were broken by 6521491
jcoomes
parents:
263
diff
changeset
|
182 SIZE_FORMAT_W(10) " " SIZE_FORMAT_W(10) " ", |
0 | 183 id, space_names[id], |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
184 summary_data().addr_to_region_idx(space->bottom()), |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
185 summary_data().addr_to_region_idx(space->top()), |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
186 summary_data().addr_to_region_idx(space->end()), |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
187 summary_data().addr_to_region_idx(_space_info[id].new_top())); |
0 | 188 } |
189 } | |
190 | |
191 void | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
192 print_generic_summary_region(size_t i, const ParallelCompactData::RegionData* c) |
0 | 193 { |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
194 #define REGION_IDX_FORMAT SIZE_FORMAT_W(7) |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
195 #define REGION_DATA_FORMAT SIZE_FORMAT_W(5) |
0 | 196 |
197 ParallelCompactData& sd = PSParallelCompact::summary_data(); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
198 size_t dci = c->destination() ? sd.addr_to_region_idx(c->destination()) : 0; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
199 tty->print_cr(REGION_IDX_FORMAT " " PTR_FORMAT " " |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
200 REGION_IDX_FORMAT " " PTR_FORMAT " " |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
201 REGION_DATA_FORMAT " " REGION_DATA_FORMAT " " |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
202 REGION_DATA_FORMAT " " REGION_IDX_FORMAT " %d", |
0 | 203 i, c->data_location(), dci, c->destination(), |
204 c->partial_obj_size(), c->live_obj_size(), | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
205 c->data_size(), c->source_region(), c->destination_count()); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
206 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
207 #undef REGION_IDX_FORMAT |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
208 #undef REGION_DATA_FORMAT |
0 | 209 } |
210 | |
211 void | |
212 print_generic_summary_data(ParallelCompactData& summary_data, | |
213 HeapWord* const beg_addr, | |
214 HeapWord* const end_addr) | |
215 { | |
216 size_t total_words = 0; | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
217 size_t i = summary_data.addr_to_region_idx(beg_addr); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
218 const size_t last = summary_data.addr_to_region_idx(end_addr); |
0 | 219 HeapWord* pdest = 0; |
220 | |
221 while (i <= last) { | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
222 ParallelCompactData::RegionData* c = summary_data.region(i); |
0 | 223 if (c->data_size() != 0 || c->destination() != pdest) { |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
224 print_generic_summary_region(i, c); |
0 | 225 total_words += c->data_size(); |
226 pdest = c->destination(); | |
227 } | |
228 ++i; | |
229 } | |
230 | |
231 tty->print_cr("summary_data_bytes=" SIZE_FORMAT, total_words * HeapWordSize); | |
232 } | |
233 | |
234 void | |
235 print_generic_summary_data(ParallelCompactData& summary_data, | |
236 SpaceInfo* space_info) | |
237 { | |
238 for (unsigned int id = 0; id < PSParallelCompact::last_space_id; ++id) { | |
239 const MutableSpace* space = space_info[id].space(); | |
240 print_generic_summary_data(summary_data, space->bottom(), | |
241 MAX2(space->top(), space_info[id].new_top())); | |
242 } | |
243 } | |
244 | |
245 void | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
246 print_initial_summary_region(size_t i, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
247 const ParallelCompactData::RegionData* c, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
248 bool newline = true) |
0 | 249 { |
264
15dd2594d08e
6718283: existing uses of *_FORMAT_W() were broken by 6521491
jcoomes
parents:
263
diff
changeset
|
250 tty->print(SIZE_FORMAT_W(5) " " PTR_FORMAT " " |
15dd2594d08e
6718283: existing uses of *_FORMAT_W() were broken by 6521491
jcoomes
parents:
263
diff
changeset
|
251 SIZE_FORMAT_W(5) " " SIZE_FORMAT_W(5) " " |
15dd2594d08e
6718283: existing uses of *_FORMAT_W() were broken by 6521491
jcoomes
parents:
263
diff
changeset
|
252 SIZE_FORMAT_W(5) " " SIZE_FORMAT_W(5) " %d", |
0 | 253 i, c->destination(), |
254 c->partial_obj_size(), c->live_obj_size(), | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
255 c->data_size(), c->source_region(), c->destination_count()); |
0 | 256 if (newline) tty->cr(); |
257 } | |
258 | |
259 void | |
260 print_initial_summary_data(ParallelCompactData& summary_data, | |
261 const MutableSpace* space) { | |
262 if (space->top() == space->bottom()) { | |
263 return; | |
264 } | |
265 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
266 const size_t region_size = ParallelCompactData::RegionSize; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
267 typedef ParallelCompactData::RegionData RegionData; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
268 HeapWord* const top_aligned_up = summary_data.region_align_up(space->top()); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
269 const size_t end_region = summary_data.addr_to_region_idx(top_aligned_up); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
270 const RegionData* c = summary_data.region(end_region - 1); |
0 | 271 HeapWord* end_addr = c->destination() + c->data_size(); |
272 const size_t live_in_space = pointer_delta(end_addr, space->bottom()); | |
273 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
274 // Print (and count) the full regions at the beginning of the space. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
275 size_t full_region_count = 0; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
276 size_t i = summary_data.addr_to_region_idx(space->bottom()); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
277 while (i < end_region && summary_data.region(i)->data_size() == region_size) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
278 print_initial_summary_region(i, summary_data.region(i)); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
279 ++full_region_count; |
0 | 280 ++i; |
281 } | |
282 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
283 size_t live_to_right = live_in_space - full_region_count * region_size; |
0 | 284 |
285 double max_reclaimed_ratio = 0.0; | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
286 size_t max_reclaimed_ratio_region = 0; |
0 | 287 size_t max_dead_to_right = 0; |
288 size_t max_live_to_right = 0; | |
289 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
290 // Print the 'reclaimed ratio' for regions while there is something live in |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
291 // the region or to the right of it. The remaining regions are empty (and |
0 | 292 // uninteresting), and computing the ratio will result in division by 0. |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
293 while (i < end_region && live_to_right > 0) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
294 c = summary_data.region(i); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
295 HeapWord* const region_addr = summary_data.region_to_addr(i); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
296 const size_t used_to_right = pointer_delta(space->top(), region_addr); |
0 | 297 const size_t dead_to_right = used_to_right - live_to_right; |
298 const double reclaimed_ratio = double(dead_to_right) / live_to_right; | |
299 | |
300 if (reclaimed_ratio > max_reclaimed_ratio) { | |
301 max_reclaimed_ratio = reclaimed_ratio; | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
302 max_reclaimed_ratio_region = i; |
0 | 303 max_dead_to_right = dead_to_right; |
304 max_live_to_right = live_to_right; | |
305 } | |
306 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
307 print_initial_summary_region(i, c, false); |
264
15dd2594d08e
6718283: existing uses of *_FORMAT_W() were broken by 6521491
jcoomes
parents:
263
diff
changeset
|
308 tty->print_cr(" %12.10f " SIZE_FORMAT_W(10) " " SIZE_FORMAT_W(10), |
0 | 309 reclaimed_ratio, dead_to_right, live_to_right); |
310 | |
311 live_to_right -= c->data_size(); | |
312 ++i; | |
313 } | |
314 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
315 // Any remaining regions are empty. Print one more if there is one. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
316 if (i < end_region) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
317 print_initial_summary_region(i, summary_data.region(i)); |
0 | 318 } |
319 | |
264
15dd2594d08e
6718283: existing uses of *_FORMAT_W() were broken by 6521491
jcoomes
parents:
263
diff
changeset
|
320 tty->print_cr("max: " SIZE_FORMAT_W(4) " d2r=" SIZE_FORMAT_W(10) " " |
15dd2594d08e
6718283: existing uses of *_FORMAT_W() were broken by 6521491
jcoomes
parents:
263
diff
changeset
|
321 "l2r=" SIZE_FORMAT_W(10) " max_ratio=%14.12f", |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
322 max_reclaimed_ratio_region, max_dead_to_right, |
0 | 323 max_live_to_right, max_reclaimed_ratio); |
324 } | |
325 | |
326 void | |
327 print_initial_summary_data(ParallelCompactData& summary_data, | |
328 SpaceInfo* space_info) { | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
329 unsigned int id = PSParallelCompact::old_space_id; |
0 | 330 const MutableSpace* space; |
331 do { | |
332 space = space_info[id].space(); | |
333 print_initial_summary_data(summary_data, space); | |
334 } while (++id < PSParallelCompact::eden_space_id); | |
335 | |
336 do { | |
337 space = space_info[id].space(); | |
338 print_generic_summary_data(summary_data, space->bottom(), space->top()); | |
339 } while (++id < PSParallelCompact::last_space_id); | |
340 } | |
341 #endif // #ifndef PRODUCT | |
342 | |
343 #ifdef ASSERT | |
344 size_t add_obj_count; | |
345 size_t add_obj_size; | |
346 size_t mark_bitmap_count; | |
347 size_t mark_bitmap_size; | |
348 #endif // #ifdef ASSERT | |
349 | |
350 ParallelCompactData::ParallelCompactData() | |
351 { | |
352 _region_start = 0; | |
353 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
354 _region_vspace = 0; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
355 _region_data = 0; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
356 _region_count = 0; |
0 | 357 } |
358 | |
359 bool ParallelCompactData::initialize(MemRegion covered_region) | |
360 { | |
361 _region_start = covered_region.start(); | |
362 const size_t region_size = covered_region.word_size(); | |
363 DEBUG_ONLY(_region_end = _region_start + region_size;) | |
364 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
365 assert(region_align_down(_region_start) == _region_start, |
0 | 366 "region start not aligned"); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
367 assert((region_size & RegionSizeOffsetMask) == 0, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
368 "region size not a multiple of RegionSize"); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
369 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
370 bool result = initialize_region_data(region_size); |
0 | 371 |
372 return result; | |
373 } | |
374 | |
375 PSVirtualSpace* | |
376 ParallelCompactData::create_vspace(size_t count, size_t element_size) | |
377 { | |
378 const size_t raw_bytes = count * element_size; | |
379 const size_t page_sz = os::page_size_for_region(raw_bytes, raw_bytes, 10); | |
380 const size_t granularity = os::vm_allocation_granularity(); | |
381 const size_t bytes = align_size_up(raw_bytes, MAX2(page_sz, granularity)); | |
382 | |
383 const size_t rs_align = page_sz == (size_t) os::vm_page_size() ? 0 : | |
384 MAX2(page_sz, granularity); | |
79
82db0859acbe
6642862: Code cache allocation fails with large pages after 6588638
jcoomes
parents:
0
diff
changeset
|
385 ReservedSpace rs(bytes, rs_align, rs_align > 0); |
0 | 386 os::trace_page_sizes("par compact", raw_bytes, raw_bytes, page_sz, rs.base(), |
387 rs.size()); | |
6197 | 388 |
389 MemTracker::record_virtual_memory_type((address)rs.base(), mtGC); | |
390 | |
0 | 391 PSVirtualSpace* vspace = new PSVirtualSpace(rs, page_sz); |
392 if (vspace != 0) { | |
393 if (vspace->expand_by(bytes)) { | |
394 return vspace; | |
395 } | |
396 delete vspace; | |
237
1fdb98a17101
6716785: implicit null checks not triggering with CompressedOops
coleenp
parents:
235
diff
changeset
|
397 // Release memory reserved in the space. |
1fdb98a17101
6716785: implicit null checks not triggering with CompressedOops
coleenp
parents:
235
diff
changeset
|
398 rs.release(); |
0 | 399 } |
400 | |
401 return 0; | |
402 } | |
403 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
404 bool ParallelCompactData::initialize_region_data(size_t region_size) |
0 | 405 { |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
406 const size_t count = (region_size + RegionSizeOffsetMask) >> Log2RegionSize; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
407 _region_vspace = create_vspace(count, sizeof(RegionData)); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
408 if (_region_vspace != 0) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
409 _region_data = (RegionData*)_region_vspace->reserved_low_addr(); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
410 _region_count = count; |
0 | 411 return true; |
412 } | |
413 return false; | |
414 } | |
415 | |
416 void ParallelCompactData::clear() | |
417 { | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
418 memset(_region_data, 0, _region_vspace->committed_size()); |
0 | 419 } |
420 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
421 void ParallelCompactData::clear_range(size_t beg_region, size_t end_region) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
422 assert(beg_region <= _region_count, "beg_region out of range"); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
423 assert(end_region <= _region_count, "end_region out of range"); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
424 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
425 const size_t region_cnt = end_region - beg_region; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
426 memset(_region_data + beg_region, 0, region_cnt * sizeof(RegionData)); |
0 | 427 } |
428 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
429 HeapWord* ParallelCompactData::partial_obj_end(size_t region_idx) const |
0 | 430 { |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
431 const RegionData* cur_cp = region(region_idx); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
432 const RegionData* const end_cp = region(region_count() - 1); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
433 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
434 HeapWord* result = region_to_addr(region_idx); |
0 | 435 if (cur_cp < end_cp) { |
436 do { | |
437 result += cur_cp->partial_obj_size(); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
438 } while (cur_cp->partial_obj_size() == RegionSize && ++cur_cp < end_cp); |
0 | 439 } |
440 return result; | |
441 } | |
442 | |
443 void ParallelCompactData::add_obj(HeapWord* addr, size_t len) | |
444 { | |
445 const size_t obj_ofs = pointer_delta(addr, _region_start); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
446 const size_t beg_region = obj_ofs >> Log2RegionSize; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
447 const size_t end_region = (obj_ofs + len - 1) >> Log2RegionSize; |
0 | 448 |
449 DEBUG_ONLY(Atomic::inc_ptr(&add_obj_count);) | |
450 DEBUG_ONLY(Atomic::add_ptr(len, &add_obj_size);) | |
451 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
452 if (beg_region == end_region) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
453 // All in one region. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
454 _region_data[beg_region].add_live_obj(len); |
0 | 455 return; |
456 } | |
457 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
458 // First region. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
459 const size_t beg_ofs = region_offset(addr); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
460 _region_data[beg_region].add_live_obj(RegionSize - beg_ofs); |
0 | 461 |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
462 Klass* klass = ((oop)addr)->klass(); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
463 // Middle regions--completely spanned by this object. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
464 for (size_t region = beg_region + 1; region < end_region; ++region) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
465 _region_data[region].set_partial_obj_size(RegionSize); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
466 _region_data[region].set_partial_obj_addr(addr); |
0 | 467 } |
468 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
469 // Last region. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
470 const size_t end_ofs = region_offset(addr + len - 1); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
471 _region_data[end_region].set_partial_obj_size(end_ofs + 1); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
472 _region_data[end_region].set_partial_obj_addr(addr); |
0 | 473 } |
474 | |
475 void | |
476 ParallelCompactData::summarize_dense_prefix(HeapWord* beg, HeapWord* end) | |
477 { | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
478 assert(region_offset(beg) == 0, "not RegionSize aligned"); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
479 assert(region_offset(end) == 0, "not RegionSize aligned"); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
480 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
481 size_t cur_region = addr_to_region_idx(beg); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
482 const size_t end_region = addr_to_region_idx(end); |
0 | 483 HeapWord* addr = beg; |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
484 while (cur_region < end_region) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
485 _region_data[cur_region].set_destination(addr); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
486 _region_data[cur_region].set_destination_count(0); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
487 _region_data[cur_region].set_source_region(cur_region); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
488 _region_data[cur_region].set_data_location(addr); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
489 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
490 // Update live_obj_size so the region appears completely full. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
491 size_t live_size = RegionSize - _region_data[cur_region].partial_obj_size(); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
492 _region_data[cur_region].set_live_obj_size(live_size); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
493 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
494 ++cur_region; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
495 addr += RegionSize; |
0 | 496 } |
497 } | |
498 | |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
499 // Find the point at which a space can be split and, if necessary, record the |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
500 // split point. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
501 // |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
502 // If the current src region (which overflowed the destination space) doesn't |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
503 // have a partial object, the split point is at the beginning of the current src |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
504 // region (an "easy" split, no extra bookkeeping required). |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
505 // |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
506 // If the current src region has a partial object, the split point is in the |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
507 // region where that partial object starts (call it the split_region). If |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
508 // split_region has a partial object, then the split point is just after that |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
509 // partial object (a "hard" split where we have to record the split data and |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
510 // zero the partial_obj_size field). With a "hard" split, we know that the |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
511 // partial_obj ends within split_region because the partial object that caused |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
512 // the overflow starts in split_region. If split_region doesn't have a partial |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
513 // obj, then the split is at the beginning of split_region (another "easy" |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
514 // split). |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
515 HeapWord* |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
516 ParallelCompactData::summarize_split_space(size_t src_region, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
517 SplitInfo& split_info, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
518 HeapWord* destination, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
519 HeapWord* target_end, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
520 HeapWord** target_next) |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
521 { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
522 assert(destination <= target_end, "sanity"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
523 assert(destination + _region_data[src_region].data_size() > target_end, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
524 "region should not fit into target space"); |
696
f18338cf04b0
6810474: par compact - crash in summary_phase with very full heap
jcoomes
parents:
628
diff
changeset
|
525 assert(is_region_aligned(target_end), "sanity"); |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
526 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
527 size_t split_region = src_region; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
528 HeapWord* split_destination = destination; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
529 size_t partial_obj_size = _region_data[src_region].partial_obj_size(); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
530 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
531 if (destination + partial_obj_size > target_end) { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
532 // The split point is just after the partial object (if any) in the |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
533 // src_region that contains the start of the object that overflowed the |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
534 // destination space. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
535 // |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
536 // Find the start of the "overflow" object and set split_region to the |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
537 // region containing it. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
538 HeapWord* const overflow_obj = _region_data[src_region].partial_obj_addr(); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
539 split_region = addr_to_region_idx(overflow_obj); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
540 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
541 // Clear the source_region field of all destination regions whose first word |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
542 // came from data after the split point (a non-null source_region field |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
543 // implies a region must be filled). |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
544 // |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
545 // An alternative to the simple loop below: clear during post_compact(), |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
546 // which uses memcpy instead of individual stores, and is easy to |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
547 // parallelize. (The downside is that it clears the entire RegionData |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
548 // object as opposed to just one field.) |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
549 // |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
550 // post_compact() would have to clear the summary data up to the highest |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
551 // address that was written during the summary phase, which would be |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
552 // |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
553 // max(top, max(new_top, clear_top)) |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
554 // |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
555 // where clear_top is a new field in SpaceInfo. Would have to set clear_top |
696
f18338cf04b0
6810474: par compact - crash in summary_phase with very full heap
jcoomes
parents:
628
diff
changeset
|
556 // to target_end. |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
557 const RegionData* const sr = region(split_region); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
558 const size_t beg_idx = |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
559 addr_to_region_idx(region_align_up(sr->destination() + |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
560 sr->partial_obj_size())); |
696
f18338cf04b0
6810474: par compact - crash in summary_phase with very full heap
jcoomes
parents:
628
diff
changeset
|
561 const size_t end_idx = addr_to_region_idx(target_end); |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
562 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
563 if (TraceParallelOldGCSummaryPhase) { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
564 gclog_or_tty->print_cr("split: clearing source_region field in [" |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
565 SIZE_FORMAT ", " SIZE_FORMAT ")", |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
566 beg_idx, end_idx); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
567 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
568 for (size_t idx = beg_idx; idx < end_idx; ++idx) { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
569 _region_data[idx].set_source_region(0); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
570 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
571 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
572 // Set split_destination and partial_obj_size to reflect the split region. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
573 split_destination = sr->destination(); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
574 partial_obj_size = sr->partial_obj_size(); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
575 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
576 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
577 // The split is recorded only if a partial object extends onto the region. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
578 if (partial_obj_size != 0) { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
579 _region_data[split_region].set_partial_obj_size(0); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
580 split_info.record(split_region, partial_obj_size, split_destination); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
581 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
582 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
583 // Setup the continuation addresses. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
584 *target_next = split_destination + partial_obj_size; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
585 HeapWord* const source_next = region_to_addr(split_region) + partial_obj_size; |
0 | 586 |
587 if (TraceParallelOldGCSummaryPhase) { | |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
588 const char * split_type = partial_obj_size == 0 ? "easy" : "hard"; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
589 gclog_or_tty->print_cr("%s split: src=" PTR_FORMAT " src_c=" SIZE_FORMAT |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
590 " pos=" SIZE_FORMAT, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
591 split_type, source_next, split_region, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
592 partial_obj_size); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
593 gclog_or_tty->print_cr("%s split: dst=" PTR_FORMAT " dst_c=" SIZE_FORMAT |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
594 " tn=" PTR_FORMAT, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
595 split_type, split_destination, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
596 addr_to_region_idx(split_destination), |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
597 *target_next); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
598 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
599 if (partial_obj_size != 0) { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
600 HeapWord* const po_beg = split_info.destination(); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
601 HeapWord* const po_end = po_beg + split_info.partial_obj_size(); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
602 gclog_or_tty->print_cr("%s split: " |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
603 "po_beg=" PTR_FORMAT " " SIZE_FORMAT " " |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
604 "po_end=" PTR_FORMAT " " SIZE_FORMAT, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
605 split_type, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
606 po_beg, addr_to_region_idx(po_beg), |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
607 po_end, addr_to_region_idx(po_end)); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
608 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
609 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
610 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
611 return source_next; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
612 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
613 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
614 bool ParallelCompactData::summarize(SplitInfo& split_info, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
615 HeapWord* source_beg, HeapWord* source_end, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
616 HeapWord** source_next, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
617 HeapWord* target_beg, HeapWord* target_end, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
618 HeapWord** target_next) |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
619 { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
620 if (TraceParallelOldGCSummaryPhase) { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
621 HeapWord* const source_next_val = source_next == NULL ? NULL : *source_next; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
622 tty->print_cr("sb=" PTR_FORMAT " se=" PTR_FORMAT " sn=" PTR_FORMAT |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
623 "tb=" PTR_FORMAT " te=" PTR_FORMAT " tn=" PTR_FORMAT, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
624 source_beg, source_end, source_next_val, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
625 target_beg, target_end, *target_next); |
0 | 626 } |
627 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
628 size_t cur_region = addr_to_region_idx(source_beg); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
629 const size_t end_region = addr_to_region_idx(region_align_up(source_end)); |
0 | 630 |
631 HeapWord *dest_addr = target_beg; | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
632 while (cur_region < end_region) { |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
633 // The destination must be set even if the region has no data. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
634 _region_data[cur_region].set_destination(dest_addr); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
635 |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
636 size_t words = _region_data[cur_region].data_size(); |
0 | 637 if (words > 0) { |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
638 // If cur_region does not fit entirely into the target space, find a point |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
639 // at which the source space can be 'split' so that part is copied to the |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
640 // target space and the rest is copied elsewhere. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
641 if (dest_addr + words > target_end) { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
642 assert(source_next != NULL, "source_next is NULL when splitting"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
643 *source_next = summarize_split_space(cur_region, split_info, dest_addr, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
644 target_end, target_next); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
645 return false; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
646 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
647 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
648 // Compute the destination_count for cur_region, and if necessary, update |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
649 // source_region for a destination region. The source_region field is |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
650 // updated if cur_region is the first (left-most) region to be copied to a |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
651 // destination region. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
652 // |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
653 // The destination_count calculation is a bit subtle. A region that has |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
654 // data that compacts into itself does not count itself as a destination. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
655 // This maintains the invariant that a zero count means the region is |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
656 // available and can be claimed and then filled. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
657 uint destination_count = 0; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
658 if (split_info.is_split(cur_region)) { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
659 // The current region has been split: the partial object will be copied |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
660 // to one destination space and the remaining data will be copied to |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
661 // another destination space. Adjust the initial destination_count and, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
662 // if necessary, set the source_region field if the partial object will |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
663 // cross a destination region boundary. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
664 destination_count = split_info.destination_count(); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
665 if (destination_count == 2) { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
666 size_t dest_idx = addr_to_region_idx(split_info.dest_region_addr()); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
667 _region_data[dest_idx].set_source_region(cur_region); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
668 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
669 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
670 |
0 | 671 HeapWord* const last_addr = dest_addr + words - 1; |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
672 const size_t dest_region_1 = addr_to_region_idx(dest_addr); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
673 const size_t dest_region_2 = addr_to_region_idx(last_addr); |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
674 |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
675 // Initially assume that the destination regions will be the same and |
0 | 676 // adjust the value below if necessary. Under this assumption, if |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
677 // cur_region == dest_region_2, then cur_region will be compacted |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
678 // completely into itself. |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
679 destination_count += cur_region == dest_region_2 ? 0 : 1; |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
680 if (dest_region_1 != dest_region_2) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
681 // Destination regions differ; adjust destination_count. |
0 | 682 destination_count += 1; |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
683 // Data from cur_region will be copied to the start of dest_region_2. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
684 _region_data[dest_region_2].set_source_region(cur_region); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
685 } else if (region_offset(dest_addr) == 0) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
686 // Data from cur_region will be copied to the start of the destination |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
687 // region. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
688 _region_data[dest_region_1].set_source_region(cur_region); |
0 | 689 } |
690 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
691 _region_data[cur_region].set_destination_count(destination_count); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
692 _region_data[cur_region].set_data_location(region_to_addr(cur_region)); |
0 | 693 dest_addr += words; |
694 } | |
695 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
696 ++cur_region; |
0 | 697 } |
698 | |
699 *target_next = dest_addr; | |
700 return true; | |
701 } | |
702 | |
703 HeapWord* ParallelCompactData::calc_new_pointer(HeapWord* addr) { | |
704 assert(addr != NULL, "Should detect NULL oop earlier"); | |
705 assert(PSParallelCompact::gc_heap()->is_in(addr), "addr not in heap"); | |
706 #ifdef ASSERT | |
707 if (PSParallelCompact::mark_bitmap()->is_unmarked(addr)) { | |
708 gclog_or_tty->print_cr("calc_new_pointer:: addr " PTR_FORMAT, addr); | |
709 } | |
710 #endif | |
711 assert(PSParallelCompact::mark_bitmap()->is_marked(addr), "obj not marked"); | |
712 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
713 // Region covering the object. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
714 size_t region_index = addr_to_region_idx(addr); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
715 const RegionData* const region_ptr = region(region_index); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
716 HeapWord* const region_addr = region_align_down(addr); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
717 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
718 assert(addr < region_addr + RegionSize, "Region does not cover object"); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
719 assert(addr_to_region_ptr(region_addr) == region_ptr, "sanity check"); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
720 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
721 HeapWord* result = region_ptr->destination(); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
722 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
723 // If all the data in the region is live, then the new location of the object |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
724 // can be calculated from the destination of the region plus the offset of the |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
725 // object in the region. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
726 if (region_ptr->data_size() == RegionSize) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
727 result += pointer_delta(addr, region_addr); |
1571
2d127394260e
6916623: Align object to 16 bytes to use Compressed Oops with java heap up to 64Gb
kvn
parents:
1489
diff
changeset
|
728 DEBUG_ONLY(PSParallelCompact::check_new_location(addr, result);) |
0 | 729 return result; |
730 } | |
731 | |
732 // The new location of the object is | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
733 // region destination + |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
734 // size of the partial object extending onto the region + |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
735 // sizes of the live objects in the Region that are to the left of addr |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
736 const size_t partial_obj_size = region_ptr->partial_obj_size(); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
737 HeapWord* const search_start = region_addr + partial_obj_size; |
0 | 738 |
739 const ParMarkBitMap* bitmap = PSParallelCompact::mark_bitmap(); | |
740 size_t live_to_left = bitmap->live_words_in_range(search_start, oop(addr)); | |
741 | |
742 result += partial_obj_size + live_to_left; | |
495
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
743 DEBUG_ONLY(PSParallelCompact::check_new_location(addr, result);) |
0 | 744 return result; |
745 } | |
746 | |
747 #ifdef ASSERT | |
748 void ParallelCompactData::verify_clear(const PSVirtualSpace* vspace) | |
749 { | |
750 const size_t* const beg = (const size_t*)vspace->committed_low_addr(); | |
751 const size_t* const end = (const size_t*)vspace->committed_high_addr(); | |
752 for (const size_t* p = beg; p < end; ++p) { | |
753 assert(*p == 0, "not zero"); | |
754 } | |
755 } | |
756 | |
757 void ParallelCompactData::verify_clear() | |
758 { | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
759 verify_clear(_region_vspace); |
0 | 760 } |
761 #endif // #ifdef ASSERT | |
762 | |
763 #ifdef NOT_PRODUCT | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
764 ParallelCompactData::RegionData* debug_region(size_t region_index) { |
0 | 765 ParallelCompactData& sd = PSParallelCompact::summary_data(); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
766 return sd.region(region_index); |
0 | 767 } |
768 #endif | |
769 | |
770 elapsedTimer PSParallelCompact::_accumulated_time; | |
771 unsigned int PSParallelCompact::_total_invocations = 0; | |
772 unsigned int PSParallelCompact::_maximum_compaction_gc_num = 0; | |
773 jlong PSParallelCompact::_time_of_last_gc = 0; | |
774 CollectorCounters* PSParallelCompact::_counters = NULL; | |
775 ParMarkBitMap PSParallelCompact::_mark_bitmap; | |
776 ParallelCompactData PSParallelCompact::_summary_data; | |
777 | |
778 PSParallelCompact::IsAliveClosure PSParallelCompact::_is_alive_closure; | |
113
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
79
diff
changeset
|
779 |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
79
diff
changeset
|
780 void PSParallelCompact::IsAliveClosure::do_object(oop p) { ShouldNotReachHere(); } |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
79
diff
changeset
|
781 bool PSParallelCompact::IsAliveClosure::do_object_b(oop p) { return mark_bitmap()->is_marked(p); } |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
79
diff
changeset
|
782 |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
79
diff
changeset
|
783 void PSParallelCompact::KeepAliveClosure::do_oop(oop* p) { PSParallelCompact::KeepAliveClosure::do_oop_work(p); } |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
79
diff
changeset
|
784 void PSParallelCompact::KeepAliveClosure::do_oop(narrowOop* p) { PSParallelCompact::KeepAliveClosure::do_oop_work(p); } |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
79
diff
changeset
|
785 |
0 | 786 PSParallelCompact::AdjustPointerClosure PSParallelCompact::_adjust_root_pointer_closure(true); |
787 PSParallelCompact::AdjustPointerClosure PSParallelCompact::_adjust_pointer_closure(false); | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
788 PSParallelCompact::AdjustKlassClosure PSParallelCompact::_adjust_klass_closure; |
0 | 789 |
113
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
79
diff
changeset
|
790 void PSParallelCompact::AdjustPointerClosure::do_oop(oop* p) { adjust_pointer(p, _is_root); } |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
79
diff
changeset
|
791 void PSParallelCompact::AdjustPointerClosure::do_oop(narrowOop* p) { adjust_pointer(p, _is_root); } |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
79
diff
changeset
|
792 |
1311
2a1472c30599
4396719: Mark Sweep stack overflow on deeply nested Object arrays
jcoomes
parents:
997
diff
changeset
|
793 void PSParallelCompact::FollowStackClosure::do_void() { _compaction_manager->follow_marking_stacks(); } |
113
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
79
diff
changeset
|
794 |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
795 void PSParallelCompact::MarkAndPushClosure::do_oop(oop* p) { |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
796 mark_and_push(_compaction_manager, p); |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
797 } |
113
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
79
diff
changeset
|
798 void PSParallelCompact::MarkAndPushClosure::do_oop(narrowOop* p) { mark_and_push(_compaction_manager, p); } |
0 | 799 |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
800 void PSParallelCompact::FollowKlassClosure::do_klass(Klass* klass) { |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
801 klass->oops_do(_mark_and_push_closure); |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
802 } |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
803 void PSParallelCompact::AdjustKlassClosure::do_klass(Klass* klass) { |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
804 klass->oops_do(&PSParallelCompact::_adjust_root_pointer_closure); |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
805 } |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
806 |
0 | 807 void PSParallelCompact::post_initialize() { |
808 ParallelScavengeHeap* heap = gc_heap(); | |
809 assert(heap->kind() == CollectedHeap::ParallelScavengeHeap, "Sanity"); | |
810 | |
811 MemRegion mr = heap->reserved_region(); | |
2369
92da084fefc9
6668573: CMS: reference processing crash if ParallelCMSThreads > ParallelGCThreads
ysr
parents:
2177
diff
changeset
|
812 _ref_processor = |
92da084fefc9
6668573: CMS: reference processing crash if ParallelCMSThreads > ParallelGCThreads
ysr
parents:
2177
diff
changeset
|
813 new ReferenceProcessor(mr, // span |
92da084fefc9
6668573: CMS: reference processing crash if ParallelCMSThreads > ParallelGCThreads
ysr
parents:
2177
diff
changeset
|
814 ParallelRefProcEnabled && (ParallelGCThreads > 1), // mt processing |
92da084fefc9
6668573: CMS: reference processing crash if ParallelCMSThreads > ParallelGCThreads
ysr
parents:
2177
diff
changeset
|
815 (int) ParallelGCThreads, // mt processing degree |
92da084fefc9
6668573: CMS: reference processing crash if ParallelCMSThreads > ParallelGCThreads
ysr
parents:
2177
diff
changeset
|
816 true, // mt discovery |
92da084fefc9
6668573: CMS: reference processing crash if ParallelCMSThreads > ParallelGCThreads
ysr
parents:
2177
diff
changeset
|
817 (int) ParallelGCThreads, // mt discovery degree |
92da084fefc9
6668573: CMS: reference processing crash if ParallelCMSThreads > ParallelGCThreads
ysr
parents:
2177
diff
changeset
|
818 true, // atomic_discovery |
92da084fefc9
6668573: CMS: reference processing crash if ParallelCMSThreads > ParallelGCThreads
ysr
parents:
2177
diff
changeset
|
819 &_is_alive_closure, // non-header is alive closure |
92da084fefc9
6668573: CMS: reference processing crash if ParallelCMSThreads > ParallelGCThreads
ysr
parents:
2177
diff
changeset
|
820 false); // write barrier for next field updates |
0 | 821 _counters = new CollectorCounters("PSParallelCompact", 1); |
822 | |
823 // Initialize static fields in ParCompactionManager. | |
824 ParCompactionManager::initialize(mark_bitmap()); | |
825 } | |
826 | |
827 bool PSParallelCompact::initialize() { | |
828 ParallelScavengeHeap* heap = gc_heap(); | |
829 assert(heap->kind() == CollectedHeap::ParallelScavengeHeap, "Sanity"); | |
830 MemRegion mr = heap->reserved_region(); | |
831 | |
832 // Was the old gen get allocated successfully? | |
833 if (!heap->old_gen()->is_allocated()) { | |
834 return false; | |
835 } | |
836 | |
837 initialize_space_info(); | |
838 initialize_dead_wood_limiter(); | |
839 | |
840 if (!_mark_bitmap.initialize(mr)) { | |
841 vm_shutdown_during_initialization("Unable to allocate bit map for " | |
842 "parallel garbage collection for the requested heap size."); | |
843 return false; | |
844 } | |
845 | |
846 if (!_summary_data.initialize(mr)) { | |
847 vm_shutdown_during_initialization("Unable to allocate tables for " | |
848 "parallel garbage collection for the requested heap size."); | |
849 return false; | |
850 } | |
851 | |
852 return true; | |
853 } | |
854 | |
855 void PSParallelCompact::initialize_space_info() | |
856 { | |
857 memset(&_space_info, 0, sizeof(_space_info)); | |
858 | |
859 ParallelScavengeHeap* heap = gc_heap(); | |
860 PSYoungGen* young_gen = heap->young_gen(); | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
861 |
0 | 862 _space_info[old_space_id].set_space(heap->old_gen()->object_space()); |
863 _space_info[eden_space_id].set_space(young_gen->eden_space()); | |
864 _space_info[from_space_id].set_space(young_gen->from_space()); | |
865 _space_info[to_space_id].set_space(young_gen->to_space()); | |
866 | |
867 _space_info[old_space_id].set_start_array(heap->old_gen()->start_array()); | |
868 } | |
869 | |
870 void PSParallelCompact::initialize_dead_wood_limiter() | |
871 { | |
872 const size_t max = 100; | |
873 _dwl_mean = double(MIN2(ParallelOldDeadWoodLimiterMean, max)) / 100.0; | |
874 _dwl_std_dev = double(MIN2(ParallelOldDeadWoodLimiterStdDev, max)) / 100.0; | |
875 _dwl_first_term = 1.0 / (sqrt(2.0 * M_PI) * _dwl_std_dev); | |
876 DEBUG_ONLY(_dwl_initialized = true;) | |
877 _dwl_adjustment = normal_distribution(1.0); | |
878 } | |
879 | |
880 // Simple class for storing info about the heap at the start of GC, to be used | |
881 // after GC for comparison/printing. | |
882 class PreGCValues { | |
883 public: | |
884 PreGCValues() { } | |
885 PreGCValues(ParallelScavengeHeap* heap) { fill(heap); } | |
886 | |
887 void fill(ParallelScavengeHeap* heap) { | |
888 _heap_used = heap->used(); | |
889 _young_gen_used = heap->young_gen()->used_in_bytes(); | |
890 _old_gen_used = heap->old_gen()->used_in_bytes(); | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
891 _metadata_used = MetaspaceAux::used_in_bytes(); |
0 | 892 }; |
893 | |
894 size_t heap_used() const { return _heap_used; } | |
895 size_t young_gen_used() const { return _young_gen_used; } | |
896 size_t old_gen_used() const { return _old_gen_used; } | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
897 size_t metadata_used() const { return _metadata_used; } |
0 | 898 |
899 private: | |
900 size_t _heap_used; | |
901 size_t _young_gen_used; | |
902 size_t _old_gen_used; | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
903 size_t _metadata_used; |
0 | 904 }; |
905 | |
906 void | |
907 PSParallelCompact::clear_data_covering_space(SpaceId id) | |
908 { | |
909 // At this point, top is the value before GC, new_top() is the value that will | |
910 // be set at the end of GC. The marking bitmap is cleared to top; nothing | |
911 // should be marked above top. The summary data is cleared to the larger of | |
912 // top & new_top. | |
913 MutableSpace* const space = _space_info[id].space(); | |
914 HeapWord* const bot = space->bottom(); | |
915 HeapWord* const top = space->top(); | |
916 HeapWord* const max_top = MAX2(top, _space_info[id].new_top()); | |
917 | |
918 const idx_t beg_bit = _mark_bitmap.addr_to_bit(bot); | |
919 const idx_t end_bit = BitMap::word_align_up(_mark_bitmap.addr_to_bit(top)); | |
920 _mark_bitmap.clear_range(beg_bit, end_bit); | |
921 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
922 const size_t beg_region = _summary_data.addr_to_region_idx(bot); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
923 const size_t end_region = |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
924 _summary_data.addr_to_region_idx(_summary_data.region_align_up(max_top)); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
925 _summary_data.clear_range(beg_region, end_region); |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
926 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
927 // Clear the data used to 'split' regions. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
928 SplitInfo& split_info = _space_info[id].split_info(); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
929 if (split_info.is_valid()) { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
930 split_info.clear(); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
931 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
932 DEBUG_ONLY(split_info.verify_clear();) |
0 | 933 } |
934 | |
935 void PSParallelCompact::pre_compact(PreGCValues* pre_gc_values) | |
936 { | |
937 // Update the from & to space pointers in space_info, since they are swapped | |
938 // at each young gen gc. Do the update unconditionally (even though a | |
939 // promotion failure does not swap spaces) because an unknown number of minor | |
940 // collections will have swapped the spaces an unknown number of times. | |
941 TraceTime tm("pre compact", print_phases(), true, gclog_or_tty); | |
942 ParallelScavengeHeap* heap = gc_heap(); | |
943 _space_info[from_space_id].set_space(heap->young_gen()->from_space()); | |
944 _space_info[to_space_id].set_space(heap->young_gen()->to_space()); | |
945 | |
946 pre_gc_values->fill(heap); | |
947 | |
948 NOT_PRODUCT(_mark_bitmap.reset_counters()); | |
949 DEBUG_ONLY(add_obj_count = add_obj_size = 0;) | |
950 DEBUG_ONLY(mark_bitmap_count = mark_bitmap_size = 0;) | |
951 | |
952 // Increment the invocation count | |
139
c0492d52d55b
6539517: CR 6186200 should be extended to perm gen allocation to prevent spurious OOM's from perm gen
apetrusenko
parents:
0
diff
changeset
|
953 heap->increment_total_collections(true); |
0 | 954 |
955 // We need to track unique mark sweep invocations as well. | |
956 _total_invocations++; | |
957 | |
4872
aa3d708d67c4
7141200: log some interesting information in ring buffers for crashes
never
parents:
4712
diff
changeset
|
958 heap->print_heap_before_gc(); |
0 | 959 |
960 // Fill in TLABs | |
961 heap->accumulate_statistics_all_tlabs(); | |
962 heap->ensure_parsability(true); // retire TLABs | |
963 | |
964 if (VerifyBeforeGC && heap->total_collections() >= VerifyGCStartAt) { | |
965 HandleMark hm; // Discard invalid handles created during verification | |
966 gclog_or_tty->print(" VerifyBeforeGC:"); | |
6865
4202510ee0fe
8000831: Heap verification output incorrect/incomplete
johnc
parents:
6787
diff
changeset
|
967 Universe::verify(); |
0 | 968 } |
969 | |
970 // Verify object start arrays | |
971 if (VerifyObjectStartArray && | |
972 VerifyBeforeGC) { | |
973 heap->old_gen()->verify_object_start_array(); | |
974 } | |
975 | |
976 DEBUG_ONLY(mark_bitmap()->verify_clear();) | |
977 DEBUG_ONLY(summary_data().verify_clear();) | |
210 | 978 |
979 // Have worker threads release resources the next time they run a task. | |
980 gc_task_manager()->release_all_resources(); | |
0 | 981 } |
982 | |
983 void PSParallelCompact::post_compact() | |
984 { | |
985 TraceTime tm("post compact", print_phases(), true, gclog_or_tty); | |
986 | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
987 for (unsigned int id = old_space_id; id < last_space_id; ++id) { |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
988 // Clear the marking bitmap, summary data and split info. |
0 | 989 clear_data_covering_space(SpaceId(id)); |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
990 // Update top(). Must be done after clearing the bitmap and summary data. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
991 _space_info[id].publish_new_top(); |
0 | 992 } |
993 | |
994 MutableSpace* const eden_space = _space_info[eden_space_id].space(); | |
995 MutableSpace* const from_space = _space_info[from_space_id].space(); | |
996 MutableSpace* const to_space = _space_info[to_space_id].space(); | |
997 | |
998 ParallelScavengeHeap* heap = gc_heap(); | |
999 bool eden_empty = eden_space->is_empty(); | |
1000 if (!eden_empty) { | |
1001 eden_empty = absorb_live_data_from_eden(heap->size_policy(), | |
1002 heap->young_gen(), heap->old_gen()); | |
1003 } | |
1004 | |
1005 // Update heap occupancy information which is used as input to the soft ref | |
1006 // clearing policy at the next gc. | |
1007 Universe::update_heap_info_at_gc(); | |
1008 | |
1009 bool young_gen_empty = eden_empty && from_space->is_empty() && | |
1010 to_space->is_empty(); | |
1011 | |
1012 BarrierSet* bs = heap->barrier_set(); | |
1013 if (bs->is_a(BarrierSet::ModRef)) { | |
1014 ModRefBarrierSet* modBS = (ModRefBarrierSet*)bs; | |
1015 MemRegion old_mr = heap->old_gen()->reserved(); | |
1016 | |
1017 if (young_gen_empty) { | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
1018 modBS->clear(MemRegion(old_mr.start(), old_mr.end())); |
0 | 1019 } else { |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
1020 modBS->invalidate(MemRegion(old_mr.start(), old_mr.end())); |
0 | 1021 } |
1022 } | |
1023 | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
1024 // Delete metaspaces for unloaded class loaders and clean up loader_data graph |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
1025 ClassLoaderDataGraph::purge(); |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
1026 |
0 | 1027 Threads::gc_epilogue(); |
1028 CodeCache::gc_epilogue(); | |
2147
9afee0b9fc1d
7012505: BreakpointWithFullGC.sh fails with Internal Error (src/share/vm/oops/methodOop.cpp:220)
kamg
parents:
1972
diff
changeset
|
1029 JvmtiExport::gc_epilogue(); |
0 | 1030 |
1031 COMPILER2_PRESENT(DerivedPointerTable::update_pointers()); | |
1032 | |
1033 ref_processor()->enqueue_discovered_references(NULL); | |
1034 | |
263
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
1035 if (ZapUnusedHeapArea) { |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
1036 heap->gen_mangle_unused_area(); |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
1037 } |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
1038 |
0 | 1039 // Update time of last GC |
1040 reset_millis_since_last_gc(); | |
1041 } | |
1042 | |
1043 HeapWord* | |
1044 PSParallelCompact::compute_dense_prefix_via_density(const SpaceId id, | |
1045 bool maximum_compaction) | |
1046 { | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1047 const size_t region_size = ParallelCompactData::RegionSize; |
0 | 1048 const ParallelCompactData& sd = summary_data(); |
1049 | |
1050 const MutableSpace* const space = _space_info[id].space(); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1051 HeapWord* const top_aligned_up = sd.region_align_up(space->top()); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1052 const RegionData* const beg_cp = sd.addr_to_region_ptr(space->bottom()); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1053 const RegionData* const end_cp = sd.addr_to_region_ptr(top_aligned_up); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1054 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1055 // Skip full regions at the beginning of the space--they are necessarily part |
0 | 1056 // of the dense prefix. |
1057 size_t full_count = 0; | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1058 const RegionData* cp; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1059 for (cp = beg_cp; cp < end_cp && cp->data_size() == region_size; ++cp) { |
0 | 1060 ++full_count; |
1061 } | |
1062 | |
1063 assert(total_invocations() >= _maximum_compaction_gc_num, "sanity"); | |
1064 const size_t gcs_since_max = total_invocations() - _maximum_compaction_gc_num; | |
1065 const bool interval_ended = gcs_since_max > HeapMaximumCompactionInterval; | |
1066 if (maximum_compaction || cp == end_cp || interval_ended) { | |
1067 _maximum_compaction_gc_num = total_invocations(); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1068 return sd.region_to_addr(cp); |
0 | 1069 } |
1070 | |
1071 HeapWord* const new_top = _space_info[id].new_top(); | |
1072 const size_t space_live = pointer_delta(new_top, space->bottom()); | |
1073 const size_t space_used = space->used_in_words(); | |
1074 const size_t space_capacity = space->capacity_in_words(); | |
1075 | |
1076 const double cur_density = double(space_live) / space_capacity; | |
1077 const double deadwood_density = | |
1078 (1.0 - cur_density) * (1.0 - cur_density) * cur_density * cur_density; | |
1079 const size_t deadwood_goal = size_t(space_capacity * deadwood_density); | |
1080 | |
1081 if (TraceParallelOldGCDensePrefix) { | |
1082 tty->print_cr("cur_dens=%5.3f dw_dens=%5.3f dw_goal=" SIZE_FORMAT, | |
1083 cur_density, deadwood_density, deadwood_goal); | |
1084 tty->print_cr("space_live=" SIZE_FORMAT " " "space_used=" SIZE_FORMAT " " | |
1085 "space_cap=" SIZE_FORMAT, | |
1086 space_live, space_used, | |
1087 space_capacity); | |
1088 } | |
1089 | |
1090 // XXX - Use binary search? | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1091 HeapWord* dense_prefix = sd.region_to_addr(cp); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1092 const RegionData* full_cp = cp; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1093 const RegionData* const top_cp = sd.addr_to_region_ptr(space->top() - 1); |
0 | 1094 while (cp < end_cp) { |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1095 HeapWord* region_destination = cp->destination(); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1096 const size_t cur_deadwood = pointer_delta(dense_prefix, region_destination); |
0 | 1097 if (TraceParallelOldGCDensePrefix && Verbose) { |
264
15dd2594d08e
6718283: existing uses of *_FORMAT_W() were broken by 6521491
jcoomes
parents:
263
diff
changeset
|
1098 tty->print_cr("c#=" SIZE_FORMAT_W(4) " dst=" PTR_FORMAT " " |
15dd2594d08e
6718283: existing uses of *_FORMAT_W() were broken by 6521491
jcoomes
parents:
263
diff
changeset
|
1099 "dp=" SIZE_FORMAT_W(8) " " "cdw=" SIZE_FORMAT_W(8), |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1100 sd.region(cp), region_destination, |
0 | 1101 dense_prefix, cur_deadwood); |
1102 } | |
1103 | |
1104 if (cur_deadwood >= deadwood_goal) { | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1105 // Found the region that has the correct amount of deadwood to the left. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1106 // This typically occurs after crossing a fairly sparse set of regions, so |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1107 // iterate backwards over those sparse regions, looking for the region |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1108 // that has the lowest density of live objects 'to the right.' |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1109 size_t space_to_left = sd.region(cp) * region_size; |
0 | 1110 size_t live_to_left = space_to_left - cur_deadwood; |
1111 size_t space_to_right = space_capacity - space_to_left; | |
1112 size_t live_to_right = space_live - live_to_left; | |
1113 double density_to_right = double(live_to_right) / space_to_right; | |
1114 while (cp > full_cp) { | |
1115 --cp; | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1116 const size_t prev_region_live_to_right = live_to_right - |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1117 cp->data_size(); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1118 const size_t prev_region_space_to_right = space_to_right + region_size; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1119 double prev_region_density_to_right = |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1120 double(prev_region_live_to_right) / prev_region_space_to_right; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1121 if (density_to_right <= prev_region_density_to_right) { |
0 | 1122 return dense_prefix; |
1123 } | |
1124 if (TraceParallelOldGCDensePrefix && Verbose) { | |
264
15dd2594d08e
6718283: existing uses of *_FORMAT_W() were broken by 6521491
jcoomes
parents:
263
diff
changeset
|
1125 tty->print_cr("backing up from c=" SIZE_FORMAT_W(4) " d2r=%10.8f " |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1126 "pc_d2r=%10.8f", sd.region(cp), density_to_right, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1127 prev_region_density_to_right); |
0 | 1128 } |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1129 dense_prefix -= region_size; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1130 live_to_right = prev_region_live_to_right; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1131 space_to_right = prev_region_space_to_right; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1132 density_to_right = prev_region_density_to_right; |
0 | 1133 } |
1134 return dense_prefix; | |
1135 } | |
1136 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1137 dense_prefix += region_size; |
0 | 1138 ++cp; |
1139 } | |
1140 | |
1141 return dense_prefix; | |
1142 } | |
1143 | |
1144 #ifndef PRODUCT | |
1145 void PSParallelCompact::print_dense_prefix_stats(const char* const algorithm, | |
1146 const SpaceId id, | |
1147 const bool maximum_compaction, | |
1148 HeapWord* const addr) | |
1149 { | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1150 const size_t region_idx = summary_data().addr_to_region_idx(addr); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1151 RegionData* const cp = summary_data().region(region_idx); |
0 | 1152 const MutableSpace* const space = _space_info[id].space(); |
1153 HeapWord* const new_top = _space_info[id].new_top(); | |
1154 | |
1155 const size_t space_live = pointer_delta(new_top, space->bottom()); | |
1156 const size_t dead_to_left = pointer_delta(addr, cp->destination()); | |
1157 const size_t space_cap = space->capacity_in_words(); | |
1158 const double dead_to_left_pct = double(dead_to_left) / space_cap; | |
1159 const size_t live_to_right = new_top - cp->destination(); | |
1160 const size_t dead_to_right = space->top() - addr - live_to_right; | |
1161 | |
264
15dd2594d08e
6718283: existing uses of *_FORMAT_W() were broken by 6521491
jcoomes
parents:
263
diff
changeset
|
1162 tty->print_cr("%s=" PTR_FORMAT " dpc=" SIZE_FORMAT_W(5) " " |
0 | 1163 "spl=" SIZE_FORMAT " " |
1164 "d2l=" SIZE_FORMAT " d2l%%=%6.4f " | |
1165 "d2r=" SIZE_FORMAT " l2r=" SIZE_FORMAT | |
1166 " ratio=%10.8f", | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1167 algorithm, addr, region_idx, |
0 | 1168 space_live, |
1169 dead_to_left, dead_to_left_pct, | |
1170 dead_to_right, live_to_right, | |
1171 double(dead_to_right) / live_to_right); | |
1172 } | |
1173 #endif // #ifndef PRODUCT | |
1174 | |
1175 // Return a fraction indicating how much of the generation can be treated as | |
1176 // "dead wood" (i.e., not reclaimed). The function uses a normal distribution | |
1177 // based on the density of live objects in the generation to determine a limit, | |
1178 // which is then adjusted so the return value is min_percent when the density is | |
1179 // 1. | |
1180 // | |
1181 // The following table shows some return values for a different values of the | |
1182 // standard deviation (ParallelOldDeadWoodLimiterStdDev); the mean is 0.5 and | |
1183 // min_percent is 1. | |
1184 // | |
1185 // fraction allowed as dead wood | |
1186 // ----------------------------------------------------------------- | |
1187 // density std_dev=70 std_dev=75 std_dev=80 std_dev=85 std_dev=90 std_dev=95 | |
1188 // ------- ---------- ---------- ---------- ---------- ---------- ---------- | |
1189 // 0.00000 0.01000000 0.01000000 0.01000000 0.01000000 0.01000000 0.01000000 | |
1190 // 0.05000 0.03193096 0.02836880 0.02550828 0.02319280 0.02130337 0.01974941 | |
1191 // 0.10000 0.05247504 0.04547452 0.03988045 0.03537016 0.03170171 0.02869272 | |
1192 // 0.15000 0.07135702 0.06111390 0.05296419 0.04641639 0.04110601 0.03676066 | |
1193 // 0.20000 0.08831616 0.07509618 0.06461766 0.05622444 0.04943437 0.04388975 | |
1194 // 0.25000 0.10311208 0.08724696 0.07471205 0.06469760 0.05661313 0.05002313 | |
1195 // 0.30000 0.11553050 0.09741183 0.08313394 0.07175114 0.06257797 0.05511132 | |
1196 // 0.35000 0.12538832 0.10545958 0.08978741 0.07731366 0.06727491 0.05911289 | |
1197 // 0.40000 0.13253818 0.11128511 0.09459590 0.08132834 0.07066107 0.06199500 | |
1198 // 0.45000 0.13687208 0.11481163 0.09750361 0.08375387 0.07270534 0.06373386 | |
1199 // 0.50000 0.13832410 0.11599237 0.09847664 0.08456518 0.07338887 0.06431510 | |
1200 // 0.55000 0.13687208 0.11481163 0.09750361 0.08375387 0.07270534 0.06373386 | |
1201 // 0.60000 0.13253818 0.11128511 0.09459590 0.08132834 0.07066107 0.06199500 | |
1202 // 0.65000 0.12538832 0.10545958 0.08978741 0.07731366 0.06727491 0.05911289 | |
1203 // 0.70000 0.11553050 0.09741183 0.08313394 0.07175114 0.06257797 0.05511132 | |
1204 // 0.75000 0.10311208 0.08724696 0.07471205 0.06469760 0.05661313 0.05002313 | |
1205 // 0.80000 0.08831616 0.07509618 0.06461766 0.05622444 0.04943437 0.04388975 | |
1206 // 0.85000 0.07135702 0.06111390 0.05296419 0.04641639 0.04110601 0.03676066 | |
1207 // 0.90000 0.05247504 0.04547452 0.03988045 0.03537016 0.03170171 0.02869272 | |
1208 // 0.95000 0.03193096 0.02836880 0.02550828 0.02319280 0.02130337 0.01974941 | |
1209 // 1.00000 0.01000000 0.01000000 0.01000000 0.01000000 0.01000000 0.01000000 | |
1210 | |
1211 double PSParallelCompact::dead_wood_limiter(double density, size_t min_percent) | |
1212 { | |
1213 assert(_dwl_initialized, "uninitialized"); | |
1214 | |
1215 // The raw limit is the value of the normal distribution at x = density. | |
1216 const double raw_limit = normal_distribution(density); | |
1217 | |
1218 // Adjust the raw limit so it becomes the minimum when the density is 1. | |
1219 // | |
1220 // First subtract the adjustment value (which is simply the precomputed value | |
1221 // normal_distribution(1.0)); this yields a value of 0 when the density is 1. | |
1222 // Then add the minimum value, so the minimum is returned when the density is | |
1223 // 1. Finally, prevent negative values, which occur when the mean is not 0.5. | |
1224 const double min = double(min_percent) / 100.0; | |
1225 const double limit = raw_limit - _dwl_adjustment + min; | |
1226 return MAX2(limit, 0.0); | |
1227 } | |
1228 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1229 ParallelCompactData::RegionData* |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1230 PSParallelCompact::first_dead_space_region(const RegionData* beg, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1231 const RegionData* end) |
0 | 1232 { |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1233 const size_t region_size = ParallelCompactData::RegionSize; |
0 | 1234 ParallelCompactData& sd = summary_data(); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1235 size_t left = sd.region(beg); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1236 size_t right = end > beg ? sd.region(end) - 1 : left; |
0 | 1237 |
1238 // Binary search. | |
1239 while (left < right) { | |
1240 // Equivalent to (left + right) / 2, but does not overflow. | |
1241 const size_t middle = left + (right - left) / 2; | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1242 RegionData* const middle_ptr = sd.region(middle); |
0 | 1243 HeapWord* const dest = middle_ptr->destination(); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1244 HeapWord* const addr = sd.region_to_addr(middle); |
0 | 1245 assert(dest != NULL, "sanity"); |
1246 assert(dest <= addr, "must move left"); | |
1247 | |
1248 if (middle > left && dest < addr) { | |
1249 right = middle - 1; | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1250 } else if (middle < right && middle_ptr->data_size() == region_size) { |
0 | 1251 left = middle + 1; |
1252 } else { | |
1253 return middle_ptr; | |
1254 } | |
1255 } | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1256 return sd.region(left); |
0 | 1257 } |
1258 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1259 ParallelCompactData::RegionData* |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1260 PSParallelCompact::dead_wood_limit_region(const RegionData* beg, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1261 const RegionData* end, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1262 size_t dead_words) |
0 | 1263 { |
1264 ParallelCompactData& sd = summary_data(); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1265 size_t left = sd.region(beg); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1266 size_t right = end > beg ? sd.region(end) - 1 : left; |
0 | 1267 |
1268 // Binary search. | |
1269 while (left < right) { | |
1270 // Equivalent to (left + right) / 2, but does not overflow. | |
1271 const size_t middle = left + (right - left) / 2; | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1272 RegionData* const middle_ptr = sd.region(middle); |
0 | 1273 HeapWord* const dest = middle_ptr->destination(); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1274 HeapWord* const addr = sd.region_to_addr(middle); |
0 | 1275 assert(dest != NULL, "sanity"); |
1276 assert(dest <= addr, "must move left"); | |
1277 | |
1278 const size_t dead_to_left = pointer_delta(addr, dest); | |
1279 if (middle > left && dead_to_left > dead_words) { | |
1280 right = middle - 1; | |
1281 } else if (middle < right && dead_to_left < dead_words) { | |
1282 left = middle + 1; | |
1283 } else { | |
1284 return middle_ptr; | |
1285 } | |
1286 } | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1287 return sd.region(left); |
0 | 1288 } |
1289 | |
1290 // The result is valid during the summary phase, after the initial summarization | |
1291 // of each space into itself, and before final summarization. | |
1292 inline double | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1293 PSParallelCompact::reclaimed_ratio(const RegionData* const cp, |
0 | 1294 HeapWord* const bottom, |
1295 HeapWord* const top, | |
1296 HeapWord* const new_top) | |
1297 { | |
1298 ParallelCompactData& sd = summary_data(); | |
1299 | |
1300 assert(cp != NULL, "sanity"); | |
1301 assert(bottom != NULL, "sanity"); | |
1302 assert(top != NULL, "sanity"); | |
1303 assert(new_top != NULL, "sanity"); | |
1304 assert(top >= new_top, "summary data problem?"); | |
1305 assert(new_top > bottom, "space is empty; should not be here"); | |
1306 assert(new_top >= cp->destination(), "sanity"); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1307 assert(top >= sd.region_to_addr(cp), "sanity"); |
0 | 1308 |
1309 HeapWord* const destination = cp->destination(); | |
1310 const size_t dense_prefix_live = pointer_delta(destination, bottom); | |
1311 const size_t compacted_region_live = pointer_delta(new_top, destination); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1312 const size_t compacted_region_used = pointer_delta(top, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1313 sd.region_to_addr(cp)); |
0 | 1314 const size_t reclaimable = compacted_region_used - compacted_region_live; |
1315 | |
1316 const double divisor = dense_prefix_live + 1.25 * compacted_region_live; | |
1317 return double(reclaimable) / divisor; | |
1318 } | |
1319 | |
1320 // Return the address of the end of the dense prefix, a.k.a. the start of the | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1321 // compacted region. The address is always on a region boundary. |
0 | 1322 // |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1323 // Completely full regions at the left are skipped, since no compaction can |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1324 // occur in those regions. Then the maximum amount of dead wood to allow is |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1325 // computed, based on the density (amount live / capacity) of the generation; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1326 // the region with approximately that amount of dead space to the left is |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1327 // identified as the limit region. Regions between the last completely full |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1328 // region and the limit region are scanned and the one that has the best |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1329 // (maximum) reclaimed_ratio() is selected. |
0 | 1330 HeapWord* |
1331 PSParallelCompact::compute_dense_prefix(const SpaceId id, | |
1332 bool maximum_compaction) | |
1333 { | |
483
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1334 if (ParallelOldGCSplitALot) { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1335 if (_space_info[id].dense_prefix() != _space_info[id].space()->bottom()) { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1336 // The value was chosen to provoke splitting a young gen space; use it. |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1337 return _space_info[id].dense_prefix(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1338 } |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1339 } |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1340 |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1341 const size_t region_size = ParallelCompactData::RegionSize; |
0 | 1342 const ParallelCompactData& sd = summary_data(); |
1343 | |
1344 const MutableSpace* const space = _space_info[id].space(); | |
1345 HeapWord* const top = space->top(); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1346 HeapWord* const top_aligned_up = sd.region_align_up(top); |
0 | 1347 HeapWord* const new_top = _space_info[id].new_top(); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1348 HeapWord* const new_top_aligned_up = sd.region_align_up(new_top); |
0 | 1349 HeapWord* const bottom = space->bottom(); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1350 const RegionData* const beg_cp = sd.addr_to_region_ptr(bottom); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1351 const RegionData* const top_cp = sd.addr_to_region_ptr(top_aligned_up); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1352 const RegionData* const new_top_cp = |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1353 sd.addr_to_region_ptr(new_top_aligned_up); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1354 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1355 // Skip full regions at the beginning of the space--they are necessarily part |
0 | 1356 // of the dense prefix. |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1357 const RegionData* const full_cp = first_dead_space_region(beg_cp, new_top_cp); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1358 assert(full_cp->destination() == sd.region_to_addr(full_cp) || |
0 | 1359 space->is_empty(), "no dead space allowed to the left"); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1360 assert(full_cp->data_size() < region_size || full_cp == new_top_cp - 1, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1361 "region must have dead space"); |
0 | 1362 |
1363 // The gc number is saved whenever a maximum compaction is done, and used to | |
1364 // determine when the maximum compaction interval has expired. This avoids | |
1365 // successive max compactions for different reasons. | |
1366 assert(total_invocations() >= _maximum_compaction_gc_num, "sanity"); | |
1367 const size_t gcs_since_max = total_invocations() - _maximum_compaction_gc_num; | |
1368 const bool interval_ended = gcs_since_max > HeapMaximumCompactionInterval || | |
1369 total_invocations() == HeapFirstMaximumCompactionCount; | |
1370 if (maximum_compaction || full_cp == top_cp || interval_ended) { | |
1371 _maximum_compaction_gc_num = total_invocations(); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1372 return sd.region_to_addr(full_cp); |
0 | 1373 } |
1374 | |
1375 const size_t space_live = pointer_delta(new_top, bottom); | |
1376 const size_t space_used = space->used_in_words(); | |
1377 const size_t space_capacity = space->capacity_in_words(); | |
1378 | |
1379 const double density = double(space_live) / double(space_capacity); | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
1380 const size_t min_percent_free = MarkSweepDeadRatio; |
0 | 1381 const double limiter = dead_wood_limiter(density, min_percent_free); |
1382 const size_t dead_wood_max = space_used - space_live; | |
1383 const size_t dead_wood_limit = MIN2(size_t(space_capacity * limiter), | |
1384 dead_wood_max); | |
1385 | |
1386 if (TraceParallelOldGCDensePrefix) { | |
1387 tty->print_cr("space_live=" SIZE_FORMAT " " "space_used=" SIZE_FORMAT " " | |
1388 "space_cap=" SIZE_FORMAT, | |
1389 space_live, space_used, | |
1390 space_capacity); | |
1391 tty->print_cr("dead_wood_limiter(%6.4f, %d)=%6.4f " | |
1392 "dead_wood_max=" SIZE_FORMAT " dead_wood_limit=" SIZE_FORMAT, | |
1393 density, min_percent_free, limiter, | |
1394 dead_wood_max, dead_wood_limit); | |
1395 } | |
1396 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1397 // Locate the region with the desired amount of dead space to the left. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1398 const RegionData* const limit_cp = |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1399 dead_wood_limit_region(full_cp, top_cp, dead_wood_limit); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1400 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1401 // Scan from the first region with dead space to the limit region and find the |
0 | 1402 // one with the best (largest) reclaimed ratio. |
1403 double best_ratio = 0.0; | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1404 const RegionData* best_cp = full_cp; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1405 for (const RegionData* cp = full_cp; cp < limit_cp; ++cp) { |
0 | 1406 double tmp_ratio = reclaimed_ratio(cp, bottom, top, new_top); |
1407 if (tmp_ratio > best_ratio) { | |
1408 best_cp = cp; | |
1409 best_ratio = tmp_ratio; | |
1410 } | |
1411 } | |
1412 | |
1413 #if 0 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1414 // Something to consider: if the region with the best ratio is 'close to' the |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1415 // first region w/free space, choose the first region with free space |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1416 // ("first-free"). The first-free region is usually near the start of the |
0 | 1417 // heap, which means we are copying most of the heap already, so copy a bit |
1418 // more to get complete compaction. | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1419 if (pointer_delta(best_cp, full_cp, sizeof(RegionData)) < 4) { |
0 | 1420 _maximum_compaction_gc_num = total_invocations(); |
1421 best_cp = full_cp; | |
1422 } | |
1423 #endif // #if 0 | |
1424 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1425 return sd.region_to_addr(best_cp); |
0 | 1426 } |
1427 | |
483
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1428 #ifndef PRODUCT |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1429 void |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1430 PSParallelCompact::fill_with_live_objects(SpaceId id, HeapWord* const start, |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1431 size_t words) |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1432 { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1433 if (TraceParallelOldGCSummaryPhase) { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1434 tty->print_cr("fill_with_live_objects [" PTR_FORMAT " " PTR_FORMAT ") " |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1435 SIZE_FORMAT, start, start + words, words); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1436 } |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1437 |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1438 ObjectStartArray* const start_array = _space_info[id].start_array(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1439 CollectedHeap::fill_with_objects(start, words); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1440 for (HeapWord* p = start; p < start + words; p += oop(p)->size()) { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1441 _mark_bitmap.mark_obj(p, words); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1442 _summary_data.add_obj(p, words); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1443 start_array->allocate_block(p); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1444 } |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1445 } |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1446 |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1447 void |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1448 PSParallelCompact::summarize_new_objects(SpaceId id, HeapWord* start) |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1449 { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1450 ParallelCompactData& sd = summary_data(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1451 MutableSpace* space = _space_info[id].space(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1452 |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1453 // Find the source and destination start addresses. |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1454 HeapWord* const src_addr = sd.region_align_down(start); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1455 HeapWord* dst_addr; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1456 if (src_addr < start) { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1457 dst_addr = sd.addr_to_region_ptr(src_addr)->destination(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1458 } else if (src_addr > space->bottom()) { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1459 // The start (the original top() value) is aligned to a region boundary so |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1460 // the associated region does not have a destination. Compute the |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1461 // destination from the previous region. |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1462 RegionData* const cp = sd.addr_to_region_ptr(src_addr) - 1; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1463 dst_addr = cp->destination() + cp->data_size(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1464 } else { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1465 // Filling the entire space. |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1466 dst_addr = space->bottom(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1467 } |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1468 assert(dst_addr != NULL, "sanity"); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1469 |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1470 // Update the summary data. |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1471 bool result = _summary_data.summarize(_space_info[id].split_info(), |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1472 src_addr, space->top(), NULL, |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1473 dst_addr, space->end(), |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1474 _space_info[id].new_top_addr()); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1475 assert(result, "should not fail: bad filler object size"); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1476 } |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1477 |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1478 void |
496
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1479 PSParallelCompact::provoke_split_fill_survivor(SpaceId id) |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1480 { |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1481 if (total_invocations() % (ParallelOldGCSplitInterval * 3) != 0) { |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1482 return; |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1483 } |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1484 |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1485 MutableSpace* const space = _space_info[id].space(); |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1486 if (space->is_empty()) { |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1487 HeapWord* b = space->bottom(); |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1488 HeapWord* t = b + space->capacity_in_words() / 2; |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1489 space->set_top(t); |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1490 if (ZapUnusedHeapArea) { |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1491 space->set_top_for_allocations(); |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1492 } |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1493 |
1571
2d127394260e
6916623: Align object to 16 bytes to use Compressed Oops with java heap up to 64Gb
kvn
parents:
1489
diff
changeset
|
1494 size_t min_size = CollectedHeap::min_fill_size(); |
2d127394260e
6916623: Align object to 16 bytes to use Compressed Oops with java heap up to 64Gb
kvn
parents:
1489
diff
changeset
|
1495 size_t obj_len = min_size; |
496
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1496 while (b + obj_len <= t) { |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1497 CollectedHeap::fill_with_object(b, obj_len); |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1498 mark_bitmap()->mark_obj(b, obj_len); |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1499 summary_data().add_obj(b, obj_len); |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1500 b += obj_len; |
1571
2d127394260e
6916623: Align object to 16 bytes to use Compressed Oops with java heap up to 64Gb
kvn
parents:
1489
diff
changeset
|
1501 obj_len = (obj_len & (min_size*3)) + min_size; // 8 16 24 32 8 16 24 32 ... |
496
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1502 } |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1503 if (b < t) { |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1504 // The loop didn't completely fill to t (top); adjust top downward. |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1505 space->set_top(b); |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1506 if (ZapUnusedHeapArea) { |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1507 space->set_top_for_allocations(); |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1508 } |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1509 } |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1510 |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1511 HeapWord** nta = _space_info[id].new_top_addr(); |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1512 bool result = summary_data().summarize(_space_info[id].split_info(), |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1513 space->bottom(), space->top(), NULL, |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1514 space->bottom(), space->end(), nta); |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1515 assert(result, "space must fit into itself"); |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1516 } |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1517 } |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1518 |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1519 void |
483
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1520 PSParallelCompact::provoke_split(bool & max_compaction) |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1521 { |
496
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1522 if (total_invocations() % ParallelOldGCSplitInterval != 0) { |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1523 return; |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1524 } |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1525 |
483
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1526 const size_t region_size = ParallelCompactData::RegionSize; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1527 ParallelCompactData& sd = summary_data(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1528 |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1529 MutableSpace* const eden_space = _space_info[eden_space_id].space(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1530 MutableSpace* const from_space = _space_info[from_space_id].space(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1531 const size_t eden_live = pointer_delta(eden_space->top(), |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1532 _space_info[eden_space_id].new_top()); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1533 const size_t from_live = pointer_delta(from_space->top(), |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1534 _space_info[from_space_id].new_top()); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1535 |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1536 const size_t min_fill_size = CollectedHeap::min_fill_size(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1537 const size_t eden_free = pointer_delta(eden_space->end(), eden_space->top()); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1538 const size_t eden_fillable = eden_free >= min_fill_size ? eden_free : 0; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1539 const size_t from_free = pointer_delta(from_space->end(), from_space->top()); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1540 const size_t from_fillable = from_free >= min_fill_size ? from_free : 0; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1541 |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1542 // Choose the space to split; need at least 2 regions live (or fillable). |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1543 SpaceId id; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1544 MutableSpace* space; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1545 size_t live_words; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1546 size_t fill_words; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1547 if (eden_live + eden_fillable >= region_size * 2) { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1548 id = eden_space_id; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1549 space = eden_space; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1550 live_words = eden_live; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1551 fill_words = eden_fillable; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1552 } else if (from_live + from_fillable >= region_size * 2) { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1553 id = from_space_id; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1554 space = from_space; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1555 live_words = from_live; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1556 fill_words = from_fillable; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1557 } else { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1558 return; // Give up. |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1559 } |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1560 assert(fill_words == 0 || fill_words >= min_fill_size, "sanity"); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1561 |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1562 if (live_words < region_size * 2) { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1563 // Fill from top() to end() w/live objects of mixed sizes. |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1564 HeapWord* const fill_start = space->top(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1565 live_words += fill_words; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1566 |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1567 space->set_top(fill_start + fill_words); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1568 if (ZapUnusedHeapArea) { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1569 space->set_top_for_allocations(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1570 } |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1571 |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1572 HeapWord* cur_addr = fill_start; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1573 while (fill_words > 0) { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1574 const size_t r = (size_t)os::random() % (region_size / 2) + min_fill_size; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1575 size_t cur_size = MIN2(align_object_size_(r), fill_words); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1576 if (fill_words - cur_size < min_fill_size) { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1577 cur_size = fill_words; // Avoid leaving a fragment too small to fill. |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1578 } |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1579 |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1580 CollectedHeap::fill_with_object(cur_addr, cur_size); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1581 mark_bitmap()->mark_obj(cur_addr, cur_size); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1582 sd.add_obj(cur_addr, cur_size); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1583 |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1584 cur_addr += cur_size; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1585 fill_words -= cur_size; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1586 } |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1587 |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1588 summarize_new_objects(id, fill_start); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1589 } |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1590 |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1591 max_compaction = false; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1592 |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1593 // Manipulate the old gen so that it has room for about half of the live data |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1594 // in the target young gen space (live_words / 2). |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1595 id = old_space_id; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1596 space = _space_info[id].space(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1597 const size_t free_at_end = space->free_in_words(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1598 const size_t free_target = align_object_size(live_words / 2); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1599 const size_t dead = pointer_delta(space->top(), _space_info[id].new_top()); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1600 |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1601 if (free_at_end >= free_target + min_fill_size) { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1602 // Fill space above top() and set the dense prefix so everything survives. |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1603 HeapWord* const fill_start = space->top(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1604 const size_t fill_size = free_at_end - free_target; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1605 space->set_top(space->top() + fill_size); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1606 if (ZapUnusedHeapArea) { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1607 space->set_top_for_allocations(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1608 } |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1609 fill_with_live_objects(id, fill_start, fill_size); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1610 summarize_new_objects(id, fill_start); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1611 _space_info[id].set_dense_prefix(sd.region_align_down(space->top())); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1612 } else if (dead + free_at_end > free_target) { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1613 // Find a dense prefix that makes the right amount of space available. |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1614 HeapWord* cur = sd.region_align_down(space->top()); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1615 HeapWord* cur_destination = sd.addr_to_region_ptr(cur)->destination(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1616 size_t dead_to_right = pointer_delta(space->end(), cur_destination); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1617 while (dead_to_right < free_target) { |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1618 cur -= region_size; |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1619 cur_destination = sd.addr_to_region_ptr(cur)->destination(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1620 dead_to_right = pointer_delta(space->end(), cur_destination); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1621 } |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1622 _space_info[id].set_dense_prefix(cur); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1623 } |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1624 } |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1625 #endif // #ifndef PRODUCT |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1626 |
0 | 1627 void PSParallelCompact::summarize_spaces_quick() |
1628 { | |
1629 for (unsigned int i = 0; i < last_space_id; ++i) { | |
1630 const MutableSpace* space = _space_info[i].space(); | |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1631 HeapWord** nta = _space_info[i].new_top_addr(); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1632 bool result = _summary_data.summarize(_space_info[i].split_info(), |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1633 space->bottom(), space->top(), NULL, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1634 space->bottom(), space->end(), nta); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1635 assert(result, "space must fit into itself"); |
0 | 1636 _space_info[i].set_dense_prefix(space->bottom()); |
1637 } | |
496
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1638 |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1639 #ifndef PRODUCT |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1640 if (ParallelOldGCSplitALot) { |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1641 provoke_split_fill_survivor(to_space_id); |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1642 } |
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1643 #endif // #ifndef PRODUCT |
0 | 1644 } |
1645 | |
1646 void PSParallelCompact::fill_dense_prefix_end(SpaceId id) | |
1647 { | |
1648 HeapWord* const dense_prefix_end = dense_prefix(id); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1649 const RegionData* region = _summary_data.addr_to_region_ptr(dense_prefix_end); |
0 | 1650 const idx_t dense_prefix_bit = _mark_bitmap.addr_to_bit(dense_prefix_end); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1651 if (dead_space_crosses_boundary(region, dense_prefix_bit)) { |
0 | 1652 // Only enough dead space is filled so that any remaining dead space to the |
1653 // left is larger than the minimum filler object. (The remainder is filled | |
1654 // during the copy/update phase.) | |
1655 // | |
1656 // The size of the dead space to the right of the boundary is not a | |
1657 // concern, since compaction will be able to use whatever space is | |
1658 // available. | |
1659 // | |
1660 // Here '||' is the boundary, 'x' represents a don't care bit and a box | |
1661 // surrounds the space to be filled with an object. | |
1662 // | |
1663 // In the 32-bit VM, each bit represents two 32-bit words: | |
1664 // +---+ | |
1665 // a) beg_bits: ... x x x | 0 | || 0 x x ... | |
1666 // end_bits: ... x x x | 0 | || 0 x x ... | |
1667 // +---+ | |
1668 // | |
1669 // In the 64-bit VM, each bit represents one 64-bit word: | |
1670 // +------------+ | |
1671 // b) beg_bits: ... x x x | 0 || 0 | x x ... | |
1672 // end_bits: ... x x 1 | 0 || 0 | x x ... | |
1673 // +------------+ | |
1674 // +-------+ | |
1675 // c) beg_bits: ... x x | 0 0 | || 0 x x ... | |
1676 // end_bits: ... x 1 | 0 0 | || 0 x x ... | |
1677 // +-------+ | |
1678 // +-----------+ | |
1679 // d) beg_bits: ... x | 0 0 0 | || 0 x x ... | |
1680 // end_bits: ... 1 | 0 0 0 | || 0 x x ... | |
1681 // +-----------+ | |
1682 // +-------+ | |
1683 // e) beg_bits: ... 0 0 | 0 0 | || 0 x x ... | |
1684 // end_bits: ... 0 0 | 0 0 | || 0 x x ... | |
1685 // +-------+ | |
1686 | |
1687 // Initially assume case a, c or e will apply. | |
1571
2d127394260e
6916623: Align object to 16 bytes to use Compressed Oops with java heap up to 64Gb
kvn
parents:
1489
diff
changeset
|
1688 size_t obj_len = CollectedHeap::min_fill_size(); |
0 | 1689 HeapWord* obj_beg = dense_prefix_end - obj_len; |
1690 | |
1691 #ifdef _LP64 | |
1571
2d127394260e
6916623: Align object to 16 bytes to use Compressed Oops with java heap up to 64Gb
kvn
parents:
1489
diff
changeset
|
1692 if (MinObjAlignment > 1) { // object alignment > heap word size |
2d127394260e
6916623: Align object to 16 bytes to use Compressed Oops with java heap up to 64Gb
kvn
parents:
1489
diff
changeset
|
1693 // Cases a, c or e. |
2d127394260e
6916623: Align object to 16 bytes to use Compressed Oops with java heap up to 64Gb
kvn
parents:
1489
diff
changeset
|
1694 } else if (_mark_bitmap.is_obj_end(dense_prefix_bit - 2)) { |
0 | 1695 // Case b above. |
1696 obj_beg = dense_prefix_end - 1; | |
1697 } else if (!_mark_bitmap.is_obj_end(dense_prefix_bit - 3) && | |
1698 _mark_bitmap.is_obj_end(dense_prefix_bit - 4)) { | |
1699 // Case d above. | |
1700 obj_beg = dense_prefix_end - 3; | |
1701 obj_len = 3; | |
1702 } | |
1703 #endif // #ifdef _LP64 | |
1704 | |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1705 CollectedHeap::fill_with_object(obj_beg, obj_len); |
0 | 1706 _mark_bitmap.mark_obj(obj_beg, obj_len); |
1707 _summary_data.add_obj(obj_beg, obj_len); | |
1708 assert(start_array(id) != NULL, "sanity"); | |
1709 start_array(id)->allocate_block(obj_beg); | |
1710 } | |
1711 } | |
1712 | |
1713 void | |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1714 PSParallelCompact::clear_source_region(HeapWord* beg_addr, HeapWord* end_addr) |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1715 { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1716 RegionData* const beg_ptr = _summary_data.addr_to_region_ptr(beg_addr); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1717 HeapWord* const end_aligned_up = _summary_data.region_align_up(end_addr); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1718 RegionData* const end_ptr = _summary_data.addr_to_region_ptr(end_aligned_up); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1719 for (RegionData* cur = beg_ptr; cur < end_ptr; ++cur) { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1720 cur->set_source_region(0); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1721 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1722 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1723 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1724 void |
0 | 1725 PSParallelCompact::summarize_space(SpaceId id, bool maximum_compaction) |
1726 { | |
1727 assert(id < last_space_id, "id out of range"); | |
483
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1728 assert(_space_info[id].dense_prefix() == _space_info[id].space()->bottom() || |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1729 ParallelOldGCSplitALot && id == old_space_id, |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1730 "should have been reset in summarize_spaces_quick()"); |
0 | 1731 |
1732 const MutableSpace* space = _space_info[id].space(); | |
265
f88815ca1af1
6483129: par compact assertion failure (new_top > bottom)
jcoomes
parents:
264
diff
changeset
|
1733 if (_space_info[id].new_top() != space->bottom()) { |
f88815ca1af1
6483129: par compact assertion failure (new_top > bottom)
jcoomes
parents:
264
diff
changeset
|
1734 HeapWord* dense_prefix_end = compute_dense_prefix(id, maximum_compaction); |
f88815ca1af1
6483129: par compact assertion failure (new_top > bottom)
jcoomes
parents:
264
diff
changeset
|
1735 _space_info[id].set_dense_prefix(dense_prefix_end); |
0 | 1736 |
1737 #ifndef PRODUCT | |
265
f88815ca1af1
6483129: par compact assertion failure (new_top > bottom)
jcoomes
parents:
264
diff
changeset
|
1738 if (TraceParallelOldGCDensePrefix) { |
f88815ca1af1
6483129: par compact assertion failure (new_top > bottom)
jcoomes
parents:
264
diff
changeset
|
1739 print_dense_prefix_stats("ratio", id, maximum_compaction, |
f88815ca1af1
6483129: par compact assertion failure (new_top > bottom)
jcoomes
parents:
264
diff
changeset
|
1740 dense_prefix_end); |
f88815ca1af1
6483129: par compact assertion failure (new_top > bottom)
jcoomes
parents:
264
diff
changeset
|
1741 HeapWord* addr = compute_dense_prefix_via_density(id, maximum_compaction); |
f88815ca1af1
6483129: par compact assertion failure (new_top > bottom)
jcoomes
parents:
264
diff
changeset
|
1742 print_dense_prefix_stats("density", id, maximum_compaction, addr); |
f88815ca1af1
6483129: par compact assertion failure (new_top > bottom)
jcoomes
parents:
264
diff
changeset
|
1743 } |
0 | 1744 #endif // #ifndef PRODUCT |
1745 | |
483
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1746 // Recompute the summary data, taking into account the dense prefix. If |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1747 // every last byte will be reclaimed, then the existing summary data which |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1748 // compacts everything can be left in place. |
265
f88815ca1af1
6483129: par compact assertion failure (new_top > bottom)
jcoomes
parents:
264
diff
changeset
|
1749 if (!maximum_compaction && dense_prefix_end != space->bottom()) { |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1750 // If dead space crosses the dense prefix boundary, it is (at least |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1751 // partially) filled with a dummy object, marked live and added to the |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1752 // summary data. This simplifies the copy/update phase and must be done |
483
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1753 // before the final locations of objects are determined, to prevent |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1754 // leaving a fragment of dead space that is too small to fill. |
265
f88815ca1af1
6483129: par compact assertion failure (new_top > bottom)
jcoomes
parents:
264
diff
changeset
|
1755 fill_dense_prefix_end(id); |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1756 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1757 // Compute the destination of each Region, and thus each object. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1758 _summary_data.summarize_dense_prefix(space->bottom(), dense_prefix_end); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1759 _summary_data.summarize(_space_info[id].split_info(), |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1760 dense_prefix_end, space->top(), NULL, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1761 dense_prefix_end, space->end(), |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1762 _space_info[id].new_top_addr()); |
265
f88815ca1af1
6483129: par compact assertion failure (new_top > bottom)
jcoomes
parents:
264
diff
changeset
|
1763 } |
0 | 1764 } |
1765 | |
1766 if (TraceParallelOldGCSummaryPhase) { | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1767 const size_t region_size = ParallelCompactData::RegionSize; |
265
f88815ca1af1
6483129: par compact assertion failure (new_top > bottom)
jcoomes
parents:
264
diff
changeset
|
1768 HeapWord* const dense_prefix_end = _space_info[id].dense_prefix(); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1769 const size_t dp_region = _summary_data.addr_to_region_idx(dense_prefix_end); |
0 | 1770 const size_t dp_words = pointer_delta(dense_prefix_end, space->bottom()); |
265
f88815ca1af1
6483129: par compact assertion failure (new_top > bottom)
jcoomes
parents:
264
diff
changeset
|
1771 HeapWord* const new_top = _space_info[id].new_top(); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1772 const HeapWord* nt_aligned_up = _summary_data.region_align_up(new_top); |
0 | 1773 const size_t cr_words = pointer_delta(nt_aligned_up, dense_prefix_end); |
1774 tty->print_cr("id=%d cap=" SIZE_FORMAT " dp=" PTR_FORMAT " " | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1775 "dp_region=" SIZE_FORMAT " " "dp_count=" SIZE_FORMAT " " |
0 | 1776 "cr_count=" SIZE_FORMAT " " "nt=" PTR_FORMAT, |
1777 id, space->capacity_in_words(), dense_prefix_end, | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1778 dp_region, dp_words / region_size, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1779 cr_words / region_size, new_top); |
0 | 1780 } |
1781 } | |
1782 | |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1783 #ifndef PRODUCT |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1784 void PSParallelCompact::summary_phase_msg(SpaceId dst_space_id, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1785 HeapWord* dst_beg, HeapWord* dst_end, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1786 SpaceId src_space_id, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1787 HeapWord* src_beg, HeapWord* src_end) |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1788 { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1789 if (TraceParallelOldGCSummaryPhase) { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1790 tty->print_cr("summarizing %d [%s] into %d [%s]: " |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1791 "src=" PTR_FORMAT "-" PTR_FORMAT " " |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1792 SIZE_FORMAT "-" SIZE_FORMAT " " |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1793 "dst=" PTR_FORMAT "-" PTR_FORMAT " " |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1794 SIZE_FORMAT "-" SIZE_FORMAT, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1795 src_space_id, space_names[src_space_id], |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1796 dst_space_id, space_names[dst_space_id], |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1797 src_beg, src_end, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1798 _summary_data.addr_to_region_idx(src_beg), |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1799 _summary_data.addr_to_region_idx(src_end), |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1800 dst_beg, dst_end, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1801 _summary_data.addr_to_region_idx(dst_beg), |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1802 _summary_data.addr_to_region_idx(dst_end)); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1803 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1804 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1805 #endif // #ifndef PRODUCT |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1806 |
0 | 1807 void PSParallelCompact::summary_phase(ParCompactionManager* cm, |
1808 bool maximum_compaction) | |
1809 { | |
1810 TraceTime tm("summary phase", print_phases(), true, gclog_or_tty); | |
1811 // trace("2"); | |
1812 | |
1813 #ifdef ASSERT | |
1814 if (TraceParallelOldGCMarkingPhase) { | |
1815 tty->print_cr("add_obj_count=" SIZE_FORMAT " " | |
1816 "add_obj_bytes=" SIZE_FORMAT, | |
1817 add_obj_count, add_obj_size * HeapWordSize); | |
1818 tty->print_cr("mark_bitmap_count=" SIZE_FORMAT " " | |
1819 "mark_bitmap_bytes=" SIZE_FORMAT, | |
1820 mark_bitmap_count, mark_bitmap_size * HeapWordSize); | |
1821 } | |
1822 #endif // #ifdef ASSERT | |
1823 | |
1824 // Quick summarization of each space into itself, to see how much is live. | |
1825 summarize_spaces_quick(); | |
1826 | |
1827 if (TraceParallelOldGCSummaryPhase) { | |
1828 tty->print_cr("summary_phase: after summarizing each space to self"); | |
1829 Universe::print(); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1830 NOT_PRODUCT(print_region_ranges()); |
0 | 1831 if (Verbose) { |
1832 NOT_PRODUCT(print_initial_summary_data(_summary_data, _space_info)); | |
1833 } | |
1834 } | |
1835 | |
1836 // The amount of live data that will end up in old space (assuming it fits). | |
1837 size_t old_space_total_live = 0; | |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1838 for (unsigned int id = old_space_id; id < last_space_id; ++id) { |
0 | 1839 old_space_total_live += pointer_delta(_space_info[id].new_top(), |
1840 _space_info[id].space()->bottom()); | |
1841 } | |
1842 | |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1843 MutableSpace* const old_space = _space_info[old_space_id].space(); |
483
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1844 const size_t old_capacity = old_space->capacity_in_words(); |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1845 if (old_space_total_live > old_capacity) { |
0 | 1846 // XXX - should also try to expand |
1847 maximum_compaction = true; | |
1848 } | |
483
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1849 #ifndef PRODUCT |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1850 if (ParallelOldGCSplitALot && old_space_total_live < old_capacity) { |
496
b27c885f75f9
6786188: par compact - "SplitALot" stress mode should fill to_space
jcoomes
parents:
495
diff
changeset
|
1851 provoke_split(maximum_compaction); |
483
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1852 } |
0f773163217d
6765954: par compact - stress mode for splitting young gen spaces
jcoomes
parents:
482
diff
changeset
|
1853 #endif // #ifndef PRODUCT |
0 | 1854 |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
1855 // Old generations. |
0 | 1856 summarize_space(old_space_id, maximum_compaction); |
1857 | |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1858 // Summarize the remaining spaces in the young gen. The initial target space |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1859 // is the old gen. If a space does not fit entirely into the target, then the |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1860 // remainder is compacted into the space itself and that space becomes the new |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1861 // target. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1862 SpaceId dst_space_id = old_space_id; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1863 HeapWord* dst_space_end = old_space->end(); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1864 HeapWord** new_top_addr = _space_info[dst_space_id].new_top_addr(); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1865 for (unsigned int id = eden_space_id; id < last_space_id; ++id) { |
0 | 1866 const MutableSpace* space = _space_info[id].space(); |
1867 const size_t live = pointer_delta(_space_info[id].new_top(), | |
1868 space->bottom()); | |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1869 const size_t available = pointer_delta(dst_space_end, *new_top_addr); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1870 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1871 NOT_PRODUCT(summary_phase_msg(dst_space_id, *new_top_addr, dst_space_end, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1872 SpaceId(id), space->bottom(), space->top());) |
266
2214b226b7f0
6724367: par compact could clear less young gen summary data
jcoomes
parents:
265
diff
changeset
|
1873 if (live > 0 && live <= available) { |
0 | 1874 // All the live data will fit. |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1875 bool done = _summary_data.summarize(_space_info[id].split_info(), |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1876 space->bottom(), space->top(), |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1877 NULL, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1878 *new_top_addr, dst_space_end, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1879 new_top_addr); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1880 assert(done, "space must fit into old gen"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1881 |
266
2214b226b7f0
6724367: par compact could clear less young gen summary data
jcoomes
parents:
265
diff
changeset
|
1882 // Reset the new_top value for the space. |
2214b226b7f0
6724367: par compact could clear less young gen summary data
jcoomes
parents:
265
diff
changeset
|
1883 _space_info[id].set_new_top(space->bottom()); |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1884 } else if (live > 0) { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1885 // Attempt to fit part of the source space into the target space. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1886 HeapWord* next_src_addr = NULL; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1887 bool done = _summary_data.summarize(_space_info[id].split_info(), |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1888 space->bottom(), space->top(), |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1889 &next_src_addr, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1890 *new_top_addr, dst_space_end, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1891 new_top_addr); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1892 assert(!done, "space should not fit into old gen"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1893 assert(next_src_addr != NULL, "sanity"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1894 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1895 // The source space becomes the new target, so the remainder is compacted |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1896 // within the space itself. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1897 dst_space_id = SpaceId(id); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1898 dst_space_end = space->end(); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1899 new_top_addr = _space_info[id].new_top_addr(); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1900 NOT_PRODUCT(summary_phase_msg(dst_space_id, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1901 space->bottom(), dst_space_end, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1902 SpaceId(id), next_src_addr, space->top());) |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1903 done = _summary_data.summarize(_space_info[id].split_info(), |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1904 next_src_addr, space->top(), |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1905 NULL, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1906 space->bottom(), dst_space_end, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1907 new_top_addr); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1908 assert(done, "space must fit when compacted into itself"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
1909 assert(*new_top_addr <= space->top(), "usage should not grow"); |
0 | 1910 } |
1911 } | |
1912 | |
1913 if (TraceParallelOldGCSummaryPhase) { | |
1914 tty->print_cr("summary_phase: after final summarization"); | |
1915 Universe::print(); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1916 NOT_PRODUCT(print_region_ranges()); |
0 | 1917 if (Verbose) { |
1918 NOT_PRODUCT(print_generic_summary_data(_summary_data, _space_info)); | |
1919 } | |
1920 } | |
1921 } | |
1922 | |
1923 // This method should contain all heap-specific policy for invoking a full | |
1924 // collection. invoke_no_policy() will only attempt to compact the heap; it | |
1925 // will do nothing further. If we need to bail out for policy reasons, scavenge | |
1926 // before full gc, or any other specialized behavior, it needs to be added here. | |
1927 // | |
1928 // Note that this method should only be called from the vm_thread while at a | |
1929 // safepoint. | |
1387
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1930 // |
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1931 // Note that the all_soft_refs_clear flag in the collector policy |
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1932 // may be true because this method can be called without intervening |
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1933 // activity. For example when the heap space is tight and full measure |
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1934 // are being taken to free space. |
0 | 1935 void PSParallelCompact::invoke(bool maximum_heap_compaction) { |
1936 assert(SafepointSynchronize::is_at_safepoint(), "should be at safepoint"); | |
1937 assert(Thread::current() == (Thread*)VMThread::vm_thread(), | |
1938 "should be in vm thread"); | |
1387
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1939 |
0 | 1940 ParallelScavengeHeap* heap = gc_heap(); |
1941 GCCause::Cause gc_cause = heap->gc_cause(); | |
1942 assert(!heap->is_gc_active(), "not reentrant"); | |
1943 | |
1944 PSAdaptiveSizePolicy* policy = heap->size_policy(); | |
1387
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1945 IsGCActiveMark mark; |
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1946 |
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1947 if (ScavengeBeforeFullGC) { |
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1948 PSScavenge::invoke_no_policy(); |
0 | 1949 } |
1387
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1950 |
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1951 const bool clear_all_soft_refs = |
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1952 heap->collector_policy()->should_clear_all_soft_refs(); |
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1953 |
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1954 PSParallelCompact::invoke_no_policy(clear_all_soft_refs || |
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1955 maximum_heap_compaction); |
0 | 1956 } |
1957 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1958 bool ParallelCompactData::region_contains(size_t region_index, HeapWord* addr) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1959 size_t addr_region_index = addr_to_region_idx(addr); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
1960 return region_index == addr_region_index; |
0 | 1961 } |
1962 | |
1963 // This method contains no policy. You should probably | |
1964 // be calling invoke() instead. | |
4913
ab4422d0ed59
7146343: PS invoke methods should indicate the type of gc done
jcoomes
parents:
4872
diff
changeset
|
1965 bool PSParallelCompact::invoke_no_policy(bool maximum_heap_compaction) { |
0 | 1966 assert(SafepointSynchronize::is_at_safepoint(), "must be at a safepoint"); |
1967 assert(ref_processor() != NULL, "Sanity"); | |
1968 | |
139
c0492d52d55b
6539517: CR 6186200 should be extended to perm gen allocation to prevent spurious OOM's from perm gen
apetrusenko
parents:
0
diff
changeset
|
1969 if (GC_locker::check_active_before_gc()) { |
4913
ab4422d0ed59
7146343: PS invoke methods should indicate the type of gc done
jcoomes
parents:
4872
diff
changeset
|
1970 return false; |
0 | 1971 } |
1972 | |
1973 TimeStamp marking_start; | |
1974 TimeStamp compaction_start; | |
1975 TimeStamp collection_exit; | |
1976 | |
1977 ParallelScavengeHeap* heap = gc_heap(); | |
1978 GCCause::Cause gc_cause = heap->gc_cause(); | |
1979 PSYoungGen* young_gen = heap->young_gen(); | |
1980 PSOldGen* old_gen = heap->old_gen(); | |
1981 PSAdaptiveSizePolicy* size_policy = heap->size_policy(); | |
1982 | |
1387
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1983 // The scope of casr should end after code that can change |
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1984 // CollectorPolicy::_should_clear_all_soft_refs. |
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1985 ClearedAllSoftRefs casr(maximum_heap_compaction, |
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1986 heap->collector_policy()); |
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
1987 |
263
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
1988 if (ZapUnusedHeapArea) { |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
1989 // Save information needed to minimize mangling |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
1990 heap->record_gen_tops_before_GC(); |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
1991 } |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
1992 |
615
c6c601a0f2d6
6797870: Add -XX:+{HeapDump,PrintClassHistogram}{Before,After}FullGC
ysr
parents:
546
diff
changeset
|
1993 heap->pre_full_gc_dump(); |
c6c601a0f2d6
6797870: Add -XX:+{HeapDump,PrintClassHistogram}{Before,After}FullGC
ysr
parents:
546
diff
changeset
|
1994 |
0 | 1995 _print_phases = PrintGCDetails && PrintParallelOldGCPhaseTimes; |
1996 | |
1997 // Make sure data structures are sane, make the heap parsable, and do other | |
1998 // miscellaneous bookkeeping. | |
1999 PreGCValues pre_gc_values; | |
2000 pre_compact(&pre_gc_values); | |
2001 | |
210 | 2002 // Get the compaction manager reserved for the VM thread. |
2003 ParCompactionManager* const vmthread_cm = | |
2004 ParCompactionManager::manager_array(gc_task_manager()->workers()); | |
2005 | |
0 | 2006 // Place after pre_compact() where the number of invocations is incremented. |
2007 AdaptiveSizePolicyOutput(size_policy, heap->total_collections()); | |
2008 | |
2009 { | |
2010 ResourceMark rm; | |
2011 HandleMark hm; | |
2012 | |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2013 // Set the number of GC threads to be used in this collection |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2014 gc_task_manager()->set_active_gang(); |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2015 gc_task_manager()->task_idle_workers(); |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2016 heap->set_par_threads(gc_task_manager()->active_workers()); |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2017 |
0 | 2018 gclog_or_tty->date_stamp(PrintGC && PrintGCDateStamps); |
2019 TraceCPUTime tcpu(PrintGCDetails, true, gclog_or_tty); | |
6064
9d679effd28c
7166894: Add gc cause to GC logging for all collectors
brutisso
parents:
4913
diff
changeset
|
2020 TraceTime t1(GCCauseString("Full GC", gc_cause), PrintGC, !PrintGCDetails, gclog_or_tty); |
0 | 2021 TraceCollectorStats tcs(counters()); |
3356
78542e2b5e35
7036199: Adding a notification to the implementation of GarbageCollectorMXBeans
fparain
parents:
3251
diff
changeset
|
2022 TraceMemoryManagerStats tms(true /* Full GC */,gc_cause); |
0 | 2023 |
2024 if (TraceGen1Time) accumulated_time()->start(); | |
2025 | |
2026 // Let the size policy know we're starting | |
2027 size_policy->major_collection_begin(); | |
2028 | |
2029 CodeCache::gc_prologue(); | |
2030 Threads::gc_prologue(); | |
2031 | |
2032 COMPILER2_PRESENT(DerivedPointerTable::clear()); | |
2033 | |
3979
4dfb2df418f2
6484982: G1: process references during evacuation pauses
johnc
parents:
3915
diff
changeset
|
2034 ref_processor()->enable_discovery(true /*verify_disabled*/, true /*verify_no_refs*/); |
457
27a80744a83b
6778647: snap(), snap_policy() should be renamed setup(), setup_policy()
ysr
parents:
453
diff
changeset
|
2035 ref_processor()->setup_policy(maximum_heap_compaction); |
0 | 2036 |
2037 bool marked_for_unloading = false; | |
2038 | |
2039 marking_start.update(); | |
210 | 2040 marking_phase(vmthread_cm, maximum_heap_compaction); |
0 | 2041 |
2042 #ifndef PRODUCT | |
2043 if (TraceParallelOldGCMarkingPhase) { | |
2044 gclog_or_tty->print_cr("marking_phase: cas_tries %d cas_retries %d " | |
2045 "cas_by_another %d", | |
2046 mark_bitmap()->cas_tries(), mark_bitmap()->cas_retries(), | |
2047 mark_bitmap()->cas_by_another()); | |
2048 } | |
2049 #endif // #ifndef PRODUCT | |
2050 | |
6064
9d679effd28c
7166894: Add gc cause to GC logging for all collectors
brutisso
parents:
4913
diff
changeset
|
2051 bool max_on_system_gc = UseMaximumCompactionOnSystemGC |
9d679effd28c
7166894: Add gc cause to GC logging for all collectors
brutisso
parents:
4913
diff
changeset
|
2052 && gc_cause == GCCause::_java_lang_system_gc; |
210 | 2053 summary_phase(vmthread_cm, maximum_heap_compaction || max_on_system_gc); |
0 | 2054 |
2055 COMPILER2_PRESENT(assert(DerivedPointerTable::is_active(), "Sanity")); | |
2056 COMPILER2_PRESENT(DerivedPointerTable::set_active(false)); | |
2057 | |
2058 // adjust_roots() updates Universe::_intArrayKlassObj which is | |
2059 // needed by the compaction for filling holes in the dense prefix. | |
2060 adjust_roots(); | |
2061 | |
2062 compaction_start.update(); | |
3251
eda9eb483d29
6841742: par compact - remove unused/unsupported options
jcoomes
parents:
2369
diff
changeset
|
2063 compact(); |
0 | 2064 |
2065 // Reset the mark bitmap, summary data, and do other bookkeeping. Must be | |
2066 // done before resizing. | |
2067 post_compact(); | |
2068 | |
2069 // Let the size policy know we're done | |
2070 size_policy->major_collection_end(old_gen->used_in_bytes(), gc_cause); | |
2071 | |
2072 if (UseAdaptiveSizePolicy) { | |
2073 if (PrintAdaptiveSizePolicy) { | |
2074 gclog_or_tty->print("AdaptiveSizeStart: "); | |
2075 gclog_or_tty->stamp(); | |
2076 gclog_or_tty->print_cr(" collection: %d ", | |
2077 heap->total_collections()); | |
2078 if (Verbose) { | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2079 gclog_or_tty->print("old_gen_capacity: %d young_gen_capacity: %d", |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2080 old_gen->capacity_in_bytes(), young_gen->capacity_in_bytes()); |
0 | 2081 } |
2082 } | |
2083 | |
2084 // Don't check if the size_policy is ready here. Let | |
2085 // the size_policy check that internally. | |
2086 if (UseAdaptiveGenerationSizePolicyAtMajorCollection && | |
2087 ((gc_cause != GCCause::_java_lang_system_gc) || | |
2088 UseAdaptiveSizePolicyWithSystemGC)) { | |
2089 // Calculate optimal free space amounts | |
2090 assert(young_gen->max_size() > | |
2091 young_gen->from_space()->capacity_in_bytes() + | |
2092 young_gen->to_space()->capacity_in_bytes(), | |
2093 "Sizes of space in young gen are out-of-bounds"); | |
2094 size_t max_eden_size = young_gen->max_size() - | |
2095 young_gen->from_space()->capacity_in_bytes() - | |
2096 young_gen->to_space()->capacity_in_bytes(); | |
263
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
2097 size_policy->compute_generation_free_space( |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
2098 young_gen->used_in_bytes(), |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
2099 young_gen->eden_space()->used_in_bytes(), |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
2100 old_gen->used_in_bytes(), |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
2101 young_gen->eden_space()->capacity_in_bytes(), |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
2102 old_gen->max_gen_size(), |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
2103 max_eden_size, |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
2104 true /* full gc*/, |
1387
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
2105 gc_cause, |
0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
jmasa
parents:
1311
diff
changeset
|
2106 heap->collector_policy()); |
263
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
2107 |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
2108 heap->resize_old_gen( |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
2109 size_policy->calculated_old_free_size_in_bytes()); |
0 | 2110 |
2111 // Don't resize the young generation at an major collection. A | |
2112 // desired young generation size may have been calculated but | |
2113 // resizing the young generation complicates the code because the | |
2114 // resizing of the old generation may have moved the boundary | |
2115 // between the young generation and the old generation. Let the | |
2116 // young generation resizing happen at the minor collections. | |
2117 } | |
2118 if (PrintAdaptiveSizePolicy) { | |
2119 gclog_or_tty->print_cr("AdaptiveSizeStop: collection: %d ", | |
2120 heap->total_collections()); | |
2121 } | |
2122 } | |
2123 | |
2124 if (UsePerfData) { | |
2125 PSGCAdaptivePolicyCounters* const counters = heap->gc_policy_counters(); | |
2126 counters->update_counters(); | |
2127 counters->update_old_capacity(old_gen->capacity_in_bytes()); | |
2128 counters->update_young_capacity(young_gen->capacity_in_bytes()); | |
2129 } | |
2130 | |
2131 heap->resize_all_tlabs(); | |
2132 | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2133 // Resize the metaspace capactiy after a collection |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2134 MetaspaceGC::compute_new_size(); |
0 | 2135 |
2136 if (TraceGen1Time) accumulated_time()->stop(); | |
2137 | |
2138 if (PrintGC) { | |
2139 if (PrintGCDetails) { | |
2140 // No GC timestamp here. This is after GC so it would be confusing. | |
2141 young_gen->print_used_change(pre_gc_values.young_gen_used()); | |
2142 old_gen->print_used_change(pre_gc_values.old_gen_used()); | |
2143 heap->print_heap_change(pre_gc_values.heap_used()); | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2144 MetaspaceAux::print_metaspace_change(pre_gc_values.metadata_used()); |
0 | 2145 } else { |
2146 heap->print_heap_change(pre_gc_values.heap_used()); | |
2147 } | |
2148 } | |
2149 | |
2150 // Track memory usage and detect low memory | |
2151 MemoryService::track_memory_usage(); | |
2152 heap->update_counters(); | |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2153 gc_task_manager()->release_idle_workers(); |
0 | 2154 } |
2155 | |
1836
894b1d7c7e01
6423256: GC stacks should use a better data structure
jcoomes
parents:
1833
diff
changeset
|
2156 #ifdef ASSERT |
894b1d7c7e01
6423256: GC stacks should use a better data structure
jcoomes
parents:
1833
diff
changeset
|
2157 for (size_t i = 0; i < ParallelGCThreads + 1; ++i) { |
894b1d7c7e01
6423256: GC stacks should use a better data structure
jcoomes
parents:
1833
diff
changeset
|
2158 ParCompactionManager* const cm = |
894b1d7c7e01
6423256: GC stacks should use a better data structure
jcoomes
parents:
1833
diff
changeset
|
2159 ParCompactionManager::manager_array(int(i)); |
894b1d7c7e01
6423256: GC stacks should use a better data structure
jcoomes
parents:
1833
diff
changeset
|
2160 assert(cm->marking_stack()->is_empty(), "should be empty"); |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2161 assert(ParCompactionManager::region_list(int(i))->is_empty(), "should be empty"); |
1836
894b1d7c7e01
6423256: GC stacks should use a better data structure
jcoomes
parents:
1833
diff
changeset
|
2162 } |
894b1d7c7e01
6423256: GC stacks should use a better data structure
jcoomes
parents:
1833
diff
changeset
|
2163 #endif // ASSERT |
894b1d7c7e01
6423256: GC stacks should use a better data structure
jcoomes
parents:
1833
diff
changeset
|
2164 |
0 | 2165 if (VerifyAfterGC && heap->total_collections() >= VerifyGCStartAt) { |
2166 HandleMark hm; // Discard invalid handles created during verification | |
2167 gclog_or_tty->print(" VerifyAfterGC:"); | |
6865
4202510ee0fe
8000831: Heap verification output incorrect/incomplete
johnc
parents:
6787
diff
changeset
|
2168 Universe::verify(); |
0 | 2169 } |
2170 | |
2171 // Re-verify object start arrays | |
2172 if (VerifyObjectStartArray && | |
2173 VerifyAfterGC) { | |
2174 old_gen->verify_object_start_array(); | |
2175 } | |
2176 | |
263
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
2177 if (ZapUnusedHeapArea) { |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
2178 old_gen->object_space()->check_mangled_unused_area_complete(); |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
2179 } |
12eea04c8b06
6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents:
210
diff
changeset
|
2180 |
0 | 2181 NOT_PRODUCT(ref_processor()->verify_no_references_recorded()); |
2182 | |
2183 collection_exit.update(); | |
2184 | |
4872
aa3d708d67c4
7141200: log some interesting information in ring buffers for crashes
never
parents:
4712
diff
changeset
|
2185 heap->print_heap_after_gc(); |
0 | 2186 if (PrintGCTaskTimeStamps) { |
2187 gclog_or_tty->print_cr("VM-Thread " INT64_FORMAT " " INT64_FORMAT " " | |
2188 INT64_FORMAT, | |
2189 marking_start.ticks(), compaction_start.ticks(), | |
2190 collection_exit.ticks()); | |
2191 gc_task_manager()->print_task_time_stamps(); | |
2192 } | |
546
05c6d52fa7a9
6690928: Use spinning in combination with yields for workstealing termination.
jmasa
parents:
496
diff
changeset
|
2193 |
615
c6c601a0f2d6
6797870: Add -XX:+{HeapDump,PrintClassHistogram}{Before,After}FullGC
ysr
parents:
546
diff
changeset
|
2194 heap->post_full_gc_dump(); |
c6c601a0f2d6
6797870: Add -XX:+{HeapDump,PrintClassHistogram}{Before,After}FullGC
ysr
parents:
546
diff
changeset
|
2195 |
546
05c6d52fa7a9
6690928: Use spinning in combination with yields for workstealing termination.
jmasa
parents:
496
diff
changeset
|
2196 #ifdef TRACESPINNING |
05c6d52fa7a9
6690928: Use spinning in combination with yields for workstealing termination.
jmasa
parents:
496
diff
changeset
|
2197 ParallelTaskTerminator::print_termination_counts(); |
05c6d52fa7a9
6690928: Use spinning in combination with yields for workstealing termination.
jmasa
parents:
496
diff
changeset
|
2198 #endif |
4913
ab4422d0ed59
7146343: PS invoke methods should indicate the type of gc done
jcoomes
parents:
4872
diff
changeset
|
2199 |
ab4422d0ed59
7146343: PS invoke methods should indicate the type of gc done
jcoomes
parents:
4872
diff
changeset
|
2200 return true; |
0 | 2201 } |
2202 | |
2203 bool PSParallelCompact::absorb_live_data_from_eden(PSAdaptiveSizePolicy* size_policy, | |
2204 PSYoungGen* young_gen, | |
2205 PSOldGen* old_gen) { | |
2206 MutableSpace* const eden_space = young_gen->eden_space(); | |
2207 assert(!eden_space->is_empty(), "eden must be non-empty"); | |
2208 assert(young_gen->virtual_space()->alignment() == | |
2209 old_gen->virtual_space()->alignment(), "alignments do not match"); | |
2210 | |
2211 if (!(UseAdaptiveSizePolicy && UseAdaptiveGCBoundary)) { | |
2212 return false; | |
2213 } | |
2214 | |
2215 // Both generations must be completely committed. | |
2216 if (young_gen->virtual_space()->uncommitted_size() != 0) { | |
2217 return false; | |
2218 } | |
2219 if (old_gen->virtual_space()->uncommitted_size() != 0) { | |
2220 return false; | |
2221 } | |
2222 | |
2223 // Figure out how much to take from eden. Include the average amount promoted | |
2224 // in the total; otherwise the next young gen GC will simply bail out to a | |
2225 // full GC. | |
2226 const size_t alignment = old_gen->virtual_space()->alignment(); | |
2227 const size_t eden_used = eden_space->used_in_bytes(); | |
2228 const size_t promoted = (size_t)size_policy->avg_promoted()->padded_average(); | |
2229 const size_t absorb_size = align_size_up(eden_used + promoted, alignment); | |
2230 const size_t eden_capacity = eden_space->capacity_in_bytes(); | |
2231 | |
2232 if (absorb_size >= eden_capacity) { | |
2233 return false; // Must leave some space in eden. | |
2234 } | |
2235 | |
2236 const size_t new_young_size = young_gen->capacity_in_bytes() - absorb_size; | |
2237 if (new_young_size < young_gen->min_gen_size()) { | |
2238 return false; // Respect young gen minimum size. | |
2239 } | |
2240 | |
2241 if (TraceAdaptiveGCBoundary && Verbose) { | |
2242 gclog_or_tty->print(" absorbing " SIZE_FORMAT "K: " | |
2243 "eden " SIZE_FORMAT "K->" SIZE_FORMAT "K " | |
2244 "from " SIZE_FORMAT "K, to " SIZE_FORMAT "K " | |
2245 "young_gen " SIZE_FORMAT "K->" SIZE_FORMAT "K ", | |
2246 absorb_size / K, | |
2247 eden_capacity / K, (eden_capacity - absorb_size) / K, | |
2248 young_gen->from_space()->used_in_bytes() / K, | |
2249 young_gen->to_space()->used_in_bytes() / K, | |
2250 young_gen->capacity_in_bytes() / K, new_young_size / K); | |
2251 } | |
2252 | |
2253 // Fill the unused part of the old gen. | |
2254 MutableSpace* const old_space = old_gen->object_space(); | |
481
7d7a7c599c17
6578152: fill_region_with_object has usability and safety issues
jcoomes
parents:
457
diff
changeset
|
2255 HeapWord* const unused_start = old_space->top(); |
7d7a7c599c17
6578152: fill_region_with_object has usability and safety issues
jcoomes
parents:
457
diff
changeset
|
2256 size_t const unused_words = pointer_delta(old_space->end(), unused_start); |
7d7a7c599c17
6578152: fill_region_with_object has usability and safety issues
jcoomes
parents:
457
diff
changeset
|
2257 |
7d7a7c599c17
6578152: fill_region_with_object has usability and safety issues
jcoomes
parents:
457
diff
changeset
|
2258 if (unused_words > 0) { |
7d7a7c599c17
6578152: fill_region_with_object has usability and safety issues
jcoomes
parents:
457
diff
changeset
|
2259 if (unused_words < CollectedHeap::min_fill_size()) { |
7d7a7c599c17
6578152: fill_region_with_object has usability and safety issues
jcoomes
parents:
457
diff
changeset
|
2260 return false; // If the old gen cannot be filled, must give up. |
7d7a7c599c17
6578152: fill_region_with_object has usability and safety issues
jcoomes
parents:
457
diff
changeset
|
2261 } |
7d7a7c599c17
6578152: fill_region_with_object has usability and safety issues
jcoomes
parents:
457
diff
changeset
|
2262 CollectedHeap::fill_with_objects(unused_start, unused_words); |
0 | 2263 } |
2264 | |
2265 // Take the live data from eden and set both top and end in the old gen to | |
2266 // eden top. (Need to set end because reset_after_change() mangles the region | |
2267 // from end to virtual_space->high() in debug builds). | |
2268 HeapWord* const new_top = eden_space->top(); | |
2269 old_gen->virtual_space()->expand_into(young_gen->virtual_space(), | |
2270 absorb_size); | |
2271 young_gen->reset_after_change(); | |
2272 old_space->set_top(new_top); | |
2273 old_space->set_end(new_top); | |
2274 old_gen->reset_after_change(); | |
2275 | |
2276 // Update the object start array for the filler object and the data from eden. | |
2277 ObjectStartArray* const start_array = old_gen->start_array(); | |
481
7d7a7c599c17
6578152: fill_region_with_object has usability and safety issues
jcoomes
parents:
457
diff
changeset
|
2278 for (HeapWord* p = unused_start; p < new_top; p += oop(p)->size()) { |
7d7a7c599c17
6578152: fill_region_with_object has usability and safety issues
jcoomes
parents:
457
diff
changeset
|
2279 start_array->allocate_block(p); |
0 | 2280 } |
2281 | |
2282 // Could update the promoted average here, but it is not typically updated at | |
2283 // full GCs and the value to use is unclear. Something like | |
2284 // | |
2285 // cur_promoted_avg + absorb_size / number_of_scavenges_since_last_full_gc. | |
2286 | |
2287 size_policy->set_bytes_absorbed_from_eden(absorb_size); | |
2288 return true; | |
2289 } | |
2290 | |
2291 GCTaskManager* const PSParallelCompact::gc_task_manager() { | |
2292 assert(ParallelScavengeHeap::gc_task_manager() != NULL, | |
2293 "shouldn't return NULL"); | |
2294 return ParallelScavengeHeap::gc_task_manager(); | |
2295 } | |
2296 | |
2297 void PSParallelCompact::marking_phase(ParCompactionManager* cm, | |
2298 bool maximum_heap_compaction) { | |
2299 // Recursively traverse all live objects and mark them | |
2300 TraceTime tm("marking phase", print_phases(), true, gclog_or_tty); | |
2301 | |
2302 ParallelScavengeHeap* heap = gc_heap(); | |
2303 uint parallel_gc_threads = heap->gc_task_manager()->workers(); | |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2304 uint active_gc_threads = heap->gc_task_manager()->active_workers(); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2305 TaskQueueSetSuper* qset = ParCompactionManager::region_array(); |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2306 ParallelTaskTerminator terminator(active_gc_threads, qset); |
0 | 2307 |
2308 PSParallelCompact::MarkAndPushClosure mark_and_push_closure(cm); | |
2309 PSParallelCompact::FollowStackClosure follow_stack_closure(cm); | |
2310 | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2311 // Need new claim bits before marking starts. |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2312 ClassLoaderDataGraph::clear_claimed_marks(); |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2313 |
0 | 2314 { |
2315 TraceTime tm_m("par mark", print_phases(), true, gclog_or_tty); | |
989
148e5441d916
6863023: need non-perm oops in code cache for JSR 292
jrose
parents:
696
diff
changeset
|
2316 ParallelScavengeHeap::ParStrongRootsScope psrs; |
0 | 2317 |
2318 GCTaskQueue* q = GCTaskQueue::create(); | |
2319 | |
2320 q->enqueue(new MarkFromRootsTask(MarkFromRootsTask::universe)); | |
2321 q->enqueue(new MarkFromRootsTask(MarkFromRootsTask::jni_handles)); | |
2322 // We scan the thread roots in parallel | |
2323 Threads::create_thread_roots_marking_tasks(q); | |
2324 q->enqueue(new MarkFromRootsTask(MarkFromRootsTask::object_synchronizer)); | |
2325 q->enqueue(new MarkFromRootsTask(MarkFromRootsTask::flat_profiler)); | |
2326 q->enqueue(new MarkFromRootsTask(MarkFromRootsTask::management)); | |
2327 q->enqueue(new MarkFromRootsTask(MarkFromRootsTask::system_dictionary)); | |
2328 q->enqueue(new MarkFromRootsTask(MarkFromRootsTask::jvmti)); | |
989
148e5441d916
6863023: need non-perm oops in code cache for JSR 292
jrose
parents:
696
diff
changeset
|
2329 q->enqueue(new MarkFromRootsTask(MarkFromRootsTask::code_cache)); |
0 | 2330 |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2331 if (active_gc_threads > 1) { |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2332 for (uint j = 0; j < active_gc_threads; j++) { |
0 | 2333 q->enqueue(new StealMarkingTask(&terminator)); |
2334 } | |
2335 } | |
2336 | |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2337 gc_task_manager()->execute_and_wait(q); |
0 | 2338 } |
2339 | |
2340 // Process reference objects found during marking | |
2341 { | |
2342 TraceTime tm_r("reference processing", print_phases(), true, gclog_or_tty); | |
2343 if (ref_processor()->processing_is_mt()) { | |
2344 RefProcTaskExecutor task_executor; | |
2345 ref_processor()->process_discovered_references( | |
453
c96030fff130
6684579: SoftReference processing can be made more efficient
ysr
parents:
376
diff
changeset
|
2346 is_alive_closure(), &mark_and_push_closure, &follow_stack_closure, |
c96030fff130
6684579: SoftReference processing can be made more efficient
ysr
parents:
376
diff
changeset
|
2347 &task_executor); |
0 | 2348 } else { |
2349 ref_processor()->process_discovered_references( | |
453
c96030fff130
6684579: SoftReference processing can be made more efficient
ysr
parents:
376
diff
changeset
|
2350 is_alive_closure(), &mark_and_push_closure, &follow_stack_closure, NULL); |
0 | 2351 } |
2352 } | |
2353 | |
2354 TraceTime tm_c("class unloading", print_phases(), true, gclog_or_tty); | |
2355 // Follow system dictionary roots and unload classes. | |
2356 bool purged_class = SystemDictionary::do_unloading(is_alive_closure()); | |
2357 | |
2358 // Follow code cache roots. | |
6787
8966c2d65d96
7200470: KeepAliveClosure not needed in CodeCache::do_unloading
brutisso
parents:
6757
diff
changeset
|
2359 CodeCache::do_unloading(is_alive_closure(), purged_class); |
1311
2a1472c30599
4396719: Mark Sweep stack overflow on deeply nested Object arrays
jcoomes
parents:
997
diff
changeset
|
2360 cm->follow_marking_stacks(); // Flush marking stack. |
0 | 2361 |
2362 // Update subklass/sibling/implementor links of live klasses | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2363 Klass::clean_weak_klass_links(is_alive_closure()); |
0 | 2364 |
2177
3582bf76420e
6990754: Use native memory and reference counting to implement SymbolTable
coleenp
parents:
2147
diff
changeset
|
2365 // Visit interned string tables and delete unmarked oops |
0 | 2366 StringTable::unlink(is_alive_closure()); |
2177
3582bf76420e
6990754: Use native memory and reference counting to implement SymbolTable
coleenp
parents:
2147
diff
changeset
|
2367 // Clean up unreferenced symbols in symbol table. |
3582bf76420e
6990754: Use native memory and reference counting to implement SymbolTable
coleenp
parents:
2147
diff
changeset
|
2368 SymbolTable::unlink(); |
0 | 2369 |
1311
2a1472c30599
4396719: Mark Sweep stack overflow on deeply nested Object arrays
jcoomes
parents:
997
diff
changeset
|
2370 assert(cm->marking_stacks_empty(), "marking stacks should be empty"); |
0 | 2371 } |
2372 | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2373 void PSParallelCompact::follow_klass(ParCompactionManager* cm, Klass* klass) { |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2374 ClassLoaderData* cld = klass->class_loader_data(); |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2375 // The actual processing of the klass is done when we |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2376 // traverse the list of Klasses in the class loader data. |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2377 PSParallelCompact::follow_class_loader(cm, cld); |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2378 } |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2379 |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2380 void PSParallelCompact::adjust_klass(ParCompactionManager* cm, Klass* klass) { |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2381 ClassLoaderData* cld = klass->class_loader_data(); |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2382 // The actual processing of the klass is done when we |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2383 // traverse the list of Klasses in the class loader data. |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2384 PSParallelCompact::adjust_class_loader(cm, cld); |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2385 } |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2386 |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2387 void PSParallelCompact::follow_class_loader(ParCompactionManager* cm, |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2388 ClassLoaderData* cld) { |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2389 PSParallelCompact::MarkAndPushClosure mark_and_push_closure(cm); |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2390 PSParallelCompact::FollowKlassClosure follow_klass_closure(&mark_and_push_closure); |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2391 |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2392 cld->oops_do(&mark_and_push_closure, &follow_klass_closure, true); |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2393 } |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2394 |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2395 void PSParallelCompact::adjust_class_loader(ParCompactionManager* cm, |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2396 ClassLoaderData* cld) { |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2397 cld->oops_do(PSParallelCompact::adjust_root_pointer_closure(), |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2398 PSParallelCompact::adjust_klass_closure(), |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2399 true); |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2400 } |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2401 |
0 | 2402 // This should be moved to the shared markSweep code! |
2403 class PSAlwaysTrueClosure: public BoolObjectClosure { | |
2404 public: | |
2405 void do_object(oop p) { ShouldNotReachHere(); } | |
2406 bool do_object_b(oop p) { return true; } | |
2407 }; | |
2408 static PSAlwaysTrueClosure always_true; | |
2409 | |
2410 void PSParallelCompact::adjust_roots() { | |
2411 // Adjust the pointers to reflect the new locations | |
2412 TraceTime tm("adjust roots", print_phases(), true, gclog_or_tty); | |
2413 | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2414 // Need new claim bits when tracing through and adjusting pointers. |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2415 ClassLoaderDataGraph::clear_claimed_marks(); |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2416 |
0 | 2417 // General strong roots. |
2418 Universe::oops_do(adjust_root_pointer_closure()); | |
2419 JNIHandles::oops_do(adjust_root_pointer_closure()); // Global (strong) JNI handles | |
7179
d0aa87f04bd5
8003720: NPG: Method in interpreter stack frame can be deallocated
stefank
parents:
6865
diff
changeset
|
2420 CLDToOopClosure adjust_from_cld(adjust_root_pointer_closure()); |
d0aa87f04bd5
8003720: NPG: Method in interpreter stack frame can be deallocated
stefank
parents:
6865
diff
changeset
|
2421 Threads::oops_do(adjust_root_pointer_closure(), &adjust_from_cld, NULL); |
0 | 2422 ObjectSynchronizer::oops_do(adjust_root_pointer_closure()); |
2423 FlatProfiler::oops_do(adjust_root_pointer_closure()); | |
2424 Management::oops_do(adjust_root_pointer_closure()); | |
2425 JvmtiExport::oops_do(adjust_root_pointer_closure()); | |
2426 // SO_AllClasses | |
2427 SystemDictionary::oops_do(adjust_root_pointer_closure()); | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2428 ClassLoaderDataGraph::oops_do(adjust_root_pointer_closure(), adjust_klass_closure(), true); |
0 | 2429 |
2430 // Now adjust pointers in remaining weak roots. (All of which should | |
2431 // have been cleared if they pointed to non-surviving objects.) | |
2432 // Global (weak) JNI handles | |
2433 JNIHandles::weak_oops_do(&always_true, adjust_root_pointer_closure()); | |
2434 | |
2435 CodeCache::oops_do(adjust_pointer_closure()); | |
2436 StringTable::oops_do(adjust_root_pointer_closure()); | |
2437 ref_processor()->weak_oops_do(adjust_root_pointer_closure()); | |
2438 // Roots were visited so references into the young gen in roots | |
2439 // may have been scanned. Process them also. | |
2440 // Should the reference processor have a span that excludes | |
2441 // young gen objects? | |
2442 PSScavenge::reference_processor()->weak_oops_do( | |
2443 adjust_root_pointer_closure()); | |
2444 } | |
2445 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2446 void PSParallelCompact::enqueue_region_draining_tasks(GCTaskQueue* q, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2447 uint parallel_gc_threads) |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2448 { |
0 | 2449 TraceTime tm("drain task setup", print_phases(), true, gclog_or_tty); |
2450 | |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2451 // Find the threads that are active |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2452 unsigned int which = 0; |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2453 |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2454 const uint task_count = MAX2(parallel_gc_threads, 1U); |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2455 for (uint j = 0; j < task_count; j++) { |
1833
8b10f48633dc
6984287: Regularize how GC parallel workers are specified.
jmasa
parents:
1638
diff
changeset
|
2456 q->enqueue(new DrainStacksCompactionTask(j)); |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2457 ParCompactionManager::verify_region_list_empty(j); |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2458 // Set the region stacks variables to "no" region stack values |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2459 // so that they will be recognized and needing a region stack |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2460 // in the stealing tasks if they do not get one by executing |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2461 // a draining stack. |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2462 ParCompactionManager* cm = ParCompactionManager::manager_array(j); |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2463 cm->set_region_stack(NULL); |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2464 cm->set_region_stack_index((uint)max_uintx); |
0 | 2465 } |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2466 ParCompactionManager::reset_recycled_stack_index(); |
0 | 2467 |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2468 // Find all regions that are available (can be filled immediately) and |
0 | 2469 // distribute them to the thread stacks. The iteration is done in reverse |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2470 // order (high to low) so the regions will be removed in ascending order. |
0 | 2471 |
2472 const ParallelCompactData& sd = PSParallelCompact::summary_data(); | |
2473 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2474 size_t fillable_regions = 0; // A count for diagnostic purposes. |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2475 // A region index which corresponds to the tasks created above. |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2476 // "which" must be 0 <= which < task_count |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2477 |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2478 which = 0; |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2479 // id + 1 is used to test termination so unsigned can |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2480 // be used with an old_space_id == 0. |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2481 for (unsigned int id = to_space_id; id + 1 > old_space_id; --id) { |
0 | 2482 SpaceInfo* const space_info = _space_info + id; |
2483 MutableSpace* const space = space_info->space(); | |
2484 HeapWord* const new_top = space_info->new_top(); | |
2485 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2486 const size_t beg_region = sd.addr_to_region_idx(space_info->dense_prefix()); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2487 const size_t end_region = |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2488 sd.addr_to_region_idx(sd.region_align_up(new_top)); |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2489 |
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2490 for (size_t cur = end_region - 1; cur + 1 > beg_region; --cur) { |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2491 if (sd.region(cur)->claim_unsafe()) { |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2492 ParCompactionManager::region_list_push(which, cur); |
0 | 2493 |
2494 if (TraceParallelOldGCCompactionPhase && Verbose) { | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2495 const size_t count_mod_8 = fillable_regions & 7; |
0 | 2496 if (count_mod_8 == 0) gclog_or_tty->print("fillable: "); |
264
15dd2594d08e
6718283: existing uses of *_FORMAT_W() were broken by 6521491
jcoomes
parents:
263
diff
changeset
|
2497 gclog_or_tty->print(" " SIZE_FORMAT_W(7), cur); |
0 | 2498 if (count_mod_8 == 7) gclog_or_tty->cr(); |
2499 } | |
2500 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2501 NOT_PRODUCT(++fillable_regions;) |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2502 |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2503 // Assign regions to tasks in round-robin fashion. |
0 | 2504 if (++which == task_count) { |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2505 assert(which <= parallel_gc_threads, |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2506 "Inconsistent number of workers"); |
0 | 2507 which = 0; |
2508 } | |
2509 } | |
2510 } | |
2511 } | |
2512 | |
2513 if (TraceParallelOldGCCompactionPhase) { | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2514 if (Verbose && (fillable_regions & 7) != 0) gclog_or_tty->cr(); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2515 gclog_or_tty->print_cr("%u initially fillable regions", fillable_regions); |
0 | 2516 } |
2517 } | |
2518 | |
2519 #define PAR_OLD_DENSE_PREFIX_OVER_PARTITIONING 4 | |
2520 | |
2521 void PSParallelCompact::enqueue_dense_prefix_tasks(GCTaskQueue* q, | |
2522 uint parallel_gc_threads) { | |
2523 TraceTime tm("dense prefix task setup", print_phases(), true, gclog_or_tty); | |
2524 | |
2525 ParallelCompactData& sd = PSParallelCompact::summary_data(); | |
2526 | |
2527 // Iterate over all the spaces adding tasks for updating | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2528 // regions in the dense prefix. Assume that 1 gc thread |
0 | 2529 // will work on opening the gaps and the remaining gc threads |
2530 // will work on the dense prefix. | |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2531 unsigned int space_id; |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2532 for (space_id = old_space_id; space_id < last_space_id; ++ space_id) { |
0 | 2533 HeapWord* const dense_prefix_end = _space_info[space_id].dense_prefix(); |
2534 const MutableSpace* const space = _space_info[space_id].space(); | |
2535 | |
2536 if (dense_prefix_end == space->bottom()) { | |
2537 // There is no dense prefix for this space. | |
2538 continue; | |
2539 } | |
2540 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2541 // The dense prefix is before this region. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2542 size_t region_index_end_dense_prefix = |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2543 sd.addr_to_region_idx(dense_prefix_end); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2544 RegionData* const dense_prefix_cp = |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2545 sd.region(region_index_end_dense_prefix); |
0 | 2546 assert(dense_prefix_end == space->end() || |
2547 dense_prefix_cp->available() || | |
2548 dense_prefix_cp->claimed(), | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2549 "The region after the dense prefix should always be ready to fill"); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2550 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2551 size_t region_index_start = sd.addr_to_region_idx(space->bottom()); |
0 | 2552 |
2553 // Is there dense prefix work? | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2554 size_t total_dense_prefix_regions = |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2555 region_index_end_dense_prefix - region_index_start; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2556 // How many regions of the dense prefix should be given to |
0 | 2557 // each thread? |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2558 if (total_dense_prefix_regions > 0) { |
0 | 2559 uint tasks_for_dense_prefix = 1; |
3251
eda9eb483d29
6841742: par compact - remove unused/unsupported options
jcoomes
parents:
2369
diff
changeset
|
2560 if (total_dense_prefix_regions <= |
eda9eb483d29
6841742: par compact - remove unused/unsupported options
jcoomes
parents:
2369
diff
changeset
|
2561 (parallel_gc_threads * PAR_OLD_DENSE_PREFIX_OVER_PARTITIONING)) { |
eda9eb483d29
6841742: par compact - remove unused/unsupported options
jcoomes
parents:
2369
diff
changeset
|
2562 // Don't over partition. This assumes that |
eda9eb483d29
6841742: par compact - remove unused/unsupported options
jcoomes
parents:
2369
diff
changeset
|
2563 // PAR_OLD_DENSE_PREFIX_OVER_PARTITIONING is a small integer value |
eda9eb483d29
6841742: par compact - remove unused/unsupported options
jcoomes
parents:
2369
diff
changeset
|
2564 // so there are not many regions to process. |
eda9eb483d29
6841742: par compact - remove unused/unsupported options
jcoomes
parents:
2369
diff
changeset
|
2565 tasks_for_dense_prefix = parallel_gc_threads; |
eda9eb483d29
6841742: par compact - remove unused/unsupported options
jcoomes
parents:
2369
diff
changeset
|
2566 } else { |
eda9eb483d29
6841742: par compact - remove unused/unsupported options
jcoomes
parents:
2369
diff
changeset
|
2567 // Over partition |
eda9eb483d29
6841742: par compact - remove unused/unsupported options
jcoomes
parents:
2369
diff
changeset
|
2568 tasks_for_dense_prefix = parallel_gc_threads * |
eda9eb483d29
6841742: par compact - remove unused/unsupported options
jcoomes
parents:
2369
diff
changeset
|
2569 PAR_OLD_DENSE_PREFIX_OVER_PARTITIONING; |
0 | 2570 } |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2571 size_t regions_per_thread = total_dense_prefix_regions / |
0 | 2572 tasks_for_dense_prefix; |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2573 // Give each thread at least 1 region. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2574 if (regions_per_thread == 0) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2575 regions_per_thread = 1; |
0 | 2576 } |
2577 | |
2578 for (uint k = 0; k < tasks_for_dense_prefix; k++) { | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2579 if (region_index_start >= region_index_end_dense_prefix) { |
0 | 2580 break; |
2581 } | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2582 // region_index_end is not processed |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2583 size_t region_index_end = MIN2(region_index_start + regions_per_thread, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2584 region_index_end_dense_prefix); |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2585 q->enqueue(new UpdateDensePrefixTask(SpaceId(space_id), |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2586 region_index_start, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2587 region_index_end)); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2588 region_index_start = region_index_end; |
0 | 2589 } |
2590 } | |
2591 // This gets any part of the dense prefix that did not | |
2592 // fit evenly. | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2593 if (region_index_start < region_index_end_dense_prefix) { |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2594 q->enqueue(new UpdateDensePrefixTask(SpaceId(space_id), |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2595 region_index_start, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2596 region_index_end_dense_prefix)); |
0 | 2597 } |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2598 } |
0 | 2599 } |
2600 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2601 void PSParallelCompact::enqueue_region_stealing_tasks( |
0 | 2602 GCTaskQueue* q, |
2603 ParallelTaskTerminator* terminator_ptr, | |
2604 uint parallel_gc_threads) { | |
2605 TraceTime tm("steal task setup", print_phases(), true, gclog_or_tty); | |
2606 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2607 // Once a thread has drained it's stack, it should try to steal regions from |
0 | 2608 // other threads. |
2609 if (parallel_gc_threads > 1) { | |
2610 for (uint j = 0; j < parallel_gc_threads; j++) { | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2611 q->enqueue(new StealRegionCompactionTask(terminator_ptr)); |
0 | 2612 } |
2613 } | |
2614 } | |
2615 | |
2616 void PSParallelCompact::compact() { | |
2617 // trace("5"); | |
2618 TraceTime tm("compaction phase", print_phases(), true, gclog_or_tty); | |
2619 | |
2620 ParallelScavengeHeap* heap = (ParallelScavengeHeap*)Universe::heap(); | |
2621 assert(heap->kind() == CollectedHeap::ParallelScavengeHeap, "Sanity"); | |
2622 PSOldGen* old_gen = heap->old_gen(); | |
2623 old_gen->start_array()->reset(); | |
2624 uint parallel_gc_threads = heap->gc_task_manager()->workers(); | |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2625 uint active_gc_threads = heap->gc_task_manager()->active_workers(); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2626 TaskQueueSetSuper* qset = ParCompactionManager::region_array(); |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2627 ParallelTaskTerminator terminator(active_gc_threads, qset); |
0 | 2628 |
2629 GCTaskQueue* q = GCTaskQueue::create(); | |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2630 enqueue_region_draining_tasks(q, active_gc_threads); |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2631 enqueue_dense_prefix_tasks(q, active_gc_threads); |
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2632 enqueue_region_stealing_tasks(q, &terminator, active_gc_threads); |
0 | 2633 |
2634 { | |
2635 TraceTime tm_pc("par compact", print_phases(), true, gclog_or_tty); | |
2636 | |
4095
bca17e38de00
6593758: RFE: Enhance GC ergonomics to dynamically choose ParallelGCThreads
jmasa
parents:
3979
diff
changeset
|
2637 gc_task_manager()->execute_and_wait(q); |
0 | 2638 |
2639 #ifdef ASSERT | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2640 // Verify that all regions have been processed before the deferred updates. |
0 | 2641 for (unsigned int id = old_space_id; id < last_space_id; ++id) { |
2642 verify_complete(SpaceId(id)); | |
2643 } | |
2644 #endif | |
2645 } | |
2646 | |
2647 { | |
2648 // Update the deferred objects, if any. Any compaction manager can be used. | |
2649 TraceTime tm_du("deferred updates", print_phases(), true, gclog_or_tty); | |
2650 ParCompactionManager* cm = ParCompactionManager::manager_array(0); | |
2651 for (unsigned int id = old_space_id; id < last_space_id; ++id) { | |
2652 update_deferred_objects(cm, SpaceId(id)); | |
2653 } | |
2654 } | |
2655 } | |
2656 | |
2657 #ifdef ASSERT | |
2658 void PSParallelCompact::verify_complete(SpaceId space_id) { | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2659 // All Regions between space bottom() to new_top() should be marked as filled |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2660 // and all Regions between new_top() and top() should be available (i.e., |
0 | 2661 // should have been emptied). |
2662 ParallelCompactData& sd = summary_data(); | |
2663 SpaceInfo si = _space_info[space_id]; | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2664 HeapWord* new_top_addr = sd.region_align_up(si.new_top()); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2665 HeapWord* old_top_addr = sd.region_align_up(si.space()->top()); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2666 const size_t beg_region = sd.addr_to_region_idx(si.space()->bottom()); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2667 const size_t new_top_region = sd.addr_to_region_idx(new_top_addr); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2668 const size_t old_top_region = sd.addr_to_region_idx(old_top_addr); |
0 | 2669 |
2670 bool issued_a_warning = false; | |
2671 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2672 size_t cur_region; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2673 for (cur_region = beg_region; cur_region < new_top_region; ++cur_region) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2674 const RegionData* const c = sd.region(cur_region); |
0 | 2675 if (!c->completed()) { |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2676 warning("region " SIZE_FORMAT " not filled: " |
0 | 2677 "destination_count=" SIZE_FORMAT, |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2678 cur_region, c->destination_count()); |
0 | 2679 issued_a_warning = true; |
2680 } | |
2681 } | |
2682 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2683 for (cur_region = new_top_region; cur_region < old_top_region; ++cur_region) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2684 const RegionData* const c = sd.region(cur_region); |
0 | 2685 if (!c->available()) { |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2686 warning("region " SIZE_FORMAT " not empty: " |
0 | 2687 "destination_count=" SIZE_FORMAT, |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2688 cur_region, c->destination_count()); |
0 | 2689 issued_a_warning = true; |
2690 } | |
2691 } | |
2692 | |
2693 if (issued_a_warning) { | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2694 print_region_ranges(); |
0 | 2695 } |
2696 } | |
2697 #endif // #ifdef ASSERT | |
2698 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2699 // Update interior oops in the ranges of regions [beg_region, end_region). |
0 | 2700 void |
2701 PSParallelCompact::update_and_deadwood_in_dense_prefix(ParCompactionManager* cm, | |
2702 SpaceId space_id, | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2703 size_t beg_region, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2704 size_t end_region) { |
0 | 2705 ParallelCompactData& sd = summary_data(); |
2706 ParMarkBitMap* const mbm = mark_bitmap(); | |
2707 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2708 HeapWord* beg_addr = sd.region_to_addr(beg_region); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2709 HeapWord* const end_addr = sd.region_to_addr(end_region); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2710 assert(beg_region <= end_region, "bad region range"); |
0 | 2711 assert(end_addr <= dense_prefix(space_id), "not in the dense prefix"); |
2712 | |
2713 #ifdef ASSERT | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2714 // Claim the regions to avoid triggering an assert when they are marked as |
0 | 2715 // filled. |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2716 for (size_t claim_region = beg_region; claim_region < end_region; ++claim_region) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2717 assert(sd.region(claim_region)->claim_unsafe(), "claim() failed"); |
0 | 2718 } |
2719 #endif // #ifdef ASSERT | |
2720 | |
2721 if (beg_addr != space(space_id)->bottom()) { | |
2722 // Find the first live object or block of dead space that *starts* in this | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2723 // range of regions. If a partial object crosses onto the region, skip it; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2724 // it will be marked for 'deferred update' when the object head is |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2725 // processed. If dead space crosses onto the region, it is also skipped; it |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2726 // will be filled when the prior region is processed. If neither of those |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2727 // apply, the first word in the region is the start of a live object or dead |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2728 // space. |
0 | 2729 assert(beg_addr > space(space_id)->bottom(), "sanity"); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2730 const RegionData* const cp = sd.region(beg_region); |
0 | 2731 if (cp->partial_obj_size() != 0) { |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2732 beg_addr = sd.partial_obj_end(beg_region); |
0 | 2733 } else if (dead_space_crosses_boundary(cp, mbm->addr_to_bit(beg_addr))) { |
2734 beg_addr = mbm->find_obj_beg(beg_addr, end_addr); | |
2735 } | |
2736 } | |
2737 | |
2738 if (beg_addr < end_addr) { | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2739 // A live object or block of dead space starts in this range of Regions. |
0 | 2740 HeapWord* const dense_prefix_end = dense_prefix(space_id); |
2741 | |
2742 // Create closures and iterate. | |
2743 UpdateOnlyClosure update_closure(mbm, cm, space_id); | |
2744 FillClosure fill_closure(cm, space_id); | |
2745 ParMarkBitMap::IterationStatus status; | |
2746 status = mbm->iterate(&update_closure, &fill_closure, beg_addr, end_addr, | |
2747 dense_prefix_end); | |
2748 if (status == ParMarkBitMap::incomplete) { | |
2749 update_closure.do_addr(update_closure.source()); | |
2750 } | |
2751 } | |
2752 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2753 // Mark the regions as filled. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2754 RegionData* const beg_cp = sd.region(beg_region); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2755 RegionData* const end_cp = sd.region(end_region); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2756 for (RegionData* cp = beg_cp; cp < end_cp; ++cp) { |
0 | 2757 cp->set_completed(); |
2758 } | |
2759 } | |
2760 | |
2761 // Return the SpaceId for the space containing addr. If addr is not in the | |
2762 // heap, last_space_id is returned. In debug mode it expects the address to be | |
2763 // in the heap and asserts such. | |
2764 PSParallelCompact::SpaceId PSParallelCompact::space_id(HeapWord* addr) { | |
2765 assert(Universe::heap()->is_in_reserved(addr), "addr not in the heap"); | |
2766 | |
6725
da91efe96a93
6964458: Reimplement class meta-data storage to use native memory
coleenp
parents:
6197
diff
changeset
|
2767 for (unsigned int id = old_space_id; id < last_space_id; ++id) { |
0 | 2768 if (_space_info[id].space()->contains(addr)) { |
2769 return SpaceId(id); | |
2770 } | |
2771 } | |
2772 | |
2773 assert(false, "no space contains the addr"); | |
2774 return last_space_id; | |
2775 } | |
2776 | |
2777 void PSParallelCompact::update_deferred_objects(ParCompactionManager* cm, | |
2778 SpaceId id) { | |
2779 assert(id < last_space_id, "bad space id"); | |
2780 | |
2781 ParallelCompactData& sd = summary_data(); | |
2782 const SpaceInfo* const space_info = _space_info + id; | |
2783 ObjectStartArray* const start_array = space_info->start_array(); | |
2784 | |
2785 const MutableSpace* const space = space_info->space(); | |
2786 assert(space_info->dense_prefix() >= space->bottom(), "dense_prefix not set"); | |
2787 HeapWord* const beg_addr = space_info->dense_prefix(); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2788 HeapWord* const end_addr = sd.region_align_up(space_info->new_top()); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2789 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2790 const RegionData* const beg_region = sd.addr_to_region_ptr(beg_addr); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2791 const RegionData* const end_region = sd.addr_to_region_ptr(end_addr); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2792 const RegionData* cur_region; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2793 for (cur_region = beg_region; cur_region < end_region; ++cur_region) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2794 HeapWord* const addr = cur_region->deferred_obj_addr(); |
0 | 2795 if (addr != NULL) { |
2796 if (start_array != NULL) { | |
2797 start_array->allocate_block(addr); | |
2798 } | |
2799 oop(addr)->update_contents(cm); | |
2800 assert(oop(addr)->is_oop_or_null(), "should be an oop now"); | |
2801 } | |
2802 } | |
2803 } | |
2804 | |
2805 // Skip over count live words starting from beg, and return the address of the | |
2806 // next live word. Unless marked, the word corresponding to beg is assumed to | |
2807 // be dead. Callers must either ensure beg does not correspond to the middle of | |
2808 // an object, or account for those live words in some other way. Callers must | |
2809 // also ensure that there are enough live words in the range [beg, end) to skip. | |
2810 HeapWord* | |
2811 PSParallelCompact::skip_live_words(HeapWord* beg, HeapWord* end, size_t count) | |
2812 { | |
2813 assert(count > 0, "sanity"); | |
2814 | |
2815 ParMarkBitMap* m = mark_bitmap(); | |
2816 idx_t bits_to_skip = m->words_to_bits(count); | |
2817 idx_t cur_beg = m->addr_to_bit(beg); | |
2818 const idx_t search_end = BitMap::word_align_up(m->addr_to_bit(end)); | |
2819 | |
2820 do { | |
2821 cur_beg = m->find_obj_beg(cur_beg, search_end); | |
2822 idx_t cur_end = m->find_obj_end(cur_beg, search_end); | |
2823 const size_t obj_bits = cur_end - cur_beg + 1; | |
2824 if (obj_bits > bits_to_skip) { | |
2825 return m->bit_to_addr(cur_beg + bits_to_skip); | |
2826 } | |
2827 bits_to_skip -= obj_bits; | |
2828 cur_beg = cur_end + 1; | |
2829 } while (bits_to_skip > 0); | |
2830 | |
2831 // Skipping the desired number of words landed just past the end of an object. | |
2832 // Find the start of the next object. | |
2833 cur_beg = m->find_obj_beg(cur_beg, search_end); | |
2834 assert(cur_beg < m->addr_to_bit(end), "not enough live words to skip"); | |
2835 return m->bit_to_addr(cur_beg); | |
2836 } | |
2837 | |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2838 HeapWord* PSParallelCompact::first_src_addr(HeapWord* const dest_addr, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2839 SpaceId src_space_id, |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2840 size_t src_region_idx) |
0 | 2841 { |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2842 assert(summary_data().is_region_aligned(dest_addr), "not aligned"); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2843 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2844 const SplitInfo& split_info = _space_info[src_space_id].split_info(); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2845 if (split_info.dest_region_addr() == dest_addr) { |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2846 // The partial object ending at the split point contains the first word to |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2847 // be copied to dest_addr. |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2848 return split_info.first_src_addr(); |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2849 } |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2850 |
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
2851 const ParallelCompactData& sd = summary_data(); |
0 | 2852 ParMarkBitMap* const bitmap = mark_bitmap(); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2853 const size_t RegionSize = ParallelCompactData::RegionSize; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2854 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2855 assert(sd.is_region_aligned(dest_addr), "not aligned"); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2856 const RegionData* const src_region_ptr = sd.region(src_region_idx); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2857 const size_t partial_obj_size = src_region_ptr->partial_obj_size(); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2858 HeapWord* const src_region_destination = src_region_ptr->destination(); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2859 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2860 assert(dest_addr >= src_region_destination, "wrong src region"); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2861 assert(src_region_ptr->data_size() > 0, "src region cannot be empty"); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2862 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2863 HeapWord* const src_region_beg = sd.region_to_addr(src_region_idx); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2864 HeapWord* const src_region_end = src_region_beg + RegionSize; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2865 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2866 HeapWord* addr = src_region_beg; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2867 if (dest_addr == src_region_destination) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2868 // Return the first live word in the source region. |
0 | 2869 if (partial_obj_size == 0) { |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2870 addr = bitmap->find_obj_beg(addr, src_region_end); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2871 assert(addr < src_region_end, "no objects start in src region"); |
0 | 2872 } |
2873 return addr; | |
2874 } | |
2875 | |
2876 // Must skip some live data. | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2877 size_t words_to_skip = dest_addr - src_region_destination; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2878 assert(src_region_ptr->data_size() > words_to_skip, "wrong src region"); |
0 | 2879 |
2880 if (partial_obj_size >= words_to_skip) { | |
2881 // All the live words to skip are part of the partial object. | |
2882 addr += words_to_skip; | |
2883 if (partial_obj_size == words_to_skip) { | |
2884 // Find the first live word past the partial object. | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2885 addr = bitmap->find_obj_beg(addr, src_region_end); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2886 assert(addr < src_region_end, "wrong src region"); |
0 | 2887 } |
2888 return addr; | |
2889 } | |
2890 | |
2891 // Skip over the partial object (if any). | |
2892 if (partial_obj_size != 0) { | |
2893 words_to_skip -= partial_obj_size; | |
2894 addr += partial_obj_size; | |
2895 } | |
2896 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2897 // Skip over live words due to objects that start in the region. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2898 addr = skip_live_words(addr, src_region_end, words_to_skip); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2899 assert(addr < src_region_end, "wrong src region"); |
0 | 2900 return addr; |
2901 } | |
2902 | |
2903 void PSParallelCompact::decrement_destination_counts(ParCompactionManager* cm, | |
495
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2904 SpaceId src_space_id, |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2905 size_t beg_region, |
0 | 2906 HeapWord* end_addr) |
2907 { | |
2908 ParallelCompactData& sd = summary_data(); | |
495
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2909 |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2910 #ifdef ASSERT |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2911 MutableSpace* const src_space = _space_info[src_space_id].space(); |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2912 HeapWord* const beg_addr = sd.region_to_addr(beg_region); |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2913 assert(src_space->contains(beg_addr) || beg_addr == src_space->end(), |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2914 "src_space_id does not match beg_addr"); |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2915 assert(src_space->contains(end_addr) || end_addr == src_space->end(), |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2916 "src_space_id does not match end_addr"); |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2917 #endif // #ifdef ASSERT |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2918 |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2919 RegionData* const beg = sd.region(beg_region); |
495
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2920 RegionData* const end = sd.addr_to_region_ptr(sd.region_align_up(end_addr)); |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2921 |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2922 // Regions up to new_top() are enqueued if they become available. |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2923 HeapWord* const new_top = _space_info[src_space_id].new_top(); |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2924 RegionData* const enqueue_end = |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2925 sd.addr_to_region_ptr(sd.region_align_up(new_top)); |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2926 |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2927 for (RegionData* cur = beg; cur < end; ++cur) { |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2928 assert(cur->data_size() > 0, "region must have live data"); |
0 | 2929 cur->decrement_destination_count(); |
495
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
2930 if (cur < enqueue_end && cur->available() && cur->claim()) { |
1638 | 2931 cm->push_region(sd.region(cur)); |
0 | 2932 } |
2933 } | |
2934 } | |
2935 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2936 size_t PSParallelCompact::next_src_region(MoveAndUpdateClosure& closure, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2937 SpaceId& src_space_id, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2938 HeapWord*& src_space_top, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2939 HeapWord* end_addr) |
0 | 2940 { |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2941 typedef ParallelCompactData::RegionData RegionData; |
0 | 2942 |
2943 ParallelCompactData& sd = PSParallelCompact::summary_data(); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2944 const size_t region_size = ParallelCompactData::RegionSize; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2945 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2946 size_t src_region_idx = 0; |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2947 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2948 // Skip empty regions (if any) up to the top of the space. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2949 HeapWord* const src_aligned_up = sd.region_align_up(end_addr); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2950 RegionData* src_region_ptr = sd.addr_to_region_ptr(src_aligned_up); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2951 HeapWord* const top_aligned_up = sd.region_align_up(src_space_top); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2952 const RegionData* const top_region_ptr = |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2953 sd.addr_to_region_ptr(top_aligned_up); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2954 while (src_region_ptr < top_region_ptr && src_region_ptr->data_size() == 0) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2955 ++src_region_ptr; |
0 | 2956 } |
2957 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2958 if (src_region_ptr < top_region_ptr) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2959 // The next source region is in the current space. Update src_region_idx |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2960 // and the source address to match src_region_ptr. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2961 src_region_idx = sd.region(src_region_ptr); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2962 HeapWord* const src_region_addr = sd.region_to_addr(src_region_idx); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2963 if (src_region_addr > closure.source()) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2964 closure.set_source(src_region_addr); |
0 | 2965 } |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2966 return src_region_idx; |
0 | 2967 } |
2968 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2969 // Switch to a new source space and find the first non-empty region. |
0 | 2970 unsigned int space_id = src_space_id + 1; |
2971 assert(space_id < last_space_id, "not enough spaces"); | |
2972 | |
2973 HeapWord* const destination = closure.destination(); | |
2974 | |
2975 do { | |
2976 MutableSpace* space = _space_info[space_id].space(); | |
2977 HeapWord* const bottom = space->bottom(); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2978 const RegionData* const bottom_cp = sd.addr_to_region_ptr(bottom); |
0 | 2979 |
2980 // Iterate over the spaces that do not compact into themselves. | |
2981 if (bottom_cp->destination() != bottom) { | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2982 HeapWord* const top_aligned_up = sd.region_align_up(space->top()); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2983 const RegionData* const top_cp = sd.addr_to_region_ptr(top_aligned_up); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2984 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2985 for (const RegionData* src_cp = bottom_cp; src_cp < top_cp; ++src_cp) { |
0 | 2986 if (src_cp->live_obj_size() > 0) { |
2987 // Found it. | |
2988 assert(src_cp->destination() == destination, | |
2989 "first live obj in the space must match the destination"); | |
2990 assert(src_cp->partial_obj_size() == 0, | |
2991 "a space cannot begin with a partial obj"); | |
2992 | |
2993 src_space_id = SpaceId(space_id); | |
2994 src_space_top = space->top(); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2995 const size_t src_region_idx = sd.region(src_cp); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2996 closure.set_source(sd.region_to_addr(src_region_idx)); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
2997 return src_region_idx; |
0 | 2998 } else { |
2999 assert(src_cp->data_size() == 0, "sanity"); | |
3000 } | |
3001 } | |
3002 } | |
3003 } while (++space_id < last_space_id); | |
3004 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3005 assert(false, "no source region was found"); |
0 | 3006 return 0; |
3007 } | |
3008 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3009 void PSParallelCompact::fill_region(ParCompactionManager* cm, size_t region_idx) |
0 | 3010 { |
3011 typedef ParMarkBitMap::IterationStatus IterationStatus; | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3012 const size_t RegionSize = ParallelCompactData::RegionSize; |
0 | 3013 ParMarkBitMap* const bitmap = mark_bitmap(); |
3014 ParallelCompactData& sd = summary_data(); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3015 RegionData* const region_ptr = sd.region(region_idx); |
0 | 3016 |
3017 // Get the items needed to construct the closure. | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3018 HeapWord* dest_addr = sd.region_to_addr(region_idx); |
0 | 3019 SpaceId dest_space_id = space_id(dest_addr); |
3020 ObjectStartArray* start_array = _space_info[dest_space_id].start_array(); | |
3021 HeapWord* new_top = _space_info[dest_space_id].new_top(); | |
3022 assert(dest_addr < new_top, "sanity"); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3023 const size_t words = MIN2(pointer_delta(new_top, dest_addr), RegionSize); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3024 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3025 // Get the source region and related info. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3026 size_t src_region_idx = region_ptr->source_region(); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3027 SpaceId src_space_id = space_id(sd.region_to_addr(src_region_idx)); |
0 | 3028 HeapWord* src_space_top = _space_info[src_space_id].space()->top(); |
3029 | |
3030 MoveAndUpdateClosure closure(bitmap, cm, start_array, dest_addr, words); | |
482
7c2386d67889
6765745: par compact - allow young gen spaces to be split
jcoomes
parents:
481
diff
changeset
|
3031 closure.set_source(first_src_addr(dest_addr, src_space_id, src_region_idx)); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3032 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3033 // Adjust src_region_idx to prepare for decrementing destination counts (the |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3034 // destination count is not decremented when a region is copied to itself). |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3035 if (src_region_idx == region_idx) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3036 src_region_idx += 1; |
0 | 3037 } |
3038 | |
3039 if (bitmap->is_unmarked(closure.source())) { | |
3040 // The first source word is in the middle of an object; copy the remainder | |
3041 // of the object or as much as will fit. The fact that pointer updates were | |
3042 // deferred will be noted when the object header is processed. | |
3043 HeapWord* const old_src_addr = closure.source(); | |
3044 closure.copy_partial_obj(); | |
3045 if (closure.is_full()) { | |
495
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
3046 decrement_destination_counts(cm, src_space_id, src_region_idx, |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
3047 closure.source()); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3048 region_ptr->set_deferred_obj_addr(NULL); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3049 region_ptr->set_completed(); |
0 | 3050 return; |
3051 } | |
3052 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3053 HeapWord* const end_addr = sd.region_align_down(closure.source()); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3054 if (sd.region_align_down(old_src_addr) != end_addr) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3055 // The partial object was copied from more than one source region. |
495
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
3056 decrement_destination_counts(cm, src_space_id, src_region_idx, end_addr); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3057 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3058 // Move to the next source region, possibly switching spaces as well. All |
0 | 3059 // args except end_addr may be modified. |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3060 src_region_idx = next_src_region(closure, src_space_id, src_space_top, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3061 end_addr); |
0 | 3062 } |
3063 } | |
3064 | |
3065 do { | |
3066 HeapWord* const cur_addr = closure.source(); | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3067 HeapWord* const end_addr = MIN2(sd.region_align_up(cur_addr + 1), |
0 | 3068 src_space_top); |
3069 IterationStatus status = bitmap->iterate(&closure, cur_addr, end_addr); | |
3070 | |
3071 if (status == ParMarkBitMap::incomplete) { | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3072 // The last obj that starts in the source region does not end in the |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3073 // region. |
1489
cff162798819
6888953: some calls to function-like macros are missing semicolons
jcoomes
parents:
1387
diff
changeset
|
3074 assert(closure.source() < end_addr, "sanity"); |
0 | 3075 HeapWord* const obj_beg = closure.source(); |
3076 HeapWord* const range_end = MIN2(obj_beg + closure.words_remaining(), | |
3077 src_space_top); | |
3078 HeapWord* const obj_end = bitmap->find_obj_end(obj_beg, range_end); | |
3079 if (obj_end < range_end) { | |
3080 // The end was found; the entire object will fit. | |
3081 status = closure.do_addr(obj_beg, bitmap->obj_size(obj_beg, obj_end)); | |
3082 assert(status != ParMarkBitMap::would_overflow, "sanity"); | |
3083 } else { | |
3084 // The end was not found; the object will not fit. | |
3085 assert(range_end < src_space_top, "obj cannot cross space boundary"); | |
3086 status = ParMarkBitMap::would_overflow; | |
3087 } | |
3088 } | |
3089 | |
3090 if (status == ParMarkBitMap::would_overflow) { | |
3091 // The last object did not fit. Note that interior oop updates were | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3092 // deferred, then copy enough of the object to fill the region. |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3093 region_ptr->set_deferred_obj_addr(closure.destination()); |
0 | 3094 status = closure.copy_until_full(); // copies from closure.source() |
3095 | |
495
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
3096 decrement_destination_counts(cm, src_space_id, src_region_idx, |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
3097 closure.source()); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3098 region_ptr->set_completed(); |
0 | 3099 return; |
3100 } | |
3101 | |
3102 if (status == ParMarkBitMap::full) { | |
495
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
3103 decrement_destination_counts(cm, src_space_id, src_region_idx, |
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
3104 closure.source()); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3105 region_ptr->set_deferred_obj_addr(NULL); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3106 region_ptr->set_completed(); |
0 | 3107 return; |
3108 } | |
3109 | |
495
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
3110 decrement_destination_counts(cm, src_space_id, src_region_idx, end_addr); |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3111 |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3112 // Move to the next source region, possibly switching spaces as well. All |
0 | 3113 // args except end_addr may be modified. |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3114 src_region_idx = next_src_region(closure, src_space_id, src_space_top, |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3115 end_addr); |
0 | 3116 } while (true); |
3117 } | |
3118 | |
3119 void | |
3120 PSParallelCompact::move_and_update(ParCompactionManager* cm, SpaceId space_id) { | |
3121 const MutableSpace* sp = space(space_id); | |
3122 if (sp->is_empty()) { | |
3123 return; | |
3124 } | |
3125 | |
3126 ParallelCompactData& sd = PSParallelCompact::summary_data(); | |
3127 ParMarkBitMap* const bitmap = mark_bitmap(); | |
3128 HeapWord* const dp_addr = dense_prefix(space_id); | |
3129 HeapWord* beg_addr = sp->bottom(); | |
3130 HeapWord* end_addr = sp->top(); | |
3131 | |
3132 assert(beg_addr <= dp_addr && dp_addr <= end_addr, "bad dense prefix"); | |
3133 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3134 const size_t beg_region = sd.addr_to_region_idx(beg_addr); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3135 const size_t dp_region = sd.addr_to_region_idx(dp_addr); |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3136 if (beg_region < dp_region) { |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3137 update_and_deadwood_in_dense_prefix(cm, space_id, beg_region, dp_region); |
0 | 3138 } |
3139 | |
375
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3140 // The destination of the first live object that starts in the region is one |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3141 // past the end of the partial object entering the region (if any). |
81cd571500b0
6725697: par compact - rename class ChunkData to RegionData
jcoomes
parents:
374
diff
changeset
|
3142 HeapWord* const dest_addr = sd.partial_obj_end(dp_region); |
0 | 3143 HeapWord* const new_top = _space_info[space_id].new_top(); |
3144 assert(new_top >= dest_addr, "bad new_top value"); | |
3145 const size_t words = pointer_delta(new_top, dest_addr); | |
3146 | |
3147 if (words > 0) { | |
3148 ObjectStartArray* start_array = _space_info[space_id].start_array(); | |
3149 MoveAndUpdateClosure closure(bitmap, cm, start_array, dest_addr, words); | |
3150 | |
3151 ParMarkBitMap::IterationStatus status; | |
3152 status = bitmap->iterate(&closure, dest_addr, end_addr); | |
3153 assert(status == ParMarkBitMap::full, "iteration not complete"); | |
3154 assert(bitmap->find_obj_beg(closure.source(), end_addr) == end_addr, | |
3155 "live objects skipped because closure is full"); | |
3156 } | |
3157 } | |
3158 | |
3159 jlong PSParallelCompact::millis_since_last_gc() { | |
4712
e7dead7e90af
7117303: VM uses non-monotonic time source and complains that it is non-monotonic
johnc
parents:
4099
diff
changeset
|
3160 // We need a monotonically non-deccreasing time in ms but |
e7dead7e90af
7117303: VM uses non-monotonic time source and complains that it is non-monotonic
johnc
parents:
4099
diff
changeset
|
3161 // os::javaTimeMillis() does not guarantee monotonicity. |
e7dead7e90af
7117303: VM uses non-monotonic time source and complains that it is non-monotonic
johnc
parents:
4099
diff
changeset
|
3162 jlong now = os::javaTimeNanos() / NANOSECS_PER_MILLISEC; |
e7dead7e90af
7117303: VM uses non-monotonic time source and complains that it is non-monotonic
johnc
parents:
4099
diff
changeset
|
3163 jlong ret_val = now - _time_of_last_gc; |
0 | 3164 // XXX See note in genCollectedHeap::millis_since_last_gc(). |
3165 if (ret_val < 0) { | |
4712
e7dead7e90af
7117303: VM uses non-monotonic time source and complains that it is non-monotonic
johnc
parents:
4099
diff
changeset
|
3166 NOT_PRODUCT(warning("time warp: "INT64_FORMAT, ret_val);) |
0 | 3167 return 0; |
3168 } | |
3169 return ret_val; | |
3170 } | |
3171 | |
3172 void PSParallelCompact::reset_millis_since_last_gc() { | |
4712
e7dead7e90af
7117303: VM uses non-monotonic time source and complains that it is non-monotonic
johnc
parents:
4099
diff
changeset
|
3173 // We need a monotonically non-deccreasing time in ms but |
e7dead7e90af
7117303: VM uses non-monotonic time source and complains that it is non-monotonic
johnc
parents:
4099
diff
changeset
|
3174 // os::javaTimeMillis() does not guarantee monotonicity. |
e7dead7e90af
7117303: VM uses non-monotonic time source and complains that it is non-monotonic
johnc
parents:
4099
diff
changeset
|
3175 _time_of_last_gc = os::javaTimeNanos() / NANOSECS_PER_MILLISEC; |
0 | 3176 } |
3177 | |
3178 ParMarkBitMap::IterationStatus MoveAndUpdateClosure::copy_until_full() | |
3179 { | |
3180 if (source() != destination()) { | |
495
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
3181 DEBUG_ONLY(PSParallelCompact::check_new_location(source(), destination());) |
0 | 3182 Copy::aligned_conjoint_words(source(), destination(), words_remaining()); |
3183 } | |
3184 update_state(words_remaining()); | |
3185 assert(is_full(), "sanity"); | |
3186 return ParMarkBitMap::full; | |
3187 } | |
3188 | |
3189 void MoveAndUpdateClosure::copy_partial_obj() | |
3190 { | |
3191 size_t words = words_remaining(); | |
3192 | |
3193 HeapWord* const range_end = MIN2(source() + words, bitmap()->region_end()); | |
3194 HeapWord* const end_addr = bitmap()->find_obj_end(source(), range_end); | |
3195 if (end_addr < range_end) { | |
3196 words = bitmap()->obj_size(source(), end_addr); | |
3197 } | |
3198 | |
3199 // This test is necessary; if omitted, the pointer updates to a partial object | |
3200 // that crosses the dense prefix boundary could be overwritten. | |
3201 if (source() != destination()) { | |
495
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
3202 DEBUG_ONLY(PSParallelCompact::check_new_location(source(), destination());) |
0 | 3203 Copy::aligned_conjoint_words(source(), destination(), words); |
3204 } | |
3205 update_state(words); | |
3206 } | |
3207 | |
3208 ParMarkBitMapClosure::IterationStatus | |
3209 MoveAndUpdateClosure::do_addr(HeapWord* addr, size_t words) { | |
3210 assert(destination() != NULL, "sanity"); | |
3211 assert(bitmap()->obj_size(addr) == words, "bad size"); | |
3212 | |
3213 _source = addr; | |
3214 assert(PSParallelCompact::summary_data().calc_new_pointer(source()) == | |
3215 destination(), "wrong destination"); | |
3216 | |
3217 if (words > words_remaining()) { | |
3218 return ParMarkBitMap::would_overflow; | |
3219 } | |
3220 | |
3221 // The start_array must be updated even if the object is not moving. | |
3222 if (_start_array != NULL) { | |
3223 _start_array->allocate_block(destination()); | |
3224 } | |
3225 | |
3226 if (destination() != source()) { | |
495
234c22e54b98
6784849: par compact - can fail when to_space is non-empty
jcoomes
parents:
483
diff
changeset
|
3227 DEBUG_ONLY(PSParallelCompact::check_new_location(source(), destination());) |
0 | 3228 Copy::aligned_conjoint_words(source(), destination(), words); |
3229 } | |
3230 | |
3231 oop moved_oop = (oop) destination(); | |
3232 moved_oop->update_contents(compaction_manager()); | |
3233 assert(moved_oop->is_oop_or_null(), "Object should be whole at this point"); | |
3234 | |
3235 update_state(words); | |
3236 assert(destination() == (HeapWord*)moved_oop + moved_oop->size(), "sanity"); | |
3237 return is_full() ? ParMarkBitMap::full : ParMarkBitMap::incomplete; | |
3238 } | |
3239 | |
3240 UpdateOnlyClosure::UpdateOnlyClosure(ParMarkBitMap* mbm, | |
3241 ParCompactionManager* cm, | |
3242 PSParallelCompact::SpaceId space_id) : | |
3243 ParMarkBitMapClosure(mbm, cm), | |
3244 _space_id(space_id), | |
3245 _start_array(PSParallelCompact::start_array(space_id)) | |
3246 { | |
3247 } | |
3248 | |
3249 // Updates the references in the object to their new values. | |
3250 ParMarkBitMapClosure::IterationStatus | |
3251 UpdateOnlyClosure::do_addr(HeapWord* addr, size_t words) { | |
3252 do_addr(addr); | |
3253 return ParMarkBitMap::incomplete; | |
3254 } |