Changeset 406 for trunk/openjdk/hotspot


Ignore:
Timestamp:
Dec 21, 2012, 10:37:13 AM (13 years ago)
Author:
dmik
Message:

trunk: Merged in openjdk6 b27 from branches/vendor/oracle.

Location:
trunk/openjdk
Files:
29 edited
6 copied

Legend:

Unmodified
Added
Removed
  • trunk/openjdk

  • trunk/openjdk/hotspot/make/linux/Makefile

    r309 r406  
    231231# Disable this check by setting DISABLE_HOTSPOT_OS_VERSION_CHECK=ok.
    232232
    233 SUPPORTED_OS_VERSION = 2.4% 2.5% 2.6% 2.7%
     233SUPPORTED_OS_VERSION = 2.4% 2.5% 2.6% 3%
    234234OS_VERSION := $(shell uname -r)
    235235EMPTY_IF_NOT_SUPPORTED = $(filter $(SUPPORTED_OS_VERSION),$(OS_VERSION))
  • trunk/openjdk/hotspot/src/os_cpu/os2_x86/vm/os2_x86_32.s

  • trunk/openjdk/hotspot/src/share/vm/ci/ciField.cpp

    r309 r406  
    11/*
    2  * Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
     2 * Copyright (c) 1999, 2012, Oracle and/or its affiliates. All rights reserved.
    33 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    44 *
     
    6868// ------------------------------------------------------------------
    6969// ciField::ciField
    70 ciField::ciField(ciInstanceKlass* klass, int index): _known_to_link_with(NULL) {
     70ciField::ciField(ciInstanceKlass* klass, int index): _known_to_link_with_put(NULL), _known_to_link_with_get(NULL) {
    7171  ASSERT_IN_VM;
    7272  CompilerThread *thread = CompilerThread::current();
     
    144144}
    145145
    146 ciField::ciField(fieldDescriptor *fd): _known_to_link_with(NULL) {
     146ciField::ciField(fieldDescriptor *fd): _known_to_link_with_put(NULL), _known_to_link_with_get(NULL) {
    147147  ASSERT_IN_VM;
    148148
     
    313313                        Bytecodes::Code bc) {
    314314  VM_ENTRY_MARK;
     315  assert(bc == Bytecodes::_getstatic || bc == Bytecodes::_putstatic ||
     316         bc == Bytecodes::_getfield  || bc == Bytecodes::_putfield,
     317         "unexpected bytecode");
     318
    315319  if (_offset == -1) {
    316320    // at creation we couldn't link to our holder so we need to
     
    320324  }
    321325
    322   if (_known_to_link_with == accessing_klass) {
    323     return true;
     326  // Check for static/nonstatic mismatch
     327  bool is_static = (bc == Bytecodes::_getstatic || bc == Bytecodes::_putstatic);
     328  if (is_static != this->is_static()) {
     329    return false;
     330  }
     331
     332  // Get and put can have different accessibility rules
     333  bool is_put    = (bc == Bytecodes::_putfield  || bc == Bytecodes::_putstatic);
     334  if (is_put) {
     335    if (_known_to_link_with_put == accessing_klass) {
     336      return true;
     337    }
     338  } else {
     339    if (_known_to_link_with_get == accessing_klass) {
     340      return true;
     341    }
    324342  }
    325343
     
    332350
    333351  // update the hit-cache, unless there is a problem with memory scoping:
    334   if (accessing_klass->is_shared() || !is_shared())
    335     _known_to_link_with = accessing_klass;
     352  if (accessing_klass->is_shared() || !is_shared()) {
     353    if (is_put) {
     354      _known_to_link_with_put = accessing_klass;
     355    } else {
     356      _known_to_link_with_get = accessing_klass;
     357    }
     358  }
    336359
    337360  return true;
  • trunk/openjdk/hotspot/src/share/vm/ci/ciField.hpp

    r309 r406  
    11/*
    2  * Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
     2 * Copyright (c) 1999, 2012, Oracle and/or its affiliates. All rights reserved.
    33 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    44 *
     
    5050  int              _offset;
    5151  bool             _is_constant;
    52   ciInstanceKlass* _known_to_link_with;
     52  ciInstanceKlass* _known_to_link_with_put;
     53  ciInstanceKlass* _known_to_link_with_get;
    5354  ciConstant       _constant_value;
    5455
  • trunk/openjdk/hotspot/src/share/vm/classfile/javaClasses.cpp

    r309 r406  
    277277  }
    278278  return result;
     279}
     280
     281unsigned int java_lang_String::to_hash(oop java_string) {
     282  int          length = java_lang_String::length(java_string);
     283  // Zero length string will hash to zero with String.toHash() function.
     284  if (length == 0) return 0;
     285
     286  typeArrayOop value  = java_lang_String::value(java_string);
     287  int          offset = java_lang_String::offset(java_string);
     288  return java_lang_String::to_hash(value->char_at_addr(offset), length);
     289}
     290
     291unsigned int java_lang_String::hash_string(oop java_string) {
     292  int          length = java_lang_String::length(java_string);
     293  // Zero length string doesn't hash necessarily hash to zero.
     294  if (length == 0) {
     295    return StringTable::hash_string(NULL, 0);
     296  }
     297
     298  typeArrayOop value  = java_lang_String::value(java_string);
     299  int          offset = java_lang_String::offset(java_string);
     300  return StringTable::hash_string(value->char_at_addr(offset), length);
    279301}
    280302
  • trunk/openjdk/hotspot/src/share/vm/classfile/javaClasses.hpp

    r309 r406  
    109109  static char*  as_platform_dependent_str(Handle java_string, TRAPS);
    110110  static jchar* as_unicode_string(oop java_string, int& length);
     111
     112  // Compute the hash value for a java.lang.String object which would
     113  // contain the characters passed in.
     114  //
     115  // As the hash value used by the String object itself, in
     116  // String.hashCode().  This value is normally calculated in Java code
     117  // in the String.hashCode method(), but is precomputed for String
     118  // objects in the shared archive file.
     119  // hash P(31) from Kernighan & Ritchie
     120  //
     121  // For this reason, THIS ALGORITHM MUST MATCH String.toHash().
     122  template <typename T> static unsigned int to_hash(T* s, int len) {
     123    unsigned int h = 0;
     124    while (len-- > 0) {
     125      h = 31*h + (unsigned int) *s;
     126      s++;
     127    }
     128    return h;
     129  }
     130  static unsigned int to_hash(oop java_string);
     131
     132  // This is the string hash code used by the StringTable, which may be
     133  // the same as String.toHash or an alternate hash code.
     134  static unsigned int hash_string(oop java_string);
    111135
    112136  static bool equals(oop java_string, jchar* chars, int len);
  • trunk/openjdk/hotspot/src/share/vm/classfile/symbolTable.cpp

    r309 r406  
    2424
    2525#include "precompiled.hpp"
     26#include "classfile/altHashing.hpp"
    2627#include "classfile/javaClasses.hpp"
    2728#include "classfile/symbolTable.hpp"
     
    3536#include "runtime/mutexLocker.hpp"
    3637#include "utilities/hashtable.inline.hpp"
     38#include "utilities/numberSeq.hpp"
    3739
    3840// --------------------------------------------------------------------------
    3941
    4042SymbolTable* SymbolTable::_the_table = NULL;
     43bool SymbolTable::_needs_rehashing = false;
     44
     45// Create a new table and using alternate hash code, populate the new table
     46// with the existing strings.   Set flag to use the alternate hash code afterwards.
     47void SymbolTable::rehash_table() {
     48
     49  assert(SafepointSynchronize::is_at_safepoint(), "must be at safepoint");
     50  // This should never happen with -Xshare:dump but it might in testing mode.
     51  if (DumpSharedSpaces) return;
     52  // Create a new symbol table
     53  SymbolTable* new_table = new SymbolTable();
     54
     55  the_table()->move_to(new_table);
     56
     57  // Delete the table and buckets (entries are reused in new table).
     58  delete _the_table;
     59  // Don't check if we need rehashing until the table gets unbalanced again.
     60  // Then rehash with a new global seed.
     61  _needs_rehashing = false;
     62  _the_table = new_table;
     63}
    4164
    4265// Lookup a symbol in a bucket.
     
    4467symbolOop SymbolTable::lookup(int index, const char* name,
    4568                              int len, unsigned int hash) {
     69  int count = 0;
    4670  for (HashtableEntry* e = bucket(index); e != NULL; e = e->next()) {
     71    count++;
    4772    if (e->hash() == hash) {
    4873      symbolOop sym = symbolOop(e->literal());
     
    5277    }
    5378  }
     79  // If the bucket size is too deep check if this hash code is insufficient.
     80  if (count >= BasicHashtable::rehash_count && !needs_rehashing()) {
     81    _needs_rehashing = check_rehash_table(count);
     82  }
    5483  return NULL;
     84}
     85
     86// Pick hashing algorithm.
     87unsigned int SymbolTable::hash_symbol(const char* s, int len) {
     88  return the_table()->use_alternate_hashcode() ?
     89           AltHashing::murmur3_32(the_table()->seed(), (const jbyte*)s, len) :
     90           java_lang_String::to_hash(s, len);
    5591}
    5692
     
    72108  if (s != NULL) return s;
    73109
     110  // We assume that lookup() has been called already, that it failed,
     111  // and symbol was not found.  We create the symbol here.
     112  symbolKlass* sk  = (symbolKlass*) Universe::symbolKlassObj()->klass_part();
     113  symbolOop s_oop = sk->allocate_symbol((u1*)name, len, CHECK_NULL);
     114  symbolHandle sym (THREAD, s_oop);
     115
     116  // Allocation must be done before grabbing the SymbolTable_lock lock
     117  MutexLocker ml(SymbolTable_lock, THREAD);
     118
    74119  // Otherwise, add to symbol to table
    75   return the_table()->basic_add(index, (u1*)name, len, hashValue, CHECK_NULL);
     120  return the_table()->basic_add(sym, index, (u1*)name, len, hashValue, CHECK_NULL);
    76121}
    77122
     
    109154  // ResourceMark.
    110155
    111   return the_table()->basic_add(index, (u1*)buffer, len, hashValue, CHECK_NULL);
     156  // We assume that lookup() has been called already, that it failed,
     157  // and symbol was not found.  We create the symbol here.
     158  symbolKlass* sk  = (symbolKlass*) Universe::symbolKlassObj()->klass_part();
     159  symbolOop s_oop = sk->allocate_symbol((u1*)buffer, len, CHECK_NULL);
     160  symbolHandle newsym (THREAD, s_oop);
     161
     162  // Allocation must be done before grabbing the SymbolTable_lock lock
     163  MutexLocker ml(SymbolTable_lock, THREAD);
     164
     165  return the_table()->basic_add(newsym, index, (u1*)buffer, len, hashValue, CHECK_NULL);
    112166}
    113167
     
    157211                      const char** names, int* lengths, int* cp_indices,
    158212                      unsigned int* hashValues, TRAPS) {
    159   SymbolTable* table = the_table();
    160   bool added = table->basic_add(cp, names_count, names, lengths,
    161                                 cp_indices, hashValues, CHECK);
    162   if (!added) {
     213
     214  symbolKlass* sk  = (symbolKlass*) Universe::symbolKlassObj()->klass_part();
     215  symbolOop sym_oops[symbol_alloc_batch_size];
     216  bool allocated = sk->allocate_symbols(names_count, names, lengths,
     217                                        sym_oops, CHECK);
     218  if (!allocated) {
    163219    // do it the hard way
    164220    for (int i=0; i<names_count; i++) {
     221      assert(!Universe::heap()->is_in_reserved(names[i]) || GC_locker::is_active(),
     222         "proposed name of symbol must be stable");
     223
     224      // We assume that lookup() has been called already, that it failed,
     225      // and symbol was not found.  We create the symbol here.
     226      symbolKlass* sk  = (symbolKlass*) Universe::symbolKlassObj()->klass_part();
     227      symbolOop s_oop = sk->allocate_symbol((u1*)names[i], lengths[i], CHECK);
     228      symbolHandle sym (THREAD, s_oop);
     229
     230      // Allocation must be done before grabbing the SymbolTable_lock lock
     231      MutexLocker ml(SymbolTable_lock, THREAD);
     232
     233      SymbolTable* table = the_table();
    165234      int index = table->hash_to_index(hashValues[i]);
    166       symbolOop sym = table->basic_add(index, (u1*)names[i], lengths[i],
     235      symbolOop s = table->basic_add(sym, index, (u1*)names[i], lengths[i],
    167236                                       hashValues[i], CHECK);
    168       cp->symbol_at_put(cp_indices[i], sym);
    169     }
    170   }
    171 }
    172 
    173 symbolOop SymbolTable::basic_add(int index, u1 *name, int len,
    174                                  unsigned int hashValue, TRAPS) {
    175   assert(!Universe::heap()->is_in_reserved(name) || GC_locker::is_active(),
    176          "proposed name of symbol must be stable");
    177 
    178   // We assume that lookup() has been called already, that it failed,
    179   // and symbol was not found.  We create the symbol here.
    180   symbolKlass* sk  = (symbolKlass*) Universe::symbolKlassObj()->klass_part();
    181   symbolOop s_oop = sk->allocate_symbol(name, len, CHECK_NULL);
    182   symbolHandle sym (THREAD, s_oop);
    183 
    184   // Allocation must be done before grapping the SymbolTable_lock lock
     237      cp->symbol_at_put(cp_indices[i], s);
     238    }
     239    return;
     240  }
     241
     242  symbolHandle syms[symbol_alloc_batch_size];
     243  for (int i=0; i<names_count; i++) {
     244    syms[i] = symbolHandle(THREAD, sym_oops[i]);
     245  }
     246
     247  // Allocation must be done before grabbing the SymbolTable_lock lock
    185248  MutexLocker ml(SymbolTable_lock, THREAD);
    186249
     250  SymbolTable* table = the_table();
     251  bool added = table->basic_add(syms, cp, names_count, names, lengths,
     252                                cp_indices, hashValues, CHECK);
     253  assert(added, "should always return true");
     254}
     255
     256symbolOop SymbolTable::basic_add(symbolHandle sym, int index_arg, u1 *name, int len,
     257                                 unsigned int hashValue_arg, TRAPS) {
     258  // Cannot hit a safepoint in this function because the "this" pointer can move.
     259  No_Safepoint_Verifier nsv;
     260
    187261  assert(sym->equals((char*)name, len), "symbol must be properly initialized");
     262
     263  // Check if the symbol table has been rehashed, if so, need to recalculate
     264  // the hash value and index.
     265  unsigned int hashValue;
     266  int index;
     267  if (use_alternate_hashcode()) {
     268    hashValue = hash_symbol((const char*)name, len);
     269    index = hash_to_index(hashValue);
     270  } else {
     271    hashValue = hashValue_arg;
     272    index = index_arg;
     273  }
    188274
    189275  // Since look-up was done lock-free, we need to check if another
     
    202288}
    203289
    204 bool SymbolTable::basic_add(constantPoolHandle cp, int names_count,
     290bool SymbolTable::basic_add(symbolHandle* syms,
     291                            constantPoolHandle cp, int names_count,
    205292                            const char** names, int* lengths,
    206293                            int* cp_indices, unsigned int* hashValues,
    207294                            TRAPS) {
    208   symbolKlass* sk  = (symbolKlass*) Universe::symbolKlassObj()->klass_part();
    209   symbolOop sym_oops[symbol_alloc_batch_size];
    210   bool allocated = sk->allocate_symbols(names_count, names, lengths,
    211                                         sym_oops, CHECK_false);
    212   if (!allocated) {
    213     return false;
    214   }
    215   symbolHandle syms[symbol_alloc_batch_size];
    216   int i;
    217   for (i=0; i<names_count; i++) {
    218     syms[i] = symbolHandle(THREAD, sym_oops[i]);
    219   }
    220 
    221   // Allocation must be done before grabbing the SymbolTable_lock lock
    222   MutexLocker ml(SymbolTable_lock, THREAD);
    223 
    224   for (i=0; i<names_count; i++) {
     295  // Cannot hit a safepoint in this function because the "this" pointer can move.
     296  No_Safepoint_Verifier nsv;
     297
     298  for (int i=0; i<names_count; i++) {
    225299    assert(syms[i]->equals(names[i], lengths[i]), "symbol must be properly initialized");
     300    // Check if the symbol table has been rehashed, if so, need to recalculate
     301    // the hash value.
     302    unsigned int hashValue;
     303    if (use_alternate_hashcode()) {
     304      hashValue = hash_symbol(names[i], lengths[i]);
     305    } else {
     306      hashValue = hashValues[i];
     307    }
    226308    // Since look-up was done lock-free, we need to check if another
    227309    // thread beat us in the race to insert the symbol.
    228     int index = hash_to_index(hashValues[i]);
    229     symbolOop test = lookup(index, names[i], lengths[i], hashValues[i]);
     310    int index = hash_to_index(hashValue);
     311    symbolOop test = lookup(index, names[i], lengths[i], hashValue);
    230312    if (test != NULL) {
    231313      // A race occurred and another thread introduced the symbol, this one
     
    234316    } else {
    235317      symbolOop sym = syms[i]();
    236       HashtableEntry* entry = new_entry(hashValues[i], sym);
     318      HashtableEntry* entry = new_entry(hashValue, sym);
    237319      add_entry(index, entry);
    238320      cp->symbol_at_put(cp_indices[i], sym);
    239321    }
    240322  }
    241 
    242   return true;
    243 }
    244 
     323  return true;  // always returns true
     324}
    245325
    246326void SymbolTable::verify() {
     
    252332      s->verify();
    253333      guarantee(s->is_perm(), "symbol not in permspace");
    254       unsigned int h = hash_symbol((char*)s->bytes(), s->utf8_length());
     334      unsigned int h = hash_symbol((const char*)s->bytes(), s->utf8_length());
    255335      guarantee(p->hash() == h, "broken hash in symbol table entry");
    256336      guarantee(the_table()->hash_to_index(h) == i,
     
    260340}
    261341
     342void SymbolTable::dump(outputStream* st) {
     343  NumberSeq summary;
     344  for (int i = 0; i < the_table()->table_size(); ++i) {
     345    int count = 0;
     346    for (HashtableEntry* e = the_table()->bucket(i);
     347       e != NULL; e = e->next()) {
     348      count++;
     349    }
     350    summary.add((double)count);
     351  }
     352  st->print_cr("SymbolTable statistics:");
     353  st->print_cr("Number of buckets       : %7d", summary.num());
     354  st->print_cr("Average bucket size     : %7.0f", summary.avg());
     355  st->print_cr("Variance of bucket size : %7.0f", summary.variance());
     356  st->print_cr("Std. dev. of bucket size: %7.0f", summary.sd());
     357  st->print_cr("Maximum bucket size     : %7.0f", summary.maximum());
     358}
    262359
    263360//---------------------------------------------------------------------------
     
    322419                    results_length, out_of_range);
    323420}
    324 
    325421#endif // PRODUCT
    326422
     
    368464
    369465
    370 // Compute the hash value for a java.lang.String object which would
    371 // contain the characters passed in. This hash value is used for at
    372 // least two purposes.
    373 //
    374 // (a) As the hash value used by the StringTable for bucket selection
    375 //     and comparison (stored in the HashtableEntry structures).  This
    376 //     is used in the String.intern() method.
    377 //
    378 // (b) As the hash value used by the String object itself, in
    379 //     String.hashCode().  This value is normally calculate in Java code
    380 //     in the String.hashCode method(), but is precomputed for String
    381 //     objects in the shared archive file.
    382 //
    383 //     For this reason, THIS ALGORITHM MUST MATCH String.hashCode().
    384 
    385 int StringTable::hash_string(jchar* s, int len) {
    386   unsigned h = 0;
    387   while (len-- > 0) {
    388     h = 31*h + (unsigned) *s;
    389     s++;
    390   }
    391   return h;
    392 }
    393 
    394 
    395466StringTable* StringTable::_the_table = NULL;
     467
     468bool StringTable::_needs_rehashing = false;
     469
     470// Pick hashing algorithm
     471unsigned int StringTable::hash_string(const jchar* s, int len) {
     472  return the_table()->use_alternate_hashcode() ? AltHashing::murmur3_32(the_table()->seed(), s, len) :
     473                                    java_lang_String::to_hash(s, len);
     474}
    396475
    397476oop StringTable::lookup(int index, jchar* name,
    398477                        int len, unsigned int hash) {
     478  int count = 0;
    399479  for (HashtableEntry* l = bucket(index); l != NULL; l = l->next()) {
     480    count++;
    400481    if (l->hash() == hash) {
    401482      if (java_lang_String::equals(l->literal(), name, len)) {
     
    404485    }
    405486  }
     487  // If the bucket size is too deep check if this hash code is insufficient.
     488  if (count >= BasicHashtable::rehash_count && !needs_rehashing()) {
     489    _needs_rehashing = check_rehash_table(count);
     490  }
    406491  return NULL;
    407492}
    408493
    409494
    410 oop StringTable::basic_add(int index, Handle string_or_null, jchar* name,
    411                            int len, unsigned int hashValue, TRAPS) {
    412   debug_only(StableMemoryChecker smc(name, len * sizeof(name[0])));
    413   assert(!Universe::heap()->is_in_reserved(name) || GC_locker::is_active(),
    414          "proposed name of symbol must be stable");
    415 
    416   Handle string;
    417   // try to reuse the string if possible
    418   if (!string_or_null.is_null() && string_or_null()->is_perm()) {
    419     string = string_or_null;
    420   } else {
    421     string = java_lang_String::create_tenured_from_unicode(name, len, CHECK_NULL);
    422   }
    423 
    424   // Allocation must be done before grapping the SymbolTable_lock lock
    425   MutexLocker ml(StringTable_lock, THREAD);
     495oop StringTable::basic_add(int index_arg, Handle string, jchar* name,
     496                           int len, unsigned int hashValue_arg, TRAPS) {
     497
     498  // Cannot hit a safepoint in this function because the "this" pointer can move.
     499  No_Safepoint_Verifier nsv;
    426500
    427501  assert(java_lang_String::equals(string(), name, len),
    428502         "string must be properly initialized");
     503
     504  // Check if the symbol table has been rehashed, if so, need to recalculate
     505  // the hash value and index before second lookup.
     506  unsigned int hashValue;
     507  int index;
     508  if (use_alternate_hashcode()) {
     509    hashValue = hash_string(name, len);
     510    index = hash_to_index(hashValue);
     511  } else {
     512    hashValue = hashValue_arg;
     513    index = index_arg;
     514  }
    429515
    430516  // Since look-up was done lock-free, we need to check if another
     
    457543  unsigned int hashValue = hash_string(name, len);
    458544  int index = the_table()->hash_to_index(hashValue);
    459   oop string = the_table()->lookup(index, name, len, hashValue);
     545  oop found_string = the_table()->lookup(index, name, len, hashValue);
    460546
    461547  // Found
    462   if (string != NULL) return string;
     548  if (found_string != NULL) return found_string;
     549
     550  debug_only(StableMemoryChecker smc(name, len * sizeof(name[0])));
     551  assert(!Universe::heap()->is_in_reserved(name) || GC_locker::is_active(),
     552         "proposed name of symbol must be stable");
     553
     554  Handle string;
     555  // try to reuse the string if possible
     556  if (!string_or_null.is_null() && string_or_null()->is_perm()) {
     557    string = string_or_null;
     558  } else {
     559    string = java_lang_String::create_tenured_from_unicode(name, len, CHECK_NULL);
     560  }
     561
     562  // Allocation must be done before grabbing the StringTable_lock lock
     563  MutexLocker ml(StringTable_lock, THREAD);
    463564
    464565  // Otherwise, add to symbol to table
    465   return the_table()->basic_add(index, string_or_null, name, len,
     566  return the_table()->basic_add(index, string, name, len,
    466567                                hashValue, CHECK_NULL);
    467568}
     
    518619  }
    519620}
     621
     622void StringTable::dump(outputStream* st) {
     623  NumberSeq summary;
     624  for (int i = 0; i < the_table()->table_size(); ++i) {
     625    HashtableEntry* p = the_table()->bucket(i);
     626    int count = 0;
     627    for ( ; p != NULL; p = p->next()) {
     628      count++;
     629    }
     630    summary.add((double)count);
     631  }
     632  st->print_cr("StringTable statistics:");
     633  st->print_cr("Number of buckets       : %7d", summary.num());
     634  st->print_cr("Average bucket size     : %7.0f", summary.avg());
     635  st->print_cr("Variance of bucket size : %7.0f", summary.variance());
     636  st->print_cr("Std. dev. of bucket size: %7.0f", summary.sd());
     637  st->print_cr("Maximum bucket size     : %7.0f", summary.maximum());
     638}
     639
     640
     641// Create a new table and using alternate hash code, populate the new table
     642// with the existing strings.   Set flag to use the alternate hash code afterwards.
     643void StringTable::rehash_table() {
     644  assert(SafepointSynchronize::is_at_safepoint(), "must be at safepoint");
     645  // This should never happen with -Xshare:dump but it might in testing mode.
     646  if (DumpSharedSpaces) return;
     647  StringTable* new_table = new StringTable();
     648
     649  // Rehash the table
     650  the_table()->move_to(new_table);
     651
     652  // Delete the table and buckets (entries are reused in new table).
     653  delete _the_table;
     654  // Don't check if we need rehashing until the table gets unbalanced again.
     655  // Then rehash with a new global seed.
     656  _needs_rehashing = false;
     657  _the_table = new_table;
     658}
  • trunk/openjdk/hotspot/src/share/vm/classfile/symbolTable.hpp

    r309 r406  
    4141
    4242class BoolObjectClosure;
     43class outputStream;
    4344
    4445
     
    5051  static SymbolTable* _the_table;
    5152
     53  // Set if one bucket is out of balance due to hash algorithm deficiency
     54  static bool _needs_rehashing;
     55
    5256  // Adding elements
    53   symbolOop basic_add(int index, u1* name, int len,
     57  symbolOop basic_add(symbolHandle sym, int index, u1* name, int len,
    5458                      unsigned int hashValue, TRAPS);
    55   bool basic_add(constantPoolHandle cp, int names_count,
     59  bool basic_add(symbolHandle* syms, constantPoolHandle cp, int names_count,
    5660                 const char** names, int* lengths, int* cp_indices,
    5761                 unsigned int* hashValues, TRAPS);
     
    6266  };
    6367
     68  static unsigned int hash_symbol(const char* s, int len);
     69
    6470  symbolOop lookup(int index, const char* name, int len, unsigned int hash);
    6571
     
    7076    : Hashtable(symbol_table_size, sizeof (HashtableEntry), t,
    7177                number_of_entries) {}
    72 
    7378
    7479public:
     
    138143  // Debugging
    139144  static void verify();
     145  static void dump(outputStream* st);
    140146
    141147  // Sharing
     
    149155    ((Hashtable*)the_table())->reverse(boundary);
    150156  }
     157
     158  // Rehash the symbol table if it gets out of balance
     159  static void rehash_table();
     160  static bool needs_rehashing()         { return _needs_rehashing; }
    151161};
    152162
     
    159169  static StringTable* _the_table;
    160170
     171  // Set if one bucket is out of balance due to hash algorithm deficiency
     172  static bool _needs_rehashing;
     173
    161174  static oop intern(Handle string_or_null, jchar* chars, int length, TRAPS);
    162   oop basic_add(int index, Handle string_or_null, jchar* name, int len,
     175  oop basic_add(int index, Handle string, jchar* name, int len,
    163176                unsigned int hashValue, TRAPS);
    164177
     
    193206  }
    194207
    195 
    196   static int hash_string(jchar* s, int len);
    197 
    198 
    199208  // GC support
    200209  //   Delete pointers to otherwise-unreachable objects.
     
    208217  }
    209218
     219  // Hashing algorithm, used as the hash value used by the
     220  //     StringTable for bucket selection and comparison (stored in the
     221  //     HashtableEntry structures).  This is used in the String.intern() method.
     222  static unsigned int hash_string(const jchar* s, int len);
     223
     224  // Internal test.
     225  static void test_alt_hash() PRODUCT_RETURN;
     226
    210227  // Probing
    211228  static oop lookup(symbolOop symbol);
     
    218235  // Debugging
    219236  static void verify();
     237  static void dump(outputStream* st);
    220238
    221239  // Sharing
     
    229247    ((BasicHashtable*)the_table())->reverse();
    230248  }
     249
     250  // Rehash the symbol table if it gets out of balance
     251  static void rehash_table();
     252  static bool needs_rehashing() { return _needs_rehashing; }
    231253};
    232 
    233254#endif // SHARE_VM_CLASSFILE_SYMBOLTABLE_HPP
  • trunk/openjdk/hotspot/src/share/vm/classfile/verifier.cpp

    r309 r406  
    18721872    VerificationType::reference_check(), CHECK_VERIFY(this));
    18731873  if (type == VerificationType::uninitialized_this_type()) {
    1874     // The method must be an <init> method of either this class, or one of its
    1875     // superclasses
     1874    // The method must be an <init> method of this class or its superclass
     1875    klassOop superk = current_class()->super();
    18761876    if (ref_class_type.name() != current_class()->name() &&
    1877         !name_in_supers(ref_class_type.name(), current_class())) {
     1877        ref_class_type.name() != superk->klass_part()->name()) {
    18781878      verify_error(bci, "Bad <init> method call");
    18791879      return;
  • trunk/openjdk/hotspot/src/share/vm/compiler/compilerOracle.cpp

    r309 r406  
    552552
    553553static const char* cc_file() {
    554   if (CompileCommandFile == NULL)
     554#ifdef ASSERT
     555  if (CompileCommandFile == NULL) {
    555556    return ".hotspot_compiler";
     557  }
     558#endif
    556559  return CompileCommandFile;
    557560}
     561
     562bool CompilerOracle::has_command_file() {
     563  return cc_file() != NULL;
     564}
     565
    558566bool CompilerOracle::_quiet = false;
    559567
    560568void CompilerOracle::parse_from_file() {
     569  assert(has_command_file(), "command file must be specified");
    561570  FILE* stream = fopen(cc_file(), "rt");
    562571  if (stream == NULL) return;
     
    565574  int  pos = 0;
    566575  int  c = getc(stream);
    567   while(c != EOF) {
     576  while(c != EOF && pos < (int)(sizeof(token)-1)) {
    568577    if (c == '\n') {
    569578      token[pos++] = '\0';
     
    586595  const char* sp = str;
    587596  int  c = *sp++;
    588   while (c != '\0') {
     597  while (c != '\0' && pos < (int)(sizeof(token)-1)) {
    589598    if (c == '\n') {
    590599      token[pos++] = '\0';
     
    601610
    602611void CompilerOracle::append_comment_to_file(const char* message) {
     612  assert(has_command_file(), "command file must be specified");
    603613  fileStream stream(fopen(cc_file(), "at"));
    604614  stream.print("# ");
     
    611621
    612622void CompilerOracle::append_exclude_to_file(methodHandle method) {
     623  assert(has_command_file(), "command file must be specified");
    613624  fileStream stream(fopen(cc_file(), "at"));
    614625  stream.print("exclude ");
     
    625636  CompilerOracle::parse_from_string(CompileCommand, CompilerOracle::parse_from_line);
    626637  CompilerOracle::parse_from_string(CompileOnly, CompilerOracle::parse_compile_only);
    627   CompilerOracle::parse_from_file();
     638  if (CompilerOracle::has_command_file()) {
     639    CompilerOracle::parse_from_file();
     640  }
    628641  if (lists[PrintCommand] != NULL) {
    629642    if (PrintAssembly) {
  • trunk/openjdk/hotspot/src/share/vm/compiler/compilerOracle.hpp

    r309 r406  
    3939
    4040 public:
     41
     42  // True if the command file has been specified or is implicit
     43  static bool has_command_file();
     44
    4145  // Reads from file and adds to lists
    4246  static void parse_from_file();
  • trunk/openjdk/hotspot/src/share/vm/memory/dump.cpp

    r309 r406  
    6363// the hash can be shared.
    6464//
    65 // NOTE THAT the algorithm in StringTable::hash_string() MUST MATCH the
    66 // algorithm in java.lang.String.hashCode().
     65// NOTE THAT we have to call java_lang_String::to_hash() to match the
     66// algorithm in java.lang.String.toHash().
    6767
    6868class StringHashCodeClosure: public OopClosure {
     
    8989          int offset = java_lang_String::offset(obj);
    9090          jchar* s = value->char_at_addr(offset);
    91           hash = StringTable::hash_string(s, length);
     91          hash = java_lang_String::to_hash(s, length);
    9292        }
    9393        obj->int_field_put(hash_offset, hash);
  • trunk/openjdk/hotspot/src/share/vm/opto/addnode.cpp

    r309 r406  
    3434
    3535// Portions of code courtesy of Clifford Click
    36 
    37 #define MAXFLOAT        ((float)3.40282346638528860e+38)
    3836
    3937// Classic Add functionality.  This covers all the usual 'add' behaviors for
  • trunk/openjdk/hotspot/src/share/vm/opto/loopTransform.cpp

    r390 r406  
    27222722  _igvn.register_new_node_with_optimizer(result_mem);
    27232723
     2724/* Disable following optimization until proper fix (add missing checks).
     2725
    27242726  // If this fill is tightly coupled to an allocation and overwrites
    27252727  // the whole body, allow it to take over the zeroing.
     
    27452747    }
    27462748  }
     2749*/
    27472750
    27482751  // Redirect the old control and memory edges that are outside the loop.
  • trunk/openjdk/hotspot/src/share/vm/opto/loopnode.cpp

    r309 r406  
    11/*
    2  * Copyright (c) 1998, 2010, Oracle and/or its affiliates. All rights reserved.
     2 * Copyright (c) 1998, 2012, Oracle and/or its affiliates. All rights reserved.
    33 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    44 *
     
    547547                      Node* expr, Node** trunc1, Node** trunc2, const TypeInt** trunc_type) {
    548548  // Quick cutouts:
    549   if (expr == NULL || expr->req() != 3)  return false;
     549  if (expr == NULL || expr->req() != 3)  return NULL;
    550550
    551551  Node *t1 = NULL;
  • trunk/openjdk/hotspot/src/share/vm/opto/runtime.cpp

    r309 r406  
    805805      tty->print_cr("# Method where it happened %s.%s ", Klass::cast(method->method_holder())->name()->as_C_string(), method->name()->as_C_string());
    806806      tty->print_cr("#");
    807       if (ShowMessageBoxOnError && UpdateHotSpotCompilerFileOnError) {
     807      if (ShowMessageBoxOnError && UpdateHotSpotCompilerFileOnError &&
     808          CompilerOracle::has_command_file()) {
    808809        const char* title    = "HotSpot Runtime Error";
    809810        const char* question = "Do you want to exclude compilation of this method in future runs?";
  • trunk/openjdk/hotspot/src/share/vm/prims/jniCheck.cpp

    r309 r406  
    102102      NativeReportJNIFatalError(thr, warn_wrong_jnienv);                 \
    103103    }                                                                    \
    104     __ENTRY(result_type, header, thr)
     104    VM_ENTRY_BASE(result_type, header, thr)
    105105
    106106
  • trunk/openjdk/hotspot/src/share/vm/prims/jvmtiEnter.xsl

    r309 r406  
    427427    <xsl:text>ThreadInVMfromNative __tiv(current_thread);</xsl:text>
    428428    <xsl:value-of select="$space"/>
    429     <xsl:text>__ENTRY(jvmtiError, </xsl:text>
     429    <xsl:text>VM_ENTRY_BASE(jvmtiError, </xsl:text>
    430430    <xsl:apply-templates select="." mode="functionid"/>
    431431    <xsl:text> , current_thread)</xsl:text>
  • trunk/openjdk/hotspot/src/share/vm/prims/jvmtiEnv.cpp

    r309 r406  
    171171
    172172    ThreadInVMfromNative __tiv(current_thread);
    173     __ENTRY(jvmtiError, JvmtiEnv::GetThreadLocalStorage , current_thread)
     173    VM_ENTRY_BASE(jvmtiError, JvmtiEnv::GetThreadLocalStorage , current_thread)
    174174    debug_only(VMNativeEntryWrapper __vew;)
    175175
  • trunk/openjdk/hotspot/src/share/vm/prims/jvmtiExport.cpp

    r390 r406  
    374374    // transition code: native to VM
    375375    ThreadInVMfromNative __tiv(current_thread);
    376     __ENTRY(jvmtiEnv*, JvmtiExport::get_jvmti_interface, current_thread)
     376    VM_ENTRY_BASE(jvmtiEnv*, JvmtiExport::get_jvmti_interface, current_thread)
    377377    debug_only(VMNativeEntryWrapper __vew;)
    378378
  • trunk/openjdk/hotspot/src/share/vm/runtime/arguments.cpp

    r309 r406  
    11/*
    2  * Copyright (c) 1997, 2011, Oracle and/or its affiliates. All rights reserved.
     2 * Copyright (c) 1997, 2012, Oracle and/or its affiliates. All rights reserved.
    33 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    44 *
     
    843843
    844844  int c = getc(stream);
    845   while(c != EOF) {
     845  while(c != EOF && pos < (int)(sizeof(token)-1)) {
    846846    if (in_white_space) {
    847847      if (in_comment) {
     
    29692969  }
    29702970
     2971#ifdef ASSERT
    29712972  // Parse default .hotspotrc settings file
    29722973  if (!settings_file_specified) {
     
    29752976    }
    29762977  }
     2978#endif
    29772979
    29782980  if (PrintVMOptions) {
  • trunk/openjdk/hotspot/src/share/vm/runtime/globals.hpp

    r390 r406  
    25122512          "use heavyweight instead of lightweight Java monitors")           \
    25132513                                                                            \
     2514  product(bool, PrintStringTableStatistics, false,                          \
     2515          "print statistics about the StringTable and SymbolTable")         \
     2516                                                                            \
    25142517  notproduct(bool, PrintSymbolTableSizeHistogram, false,                    \
    25152518          "print histogram of the symbol table")                            \
  • trunk/openjdk/hotspot/src/share/vm/runtime/init.cpp

    r309 r406  
    2424
    2525#include "precompiled.hpp"
     26#include "classfile/symbolTable.hpp"
    2627#include "code/icBuffer.hpp"
    2728#include "gc_interface/collectedHeap.hpp"
     
    154155      SafepointSynchronize::print_stat_on_exit();
    155156    }
     157    if (PrintStringTableStatistics) {
     158      SymbolTable::dump(tty);
     159      StringTable::dump(tty);
     160    }
    156161    ostream_exit();
    157162  }
  • trunk/openjdk/hotspot/src/share/vm/runtime/interfaceSupport.hpp

    r309 r406  
    7070};
    7171
    72 // InterfaceSupport provides functionality used by the __LEAF and __ENTRY
    73 // macros. These macros are used to guard entry points into the VM and
    74 // perform checks upon leave of the VM.
     72// InterfaceSupport provides functionality used by the VM_LEAF_BASE and
     73// VM_ENTRY_BASE macros. These macros are used to guard entry points into
     74// the VM and perform checks upon leave of the VM.
    7575
    7676
     
    424424// LEAF routines do not lock, GC or throw exceptions
    425425
    426 #define __LEAF(result_type, header)                                  \
     426#define VM_LEAF_BASE(result_type, header)                            \
    427427  TRACE_CALL(result_type, header)                                    \
    428428  debug_only(NoHandleMark __hm;)                                     \
     
    432432// ENTRY routines may lock, GC and throw exceptions
    433433
    434 #define __ENTRY(result_type, header, thread)                         \
     434#define VM_ENTRY_BASE(result_type, header, thread)                   \
    435435  TRACE_CALL(result_type, header)                                    \
    436436  HandleMarkCleaner __hm(thread);                                    \
     
    441441// QUICK_ENTRY routines behave like ENTRY but without a handle mark
    442442
    443 #define __QUICK_ENTRY(result_type, header, thread)                   \
     443#define VM_QUICK_ENTRY_BASE(result_type, header, thread)             \
    444444  TRACE_CALL(result_type, header)                                    \
    445445  debug_only(NoHandleMark __hm;)                                     \
     
    454454  result_type header {                                               \
    455455    ThreadInVMfromJava __tiv(thread);                                \
    456     __ENTRY(result_type, header, thread)                             \
     456    VM_ENTRY_BASE(result_type, header, thread)                       \
    457457    debug_only(VMEntryWrapper __vew;)
    458458
     
    460460#define IRT_LEAF(result_type, header)                                \
    461461  result_type header {                                               \
    462     __LEAF(result_type, header)                                      \
     462    VM_LEAF_BASE(result_type, header)                                \
    463463    debug_only(No_Safepoint_Verifier __nspv(true);)
    464464
     
    467467  result_type header {                                               \
    468468    ThreadInVMfromJavaNoAsyncException __tiv(thread);                \
    469     __ENTRY(result_type, header, thread)                             \
     469    VM_ENTRY_BASE(result_type, header, thread)                       \
    470470    debug_only(VMEntryWrapper __vew;)
    471471
     
    478478    nmethodLocker _nmlock(nm);                                       \
    479479    ThreadInVMfromJavaNoAsyncException __tiv(thread);                                \
    480     __ENTRY(result_type, header, thread)
     480    VM_ENTRY_BASE(result_type, header, thread)
    481481
    482482#define IRT_END }
     
    488488  result_type header {                                               \
    489489    ThreadInVMfromJava __tiv(thread);                                \
    490     __ENTRY(result_type, header, thread)                             \
     490    VM_ENTRY_BASE(result_type, header, thread)                       \
    491491    debug_only(VMEntryWrapper __vew;)
    492492
     
    494494#define JRT_LEAF(result_type, header)                                \
    495495  result_type header {                                               \
    496   __LEAF(result_type, header)                                        \
     496  VM_LEAF_BASE(result_type, header)                                  \
    497497  debug_only(JRT_Leaf_Verifier __jlv;)
    498498
     
    501501  result_type header {                                               \
    502502    ThreadInVMfromJavaNoAsyncException __tiv(thread);                \
    503     __ENTRY(result_type, header, thread)                             \
     503    VM_ENTRY_BASE(result_type, header, thread)                       \
    504504    debug_only(VMEntryWrapper __vew;)
    505505
     
    534534    ThreadInVMfromNative __tiv(thread);                              \
    535535    debug_only(VMNativeEntryWrapper __vew;)                          \
    536     __ENTRY(result_type, header, thread)
     536    VM_ENTRY_BASE(result_type, header, thread)
    537537
    538538
    539539// Ensure that the VMNativeEntryWrapper constructor, which can cause
    540 // a GC, is called outside the NoHandleMark (set via __QUICK_ENTRY).
     540// a GC, is called outside the NoHandleMark (set via VM_QUICK_ENTRY_BASE).
    541541#define JNI_QUICK_ENTRY(result_type, header)                         \
    542542extern "C" {                                                         \
     
    546546    ThreadInVMfromNative __tiv(thread);                              \
    547547    debug_only(VMNativeEntryWrapper __vew;)                          \
    548     __QUICK_ENTRY(result_type, header, thread)
     548    VM_QUICK_ENTRY_BASE(result_type, header, thread)
    549549
    550550
     
    554554    JavaThread* thread=JavaThread::thread_from_jni_environment(env); \
    555555    assert( !VerifyJNIEnvThread || (thread == Thread::current()), "JNIEnv is only valid in same thread"); \
    556     __LEAF(result_type, header)
     556    VM_LEAF_BASE(result_type, header)
    557557
    558558
     
    570570    ThreadInVMfromNative __tiv(thread);                              \
    571571    debug_only(VMNativeEntryWrapper __vew;)                          \
    572     __ENTRY(result_type, header, thread)
     572    VM_ENTRY_BASE(result_type, header, thread)
    573573
    574574
     
    579579    ThreadInVMfromNative __tiv(thread);                              \
    580580    debug_only(VMNativeEntryWrapper __vew;)                          \
    581     __ENTRY(result_type, header, thread)
     581    VM_ENTRY_BASE(result_type, header, thread)
    582582
    583583
     
    588588    ThreadInVMfromNative __tiv(thread);                              \
    589589    debug_only(VMNativeEntryWrapper __vew;)                          \
    590     __QUICK_ENTRY(result_type, header, thread)
     590    VM_QUICK_ENTRY_BASE(result_type, header, thread)
    591591
    592592
     
    595595  result_type JNICALL header {                                       \
    596596    VM_Exit::block_if_vm_exited();                                   \
    597     __LEAF(result_type, header)
     597    VM_LEAF_BASE(result_type, header)
    598598
    599599
  • trunk/openjdk/hotspot/src/share/vm/runtime/safepoint.cpp

    r309 r406  
    2424
    2525#include "precompiled.hpp"
     26#include "classfile/symbolTable.hpp"
    2627#include "classfile/systemDictionary.hpp"
    2728#include "code/codeCache.hpp"
     
    502503  }
    503504
    504   TraceTime t4("sweeping nmethods", TraceSafepointCleanupTime);
    505   NMethodSweeper::scan_stacks();
     505  {
     506    TraceTime t4("sweeping nmethods", TraceSafepointCleanupTime);
     507    NMethodSweeper::scan_stacks();
     508  }
     509
     510  if (SymbolTable::needs_rehashing()) {
     511    TraceTime t5("rehashing symbol table", TraceSafepointCleanupTime);
     512    SymbolTable::rehash_table();
     513  }
     514
     515  if (StringTable::needs_rehashing()) {
     516    TraceTime t6("rehashing string table", TraceSafepointCleanupTime);
     517    StringTable::rehash_table();
     518  }
    506519}
    507520
  • trunk/openjdk/hotspot/src/share/vm/utilities/hashtable.cpp

    r309 r406  
    1 /*
    2  * Copyright (c) 2003, 2010, Oracle and/or its affiliates. All rights reserved.
     1/* * Copyright (c) 2003, 2012, Oracle and/or its affiliates. All rights reserved.
    32 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    43 *
     
    2423
    2524#include "precompiled.hpp"
     25#include "classfile/altHashing.hpp"
     26#include "classfile/javaClasses.hpp"
    2627#include "memory/allocation.inline.hpp"
     28#include "memory/filemap.hpp"
    2729#include "memory/resourceArea.hpp"
    2830#include "oops/oop.inline.hpp"
     
    7072HashtableEntry* Hashtable::new_entry(unsigned int hashValue, oop obj) {
    7173  HashtableEntry* entry;
    72 
    7374  entry = (HashtableEntry*)BasicHashtable::new_entry(hashValue);
    7475  entry->set_literal(obj);   // clears literal string field
     
    8687  assert(SafepointSynchronize::is_at_safepoint(), "must be at safepoint");
    8788  for (int i = 0; i < table_size(); ++i) {
    88     for (HashtableEntry** p = bucket_addr(i); *p != NULL; ) {
    89       HashtableEntry* entry = *p;
    90       if (entry->is_shared()) {
     89    HashtableEntry** p = bucket_addr(i);
     90    HashtableEntry* entry = bucket(i);
     91    while (entry != NULL) {
     92      // Shared entries are normally at the end of the bucket and if we run into
     93      // a shared entry, then there is nothing more to remove. However, if we
     94      // have rehashed the table, then the shared entries are no longer at the
     95      // end of the bucket.
     96      if (entry->is_shared() && !use_alternate_hashcode()) {
    9197        break;
    9298      }
    9399      assert(entry->literal() != NULL, "just checking");
    94       if (is_alive->do_object_b(entry->literal())) {
     100      if (entry->is_shared() || is_alive->do_object_b(entry->literal())) {
    95101        p = entry->next_addr();
    96102      } else {
     
    98104        free_entry(entry);
    99105      }
     106      entry = (HashtableEntry*)HashtableEntry::make_ptr(*p);
    100107    }
    101108  }
     
    120127      entry = (HashtableEntry*)HashtableEntry::make_ptr(*p);
    121128    }
     129  }
     130}
     131
     132
     133// Check to see if the hashtable is unbalanced.  The caller set a flag to
     134// rehash at the next safepoint.  If this bucket is 60 times greater than the
     135// expected average bucket length, it's an unbalanced hashtable.
     136// This is somewhat an arbitrary heuristic but if one bucket gets to
     137// rehash_count which is currently 100, there's probably something wrong.
     138
     139bool BasicHashtable::check_rehash_table(int count) {
     140  assert(table_size() != 0, "underflow");
     141  if (count > (((double)number_of_entries()/(double)table_size())*rehash_multiple)) {
     142    // Set a flag for the next safepoint, which should be at some guaranteed
     143    // safepoint interval.
     144    return true;
     145  }
     146  return false;
     147}
     148
     149unsigned int Hashtable::new_hash(oop string) {
     150  ResourceMark rm;
     151  int length;
     152  if (java_lang_String::is_instance(string)) {
     153    jchar* chars = java_lang_String::as_unicode_string(string, length);
     154    // Use alternate hashing algorithm on the string
     155    return AltHashing::murmur3_32(seed(), chars, length);
     156  } else {
     157    // Use alternate hashing algorithm on this symbol.
     158    symbolOop symOop = (symbolOop) string;
     159    return AltHashing::murmur3_32(seed(), (const jbyte*)symOop->bytes(), symOop->utf8_length());
     160  }
     161}
     162
     163// Create a new table and using alternate hash code, populate the new table
     164// with the existing elements.   This can be used to change the hash code
     165// and could in the future change the size of the table.
     166
     167void Hashtable::move_to(Hashtable* new_table) {
     168  // Initialize the global seed for hashing.
     169  assert(new_table->seed() == 0, "should be zero");
     170  _seed = AltHashing::compute_seed();
     171  assert(seed() != 0, "shouldn't be zero");
     172  new_table->set_seed(_seed);
     173
     174  int saved_entry_count = this->number_of_entries();
     175 
     176  // Iterate through the table and create a new entry for the new table
     177  for (int i = 0; i < new_table->table_size(); ++i) {
     178    for (HashtableEntry* p = bucket(i); p != NULL; ) {
     179      HashtableEntry* next = p->next();
     180      oop string = p->literal();
     181      // Use alternate hashing algorithm on the symbol in the first table
     182      unsigned int hashValue = new_hash(string);
     183      // Get a new index relative to the new table (can also change size)
     184      int index = new_table->hash_to_index(hashValue);
     185      p->set_hash(hashValue);
     186      // Keep the shared bit in the Hashtable entry to indicate that this entry
     187      // can't be deleted.   The shared bit is the LSB in the _next field so
     188      // walking the hashtable past these entries requires
     189      // BasicHashtableEntry::make_ptr() call.
     190      bool keep_shared = p->is_shared();
     191      unlink_entry(p);
     192      new_table->add_entry(index, p);
     193      if (keep_shared) {
     194        p->set_shared();
     195      }
     196      p = next;
     197    }
     198  }
     199  // give the new table the free list as well
     200  new_table->copy_freelist(this);
     201  assert(new_table->number_of_entries() == saved_entry_count, "lost entry on dictionary copy?");
     202
     203  // Destroy memory used by the buckets in the hashtable.  The memory
     204  // for the elements has been used in a new table and is not
     205  // destroyed.  The memory reuse will benefit resizing the SystemDictionary
     206  // to avoid a memory allocation spike at safepoint.
     207  free_buckets();
     208}
     209
     210void BasicHashtable::free_buckets() {
     211  if (NULL != _buckets) {
     212    // Don't delete the buckets in the shared space.  They aren't
     213    // allocated by os::malloc
     214    if (!UseSharedSpaces ||
     215        !FileMapInfo::current_info()->is_in_shared_space(_buckets)) {
     216       FREE_C_HEAP_ARRAY(HashtableBucket, _buckets);
     217    }
     218    _buckets = NULL;
    122219  }
    123220}
  • trunk/openjdk/hotspot/src/share/vm/utilities/hashtable.hpp

    r309 r406  
    178178#endif
    179179
     180  enum {
     181    rehash_count = 100,
     182    rehash_multiple = 60
     183  };
     184
    180185  void initialize(int table_size, int entry_size, int number_of_entries);
    181186
     
    193198  BasicHashtableEntry* new_entry(unsigned int hashValue);
    194199
     200  // Check that the table is unbalanced
     201  bool check_rehash_table(int count);
     202
     203  // Used when moving the entry to another table
     204  // Clean up links, but do not add to free_list
     205  void unlink_entry(BasicHashtableEntry* entry) {
     206    entry->set_next(NULL);
     207    --_number_of_entries;
     208  }
     209
     210  // Move over freelist and free block for allocation
     211  void copy_freelist(BasicHashtable* src) {
     212    _free_list = src->_free_list;
     213    src->_free_list = NULL;
     214    _first_free_entry = src->_first_free_entry;
     215    src->_first_free_entry = NULL;
     216    _end_block = src->_end_block;
     217    src->_end_block = NULL;
     218  }
     219
     220  // Free the buckets in this hashtable
     221  void free_buckets();
     222
    195223public:
    196224  void set_entry(int index, BasicHashtableEntry* entry);
     
    211239public:
    212240  Hashtable(int table_size, int entry_size)
    213     : BasicHashtable(table_size, entry_size) { }
     241    : BasicHashtable(table_size, entry_size), _seed(0) { }
    214242
    215243  Hashtable(int table_size, int entry_size,
    216244                   HashtableBucket* buckets, int number_of_entries)
    217     : BasicHashtable(table_size, entry_size, buckets, number_of_entries) { }
     245    : BasicHashtable(table_size, entry_size, buckets, number_of_entries), _seed(0) { }
    218246
    219247  // Invoke "f->do_oop" on the locations of all oops in the table.
     
    235263protected:
    236264
    237   static unsigned int hash_symbol(const char* s, int len);
    238 
    239265  unsigned int compute_hash(symbolHandle name) {
    240266    return (unsigned int) name->identity_hash();
     
    257283    return (HashtableEntry**)BasicHashtable::bucket_addr(i);
    258284  }
     285
     286  // Function to move these elements into the new table.
     287  void move_to(Hashtable* new_table);
     288  bool use_alternate_hashcode()  { return _seed != 0; }
     289  jint seed()                    { return _seed; }
     290  void set_seed(jint seed)       { _seed = seed; }
     291
     292 private:
     293  jint _seed;
     294
     295  unsigned int new_hash(oop string);
    259296};
    260297
  • trunk/openjdk/hotspot/src/share/vm/utilities/hashtable.inline.hpp

    r309 r406  
    3030
    3131// Inline function definitions for hashtable.hpp.
    32 
    33 
    34 // --------------------------------------------------------------------------
    35 // Hash function
    36 
    37 // We originally used hashpjw, but hash P(31) gives just as good results
    38 // and is slighly faster. We would like a hash function that looks at every
    39 // character, since package names have large common prefixes, and also because
    40 // hash_or_fail does error checking while iterating.
    41 
    42 // hash P(31) from Kernighan & Ritchie
    43 
    44 inline unsigned int Hashtable::hash_symbol(const char* s, int len) {
    45   unsigned int h = 0;
    46   while (len-- > 0) {
    47     h = 31*h + (unsigned) *s;
    48     s++;
    49   }
    50   return h;
    51 }
    52 
    5332
    5433// --------------------------------------------------------------------------
Note: See TracChangeset for help on using the changeset viewer.