mirror of
https://github.com/openjdk/jdk.git
synced 2025-08-28 07:14:30 +02:00
8223956: Make SymbolTable and StringTable AllStatic
Removed superfluous and confusing _the_table pointer. Reviewed-by: gziemski, rehn
This commit is contained in:
parent
5fc3474639
commit
4915cf9b71
7 changed files with 186 additions and 270 deletions
|
@ -70,9 +70,26 @@ static OffsetCompactHashtable<
|
|||
> _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 @@ public:
|
|||
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 @@ static size_t ceil_log2(size_t value) {
|
|||
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::delete_symbol(Symbol* sym) {
|
|||
}
|
||||
}
|
||||
|
||||
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 @@ size_t SymbolTable::table_size() {
|
|||
|
||||
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 @@ Symbol* SymbolTable::allocate_symbol(const char* name, int len, bool c_heap) {
|
|||
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 @@ void SymbolTable::symbols_do(SymbolClosure *cl) {
|
|||
|
||||
// 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 @@ public:
|
|||
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_dynamic(const char* name,
|
|||
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::lookup_common(const char* name,
|
|||
}
|
||||
|
||||
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 @@ Symbol* SymbolTable::new_symbol(const Symbol* sym, int begin, int end) {
|
|||
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::do_lookup(const char* name, int len, uintx hash) {
|
|||
}
|
||||
|
||||
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 @@ void SymbolTable::new_symbols(ClassLoaderData* loader_data, const constantPoolHa
|
|||
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 @@ Symbol* SymbolTable::do_add_if_needed(const char* name, int len, uintx hash, boo
|
|||
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 @@ Symbol* SymbolTable::new_permanent_symbol(const char* name) {
|
|||
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 @@ public:
|
|||
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 @@ public:
|
|||
|
||||
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 @@ struct CopyToArchive : StackObj {
|
|||
|
||||
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 @@ void SymbolTable::write_to_archive() {
|
|||
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 @@ void SymbolTable::clean_dead_entries(JavaThread* jt) {
|
|||
}
|
||||
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::check_concurrent_work() {
|
|||
}
|
||||
}
|
||||
|
||||
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 @@ void SymbolTable::concurrent_work(JavaThread* jt) {
|
|||
_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 @@ bool SymbolTable::do_rehash() {
|
|||
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 @@ void SymbolTable::try_rehash_table() {
|
|||
_needs_rehashing = false;
|
||||
}
|
||||
|
||||
void SymbolTable::rehash_table() {
|
||||
SymbolTable::the_table()->try_rehash_table();
|
||||
}
|
||||
|
||||
//---------------------------------------------------------------------------
|
||||
// Non-product code
|
||||
|
||||
|
@ -830,18 +827,17 @@ public:
|
|||
};
|
||||
|
||||
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);
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue