Mercurial > hg > graal-jvmci-8
diff src/share/vm/classfile/dictionary.hpp @ 0:a61af66fc99e jdk7-b24
Initial load
author | duke |
---|---|
date | Sat, 01 Dec 2007 00:00:00 +0000 |
parents | |
children | e5b0439ef4ae |
line wrap: on
line diff
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/src/share/vm/classfile/dictionary.hpp Sat Dec 01 00:00:00 2007 +0000 @@ -0,0 +1,219 @@ +/* + * Copyright 2003-2006 Sun Microsystems, Inc. All Rights Reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, + * CA 95054 USA or visit www.sun.com if you need additional information or + * have any questions. + * + */ + +class DictionaryEntry; + +//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +// The data structure for the system dictionary (and the shared system +// dictionary). + +class Dictionary : public TwoOopHashtable { + friend class VMStructs; +private: + // current iteration index. + static int _current_class_index; + // pointer to the current hash table entry. + static DictionaryEntry* _current_class_entry; + + DictionaryEntry* get_entry(int index, unsigned int hash, + symbolHandle name, Handle loader); + + DictionaryEntry* bucket(int i) { + return (DictionaryEntry*)Hashtable::bucket(i); + } + + // The following method is not MT-safe and must be done under lock. + DictionaryEntry** bucket_addr(int i) { + return (DictionaryEntry**)Hashtable::bucket_addr(i); + } + + void add_entry(int index, DictionaryEntry* new_entry) { + Hashtable::add_entry(index, (HashtableEntry*)new_entry); + } + + +public: + Dictionary(int table_size); + Dictionary(int table_size, HashtableBucket* t, int number_of_entries); + + DictionaryEntry* new_entry(unsigned int hash, klassOop klass, oop loader); + + DictionaryEntry* new_entry(); + + void free_entry(DictionaryEntry* entry); + + void add_klass(symbolHandle class_name, Handle class_loader,KlassHandle obj); + + klassOop find_class(int index, unsigned int hash, + symbolHandle name, Handle loader); + + klassOop find_shared_class(int index, unsigned int hash, symbolHandle name); + + // Compiler support + klassOop try_get_next_class(); + + // GC support + + void oops_do(OopClosure* f); + void always_strong_classes_do(OopClosure* blk); + void classes_do(void f(klassOop)); + void classes_do(void f(klassOop, TRAPS), TRAPS); + void classes_do(void f(klassOop, oop)); + void classes_do(void f(klassOop, oop, TRAPS), TRAPS); + + void methods_do(void f(methodOop)); + + + // Classes loaded by the bootstrap loader are always strongly reachable. + // If we're not doing class unloading, all classes are strongly reachable. + static bool is_strongly_reachable(oop class_loader, oop klass) { + assert (klass != NULL, "should have non-null klass"); + return (class_loader == NULL || !ClassUnloading); + } + + // Unload (that is, break root links to) all unmarked classes and + // loaders. Returns "true" iff something was unloaded. + bool do_unloading(BoolObjectClosure* is_alive); + + // Protection domains + klassOop find(int index, unsigned int hash, symbolHandle name, + Handle loader, Handle protection_domain, TRAPS); + bool is_valid_protection_domain(int index, unsigned int hash, + symbolHandle name, Handle class_loader, + Handle protection_domain); + void add_protection_domain(int index, unsigned int hash, + instanceKlassHandle klass, Handle loader, + Handle protection_domain, TRAPS); + + // Sharing support + void dump(SerializeOopClosure* soc); + void restore(SerializeOopClosure* soc); + void reorder_dictionary(); + + +#ifndef PRODUCT + void print(); +#endif + void verify(); +}; + +// The following classes can be in dictionary.cpp, but we need these +// to be in header file so that SA's vmStructs can access. + +class ProtectionDomainEntry :public CHeapObj { + friend class VMStructs; + public: + ProtectionDomainEntry* _next; + oop _protection_domain; + + ProtectionDomainEntry(oop protection_domain, ProtectionDomainEntry* next) { + _protection_domain = protection_domain; + _next = next; + } + + ProtectionDomainEntry* next() { return _next; } + oop protection_domain() { return _protection_domain; } +}; + +// An entry in the system dictionary, this describes a class as +// { klassOop, loader, protection_domain }. + +class DictionaryEntry : public HashtableEntry { + friend class VMStructs; + private: + // Contains the set of approved protection domains that can access + // this system dictionary entry. + ProtectionDomainEntry* _pd_set; + oop _loader; + + + public: + // Tells whether a protection is in the approved set. + bool contains_protection_domain(oop protection_domain) const; + // Adds a protection domain to the approved set. + void add_protection_domain(oop protection_domain); + + klassOop klass() const { return (klassOop)literal(); } + klassOop* klass_addr() { return (klassOop*)literal_addr(); } + + DictionaryEntry* next() const { + return (DictionaryEntry*)HashtableEntry::next(); + } + + DictionaryEntry** next_addr() { + return (DictionaryEntry**)HashtableEntry::next_addr(); + } + + oop loader() const { return _loader; } + void set_loader(oop loader) { _loader = loader; } + oop* loader_addr() { return &_loader; } + + ProtectionDomainEntry* pd_set() const { return _pd_set; } + void set_pd_set(ProtectionDomainEntry* pd_set) { _pd_set = pd_set; } + + bool has_protection_domain() { return _pd_set != NULL; } + + // Tells whether the initiating class' protection can access the this _klass + bool is_valid_protection_domain(Handle protection_domain) { + if (!ProtectionDomainVerification) return true; + if (!SystemDictionary::has_checkPackageAccess()) return true; + + return protection_domain() == NULL + ? true + : contains_protection_domain(protection_domain()); + } + + + void protection_domain_set_oops_do(OopClosure* f) { + for (ProtectionDomainEntry* current = _pd_set; + current != NULL; + current = current->_next) { + f->do_oop(&(current->_protection_domain)); + } + } + + void verify_protection_domain_set() { + for (ProtectionDomainEntry* current = _pd_set; + current != NULL; + current = current->_next) { + current->_protection_domain->verify(); + } + } + + bool equals(symbolOop class_name, oop class_loader) const { + klassOop klass = (klassOop)literal(); + return (instanceKlass::cast(klass)->name() == class_name && + _loader == class_loader); + } + + void print() { + int count = 0; + for (ProtectionDomainEntry* current = _pd_set; + current != NULL; + current = current->_next) { + count++; + } + tty->print_cr("pd set = #%d", count); + } +};