src/share/vm/classfile/dictionary.hpp

Tue, 21 Apr 2009 23:21:04 -0700

author
jrose
date
Tue, 21 Apr 2009 23:21:04 -0700
changeset 1161
be93aad57795
parent 1145
e5b0439ef4ae
child 1862
cd5dbf694d45
permissions
-rw-r--r--

6655646: dynamic languages need dynamically linked call sites
Summary: invokedynamic instruction (JSR 292 RI)
Reviewed-by: twisti, never

     1 /*
     2  * Copyright 2003-2009 Sun Microsystems, Inc.  All Rights Reserved.
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     4  *
     5  * This code is free software; you can redistribute it and/or modify it
     6  * under the terms of the GNU General Public License version 2 only, as
     7  * published by the Free Software Foundation.
     8  *
     9  * This code is distributed in the hope that it will be useful, but WITHOUT
    10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
    11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
    12  * version 2 for more details (a copy is included in the LICENSE file that
    13  * accompanied this code).
    14  *
    15  * You should have received a copy of the GNU General Public License version
    16  * 2 along with this work; if not, write to the Free Software Foundation,
    17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
    18  *
    19  * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
    20  * CA 95054 USA or visit www.sun.com if you need additional information or
    21  * have any questions.
    22  *
    23  */
    25 class DictionaryEntry;
    27 //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    28 // The data structure for the system dictionary (and the shared system
    29 // dictionary).
    31 class Dictionary : public TwoOopHashtable {
    32   friend class VMStructs;
    33 private:
    34   // current iteration index.
    35   static int                    _current_class_index;
    36   // pointer to the current hash table entry.
    37   static DictionaryEntry*       _current_class_entry;
    39   DictionaryEntry* get_entry(int index, unsigned int hash,
    40                              symbolHandle name, Handle loader);
    42   DictionaryEntry* bucket(int i) {
    43     return (DictionaryEntry*)Hashtable::bucket(i);
    44   }
    46   // The following method is not MT-safe and must be done under lock.
    47   DictionaryEntry** bucket_addr(int i) {
    48     return (DictionaryEntry**)Hashtable::bucket_addr(i);
    49   }
    51   void add_entry(int index, DictionaryEntry* new_entry) {
    52     Hashtable::add_entry(index, (HashtableEntry*)new_entry);
    53   }
    56 public:
    57   Dictionary(int table_size);
    58   Dictionary(int table_size, HashtableBucket* t, int number_of_entries);
    60   DictionaryEntry* new_entry(unsigned int hash, klassOop klass, oop loader);
    62   DictionaryEntry* new_entry();
    64   void free_entry(DictionaryEntry* entry);
    66   void add_klass(symbolHandle class_name, Handle class_loader,KlassHandle obj);
    68   klassOop find_class(int index, unsigned int hash,
    69                       symbolHandle name, Handle loader);
    71   klassOop find_shared_class(int index, unsigned int hash, symbolHandle name);
    73   // Compiler support
    74   klassOop try_get_next_class();
    76   // GC support
    78   void oops_do(OopClosure* f);
    79   void always_strong_classes_do(OopClosure* blk);
    80   void classes_do(void f(klassOop));
    81   void classes_do(void f(klassOop, TRAPS), TRAPS);
    82   void classes_do(void f(klassOop, oop));
    83   void classes_do(void f(klassOop, oop, TRAPS), TRAPS);
    85   void methods_do(void f(methodOop));
    88   // Classes loaded by the bootstrap loader are always strongly reachable.
    89   // If we're not doing class unloading, all classes are strongly reachable.
    90   static bool is_strongly_reachable(oop class_loader, oop klass) {
    91     assert (klass != NULL, "should have non-null klass");
    92     return (class_loader == NULL || !ClassUnloading);
    93   }
    95   // Unload (that is, break root links to) all unmarked classes and
    96   // loaders.  Returns "true" iff something was unloaded.
    97   bool do_unloading(BoolObjectClosure* is_alive);
    99   // Protection domains
   100   klassOop find(int index, unsigned int hash, symbolHandle name,
   101                 Handle loader, Handle protection_domain, TRAPS);
   102   bool is_valid_protection_domain(int index, unsigned int hash,
   103                                   symbolHandle name, Handle class_loader,
   104                                   Handle protection_domain);
   105   void add_protection_domain(int index, unsigned int hash,
   106                              instanceKlassHandle klass, Handle loader,
   107                              Handle protection_domain, TRAPS);
   109   // Sharing support
   110   void dump(SerializeOopClosure* soc);
   111   void restore(SerializeOopClosure* soc);
   112   void reorder_dictionary();
   115 #ifndef PRODUCT
   116   void print();
   117 #endif
   118   void verify();
   119 };
   121 // The following classes can be in dictionary.cpp, but we need these
   122 // to be in header file so that SA's vmStructs can access.
   124 class ProtectionDomainEntry :public CHeapObj {
   125   friend class VMStructs;
   126  public:
   127   ProtectionDomainEntry* _next;
   128   oop                    _protection_domain;
   130   ProtectionDomainEntry(oop protection_domain, ProtectionDomainEntry* next) {
   131     _protection_domain = protection_domain;
   132     _next              = next;
   133   }
   135   ProtectionDomainEntry* next() { return _next; }
   136   oop protection_domain() { return _protection_domain; }
   137 };
   139 // An entry in the system dictionary, this describes a class as
   140 // { klassOop, loader, protection_domain }.
   142 class DictionaryEntry : public HashtableEntry {
   143   friend class VMStructs;
   144  private:
   145   // Contains the set of approved protection domains that can access
   146   // this system dictionary entry.
   147   ProtectionDomainEntry* _pd_set;
   148   oop                    _loader;
   151  public:
   152   // Tells whether a protection is in the approved set.
   153   bool contains_protection_domain(oop protection_domain) const;
   154   // Adds a protection domain to the approved set.
   155   void add_protection_domain(oop protection_domain);
   157   klassOop klass() const { return (klassOop)literal(); }
   158   klassOop* klass_addr() { return (klassOop*)literal_addr(); }
   160   DictionaryEntry* next() const {
   161     return (DictionaryEntry*)HashtableEntry::next();
   162   }
   164   DictionaryEntry** next_addr() {
   165     return (DictionaryEntry**)HashtableEntry::next_addr();
   166   }
   168   oop loader() const { return _loader; }
   169   void set_loader(oop loader) { _loader = loader; }
   170   oop* loader_addr() { return &_loader; }
   172   ProtectionDomainEntry* pd_set() const { return _pd_set; }
   173   void set_pd_set(ProtectionDomainEntry* pd_set) { _pd_set = pd_set; }
   175   bool has_protection_domain() { return _pd_set != NULL; }
   177   // Tells whether the initiating class' protection can access the this _klass
   178   bool is_valid_protection_domain(Handle protection_domain) {
   179     if (!ProtectionDomainVerification) return true;
   180     if (!SystemDictionary::has_checkPackageAccess()) return true;
   182     return protection_domain() == NULL
   183          ? true
   184          : contains_protection_domain(protection_domain());
   185   }
   188   void protection_domain_set_oops_do(OopClosure* f) {
   189     for (ProtectionDomainEntry* current = _pd_set;
   190                                 current != NULL;
   191                                 current = current->_next) {
   192       f->do_oop(&(current->_protection_domain));
   193     }
   194   }
   196   void verify_protection_domain_set() {
   197     for (ProtectionDomainEntry* current = _pd_set;
   198                                 current != NULL;
   199                                 current = current->_next) {
   200       current->_protection_domain->verify();
   201     }
   202   }
   204   bool equals(symbolOop class_name, oop class_loader) const {
   205     klassOop klass = (klassOop)literal();
   206     return (instanceKlass::cast(klass)->name() == class_name &&
   207             _loader == class_loader);
   208   }
   210   void print() {
   211     int count = 0;
   212     for (ProtectionDomainEntry* current = _pd_set;
   213                                 current != NULL;
   214                                 current = current->_next) {
   215       count++;
   216     }
   217     tty->print_cr("pd set = #%d", count);
   218   }
   219 };
   221 // Entry in a SymbolPropertyTable, mapping a single symbolOop
   222 // to a managed and an unmanaged pointer.
   223 class SymbolPropertyEntry : public HashtableEntry {
   224   friend class VMStructs;
   225  private:
   226   oop     _property_oop;
   227   address _property_data;
   229  public:
   230   symbolOop symbol() const          { return (symbolOop) literal(); }
   232   oop      property_oop() const     { return _property_oop; }
   233   void set_property_oop(oop p)      { _property_oop = p; }
   235   address  property_data() const    { return _property_data; }
   236   void set_property_data(address p) { _property_data = p; }
   238   SymbolPropertyEntry* next() const {
   239     return (SymbolPropertyEntry*)HashtableEntry::next();
   240   }
   242   SymbolPropertyEntry** next_addr() {
   243     return (SymbolPropertyEntry**)HashtableEntry::next_addr();
   244   }
   246   oop* symbol_addr()                { return literal_addr(); }
   247   oop* property_oop_addr()          { return &_property_oop; }
   249   void print_on(outputStream* st) const {
   250     symbol()->print_value_on(st);
   251     st->print(" -> ");
   252     bool printed = false;
   253     if (property_oop() != NULL) {
   254       property_oop()->print_value_on(st);
   255       printed = true;
   256     }
   257     if (property_data() != NULL) {
   258       if (printed)  st->print(" and ");
   259       st->print(INTPTR_FORMAT, property_data());
   260       printed = true;
   261     }
   262     st->print_cr(printed ? "" : "(empty)");
   263   }
   264 };
   266 // A system-internal mapping of symbols to pointers, both managed
   267 // and unmanaged.  Used to record the auto-generation of each method
   268 // MethodHandle.invoke(S)T, for all signatures (S)T.
   269 class SymbolPropertyTable : public Hashtable {
   270   friend class VMStructs;
   271 private:
   272   SymbolPropertyEntry* bucket(int i) {
   273     return (SymbolPropertyEntry*) Hashtable::bucket(i);
   274   }
   276   // The following method is not MT-safe and must be done under lock.
   277   SymbolPropertyEntry** bucket_addr(int i) {
   278     return (SymbolPropertyEntry**) Hashtable::bucket_addr(i);
   279   }
   281   void add_entry(int index, SymbolPropertyEntry* new_entry) {
   282     ShouldNotReachHere();
   283   }
   284   void set_entry(int index, SymbolPropertyEntry* new_entry) {
   285     ShouldNotReachHere();
   286   }
   288   SymbolPropertyEntry* new_entry(unsigned int hash, symbolOop symbol) {
   289     SymbolPropertyEntry* entry = (SymbolPropertyEntry*) Hashtable::new_entry(hash, symbol);
   290     entry->set_property_oop(NULL);
   291     entry->set_property_data(NULL);
   292     return entry;
   293   }
   295 public:
   296   SymbolPropertyTable(int table_size);
   297   SymbolPropertyTable(int table_size, HashtableBucket* t, int number_of_entries);
   299   void free_entry(SymbolPropertyEntry* entry) {
   300     Hashtable::free_entry(entry);
   301   }
   303   unsigned int compute_hash(symbolHandle sym) {
   304     // Use the regular identity_hash.
   305     return Hashtable::compute_hash(sym);
   306   }
   308   // need not be locked; no state change
   309   SymbolPropertyEntry* find_entry(int index, unsigned int hash, symbolHandle name);
   311   // must be done under SystemDictionary_lock
   312   SymbolPropertyEntry* add_entry(int index, unsigned int hash, symbolHandle name);
   314   // GC support
   315   void oops_do(OopClosure* f);
   316   void methods_do(void f(methodOop));
   318   // Sharing support
   319   void dump(SerializeOopClosure* soc);
   320   void restore(SerializeOopClosure* soc);
   321   void reorder_dictionary();
   323 #ifndef PRODUCT
   324   void print();
   325 #endif
   326   void verify();
   327 };

mercurial