Mercurial > hg > truffle
comparison src/share/vm/gc_implementation/parallelScavenge/psMarkSweep.cpp @ 1387:0bfd3fb24150
6858496: Clear all SoftReferences before an out-of-memory due to GC overhead limit.
Summary: Ensure a full GC that clears SoftReferences before throwing an out-of-memory
Reviewed-by: ysr, jcoomes
author | jmasa |
---|---|
date | Tue, 13 Apr 2010 13:52:10 -0700 |
parents | 2a1472c30599 |
children | c18cbe5936b8 |
comparison
equal
deleted
inserted
replaced
1361:6b73e879f1c2 | 1387:0bfd3fb24150 |
---|---|
1 /* | 1 /* |
2 * Copyright 2001-2009 Sun Microsystems, Inc. All Rights Reserved. | 2 * Copyright 2001-2010 Sun Microsystems, Inc. All Rights Reserved. |
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. | 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. |
4 * | 4 * |
5 * This code is free software; you can redistribute it and/or modify it | 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 | 6 * under the terms of the GNU General Public License version 2 only, as |
7 * published by the Free Software Foundation. | 7 * published by the Free Software Foundation. |
44 // reasons, scavenge before full gc, or any other specialized behavior, it | 44 // reasons, scavenge before full gc, or any other specialized behavior, it |
45 // needs to be added here. | 45 // needs to be added here. |
46 // | 46 // |
47 // Note that this method should only be called from the vm_thread while | 47 // Note that this method should only be called from the vm_thread while |
48 // at a safepoint! | 48 // at a safepoint! |
49 // | |
50 // Note that the all_soft_refs_clear flag in the collector policy | |
51 // may be true because this method can be called without intervening | |
52 // activity. For example when the heap space is tight and full measure | |
53 // are being taken to free space. | |
54 | |
49 void PSMarkSweep::invoke(bool maximum_heap_compaction) { | 55 void PSMarkSweep::invoke(bool maximum_heap_compaction) { |
50 assert(SafepointSynchronize::is_at_safepoint(), "should be at safepoint"); | 56 assert(SafepointSynchronize::is_at_safepoint(), "should be at safepoint"); |
51 assert(Thread::current() == (Thread*)VMThread::vm_thread(), "should be in vm thread"); | 57 assert(Thread::current() == (Thread*)VMThread::vm_thread(), "should be in vm thread"); |
52 assert(!Universe::heap()->is_gc_active(), "not reentrant"); | 58 assert(!Universe::heap()->is_gc_active(), "not reentrant"); |
53 | 59 |
54 ParallelScavengeHeap* heap = (ParallelScavengeHeap*)Universe::heap(); | 60 ParallelScavengeHeap* heap = (ParallelScavengeHeap*)Universe::heap(); |
55 GCCause::Cause gc_cause = heap->gc_cause(); | 61 GCCause::Cause gc_cause = heap->gc_cause(); |
56 PSAdaptiveSizePolicy* policy = heap->size_policy(); | 62 PSAdaptiveSizePolicy* policy = heap->size_policy(); |
57 | 63 IsGCActiveMark mark; |
58 // Before each allocation/collection attempt, find out from the | 64 |
59 // policy object if GCs are, on the whole, taking too long. If so, | 65 if (ScavengeBeforeFullGC) { |
60 // bail out without attempting a collection. The exceptions are | 66 PSScavenge::invoke_no_policy(); |
61 // for explicitly requested GC's. | 67 } |
62 if (!policy->gc_time_limit_exceeded() || | 68 |
63 GCCause::is_user_requested_gc(gc_cause) || | 69 const bool clear_all_soft_refs = |
64 GCCause::is_serviceability_requested_gc(gc_cause)) { | 70 heap->collector_policy()->should_clear_all_soft_refs(); |
65 IsGCActiveMark mark; | 71 |
66 | 72 int count = (maximum_heap_compaction)?1:MarkSweepAlwaysCompactCount; |
67 if (ScavengeBeforeFullGC) { | 73 IntFlagSetting flag_setting(MarkSweepAlwaysCompactCount, count); |
68 PSScavenge::invoke_no_policy(); | 74 PSMarkSweep::invoke_no_policy(clear_all_soft_refs || maximum_heap_compaction); |
69 } | |
70 | |
71 int count = (maximum_heap_compaction)?1:MarkSweepAlwaysCompactCount; | |
72 IntFlagSetting flag_setting(MarkSweepAlwaysCompactCount, count); | |
73 PSMarkSweep::invoke_no_policy(maximum_heap_compaction); | |
74 } | |
75 } | 75 } |
76 | 76 |
77 // This method contains no policy. You should probably | 77 // This method contains no policy. You should probably |
78 // be calling invoke() instead. | 78 // be calling invoke() instead. |
79 void PSMarkSweep::invoke_no_policy(bool clear_all_softrefs) { | 79 void PSMarkSweep::invoke_no_policy(bool clear_all_softrefs) { |
86 | 86 |
87 ParallelScavengeHeap* heap = (ParallelScavengeHeap*)Universe::heap(); | 87 ParallelScavengeHeap* heap = (ParallelScavengeHeap*)Universe::heap(); |
88 GCCause::Cause gc_cause = heap->gc_cause(); | 88 GCCause::Cause gc_cause = heap->gc_cause(); |
89 assert(heap->kind() == CollectedHeap::ParallelScavengeHeap, "Sanity"); | 89 assert(heap->kind() == CollectedHeap::ParallelScavengeHeap, "Sanity"); |
90 PSAdaptiveSizePolicy* size_policy = heap->size_policy(); | 90 PSAdaptiveSizePolicy* size_policy = heap->size_policy(); |
91 | |
92 // The scope of casr should end after code that can change | |
93 // CollectorPolicy::_should_clear_all_soft_refs. | |
94 ClearedAllSoftRefs casr(clear_all_softrefs, heap->collector_policy()); | |
91 | 95 |
92 PSYoungGen* young_gen = heap->young_gen(); | 96 PSYoungGen* young_gen = heap->young_gen(); |
93 PSOldGen* old_gen = heap->old_gen(); | 97 PSOldGen* old_gen = heap->old_gen(); |
94 PSPermGen* perm_gen = heap->perm_gen(); | 98 PSPermGen* perm_gen = heap->perm_gen(); |
95 | 99 |
273 perm_gen->used_in_bytes(), | 277 perm_gen->used_in_bytes(), |
274 young_gen->eden_space()->capacity_in_bytes(), | 278 young_gen->eden_space()->capacity_in_bytes(), |
275 old_gen->max_gen_size(), | 279 old_gen->max_gen_size(), |
276 max_eden_size, | 280 max_eden_size, |
277 true /* full gc*/, | 281 true /* full gc*/, |
278 gc_cause); | 282 gc_cause, |
283 heap->collector_policy()); | |
279 | 284 |
280 heap->resize_old_gen(size_policy->calculated_old_free_size_in_bytes()); | 285 heap->resize_old_gen(size_policy->calculated_old_free_size_in_bytes()); |
281 | 286 |
282 // Don't resize the young generation at an major collection. A | 287 // Don't resize the young generation at an major collection. A |
283 // desired young generation size may have been calculated but | 288 // desired young generation size may have been calculated but |
324 } | 329 } |
325 | 330 |
326 // Track memory usage and detect low memory | 331 // Track memory usage and detect low memory |
327 MemoryService::track_memory_usage(); | 332 MemoryService::track_memory_usage(); |
328 heap->update_counters(); | 333 heap->update_counters(); |
329 | |
330 if (PrintGCDetails) { | |
331 if (size_policy->print_gc_time_limit_would_be_exceeded()) { | |
332 if (size_policy->gc_time_limit_exceeded()) { | |
333 gclog_or_tty->print_cr(" GC time is exceeding GCTimeLimit " | |
334 "of %d%%", GCTimeLimit); | |
335 } else { | |
336 gclog_or_tty->print_cr(" GC time would exceed GCTimeLimit " | |
337 "of %d%%", GCTimeLimit); | |
338 } | |
339 } | |
340 size_policy->set_print_gc_time_limit_would_be_exceeded(false); | |
341 } | |
342 } | 334 } |
343 | 335 |
344 if (VerifyAfterGC && heap->total_collections() >= VerifyGCStartAt) { | 336 if (VerifyAfterGC && heap->total_collections() >= VerifyGCStartAt) { |
345 HandleMark hm; // Discard invalid handles created during verification | 337 HandleMark hm; // Discard invalid handles created during verification |
346 gclog_or_tty->print(" VerifyAfterGC:"); | 338 gclog_or_tty->print(" VerifyAfterGC:"); |