--- old/src/hotspot/share/gc/g1/g1StringDedup.hpp 2018-05-28 11:50:27.139067439 -0400 +++ new/src/hotspot/share/gc/g1/g1StringDedup.hpp 2018-05-28 11:50:27.029067399 -0400 @@ -82,24 +82,43 @@ // http://openjdk.java.net/jeps/192 // +#include "gc/shared/stringdedup/stringDedup.hpp" #include "memory/allocation.hpp" #include "oops/oop.hpp" class OopClosure; class BoolObjectClosure; -class ThreadClosure; -class outputStream; -class G1StringDedupTable; -class G1StringDedupUnlinkOrOopsDoClosure; class G1GCPhaseTimes; +class G1StringDedupUnlinkOrOopsDoClosure; + +// +// Candidate selection +// +// An object is considered a deduplication candidate if all of the following +// statements are true: +// +// - The object is an instance of java.lang.String +// +// - The object is being evacuated from a young heap region +// +// - The object is being evacuated to a young/survivor heap region and the +// object's age is equal to the deduplication age threshold +// +// or +// +// The object is being evacuated to an old heap region and the object's age is +// less than the deduplication age threshold +// +// Once an string object has been promoted to an old region, or its age is higher +// than the deduplication age threshold, is will never become a candidate again. +// This approach avoids making the same object a candidate more than once. + // -// Main interface for interacting with string deduplication. +// G1 interface for interacting with string deduplication. // -class G1StringDedup : public AllStatic { +class G1StringDedup : public StringDedup { private: - // Single state for checking if both G1 and string deduplication is enabled. - static bool _enabled; // Candidate selection policies, returns true if the given object is // candidate for string deduplication. @@ -107,21 +126,9 @@ static bool is_candidate_from_evacuation(bool from_young, bool to_young, oop obj); public: - // Returns true if both G1 and string deduplication is enabled. - static bool is_enabled() { - return _enabled; - } - // Initialize string deduplication. static void initialize(); - // Stop the deduplication thread. - static void stop(); - - // Immediately deduplicates the given String object, bypassing the - // the deduplication queue. - static void deduplicate(oop java_string); - // Enqueues a deduplication candidate for later processing by the deduplication // thread. Before enqueuing, these functions apply the appropriate candidate // selection policy to filters out non-candidates. @@ -133,70 +140,28 @@ static void parallel_unlink(G1StringDedupUnlinkOrOopsDoClosure* unlink, uint worker_id); static void unlink_or_oops_do(BoolObjectClosure* is_alive, OopClosure* keep_alive, bool allow_resize_and_rehash, G1GCPhaseTimes* phase_times = NULL); - - static void threads_do(ThreadClosure* tc); - static void print_worker_threads_on(outputStream* st); - static void verify(); }; // // This closure encapsulates the state and the closures needed when scanning // the deduplication queue and table during the unlink_or_oops_do() operation. // A single instance of this closure is created and then shared by all worker -// threads participating in the scan. The _next_queue and _next_bucket fields -// provide a simple mechanism for GC workers to claim exclusive access to a -// queue or a table partition. +// threads participating in the scan. // -class G1StringDedupUnlinkOrOopsDoClosure : public StackObj { -private: - BoolObjectClosure* _is_alive; - OopClosure* _keep_alive; - G1StringDedupTable* _resized_table; - G1StringDedupTable* _rehashed_table; - size_t _next_queue; - size_t _next_bucket; - +class G1StringDedupUnlinkOrOopsDoClosure : public StringDedupUnlinkOrOopsDoClosure { public: G1StringDedupUnlinkOrOopsDoClosure(BoolObjectClosure* is_alive, OopClosure* keep_alive, - bool allow_resize_and_rehash); - ~G1StringDedupUnlinkOrOopsDoClosure(); - - bool is_resizing() { - return _resized_table != NULL; - } - - G1StringDedupTable* resized_table() { - return _resized_table; - } - - bool is_rehashing() { - return _rehashed_table != NULL; - } - - // Atomically claims the next available queue for exclusive access by - // the current thread. Returns the queue number of the claimed queue. - size_t claim_queue(); - - // Atomically claims the next available table partition for exclusive - // access by the current thread. Returns the table bucket number where - // the claimed partition starts. - size_t claim_table_partition(size_t partition_size); - - // Applies and returns the result from the is_alive closure, or - // returns true if no such closure was provided. - bool is_alive(oop o) { - if (_is_alive != NULL) { - return _is_alive->do_object_b(o); + bool allow_resize_and_rehash) : + StringDedupUnlinkOrOopsDoClosure(is_alive, keep_alive) { + if (G1StringDedup::is_enabled()) { + G1StringDedup::gc_prologue(allow_resize_and_rehash); + } } - return true; - } - - // Applies the keep_alive closure, or does nothing if no such - // closure was provided. - void keep_alive(oop* p) { - if (_keep_alive != NULL) { - _keep_alive->do_oop(p); + + ~G1StringDedupUnlinkOrOopsDoClosure() { + if (G1StringDedup::is_enabled()) { + G1StringDedup::gc_epilogue(); } } };