symbolTable.hpp 6.9 KB
Newer Older
D
duke 已提交
1
/*
2
 * Copyright 1997-2009 Sun Microsystems, Inc.  All Rights Reserved.
D
duke 已提交
3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93
 * 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.
 *
 */

// The symbol table holds all symbolOops and corresponding interned strings.
// symbolOops and literal strings should be canonicalized.
//
// The interned strings are created lazily.
//
// It is implemented as an open hash table with a fixed number of buckets.
//
// %note:
//  - symbolTableEntrys are allocated in blocks to reduce the space overhead.

class BoolObjectClosure;


class SymbolTable : public Hashtable {
  friend class VMStructs;

private:
  // The symbol table
  static SymbolTable* _the_table;

  // Adding elements
  symbolOop basic_add(int index, u1* name, int len,
                      unsigned int hashValue, TRAPS);
  bool basic_add(constantPoolHandle cp, int names_count,
                 const char** names, int* lengths, int* cp_indices,
                 unsigned int* hashValues, TRAPS);

  // Table size
  enum {
    symbol_table_size = 20011
  };

  symbolOop lookup(int index, const char* name, int len, unsigned int hash);

  SymbolTable()
    : Hashtable(symbol_table_size, sizeof (HashtableEntry)) {}

  SymbolTable(HashtableBucket* t, int number_of_entries)
    : Hashtable(symbol_table_size, sizeof (HashtableEntry), t,
                number_of_entries) {}


public:
  enum {
    symbol_alloc_batch_size = 8
  };

  // The symbol table
  static SymbolTable* the_table() { return _the_table; }

  static void create_table() {
    assert(_the_table == NULL, "One symbol table allowed.");
    _the_table = new SymbolTable();
  }

  static void create_table(HashtableBucket* t, int length,
                           int number_of_entries) {
    assert(_the_table == NULL, "One symbol table allowed.");
    assert(length == symbol_table_size * sizeof(HashtableBucket),
           "bad shared symbol size.");
    _the_table = new SymbolTable(t, number_of_entries);
  }

  static symbolOop lookup(const char* name, int len, TRAPS);
  // lookup only, won't add. Also calculate hash.
  static symbolOop lookup_only(const char* name, int len, unsigned int& hash);
  // Only copy to C string to be added if lookup failed.
  static symbolOop lookup(symbolHandle sym, int begin, int end, TRAPS);

94 95 96 97
  // jchar (utf16) version of lookups
  static symbolOop lookup_unicode(const jchar* name, int len, TRAPS);
  static symbolOop lookup_only_unicode(const jchar* name, int len, unsigned int& hash);

D
duke 已提交
98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118
  static void add(constantPoolHandle cp, int names_count,
                  const char** names, int* lengths, int* cp_indices,
                  unsigned int* hashValues, TRAPS);

  // GC support
  //   Delete pointers to otherwise-unreachable objects.
  static void unlink(BoolObjectClosure* cl) {
    the_table()->Hashtable::unlink(cl);
  }

  // Invoke "f->do_oop" on the locations of all oops in the table.
  static void oops_do(OopClosure* f) {
    the_table()->Hashtable::oops_do(f);
  }

  // Symbol lookup
  static symbolOop lookup(int index, const char* name, int len, TRAPS);

  // Needed for preloading classes in signatures when compiling.
  // Returns the symbol is already present in symbol table, otherwise
  // NULL.  NO ALLOCATION IS GUARANTEED!
119 120 121 122 123 124 125 126
  static symbolOop probe(const char* name, int len) {
    unsigned int ignore_hash;
    return lookup_only(name, len, ignore_hash);
  }
  static symbolOop probe_unicode(const jchar* name, int len) {
    unsigned int ignore_hash;
    return lookup_only_unicode(name, len, ignore_hash);
  }
D
duke 已提交
127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224

  // Histogram
  static void print_histogram()     PRODUCT_RETURN;

  // Debugging
  static void verify();

  // Sharing
  static void copy_buckets(char** top, char*end) {
    the_table()->Hashtable::copy_buckets(top, end);
  }
  static void copy_table(char** top, char*end) {
    the_table()->Hashtable::copy_table(top, end);
  }
  static void reverse(void* boundary = NULL) {
    ((Hashtable*)the_table())->reverse(boundary);
  }
};


class StringTable : public Hashtable {
  friend class VMStructs;

private:
  // The string table
  static StringTable* _the_table;

  static oop intern(Handle string_or_null, jchar* chars, int length, TRAPS);
  oop basic_add(int index, Handle string_or_null, jchar* name, int len,
                unsigned int hashValue, TRAPS);

  // Table size
  enum {
    string_table_size = 1009
  };

  oop lookup(int index, jchar* chars, int length, unsigned int hashValue);

  StringTable() : Hashtable(string_table_size, sizeof (HashtableEntry)) {}

  StringTable(HashtableBucket* t, int number_of_entries)
    : Hashtable(string_table_size, sizeof (HashtableEntry), t,
                number_of_entries) {}

public:
  // The string table
  static StringTable* the_table() { return _the_table; }

  static void create_table() {
    assert(_the_table == NULL, "One string table allowed.");
    _the_table = new StringTable();
  }

  static void create_table(HashtableBucket* t, int length,
                           int number_of_entries) {
    assert(_the_table == NULL, "One string table allowed.");
    assert(length == string_table_size * sizeof(HashtableBucket),
           "bad shared string size.");
    _the_table = new StringTable(t, number_of_entries);
  }


  static int hash_string(jchar* s, int len);


  // GC support
  //   Delete pointers to otherwise-unreachable objects.
  static void unlink(BoolObjectClosure* cl) {
    the_table()->Hashtable::unlink(cl);
  }

  // Invoke "f->do_oop" on the locations of all oops in the table.
  static void oops_do(OopClosure* f) {
    the_table()->Hashtable::oops_do(f);
  }

  // Probing
  static oop lookup(symbolOop symbol);

  // Interning
  static oop intern(symbolOop symbol, TRAPS);
  static oop intern(oop string, TRAPS);
  static oop intern(const char *utf8_string, TRAPS);

  // Debugging
  static void verify();

  // Sharing
  static void copy_buckets(char** top, char*end) {
    the_table()->Hashtable::copy_buckets(top, end);
  }
  static void copy_table(char** top, char*end) {
    the_table()->Hashtable::copy_table(top, end);
  }
  static void reverse() {
    ((BasicHashtable*)the_table())->reverse();
  }
};