97 } |
97 } |
98 |
98 |
99 jint GenCollectedHeap::initialize() { |
99 jint GenCollectedHeap::initialize() { |
100 CollectedHeap::pre_initialize(); |
100 CollectedHeap::pre_initialize(); |
101 |
101 |
102 _n_gens = gen_policy()->number_of_generations(); |
|
103 assert(_n_gens == 2, "There is no support for more than two generations"); |
|
104 |
|
105 // While there are no constraints in the GC code that HeapWordSize |
102 // While there are no constraints in the GC code that HeapWordSize |
106 // be any particular value, there are multiple other areas in the |
103 // be any particular value, there are multiple other areas in the |
107 // system which believe this to be true (e.g. oop->object_size in some |
104 // system which believe this to be true (e.g. oop->object_size in some |
108 // cases incorrectly returns the size in wordSize units rather than |
105 // cases incorrectly returns the size in wordSize units rather than |
109 // HeapWordSize). |
106 // HeapWordSize). |
207 return _young_gen->used() + _old_gen->used(); |
204 return _young_gen->used() + _old_gen->used(); |
208 } |
205 } |
209 |
206 |
210 // Save the "used_region" for generations level and lower. |
207 // Save the "used_region" for generations level and lower. |
211 void GenCollectedHeap::save_used_regions(int level) { |
208 void GenCollectedHeap::save_used_regions(int level) { |
212 assert(level >= 0, "Illegal level parameter"); |
209 assert(level == 0 || level == 1, "Illegal level parameter"); |
213 assert(level < _n_gens, "Illegal level parameter"); |
|
214 if (level == 1) { |
210 if (level == 1) { |
215 _old_gen->save_used_region(); |
211 _old_gen->save_used_region(); |
216 } |
212 } |
217 _young_gen->save_used_region(); |
213 _young_gen->save_used_region(); |
218 } |
214 } |
424 my_thread->is_ConcurrentGC_thread(), |
420 my_thread->is_ConcurrentGC_thread(), |
425 "incorrect thread type capability"); |
421 "incorrect thread type capability"); |
426 assert(Heap_lock->is_locked(), |
422 assert(Heap_lock->is_locked(), |
427 "the requesting thread should have the Heap_lock"); |
423 "the requesting thread should have the Heap_lock"); |
428 guarantee(!is_gc_active(), "collection is not reentrant"); |
424 guarantee(!is_gc_active(), "collection is not reentrant"); |
429 assert(max_level < n_gens(), "sanity check"); |
|
430 |
425 |
431 if (GC_locker::check_active_before_gc()) { |
426 if (GC_locker::check_active_before_gc()) { |
432 return; // GC is disabled (e.g. JNI GetXXXCritical operation) |
427 return; // GC is disabled (e.g. JNI GetXXXCritical operation) |
433 } |
428 } |
434 |
429 |
442 print_heap_before_gc(); |
437 print_heap_before_gc(); |
443 |
438 |
444 { |
439 { |
445 FlagSetting fl(_is_gc_active, true); |
440 FlagSetting fl(_is_gc_active, true); |
446 |
441 |
447 bool complete = full && (max_level == (n_gens()-1)); |
442 bool complete = full && (max_level == 1 /* old */); |
448 const char* gc_cause_prefix = complete ? "Full GC" : "GC"; |
443 const char* gc_cause_prefix = complete ? "Full GC" : "GC"; |
449 TraceCPUTime tcpu(PrintGCDetails, true, gclog_or_tty); |
444 TraceCPUTime tcpu(PrintGCDetails, true, gclog_or_tty); |
450 // The PrintGCDetails logging starts before we have incremented the GC id. We will do that later |
445 // The PrintGCDetails logging starts before we have incremented the GC id. We will do that later |
451 // so we can assume here that the next GC id is what we want. |
446 // so we can assume here that the next GC id is what we want. |
452 GCTraceTime t(GCCauseString(gc_cause_prefix, gc_cause()), PrintGCDetails, false, NULL, GCId::peek()); |
447 GCTraceTime t(GCCauseString(gc_cause_prefix, gc_cause()), PrintGCDetails, false, NULL, GCId::peek()); |
514 } |
509 } |
515 |
510 |
516 // Update "complete" boolean wrt what actually transpired -- |
511 // Update "complete" boolean wrt what actually transpired -- |
517 // for instance, a promotion failure could have led to |
512 // for instance, a promotion failure could have led to |
518 // a whole heap collection. |
513 // a whole heap collection. |
519 complete = complete || (max_level_collected == n_gens() - 1); |
514 complete = complete || (max_level_collected == 1 /* old */); |
520 |
515 |
521 if (complete) { // We did a "major" collection |
516 if (complete) { // We did a "major" collection |
522 // FIXME: See comment at pre_full_gc_dump call |
517 // FIXME: See comment at pre_full_gc_dump call |
523 post_full_gc_dump(NULL); // do any post full gc dumps |
518 post_full_gc_dump(NULL); // do any post full gc dumps |
524 } |
519 } |
531 MetaspaceAux::print_metaspace_change(metadata_prev_used); |
526 MetaspaceAux::print_metaspace_change(metadata_prev_used); |
532 } |
527 } |
533 } |
528 } |
534 |
529 |
535 // Adjust generation sizes. |
530 // Adjust generation sizes. |
536 if (max_level_collected == 1) { |
531 if (max_level_collected == 1 /* old */) { |
537 _old_gen->compute_new_size(); |
532 _old_gen->compute_new_size(); |
538 } |
533 } |
539 _young_gen->compute_new_size(); |
534 _young_gen->compute_new_size(); |
540 |
535 |
541 if (complete) { |
536 if (complete) { |
780 #else // INCLUDE_ALL_GCS |
775 #else // INCLUDE_ALL_GCS |
781 ShouldNotReachHere(); |
776 ShouldNotReachHere(); |
782 #endif // INCLUDE_ALL_GCS |
777 #endif // INCLUDE_ALL_GCS |
783 } else if (cause == GCCause::_wb_young_gc) { |
778 } else if (cause == GCCause::_wb_young_gc) { |
784 // minor collection for WhiteBox API |
779 // minor collection for WhiteBox API |
785 collect(cause, 0); |
780 collect(cause, 0 /* young */); |
786 } else { |
781 } else { |
787 #ifdef ASSERT |
782 #ifdef ASSERT |
788 if (cause == GCCause::_scavenge_alot) { |
783 if (cause == GCCause::_scavenge_alot) { |
789 // minor collection only |
784 // minor collection only |
790 collect(cause, 0); |
785 collect(cause, 0 /* young */); |
791 } else { |
786 } else { |
792 // Stop-the-world full collection |
787 // Stop-the-world full collection |
793 collect(cause, n_gens() - 1); |
788 collect(cause, 1 /* old */); |
794 } |
789 } |
795 #else |
790 #else |
796 // Stop-the-world full collection |
791 // Stop-the-world full collection |
797 collect(cause, n_gens() - 1); |
792 collect(cause, 1 /* old */); |
798 #endif |
793 #endif |
799 } |
794 } |
800 } |
795 } |
801 |
796 |
802 void GenCollectedHeap::collect(GCCause::Cause cause, int max_level) { |
797 void GenCollectedHeap::collect(GCCause::Cause cause, int max_level) { |
807 } |
802 } |
808 |
803 |
809 void GenCollectedHeap::collect_locked(GCCause::Cause cause) { |
804 void GenCollectedHeap::collect_locked(GCCause::Cause cause) { |
810 // The caller has the Heap_lock |
805 // The caller has the Heap_lock |
811 assert(Heap_lock->owned_by_self(), "this thread should own the Heap_lock"); |
806 assert(Heap_lock->owned_by_self(), "this thread should own the Heap_lock"); |
812 collect_locked(cause, n_gens() - 1); |
807 collect_locked(cause, 1 /* old */); |
813 } |
808 } |
814 |
809 |
815 // this is the private collection interface |
810 // this is the private collection interface |
816 // The Heap_lock is expected to be held on entry. |
811 // The Heap_lock is expected to be held on entry. |
817 |
812 |
863 } |
858 } |
864 } |
859 } |
865 #endif // INCLUDE_ALL_GCS |
860 #endif // INCLUDE_ALL_GCS |
866 |
861 |
867 void GenCollectedHeap::do_full_collection(bool clear_all_soft_refs) { |
862 void GenCollectedHeap::do_full_collection(bool clear_all_soft_refs) { |
868 do_full_collection(clear_all_soft_refs, _n_gens - 1); |
863 do_full_collection(clear_all_soft_refs, 1 /* old */); |
869 } |
864 } |
870 |
865 |
871 void GenCollectedHeap::do_full_collection(bool clear_all_soft_refs, |
866 void GenCollectedHeap::do_full_collection(bool clear_all_soft_refs, |
872 int max_level) { |
867 int max_level) { |
873 int local_max_level; |
868 int local_max_level; |
895 // This time allow the old gen to be collected as well |
890 // This time allow the old gen to be collected as well |
896 do_collection(true /* full */, |
891 do_collection(true /* full */, |
897 clear_all_soft_refs /* clear_all_soft_refs */, |
892 clear_all_soft_refs /* clear_all_soft_refs */, |
898 0 /* size */, |
893 0 /* size */, |
899 false /* is_tlab */, |
894 false /* is_tlab */, |
900 n_gens() - 1 /* max_level */); |
895 1 /* old */ /* max_level */); |
901 } |
896 } |
902 } |
897 } |
903 |
898 |
904 bool GenCollectedHeap::is_in_young(oop p) { |
899 bool GenCollectedHeap::is_in_young(oop p) { |
905 bool result = ((HeapWord*)p) < _old_gen->reserved().start(); |
900 bool result = ((HeapWord*)p) < _old_gen->reserved().start(); |
1121 assert(_gch != NULL, "Uninitialized access to GenCollectedHeap::heap()"); |
1116 assert(_gch != NULL, "Uninitialized access to GenCollectedHeap::heap()"); |
1122 assert(_gch->kind() == CollectedHeap::GenCollectedHeap, "not a generational heap"); |
1117 assert(_gch->kind() == CollectedHeap::GenCollectedHeap, "not a generational heap"); |
1123 return _gch; |
1118 return _gch; |
1124 } |
1119 } |
1125 |
1120 |
1126 |
|
1127 void GenCollectedHeap::prepare_for_compaction() { |
1121 void GenCollectedHeap::prepare_for_compaction() { |
1128 guarantee(_n_gens = 2, "Wrong number of generations"); |
|
1129 // Start by compacting into same gen. |
1122 // Start by compacting into same gen. |
1130 CompactPoint cp(_old_gen); |
1123 CompactPoint cp(_old_gen); |
1131 _old_gen->prepare_for_compaction(&cp); |
1124 _old_gen->prepare_for_compaction(&cp); |
1132 _young_gen->prepare_for_compaction(&cp); |
1125 _young_gen->prepare_for_compaction(&cp); |
1133 } |
1126 } |