581 _size = size;
582 sample(_save_buf);
583 }
584
585 bool verify() {
586 u1 check_buf[sizeof(_save_buf)];
587 int check_size = sample(check_buf);
588 return (0 == memcmp(_save_buf, check_buf, check_size));
589 }
590
591 void set_region(const void* region) { _region = (address) region; }
592 };
593 #endif
594
595
596 // --------------------------------------------------------------------------
597 StringTable* StringTable::_the_table = NULL;
598
599 bool StringTable::_needs_rehashing = false;
600
601 // Pick hashing algorithm
602 unsigned int StringTable::hash_string(const jchar* s, int len) {
603 return use_alternate_hashcode() ? AltHashing::murmur3_32(seed(), s, len) :
604 java_lang_String::hash_code(s, len);
605 }
606
607 oop StringTable::lookup(int index, jchar* name,
608 int len, unsigned int hash) {
609 int count = 0;
610 for (HashtableEntry<oop, mtSymbol>* l = bucket(index); l != NULL; l = l->next()) {
611 count++;
612 if (l->hash() == hash) {
613 if (java_lang_String::equals(l->literal(), name, len)) {
614 return l->literal();
615 }
616 }
617 }
618 // If the bucket size is too deep check if this hash code is insufficient.
619 if (count >= BasicHashtable<mtSymbol>::rehash_count && !needs_rehashing()) {
620 _needs_rehashing = check_rehash_table(count);
744 for (int i = 0; i < the_table()->table_size(); ++i) {
745 HashtableEntry<oop, mtSymbol>** p = the_table()->bucket_addr(i);
746 HashtableEntry<oop, mtSymbol>* entry = the_table()->bucket(i);
747 while (entry != NULL) {
748 assert(!entry->is_shared(), "CDS not used for the StringTable");
749
750 if (is_alive->do_object_b(entry->literal())) {
751 if (f != NULL) {
752 f->do_oop((oop*)entry->literal_addr());
753 }
754 p = entry->next_addr();
755 } else {
756 *p = entry->next();
757 the_table()->free_entry(entry);
758 }
759 entry = *p;
760 }
761 }
762 }
763
764 void StringTable::oops_do(OopClosure* f) {
765 for (int i = 0; i < the_table()->table_size(); ++i) {
766 HashtableEntry<oop, mtSymbol>* entry = the_table()->bucket(i);
767 while (entry != NULL) {
768 assert(!entry->is_shared(), "CDS not used for the StringTable");
769
770 f->do_oop((oop*)entry->literal_addr());
771
772 entry = entry->next();
773 }
774 }
775 }
776
777 void StringTable::verify() {
778 for (int i = 0; i < the_table()->table_size(); ++i) {
779 HashtableEntry<oop, mtSymbol>* p = the_table()->bucket(i);
780 for ( ; p != NULL; p = p->next()) {
781 oop s = p->literal();
782 guarantee(s != NULL, "interned string is NULL");
783 unsigned int h = java_lang_String::hash_string(s);
784 guarantee(p->hash() == h, "broken hash in string table entry");
785 guarantee(the_table()->hash_to_index(h) == i,
786 "wrong index in string table");
787 }
788 }
789 }
790
791 void StringTable::dump(outputStream* st) {
792 the_table()->dump_table(st, "StringTable");
793 }
794
795
796 // Create a new table and using alternate hash code, populate the new table
|
581 _size = size;
582 sample(_save_buf);
583 }
584
585 bool verify() {
586 u1 check_buf[sizeof(_save_buf)];
587 int check_size = sample(check_buf);
588 return (0 == memcmp(_save_buf, check_buf, check_size));
589 }
590
591 void set_region(const void* region) { _region = (address) region; }
592 };
593 #endif
594
595
596 // --------------------------------------------------------------------------
597 StringTable* StringTable::_the_table = NULL;
598
599 bool StringTable::_needs_rehashing = false;
600
601 volatile int StringTable::_par_claimed_idx = 0;
602
603 // Pick hashing algorithm
604 unsigned int StringTable::hash_string(const jchar* s, int len) {
605 return use_alternate_hashcode() ? AltHashing::murmur3_32(seed(), s, len) :
606 java_lang_String::hash_code(s, len);
607 }
608
609 oop StringTable::lookup(int index, jchar* name,
610 int len, unsigned int hash) {
611 int count = 0;
612 for (HashtableEntry<oop, mtSymbol>* l = bucket(index); l != NULL; l = l->next()) {
613 count++;
614 if (l->hash() == hash) {
615 if (java_lang_String::equals(l->literal(), name, len)) {
616 return l->literal();
617 }
618 }
619 }
620 // If the bucket size is too deep check if this hash code is insufficient.
621 if (count >= BasicHashtable<mtSymbol>::rehash_count && !needs_rehashing()) {
622 _needs_rehashing = check_rehash_table(count);
746 for (int i = 0; i < the_table()->table_size(); ++i) {
747 HashtableEntry<oop, mtSymbol>** p = the_table()->bucket_addr(i);
748 HashtableEntry<oop, mtSymbol>* entry = the_table()->bucket(i);
749 while (entry != NULL) {
750 assert(!entry->is_shared(), "CDS not used for the StringTable");
751
752 if (is_alive->do_object_b(entry->literal())) {
753 if (f != NULL) {
754 f->do_oop((oop*)entry->literal_addr());
755 }
756 p = entry->next_addr();
757 } else {
758 *p = entry->next();
759 the_table()->free_entry(entry);
760 }
761 entry = *p;
762 }
763 }
764 }
765
766 void StringTable::buckets_do(OopClosure* f, int start_idx, int end_idx) {
767 const int limit = the_table()->table_size();
768
769 assert(0 <= start_idx && start_idx <= limit,
770 err_msg("start_idx (" INT32_FORMAT ") oob?", start_idx));
771 assert(0 <= end_idx && end_idx <= limit,
772 err_msg("end_idx (" INT32_FORMAT ") oob?", end_idx));
773 assert(start_idx <= end_idx,
774 err_msg("Ordering: start_idx=" INT32_FORMAT", end_idx=" INT32_FORMAT,
775 start_idx, end_idx));
776
777 for (int i = start_idx; i < end_idx; i += 1) {
778 HashtableEntry<oop, mtSymbol>* entry = the_table()->bucket(i);
779 while (entry != NULL) {
780 assert(!entry->is_shared(), "CDS not used for the StringTable");
781
782 f->do_oop((oop*)entry->literal_addr());
783
784 entry = entry->next();
785 }
786 }
787 }
788
789 void StringTable::oops_do(OopClosure* f) {
790 buckets_do(f, 0, the_table()->table_size());
791 }
792
793 void StringTable::possibly_parallel_oops_do(OopClosure* f) {
794 const int ClaimChunkSize = 32;
795 const int limit = the_table()->table_size();
796
797 for (;;) {
798 // Grab next set of buckets to scan
799 int start_idx = Atomic::add(ClaimChunkSize, &_par_claimed_idx) - ClaimChunkSize;
800 if (start_idx >= limit) {
801 // End of table
802 break;
803 }
804
805 int end_idx = MIN2(limit, start_idx + ClaimChunkSize);
806 buckets_do(f, start_idx, end_idx);
807 }
808 }
809
810 void StringTable::verify() {
811 for (int i = 0; i < the_table()->table_size(); ++i) {
812 HashtableEntry<oop, mtSymbol>* p = the_table()->bucket(i);
813 for ( ; p != NULL; p = p->next()) {
814 oop s = p->literal();
815 guarantee(s != NULL, "interned string is NULL");
816 unsigned int h = java_lang_String::hash_string(s);
817 guarantee(p->hash() == h, "broken hash in string table entry");
818 guarantee(the_table()->hash_to_index(h) == i,
819 "wrong index in string table");
820 }
821 }
822 }
823
824 void StringTable::dump(outputStream* st) {
825 the_table()->dump_table(st, "StringTable");
826 }
827
828
829 // Create a new table and using alternate hash code, populate the new table
|