8223956: Make SymbolTable and StringTable AllStatic
authorcoleenp
Thu, 16 May 2019 07:09:17 -0400
changeset 54896 ea619918de95
parent 54895 4f1f939d8f5d
child 54897 2e5e9d31a6c5
8223956: Make SymbolTable and StringTable AllStatic Summary: Removed superfluous and confusing _the_table pointer. Reviewed-by: gziemski, rehn
src/hotspot/share/classfile/stringTable.cpp
src/hotspot/share/classfile/stringTable.hpp
src/hotspot/share/classfile/symbolTable.cpp
src/hotspot/share/classfile/symbolTable.hpp
src/hotspot/share/jfr/periodic/jfrPeriodic.cpp
src/hotspot/share/prims/resolvedMethodTable.cpp
src/hotspot/share/prims/resolvedMethodTable.hpp
--- a/src/hotspot/share/classfile/stringTable.cpp	Thu May 16 16:40:48 2019 +0530
+++ b/src/hotspot/share/classfile/stringTable.cpp	Thu May 16 07:09:17 2019 -0400
@@ -30,7 +30,6 @@
 #include "classfile/systemDictionary.hpp"
 #include "gc/shared/collectedHeap.hpp"
 #include "gc/shared/oopStorage.inline.hpp"
-#include "gc/shared/oopStorageParState.inline.hpp"
 #include "logging/log.hpp"
 #include "logging/logStream.hpp"
 #include "memory/allocation.inline.hpp"
@@ -79,9 +78,21 @@
 #endif
 
 // --------------------------------------------------------------------------
-StringTable* StringTable::_the_table = NULL;
-volatile bool StringTable::_alt_hash = false;
+
+typedef ConcurrentHashTable<WeakHandle<vm_string_table_data>,
+                            StringTableConfig, mtSymbol> StringTableHash;
+static StringTableHash* _local_table = NULL;
+
+volatile bool StringTable::_has_work = false;
+volatile bool StringTable::_needs_rehashing = false;
 
+volatile size_t StringTable::_uncleaned_items_count = 0;
+OopStorage* StringTable::_weak_handles = NULL;
+
+static size_t _current_size = 0;
+static volatile size_t _items_count = 0;
+
+volatile bool _alt_hash = false;
 static juint murmur_seed = 0;
 
 uintx hash_string(const jchar* s, int len, bool useAlt) {
@@ -107,7 +118,7 @@
     int length;
     jchar* chars = java_lang_String::as_unicode_string(val_oop, length, THREAD);
     if (chars != NULL) {
-      return hash_string(chars, length, StringTable::_alt_hash);
+      return hash_string(chars, length, _alt_hash);
     }
     vm_exit_out_of_memory(length, OOM_MALLOC_ERROR, "get hash from oop");
     return 0;
@@ -196,8 +207,7 @@
   return ret;
 }
 
-StringTable::StringTable() : _local_table(NULL), _current_size(0), _has_work(0),
-  _needs_rehashing(false), _weak_handles(NULL), _items_count(0), _uncleaned_items_count(0) {
+void StringTable::create_table() {
   _weak_handles = new OopStorage("StringTable weak",
                                  StringTableWeakAlloc_lock,
                                  StringTableWeakActive_lock);
@@ -208,33 +218,27 @@
   _local_table = new StringTableHash(start_size_log_2, END_SIZE, REHASH_LEN);
 }
 
-void StringTable::update_needs_rehash(bool rehash) {
-  if (rehash) {
-    _needs_rehashing = true;
-  }
-}
-
 size_t StringTable::item_added() {
-  return Atomic::add((size_t)1, &(the_table()->_items_count));
+  return Atomic::add((size_t)1, &_items_count);
 }
 
 size_t StringTable::add_items_to_clean(size_t ndead) {
-  size_t total = Atomic::add((size_t)ndead, &(the_table()->_uncleaned_items_count));
+  size_t total = Atomic::add((size_t)ndead, &_uncleaned_items_count);
   log_trace(stringtable)(
      "Uncleaned items:" SIZE_FORMAT " added: " SIZE_FORMAT " total:" SIZE_FORMAT,
-     the_table()->_uncleaned_items_count, ndead, total);
+     _uncleaned_items_count, ndead, total);
   return total;
 }
 
 void StringTable::item_removed() {
-  Atomic::add((size_t)-1, &(the_table()->_items_count));
+  Atomic::add((size_t)-1, &_items_count);
 }
 
-double StringTable::get_load_factor() const {
+double StringTable::get_load_factor() {
   return (double)_items_count/_current_size;
 }
 
-double StringTable::get_dead_factor() const {
+double StringTable::get_dead_factor() {
   return (double)_uncleaned_items_count/_current_size;
 }
 
@@ -244,7 +248,7 @@
 
 void StringTable::trigger_concurrent_work() {
   MutexLocker ml(Service_lock, Mutex::_no_safepoint_check_flag);
-  the_table()->_has_work = true;
+  _has_work = true;
   Service_lock->notify_all();
 }
 
@@ -258,14 +262,14 @@
 
 oop StringTable::lookup(const jchar* name, int len) {
   unsigned int hash = java_lang_String::hash_code(name, len);
-  oop string = StringTable::the_table()->lookup_shared(name, len, hash);
+  oop string = lookup_shared(name, len, hash);
   if (string != NULL) {
     return string;
   }
-  if (StringTable::_alt_hash) {
+  if (_alt_hash) {
     hash = hash_string(name, len, true);
   }
-  return StringTable::the_table()->do_lookup(name, len, hash);
+  return do_lookup(name, len, hash);
 }
 
 class StringTableGet : public StackObj {
@@ -329,19 +333,18 @@
 oop StringTable::intern(Handle string_or_null_h, const jchar* name, int len, TRAPS) {
   // shared table always uses java_lang_String::hash_code
   unsigned int hash = java_lang_String::hash_code(name, len);
-  oop found_string = StringTable::the_table()->lookup_shared(name, len, hash);
+  oop found_string = lookup_shared(name, len, hash);
   if (found_string != NULL) {
     return found_string;
   }
-  if (StringTable::_alt_hash) {
+  if (_alt_hash) {
     hash = hash_string(name, len, true);
   }
-  found_string = StringTable::the_table()->do_lookup(name, len, hash);
+  found_string = do_lookup(name, len, hash);
   if (found_string != NULL) {
     return found_string;
   }
-  return StringTable::the_table()->do_intern(string_or_null_h, name, len,
-                                             hash, CHECK_NULL);
+  return do_intern(string_or_null_h, name, len, hash, CHECK_NULL);
 }
 
 oop StringTable::do_intern(Handle string_or_null_h, const jchar* name,
@@ -384,15 +387,7 @@
 
 void StringTable::oops_do(OopClosure* f) {
   assert(f != NULL, "No closure");
-  StringTable::the_table()->_weak_handles->oops_do(f);
-}
-
-void StringTable::possibly_parallel_oops_do(
-   OopStorage::ParState<false /* concurrent */, false /* const */>*
-   _par_state_string, OopClosure* f)
-{
-  assert(f != NULL, "No closure");
-  _par_state_string->oops_do(f);
+  _weak_handles->oops_do(f);
 }
 
 // Concurrent work
@@ -480,7 +475,7 @@
   }
 }
 
-void StringTable::concurrent_work(JavaThread* jt) {
+void StringTable::do_concurrent_work(JavaThread* jt) {
   _has_work = false;
   double load_factor = get_load_factor();
   log_debug(stringtable, perf)("Concurrent work, live factor: %g", load_factor);
@@ -492,10 +487,6 @@
   }
 }
 
-void StringTable::do_concurrent_work(JavaThread* jt) {
-  StringTable::the_table()->concurrent_work(jt);
-}
-
 // Rehash
 bool StringTable::do_rehash() {
   if (!_local_table->is_safepoint_safe()) {
@@ -519,7 +510,7 @@
   return true;
 }
 
-void StringTable::try_rehash_table() {
+void StringTable::rehash_table() {
   static bool rehashed = false;
   log_debug(stringtable)("Table imbalanced, rehashing called.");
 
@@ -550,10 +541,6 @@
   _needs_rehashing = false;
 }
 
-void StringTable::rehash_table() {
-  StringTable::the_table()->try_rehash_table();
-}
-
 // Statistics
 static int literal_size(oop obj) {
   // NOTE: this would over-count if (pre-JDK8)
@@ -609,7 +596,7 @@
 void StringTable::verify() {
   Thread* thr = Thread::current();
   VerifyStrings vs;
-  if (!the_table()->_local_table->try_scan(thr, vs)) {
+  if (!_local_table->try_scan(thr, vs)) {
     log_info(stringtable)("verify unavailable at this moment");
   }
 }
@@ -642,10 +629,10 @@
   Thread* thr = Thread::current();
   GrowableArray<oop>* oops =
     new (ResourceObj::C_HEAP, mtInternal)
-      GrowableArray<oop>((int)the_table()->_current_size, true);
+      GrowableArray<oop>((int)_current_size, true);
 
   VerifyCompStrings vcs(oops);
-  if (!the_table()->_local_table->try_scan(thr, vcs)) {
+  if (!_local_table->try_scan(thr, vcs)) {
     log_info(stringtable)("verify unavailable at this moment");
   }
   delete oops;
@@ -692,13 +679,13 @@
 
 void StringTable::dump(outputStream* st, bool verbose) {
   if (!verbose) {
-    the_table()->print_table_statistics(st, "StringTable");
+    print_table_statistics(st, "StringTable");
   } else {
     Thread* thr = Thread::current();
     ResourceMark rm(thr);
     st->print_cr("VERSION: 1.1");
     PrintString ps(thr, st);
-    if (!the_table()->_local_table->try_scan(thr, ps)) {
+    if (!_local_table->try_scan(thr, ps)) {
       st->print_cr("dump unavailable at this moment");
     }
   }
@@ -785,15 +772,14 @@
   assert(HeapShared::is_heap_object_archiving_allowed(), "must be");
 
   CopyToArchive copy(writer);
-  StringTable::the_table()->_local_table->do_safepoint_scan(copy);
+  _local_table->do_safepoint_scan(copy);
 }
 
 void StringTable::write_to_archive() {
   assert(HeapShared::is_heap_object_archiving_allowed(), "must be");
 
   _shared_table.reset();
-  int num_buckets = CompactHashtableWriter::default_num_buckets(
-      StringTable::the_table()->_items_count);
+  int num_buckets = CompactHashtableWriter::default_num_buckets(_items_count);
   CompactHashtableWriter writer(num_buckets,
                                 &MetaspaceShared::stats()->string);
 
--- a/src/hotspot/share/classfile/stringTable.hpp	Thu May 16 16:40:48 2019 +0530
+++ b/src/hotspot/share/classfile/stringTable.hpp	Thu May 16 07:09:17 2019 -0400
@@ -26,21 +26,17 @@
 #define SHARE_CLASSFILE_STRINGTABLE_HPP
 
 #include "gc/shared/oopStorage.hpp"
-#include "gc/shared/oopStorageParState.hpp"
 #include "memory/allocation.hpp"
 #include "memory/padded.hpp"
 #include "oops/oop.hpp"
 #include "oops/weakHandle.hpp"
-#include "utilities/concurrentHashTable.hpp"
+#include "utilities/tableStatistics.hpp"
 
 class CompactHashtableWriter;
 class SerializeClosure;
 
 class StringTable;
 class StringTableConfig;
-typedef ConcurrentHashTable<WeakHandle<vm_string_table_data>,
-                            StringTableConfig, mtSymbol> StringTableHash;
-
 class StringTableCreateEntry;
 
 class StringTable : public CHeapObj<mtSymbol>{
@@ -49,94 +45,64 @@
   friend class StringTableConfig;
   friend class StringTableCreateEntry;
 
-private:
-  void grow(JavaThread* jt);
-  void clean_dead_entries(JavaThread* jt);
+  static volatile bool _has_work;
+  static volatile size_t _uncleaned_items_count;
 
-  // The string table
-  static StringTable* _the_table;
-  static volatile bool _alt_hash;
-
-private:
-
-  StringTableHash* _local_table;
-  size_t _current_size;
-  volatile bool _has_work;
   // Set if one bucket is out of balance due to hash algorithm deficiency
-  volatile bool _needs_rehashing;
+  static volatile bool _needs_rehashing;
 
-  OopStorage* _weak_handles;
+  static OopStorage* _weak_handles;
 
-  volatile size_t _items_count;
-  DEFINE_PAD_MINUS_SIZE(1, DEFAULT_CACHE_LINE_SIZE, sizeof(volatile size_t));
-  volatile size_t _uncleaned_items_count;
-  DEFINE_PAD_MINUS_SIZE(2, DEFAULT_CACHE_LINE_SIZE, sizeof(volatile size_t));
+  static void grow(JavaThread* jt);
+  static void clean_dead_entries(JavaThread* jt);
 
-  double get_load_factor() const;
-  double get_dead_factor() const;
+  static double get_load_factor();
+  static double get_dead_factor();
 
-  void check_concurrent_work();
-  void trigger_concurrent_work();
+  static void check_concurrent_work();
+  static void trigger_concurrent_work();
 
   static size_t item_added();
   static void item_removed();
-  size_t add_items_to_clean(size_t ndead);
-
-  StringTable();
+  static size_t add_items_to_clean(size_t ndead);
 
   static oop intern(Handle string_or_null_h, const jchar* name, int len, TRAPS);
-  oop do_intern(Handle string_or_null, const jchar* name, int len, uintx hash, TRAPS);
-  oop do_lookup(const jchar* name, int len, uintx hash);
+  static oop do_intern(Handle string_or_null, const jchar* name, int len, uintx hash, TRAPS);
+  static oop do_lookup(const jchar* name, int len, uintx hash);
 
-  void concurrent_work(JavaThread* jt);
-  void print_table_statistics(outputStream* st, const char* table_name);
+  static void print_table_statistics(outputStream* st, const char* table_name);
 
-  void try_rehash_table();
-  bool do_rehash();
-  inline void update_needs_rehash(bool rehash);
+  static bool do_rehash();
 
  public:
-  // The string table
-  static StringTable* the_table() { return _the_table; }
-  size_t table_size();
-  TableStatistics get_table_statistics();
+  static size_t table_size();
+  static TableStatistics get_table_statistics();
 
-  static OopStorage* weak_storage() { return the_table()->_weak_handles; }
+  static OopStorage* weak_storage() { return _weak_handles; }
 
-  static void create_table() {
-    assert(_the_table == NULL, "One string table allowed.");
-    _the_table = new StringTable();
-  }
+  static void create_table();
 
   static void do_concurrent_work(JavaThread* jt);
-  static bool has_work() { return the_table()->_has_work; }
+  static bool has_work() { return _has_work; }
 
   // GC support
 
   // Must be called before a parallel walk where strings might die.
-  static void reset_dead_counter() {
-    the_table()->_uncleaned_items_count = 0;
-  }
+  static void reset_dead_counter() { _uncleaned_items_count = 0; }
+
   // After the parallel walk this method must be called to trigger
   // cleaning. Note it might trigger a resize instead.
-  static void finish_dead_counter() {
-    the_table()->check_concurrent_work();
-  }
+  static void finish_dead_counter() { check_concurrent_work(); }
 
   // If GC uses ParState directly it should add the number of cleared
   // strings to this method.
-  static void inc_dead_counter(size_t ndead) {
-    the_table()->add_items_to_clean(ndead);
-  }
+  static void inc_dead_counter(size_t ndead) { add_items_to_clean(ndead); }
 
   // Serially invoke "f->do_oop" on the locations of all oops in the table.
+  // Used by JFR leak profiler.  TODO: it should find these oops through
+  // the WeakProcessor.
   static void oops_do(OopClosure* f);
 
-  // Possibly parallel versions of the above
-  static void possibly_parallel_oops_do(
-     OopStorage::ParState<false /* concurrent */, false /* const*/>* par_state_string,
-     OopClosure* f);
-
   // Probing
   static oop lookup(Symbol* symbol);
   static oop lookup(const jchar* chars, int length);
@@ -148,12 +114,16 @@
 
   // Rehash the string table if it gets out of balance
   static void rehash_table();
-  static bool needs_rehashing()
-    { return StringTable::the_table()->_needs_rehashing; }
+  static bool needs_rehashing() { return _needs_rehashing; }
+  static inline void update_needs_rehash(bool rehash) {
+    if (rehash) {
+      _needs_rehashing = true;
+    }
+  }
 
   // Sharing
  private:
-  oop lookup_shared(const jchar* name, int len, unsigned int hash) NOT_CDS_JAVA_HEAP_RETURN_(NULL);
+  static oop lookup_shared(const jchar* name, int len, unsigned int hash) NOT_CDS_JAVA_HEAP_RETURN_(NULL);
   static void copy_shared_string_table(CompactHashtableWriter* ch_table) NOT_CDS_JAVA_HEAP_RETURN;
  public:
   static oop create_archived_string(oop s, Thread* THREAD) NOT_CDS_JAVA_HEAP_RETURN_(NULL);
--- a/src/hotspot/share/classfile/symbolTable.cpp	Thu May 16 16:40:48 2019 +0530
+++ b/src/hotspot/share/classfile/symbolTable.cpp	Thu May 16 07:09:17 2019 -0400
@@ -70,9 +70,26 @@
 > _shared_table;
 
 // --------------------------------------------------------------------------
-SymbolTable* SymbolTable::_the_table = NULL;
-volatile bool SymbolTable::_alt_hash = false;
-volatile bool SymbolTable::_lookup_shared_first = false;
+
+typedef ConcurrentHashTable<Symbol*,
+                            SymbolTableConfig, mtSymbol> SymbolTableHash;
+static SymbolTableHash* _local_table = NULL;
+
+volatile bool SymbolTable::_has_work = 0;
+volatile bool SymbolTable::_needs_rehashing = false;
+
+// For statistics
+static size_t _symbols_removed = 0;
+static size_t _symbols_counted = 0;
+static size_t _current_size = 0;
+
+static volatile size_t _items_count = 0;
+static volatile bool   _has_items_to_clean = false;
+
+
+static volatile bool _alt_hash = false;
+static volatile bool _lookup_shared_first = false;
+
 // Static arena for symbols that are not deallocated
 Arena* SymbolTable::_arena = NULL;
 
@@ -104,7 +121,7 @@
     if (*is_dead) {
       return 0;
     } else {
-      return hash_symbol((const char*)value->bytes(), value->utf8_length(), SymbolTable::_alt_hash);
+      return hash_symbol((const char*)value->bytes(), value->utf8_length(), _alt_hash);
     }
   }
   // We use default allocation/deallocation but counted
@@ -136,16 +153,19 @@
   return ret;
 }
 
-SymbolTable::SymbolTable() :
-  _symbols_removed(0), _symbols_counted(0), _local_table(NULL),
-  _current_size(0), _has_work(0), _needs_rehashing(false),
-  _items_count(0), _has_items_to_clean(false) {
-
+void SymbolTable::create_table ()  {
   size_t start_size_log_2 = ceil_log2(SymbolTableSize);
   _current_size = ((size_t)1) << start_size_log_2;
   log_trace(symboltable)("Start size: " SIZE_FORMAT " (" SIZE_FORMAT ")",
                          _current_size, start_size_log_2);
   _local_table = new SymbolTableHash(start_size_log_2, END_SIZE, REHASH_LEN);
+
+  // Initialize the arena for global symbols, size passed in depends on CDS.
+  if (symbol_alloc_arena_size == 0) {
+    _arena = new (mtSymbol) Arena(mtSymbol);
+  } else {
+    _arena = new (mtSymbol) Arena(mtSymbol, symbol_alloc_arena_size);
+  }
 }
 
 void SymbolTable::delete_symbol(Symbol* sym) {
@@ -162,26 +182,20 @@
   }
 }
 
-void SymbolTable::update_needs_rehash(bool rehash) {
-  if (rehash) {
-    _needs_rehashing = true;
-  }
-}
-
 void SymbolTable::reset_has_items_to_clean() { Atomic::store(false, &_has_items_to_clean); }
 void SymbolTable::mark_has_items_to_clean()  { Atomic::store(true, &_has_items_to_clean); }
-bool SymbolTable::has_items_to_clean() const { return Atomic::load(&_has_items_to_clean); }
+bool SymbolTable::has_items_to_clean()       { return Atomic::load(&_has_items_to_clean); }
 
 void SymbolTable::item_added() {
-  Atomic::inc(&(SymbolTable::the_table()->_items_count));
+  Atomic::inc(&_items_count);
 }
 
 void SymbolTable::item_removed() {
-  Atomic::inc(&(SymbolTable::the_table()->_symbols_removed));
-  Atomic::dec(&(SymbolTable::the_table()->_items_count));
+  Atomic::inc(&(_symbols_removed));
+  Atomic::dec(&_items_count);
 }
 
-double SymbolTable::get_load_factor() const {
+double SymbolTable::get_load_factor() {
   return (double)_items_count/_current_size;
 }
 
@@ -191,7 +205,7 @@
 
 void SymbolTable::trigger_cleanup() {
   MutexLocker ml(Service_lock, Mutex::_no_safepoint_check_flag);
-  SymbolTable::the_table()->_has_work = true;
+  _has_work = true;
   Service_lock->notify_all();
 }
 
@@ -214,15 +228,6 @@
   return sym;
 }
 
-void SymbolTable::initialize_symbols(int arena_alloc_size) {
-  // Initialize the arena for global symbols, size passed in depends on CDS.
-  if (arena_alloc_size == 0) {
-    _arena = new (mtSymbol) Arena(mtSymbol);
-  } else {
-    _arena = new (mtSymbol) Arena(mtSymbol, arena_alloc_size);
-  }
-}
-
 class SymbolsDo : StackObj {
   SymbolClosure *_cl;
 public:
@@ -252,7 +257,7 @@
 
   // all symbols from the dynamic table
   SymbolsDo sd(cl);
-  if (!SymbolTable::the_table()->_local_table->try_scan(Thread::current(), sd)) {
+  if (!_local_table->try_scan(Thread::current(), sd)) {
     log_info(stringtable)("symbols_do unavailable at this moment");
   }
 }
@@ -272,12 +277,12 @@
 void SymbolTable::metaspace_pointers_do(MetaspaceClosure* it) {
   assert(DumpSharedSpaces, "called only during dump time");
   MetaspacePointersDo mpd(it);
-  SymbolTable::the_table()->_local_table->do_safepoint_scan(mpd);
+  _local_table->do_safepoint_scan(mpd);
 }
 
 Symbol* SymbolTable::lookup_dynamic(const char* name,
                                     int len, unsigned int hash) {
-  Symbol* sym = SymbolTable::the_table()->do_lookup(name, len, hash);
+  Symbol* sym = do_lookup(name, len, hash);
   assert((sym == NULL) || sym->refcount() != 0, "refcount must not be zero");
   return sym;
 }
@@ -285,7 +290,7 @@
 Symbol* SymbolTable::lookup_shared(const char* name,
                                    int len, unsigned int hash) {
   if (!_shared_table.empty()) {
-    if (SymbolTable::_alt_hash) {
+    if (_alt_hash) {
       // hash_code parameter may use alternate hashing algorithm but the shared table
       // always uses the same original hash code.
       hash = hash_shared_symbol(name, len);
@@ -318,10 +323,10 @@
 }
 
 Symbol* SymbolTable::new_symbol(const char* name, int len) {
-  unsigned int hash = hash_symbol(name, len, SymbolTable::_alt_hash);
-  Symbol* sym = SymbolTable::the_table()->lookup_common(name, len, hash);
+  unsigned int hash = hash_symbol(name, len, _alt_hash);
+  Symbol* sym = lookup_common(name, len, hash);
   if (sym == NULL) {
-    sym = SymbolTable::the_table()->do_add_if_needed(name, len, hash, true);
+    sym = do_add_if_needed(name, len, hash, true);
   }
   assert(sym->refcount() != 0, "lookup should have incremented the count");
   assert(sym->equals(name, len), "symbol must be properly initialized");
@@ -333,10 +338,10 @@
   assert(sym->refcount() != 0, "require a valid symbol");
   const char* name = (const char*)sym->base() + begin;
   int len = end - begin;
-  unsigned int hash = hash_symbol(name, len, SymbolTable::_alt_hash);
-  Symbol* found = SymbolTable::the_table()->lookup_common(name, len, hash);
+  unsigned int hash = hash_symbol(name, len, _alt_hash);
+  Symbol* found = lookup_common(name, len, hash);
   if (found == NULL) {
-    found = SymbolTable::the_table()->do_add_if_needed(name, len, hash, true);
+    found = do_add_if_needed(name, len, hash, true);
   }
   return found;
 }
@@ -400,8 +405,8 @@
 }
 
 Symbol* SymbolTable::lookup_only(const char* name, int len, unsigned int& hash) {
-  hash = hash_symbol(name, len, SymbolTable::_alt_hash);
-  return SymbolTable::the_table()->lookup_common(name, len, hash);
+  hash = hash_symbol(name, len, _alt_hash);
+  return lookup_common(name, len, hash);
 }
 
 // Suggestion: Push unicode-based lookup all the way into the hashing
@@ -446,8 +451,8 @@
     const char *name = names[i];
     int len = lengths[i];
     unsigned int hash = hashValues[i];
-    assert(SymbolTable::the_table()->lookup_shared(name, len, hash) == NULL, "must have checked already");
-    Symbol* sym = SymbolTable::the_table()->do_add_if_needed(name, len, hash, c_heap);
+    assert(lookup_shared(name, len, hash) == NULL, "must have checked already");
+    Symbol* sym = do_add_if_needed(name, len, hash, c_heap);
     assert(sym->refcount() != 0, "lookup should have incremented the count");
     cp->symbol_at_put(cp_indices[i], sym);
   }
@@ -466,7 +471,7 @@
       sym = stg.get_res_sym();
       break;
     }
-    sym = SymbolTable::the_table()->allocate_symbol(name, len, heap);
+    sym = allocate_symbol(name, len, heap);
     if (_local_table->insert(THREAD, lookup, sym, &rehash_warning, &clean_hint)) {
       break;
     }
@@ -488,7 +493,7 @@
   int len = (int)strlen(name);
   Symbol* sym = SymbolTable::lookup_only(name, len, hash);
   if (sym == NULL) {
-    sym = SymbolTable::the_table()->do_add_if_needed(name, len, hash, false);
+    sym = do_add_if_needed(name, len, hash, false);
   }
   if (!sym->is_permanent()) {
     sym->make_permanent();
@@ -534,7 +539,7 @@
 void SymbolTable::verify() {
   Thread* thr = Thread::current();
   VerifySymbols vs;
-  if (!SymbolTable::the_table()->_local_table->try_scan(thr, vs)) {
+  if (!_local_table->try_scan(thr, vs)) {
     log_info(stringtable)("verify unavailable at this moment");
   }
 }
@@ -560,13 +565,13 @@
 
 void SymbolTable::dump(outputStream* st, bool verbose) {
   if (!verbose) {
-    SymbolTable::the_table()->print_table_statistics(st, "SymbolTable");
+    print_table_statistics(st, "SymbolTable");
   } else {
     Thread* thr = Thread::current();
     ResourceMark rm(thr);
     st->print_cr("VERSION: 1.1");
     DumpSymbol ds(thr, st);
-    if (!SymbolTable::the_table()->_local_table->try_scan(thr, ds)) {
+    if (!_local_table->try_scan(thr, ds)) {
       log_info(symboltable)("dump unavailable at this moment");
     }
   }
@@ -590,14 +595,14 @@
 
 void SymbolTable::copy_shared_symbol_table(CompactHashtableWriter* writer) {
   CopyToArchive copy(writer);
-  SymbolTable::the_table()->_local_table->do_safepoint_scan(copy);
+  _local_table->do_safepoint_scan(copy);
 }
 
 void SymbolTable::write_to_archive() {
   _shared_table.reset();
 
   int num_buckets = CompactHashtableWriter::default_num_buckets(
-      SymbolTable::the_table()->_items_count);
+      _items_count);
   CompactHashtableWriter writer(num_buckets,
                                 &MetaspaceShared::stats()->symbol);
   copy_shared_symbol_table(&writer);
@@ -607,7 +612,7 @@
   Symbol* sym = vmSymbols::java_lang_Object();
   const char* name = (const char*)sym->bytes();
   int len = sym->utf8_length();
-  unsigned int hash = hash_symbol(name, len, SymbolTable::_alt_hash);
+  unsigned int hash = hash_symbol(name, len, _alt_hash);
   assert(sym == _shared_table.lookup(name, hash, len), "sanity");
 }
 
@@ -684,7 +689,7 @@
       }
       bdt.cont(jt);
     }
-    SymbolTable::the_table()->reset_has_items_to_clean();
+    reset_has_items_to_clean();
     bdt.done(jt);
   }
 
@@ -708,7 +713,7 @@
   }
 }
 
-void SymbolTable::concurrent_work(JavaThread* jt) {
+void SymbolTable::do_concurrent_work(JavaThread* jt) {
   double load_factor = get_load_factor();
   log_debug(symboltable, perf)("Concurrent work, live factor: %g", load_factor);
   // We prefer growing, since that also removes dead items
@@ -720,10 +725,6 @@
   _has_work = false;
 }
 
-void SymbolTable::do_concurrent_work(JavaThread* jt) {
-  SymbolTable::the_table()->concurrent_work(jt);
-}
-
 // Rehash
 bool SymbolTable::do_rehash() {
   if (!_local_table->is_safepoint_safe()) {
@@ -747,7 +748,7 @@
   return true;
 }
 
-void SymbolTable::try_rehash_table() {
+void SymbolTable::rehash_table() {
   static bool rehashed = false;
   log_debug(symboltable)("Table imbalanced, rehashing called.");
 
@@ -779,10 +780,6 @@
   _needs_rehashing = false;
 }
 
-void SymbolTable::rehash_table() {
-  SymbolTable::the_table()->try_rehash_table();
-}
-
 //---------------------------------------------------------------------------
 // Non-product code
 
@@ -830,18 +827,17 @@
 };
 
 void SymbolTable::print_histogram() {
-  SymbolTable* st = SymbolTable::the_table();
   HistogramIterator hi;
-  st->_local_table->do_scan(Thread::current(), hi);
+  _local_table->do_scan(Thread::current(), hi);
   tty->print_cr("Symbol Table Histogram:");
   tty->print_cr("  Total number of symbols  " SIZE_FORMAT_W(7), hi.total_count);
   tty->print_cr("  Total size in memory     " SIZE_FORMAT_W(7) "K",
           (hi.total_size * wordSize) / 1024);
-  tty->print_cr("  Total counted            " SIZE_FORMAT_W(7), st->_symbols_counted);
-  tty->print_cr("  Total removed            " SIZE_FORMAT_W(7), st->_symbols_removed);
-  if (SymbolTable::the_table()->_symbols_counted > 0) {
+  tty->print_cr("  Total counted            " SIZE_FORMAT_W(7), _symbols_counted);
+  tty->print_cr("  Total removed            " SIZE_FORMAT_W(7), _symbols_removed);
+  if (_symbols_counted > 0) {
     tty->print_cr("  Percent removed          %3.2f",
-          ((float)st->_symbols_removed / st->_symbols_counted) * 100);
+          ((float)_symbols_removed / _symbols_counted) * 100);
   }
   tty->print_cr("  Reference counts         " SIZE_FORMAT_W(7), Symbol::_total_count);
   tty->print_cr("  Symbol arena used        " SIZE_FORMAT_W(7) "K", arena()->used() / 1024);
--- a/src/hotspot/share/classfile/symbolTable.hpp	Thu May 16 16:40:48 2019 +0530
+++ b/src/hotspot/share/classfile/symbolTable.hpp	Thu May 16 07:09:17 2019 -0400
@@ -28,8 +28,7 @@
 #include "memory/allocation.hpp"
 #include "memory/padded.hpp"
 #include "oops/symbol.hpp"
-#include "utilities/concurrentHashTable.hpp"
-#include "utilities/hashtable.hpp"
+#include "utilities/tableStatistics.hpp"
 
 class JavaThread;
 
@@ -90,58 +89,43 @@
 class SerializeClosure;
 
 class SymbolTableConfig;
-typedef ConcurrentHashTable<Symbol*,
-                              SymbolTableConfig, mtSymbol> SymbolTableHash;
-
 class SymbolTableCreateEntry;
 
-class SymbolTable : public CHeapObj<mtSymbol> {
+class constantPoolHandle;
+class SymbolClosure;
+
+class SymbolTable : public AllStatic {
   friend class VMStructs;
   friend class Symbol;
   friend class ClassFileParser;
   friend class SymbolTableConfig;
   friend class SymbolTableCreateEntry;
 
-private:
-  static void delete_symbol(Symbol* sym);
-  void grow(JavaThread* jt);
-  void clean_dead_entries(JavaThread* jt);
+ private:
+  static volatile bool _has_work;
 
-  // The symbol table
-  static SymbolTable* _the_table;
-  static volatile bool _lookup_shared_first;
-  static volatile bool _alt_hash;
+  // Set if one bucket is out of balance due to hash algorithm deficiency
+  static volatile bool _needs_rehashing;
 
-  // For statistics
-  volatile size_t _symbols_removed;
-  volatile size_t _symbols_counted;
+  static void delete_symbol(Symbol* sym);
+  static void grow(JavaThread* jt);
+  static void clean_dead_entries(JavaThread* jt);
 
-  SymbolTableHash* _local_table;
-  size_t _current_size;
-  volatile bool _has_work;
-  // Set if one bucket is out of balance due to hash algorithm deficiency
-  volatile bool _needs_rehashing;
+  static double get_load_factor();
 
-  volatile size_t _items_count;
-  volatile bool   _has_items_to_clean;
-
-  double get_load_factor() const;
-
-  void check_concurrent_work();
+  static void check_concurrent_work();
 
   static void item_added();
   static void item_removed();
 
   // For cleaning
-  void reset_has_items_to_clean();
-  void mark_has_items_to_clean();
-  bool has_items_to_clean() const;
+  static void reset_has_items_to_clean();
+  static void mark_has_items_to_clean();
+  static bool has_items_to_clean();
 
-  SymbolTable();
-
-  Symbol* allocate_symbol(const char* name, int len, bool c_heap); // Assumes no characters larger than 0x7F
-  Symbol* do_lookup(const char* name, int len, uintx hash);
-  Symbol* do_add_if_needed(const char* name, int len, uintx hash, bool heap);
+  static Symbol* allocate_symbol(const char* name, int len, bool c_heap); // Assumes no characters larger than 0x7F
+  static Symbol* do_lookup(const char* name, int len, uintx hash);
+  static Symbol* do_add_if_needed(const char* name, int len, uintx hash, bool heap);
 
   // lookup only, won't add. Also calculate hash. Used by the ClassfileParser.
   static Symbol* lookup_only(const char* name, int len, unsigned int& hash);
@@ -154,27 +138,22 @@
                           int* cp_indices, unsigned int* hashValues);
 
   static Symbol* lookup_shared(const char* name, int len, unsigned int hash);
-  Symbol* lookup_dynamic(const char* name, int len, unsigned int hash);
-  Symbol* lookup_common(const char* name, int len, unsigned int hash);
+  static Symbol* lookup_dynamic(const char* name, int len, unsigned int hash);
+  static Symbol* lookup_common(const char* name, int len, unsigned int hash);
 
   // Arena for permanent symbols (null class loader) that are never unloaded
   static Arena*  _arena;
   static Arena* arena() { return _arena; }  // called for statistics
 
-  static void initialize_symbols(int arena_alloc_size = 0);
+  static void print_table_statistics(outputStream* st, const char* table_name);
 
-  void concurrent_work(JavaThread* jt);
-  void print_table_statistics(outputStream* st, const char* table_name);
-
-  void try_rehash_table();
-  bool do_rehash();
-  inline void update_needs_rehash(bool rehash);
+  static void try_rehash_table();
+  static bool do_rehash();
 
 public:
   // The symbol table
-  static SymbolTable* the_table() { return _the_table; }
-  size_t table_size();
-  TableStatistics get_table_statistics();
+  static size_t table_size();
+  static TableStatistics get_table_statistics();
 
   enum {
     symbol_alloc_batch_size = 8,
@@ -182,14 +161,10 @@
     symbol_alloc_arena_size = 360*K // TODO (revisit)
   };
 
-  static void create_table() {
-    assert(_the_table == NULL, "One symbol table allowed.");
-    _the_table = new SymbolTable();
-    initialize_symbols(symbol_alloc_arena_size);
-  }
+  static void create_table();
 
   static void do_concurrent_work(JavaThread* jt);
-  static bool has_work() { return the_table()->_has_work; }
+  static bool has_work() { return _has_work; }
   static void trigger_cleanup();
 
   // Probing
@@ -220,8 +195,12 @@
 
   // Rehash the string table if it gets out of balance
   static void rehash_table();
-  static bool needs_rehashing()
-    { return SymbolTable::the_table()->_needs_rehashing; }
+  static bool needs_rehashing() { return _needs_rehashing; }
+  static inline void update_needs_rehash(bool rehash) {
+    if (rehash) {
+      _needs_rehashing = true;
+    }
+  }
 
   // Heap dumper and CDS
   static void symbols_do(SymbolClosure *cl);
--- a/src/hotspot/share/jfr/periodic/jfrPeriodic.cpp	Thu May 16 16:40:48 2019 +0530
+++ b/src/hotspot/share/jfr/periodic/jfrPeriodic.cpp	Thu May 16 07:09:17 2019 -0400
@@ -525,12 +525,12 @@
 }
 
 TRACE_REQUEST_FUNC(SymbolTableStatistics) {
-  TableStatistics statistics = SymbolTable::the_table()->get_table_statistics();
+  TableStatistics statistics = SymbolTable::get_table_statistics();
   emit_table_statistics<EventSymbolTableStatistics>(statistics);
 }
 
 TRACE_REQUEST_FUNC(StringTableStatistics) {
-  TableStatistics statistics = StringTable::the_table()->get_table_statistics();
+  TableStatistics statistics = StringTable::get_table_statistics();
   emit_table_statistics<EventStringTableStatistics>(statistics);
 }
 
--- a/src/hotspot/share/prims/resolvedMethodTable.cpp	Thu May 16 16:40:48 2019 +0530
+++ b/src/hotspot/share/prims/resolvedMethodTable.cpp	Thu May 16 07:09:17 2019 -0400
@@ -56,6 +56,10 @@
   return name_hash ^ signature_hash;
 }
 
+typedef ConcurrentHashTable<WeakHandle<vm_resolved_method_table_data>,
+                            ResolvedMethodTableConfig,
+                            mtClass> ResolvedMethodTableHash;
+
 class ResolvedMethodTableConfig : public ResolvedMethodTableHash::BaseConfig {
  private:
  public:
@@ -83,14 +87,14 @@
   }
 };
 
-ResolvedMethodTableHash* ResolvedMethodTable::_local_table           = NULL;
-size_t                   ResolvedMethodTable::_current_size          = (size_t)1 << ResolvedMethodTableSizeLog;
+static ResolvedMethodTableHash* _local_table           = NULL;
+static size_t                   _current_size          = (size_t)1 << ResolvedMethodTableSizeLog;
 
 OopStorage*              ResolvedMethodTable::_weak_handles          = NULL;
+volatile bool            ResolvedMethodTable::_has_work              = false;
 
-volatile bool            ResolvedMethodTable::_has_work              = false;
-volatile size_t          ResolvedMethodTable::_items_count           = 0;
-volatile size_t          ResolvedMethodTable::_uncleaned_items_count = 0;
+volatile size_t          _items_count           = 0;
+volatile size_t          _uncleaned_items_count = 0;
 
 void ResolvedMethodTable::create_table() {
   _local_table  = new ResolvedMethodTableHash(ResolvedMethodTableSizeLog, END_SIZE, GROW_HINT);
@@ -209,14 +213,6 @@
   log_trace(membername, table) ("ResolvedMethod entry removed");
 }
 
-bool ResolvedMethodTable::has_work() {
-  return _has_work;
-}
-
-OopStorage* ResolvedMethodTable::weak_storage() {
-  return _weak_handles;
-}
-
 double ResolvedMethodTable::get_load_factor() {
   return (double)_items_count/_current_size;
 }
--- a/src/hotspot/share/prims/resolvedMethodTable.hpp	Thu May 16 16:40:48 2019 +0530
+++ b/src/hotspot/share/prims/resolvedMethodTable.hpp	Thu May 16 07:09:17 2019 -0400
@@ -26,28 +26,17 @@
 #define SHARE_PRIMS_RESOLVEDMETHODTABLE_HPP
 
 #include "gc/shared/oopStorage.hpp"
-#include "gc/shared/oopStorageParState.hpp"
 #include "memory/allocation.hpp"
 #include "oops/symbol.hpp"
 #include "oops/weakHandle.hpp"
-#include "utilities/concurrentHashTable.hpp"
-#include "utilities/hashtable.hpp"
 
 class ResolvedMethodTable;
 class ResolvedMethodTableConfig;
-typedef ConcurrentHashTable<WeakHandle<vm_resolved_method_table_data>, ResolvedMethodTableConfig, mtClass> ResolvedMethodTableHash;
 
 class ResolvedMethodTable : public AllStatic {
-  static ResolvedMethodTableHash* _local_table;
-  static size_t                   _current_size;
-
   static OopStorage*              _weak_handles;
 
   static volatile bool            _has_work;
-
-  static volatile size_t          _items_count;
-  static volatile size_t          _uncleaned_items_count;
-
 public:
   // Initialization
   static void create_table();
@@ -63,10 +52,10 @@
   static void item_removed();
 
   // Cleaning
-  static bool has_work();
+  static bool has_work() { return _has_work; }
 
   // GC Support - Backing storage for the oop*s
-  static OopStorage* weak_storage();
+  static OopStorage* weak_storage() { return _weak_handles; }
 
   // Cleaning and table management