Mercurial > hg > graal-compiler
annotate src/share/vm/memory/universe.hpp @ 452:00b023ae2d78
6722113: CMS: Incorrect overflow handling during precleaning of Reference lists
Summary: When we encounter marking stack overflow during precleaning of Reference lists, we were using the overflow list mechanism, which can cause problems on account of mutating the mark word of the header because of conflicts with mutator accesses and updates of that field. Instead we should use the usual mechanism for overflow handling in concurrent phases, namely dirtying of the card on which the overflowed object lies. Since precleaning effectively does a form of discovered list processing, albeit with discovery enabled, we needed to adjust some code to be correct in the face of interleaved processing and discovery.
Reviewed-by: apetrusenko, jcoomes
author | ysr |
---|---|
date | Thu, 20 Nov 2008 12:27:41 -0800 |
parents | d1605aabd0a1 |
children | 7d7a7c599c17 |
rev | line source |
---|---|
0 | 1 /* |
196 | 2 * Copyright 1997-2008 Sun Microsystems, Inc. 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 * | |
19 * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, | |
20 * CA 95054 USA or visit www.sun.com if you need additional information or | |
21 * have any questions. | |
22 * | |
23 */ | |
24 | |
25 // Universe is a name space holding known system classes and objects in the VM. | |
26 // | |
27 // Loaded classes are accessible through the SystemDictionary. | |
28 // | |
29 // The object heap is allocated and accessed through Universe, and various allocation | |
30 // support is provided. Allocation by the interpreter and compiled code is done inline | |
31 // and bails out to Scavenge::invoke_and_allocate. | |
32 | |
33 class CollectedHeap; | |
34 class DeferredObjAllocEvent; | |
35 | |
36 | |
37 // Common parts of a methodOop cache. This cache safely interacts with | |
38 // the RedefineClasses API. | |
39 // | |
40 class CommonMethodOopCache : public CHeapObj { | |
41 // We save the klassOop and the idnum of methodOop in order to get | |
42 // the current cached methodOop. | |
43 private: | |
44 klassOop _klass; | |
45 int _method_idnum; | |
46 | |
47 public: | |
48 CommonMethodOopCache() { _klass = NULL; _method_idnum = -1; } | |
49 ~CommonMethodOopCache() { _klass = NULL; _method_idnum = -1; } | |
50 | |
51 void init(klassOop k, methodOop m, TRAPS); | |
52 klassOop klass() const { return _klass; } | |
53 int method_idnum() const { return _method_idnum; } | |
54 | |
55 // GC support | |
56 void oops_do(OopClosure* f) { f->do_oop((oop*)&_klass); } | |
57 }; | |
58 | |
59 | |
60 // A helper class for caching a methodOop when the user of the cache | |
61 // cares about all versions of the methodOop. | |
62 // | |
63 class ActiveMethodOopsCache : public CommonMethodOopCache { | |
64 // This subclass adds weak references to older versions of the | |
65 // methodOop and a query method for a methodOop. | |
66 | |
67 private: | |
68 // If the cached methodOop has not been redefined, then | |
69 // _prev_methods will be NULL. If all of the previous | |
70 // versions of the method have been collected, then | |
71 // _prev_methods can have a length of zero. | |
72 GrowableArray<jweak>* _prev_methods; | |
73 | |
74 public: | |
75 ActiveMethodOopsCache() { _prev_methods = NULL; } | |
76 ~ActiveMethodOopsCache(); | |
77 | |
78 void add_previous_version(const methodOop method); | |
79 bool is_same_method(const methodOop method) const; | |
80 }; | |
81 | |
82 | |
83 // A helper class for caching a methodOop when the user of the cache | |
84 // only cares about the latest version of the methodOop. | |
85 // | |
86 class LatestMethodOopCache : public CommonMethodOopCache { | |
87 // This subclass adds a getter method for the latest methodOop. | |
88 | |
89 public: | |
90 methodOop get_methodOop(); | |
91 }; | |
92 | |
93 | |
94 class Universe: AllStatic { | |
95 friend class MarkSweep; | |
96 friend class oopDesc; | |
97 friend class ClassLoader; | |
98 friend class Arguments; | |
99 friend class SystemDictionary; | |
100 friend class VMStructs; | |
101 friend class CompactingPermGenGen; | |
102 friend class VM_PopulateDumpSharedSpace; | |
103 | |
104 friend jint universe_init(); | |
105 friend void universe2_init(); | |
106 friend bool universe_post_init(); | |
107 | |
108 private: | |
109 // Known classes in the VM | |
110 static klassOop _boolArrayKlassObj; | |
111 static klassOop _byteArrayKlassObj; | |
112 static klassOop _charArrayKlassObj; | |
113 static klassOop _intArrayKlassObj; | |
114 static klassOop _shortArrayKlassObj; | |
115 static klassOop _longArrayKlassObj; | |
116 static klassOop _singleArrayKlassObj; | |
117 static klassOop _doubleArrayKlassObj; | |
118 static klassOop _typeArrayKlassObjs[T_VOID+1]; | |
119 | |
120 static klassOop _objectArrayKlassObj; | |
121 | |
122 static klassOop _symbolKlassObj; | |
123 static klassOop _methodKlassObj; | |
124 static klassOop _constMethodKlassObj; | |
125 static klassOop _methodDataKlassObj; | |
126 static klassOop _klassKlassObj; | |
127 static klassOop _arrayKlassKlassObj; | |
128 static klassOop _objArrayKlassKlassObj; | |
129 static klassOop _typeArrayKlassKlassObj; | |
130 static klassOop _instanceKlassKlassObj; | |
131 static klassOop _constantPoolKlassObj; | |
132 static klassOop _constantPoolCacheKlassObj; | |
133 static klassOop _compiledICHolderKlassObj; | |
134 static klassOop _systemObjArrayKlassObj; | |
135 | |
136 // Known objects in the VM | |
137 | |
138 // Primitive objects | |
139 static oop _int_mirror; | |
140 static oop _float_mirror; | |
141 static oop _double_mirror; | |
142 static oop _byte_mirror; | |
143 static oop _bool_mirror; | |
144 static oop _char_mirror; | |
145 static oop _long_mirror; | |
146 static oop _short_mirror; | |
147 static oop _void_mirror; | |
148 | |
149 static oop _main_thread_group; // Reference to the main thread group object | |
150 static oop _system_thread_group; // Reference to the system thread group object | |
151 | |
152 static typeArrayOop _the_empty_byte_array; // Canonicalized byte array | |
153 static typeArrayOop _the_empty_short_array; // Canonicalized short array | |
154 static typeArrayOop _the_empty_int_array; // Canonicalized int array | |
155 static objArrayOop _the_empty_system_obj_array; // Canonicalized system obj array | |
156 static objArrayOop _the_empty_class_klass_array; // Canonicalized obj array of type java.lang.Class | |
157 static objArrayOop _the_array_interfaces_array; // Canonicalized 2-array of cloneable & serializable klasses | |
158 static LatestMethodOopCache* _finalizer_register_cache; // static method for registering finalizable objects | |
159 static LatestMethodOopCache* _loader_addClass_cache; // method for registering loaded classes in class loader vector | |
160 static ActiveMethodOopsCache* _reflect_invoke_cache; // method for security checks | |
161 static oop _out_of_memory_error_java_heap; // preallocated error object (no backtrace) | |
162 static oop _out_of_memory_error_perm_gen; // preallocated error object (no backtrace) | |
163 static oop _out_of_memory_error_array_size;// preallocated error object (no backtrace) | |
164 static oop _out_of_memory_error_gc_overhead_limit; // preallocated error object (no backtrace) | |
165 | |
166 // array of preallocated error objects with backtrace | |
167 static objArrayOop _preallocated_out_of_memory_error_array; | |
168 | |
169 // number of preallocated error objects available for use | |
170 static volatile jint _preallocated_out_of_memory_error_avail_count; | |
171 | |
172 static oop _null_ptr_exception_instance; // preallocated exception object | |
173 static oop _arithmetic_exception_instance; // preallocated exception object | |
174 static oop _virtual_machine_error_instance; // preallocated exception object | |
175 // The object used as an exception dummy when exceptions are thrown for | |
176 // the vm thread. | |
177 static oop _vm_exception; | |
178 | |
179 static oop _emptySymbol; // Canonical empty string ("") symbol | |
180 | |
181 // The particular choice of collected heap. | |
182 static CollectedHeap* _collectedHeap; | |
113
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
183 // Base address for oop-within-java-object materialization. |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
184 // NULL if using wide oops. Doubles as heap oop null value. |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
185 static address _heap_base; |
0 | 186 |
187 // array of dummy objects used with +FullGCAlot | |
188 debug_only(static objArrayOop _fullgc_alot_dummy_array;) | |
113
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
189 // index of next entry to clear |
0 | 190 debug_only(static int _fullgc_alot_dummy_next;) |
191 | |
192 // Compiler/dispatch support | |
193 static int _base_vtable_size; // Java vtbl size of klass Object (in words) | |
194 | |
195 // Initialization | |
196 static bool _bootstrapping; // true during genesis | |
197 static bool _fully_initialized; // true after universe_init and initialize_vtables called | |
198 | |
199 // the array of preallocated errors with backtraces | |
200 static objArrayOop preallocated_out_of_memory_errors() { return _preallocated_out_of_memory_error_array; } | |
201 | |
202 // generate an out of memory error; if possible using an error with preallocated backtrace; | |
203 // otherwise return the given default error. | |
204 static oop gen_out_of_memory_error(oop default_err); | |
205 | |
206 // Historic gc information | |
207 static size_t _heap_capacity_at_last_gc; | |
208 static size_t _heap_used_at_last_gc; | |
209 | |
210 static jint initialize_heap(); | |
211 static void initialize_basic_type_mirrors(TRAPS); | |
212 static void fixup_mirrors(TRAPS); | |
213 | |
214 static void reinitialize_vtable_of(KlassHandle h_k, TRAPS); | |
215 static void reinitialize_itables(TRAPS); | |
216 static void compute_base_vtable_size(); // compute vtable size of class Object | |
217 | |
218 static void genesis(TRAPS); // Create the initial world | |
219 | |
220 // Mirrors for primitive classes (created eagerly) | |
221 static oop check_mirror(oop m) { | |
222 assert(m != NULL, "mirror not initialized"); | |
223 return m; | |
224 } | |
225 | |
226 // Debugging | |
227 static int _verify_count; // number of verifies done | |
228 // True during call to verify(). Should only be set/cleared in verify(). | |
229 static bool _verify_in_progress; | |
230 | |
231 static void compute_verify_oop_data(); | |
232 | |
233 public: | |
234 // Known classes in the VM | |
235 static klassOop boolArrayKlassObj() { return _boolArrayKlassObj; } | |
236 static klassOop byteArrayKlassObj() { return _byteArrayKlassObj; } | |
237 static klassOop charArrayKlassObj() { return _charArrayKlassObj; } | |
238 static klassOop intArrayKlassObj() { return _intArrayKlassObj; } | |
239 static klassOop shortArrayKlassObj() { return _shortArrayKlassObj; } | |
240 static klassOop longArrayKlassObj() { return _longArrayKlassObj; } | |
241 static klassOop singleArrayKlassObj() { return _singleArrayKlassObj; } | |
242 static klassOop doubleArrayKlassObj() { return _doubleArrayKlassObj; } | |
243 | |
244 static klassOop objectArrayKlassObj() { | |
245 return _objectArrayKlassObj; | |
246 } | |
247 | |
248 static klassOop typeArrayKlassObj(BasicType t) { | |
249 assert((uint)t < T_VOID+1, "range check"); | |
250 assert(_typeArrayKlassObjs[t] != NULL, "domain check"); | |
251 return _typeArrayKlassObjs[t]; | |
252 } | |
253 | |
254 static klassOop symbolKlassObj() { return _symbolKlassObj; } | |
255 static klassOop methodKlassObj() { return _methodKlassObj; } | |
256 static klassOop constMethodKlassObj() { return _constMethodKlassObj; } | |
257 static klassOop methodDataKlassObj() { return _methodDataKlassObj; } | |
258 static klassOop klassKlassObj() { return _klassKlassObj; } | |
259 static klassOop arrayKlassKlassObj() { return _arrayKlassKlassObj; } | |
260 static klassOop objArrayKlassKlassObj() { return _objArrayKlassKlassObj; } | |
261 static klassOop typeArrayKlassKlassObj() { return _typeArrayKlassKlassObj; } | |
262 static klassOop instanceKlassKlassObj() { return _instanceKlassKlassObj; } | |
263 static klassOop constantPoolKlassObj() { return _constantPoolKlassObj; } | |
264 static klassOop constantPoolCacheKlassObj() { return _constantPoolCacheKlassObj; } | |
265 static klassOop compiledICHolderKlassObj() { return _compiledICHolderKlassObj; } | |
266 static klassOop systemObjArrayKlassObj() { return _systemObjArrayKlassObj; } | |
267 | |
268 // Known objects in tbe VM | |
269 static oop int_mirror() { return check_mirror(_int_mirror); | |
270 } | |
271 static oop float_mirror() { return check_mirror(_float_mirror); } | |
272 static oop double_mirror() { return check_mirror(_double_mirror); } | |
273 static oop byte_mirror() { return check_mirror(_byte_mirror); } | |
274 static oop bool_mirror() { return check_mirror(_bool_mirror); } | |
275 static oop char_mirror() { return check_mirror(_char_mirror); } | |
276 static oop long_mirror() { return check_mirror(_long_mirror); } | |
277 static oop short_mirror() { return check_mirror(_short_mirror); } | |
278 static oop void_mirror() { return check_mirror(_void_mirror); } | |
279 | |
280 // table of same | |
281 static oop _mirrors[T_VOID+1]; | |
282 | |
283 static oop java_mirror(BasicType t) { | |
284 assert((uint)t < T_VOID+1, "range check"); | |
285 return check_mirror(_mirrors[t]); | |
286 } | |
287 static oop main_thread_group() { return _main_thread_group; } | |
288 static void set_main_thread_group(oop group) { _main_thread_group = group;} | |
289 | |
290 static oop system_thread_group() { return _system_thread_group; } | |
291 static void set_system_thread_group(oop group) { _system_thread_group = group;} | |
292 | |
293 static typeArrayOop the_empty_byte_array() { return _the_empty_byte_array; } | |
294 static typeArrayOop the_empty_short_array() { return _the_empty_short_array; } | |
295 static typeArrayOop the_empty_int_array() { return _the_empty_int_array; } | |
296 static objArrayOop the_empty_system_obj_array () { return _the_empty_system_obj_array; } | |
297 static objArrayOop the_empty_class_klass_array () { return _the_empty_class_klass_array; } | |
298 static objArrayOop the_array_interfaces_array() { return _the_array_interfaces_array; } | |
299 static methodOop finalizer_register_method() { return _finalizer_register_cache->get_methodOop(); } | |
300 static methodOop loader_addClass_method() { return _loader_addClass_cache->get_methodOop(); } | |
301 static ActiveMethodOopsCache* reflect_invoke_cache() { return _reflect_invoke_cache; } | |
302 static oop null_ptr_exception_instance() { return _null_ptr_exception_instance; } | |
303 static oop arithmetic_exception_instance() { return _arithmetic_exception_instance; } | |
304 static oop virtual_machine_error_instance() { return _virtual_machine_error_instance; } | |
305 static oop vm_exception() { return _vm_exception; } | |
306 static oop emptySymbol() { return _emptySymbol; } | |
307 | |
308 // OutOfMemoryError support. Returns an error with the required message. The returned error | |
309 // may or may not have a backtrace. If error has a backtrace then the stack trace is already | |
310 // filled in. | |
311 static oop out_of_memory_error_java_heap() { return gen_out_of_memory_error(_out_of_memory_error_java_heap); } | |
312 static oop out_of_memory_error_perm_gen() { return gen_out_of_memory_error(_out_of_memory_error_perm_gen); } | |
313 static oop out_of_memory_error_array_size() { return gen_out_of_memory_error(_out_of_memory_error_array_size); } | |
314 static oop out_of_memory_error_gc_overhead_limit() { return gen_out_of_memory_error(_out_of_memory_error_gc_overhead_limit); } | |
315 | |
316 // Accessors needed for fast allocation | |
317 static klassOop* boolArrayKlassObj_addr() { return &_boolArrayKlassObj; } | |
318 static klassOop* byteArrayKlassObj_addr() { return &_byteArrayKlassObj; } | |
319 static klassOop* charArrayKlassObj_addr() { return &_charArrayKlassObj; } | |
320 static klassOop* intArrayKlassObj_addr() { return &_intArrayKlassObj; } | |
321 static klassOop* shortArrayKlassObj_addr() { return &_shortArrayKlassObj; } | |
322 static klassOop* longArrayKlassObj_addr() { return &_longArrayKlassObj; } | |
323 static klassOop* singleArrayKlassObj_addr() { return &_singleArrayKlassObj; } | |
324 static klassOop* doubleArrayKlassObj_addr() { return &_doubleArrayKlassObj; } | |
325 | |
326 // The particular choice of collected heap. | |
327 static CollectedHeap* heap() { return _collectedHeap; } | |
328 | |
113
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
329 // For UseCompressedOops |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
330 static address heap_base() { return _heap_base; } |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
331 static address* heap_base_addr() { return &_heap_base; } |
ba764ed4b6f2
6420645: Create a vm that uses compressed oops for up to 32gb heapsizes
coleenp
parents:
0
diff
changeset
|
332 |
0 | 333 // Historic gc information |
334 static size_t get_heap_capacity_at_last_gc() { return _heap_capacity_at_last_gc; } | |
335 static size_t get_heap_free_at_last_gc() { return _heap_capacity_at_last_gc - _heap_used_at_last_gc; } | |
336 static size_t get_heap_used_at_last_gc() { return _heap_used_at_last_gc; } | |
337 static void update_heap_info_at_gc(); | |
338 | |
339 // Testers | |
340 static bool is_bootstrapping() { return _bootstrapping; } | |
341 static bool is_fully_initialized() { return _fully_initialized; } | |
342 | |
343 static inline bool element_type_should_be_aligned(BasicType type); | |
344 static inline bool field_type_should_be_aligned(BasicType type); | |
345 static bool on_page_boundary(void* addr); | |
346 static bool should_fill_in_stack_trace(Handle throwable); | |
347 static void check_alignment(uintx size, uintx alignment, const char* name); | |
348 | |
349 // Finalizer support. | |
350 static void run_finalizers_on_exit(); | |
351 | |
352 // Iteration | |
353 | |
354 // Apply "f" to the addresses of all the direct heap pointers maintained | |
355 // as static fields of "Universe". | |
356 static void oops_do(OopClosure* f, bool do_all = false); | |
357 | |
358 // Apply "f" to all klasses for basic types (classes not present in | |
359 // SystemDictionary). | |
360 static void basic_type_classes_do(void f(klassOop)); | |
361 | |
362 // Apply "f" to all system klasses (classes not present in SystemDictionary). | |
363 static void system_classes_do(void f(klassOop)); | |
364 | |
365 // For sharing -- fill in a list of known vtable pointers. | |
366 static void init_self_patching_vtbl_list(void** list, int count); | |
367 | |
368 // Debugging | |
369 static bool verify_in_progress() { return _verify_in_progress; } | |
370 static void verify(bool allow_dirty = true, bool silent = false); | |
371 static int verify_count() { return _verify_count; } | |
372 static void print(); | |
373 static void print_on(outputStream* st); | |
374 static void print_heap_at_SIGBREAK(); | |
375 static void print_heap_before_gc() { print_heap_before_gc(gclog_or_tty); } | |
376 static void print_heap_after_gc() { print_heap_after_gc(gclog_or_tty); } | |
377 static void print_heap_before_gc(outputStream* st); | |
378 static void print_heap_after_gc(outputStream* st); | |
379 | |
380 // Change the number of dummy objects kept reachable by the full gc dummy | |
381 // array; this should trigger relocation in a sliding compaction collector. | |
382 debug_only(static bool release_fullgc_alot_dummy();) | |
383 // The non-oop pattern (see compiledIC.hpp, etc) | |
384 static void* non_oop_word(); | |
385 | |
386 // Oop verification (see MacroAssembler::verify_oop) | |
387 static uintptr_t verify_oop_mask() PRODUCT_RETURN0; | |
388 static uintptr_t verify_oop_bits() PRODUCT_RETURN0; | |
389 static uintptr_t verify_mark_bits() PRODUCT_RETURN0; | |
390 static uintptr_t verify_mark_mask() PRODUCT_RETURN0; | |
391 static uintptr_t verify_klass_mask() PRODUCT_RETURN0; | |
392 static uintptr_t verify_klass_bits() PRODUCT_RETURN0; | |
393 | |
394 // Flushing and deoptimization | |
395 static void flush_dependents_on(instanceKlassHandle dependee); | |
396 #ifdef HOTSWAP | |
397 // Flushing and deoptimization in case of evolution | |
398 static void flush_evol_dependents_on(instanceKlassHandle dependee); | |
399 #endif // HOTSWAP | |
400 // Support for fullspeed debugging | |
401 static void flush_dependents_on_method(methodHandle dependee); | |
402 | |
403 // Compiler support | |
404 static int base_vtable_size() { return _base_vtable_size; } | |
405 }; | |
406 | |
407 class DeferredObjAllocEvent : public CHeapObj { | |
408 private: | |
409 oop _oop; | |
410 size_t _bytesize; | |
411 jint _arena_id; | |
412 | |
413 public: | |
414 DeferredObjAllocEvent(const oop o, const size_t s, const jint id) { | |
415 _oop = o; | |
416 _bytesize = s; | |
417 _arena_id = id; | |
418 } | |
419 | |
420 ~DeferredObjAllocEvent() { | |
421 } | |
422 | |
423 jint arena_id() { return _arena_id; } | |
424 size_t bytesize() { return _bytesize; } | |
425 oop get_oop() { return _oop; } | |
426 }; |