Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(238)

Unified Diff: src/heap.cc

Issue 11593007: Replace the use CharacterStreams in Heap::AllocateSymbolInternal and String::ComputeHash (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Created 8 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: src/heap.cc
diff --git a/src/heap.cc b/src/heap.cc
index 4cc47d0405a2dac3fad5b79c8fe9a692b46751af..3e6409147eb722c7532360c5fed5678663158410 100644
--- a/src/heap.cc
+++ b/src/heap.cc
@@ -3302,8 +3302,8 @@ static inline bool Between(uint32_t character, uint32_t from, uint32_t to) {
MUST_USE_RESULT static inline MaybeObject* MakeOrFindTwoCharacterString(
Heap* heap,
- uint32_t c1,
- uint32_t c2) {
+ uint16_t c1,
+ uint16_t c2) {
String* symbol;
// Numeric strings have a different hash algorithm not known by
// LookupTwoCharsSymbolIfExists, so we skip this step for such strings.
@@ -3352,8 +3352,8 @@ MaybeObject* Heap::AllocateConsString(String* first, String* second) {
// dictionary. Check whether we already have the string in the symbol
// table to prevent creation of many unneccesary strings.
if (length == 2) {
- unsigned c1 = first->Get(0);
- unsigned c2 = second->Get(0);
+ uint16_t c1 = first->Get(0);
+ uint16_t c2 = second->Get(0);
return MakeOrFindTwoCharacterString(this, c1, c2);
}
@@ -3467,8 +3467,8 @@ MaybeObject* Heap::AllocateSubString(String* buffer,
// Optimization for 2-byte strings often used as keys in a decompression
// dictionary. Check whether we already have the string in the symbol
// table to prevent creation of many unneccesary strings.
- unsigned c1 = buffer->Get(start);
- unsigned c2 = buffer->Get(start + 1);
+ uint16_t c1 = buffer->Get(start);
+ uint16_t c2 = buffer->Get(start + 1);
return MakeOrFindTwoCharacterString(this, c1, c2);
}
@@ -4623,27 +4623,92 @@ Map* Heap::SymbolMapForString(String* string) {
}
-MaybeObject* Heap::AllocateInternalSymbol(unibrow::CharacterStream* buffer,
+template<typename T>
+struct AllocateInternalSymbolHelper {
+ static bool IsOneByte(T t, int chars);
+ static void WriteOneByteData(T t, char* chars, int len);
+ static void WriteTwoByteData(T t, uint16_t* chars, int len);
+};
+
+
+template<>
+struct AllocateInternalSymbolHelper< Vector<const char> > {
+ static bool IsOneByte(Vector<const char> vector, int chars) {
+ // TODO(dcarney): check for Latin-1 when Latin-1 is actually supported.
+ // At the moment this code path is never hit for ascii.
+ ASSERT(chars <= vector.length());
+ return chars == vector.length();
+ }
+
+ static inline void WriteOneByteData(Vector<const char> vector,
+ char* chars,
+ int len) {
+ // Only works for ascii.
+ ASSERT(vector.length() == len);
+ memcpy(chars, vector.start(), len);
+ }
+
+ static inline void WriteTwoByteData(Vector<const char> vector,
+ uint16_t* chars,
+ int len) {
+ const uint8_t* stream = reinterpret_cast<const uint8_t*>(vector.start());
+ unsigned stream_length = vector.length();
+ while (stream_length != 0) {
+ unsigned consumed = 0;
+ uint32_t c = unibrow::Utf8::ValueOf(stream, stream_length, &consumed);
+ if (c == unibrow::Utf8::kBadChar) break;
+ ASSERT(consumed <= stream_length);
+ stream_length -= consumed;
+ stream += consumed;
+ if (c > unibrow::Utf16::kMaxNonSurrogateCharCode) {
+ len -= 2;
+ if (len < 0) break;
+ *chars++ = unibrow::Utf16::LeadSurrogate(c);
+ *chars++ = unibrow::Utf16::TrailSurrogate(c);
+ } else {
+ len -= 1;
+ if (len < 0) break;
+ *chars++ = c;
+ }
+ }
+ ASSERT(stream_length == 0);
+ ASSERT(len == 0);
+ }
+};
+
+
+template<>
+struct AllocateInternalSymbolHelper<String*> {
+ static inline bool IsOneByte(String* string, int chars) {
+ return string->IsOneByteRepresentation();
+ }
+
+ static inline void WriteOneByteData(String* s, char* chars, int len) {
+ ASSERT(s->length() == len);
+ String::WriteToFlat(s, chars, 0, len);
+ }
+
+ static inline void WriteTwoByteData(String* s, uint16_t* chars, int len) {
+ ASSERT(s->length() == len);
+ String::WriteToFlat(s, chars, 0, len);
+ }
+};
+
+
+template<typename T>
+MaybeObject* Heap::AllocateInternalSymbol(T t,
int chars,
uint32_t hash_field) {
+ typedef AllocateInternalSymbolHelper<T> H;
ASSERT(chars >= 0);
- // Ensure the chars matches the number of characters in the buffer.
- ASSERT(static_cast<unsigned>(chars) == buffer->Utf16Length());
- // Determine whether the string is ASCII.
- bool is_ascii = true;
- while (buffer->has_more()) {
- if (buffer->GetNext() > unibrow::Utf8::kMaxOneByteChar) {
- is_ascii = false;
- break;
- }
- }
- buffer->Rewind();
+ // Determine whether the string is potentially one byte.
+ bool is_one_byte = H::IsOneByte(t, chars);
// Compute map and object size.
int size;
Map* map;
- if (is_ascii) {
+ if (is_one_byte) {
if (chars > SeqOneByteString::kMaxLength) {
return Failure::OutOfMemoryException();
}
@@ -4673,21 +4738,22 @@ MaybeObject* Heap::AllocateInternalSymbol(unibrow::CharacterStream* buffer,
ASSERT_EQ(size, answer->Size());
- // Fill in the characters.
- int i = 0;
- while (i < chars) {
- uint32_t character = buffer->GetNext();
- if (character > unibrow::Utf16::kMaxNonSurrogateCharCode) {
- answer->Set(i++, unibrow::Utf16::LeadSurrogate(character));
- answer->Set(i++, unibrow::Utf16::TrailSurrogate(character));
- } else {
- answer->Set(i++, character);
- }
+ if (is_one_byte) {
+ H::WriteOneByteData(t, SeqOneByteString::cast(answer)->GetChars(), chars);
+ } else {
+ H::WriteTwoByteData(t, SeqTwoByteString::cast(answer)->GetChars(), chars);
}
return answer;
}
+// Need explicit instantiations.
+template
+MaybeObject* Heap::AllocateInternalSymbol(String*, int, uint32_t);
+template
+MaybeObject* Heap::AllocateInternalSymbol(Vector<const char>, int, uint32_t);
+
+
MaybeObject* Heap::AllocateRawOneByteString(int length,
PretenureFlag pretenure) {
if (length < 0 || length > SeqOneByteString::kMaxLength) {

Powered by Google App Engine
This is Rietveld 408576698