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

Unified Diff: src/objects-inl.h

Issue 7477045: Tentative implementation of string slices (hidden under the flag --string-slices). (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Patched RegExp for string slices. Created 9 years, 4 months 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/objects-inl.h
diff --git a/src/objects-inl.h b/src/objects-inl.h
index 53a3183694cbfdfc87f16524888036e27d434d14..09ab365750fe97986721576e2d7e3ce2de0819f5 100644
--- a/src/objects-inl.h
+++ b/src/objects-inl.h
@@ -177,10 +177,14 @@ bool Object::IsSymbol() {
bool Object::IsConsString() {
- if (!this->IsHeapObject()) return false;
- uint32_t type = HeapObject::cast(this)->map()->instance_type();
- return (type & (kIsNotStringMask | kStringRepresentationMask)) ==
- (kStringTag | kConsStringTag);
+ if (!IsString()) return false;
+ return StringShape(String::cast(this)).IsCons();
+}
+
+
+bool Object::IsSlicedString() {
+ if (!IsString()) return false;
+ return StringShape(String::cast(this)).IsSliced();
}
@@ -280,6 +284,19 @@ bool StringShape::IsCons() {
}
+bool StringShape::IsSliced() {
+ return (type_ & kStringRepresentationMask) == kSlicedStringTag;
+}
+
+
+bool StringShape::IsIndirect() {
+ ASSERT(((type_ & kIsIndirectStringMask) == kIsIndirectStringTag)
+ == (((type_ & kStringRepresentationMask) == kConsStringTag)
+ || ((type_ & kStringRepresentationMask) == kSlicedStringTag)));
antonm 2011/08/04 12:18:48 Isn't it similar to change to Heap::TargetSpaceId?
+ return (type_ & kIsIndirectStringMask) == kIsIndirectStringTag;
+}
Yang 2011/08/04 09:19:53 Being 'indirect' means either cons or slice. Acces
+
+
bool StringShape::IsExternal() {
return (type_ & kStringRepresentationMask) == kExternalStringTag;
}
@@ -2041,6 +2058,7 @@ CAST_ACCESSOR(String)
CAST_ACCESSOR(SeqString)
CAST_ACCESSOR(SeqAsciiString)
CAST_ACCESSOR(SeqTwoByteString)
+CAST_ACCESSOR(SlicedString)
CAST_ACCESSOR(ConsString)
CAST_ACCESSOR(ExternalString)
CAST_ACCESSOR(ExternalAsciiString)
@@ -2127,7 +2145,7 @@ bool String::Equals(String* other) {
MaybeObject* String::TryFlatten(PretenureFlag pretenure) {
if (!StringShape(this).IsCons()) return this;
ConsString* cons = ConsString::cast(this);
- if (cons->second()->length() == 0) return cons->first();
+ if (cons->IsFlat()) return cons->first();
return SlowTryFlatten(pretenure);
}
@@ -2135,10 +2153,42 @@ MaybeObject* String::TryFlatten(PretenureFlag pretenure) {
String* String::TryFlattenGetString(PretenureFlag pretenure) {
MaybeObject* flat = TryFlatten(pretenure);
Object* successfully_flattened;
- if (flat->ToObject(&successfully_flattened)) {
- return String::cast(successfully_flattened);
+ if (!flat->ToObject(&successfully_flattened)) return this;
+ return String::cast(successfully_flattened);
+}
+
+
+MaybeObject* String::TryTruncate(PretenureFlag pretenure) {
+ if (!StringShape(this).IsSliced()) return this;
+ SlicedString* slice = SlicedString::cast(this);
+ if (slice->IsTruncated()) return slice->parent();
+ return SlowTryTruncate(pretenure);
+}
+
+
+String* String::TryTruncateGetString(PretenureFlag pretenure) {
+ MaybeObject* truncate = TryTruncate(pretenure);
+ Object* successfully_truncated;
+ if (!truncate->ToObject(&successfully_truncated)) return this;
+ return String::cast(successfully_truncated);
+}
+
+
+MaybeObject* String::TryFlattenOrTruncate(PretenureFlag pretenure) {
+ switch (StringShape(this).representation_tag()) {
+ case kSlicedStringTag: {
+ SlicedString* slice = SlicedString::cast(this);
+ if (slice->IsTruncated()) return slice->parent();
+ return SlowTryTruncate(pretenure);
+ }
+ case kConsStringTag: {
+ ConsString* cons = ConsString::cast(this);
+ if (cons->IsFlat()) return cons->first();
+ return SlowTryFlatten(pretenure);
+ }
+ default:
+ return this;
}
- return this;
}
@@ -2156,6 +2206,9 @@ uint16_t String::Get(int index) {
return ExternalAsciiString::cast(this)->ExternalAsciiStringGet(index);
case kExternalStringTag | kTwoByteStringTag:
return ExternalTwoByteString::cast(this)->ExternalTwoByteStringGet(index);
+ case kSlicedStringTag | kAsciiStringTag:
+ case kSlicedStringTag | kTwoByteStringTag:
+ return SlicedString::cast(this)->SlicedStringGet(index);
default:
break;
}
@@ -2176,18 +2229,41 @@ void String::Set(int index, uint16_t value) {
bool String::IsFlat() {
+ if (!StringShape(this).IsCons()) return true;
+ return ConsString::cast(this)->second() == GetHeap()->empty_string();
+}
+
+
+bool String::IsTruncated() {
+ if (!StringShape(this).IsSliced()) return true;
+ SlicedString* slice = SlicedString::cast(this);
+ return slice->parent()->length() == slice->length();
+}
+
+
+bool String::IsFlatAndTruncated() {
switch (StringShape(this).representation_tag()) {
- case kConsStringTag: {
- String* second = ConsString::cast(this)->second();
- // Only flattened strings have second part empty.
- return second->length() == 0;
+ case kSlicedStringTag: {
+ SlicedString* slice = SlicedString::cast(this);
+ return slice->parent()->length() == slice->length();
}
+ case kConsStringTag:
+ return ConsString::cast(this)->second() == GetHeap()->empty_string();
default:
return true;
}
}
+String* String::GetIndirect() {
+ STATIC_ASSERT(ConsString::kFirstOffset == SlicedString::kParentOffset);
+ ASSERT(this->IsFlat());
+ ASSERT(this->IsTruncated());
+ ASSERT(StringShape(this).IsIndirect());
+ return String::cast(reinterpret_cast<ConsString*>(this)->first());
+}
+
+
uint16_t SeqAsciiString::SeqAsciiStringGet(int index) {
ASSERT(index >= 0 && index < length());
return READ_BYTE_FIELD(this, kHeaderSize + index * kCharSize);
@@ -2243,6 +2319,20 @@ int SeqAsciiString::SeqAsciiStringSize(InstanceType instance_type) {
}
+String* SlicedString::parent() {
+ return String::cast(READ_FIELD(this, kParentOffset));
+}
+
+
+void SlicedString::set_parent(String* parent) {
+ ASSERT(parent->IsSeqString());
+ WRITE_FIELD(this, kParentOffset, parent);
+}
+
+
+SMI_ACCESSORS(SlicedString, offset, kOffsetOffset)
+
+
String* ConsString::first() {
return String::cast(READ_FIELD(this, kFirstOffset));
}

Powered by Google App Engine
This is Rietveld 408576698