提交 c075680f 编写于 作者: A acorn

7114376: Make system dictionary hashtable bucket array size configurable

Summary: 7u4 new experimental flag -XX:PredictedClassLoadedCount=#
Reviewed-by: dholmes, phh, dcubed
上级 981015c1
/* /*
* Copyright (c) 2003, Oracle and/or its affiliates. All rights reserved. * Copyright (c) 2003, 2012 Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* *
* This code is free software; you can redistribute it and/or modify it * This code is free software; you can redistribute it and/or modify it
...@@ -42,15 +42,6 @@ public class LoaderConstraintTable extends TwoOopHashtable { ...@@ -42,15 +42,6 @@ public class LoaderConstraintTable extends TwoOopHashtable {
private static synchronized void initialize(TypeDataBase db) { private static synchronized void initialize(TypeDataBase db) {
Type type = db.lookupType("LoaderConstraintTable"); Type type = db.lookupType("LoaderConstraintTable");
nofBuckets = db.lookupIntConstant("LoaderConstraintTable::_nof_buckets").intValue();
}
// Fields
private static int nofBuckets;
// Accessors
public static int getNumOfBuckets() {
return nofBuckets;
} }
public LoaderConstraintTable(Address addr) { public LoaderConstraintTable(Address addr) {
......
/* /*
* Copyright (c) 2001, 2010, Oracle and/or its affiliates. All rights reserved. * Copyright (c) 2001, 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* *
* This code is free software; you can redistribute it and/or modify it * This code is free software; you can redistribute it and/or modify it
...@@ -36,7 +36,6 @@ public class SystemDictionary { ...@@ -36,7 +36,6 @@ public class SystemDictionary {
private static AddressField placeholdersField; private static AddressField placeholdersField;
private static AddressField loaderConstraintTableField; private static AddressField loaderConstraintTableField;
private static sun.jvm.hotspot.types.OopField javaSystemLoaderField; private static sun.jvm.hotspot.types.OopField javaSystemLoaderField;
private static int nofBuckets;
private static sun.jvm.hotspot.types.OopField objectKlassField; private static sun.jvm.hotspot.types.OopField objectKlassField;
private static sun.jvm.hotspot.types.OopField classLoaderKlassField; private static sun.jvm.hotspot.types.OopField classLoaderKlassField;
...@@ -62,7 +61,6 @@ public class SystemDictionary { ...@@ -62,7 +61,6 @@ public class SystemDictionary {
placeholdersField = type.getAddressField("_placeholders"); placeholdersField = type.getAddressField("_placeholders");
loaderConstraintTableField = type.getAddressField("_loader_constraints"); loaderConstraintTableField = type.getAddressField("_loader_constraints");
javaSystemLoaderField = type.getOopField("_java_system_loader"); javaSystemLoaderField = type.getOopField("_java_system_loader");
nofBuckets = db.lookupIntConstant("SystemDictionary::_nof_buckets").intValue();
objectKlassField = type.getOopField(WK_KLASS("Object_klass")); objectKlassField = type.getOopField(WK_KLASS("Object_klass"));
classLoaderKlassField = type.getOopField(WK_KLASS("ClassLoader_klass")); classLoaderKlassField = type.getOopField(WK_KLASS("ClassLoader_klass"));
...@@ -142,10 +140,6 @@ public class SystemDictionary { ...@@ -142,10 +140,6 @@ public class SystemDictionary {
return newOop(javaSystemLoaderField.getValue()); return newOop(javaSystemLoaderField.getValue());
} }
public static int getNumOfBuckets() {
return nofBuckets;
}
private static Oop newOop(OopHandle handle) { private static Oop newOop(OopHandle handle) {
return VM.getVM().getObjectHeap().newOop(handle); return VM.getVM().getObjectHeap().newOop(handle);
} }
......
/* /*
* Copyright (c) 2003, 2011, Oracle and/or its affiliates. All rights reserved. * Copyright (c) 2003, 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* *
* This code is free software; you can redistribute it and/or modify it * This code is free software; you can redistribute it and/or modify it
...@@ -618,7 +618,8 @@ void Dictionary::print() { ...@@ -618,7 +618,8 @@ void Dictionary::print() {
ResourceMark rm; ResourceMark rm;
HandleMark hm; HandleMark hm;
tty->print_cr("Java system dictionary (classes=%d)", number_of_entries()); tty->print_cr("Java system dictionary (table_size=%d, classes=%d)",
table_size(), number_of_entries());
tty->print_cr("^ indicates that initiating loader is different from " tty->print_cr("^ indicates that initiating loader is different from "
"defining loader"); "defining loader");
......
/* /*
* Copyright (c) 1997, 2011, Oracle and/or its affiliates. All rights reserved. * Copyright (c) 1997, 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* *
* This code is free software; you can redistribute it and/or modify it * This code is free software; you can redistribute it and/or modify it
...@@ -64,6 +64,9 @@ SymbolPropertyTable* SystemDictionary::_invoke_method_table = NULL; ...@@ -64,6 +64,9 @@ SymbolPropertyTable* SystemDictionary::_invoke_method_table = NULL;
int SystemDictionary::_number_of_modifications = 0; int SystemDictionary::_number_of_modifications = 0;
int SystemDictionary::_sdgeneration = 0;
const int SystemDictionary::_primelist[_prime_array_size] = {1009,2017,4049,5051,10103,
20201,40423,99991};
oop SystemDictionary::_system_loader_lock_obj = NULL; oop SystemDictionary::_system_loader_lock_obj = NULL;
...@@ -1178,8 +1181,8 @@ void SystemDictionary::set_shared_dictionary(HashtableBucket* t, int length, ...@@ -1178,8 +1181,8 @@ void SystemDictionary::set_shared_dictionary(HashtableBucket* t, int length,
klassOop SystemDictionary::find_shared_class(Symbol* class_name) { klassOop SystemDictionary::find_shared_class(Symbol* class_name) {
if (shared_dictionary() != NULL) { if (shared_dictionary() != NULL) {
unsigned int d_hash = dictionary()->compute_hash(class_name, Handle()); unsigned int d_hash = shared_dictionary()->compute_hash(class_name, Handle());
int d_index = dictionary()->hash_to_index(d_hash); int d_index = shared_dictionary()->hash_to_index(d_hash);
return shared_dictionary()->find_shared_class(d_index, d_hash, class_name); return shared_dictionary()->find_shared_class(d_index, d_hash, class_name);
} else { } else {
return NULL; return NULL;
...@@ -1750,7 +1753,21 @@ void SystemDictionary::placeholders_do(OopClosure* blk) { ...@@ -1750,7 +1753,21 @@ void SystemDictionary::placeholders_do(OopClosure* blk) {
placeholders()->oops_do(blk); placeholders()->oops_do(blk);
} }
// Calculate a "good" systemdictionary size based
// on predicted or current loaded classes count
int SystemDictionary::calculate_systemdictionary_size(int classcount) {
int newsize = _old_default_sdsize;
if ((classcount > 0) && !DumpSharedSpaces) {
int desiredsize = classcount/_average_depth_goal;
for (newsize = _primelist[_sdgeneration]; _sdgeneration < _prime_array_size -1;
newsize = _primelist[++_sdgeneration]) {
if (desiredsize <= newsize) {
break;
}
}
}
return newsize;
}
bool SystemDictionary::do_unloading(BoolObjectClosure* is_alive) { bool SystemDictionary::do_unloading(BoolObjectClosure* is_alive) {
bool result = dictionary()->do_unloading(is_alive); bool result = dictionary()->do_unloading(is_alive);
constraints()->purge_loader_constraints(is_alive); constraints()->purge_loader_constraints(is_alive);
...@@ -1873,7 +1890,8 @@ void SystemDictionary::initialize(TRAPS) { ...@@ -1873,7 +1890,8 @@ void SystemDictionary::initialize(TRAPS) {
// Allocate arrays // Allocate arrays
assert(dictionary() == NULL, assert(dictionary() == NULL,
"SystemDictionary should only be initialized once"); "SystemDictionary should only be initialized once");
_dictionary = new Dictionary(_nof_buckets); _sdgeneration = 0;
_dictionary = new Dictionary(calculate_systemdictionary_size(PredictedLoadedClassCount));
_placeholders = new PlaceholderTable(_nof_buckets); _placeholders = new PlaceholderTable(_nof_buckets);
_number_of_modifications = 0; _number_of_modifications = 0;
_loader_constraints = new LoaderConstraintTable(_loader_constraint_size); _loader_constraints = new LoaderConstraintTable(_loader_constraint_size);
......
/* /*
* Copyright (c) 1997, 2011, Oracle and/or its affiliates. All rights reserved. * Copyright (c) 1997, 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* *
* This code is free software; you can redistribute it and/or modify it * This code is free software; you can redistribute it and/or modify it
...@@ -346,6 +346,8 @@ public: ...@@ -346,6 +346,8 @@ public:
// loaders. Returns "true" iff something was unloaded. // loaders. Returns "true" iff something was unloaded.
static bool do_unloading(BoolObjectClosure* is_alive); static bool do_unloading(BoolObjectClosure* is_alive);
static int calculate_systemdictionary_size(int loadedclasses);
// Applies "f->do_oop" to all root oops in the system dictionary. // Applies "f->do_oop" to all root oops in the system dictionary.
static void oops_do(OopClosure* f); static void oops_do(OopClosure* f);
...@@ -538,12 +540,20 @@ public: ...@@ -538,12 +540,20 @@ public:
_loader_constraint_size = 107, // number of entries in constraint table _loader_constraint_size = 107, // number of entries in constraint table
_resolution_error_size = 107, // number of entries in resolution error table _resolution_error_size = 107, // number of entries in resolution error table
_invoke_method_size = 139, // number of entries in invoke method table _invoke_method_size = 139, // number of entries in invoke method table
_nof_buckets = 1009 // number of buckets in hash table _nof_buckets = 1009, // number of buckets in hash table for placeholders
_old_default_sdsize = 1009, // backward compat for system dictionary size
_prime_array_size = 8, // array of primes for system dictionary size
_average_depth_goal = 3 // goal for lookup length
}; };
// Static variables // Static variables
// hashtable sizes for system dictionary to allow growth
// prime numbers for system dictionary size
static int _sdgeneration;
static const int _primelist[_prime_array_size];
// Hashtable holding loaded classes. // Hashtable holding loaded classes.
static Dictionary* _dictionary; static Dictionary* _dictionary;
......
...@@ -1042,6 +1042,9 @@ class CommandLineFlags { ...@@ -1042,6 +1042,9 @@ class CommandLineFlags {
notproduct(bool, PrintSystemDictionaryAtExit, false, \ notproduct(bool, PrintSystemDictionaryAtExit, false, \
"Prints the system dictionary at exit") \ "Prints the system dictionary at exit") \
\ \
experimental(intx, PredictedLoadedClassCount, 0, \
"Experimental: Tune loaded class cache starting size.") \
\
diagnostic(bool, UnsyncloadClass, false, \ diagnostic(bool, UnsyncloadClass, false, \
"Unstable: VM calls loadClass unsynchronized. Custom " \ "Unstable: VM calls loadClass unsynchronized. Custom " \
"class loader must call VM synchronized for findClass " \ "class loader must call VM synchronized for findClass " \
......
/* /*
* Copyright (c) 2000, 2011, Oracle and/or its affiliates. All rights reserved. * Copyright (c) 2000, 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* *
* This code is free software; you can redistribute it and/or modify it * This code is free software; you can redistribute it and/or modify it
...@@ -2261,13 +2261,6 @@ static inline uint64_t cast_uint64_t(size_t x) ...@@ -2261,13 +2261,6 @@ static inline uint64_t cast_uint64_t(size_t x)
\ \
declare_constant(SymbolTable::symbol_table_size) \ declare_constant(SymbolTable::symbol_table_size) \
\ \
/********************/ \
/* SystemDictionary */ \
/********************/ \
\
declare_constant(SystemDictionary::_loader_constraint_size) \
declare_constant(SystemDictionary::_nof_buckets) \
\
/***********************************/ \ /***********************************/ \
/* LoaderConstraintTable constants */ \ /* LoaderConstraintTable constants */ \
/***********************************/ \ /***********************************/ \
......
/* /*
* Copyright (c) 2003, 2011, Oracle and/or its affiliates. All rights reserved. * Copyright (c) 2003, 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* *
* This code is free software; you can redistribute it and/or modify it * This code is free software; you can redistribute it and/or modify it
...@@ -183,7 +183,6 @@ protected: ...@@ -183,7 +183,6 @@ protected:
// Accessor // Accessor
int entry_size() const { return _entry_size; } int entry_size() const { return _entry_size; }
int table_size() { return _table_size; }
// The following method is MT-safe and may be used with caution. // The following method is MT-safe and may be used with caution.
BasicHashtableEntry* bucket(int i); BasicHashtableEntry* bucket(int i);
...@@ -195,6 +194,7 @@ protected: ...@@ -195,6 +194,7 @@ protected:
BasicHashtableEntry* new_entry(unsigned int hashValue); BasicHashtableEntry* new_entry(unsigned int hashValue);
public: public:
int table_size() { return _table_size; }
void set_entry(int index, BasicHashtableEntry* entry); void set_entry(int index, BasicHashtableEntry* entry);
void add_entry(int index, BasicHashtableEntry* entry); void add_entry(int index, BasicHashtableEntry* entry);
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册