mirror of
https://github.com/openjdk/jdk.git
synced 2025-09-21 19:44:41 +02:00
6964458: Reimplement class meta-data storage to use native memory
Remove PermGen, allocate meta-data in metaspace linked to class loaders, rewrite GC walking, rewrite and rename metadata to be C++ classes Co-authored-by: Stefan Karlsson <stefan.karlsson@oracle.com> Co-authored-by: Mikael Gerdin <mikael.gerdin@oracle.com> Co-authored-by: Tom Rodriguez <tom.rodriguez@oracle.com> Reviewed-by: jmasa, stefank, never, coleenp, kvn, brutisso, mgerdin, dholmes, jrose, twisti, roland
This commit is contained in:
parent
36eee7c8c8
commit
5c58d27aac
853 changed files with 26124 additions and 82956 deletions
|
@ -78,14 +78,13 @@ void GenMarkSweep::invoke_at_safepoint(int level, ReferenceProcessor* rp,
|
|||
|
||||
TraceTime t1(GCCauseString("Full GC", gch->gc_cause()), PrintGC && !PrintGCDetails, true, gclog_or_tty);
|
||||
|
||||
// When collecting the permanent generation methodOops may be moving,
|
||||
// When collecting the permanent generation Method*s may be moving,
|
||||
// so we either have to flush all bcp data or convert it into bci.
|
||||
CodeCache::gc_prologue();
|
||||
Threads::gc_prologue();
|
||||
|
||||
// Increment the invocation count for the permanent generation, since it is
|
||||
// implicitly collected whenever we do a full mark sweep collection.
|
||||
gch->perm_gen()->stat_record()->invocations++;
|
||||
// Increment the invocation count
|
||||
_total_invocations++;
|
||||
|
||||
// Capture heap size before collection for printing.
|
||||
size_t gch_prev_used = gch->used();
|
||||
|
@ -98,7 +97,7 @@ void GenMarkSweep::invoke_at_safepoint(int level, ReferenceProcessor* rp,
|
|||
// Capture used regions for each generation that will be
|
||||
// subject to collection, so that card table adjustments can
|
||||
// be made intelligently (see clear / invalidate further below).
|
||||
gch->save_used_regions(level, true /* perm */);
|
||||
gch->save_used_regions(level);
|
||||
|
||||
allocate_stacks();
|
||||
|
||||
|
@ -149,14 +148,13 @@ void GenMarkSweep::invoke_at_safepoint(int level, ReferenceProcessor* rp,
|
|||
if (all_empty) {
|
||||
// We've evacuated all generations below us.
|
||||
Generation* g = gch->get_gen(level);
|
||||
rs->clear_into_younger(g, true /* perm */);
|
||||
rs->clear_into_younger(g);
|
||||
} else {
|
||||
// Invalidate the cards corresponding to the currently used
|
||||
// region and clear those corresponding to the evacuated region
|
||||
// of all generations just collected (i.e. level and younger).
|
||||
rs->invalidate_or_clear(gch->get_gen(level),
|
||||
true /* younger */,
|
||||
true /* perm */);
|
||||
true /* younger */);
|
||||
}
|
||||
|
||||
Threads::gc_epilogue();
|
||||
|
@ -238,8 +236,6 @@ void GenMarkSweep::deallocate_stacks() {
|
|||
_preserved_oop_stack.clear(true);
|
||||
_marking_stack.clear();
|
||||
_objarray_stack.clear(true);
|
||||
_revisit_klass_stack.clear(true);
|
||||
_revisit_mdo_stack.clear(true);
|
||||
|
||||
#ifdef VALIDATE_MARK_SWEEP
|
||||
if (ValidateMarkSweep) {
|
||||
|
@ -261,7 +257,7 @@ void GenMarkSweep::mark_sweep_phase1(int level,
|
|||
TraceTime tm("phase 1", PrintGC && Verbose, true, gclog_or_tty);
|
||||
trace(" 1");
|
||||
|
||||
VALIDATE_MARK_SWEEP_ONLY(reset_live_oop_tracking(false));
|
||||
VALIDATE_MARK_SWEEP_ONLY(reset_live_oop_tracking());
|
||||
|
||||
GenCollectedHeap* gch = GenCollectedHeap::heap();
|
||||
|
||||
|
@ -271,14 +267,18 @@ void GenMarkSweep::mark_sweep_phase1(int level,
|
|||
// are run.
|
||||
follow_root_closure.set_orig_generation(gch->get_gen(level));
|
||||
|
||||
// Need new claim bits before marking starts.
|
||||
ClassLoaderDataGraph::clear_claimed_marks();
|
||||
|
||||
gch->gen_process_strong_roots(level,
|
||||
false, // Younger gens are not roots.
|
||||
true, // activate StrongRootsScope
|
||||
true, // Collecting permanent generation.
|
||||
false, // not scavenging
|
||||
SharedHeap::SO_SystemClasses,
|
||||
&follow_root_closure,
|
||||
true, // walk code active on stacks
|
||||
&follow_root_closure);
|
||||
&follow_root_closure,
|
||||
&follow_klass_closure);
|
||||
|
||||
// Process reference objects found during marking
|
||||
{
|
||||
|
@ -295,11 +295,7 @@ void GenMarkSweep::mark_sweep_phase1(int level,
|
|||
follow_stack(); // Flush marking stack
|
||||
|
||||
// Update subklass/sibling/implementor links of live klasses
|
||||
follow_weak_klass_links();
|
||||
assert(_marking_stack.is_empty(), "just drained");
|
||||
|
||||
// Visit memoized MDO's and clear any unmarked weak refs
|
||||
follow_mdo_weak_refs();
|
||||
Klass::clean_weak_klass_links(&is_alive);
|
||||
assert(_marking_stack.is_empty(), "just drained");
|
||||
|
||||
// Visit interned string tables and delete unmarked oops
|
||||
|
@ -316,28 +312,23 @@ void GenMarkSweep::mark_sweep_phase2() {
|
|||
|
||||
// It is imperative that we traverse perm_gen LAST. If dead space is
|
||||
// allowed a range of dead object may get overwritten by a dead int
|
||||
// array. If perm_gen is not traversed last a klassOop may get
|
||||
// array. If perm_gen is not traversed last a Klass* may get
|
||||
// overwritten. This is fine since it is dead, but if the class has dead
|
||||
// instances we have to skip them, and in order to find their size we
|
||||
// need the klassOop!
|
||||
// need the Klass*!
|
||||
//
|
||||
// It is not required that we traverse spaces in the same order in
|
||||
// phase2, phase3 and phase4, but the ValidateMarkSweep live oops
|
||||
// tracking expects us to do so. See comment under phase4.
|
||||
|
||||
GenCollectedHeap* gch = GenCollectedHeap::heap();
|
||||
Generation* pg = gch->perm_gen();
|
||||
|
||||
TraceTime tm("phase 2", PrintGC && Verbose, true, gclog_or_tty);
|
||||
trace("2");
|
||||
|
||||
VALIDATE_MARK_SWEEP_ONLY(reset_live_oop_tracking(false));
|
||||
VALIDATE_MARK_SWEEP_ONLY(reset_live_oop_tracking());
|
||||
|
||||
gch->prepare_for_compaction();
|
||||
|
||||
VALIDATE_MARK_SWEEP_ONLY(_live_oops_index_at_perm = _live_oops_index);
|
||||
CompactPoint perm_cp(pg, NULL, NULL);
|
||||
pg->prepare_for_compaction(&perm_cp);
|
||||
}
|
||||
|
||||
class GenAdjustPointersClosure: public GenCollectedHeap::GenClosure {
|
||||
|
@ -349,16 +340,15 @@ public:
|
|||
|
||||
void GenMarkSweep::mark_sweep_phase3(int level) {
|
||||
GenCollectedHeap* gch = GenCollectedHeap::heap();
|
||||
Generation* pg = gch->perm_gen();
|
||||
|
||||
// Adjust the pointers to reflect the new locations
|
||||
TraceTime tm("phase 3", PrintGC && Verbose, true, gclog_or_tty);
|
||||
trace("3");
|
||||
|
||||
VALIDATE_MARK_SWEEP_ONLY(reset_live_oop_tracking(false));
|
||||
// Need new claim bits for the pointer adjustment tracing.
|
||||
ClassLoaderDataGraph::clear_claimed_marks();
|
||||
|
||||
// Needs to be done before the system dictionary is adjusted.
|
||||
pg->pre_adjust_pointers();
|
||||
VALIDATE_MARK_SWEEP_ONLY(reset_live_oop_tracking());
|
||||
|
||||
// Because the two closures below are created statically, cannot
|
||||
// use OopsInGenClosure constructor which takes a generation,
|
||||
|
@ -370,11 +360,12 @@ void GenMarkSweep::mark_sweep_phase3(int level) {
|
|||
gch->gen_process_strong_roots(level,
|
||||
false, // Younger gens are not roots.
|
||||
true, // activate StrongRootsScope
|
||||
true, // Collecting permanent generation.
|
||||
false, // not scavenging
|
||||
SharedHeap::SO_AllClasses,
|
||||
&adjust_root_pointer_closure,
|
||||
false, // do not walk code
|
||||
&adjust_root_pointer_closure);
|
||||
&adjust_root_pointer_closure,
|
||||
&adjust_klass_closure);
|
||||
|
||||
// Now adjust pointers in remaining weak roots. (All of which should
|
||||
// have been cleared if they pointed to non-surviving objects.)
|
||||
|
@ -387,7 +378,6 @@ void GenMarkSweep::mark_sweep_phase3(int level) {
|
|||
adjust_marks();
|
||||
GenAdjustPointersClosure blk;
|
||||
gch->generation_iterate(&blk, true);
|
||||
pg->adjust_pointers();
|
||||
}
|
||||
|
||||
class GenCompactClosure: public GenCollectedHeap::GenClosure {
|
||||
|
@ -402,7 +392,7 @@ void GenMarkSweep::mark_sweep_phase4() {
|
|||
|
||||
// It is imperative that we traverse perm_gen first in phase4. All
|
||||
// classes must be allocated earlier than their instances, and traversing
|
||||
// perm_gen first makes sure that all klassOops have moved to their new
|
||||
// perm_gen first makes sure that all Klass*s have moved to their new
|
||||
// location before any instance does a dispatch through it's klass!
|
||||
|
||||
// The ValidateMarkSweep live oops tracking expects us to traverse spaces
|
||||
|
@ -410,21 +400,14 @@ void GenMarkSweep::mark_sweep_phase4() {
|
|||
// here (perm_gen first rather than last), so we tell the validate code
|
||||
// to use a higher index (saved from phase2) when verifying perm_gen.
|
||||
GenCollectedHeap* gch = GenCollectedHeap::heap();
|
||||
Generation* pg = gch->perm_gen();
|
||||
|
||||
TraceTime tm("phase 4", PrintGC && Verbose, true, gclog_or_tty);
|
||||
trace("4");
|
||||
|
||||
VALIDATE_MARK_SWEEP_ONLY(reset_live_oop_tracking(true));
|
||||
|
||||
pg->compact();
|
||||
|
||||
VALIDATE_MARK_SWEEP_ONLY(reset_live_oop_tracking(false));
|
||||
VALIDATE_MARK_SWEEP_ONLY(reset_live_oop_tracking());
|
||||
|
||||
GenCompactClosure blk;
|
||||
gch->generation_iterate(&blk, true);
|
||||
|
||||
VALIDATE_MARK_SWEEP_ONLY(compaction_complete());
|
||||
|
||||
pg->post_compact(); // Shared spaces verification.
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue