提交 5c7ada2a 编写于 作者: J johnc

Merge

...@@ -239,7 +239,7 @@ TreeList<Chunk_t, FreeList_t>* TreeList<Chunk_t, FreeList_t>::remove_chunk_repla ...@@ -239,7 +239,7 @@ TreeList<Chunk_t, FreeList_t>* TreeList<Chunk_t, FreeList_t>::remove_chunk_repla
} else { } else {
if (nextTC == NULL) { if (nextTC == NULL) {
// Removing chunk at tail of list // Removing chunk at tail of list
link_tail(prevFC); this->link_tail(prevFC);
} }
// Chunk is interior to the list // Chunk is interior to the list
prevFC->link_after(nextTC); prevFC->link_after(nextTC);
...@@ -296,7 +296,7 @@ void TreeList<Chunk_t, FreeList_t>::return_chunk_at_tail(TreeChunk<Chunk_t, Free ...@@ -296,7 +296,7 @@ void TreeList<Chunk_t, FreeList_t>::return_chunk_at_tail(TreeChunk<Chunk_t, Free
Chunk_t* fc = tail(); Chunk_t* fc = tail();
fc->link_after(chunk); fc->link_after(chunk);
link_tail(chunk); this->link_tail(chunk);
assert(!tail() || size() == tail()->size(), "Wrong sized chunk in list"); assert(!tail() || size() == tail()->size(), "Wrong sized chunk in list");
FreeList_t<Chunk_t>::increment_count(); FreeList_t<Chunk_t>::increment_count();
...@@ -323,7 +323,7 @@ void TreeList<Chunk_t, FreeList_t>::return_chunk_at_head(TreeChunk<Chunk_t, Free ...@@ -323,7 +323,7 @@ void TreeList<Chunk_t, FreeList_t>::return_chunk_at_head(TreeChunk<Chunk_t, Free
chunk->link_after(fc); chunk->link_after(fc);
} else { } else {
assert(tail() == NULL, "List is inconsistent"); assert(tail() == NULL, "List is inconsistent");
link_tail(chunk); this->link_tail(chunk);
} }
head()->link_after(chunk); head()->link_after(chunk);
assert(!head() || size() == head()->size(), "Wrong sized chunk in list"); assert(!head() || size() == head()->size(), "Wrong sized chunk in list");
...@@ -940,7 +940,7 @@ class AscendTreeCensusClosure : public TreeCensusClosure<Chunk_t, FreeList_t> { ...@@ -940,7 +940,7 @@ class AscendTreeCensusClosure : public TreeCensusClosure<Chunk_t, FreeList_t> {
void do_tree(TreeList<Chunk_t, FreeList_t>* tl) { void do_tree(TreeList<Chunk_t, FreeList_t>* tl) {
if (tl != NULL) { if (tl != NULL) {
do_tree(tl->left()); do_tree(tl->left());
do_list(tl); this->do_list(tl);
do_tree(tl->right()); do_tree(tl->right());
} }
} }
...@@ -952,7 +952,7 @@ class DescendTreeCensusClosure : public TreeCensusClosure<Chunk_t, FreeList_t> { ...@@ -952,7 +952,7 @@ class DescendTreeCensusClosure : public TreeCensusClosure<Chunk_t, FreeList_t> {
void do_tree(TreeList<Chunk_t, FreeList_t>* tl) { void do_tree(TreeList<Chunk_t, FreeList_t>* tl) {
if (tl != NULL) { if (tl != NULL) {
do_tree(tl->right()); do_tree(tl->right());
do_list(tl); this->do_list(tl);
do_tree(tl->left()); do_tree(tl->left());
} }
} }
...@@ -1022,7 +1022,7 @@ class DescendTreeSearchClosure : public TreeSearchClosure<Chunk_t, FreeList_t> { ...@@ -1022,7 +1022,7 @@ class DescendTreeSearchClosure : public TreeSearchClosure<Chunk_t, FreeList_t> {
bool do_tree(TreeList<Chunk_t, FreeList_t>* tl) { bool do_tree(TreeList<Chunk_t, FreeList_t>* tl) {
if (tl != NULL) { if (tl != NULL) {
if (do_tree(tl->right())) return true; if (do_tree(tl->right())) return true;
if (do_list(tl)) return true; if (this->do_list(tl)) return true;
if (do_tree(tl->left())) return true; if (do_tree(tl->left())) return true;
} }
return false; return false;
......
...@@ -42,6 +42,10 @@ ...@@ -42,6 +42,10 @@
typedef BinaryTreeDictionary<Metablock, FreeList> BlockTreeDictionary; typedef BinaryTreeDictionary<Metablock, FreeList> BlockTreeDictionary;
typedef BinaryTreeDictionary<Metachunk, FreeList> ChunkTreeDictionary; typedef BinaryTreeDictionary<Metachunk, FreeList> ChunkTreeDictionary;
// Define this macro to enable slow integrity checking of
// the free chunk lists
const bool metaspace_slow_verify = false;
// Parameters for stress mode testing // Parameters for stress mode testing
const uint metadata_deallocate_a_lot_block = 10; const uint metadata_deallocate_a_lot_block = 10;
...@@ -161,7 +165,17 @@ class ChunkManager VALUE_OBJ_CLASS_SPEC { ...@@ -161,7 +165,17 @@ class ChunkManager VALUE_OBJ_CLASS_SPEC {
size_t sum_free_chunks_count(); size_t sum_free_chunks_count();
void locked_verify_free_chunks_total(); void locked_verify_free_chunks_total();
void slow_locked_verify_free_chunks_total() {
if (metaspace_slow_verify) {
locked_verify_free_chunks_total();
}
}
void locked_verify_free_chunks_count(); void locked_verify_free_chunks_count();
void slow_locked_verify_free_chunks_count() {
if (metaspace_slow_verify) {
locked_verify_free_chunks_count();
}
}
void verify_free_chunks_count(); void verify_free_chunks_count();
public: public:
...@@ -201,7 +215,17 @@ class ChunkManager VALUE_OBJ_CLASS_SPEC { ...@@ -201,7 +215,17 @@ class ChunkManager VALUE_OBJ_CLASS_SPEC {
// Debug support // Debug support
void verify(); void verify();
void slow_verify() {
if (metaspace_slow_verify) {
verify();
}
}
void locked_verify(); void locked_verify();
void slow_locked_verify() {
if (metaspace_slow_verify) {
locked_verify();
}
}
void verify_free_chunks_total(); void verify_free_chunks_total();
void locked_print_free_chunks(outputStream* st); void locked_print_free_chunks(outputStream* st);
...@@ -1507,7 +1531,7 @@ size_t ChunkManager::free_chunks_total() { ...@@ -1507,7 +1531,7 @@ size_t ChunkManager::free_chunks_total() {
if (!UseConcMarkSweepGC && !SpaceManager::expand_lock()->is_locked()) { if (!UseConcMarkSweepGC && !SpaceManager::expand_lock()->is_locked()) {
MutexLockerEx cl(SpaceManager::expand_lock(), MutexLockerEx cl(SpaceManager::expand_lock(),
Mutex::_no_safepoint_check_flag); Mutex::_no_safepoint_check_flag);
locked_verify_free_chunks_total(); slow_locked_verify_free_chunks_total();
} }
#endif #endif
return _free_chunks_total; return _free_chunks_total;
...@@ -1524,10 +1548,10 @@ size_t ChunkManager::free_chunks_count() { ...@@ -1524,10 +1548,10 @@ size_t ChunkManager::free_chunks_count() {
Mutex::_no_safepoint_check_flag); Mutex::_no_safepoint_check_flag);
// This lock is only needed in debug because the verification // This lock is only needed in debug because the verification
// of the _free_chunks_totals walks the list of free chunks // of the _free_chunks_totals walks the list of free chunks
locked_verify_free_chunks_count(); slow_locked_verify_free_chunks_count();
} }
#endif #endif
return _free_chunks_count; return _free_chunks_count;
} }
void ChunkManager::locked_verify_free_chunks_total() { void ChunkManager::locked_verify_free_chunks_total() {
...@@ -1561,14 +1585,9 @@ void ChunkManager::verify_free_chunks_count() { ...@@ -1561,14 +1585,9 @@ void ChunkManager::verify_free_chunks_count() {
} }
void ChunkManager::verify() { void ChunkManager::verify() {
#ifdef ASSERT MutexLockerEx cl(SpaceManager::expand_lock(),
if (!UseConcMarkSweepGC) { Mutex::_no_safepoint_check_flag);
MutexLockerEx cl(SpaceManager::expand_lock(), locked_verify();
Mutex::_no_safepoint_check_flag);
locked_verify_free_chunks_total();
locked_verify_free_chunks_count();
}
#endif
} }
void ChunkManager::locked_verify() { void ChunkManager::locked_verify() {
...@@ -1642,7 +1661,7 @@ void ChunkManager::free_chunks_put(Metachunk* chunk) { ...@@ -1642,7 +1661,7 @@ void ChunkManager::free_chunks_put(Metachunk* chunk) {
free_list->set_head(chunk); free_list->set_head(chunk);
// chunk is being returned to the chunk free list // chunk is being returned to the chunk free list
inc_free_chunks_total(chunk->capacity_word_size()); inc_free_chunks_total(chunk->capacity_word_size());
locked_verify(); slow_locked_verify();
} }
void ChunkManager::chunk_freelist_deallocate(Metachunk* chunk) { void ChunkManager::chunk_freelist_deallocate(Metachunk* chunk) {
...@@ -1650,8 +1669,8 @@ void ChunkManager::chunk_freelist_deallocate(Metachunk* chunk) { ...@@ -1650,8 +1669,8 @@ void ChunkManager::chunk_freelist_deallocate(Metachunk* chunk) {
// manangement code for a Metaspace and does not hold the // manangement code for a Metaspace and does not hold the
// lock. // lock.
assert(chunk != NULL, "Deallocating NULL"); assert(chunk != NULL, "Deallocating NULL");
// MutexLockerEx fcl(SpaceManager::expand_lock(), Mutex::_no_safepoint_check_flag); assert_lock_strong(SpaceManager::expand_lock());
locked_verify(); slow_locked_verify();
if (TraceMetadataChunkAllocation) { if (TraceMetadataChunkAllocation) {
tty->print_cr("ChunkManager::chunk_freelist_deallocate: chunk " tty->print_cr("ChunkManager::chunk_freelist_deallocate: chunk "
PTR_FORMAT " size " SIZE_FORMAT, PTR_FORMAT " size " SIZE_FORMAT,
...@@ -1663,7 +1682,7 @@ void ChunkManager::chunk_freelist_deallocate(Metachunk* chunk) { ...@@ -1663,7 +1682,7 @@ void ChunkManager::chunk_freelist_deallocate(Metachunk* chunk) {
Metachunk* ChunkManager::free_chunks_get(size_t word_size) { Metachunk* ChunkManager::free_chunks_get(size_t word_size) {
assert_lock_strong(SpaceManager::expand_lock()); assert_lock_strong(SpaceManager::expand_lock());
locked_verify(); slow_locked_verify();
Metachunk* chunk = NULL; Metachunk* chunk = NULL;
if (!SpaceManager::is_humongous(word_size)) { if (!SpaceManager::is_humongous(word_size)) {
...@@ -1708,13 +1727,13 @@ Metachunk* ChunkManager::free_chunks_get(size_t word_size) { ...@@ -1708,13 +1727,13 @@ Metachunk* ChunkManager::free_chunks_get(size_t word_size) {
#endif #endif
} }
} }
locked_verify(); slow_locked_verify();
return chunk; return chunk;
} }
Metachunk* ChunkManager::chunk_freelist_allocate(size_t word_size) { Metachunk* ChunkManager::chunk_freelist_allocate(size_t word_size) {
assert_lock_strong(SpaceManager::expand_lock()); assert_lock_strong(SpaceManager::expand_lock());
locked_verify(); slow_locked_verify();
// Take from the beginning of the list // Take from the beginning of the list
Metachunk* chunk = free_chunks_get(word_size); Metachunk* chunk = free_chunks_get(word_size);
...@@ -1959,7 +1978,7 @@ SpaceManager::~SpaceManager() { ...@@ -1959,7 +1978,7 @@ SpaceManager::~SpaceManager() {
ChunkManager* chunk_manager = vs_list()->chunk_manager(); ChunkManager* chunk_manager = vs_list()->chunk_manager();
chunk_manager->locked_verify(); chunk_manager->slow_locked_verify();
if (TraceMetadataChunkAllocation && Verbose) { if (TraceMetadataChunkAllocation && Verbose) {
gclog_or_tty->print_cr("~SpaceManager(): " PTR_FORMAT, this); gclog_or_tty->print_cr("~SpaceManager(): " PTR_FORMAT, this);
...@@ -2015,7 +2034,7 @@ SpaceManager::~SpaceManager() { ...@@ -2015,7 +2034,7 @@ SpaceManager::~SpaceManager() {
humongous_chunks = next_humongous_chunks; humongous_chunks = next_humongous_chunks;
} }
set_chunks_in_use(HumongousIndex, NULL); set_chunks_in_use(HumongousIndex, NULL);
chunk_manager->locked_verify(); chunk_manager->slow_locked_verify();
} }
void SpaceManager::deallocate(MetaWord* p, size_t word_size) { void SpaceManager::deallocate(MetaWord* p, size_t word_size) {
...@@ -2330,8 +2349,7 @@ size_t MetaspaceAux::free_chunks_total(Metaspace::MetadataType mdtype) { ...@@ -2330,8 +2349,7 @@ size_t MetaspaceAux::free_chunks_total(Metaspace::MetadataType mdtype) {
ChunkManager* chunk = (mdtype == Metaspace::ClassType) ? ChunkManager* chunk = (mdtype == Metaspace::ClassType) ?
Metaspace::class_space_list()->chunk_manager() : Metaspace::class_space_list()->chunk_manager() :
Metaspace::space_list()->chunk_manager(); Metaspace::space_list()->chunk_manager();
chunk->slow_verify();
chunk->verify_free_chunks_total();
return chunk->free_chunks_total(); return chunk->free_chunks_total();
} }
...@@ -2435,6 +2453,11 @@ void MetaspaceAux::dump(outputStream* out) { ...@@ -2435,6 +2453,11 @@ void MetaspaceAux::dump(outputStream* out) {
print_waste(out); print_waste(out);
} }
void MetaspaceAux::verify_free_chunks() {
Metaspace::space_list()->chunk_manager()->verify();
Metaspace::class_space_list()->chunk_manager()->verify();
}
// Metaspace methods // Metaspace methods
size_t Metaspace::_first_chunk_word_size = 0; size_t Metaspace::_first_chunk_word_size = 0;
......
...@@ -189,6 +189,7 @@ class MetaspaceAux : AllStatic { ...@@ -189,6 +189,7 @@ class MetaspaceAux : AllStatic {
static void print_waste(outputStream* out); static void print_waste(outputStream* out);
static void dump(outputStream* out); static void dump(outputStream* out);
static void verify_free_chunks();
}; };
// Metaspace are deallocated when their class loader are GC'ed. // Metaspace are deallocated when their class loader are GC'ed.
......
...@@ -1304,6 +1304,8 @@ void Universe::verify(bool silent, VerifyOption option) { ...@@ -1304,6 +1304,8 @@ void Universe::verify(bool silent, VerifyOption option) {
if (!silent) gclog_or_tty->print("cldg "); if (!silent) gclog_or_tty->print("cldg ");
ClassLoaderDataGraph::verify(); ClassLoaderDataGraph::verify();
#endif #endif
if (!silent) gclog_or_tty->print("metaspace chunks ");
MetaspaceAux::verify_free_chunks();
if (!silent) gclog_or_tty->print("hand "); if (!silent) gclog_or_tty->print("hand ");
JNIHandles::verify(); JNIHandles::verify();
if (!silent) gclog_or_tty->print("C-heap "); if (!silent) gclog_or_tty->print("C-heap ");
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册