--- old/src/share/vm/gc/g1/g1CollectedHeap.cpp 2015-06-06 02:21:43.000000000 +0200 +++ new/src/share/vm/gc/g1/g1CollectedHeap.cpp 2015-06-06 02:21:43.000000000 +0200 @@ -4373,7 +4373,7 @@ // We also need to mark copied objects. strong_root_cl = &scan_mark_root_cl; strong_cld_cl = &scan_mark_cld_cl; - if (ClassUnloadingWithConcurrentMark) { + if (ClassUnloading && ClassUnloadingWithConcurrentMark) { weak_root_cl = &scan_mark_weak_root_cl; weak_cld_cl = &scan_mark_weak_cld_cl; trace_metadata = true; @@ -4706,12 +4706,14 @@ public: void clean_klass(InstanceKlass* ik) { - ik->clean_implementors_list(_is_alive); - ik->clean_method_data(_is_alive); - - // G1 specific cleanup work that has - // been moved here to be done in parallel. - ik->clean_dependent_nmethods(); + if (ClassUnloading) { + ik->clean_implementors_list(_is_alive); + ik->clean_method_data(_is_alive); + + // G1 specific cleanup work that has + // been moved here to be done in parallel. + ik->clean_dependent_nmethods(); + } } void work() { --- old/src/share/vm/gc/g1/g1MarkSweep.cpp 2015-06-06 02:21:44.000000000 +0200 +++ new/src/share/vm/gc/g1/g1MarkSweep.cpp 2015-06-06 02:21:44.000000000 +0200 @@ -151,14 +151,16 @@ // This is the point where the entire marking should have completed. assert(GenMarkSweep::_marking_stack.is_empty(), "Marking should have completed"); - // Unload classes and purge the SystemDictionary. - bool purged_class = SystemDictionary::do_unloading(&GenMarkSweep::is_alive); + if (ClassUnloading) { + // Unload classes and purge the SystemDictionary. + bool purged_class = SystemDictionary::do_unloading(&GenMarkSweep::is_alive); - // Unload nmethods. - CodeCache::do_unloading(&GenMarkSweep::is_alive, purged_class); + // Unload nmethods. + CodeCache::do_unloading(&GenMarkSweep::is_alive, purged_class); - // Prune dead klasses from subklass/sibling/implementor lists. - Klass::clean_weak_klass_links(&GenMarkSweep::is_alive); + // Prune dead klasses from subklass/sibling/implementor lists. + Klass::clean_weak_klass_links(&GenMarkSweep::is_alive); + } // Delete entries for dead interned string and clean up unreferenced symbols in symbol table. g1h->unlink_string_and_symbol_table(&GenMarkSweep::is_alive); --- old/src/share/vm/gc/g1/g1RootProcessor.cpp 2015-06-06 02:21:44.000000000 +0200 +++ new/src/share/vm/gc/g1/g1RootProcessor.cpp 2015-06-06 02:21:44.000000000 +0200 @@ -90,7 +90,7 @@ void G1RootProcessor::worker_has_discovered_all_strong_classes() { - assert(ClassUnloadingWithConcurrentMark, "Currently only needed when doing G1 Class Unloading"); + assert(ClassUnloading && ClassUnloadingWithConcurrentMark, "Currently only needed when doing G1 Class Unloading"); uint new_value = (uint)Atomic::add(1, &_n_workers_discovered_strong_classes); if (new_value == n_workers()) { @@ -101,7 +101,7 @@ } void G1RootProcessor::wait_until_all_strong_classes_discovered() { - assert(ClassUnloadingWithConcurrentMark, "Currently only needed when doing G1 Class Unloading"); + assert(ClassUnloading && ClassUnloadingWithConcurrentMark, "Currently only needed when doing G1 Class Unloading"); if ((uint)_n_workers_discovered_strong_classes != n_workers()) { MonitorLockerEx ml(&_lock, Mutex::_no_safepoint_check_flag); @@ -211,7 +211,7 @@ CLDClosure* clds, CodeBlobClosure* blobs) { - process_java_roots(oops, clds, clds, NULL, blobs, NULL, 0); + process_java_roots(oops, clds, clds, ClassUnloading ? NULL : clds, blobs, NULL, 0); process_vm_roots(oops, NULL, NULL, 0); _process_strong_tasks->all_tasks_completed(n_workers()); @@ -238,7 +238,7 @@ CodeBlobClosure* strong_code, G1GCPhaseTimes* phase_times, uint worker_i) { - assert(thread_stack_clds == NULL || weak_clds == NULL, "There is overlap between those, only one may be set"); + assert(thread_stack_clds == NULL || weak_clds == NULL || !ClassUnloading, "There is overlap between those, only one may be set"); // Iterating over the CLDG and the Threads are done early to allow us to // first process the strong CLDs and nmethods and then, after a barrier, // let the thread process the weak CLDs and nmethods. --- old/src/share/vm/gc/g1/heapRegion.inline.hpp 2015-06-06 02:21:45.000000000 +0200 +++ new/src/share/vm/gc/g1/heapRegion.inline.hpp 2015-06-06 02:21:45.000000000 +0200 @@ -95,7 +95,7 @@ inline bool HeapRegion::block_is_obj(const HeapWord* p) const { G1CollectedHeap* g1h = G1CollectedHeap::heap(); - if (ClassUnloadingWithConcurrentMark) { + if (ClassUnloading && ClassUnloadingWithConcurrentMark) { return !g1h->is_obj_dead(oop(p), this); } return p < top(); @@ -111,7 +111,7 @@ return oop(addr)->size(); } - assert(ClassUnloadingWithConcurrentMark, + assert(ClassUnloading && ClassUnloadingWithConcurrentMark, err_msg("All blocks should be objects if G1 Class Unloading isn't used. " "HR: ["PTR_FORMAT", "PTR_FORMAT", "PTR_FORMAT") " "addr: " PTR_FORMAT,