annotate src/share/vm/memory/generation.cpp @ 453:c96030fff130

6684579: SoftReference processing can be made more efficient Summary: For current soft-ref clearing policies, we can decide at marking time if a soft-reference will definitely not be cleared, postponing the decision of whether it will definitely be cleared to the final reference processing phase. This can be especially beneficial in the case of concurrent collectors where the marking is usually concurrent but reference processing is usually not. Reviewed-by: jmasa
author ysr
date Thu, 20 Nov 2008 16:56:09 -0800
parents 818a18cd69a8
children e9be0e04635a
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
0
a61af66fc99e Initial load
duke
parents:
diff changeset
1 /*
196
d1605aabd0a1 6719955: Update copyright year
xdono
parents: 113
diff changeset
2 * Copyright 1997-2008 Sun Microsystems, Inc. All Rights Reserved.
0
a61af66fc99e Initial load
duke
parents:
diff changeset
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
a61af66fc99e Initial load
duke
parents:
diff changeset
4 *
a61af66fc99e Initial load
duke
parents:
diff changeset
5 * This code is free software; you can redistribute it and/or modify it
a61af66fc99e Initial load
duke
parents:
diff changeset
6 * under the terms of the GNU General Public License version 2 only, as
a61af66fc99e Initial load
duke
parents:
diff changeset
7 * published by the Free Software Foundation.
a61af66fc99e Initial load
duke
parents:
diff changeset
8 *
a61af66fc99e Initial load
duke
parents:
diff changeset
9 * This code is distributed in the hope that it will be useful, but WITHOUT
a61af66fc99e Initial load
duke
parents:
diff changeset
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
a61af66fc99e Initial load
duke
parents:
diff changeset
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
a61af66fc99e Initial load
duke
parents:
diff changeset
12 * version 2 for more details (a copy is included in the LICENSE file that
a61af66fc99e Initial load
duke
parents:
diff changeset
13 * accompanied this code).
a61af66fc99e Initial load
duke
parents:
diff changeset
14 *
a61af66fc99e Initial load
duke
parents:
diff changeset
15 * You should have received a copy of the GNU General Public License version
a61af66fc99e Initial load
duke
parents:
diff changeset
16 * 2 along with this work; if not, write to the Free Software Foundation,
a61af66fc99e Initial load
duke
parents:
diff changeset
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
a61af66fc99e Initial load
duke
parents:
diff changeset
18 *
a61af66fc99e Initial load
duke
parents:
diff changeset
19 * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
a61af66fc99e Initial load
duke
parents:
diff changeset
20 * CA 95054 USA or visit www.sun.com if you need additional information or
a61af66fc99e Initial load
duke
parents:
diff changeset
21 * have any questions.
a61af66fc99e Initial load
duke
parents:
diff changeset
22 *
a61af66fc99e Initial load
duke
parents:
diff changeset
23 */
a61af66fc99e Initial load
duke
parents:
diff changeset
24
a61af66fc99e Initial load
duke
parents:
diff changeset
25 # include "incls/_precompiled.incl"
a61af66fc99e Initial load
duke
parents:
diff changeset
26 # include "incls/_generation.cpp.incl"
a61af66fc99e Initial load
duke
parents:
diff changeset
27
a61af66fc99e Initial load
duke
parents:
diff changeset
28 Generation::Generation(ReservedSpace rs, size_t initial_size, int level) :
a61af66fc99e Initial load
duke
parents:
diff changeset
29 _level(level),
a61af66fc99e Initial load
duke
parents:
diff changeset
30 _ref_processor(NULL) {
a61af66fc99e Initial load
duke
parents:
diff changeset
31 if (!_virtual_space.initialize(rs, initial_size)) {
a61af66fc99e Initial load
duke
parents:
diff changeset
32 vm_exit_during_initialization("Could not reserve enough space for "
a61af66fc99e Initial load
duke
parents:
diff changeset
33 "object heap");
a61af66fc99e Initial load
duke
parents:
diff changeset
34 }
263
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
35 // Mangle all of the the initial generation.
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
36 if (ZapUnusedHeapArea) {
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
37 MemRegion mangle_region((HeapWord*)_virtual_space.low(),
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
38 (HeapWord*)_virtual_space.high());
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
39 SpaceMangler::mangle_region(mangle_region);
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
40 }
0
a61af66fc99e Initial load
duke
parents:
diff changeset
41 _reserved = MemRegion((HeapWord*)_virtual_space.low_boundary(),
a61af66fc99e Initial load
duke
parents:
diff changeset
42 (HeapWord*)_virtual_space.high_boundary());
a61af66fc99e Initial load
duke
parents:
diff changeset
43 }
a61af66fc99e Initial load
duke
parents:
diff changeset
44
a61af66fc99e Initial load
duke
parents:
diff changeset
45 GenerationSpec* Generation::spec() {
a61af66fc99e Initial load
duke
parents:
diff changeset
46 GenCollectedHeap* gch = GenCollectedHeap::heap();
a61af66fc99e Initial load
duke
parents:
diff changeset
47 assert(0 <= level() && level() < gch->_n_gens, "Bad gen level");
a61af66fc99e Initial load
duke
parents:
diff changeset
48 return gch->_gen_specs[level()];
a61af66fc99e Initial load
duke
parents:
diff changeset
49 }
a61af66fc99e Initial load
duke
parents:
diff changeset
50
a61af66fc99e Initial load
duke
parents:
diff changeset
51 size_t Generation::max_capacity() const {
a61af66fc99e Initial load
duke
parents:
diff changeset
52 return reserved().byte_size();
a61af66fc99e Initial load
duke
parents:
diff changeset
53 }
a61af66fc99e Initial load
duke
parents:
diff changeset
54
a61af66fc99e Initial load
duke
parents:
diff changeset
55 void Generation::print_heap_change(size_t prev_used) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
56 if (PrintGCDetails && Verbose) {
a61af66fc99e Initial load
duke
parents:
diff changeset
57 gclog_or_tty->print(" " SIZE_FORMAT
a61af66fc99e Initial load
duke
parents:
diff changeset
58 "->" SIZE_FORMAT
a61af66fc99e Initial load
duke
parents:
diff changeset
59 "(" SIZE_FORMAT ")",
a61af66fc99e Initial load
duke
parents:
diff changeset
60 prev_used, used(), capacity());
a61af66fc99e Initial load
duke
parents:
diff changeset
61 } else {
a61af66fc99e Initial load
duke
parents:
diff changeset
62 gclog_or_tty->print(" " SIZE_FORMAT "K"
a61af66fc99e Initial load
duke
parents:
diff changeset
63 "->" SIZE_FORMAT "K"
a61af66fc99e Initial load
duke
parents:
diff changeset
64 "(" SIZE_FORMAT "K)",
a61af66fc99e Initial load
duke
parents:
diff changeset
65 prev_used / K, used() / K, capacity() / K);
a61af66fc99e Initial load
duke
parents:
diff changeset
66 }
a61af66fc99e Initial load
duke
parents:
diff changeset
67 }
a61af66fc99e Initial load
duke
parents:
diff changeset
68
a61af66fc99e Initial load
duke
parents:
diff changeset
69 // By default we get a single threaded default reference processor;
a61af66fc99e Initial load
duke
parents:
diff changeset
70 // generations needing multi-threaded refs discovery override this method.
a61af66fc99e Initial load
duke
parents:
diff changeset
71 void Generation::ref_processor_init() {
a61af66fc99e Initial load
duke
parents:
diff changeset
72 assert(_ref_processor == NULL, "a reference processor already exists");
a61af66fc99e Initial load
duke
parents:
diff changeset
73 assert(!_reserved.is_empty(), "empty generation?");
a61af66fc99e Initial load
duke
parents:
diff changeset
74 _ref_processor =
a61af66fc99e Initial load
duke
parents:
diff changeset
75 new ReferenceProcessor(_reserved, // span
a61af66fc99e Initial load
duke
parents:
diff changeset
76 refs_discovery_is_atomic(), // atomic_discovery
a61af66fc99e Initial load
duke
parents:
diff changeset
77 refs_discovery_is_mt()); // mt_discovery
a61af66fc99e Initial load
duke
parents:
diff changeset
78 if (_ref_processor == NULL) {
a61af66fc99e Initial load
duke
parents:
diff changeset
79 vm_exit_during_initialization("Could not allocate ReferenceProcessor object");
a61af66fc99e Initial load
duke
parents:
diff changeset
80 }
a61af66fc99e Initial load
duke
parents:
diff changeset
81 }
a61af66fc99e Initial load
duke
parents:
diff changeset
82
a61af66fc99e Initial load
duke
parents:
diff changeset
83 void Generation::print() const { print_on(tty); }
a61af66fc99e Initial load
duke
parents:
diff changeset
84
a61af66fc99e Initial load
duke
parents:
diff changeset
85 void Generation::print_on(outputStream* st) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
86 st->print(" %-20s", name());
a61af66fc99e Initial load
duke
parents:
diff changeset
87 st->print(" total " SIZE_FORMAT "K, used " SIZE_FORMAT "K",
a61af66fc99e Initial load
duke
parents:
diff changeset
88 capacity()/K, used()/K);
a61af66fc99e Initial load
duke
parents:
diff changeset
89 st->print_cr(" [" INTPTR_FORMAT ", " INTPTR_FORMAT ", " INTPTR_FORMAT ")",
a61af66fc99e Initial load
duke
parents:
diff changeset
90 _virtual_space.low_boundary(),
a61af66fc99e Initial load
duke
parents:
diff changeset
91 _virtual_space.high(),
a61af66fc99e Initial load
duke
parents:
diff changeset
92 _virtual_space.high_boundary());
a61af66fc99e Initial load
duke
parents:
diff changeset
93 }
a61af66fc99e Initial load
duke
parents:
diff changeset
94
a61af66fc99e Initial load
duke
parents:
diff changeset
95 void Generation::print_summary_info() { print_summary_info_on(tty); }
a61af66fc99e Initial load
duke
parents:
diff changeset
96
a61af66fc99e Initial load
duke
parents:
diff changeset
97 void Generation::print_summary_info_on(outputStream* st) {
a61af66fc99e Initial load
duke
parents:
diff changeset
98 StatRecord* sr = stat_record();
a61af66fc99e Initial load
duke
parents:
diff changeset
99 double time = sr->accumulated_time.seconds();
a61af66fc99e Initial load
duke
parents:
diff changeset
100 st->print_cr("[Accumulated GC generation %d time %3.7f secs, "
a61af66fc99e Initial load
duke
parents:
diff changeset
101 "%d GC's, avg GC time %3.7f]",
a61af66fc99e Initial load
duke
parents:
diff changeset
102 level(), time, sr->invocations,
a61af66fc99e Initial load
duke
parents:
diff changeset
103 sr->invocations > 0 ? time / sr->invocations : 0.0);
a61af66fc99e Initial load
duke
parents:
diff changeset
104 }
a61af66fc99e Initial load
duke
parents:
diff changeset
105
a61af66fc99e Initial load
duke
parents:
diff changeset
106 // Utility iterator classes
a61af66fc99e Initial load
duke
parents:
diff changeset
107
a61af66fc99e Initial load
duke
parents:
diff changeset
108 class GenerationIsInReservedClosure : public SpaceClosure {
a61af66fc99e Initial load
duke
parents:
diff changeset
109 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
110 const void* _p;
a61af66fc99e Initial load
duke
parents:
diff changeset
111 Space* sp;
a61af66fc99e Initial load
duke
parents:
diff changeset
112 virtual void do_space(Space* s) {
a61af66fc99e Initial load
duke
parents:
diff changeset
113 if (sp == NULL) {
a61af66fc99e Initial load
duke
parents:
diff changeset
114 if (s->is_in_reserved(_p)) sp = s;
a61af66fc99e Initial load
duke
parents:
diff changeset
115 }
a61af66fc99e Initial load
duke
parents:
diff changeset
116 }
a61af66fc99e Initial load
duke
parents:
diff changeset
117 GenerationIsInReservedClosure(const void* p) : _p(p), sp(NULL) {}
a61af66fc99e Initial load
duke
parents:
diff changeset
118 };
a61af66fc99e Initial load
duke
parents:
diff changeset
119
a61af66fc99e Initial load
duke
parents:
diff changeset
120 class GenerationIsInClosure : public SpaceClosure {
a61af66fc99e Initial load
duke
parents:
diff changeset
121 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
122 const void* _p;
a61af66fc99e Initial load
duke
parents:
diff changeset
123 Space* sp;
a61af66fc99e Initial load
duke
parents:
diff changeset
124 virtual void do_space(Space* s) {
a61af66fc99e Initial load
duke
parents:
diff changeset
125 if (sp == NULL) {
a61af66fc99e Initial load
duke
parents:
diff changeset
126 if (s->is_in(_p)) sp = s;
a61af66fc99e Initial load
duke
parents:
diff changeset
127 }
a61af66fc99e Initial load
duke
parents:
diff changeset
128 }
a61af66fc99e Initial load
duke
parents:
diff changeset
129 GenerationIsInClosure(const void* p) : _p(p), sp(NULL) {}
a61af66fc99e Initial load
duke
parents:
diff changeset
130 };
a61af66fc99e Initial load
duke
parents:
diff changeset
131
a61af66fc99e Initial load
duke
parents:
diff changeset
132 bool Generation::is_in(const void* p) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
133 GenerationIsInClosure blk(p);
a61af66fc99e Initial load
duke
parents:
diff changeset
134 ((Generation*)this)->space_iterate(&blk);
a61af66fc99e Initial load
duke
parents:
diff changeset
135 return blk.sp != NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
136 }
a61af66fc99e Initial load
duke
parents:
diff changeset
137
a61af66fc99e Initial load
duke
parents:
diff changeset
138 DefNewGeneration* Generation::as_DefNewGeneration() {
a61af66fc99e Initial load
duke
parents:
diff changeset
139 assert((kind() == Generation::DefNew) ||
a61af66fc99e Initial load
duke
parents:
diff changeset
140 (kind() == Generation::ParNew) ||
a61af66fc99e Initial load
duke
parents:
diff changeset
141 (kind() == Generation::ASParNew),
a61af66fc99e Initial load
duke
parents:
diff changeset
142 "Wrong youngest generation type");
a61af66fc99e Initial load
duke
parents:
diff changeset
143 return (DefNewGeneration*) this;
a61af66fc99e Initial load
duke
parents:
diff changeset
144 }
a61af66fc99e Initial load
duke
parents:
diff changeset
145
a61af66fc99e Initial load
duke
parents:
diff changeset
146 Generation* Generation::next_gen() const {
a61af66fc99e Initial load
duke
parents:
diff changeset
147 GenCollectedHeap* gch = GenCollectedHeap::heap();
a61af66fc99e Initial load
duke
parents:
diff changeset
148 int next = level() + 1;
a61af66fc99e Initial load
duke
parents:
diff changeset
149 if (next < gch->_n_gens) {
a61af66fc99e Initial load
duke
parents:
diff changeset
150 return gch->_gens[next];
a61af66fc99e Initial load
duke
parents:
diff changeset
151 } else {
a61af66fc99e Initial load
duke
parents:
diff changeset
152 return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
153 }
a61af66fc99e Initial load
duke
parents:
diff changeset
154 }
a61af66fc99e Initial load
duke
parents:
diff changeset
155
a61af66fc99e Initial load
duke
parents:
diff changeset
156 size_t Generation::max_contiguous_available() const {
a61af66fc99e Initial load
duke
parents:
diff changeset
157 // The largest number of contiguous free words in this or any higher generation.
a61af66fc99e Initial load
duke
parents:
diff changeset
158 size_t max = 0;
a61af66fc99e Initial load
duke
parents:
diff changeset
159 for (const Generation* gen = this; gen != NULL; gen = gen->next_gen()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
160 size_t avail = gen->contiguous_available();
a61af66fc99e Initial load
duke
parents:
diff changeset
161 if (avail > max) {
a61af66fc99e Initial load
duke
parents:
diff changeset
162 max = avail;
a61af66fc99e Initial load
duke
parents:
diff changeset
163 }
a61af66fc99e Initial load
duke
parents:
diff changeset
164 }
a61af66fc99e Initial load
duke
parents:
diff changeset
165 return max;
a61af66fc99e Initial load
duke
parents:
diff changeset
166 }
a61af66fc99e Initial load
duke
parents:
diff changeset
167
a61af66fc99e Initial load
duke
parents:
diff changeset
168 bool Generation::promotion_attempt_is_safe(size_t promotion_in_bytes,
a61af66fc99e Initial load
duke
parents:
diff changeset
169 bool not_used) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
170 if (PrintGC && Verbose) {
a61af66fc99e Initial load
duke
parents:
diff changeset
171 gclog_or_tty->print_cr("Generation::promotion_attempt_is_safe"
a61af66fc99e Initial load
duke
parents:
diff changeset
172 " contiguous_available: " SIZE_FORMAT
a61af66fc99e Initial load
duke
parents:
diff changeset
173 " promotion_in_bytes: " SIZE_FORMAT,
a61af66fc99e Initial load
duke
parents:
diff changeset
174 max_contiguous_available(), promotion_in_bytes);
a61af66fc99e Initial load
duke
parents:
diff changeset
175 }
a61af66fc99e Initial load
duke
parents:
diff changeset
176 return max_contiguous_available() >= promotion_in_bytes;
a61af66fc99e Initial load
duke
parents:
diff changeset
177 }
a61af66fc99e Initial load
duke
parents:
diff changeset
178
a61af66fc99e Initial load
duke
parents:
diff changeset
179 // Ignores "ref" and calls allocate().
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
180 oop Generation::promote(oop obj, size_t obj_size) {
0
a61af66fc99e Initial load
duke
parents:
diff changeset
181 assert(obj_size == (size_t)obj->size(), "bad obj_size passed in");
a61af66fc99e Initial load
duke
parents:
diff changeset
182
a61af66fc99e Initial load
duke
parents:
diff changeset
183 #ifndef PRODUCT
a61af66fc99e Initial load
duke
parents:
diff changeset
184 if (Universe::heap()->promotion_should_fail()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
185 return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
186 }
a61af66fc99e Initial load
duke
parents:
diff changeset
187 #endif // #ifndef PRODUCT
a61af66fc99e Initial load
duke
parents:
diff changeset
188
a61af66fc99e Initial load
duke
parents:
diff changeset
189 HeapWord* result = allocate(obj_size, false);
a61af66fc99e Initial load
duke
parents:
diff changeset
190 if (result != NULL) {
a61af66fc99e Initial load
duke
parents:
diff changeset
191 Copy::aligned_disjoint_words((HeapWord*)obj, result, obj_size);
a61af66fc99e Initial load
duke
parents:
diff changeset
192 return oop(result);
a61af66fc99e Initial load
duke
parents:
diff changeset
193 } else {
a61af66fc99e Initial load
duke
parents:
diff changeset
194 GenCollectedHeap* gch = GenCollectedHeap::heap();
113
ba764ed4b6f2 6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents: 0
diff changeset
195 return gch->handle_failed_promotion(this, obj, obj_size);
0
a61af66fc99e Initial load
duke
parents:
diff changeset
196 }
a61af66fc99e Initial load
duke
parents:
diff changeset
197 }
a61af66fc99e Initial load
duke
parents:
diff changeset
198
a61af66fc99e Initial load
duke
parents:
diff changeset
199 oop Generation::par_promote(int thread_num,
a61af66fc99e Initial load
duke
parents:
diff changeset
200 oop obj, markOop m, size_t word_sz) {
a61af66fc99e Initial load
duke
parents:
diff changeset
201 // Could do a bad general impl here that gets a lock. But no.
a61af66fc99e Initial load
duke
parents:
diff changeset
202 ShouldNotCallThis();
a61af66fc99e Initial load
duke
parents:
diff changeset
203 return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
204 }
a61af66fc99e Initial load
duke
parents:
diff changeset
205
a61af66fc99e Initial load
duke
parents:
diff changeset
206 void Generation::par_promote_alloc_undo(int thread_num,
a61af66fc99e Initial load
duke
parents:
diff changeset
207 HeapWord* obj, size_t word_sz) {
a61af66fc99e Initial load
duke
parents:
diff changeset
208 // Could do a bad general impl here that gets a lock. But no.
a61af66fc99e Initial load
duke
parents:
diff changeset
209 guarantee(false, "No good general implementation.");
a61af66fc99e Initial load
duke
parents:
diff changeset
210 }
a61af66fc99e Initial load
duke
parents:
diff changeset
211
a61af66fc99e Initial load
duke
parents:
diff changeset
212 Space* Generation::space_containing(const void* p) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
213 GenerationIsInReservedClosure blk(p);
a61af66fc99e Initial load
duke
parents:
diff changeset
214 // Cast away const
a61af66fc99e Initial load
duke
parents:
diff changeset
215 ((Generation*)this)->space_iterate(&blk);
a61af66fc99e Initial load
duke
parents:
diff changeset
216 return blk.sp;
a61af66fc99e Initial load
duke
parents:
diff changeset
217 }
a61af66fc99e Initial load
duke
parents:
diff changeset
218
a61af66fc99e Initial load
duke
parents:
diff changeset
219 // Some of these are mediocre general implementations. Should be
a61af66fc99e Initial load
duke
parents:
diff changeset
220 // overridden to get better performance.
a61af66fc99e Initial load
duke
parents:
diff changeset
221
a61af66fc99e Initial load
duke
parents:
diff changeset
222 class GenerationBlockStartClosure : public SpaceClosure {
a61af66fc99e Initial load
duke
parents:
diff changeset
223 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
224 const void* _p;
a61af66fc99e Initial load
duke
parents:
diff changeset
225 HeapWord* _start;
a61af66fc99e Initial load
duke
parents:
diff changeset
226 virtual void do_space(Space* s) {
a61af66fc99e Initial load
duke
parents:
diff changeset
227 if (_start == NULL && s->is_in_reserved(_p)) {
a61af66fc99e Initial load
duke
parents:
diff changeset
228 _start = s->block_start(_p);
a61af66fc99e Initial load
duke
parents:
diff changeset
229 }
a61af66fc99e Initial load
duke
parents:
diff changeset
230 }
a61af66fc99e Initial load
duke
parents:
diff changeset
231 GenerationBlockStartClosure(const void* p) { _p = p; _start = NULL; }
a61af66fc99e Initial load
duke
parents:
diff changeset
232 };
a61af66fc99e Initial load
duke
parents:
diff changeset
233
a61af66fc99e Initial load
duke
parents:
diff changeset
234 HeapWord* Generation::block_start(const void* p) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
235 GenerationBlockStartClosure blk(p);
a61af66fc99e Initial load
duke
parents:
diff changeset
236 // Cast away const
a61af66fc99e Initial load
duke
parents:
diff changeset
237 ((Generation*)this)->space_iterate(&blk);
a61af66fc99e Initial load
duke
parents:
diff changeset
238 return blk._start;
a61af66fc99e Initial load
duke
parents:
diff changeset
239 }
a61af66fc99e Initial load
duke
parents:
diff changeset
240
a61af66fc99e Initial load
duke
parents:
diff changeset
241 class GenerationBlockSizeClosure : public SpaceClosure {
a61af66fc99e Initial load
duke
parents:
diff changeset
242 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
243 const HeapWord* _p;
a61af66fc99e Initial load
duke
parents:
diff changeset
244 size_t size;
a61af66fc99e Initial load
duke
parents:
diff changeset
245 virtual void do_space(Space* s) {
a61af66fc99e Initial load
duke
parents:
diff changeset
246 if (size == 0 && s->is_in_reserved(_p)) {
a61af66fc99e Initial load
duke
parents:
diff changeset
247 size = s->block_size(_p);
a61af66fc99e Initial load
duke
parents:
diff changeset
248 }
a61af66fc99e Initial load
duke
parents:
diff changeset
249 }
a61af66fc99e Initial load
duke
parents:
diff changeset
250 GenerationBlockSizeClosure(const HeapWord* p) { _p = p; size = 0; }
a61af66fc99e Initial load
duke
parents:
diff changeset
251 };
a61af66fc99e Initial load
duke
parents:
diff changeset
252
a61af66fc99e Initial load
duke
parents:
diff changeset
253 size_t Generation::block_size(const HeapWord* p) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
254 GenerationBlockSizeClosure blk(p);
a61af66fc99e Initial load
duke
parents:
diff changeset
255 // Cast away const
a61af66fc99e Initial load
duke
parents:
diff changeset
256 ((Generation*)this)->space_iterate(&blk);
a61af66fc99e Initial load
duke
parents:
diff changeset
257 assert(blk.size > 0, "seems reasonable");
a61af66fc99e Initial load
duke
parents:
diff changeset
258 return blk.size;
a61af66fc99e Initial load
duke
parents:
diff changeset
259 }
a61af66fc99e Initial load
duke
parents:
diff changeset
260
a61af66fc99e Initial load
duke
parents:
diff changeset
261 class GenerationBlockIsObjClosure : public SpaceClosure {
a61af66fc99e Initial load
duke
parents:
diff changeset
262 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
263 const HeapWord* _p;
a61af66fc99e Initial load
duke
parents:
diff changeset
264 bool is_obj;
a61af66fc99e Initial load
duke
parents:
diff changeset
265 virtual void do_space(Space* s) {
a61af66fc99e Initial load
duke
parents:
diff changeset
266 if (!is_obj && s->is_in_reserved(_p)) {
a61af66fc99e Initial load
duke
parents:
diff changeset
267 is_obj |= s->block_is_obj(_p);
a61af66fc99e Initial load
duke
parents:
diff changeset
268 }
a61af66fc99e Initial load
duke
parents:
diff changeset
269 }
a61af66fc99e Initial load
duke
parents:
diff changeset
270 GenerationBlockIsObjClosure(const HeapWord* p) { _p = p; is_obj = false; }
a61af66fc99e Initial load
duke
parents:
diff changeset
271 };
a61af66fc99e Initial load
duke
parents:
diff changeset
272
a61af66fc99e Initial load
duke
parents:
diff changeset
273 bool Generation::block_is_obj(const HeapWord* p) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
274 GenerationBlockIsObjClosure blk(p);
a61af66fc99e Initial load
duke
parents:
diff changeset
275 // Cast away const
a61af66fc99e Initial load
duke
parents:
diff changeset
276 ((Generation*)this)->space_iterate(&blk);
a61af66fc99e Initial load
duke
parents:
diff changeset
277 return blk.is_obj;
a61af66fc99e Initial load
duke
parents:
diff changeset
278 }
a61af66fc99e Initial load
duke
parents:
diff changeset
279
a61af66fc99e Initial load
duke
parents:
diff changeset
280 class GenerationOopIterateClosure : public SpaceClosure {
a61af66fc99e Initial load
duke
parents:
diff changeset
281 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
282 OopClosure* cl;
a61af66fc99e Initial load
duke
parents:
diff changeset
283 MemRegion mr;
a61af66fc99e Initial load
duke
parents:
diff changeset
284 virtual void do_space(Space* s) {
a61af66fc99e Initial load
duke
parents:
diff changeset
285 s->oop_iterate(mr, cl);
a61af66fc99e Initial load
duke
parents:
diff changeset
286 }
a61af66fc99e Initial load
duke
parents:
diff changeset
287 GenerationOopIterateClosure(OopClosure* _cl, MemRegion _mr) :
a61af66fc99e Initial load
duke
parents:
diff changeset
288 cl(_cl), mr(_mr) {}
a61af66fc99e Initial load
duke
parents:
diff changeset
289 };
a61af66fc99e Initial load
duke
parents:
diff changeset
290
a61af66fc99e Initial load
duke
parents:
diff changeset
291 void Generation::oop_iterate(OopClosure* cl) {
a61af66fc99e Initial load
duke
parents:
diff changeset
292 GenerationOopIterateClosure blk(cl, _reserved);
a61af66fc99e Initial load
duke
parents:
diff changeset
293 space_iterate(&blk);
a61af66fc99e Initial load
duke
parents:
diff changeset
294 }
a61af66fc99e Initial load
duke
parents:
diff changeset
295
a61af66fc99e Initial load
duke
parents:
diff changeset
296 void Generation::oop_iterate(MemRegion mr, OopClosure* cl) {
a61af66fc99e Initial load
duke
parents:
diff changeset
297 GenerationOopIterateClosure blk(cl, mr);
a61af66fc99e Initial load
duke
parents:
diff changeset
298 space_iterate(&blk);
a61af66fc99e Initial load
duke
parents:
diff changeset
299 }
a61af66fc99e Initial load
duke
parents:
diff changeset
300
a61af66fc99e Initial load
duke
parents:
diff changeset
301 void Generation::younger_refs_in_space_iterate(Space* sp,
a61af66fc99e Initial load
duke
parents:
diff changeset
302 OopsInGenClosure* cl) {
a61af66fc99e Initial load
duke
parents:
diff changeset
303 GenRemSet* rs = SharedHeap::heap()->rem_set();
a61af66fc99e Initial load
duke
parents:
diff changeset
304 rs->younger_refs_in_space_iterate(sp, cl);
a61af66fc99e Initial load
duke
parents:
diff changeset
305 }
a61af66fc99e Initial load
duke
parents:
diff changeset
306
a61af66fc99e Initial load
duke
parents:
diff changeset
307 class GenerationObjIterateClosure : public SpaceClosure {
a61af66fc99e Initial load
duke
parents:
diff changeset
308 private:
a61af66fc99e Initial load
duke
parents:
diff changeset
309 ObjectClosure* _cl;
a61af66fc99e Initial load
duke
parents:
diff changeset
310 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
311 virtual void do_space(Space* s) {
a61af66fc99e Initial load
duke
parents:
diff changeset
312 s->object_iterate(_cl);
a61af66fc99e Initial load
duke
parents:
diff changeset
313 }
a61af66fc99e Initial load
duke
parents:
diff changeset
314 GenerationObjIterateClosure(ObjectClosure* cl) : _cl(cl) {}
a61af66fc99e Initial load
duke
parents:
diff changeset
315 };
a61af66fc99e Initial load
duke
parents:
diff changeset
316
a61af66fc99e Initial load
duke
parents:
diff changeset
317 void Generation::object_iterate(ObjectClosure* cl) {
a61af66fc99e Initial load
duke
parents:
diff changeset
318 GenerationObjIterateClosure blk(cl);
a61af66fc99e Initial load
duke
parents:
diff changeset
319 space_iterate(&blk);
a61af66fc99e Initial load
duke
parents:
diff changeset
320 }
a61af66fc99e Initial load
duke
parents:
diff changeset
321
a61af66fc99e Initial load
duke
parents:
diff changeset
322 void Generation::prepare_for_compaction(CompactPoint* cp) {
a61af66fc99e Initial load
duke
parents:
diff changeset
323 // Generic implementation, can be specialized
a61af66fc99e Initial load
duke
parents:
diff changeset
324 CompactibleSpace* space = first_compaction_space();
a61af66fc99e Initial load
duke
parents:
diff changeset
325 while (space != NULL) {
a61af66fc99e Initial load
duke
parents:
diff changeset
326 space->prepare_for_compaction(cp);
a61af66fc99e Initial load
duke
parents:
diff changeset
327 space = space->next_compaction_space();
a61af66fc99e Initial load
duke
parents:
diff changeset
328 }
a61af66fc99e Initial load
duke
parents:
diff changeset
329 }
a61af66fc99e Initial load
duke
parents:
diff changeset
330
a61af66fc99e Initial load
duke
parents:
diff changeset
331 class AdjustPointersClosure: public SpaceClosure {
a61af66fc99e Initial load
duke
parents:
diff changeset
332 public:
a61af66fc99e Initial load
duke
parents:
diff changeset
333 void do_space(Space* sp) {
a61af66fc99e Initial load
duke
parents:
diff changeset
334 sp->adjust_pointers();
a61af66fc99e Initial load
duke
parents:
diff changeset
335 }
a61af66fc99e Initial load
duke
parents:
diff changeset
336 };
a61af66fc99e Initial load
duke
parents:
diff changeset
337
a61af66fc99e Initial load
duke
parents:
diff changeset
338 void Generation::adjust_pointers() {
a61af66fc99e Initial load
duke
parents:
diff changeset
339 // Note that this is done over all spaces, not just the compactible
a61af66fc99e Initial load
duke
parents:
diff changeset
340 // ones.
a61af66fc99e Initial load
duke
parents:
diff changeset
341 AdjustPointersClosure blk;
a61af66fc99e Initial load
duke
parents:
diff changeset
342 space_iterate(&blk, true);
a61af66fc99e Initial load
duke
parents:
diff changeset
343 }
a61af66fc99e Initial load
duke
parents:
diff changeset
344
a61af66fc99e Initial load
duke
parents:
diff changeset
345 void Generation::compact() {
a61af66fc99e Initial load
duke
parents:
diff changeset
346 CompactibleSpace* sp = first_compaction_space();
a61af66fc99e Initial load
duke
parents:
diff changeset
347 while (sp != NULL) {
a61af66fc99e Initial load
duke
parents:
diff changeset
348 sp->compact();
a61af66fc99e Initial load
duke
parents:
diff changeset
349 sp = sp->next_compaction_space();
a61af66fc99e Initial load
duke
parents:
diff changeset
350 }
a61af66fc99e Initial load
duke
parents:
diff changeset
351 }
a61af66fc99e Initial load
duke
parents:
diff changeset
352
a61af66fc99e Initial load
duke
parents:
diff changeset
353 CardGeneration::CardGeneration(ReservedSpace rs, size_t initial_byte_size,
a61af66fc99e Initial load
duke
parents:
diff changeset
354 int level,
a61af66fc99e Initial load
duke
parents:
diff changeset
355 GenRemSet* remset) :
a61af66fc99e Initial load
duke
parents:
diff changeset
356 Generation(rs, initial_byte_size, level), _rs(remset)
a61af66fc99e Initial load
duke
parents:
diff changeset
357 {
a61af66fc99e Initial load
duke
parents:
diff changeset
358 HeapWord* start = (HeapWord*)rs.base();
a61af66fc99e Initial load
duke
parents:
diff changeset
359 size_t reserved_byte_size = rs.size();
a61af66fc99e Initial load
duke
parents:
diff changeset
360 assert((uintptr_t(start) & 3) == 0, "bad alignment");
a61af66fc99e Initial load
duke
parents:
diff changeset
361 assert((reserved_byte_size & 3) == 0, "bad alignment");
a61af66fc99e Initial load
duke
parents:
diff changeset
362 MemRegion reserved_mr(start, heap_word_size(reserved_byte_size));
a61af66fc99e Initial load
duke
parents:
diff changeset
363 _bts = new BlockOffsetSharedArray(reserved_mr,
a61af66fc99e Initial load
duke
parents:
diff changeset
364 heap_word_size(initial_byte_size));
a61af66fc99e Initial load
duke
parents:
diff changeset
365 MemRegion committed_mr(start, heap_word_size(initial_byte_size));
a61af66fc99e Initial load
duke
parents:
diff changeset
366 _rs->resize_covered_region(committed_mr);
a61af66fc99e Initial load
duke
parents:
diff changeset
367 if (_bts == NULL)
a61af66fc99e Initial load
duke
parents:
diff changeset
368 vm_exit_during_initialization("Could not allocate a BlockOffsetArray");
a61af66fc99e Initial load
duke
parents:
diff changeset
369
a61af66fc99e Initial load
duke
parents:
diff changeset
370 // Verify that the start and end of this generation is the start of a card.
a61af66fc99e Initial load
duke
parents:
diff changeset
371 // If this wasn't true, a single card could span more than on generation,
a61af66fc99e Initial load
duke
parents:
diff changeset
372 // which would cause problems when we commit/uncommit memory, and when we
a61af66fc99e Initial load
duke
parents:
diff changeset
373 // clear and dirty cards.
a61af66fc99e Initial load
duke
parents:
diff changeset
374 guarantee(_rs->is_aligned(reserved_mr.start()), "generation must be card aligned");
a61af66fc99e Initial load
duke
parents:
diff changeset
375 if (reserved_mr.end() != Universe::heap()->reserved_region().end()) {
a61af66fc99e Initial load
duke
parents:
diff changeset
376 // Don't check at the very end of the heap as we'll assert that we're probing off
a61af66fc99e Initial load
duke
parents:
diff changeset
377 // the end if we try.
a61af66fc99e Initial load
duke
parents:
diff changeset
378 guarantee(_rs->is_aligned(reserved_mr.end()), "generation must be card aligned");
a61af66fc99e Initial load
duke
parents:
diff changeset
379 }
a61af66fc99e Initial load
duke
parents:
diff changeset
380 }
a61af66fc99e Initial load
duke
parents:
diff changeset
381
271
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
382 bool CardGeneration::expand(size_t bytes, size_t expand_bytes) {
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
383 assert_locked_or_safepoint(Heap_lock);
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
384 if (bytes == 0) {
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
385 return true; // That's what grow_by(0) would return
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
386 }
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
387 size_t aligned_bytes = ReservedSpace::page_align_size_up(bytes);
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
388 if (aligned_bytes == 0){
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
389 // The alignment caused the number of bytes to wrap. An expand_by(0) will
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
390 // return true with the implication that an expansion was done when it
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
391 // was not. A call to expand implies a best effort to expand by "bytes"
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
392 // but not a guarantee. Align down to give a best effort. This is likely
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
393 // the most that the generation can expand since it has some capacity to
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
394 // start with.
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
395 aligned_bytes = ReservedSpace::page_align_size_down(bytes);
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
396 }
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
397 size_t aligned_expand_bytes = ReservedSpace::page_align_size_up(expand_bytes);
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
398 bool success = false;
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
399 if (aligned_expand_bytes > aligned_bytes) {
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
400 success = grow_by(aligned_expand_bytes);
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
401 }
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
402 if (!success) {
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
403 success = grow_by(aligned_bytes);
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
404 }
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
405 if (!success) {
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
406 success = grow_to_reserved();
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
407 }
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
408 if (PrintGC && Verbose) {
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
409 if (success && GC_locker::is_active()) {
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
410 gclog_or_tty->print_cr("Garbage collection disabled, expanded heap instead");
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
411 }
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
412 }
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
413
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
414 return success;
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
415 }
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
416
0
a61af66fc99e Initial load
duke
parents:
diff changeset
417
a61af66fc99e Initial load
duke
parents:
diff changeset
418 // No young generation references, clear this generation's cards.
a61af66fc99e Initial load
duke
parents:
diff changeset
419 void CardGeneration::clear_remembered_set() {
a61af66fc99e Initial load
duke
parents:
diff changeset
420 _rs->clear(reserved());
a61af66fc99e Initial load
duke
parents:
diff changeset
421 }
a61af66fc99e Initial load
duke
parents:
diff changeset
422
a61af66fc99e Initial load
duke
parents:
diff changeset
423
a61af66fc99e Initial load
duke
parents:
diff changeset
424 // Objects in this generation may have moved, invalidate this
a61af66fc99e Initial load
duke
parents:
diff changeset
425 // generation's cards.
a61af66fc99e Initial load
duke
parents:
diff changeset
426 void CardGeneration::invalidate_remembered_set() {
a61af66fc99e Initial load
duke
parents:
diff changeset
427 _rs->invalidate(used_region());
a61af66fc99e Initial load
duke
parents:
diff changeset
428 }
a61af66fc99e Initial load
duke
parents:
diff changeset
429
a61af66fc99e Initial load
duke
parents:
diff changeset
430
a61af66fc99e Initial load
duke
parents:
diff changeset
431 // Currently nothing to do.
a61af66fc99e Initial load
duke
parents:
diff changeset
432 void CardGeneration::prepare_for_verify() {}
a61af66fc99e Initial load
duke
parents:
diff changeset
433
a61af66fc99e Initial load
duke
parents:
diff changeset
434
a61af66fc99e Initial load
duke
parents:
diff changeset
435 void OneContigSpaceCardGeneration::collect(bool full,
a61af66fc99e Initial load
duke
parents:
diff changeset
436 bool clear_all_soft_refs,
a61af66fc99e Initial load
duke
parents:
diff changeset
437 size_t size,
a61af66fc99e Initial load
duke
parents:
diff changeset
438 bool is_tlab) {
a61af66fc99e Initial load
duke
parents:
diff changeset
439 SpecializationStats::clear();
a61af66fc99e Initial load
duke
parents:
diff changeset
440 // Temporarily expand the span of our ref processor, so
a61af66fc99e Initial load
duke
parents:
diff changeset
441 // refs discovery is over the entire heap, not just this generation
a61af66fc99e Initial load
duke
parents:
diff changeset
442 ReferenceProcessorSpanMutator
a61af66fc99e Initial load
duke
parents:
diff changeset
443 x(ref_processor(), GenCollectedHeap::heap()->reserved_region());
a61af66fc99e Initial load
duke
parents:
diff changeset
444 GenMarkSweep::invoke_at_safepoint(_level, ref_processor(), clear_all_soft_refs);
a61af66fc99e Initial load
duke
parents:
diff changeset
445 SpecializationStats::print();
a61af66fc99e Initial load
duke
parents:
diff changeset
446 }
a61af66fc99e Initial load
duke
parents:
diff changeset
447
a61af66fc99e Initial load
duke
parents:
diff changeset
448 HeapWord*
a61af66fc99e Initial load
duke
parents:
diff changeset
449 OneContigSpaceCardGeneration::expand_and_allocate(size_t word_size,
a61af66fc99e Initial load
duke
parents:
diff changeset
450 bool is_tlab,
a61af66fc99e Initial load
duke
parents:
diff changeset
451 bool parallel) {
a61af66fc99e Initial load
duke
parents:
diff changeset
452 assert(!is_tlab, "OneContigSpaceCardGeneration does not support TLAB allocation");
a61af66fc99e Initial load
duke
parents:
diff changeset
453 if (parallel) {
a61af66fc99e Initial load
duke
parents:
diff changeset
454 MutexLocker x(ParGCRareEvent_lock);
a61af66fc99e Initial load
duke
parents:
diff changeset
455 HeapWord* result = NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
456 size_t byte_size = word_size * HeapWordSize;
a61af66fc99e Initial load
duke
parents:
diff changeset
457 while (true) {
a61af66fc99e Initial load
duke
parents:
diff changeset
458 expand(byte_size, _min_heap_delta_bytes);
a61af66fc99e Initial load
duke
parents:
diff changeset
459 if (GCExpandToAllocateDelayMillis > 0) {
a61af66fc99e Initial load
duke
parents:
diff changeset
460 os::sleep(Thread::current(), GCExpandToAllocateDelayMillis, false);
a61af66fc99e Initial load
duke
parents:
diff changeset
461 }
a61af66fc99e Initial load
duke
parents:
diff changeset
462 result = _the_space->par_allocate(word_size);
a61af66fc99e Initial load
duke
parents:
diff changeset
463 if ( result != NULL) {
a61af66fc99e Initial load
duke
parents:
diff changeset
464 return result;
a61af66fc99e Initial load
duke
parents:
diff changeset
465 } else {
a61af66fc99e Initial load
duke
parents:
diff changeset
466 // If there's not enough expansion space available, give up.
a61af66fc99e Initial load
duke
parents:
diff changeset
467 if (_virtual_space.uncommitted_size() < byte_size) {
a61af66fc99e Initial load
duke
parents:
diff changeset
468 return NULL;
a61af66fc99e Initial load
duke
parents:
diff changeset
469 }
a61af66fc99e Initial load
duke
parents:
diff changeset
470 // else try again
a61af66fc99e Initial load
duke
parents:
diff changeset
471 }
a61af66fc99e Initial load
duke
parents:
diff changeset
472 }
a61af66fc99e Initial load
duke
parents:
diff changeset
473 } else {
a61af66fc99e Initial load
duke
parents:
diff changeset
474 expand(word_size*HeapWordSize, _min_heap_delta_bytes);
a61af66fc99e Initial load
duke
parents:
diff changeset
475 return _the_space->allocate(word_size);
a61af66fc99e Initial load
duke
parents:
diff changeset
476 }
a61af66fc99e Initial load
duke
parents:
diff changeset
477 }
a61af66fc99e Initial load
duke
parents:
diff changeset
478
271
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
479 bool OneContigSpaceCardGeneration::expand(size_t bytes, size_t expand_bytes) {
0
a61af66fc99e Initial load
duke
parents:
diff changeset
480 GCMutexLocker x(ExpandHeap_lock);
271
818a18cd69a8 6730514: assertion failure in mangling code when expanding by 0 bytes
jmasa
parents: 269
diff changeset
481 return CardGeneration::expand(bytes, expand_bytes);
0
a61af66fc99e Initial load
duke
parents:
diff changeset
482 }
a61af66fc99e Initial load
duke
parents:
diff changeset
483
a61af66fc99e Initial load
duke
parents:
diff changeset
484
a61af66fc99e Initial load
duke
parents:
diff changeset
485 void OneContigSpaceCardGeneration::shrink(size_t bytes) {
a61af66fc99e Initial load
duke
parents:
diff changeset
486 assert_locked_or_safepoint(ExpandHeap_lock);
a61af66fc99e Initial load
duke
parents:
diff changeset
487 size_t size = ReservedSpace::page_align_size_down(bytes);
a61af66fc99e Initial load
duke
parents:
diff changeset
488 if (size > 0) {
a61af66fc99e Initial load
duke
parents:
diff changeset
489 shrink_by(size);
a61af66fc99e Initial load
duke
parents:
diff changeset
490 }
a61af66fc99e Initial load
duke
parents:
diff changeset
491 }
a61af66fc99e Initial load
duke
parents:
diff changeset
492
a61af66fc99e Initial load
duke
parents:
diff changeset
493
a61af66fc99e Initial load
duke
parents:
diff changeset
494 size_t OneContigSpaceCardGeneration::capacity() const {
a61af66fc99e Initial load
duke
parents:
diff changeset
495 return _the_space->capacity();
a61af66fc99e Initial load
duke
parents:
diff changeset
496 }
a61af66fc99e Initial load
duke
parents:
diff changeset
497
a61af66fc99e Initial load
duke
parents:
diff changeset
498
a61af66fc99e Initial load
duke
parents:
diff changeset
499 size_t OneContigSpaceCardGeneration::used() const {
a61af66fc99e Initial load
duke
parents:
diff changeset
500 return _the_space->used();
a61af66fc99e Initial load
duke
parents:
diff changeset
501 }
a61af66fc99e Initial load
duke
parents:
diff changeset
502
a61af66fc99e Initial load
duke
parents:
diff changeset
503
a61af66fc99e Initial load
duke
parents:
diff changeset
504 size_t OneContigSpaceCardGeneration::free() const {
a61af66fc99e Initial load
duke
parents:
diff changeset
505 return _the_space->free();
a61af66fc99e Initial load
duke
parents:
diff changeset
506 }
a61af66fc99e Initial load
duke
parents:
diff changeset
507
a61af66fc99e Initial load
duke
parents:
diff changeset
508 MemRegion OneContigSpaceCardGeneration::used_region() const {
a61af66fc99e Initial load
duke
parents:
diff changeset
509 return the_space()->used_region();
a61af66fc99e Initial load
duke
parents:
diff changeset
510 }
a61af66fc99e Initial load
duke
parents:
diff changeset
511
a61af66fc99e Initial load
duke
parents:
diff changeset
512 size_t OneContigSpaceCardGeneration::unsafe_max_alloc_nogc() const {
a61af66fc99e Initial load
duke
parents:
diff changeset
513 return _the_space->free();
a61af66fc99e Initial load
duke
parents:
diff changeset
514 }
a61af66fc99e Initial load
duke
parents:
diff changeset
515
a61af66fc99e Initial load
duke
parents:
diff changeset
516 size_t OneContigSpaceCardGeneration::contiguous_available() const {
a61af66fc99e Initial load
duke
parents:
diff changeset
517 return _the_space->free() + _virtual_space.uncommitted_size();
a61af66fc99e Initial load
duke
parents:
diff changeset
518 }
a61af66fc99e Initial load
duke
parents:
diff changeset
519
a61af66fc99e Initial load
duke
parents:
diff changeset
520 bool OneContigSpaceCardGeneration::grow_by(size_t bytes) {
a61af66fc99e Initial load
duke
parents:
diff changeset
521 assert_locked_or_safepoint(ExpandHeap_lock);
a61af66fc99e Initial load
duke
parents:
diff changeset
522 bool result = _virtual_space.expand_by(bytes);
a61af66fc99e Initial load
duke
parents:
diff changeset
523 if (result) {
a61af66fc99e Initial load
duke
parents:
diff changeset
524 size_t new_word_size =
a61af66fc99e Initial load
duke
parents:
diff changeset
525 heap_word_size(_virtual_space.committed_size());
a61af66fc99e Initial load
duke
parents:
diff changeset
526 MemRegion mr(_the_space->bottom(), new_word_size);
a61af66fc99e Initial load
duke
parents:
diff changeset
527 // Expand card table
a61af66fc99e Initial load
duke
parents:
diff changeset
528 Universe::heap()->barrier_set()->resize_covered_region(mr);
a61af66fc99e Initial load
duke
parents:
diff changeset
529 // Expand shared block offset array
a61af66fc99e Initial load
duke
parents:
diff changeset
530 _bts->resize(new_word_size);
a61af66fc99e Initial load
duke
parents:
diff changeset
531
a61af66fc99e Initial load
duke
parents:
diff changeset
532 // Fix for bug #4668531
263
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
533 if (ZapUnusedHeapArea) {
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
534 MemRegion mangle_region(_the_space->end(),
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
535 (HeapWord*)_virtual_space.high());
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
536 SpaceMangler::mangle_region(mangle_region);
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
537 }
0
a61af66fc99e Initial load
duke
parents:
diff changeset
538
a61af66fc99e Initial load
duke
parents:
diff changeset
539 // Expand space -- also expands space's BOT
a61af66fc99e Initial load
duke
parents:
diff changeset
540 // (which uses (part of) shared array above)
a61af66fc99e Initial load
duke
parents:
diff changeset
541 _the_space->set_end((HeapWord*)_virtual_space.high());
a61af66fc99e Initial load
duke
parents:
diff changeset
542
a61af66fc99e Initial load
duke
parents:
diff changeset
543 // update the space and generation capacity counters
a61af66fc99e Initial load
duke
parents:
diff changeset
544 update_counters();
a61af66fc99e Initial load
duke
parents:
diff changeset
545
a61af66fc99e Initial load
duke
parents:
diff changeset
546 if (Verbose && PrintGC) {
a61af66fc99e Initial load
duke
parents:
diff changeset
547 size_t new_mem_size = _virtual_space.committed_size();
a61af66fc99e Initial load
duke
parents:
diff changeset
548 size_t old_mem_size = new_mem_size - bytes;
a61af66fc99e Initial load
duke
parents:
diff changeset
549 gclog_or_tty->print_cr("Expanding %s from " SIZE_FORMAT "K by "
a61af66fc99e Initial load
duke
parents:
diff changeset
550 SIZE_FORMAT "K to " SIZE_FORMAT "K",
a61af66fc99e Initial load
duke
parents:
diff changeset
551 name(), old_mem_size/K, bytes/K, new_mem_size/K);
a61af66fc99e Initial load
duke
parents:
diff changeset
552 }
a61af66fc99e Initial load
duke
parents:
diff changeset
553 }
a61af66fc99e Initial load
duke
parents:
diff changeset
554 return result;
a61af66fc99e Initial load
duke
parents:
diff changeset
555 }
a61af66fc99e Initial load
duke
parents:
diff changeset
556
a61af66fc99e Initial load
duke
parents:
diff changeset
557
a61af66fc99e Initial load
duke
parents:
diff changeset
558 bool OneContigSpaceCardGeneration::grow_to_reserved() {
a61af66fc99e Initial load
duke
parents:
diff changeset
559 assert_locked_or_safepoint(ExpandHeap_lock);
a61af66fc99e Initial load
duke
parents:
diff changeset
560 bool success = true;
a61af66fc99e Initial load
duke
parents:
diff changeset
561 const size_t remaining_bytes = _virtual_space.uncommitted_size();
a61af66fc99e Initial load
duke
parents:
diff changeset
562 if (remaining_bytes > 0) {
a61af66fc99e Initial load
duke
parents:
diff changeset
563 success = grow_by(remaining_bytes);
a61af66fc99e Initial load
duke
parents:
diff changeset
564 DEBUG_ONLY(if (!success) warning("grow to reserved failed");)
a61af66fc99e Initial load
duke
parents:
diff changeset
565 }
a61af66fc99e Initial load
duke
parents:
diff changeset
566 return success;
a61af66fc99e Initial load
duke
parents:
diff changeset
567 }
a61af66fc99e Initial load
duke
parents:
diff changeset
568
a61af66fc99e Initial load
duke
parents:
diff changeset
569 void OneContigSpaceCardGeneration::shrink_by(size_t bytes) {
a61af66fc99e Initial load
duke
parents:
diff changeset
570 assert_locked_or_safepoint(ExpandHeap_lock);
a61af66fc99e Initial load
duke
parents:
diff changeset
571 // Shrink committed space
a61af66fc99e Initial load
duke
parents:
diff changeset
572 _virtual_space.shrink_by(bytes);
a61af66fc99e Initial load
duke
parents:
diff changeset
573 // Shrink space; this also shrinks the space's BOT
a61af66fc99e Initial load
duke
parents:
diff changeset
574 _the_space->set_end((HeapWord*) _virtual_space.high());
a61af66fc99e Initial load
duke
parents:
diff changeset
575 size_t new_word_size = heap_word_size(_the_space->capacity());
a61af66fc99e Initial load
duke
parents:
diff changeset
576 // Shrink the shared block offset array
a61af66fc99e Initial load
duke
parents:
diff changeset
577 _bts->resize(new_word_size);
a61af66fc99e Initial load
duke
parents:
diff changeset
578 MemRegion mr(_the_space->bottom(), new_word_size);
a61af66fc99e Initial load
duke
parents:
diff changeset
579 // Shrink the card table
a61af66fc99e Initial load
duke
parents:
diff changeset
580 Universe::heap()->barrier_set()->resize_covered_region(mr);
a61af66fc99e Initial load
duke
parents:
diff changeset
581
a61af66fc99e Initial load
duke
parents:
diff changeset
582 if (Verbose && PrintGC) {
a61af66fc99e Initial load
duke
parents:
diff changeset
583 size_t new_mem_size = _virtual_space.committed_size();
a61af66fc99e Initial load
duke
parents:
diff changeset
584 size_t old_mem_size = new_mem_size + bytes;
a61af66fc99e Initial load
duke
parents:
diff changeset
585 gclog_or_tty->print_cr("Shrinking %s from " SIZE_FORMAT "K to " SIZE_FORMAT "K",
a61af66fc99e Initial load
duke
parents:
diff changeset
586 name(), old_mem_size/K, new_mem_size/K);
a61af66fc99e Initial load
duke
parents:
diff changeset
587 }
a61af66fc99e Initial load
duke
parents:
diff changeset
588 }
a61af66fc99e Initial load
duke
parents:
diff changeset
589
a61af66fc99e Initial load
duke
parents:
diff changeset
590 // Currently nothing to do.
a61af66fc99e Initial load
duke
parents:
diff changeset
591 void OneContigSpaceCardGeneration::prepare_for_verify() {}
a61af66fc99e Initial load
duke
parents:
diff changeset
592
a61af66fc99e Initial load
duke
parents:
diff changeset
593
a61af66fc99e Initial load
duke
parents:
diff changeset
594 void OneContigSpaceCardGeneration::object_iterate(ObjectClosure* blk) {
a61af66fc99e Initial load
duke
parents:
diff changeset
595 _the_space->object_iterate(blk);
a61af66fc99e Initial load
duke
parents:
diff changeset
596 }
a61af66fc99e Initial load
duke
parents:
diff changeset
597
a61af66fc99e Initial load
duke
parents:
diff changeset
598 void OneContigSpaceCardGeneration::space_iterate(SpaceClosure* blk,
a61af66fc99e Initial load
duke
parents:
diff changeset
599 bool usedOnly) {
a61af66fc99e Initial load
duke
parents:
diff changeset
600 blk->do_space(_the_space);
a61af66fc99e Initial load
duke
parents:
diff changeset
601 }
a61af66fc99e Initial load
duke
parents:
diff changeset
602
a61af66fc99e Initial load
duke
parents:
diff changeset
603 void OneContigSpaceCardGeneration::object_iterate_since_last_GC(ObjectClosure* blk) {
a61af66fc99e Initial load
duke
parents:
diff changeset
604 // Deal with delayed initialization of _the_space,
a61af66fc99e Initial load
duke
parents:
diff changeset
605 // and lack of initialization of _last_gc.
a61af66fc99e Initial load
duke
parents:
diff changeset
606 if (_last_gc.space() == NULL) {
a61af66fc99e Initial load
duke
parents:
diff changeset
607 assert(the_space() != NULL, "shouldn't be NULL");
a61af66fc99e Initial load
duke
parents:
diff changeset
608 _last_gc = the_space()->bottom_mark();
a61af66fc99e Initial load
duke
parents:
diff changeset
609 }
a61af66fc99e Initial load
duke
parents:
diff changeset
610 the_space()->object_iterate_from(_last_gc, blk);
a61af66fc99e Initial load
duke
parents:
diff changeset
611 }
a61af66fc99e Initial load
duke
parents:
diff changeset
612
a61af66fc99e Initial load
duke
parents:
diff changeset
613 void OneContigSpaceCardGeneration::younger_refs_iterate(OopsInGenClosure* blk) {
a61af66fc99e Initial load
duke
parents:
diff changeset
614 blk->set_generation(this);
a61af66fc99e Initial load
duke
parents:
diff changeset
615 younger_refs_in_space_iterate(_the_space, blk);
a61af66fc99e Initial load
duke
parents:
diff changeset
616 blk->reset_generation();
a61af66fc99e Initial load
duke
parents:
diff changeset
617 }
a61af66fc99e Initial load
duke
parents:
diff changeset
618
a61af66fc99e Initial load
duke
parents:
diff changeset
619 void OneContigSpaceCardGeneration::save_marks() {
a61af66fc99e Initial load
duke
parents:
diff changeset
620 _the_space->set_saved_mark();
a61af66fc99e Initial load
duke
parents:
diff changeset
621 }
a61af66fc99e Initial load
duke
parents:
diff changeset
622
a61af66fc99e Initial load
duke
parents:
diff changeset
623
a61af66fc99e Initial load
duke
parents:
diff changeset
624 void OneContigSpaceCardGeneration::reset_saved_marks() {
a61af66fc99e Initial load
duke
parents:
diff changeset
625 _the_space->reset_saved_mark();
a61af66fc99e Initial load
duke
parents:
diff changeset
626 }
a61af66fc99e Initial load
duke
parents:
diff changeset
627
a61af66fc99e Initial load
duke
parents:
diff changeset
628
a61af66fc99e Initial load
duke
parents:
diff changeset
629 bool OneContigSpaceCardGeneration::no_allocs_since_save_marks() {
a61af66fc99e Initial load
duke
parents:
diff changeset
630 return _the_space->saved_mark_at_top();
a61af66fc99e Initial load
duke
parents:
diff changeset
631 }
a61af66fc99e Initial load
duke
parents:
diff changeset
632
a61af66fc99e Initial load
duke
parents:
diff changeset
633 #define OneContig_SINCE_SAVE_MARKS_ITERATE_DEFN(OopClosureType, nv_suffix) \
a61af66fc99e Initial load
duke
parents:
diff changeset
634 \
a61af66fc99e Initial load
duke
parents:
diff changeset
635 void OneContigSpaceCardGeneration:: \
a61af66fc99e Initial load
duke
parents:
diff changeset
636 oop_since_save_marks_iterate##nv_suffix(OopClosureType* blk) { \
a61af66fc99e Initial load
duke
parents:
diff changeset
637 blk->set_generation(this); \
a61af66fc99e Initial load
duke
parents:
diff changeset
638 _the_space->oop_since_save_marks_iterate##nv_suffix(blk); \
a61af66fc99e Initial load
duke
parents:
diff changeset
639 blk->reset_generation(); \
a61af66fc99e Initial load
duke
parents:
diff changeset
640 save_marks(); \
a61af66fc99e Initial load
duke
parents:
diff changeset
641 }
a61af66fc99e Initial load
duke
parents:
diff changeset
642
a61af66fc99e Initial load
duke
parents:
diff changeset
643 ALL_SINCE_SAVE_MARKS_CLOSURES(OneContig_SINCE_SAVE_MARKS_ITERATE_DEFN)
a61af66fc99e Initial load
duke
parents:
diff changeset
644
a61af66fc99e Initial load
duke
parents:
diff changeset
645 #undef OneContig_SINCE_SAVE_MARKS_ITERATE_DEFN
a61af66fc99e Initial load
duke
parents:
diff changeset
646
a61af66fc99e Initial load
duke
parents:
diff changeset
647
a61af66fc99e Initial load
duke
parents:
diff changeset
648 void OneContigSpaceCardGeneration::gc_epilogue(bool full) {
a61af66fc99e Initial load
duke
parents:
diff changeset
649 _last_gc = WaterMark(the_space(), the_space()->top());
a61af66fc99e Initial load
duke
parents:
diff changeset
650
a61af66fc99e Initial load
duke
parents:
diff changeset
651 // update the generation and space performance counters
a61af66fc99e Initial load
duke
parents:
diff changeset
652 update_counters();
263
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
653 if (ZapUnusedHeapArea) {
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
654 the_space()->check_mangled_unused_area_complete();
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
655 }
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
656 }
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
657
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
658 void OneContigSpaceCardGeneration::record_spaces_top() {
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
659 assert(ZapUnusedHeapArea, "Not mangling unused space");
12eea04c8b06 6672698: mangle_unused_area() should not remangle the entire heap at each collection.
jmasa
parents: 113
diff changeset
660 the_space()->set_top_for_allocations();
0
a61af66fc99e Initial load
duke
parents:
diff changeset
661 }
a61af66fc99e Initial load
duke
parents:
diff changeset
662
a61af66fc99e Initial load
duke
parents:
diff changeset
663 void OneContigSpaceCardGeneration::verify(bool allow_dirty) {
a61af66fc99e Initial load
duke
parents:
diff changeset
664 the_space()->verify(allow_dirty);
a61af66fc99e Initial load
duke
parents:
diff changeset
665 }
a61af66fc99e Initial load
duke
parents:
diff changeset
666
a61af66fc99e Initial load
duke
parents:
diff changeset
667 void OneContigSpaceCardGeneration::print_on(outputStream* st) const {
a61af66fc99e Initial load
duke
parents:
diff changeset
668 Generation::print_on(st);
a61af66fc99e Initial load
duke
parents:
diff changeset
669 st->print(" the");
a61af66fc99e Initial load
duke
parents:
diff changeset
670 the_space()->print_on(st);
a61af66fc99e Initial load
duke
parents:
diff changeset
671 }