- Added new object type, RegExp, for regular expressions.

- Renamed some ::kSizes to ::kHeaderSizes to avoid confusion.


git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@362 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
parent 88c9fa5d
...@@ -655,7 +655,7 @@ void Genesis::CreateRoots(v8::Handle<v8::ObjectTemplate> global_template, ...@@ -655,7 +655,7 @@ void Genesis::CreateRoots(v8::Handle<v8::ObjectTemplate> global_template,
{ // -- R e g E x p { // -- R e g E x p
// Builtin functions for RegExp.prototype. // Builtin functions for RegExp.prototype.
Handle<JSFunction> regexp_fun = Handle<JSFunction> regexp_fun =
InstallFunction(global, "RegExp", JS_VALUE_TYPE, JSValue::kSize, InstallFunction(global, "RegExp", JS_REGEXP_TYPE, JSRegExp::kSize,
Top::initial_object_prototype(), Builtins::Illegal, Top::initial_object_prototype(), Builtins::Illegal,
true); true);
......
...@@ -974,15 +974,15 @@ bool Heap::CreateInitialMaps() { ...@@ -974,15 +974,15 @@ bool Heap::CreateInitialMaps() {
STRUCT_LIST(ALLOCATE_STRUCT_MAP) STRUCT_LIST(ALLOCATE_STRUCT_MAP)
#undef ALLOCATE_STRUCT_MAP #undef ALLOCATE_STRUCT_MAP
obj = AllocateMap(FIXED_ARRAY_TYPE, HeapObject::kSize); obj = AllocateMap(FIXED_ARRAY_TYPE, HeapObject::kHeaderSize);
if (obj->IsFailure()) return false; if (obj->IsFailure()) return false;
hash_table_map_ = Map::cast(obj); hash_table_map_ = Map::cast(obj);
obj = AllocateMap(FIXED_ARRAY_TYPE, HeapObject::kSize); obj = AllocateMap(FIXED_ARRAY_TYPE, HeapObject::kHeaderSize);
if (obj->IsFailure()) return false; if (obj->IsFailure()) return false;
context_map_ = Map::cast(obj); context_map_ = Map::cast(obj);
obj = AllocateMap(FIXED_ARRAY_TYPE, HeapObject::kSize); obj = AllocateMap(FIXED_ARRAY_TYPE, HeapObject::kHeaderSize);
if (obj->IsFailure()) return false; if (obj->IsFailure()) return false;
global_context_map_ = Map::cast(obj); global_context_map_ = Map::cast(obj);
......
...@@ -142,7 +142,7 @@ Handle<String> RegExpImpl::StringToTwoByte(Handle<String> pattern) { ...@@ -142,7 +142,7 @@ Handle<String> RegExpImpl::StringToTwoByte(Handle<String> pattern) {
} }
Handle<Object> RegExpImpl::JsreCompile(Handle<JSValue> re, Handle<Object> RegExpImpl::JsreCompile(Handle<JSRegExp> re,
Handle<String> pattern, Handle<String> pattern,
Handle<String> flags) { Handle<String> flags) {
JSRegExpIgnoreCaseOption case_option = JSRegExpDoNotIgnoreCase; JSRegExpIgnoreCaseOption case_option = JSRegExpDoNotIgnoreCase;
...@@ -159,10 +159,10 @@ Handle<Object> RegExpImpl::JsreCompile(Handle<JSValue> re, ...@@ -159,10 +159,10 @@ Handle<Object> RegExpImpl::JsreCompile(Handle<JSValue> re,
const char* error_message = NULL; const char* error_message = NULL;
malloc_failure = Failure::Exception(); malloc_failure = Failure::Exception();
JSRegExp* code = jsRegExpCompile(two_byte_pattern->GetTwoByteData(), JscreRegExp* code = jsRegExpCompile(two_byte_pattern->GetTwoByteData(),
pattern->length(), case_option, pattern->length(), case_option,
multiline_option, &number_of_captures, multiline_option, &number_of_captures,
&error_message, &JSREMalloc, &JSREFree); &error_message, &JSREMalloc, &JSREFree);
if (code == NULL && malloc_failure->IsRetryAfterGC()) { if (code == NULL && malloc_failure->IsRetryAfterGC()) {
// Performs a GC, then retries. // Performs a GC, then retries.
...@@ -203,7 +203,8 @@ Handle<Object> RegExpImpl::JsreCompile(Handle<JSValue> re, ...@@ -203,7 +203,8 @@ Handle<Object> RegExpImpl::JsreCompile(Handle<JSValue> re,
Handle<FixedArray> value = Factory::NewFixedArray(2); Handle<FixedArray> value = Factory::NewFixedArray(2);
value->set(CAPTURE_INDEX, Smi::FromInt(number_of_captures)); value->set(CAPTURE_INDEX, Smi::FromInt(number_of_captures));
value->set(INTERNAL_INDEX, *internal); value->set(INTERNAL_INDEX, *internal);
re->set_value(*value); re->set_type_tag(JSRegExp::JSCRE);
re->set_data(*value);
LOG(RegExpCompileEvent(re)); LOG(RegExpCompileEvent(re));
...@@ -211,7 +212,7 @@ Handle<Object> RegExpImpl::JsreCompile(Handle<JSValue> re, ...@@ -211,7 +212,7 @@ Handle<Object> RegExpImpl::JsreCompile(Handle<JSValue> re,
} }
Handle<Object> RegExpImpl::JsreExecOnce(Handle<JSValue> regexp, Handle<Object> RegExpImpl::JsreExecOnce(Handle<JSRegExp> regexp,
int num_captures, int num_captures,
Handle<String> subject, Handle<String> subject,
int previous_index, int previous_index,
...@@ -222,16 +223,17 @@ Handle<Object> RegExpImpl::JsreExecOnce(Handle<JSValue> regexp, ...@@ -222,16 +223,17 @@ Handle<Object> RegExpImpl::JsreExecOnce(Handle<JSValue> regexp,
{ {
AssertNoAllocation a; AssertNoAllocation a;
ByteArray* internal = JsreInternal(regexp); ByteArray* internal = JsreInternal(regexp);
const JSRegExp* js_regexp = const JscreRegExp* js_regexp =
reinterpret_cast<JSRegExp*>(internal->GetDataStartAddress()); reinterpret_cast<JscreRegExp*>(internal->GetDataStartAddress());
LOG(RegExpExecEvent(regexp, previous_index, subject)); LOG(RegExpExecEvent(regexp, previous_index, subject));
rc = jsRegExpExecute(js_regexp, two_byte_subject, rc = jsRegExpExecute(js_regexp,
subject->length(), two_byte_subject,
previous_index, subject->length(),
offsets_vector, previous_index,
offsets_vector_length); offsets_vector,
offsets_vector_length);
} }
// The KJS JavaScript engine returns null (ie, a failed match) when // The KJS JavaScript engine returns null (ie, a failed match) when
...@@ -304,7 +306,7 @@ int OffsetsVector::static_offsets_vector_[ ...@@ -304,7 +306,7 @@ int OffsetsVector::static_offsets_vector_[
OffsetsVector::kStaticOffsetsVectorSize]; OffsetsVector::kStaticOffsetsVectorSize];
Handle<Object> RegExpImpl::JsreExec(Handle<JSValue> regexp, Handle<Object> RegExpImpl::JsreExec(Handle<JSRegExp> regexp,
Handle<String> subject, Handle<String> subject,
Handle<Object> index) { Handle<Object> index) {
// Prepare space for the return values. // Prepare space for the return values.
...@@ -325,7 +327,7 @@ Handle<Object> RegExpImpl::JsreExec(Handle<JSValue> regexp, ...@@ -325,7 +327,7 @@ Handle<Object> RegExpImpl::JsreExec(Handle<JSValue> regexp,
} }
Handle<Object> RegExpImpl::JsreExecGlobal(Handle<JSValue> regexp, Handle<Object> RegExpImpl::JsreExecGlobal(Handle<JSRegExp> regexp,
Handle<String> subject) { Handle<String> subject) {
// Prepare space for the return values. // Prepare space for the return values.
int num_captures = JsreCapture(regexp); int num_captures = JsreCapture(regexp);
...@@ -370,15 +372,15 @@ Handle<Object> RegExpImpl::JsreExecGlobal(Handle<JSValue> regexp, ...@@ -370,15 +372,15 @@ Handle<Object> RegExpImpl::JsreExecGlobal(Handle<JSValue> regexp,
} }
int RegExpImpl::JsreCapture(Handle<JSValue> re) { int RegExpImpl::JsreCapture(Handle<JSRegExp> re) {
Object* value = re->value(); Object* value = re->data();
ASSERT(value->IsFixedArray()); ASSERT(value->IsFixedArray());
return Smi::cast(FixedArray::cast(value)->get(CAPTURE_INDEX))->value(); return Smi::cast(FixedArray::cast(value)->get(CAPTURE_INDEX))->value();
} }
ByteArray* RegExpImpl::JsreInternal(Handle<JSValue> re) { ByteArray* RegExpImpl::JsreInternal(Handle<JSRegExp> re) {
Object* value = re->value(); Object* value = re->data();
ASSERT(value->IsFixedArray()); ASSERT(value->IsFixedArray());
return ByteArray::cast(FixedArray::cast(value)->get(INTERNAL_INDEX)); return ByteArray::cast(FixedArray::cast(value)->get(INTERNAL_INDEX));
} }
......
...@@ -44,21 +44,21 @@ class RegExpImpl { ...@@ -44,21 +44,21 @@ class RegExpImpl {
// This function calls the garbage collector if necessary. // This function calls the garbage collector if necessary.
static Handle<String> ToString(Handle<Object> value); static Handle<String> ToString(Handle<Object> value);
static Handle<Object> JsreCompile(Handle<JSValue> re, static Handle<Object> JsreCompile(Handle<JSRegExp> re,
Handle<String> pattern, Handle<String> pattern,
Handle<String> flags); Handle<String> flags);
// Implements RegExp.prototype.exec(string) function. // Implements RegExp.prototype.exec(string) function.
// See ECMA-262 section 15.10.6.2. // See ECMA-262 section 15.10.6.2.
// This function calls the garbage collector if necessary. // This function calls the garbage collector if necessary.
static Handle<Object> JsreExec(Handle<JSValue> regexp, static Handle<Object> JsreExec(Handle<JSRegExp> regexp,
Handle<String> subject, Handle<String> subject,
Handle<Object> index); Handle<Object> index);
// Call RegExp.prototyp.exec(string) in a loop. // Call RegExp.prototyp.exec(string) in a loop.
// Used by String.prototype.match and String.prototype.replace. // Used by String.prototype.match and String.prototype.replace.
// This function calls the garbage collector if necessary. // This function calls the garbage collector if necessary.
static Handle<Object> JsreExecGlobal(Handle<JSValue> regexp, static Handle<Object> JsreExecGlobal(Handle<JSRegExp> regexp,
Handle<String> subject); Handle<String> subject);
static void NewSpaceCollectionPrologue(); static void NewSpaceCollectionPrologue();
...@@ -75,11 +75,11 @@ class RegExpImpl { ...@@ -75,11 +75,11 @@ class RegExpImpl {
static String* two_byte_cached_string_; static String* two_byte_cached_string_;
// Returns the caputure from the re. // Returns the caputure from the re.
static int JsreCapture(Handle<JSValue> re); static int JsreCapture(Handle<JSRegExp> re);
static ByteArray* JsreInternal(Handle<JSValue> re); static ByteArray* JsreInternal(Handle<JSRegExp> re);
// Call jsRegExpExecute once // Call jsRegExpExecute once
static Handle<Object> JsreExecOnce(Handle<JSValue> regexp, static Handle<Object> JsreExecOnce(Handle<JSRegExp> regexp,
int num_captures, int num_captures,
Handle<String> subject, Handle<String> subject,
int previous_index, int previous_index,
......
...@@ -348,7 +348,7 @@ void Logger::SharedLibraryEvent(const wchar_t* library_path, ...@@ -348,7 +348,7 @@ void Logger::SharedLibraryEvent(const wchar_t* library_path,
#ifdef ENABLE_LOGGING_AND_PROFILING #ifdef ENABLE_LOGGING_AND_PROFILING
void Logger::LogRegExpSource(Handle<JSValue> regexp) { void Logger::LogRegExpSource(Handle<JSRegExp> regexp) {
// Prints "/" + re.source + "/" + // Prints "/" + re.source + "/" +
// (re.global?"g":"") + (re.ignorecase?"i":"") + (re.multiline?"m":"") // (re.global?"g":"") + (re.ignorecase?"i":"") + (re.multiline?"m":"")
...@@ -392,7 +392,7 @@ void Logger::LogRegExpSource(Handle<JSValue> regexp) { ...@@ -392,7 +392,7 @@ void Logger::LogRegExpSource(Handle<JSValue> regexp) {
#endif // ENABLE_LOGGING_AND_PROFILING #endif // ENABLE_LOGGING_AND_PROFILING
void Logger::RegExpCompileEvent(Handle<JSValue> regexp) { void Logger::RegExpCompileEvent(Handle<JSRegExp> regexp) {
#ifdef ENABLE_LOGGING_AND_PROFILING #ifdef ENABLE_LOGGING_AND_PROFILING
if (logfile_ == NULL || !FLAG_log_regexp) return; if (logfile_ == NULL || !FLAG_log_regexp) return;
ScopedLock sl(mutex_); ScopedLock sl(mutex_);
...@@ -404,7 +404,7 @@ void Logger::RegExpCompileEvent(Handle<JSValue> regexp) { ...@@ -404,7 +404,7 @@ void Logger::RegExpCompileEvent(Handle<JSValue> regexp) {
} }
void Logger::RegExpExecEvent(Handle<JSValue> regexp, void Logger::RegExpExecEvent(Handle<JSRegExp> regexp,
int start_index, int start_index,
Handle<String> input_string) { Handle<String> input_string) {
#ifdef ENABLE_LOGGING_AND_PROFILING #ifdef ENABLE_LOGGING_AND_PROFILING
......
...@@ -181,9 +181,9 @@ class Logger { ...@@ -181,9 +181,9 @@ class Logger {
// ==== Events logged by --log-regexp ==== // ==== Events logged by --log-regexp ====
// Regexp compilation and execution events. // Regexp compilation and execution events.
static void RegExpCompileEvent(Handle<JSValue> regexp); static void RegExpCompileEvent(Handle<JSRegExp> regexp);
static void RegExpExecEvent(Handle<JSValue> regexp, static void RegExpExecEvent(Handle<JSRegExp> regexp,
int start_index, int start_index,
Handle<String> input_string); Handle<String> input_string);
...@@ -197,7 +197,7 @@ class Logger { ...@@ -197,7 +197,7 @@ class Logger {
private: private:
// Emits the source code of a regexp. Used by regexp events. // Emits the source code of a regexp. Used by regexp events.
static void LogRegExpSource(Handle<JSValue> regexp); static void LogRegExpSource(Handle<JSRegExp> regexp);
// Emits a profiler tick event. Used by the profiler thread. // Emits a profiler tick event. Used by the profiler thread.
static void TickEvent(TickSample* sample, bool overflow); static void TickEvent(TickSample* sample, bool overflow);
......
...@@ -118,6 +118,7 @@ void HeapObject::HeapObjectPrint() { ...@@ -118,6 +118,7 @@ void HeapObject::HeapObjectPrint() {
break; break;
case JS_OBJECT_TYPE: // fall through case JS_OBJECT_TYPE: // fall through
case JS_ARRAY_TYPE: case JS_ARRAY_TYPE:
case JS_REGEXP_TYPE:
JSObject::cast(this)->JSObjectPrint(); JSObject::cast(this)->JSObjectPrint();
break; break;
case ODDBALL_TYPE: case ODDBALL_TYPE:
...@@ -206,6 +207,9 @@ void HeapObject::HeapObjectVerify() { ...@@ -206,6 +207,9 @@ void HeapObject::HeapObjectVerify() {
case JS_ARRAY_TYPE: case JS_ARRAY_TYPE:
JSArray::cast(this)->JSArrayVerify(); JSArray::cast(this)->JSArrayVerify();
break; break;
case JS_REGEXP_TYPE:
JSRegExp::cast(this)->JSRegExpVerify();
break;
case FILLER_TYPE: case FILLER_TYPE:
break; break;
case PROXY_TYPE: case PROXY_TYPE:
...@@ -375,6 +379,7 @@ static const char* TypeToString(InstanceType type) { ...@@ -375,6 +379,7 @@ static const char* TypeToString(InstanceType type) {
case JS_FUNCTION_TYPE: return "JS_FUNCTION"; case JS_FUNCTION_TYPE: return "JS_FUNCTION";
case CODE_TYPE: return "CODE"; case CODE_TYPE: return "CODE";
case JS_ARRAY_TYPE: return "JS_ARRAY"; case JS_ARRAY_TYPE: return "JS_ARRAY";
case JS_REGEXP_TYPE: return "JS_REGEXP";
case JS_VALUE_TYPE: return "JS_VALUE"; case JS_VALUE_TYPE: return "JS_VALUE";
case JS_GLOBAL_OBJECT_TYPE: return "JS_GLOBAL_OBJECT"; case JS_GLOBAL_OBJECT_TYPE: return "JS_GLOBAL_OBJECT";
case JS_BUILTINS_OBJECT_TYPE: return "JS_BUILTINS_OBJECT"; case JS_BUILTINS_OBJECT_TYPE: return "JS_BUILTINS_OBJECT";
...@@ -622,6 +627,13 @@ void JSArray::JSArrayVerify() { ...@@ -622,6 +627,13 @@ void JSArray::JSArrayVerify() {
} }
void JSRegExp::JSRegExpVerify() {
JSObjectVerify();
ASSERT(type()->IsSmi() || type()->IsUndefined());
ASSERT(data()->IsUndefined() || data()->IsFixedArray());
}
void Proxy::ProxyPrint() { void Proxy::ProxyPrint() {
PrintF("proxy to %p", proxy()); PrintF("proxy to %p", proxy());
} }
......
...@@ -293,6 +293,12 @@ bool Object::IsJSArray() { ...@@ -293,6 +293,12 @@ bool Object::IsJSArray() {
} }
bool Object::IsJSRegExp() {
return Object::IsHeapObject()
&& HeapObject::cast(this)->map()->instance_type() == JS_REGEXP_TYPE;
}
template <> inline bool Is<JSArray>(Object* obj) { template <> inline bool Is<JSArray>(Object* obj) {
return obj->IsJSArray(); return obj->IsJSArray();
} }
...@@ -487,7 +493,7 @@ Object* Object::GetProperty(String* key, PropertyAttributes* attributes) { ...@@ -487,7 +493,7 @@ Object* Object::GetProperty(String* key, PropertyAttributes* attributes) {
Object* HeapObject::GetHeapObjectField(HeapObject* obj, int index) { Object* HeapObject::GetHeapObjectField(HeapObject* obj, int index) {
return READ_FIELD(obj, HeapObject::kSize + kPointerSize * index); return READ_FIELD(obj, HeapObject::kHeaderSize + kPointerSize * index);
} }
...@@ -756,7 +762,7 @@ void HeapObject::CopyBody(JSObject* from) { ...@@ -756,7 +762,7 @@ void HeapObject::CopyBody(JSObject* from) {
ASSERT(map() == from->map()); ASSERT(map() == from->map());
ASSERT(Size() == from->Size()); ASSERT(Size() == from->Size());
int object_size = Size(); int object_size = Size();
for (int offset = kSize; offset < object_size; offset += kPointerSize) { for (int offset = kHeaderSize; offset < object_size; offset += kPointerSize) {
Object* value = READ_FIELD(from, offset); Object* value = READ_FIELD(from, offset);
// Note: WRITE_FIELD does not update the write barrier. // Note: WRITE_FIELD does not update the write barrier.
WRITE_FIELD(this, offset, value); WRITE_FIELD(this, offset, value);
...@@ -848,6 +854,8 @@ int JSObject::GetHeaderSize() { ...@@ -848,6 +854,8 @@ int JSObject::GetHeaderSize() {
return JSValue::kSize; return JSValue::kSize;
case JS_ARRAY_TYPE: case JS_ARRAY_TYPE:
return JSValue::kSize; return JSValue::kSize;
case JS_REGEXP_TYPE:
return JSValue::kSize;
case JS_OBJECT_TYPE: case JS_OBJECT_TYPE:
return JSObject::kHeaderSize; return JSObject::kHeaderSize;
default: default:
...@@ -885,7 +893,7 @@ void JSObject::InitializeBody(int object_size) { ...@@ -885,7 +893,7 @@ void JSObject::InitializeBody(int object_size) {
void Struct::InitializeBody(int object_size) { void Struct::InitializeBody(int object_size) {
for (int offset = kSize; offset < object_size; offset += kPointerSize) { for (int offset = kHeaderSize; offset < object_size; offset += kPointerSize) {
WRITE_FIELD(this, offset, Heap::undefined_value()); WRITE_FIELD(this, offset, Heap::undefined_value());
} }
} }
...@@ -1124,6 +1132,7 @@ CAST_ACCESSOR(JSGlobalObject) ...@@ -1124,6 +1132,7 @@ CAST_ACCESSOR(JSGlobalObject)
CAST_ACCESSOR(JSBuiltinsObject) CAST_ACCESSOR(JSBuiltinsObject)
CAST_ACCESSOR(Code) CAST_ACCESSOR(Code)
CAST_ACCESSOR(JSArray) CAST_ACCESSOR(JSArray)
CAST_ACCESSOR(JSRegExp)
CAST_ACCESSOR(Proxy) CAST_ACCESSOR(Proxy)
CAST_ACCESSOR(ByteArray) CAST_ACCESSOR(ByteArray)
CAST_ACCESSOR(Struct) CAST_ACCESSOR(Struct)
...@@ -2005,6 +2014,20 @@ byte* Code::sinfo_start() { ...@@ -2005,6 +2014,20 @@ byte* Code::sinfo_start() {
ACCESSORS(JSArray, length, Object, kLengthOffset) ACCESSORS(JSArray, length, Object, kLengthOffset)
ACCESSORS(JSRegExp, data, Object, kDataOffset)
ACCESSORS(JSRegExp, type, Object, kTypeOffset)
JSRegExp::Type JSRegExp::type_tag() {
return static_cast<JSRegExp::Type>(Smi::cast(type())->value());
}
void JSRegExp::set_type_tag(JSRegExp::Type value) {
set_type(Smi::FromInt(value));
}
bool JSObject::HasFastElements() { bool JSObject::HasFastElements() {
return !elements()->IsDictionary(); return !elements()->IsDictionary();
} }
......
...@@ -620,6 +620,10 @@ void JSObject::JSObjectShortPrint(StringStream* accumulator) { ...@@ -620,6 +620,10 @@ void JSObject::JSObjectShortPrint(StringStream* accumulator) {
accumulator->Add("<JS array[%u]>", static_cast<uint32_t>(length)); accumulator->Add("<JS array[%u]>", static_cast<uint32_t>(length));
break; break;
} }
case JS_REGEXP_TYPE: {
accumulator->Add("<JS RegExp>");
break;
}
case JS_FUNCTION_TYPE: { case JS_FUNCTION_TYPE: {
Object* fun_name = JSFunction::cast(this)->shared()->name(); Object* fun_name = JSFunction::cast(this)->shared()->name();
bool printed = false; bool printed = false;
...@@ -819,6 +823,7 @@ void HeapObject::IterateBody(InstanceType type, int object_size, ...@@ -819,6 +823,7 @@ void HeapObject::IterateBody(InstanceType type, int object_size,
case JS_OBJECT_TYPE: case JS_OBJECT_TYPE:
case JS_VALUE_TYPE: case JS_VALUE_TYPE:
case JS_ARRAY_TYPE: case JS_ARRAY_TYPE:
case JS_REGEXP_TYPE:
case JS_FUNCTION_TYPE: case JS_FUNCTION_TYPE:
case JS_GLOBAL_OBJECT_TYPE: case JS_GLOBAL_OBJECT_TYPE:
reinterpret_cast<JSObject*>(this)->JSObjectIterateBody(object_size, v); reinterpret_cast<JSObject*>(this)->JSObjectIterateBody(object_size, v);
...@@ -861,7 +866,7 @@ void HeapObject::IterateBody(InstanceType type, int object_size, ...@@ -861,7 +866,7 @@ void HeapObject::IterateBody(InstanceType type, int object_size,
void HeapObject::IterateStructBody(int object_size, ObjectVisitor* v) { void HeapObject::IterateStructBody(int object_size, ObjectVisitor* v) {
IteratePointers(v, HeapObject::kSize, object_size); IteratePointers(v, HeapObject::kHeaderSize, object_size);
} }
......
...@@ -43,6 +43,7 @@ ...@@ -43,6 +43,7 @@
// - HeapObject (superclass for everything allocated in the heap) // - HeapObject (superclass for everything allocated in the heap)
// - JSObject // - JSObject
// - JSArray // - JSArray
// - JSRegExp
// - JSFunction // - JSFunction
// - GlobalObject // - GlobalObject
// - JSGlobalObject // - JSGlobalObject
...@@ -263,6 +264,7 @@ class PropertyDetails BASE_EMBEDDED { ...@@ -263,6 +264,7 @@ class PropertyDetails BASE_EMBEDDED {
V(JS_GLOBAL_OBJECT_TYPE) \ V(JS_GLOBAL_OBJECT_TYPE) \
V(JS_BUILTINS_OBJECT_TYPE) \ V(JS_BUILTINS_OBJECT_TYPE) \
V(JS_ARRAY_TYPE) \ V(JS_ARRAY_TYPE) \
V(JS_REGEXP_TYPE) \
\ \
V(JS_FUNCTION_TYPE) \ V(JS_FUNCTION_TYPE) \
...@@ -517,6 +519,7 @@ enum InstanceType { ...@@ -517,6 +519,7 @@ enum InstanceType {
JS_GLOBAL_OBJECT_TYPE, JS_GLOBAL_OBJECT_TYPE,
JS_BUILTINS_OBJECT_TYPE, JS_BUILTINS_OBJECT_TYPE,
JS_ARRAY_TYPE, JS_ARRAY_TYPE,
JS_REGEXP_TYPE,
JS_FUNCTION_TYPE, JS_FUNCTION_TYPE,
...@@ -528,7 +531,7 @@ enum InstanceType { ...@@ -528,7 +531,7 @@ enum InstanceType {
// function objects are not counted as objects, even though they are // function objects are not counted as objects, even though they are
// implemented as such; only values whose typeof is "object" are included. // implemented as such; only values whose typeof is "object" are included.
FIRST_JS_OBJECT_TYPE = JS_VALUE_TYPE, FIRST_JS_OBJECT_TYPE = JS_VALUE_TYPE,
LAST_JS_OBJECT_TYPE = JS_ARRAY_TYPE LAST_JS_OBJECT_TYPE = JS_REGEXP_TYPE
}; };
...@@ -611,6 +614,7 @@ class Object BASE_EMBEDDED { ...@@ -611,6 +614,7 @@ class Object BASE_EMBEDDED {
inline bool IsProxy(); inline bool IsProxy();
inline bool IsBoolean(); inline bool IsBoolean();
inline bool IsJSArray(); inline bool IsJSArray();
inline bool IsJSRegExp();
inline bool IsHashTable(); inline bool IsHashTable();
inline bool IsDictionary(); inline bool IsDictionary();
inline bool IsSymbolTable(); inline bool IsSymbolTable();
...@@ -700,7 +704,7 @@ class Object BASE_EMBEDDED { ...@@ -700,7 +704,7 @@ class Object BASE_EMBEDDED {
static Object* cast(Object* value) { return value; } static Object* cast(Object* value) { return value; }
// Layout description. // Layout description.
static const int kSize = 0; // Object does not take up any space. static const int kHeaderSize = 0; // Object does not take up any space.
private: private:
DISALLOW_IMPLICIT_CONSTRUCTORS(Object); DISALLOW_IMPLICIT_CONSTRUCTORS(Object);
...@@ -1042,8 +1046,8 @@ class HeapObject: public Object { ...@@ -1042,8 +1046,8 @@ class HeapObject: public Object {
// Layout description. // Layout description.
// First field in a heap object is map. // First field in a heap object is map.
static const int kMapOffset = Object::kSize; static const int kMapOffset = Object::kHeaderSize;
static const int kSize = kMapOffset + kPointerSize; static const int kHeaderSize = kMapOffset + kPointerSize;
protected: protected:
// helpers for calling an ObjectVisitor to iterate over pointers in the // helpers for calling an ObjectVisitor to iterate over pointers in the
...@@ -1081,7 +1085,7 @@ class HeapNumber: public HeapObject { ...@@ -1081,7 +1085,7 @@ class HeapNumber: public HeapObject {
#endif #endif
// Layout description. // Layout description.
static const int kValueOffset = HeapObject::kSize; static const int kValueOffset = HeapObject::kHeaderSize;
static const int kSize = kValueOffset + kDoubleSize; static const int kSize = kValueOffset + kDoubleSize;
private: private:
...@@ -1371,7 +1375,7 @@ class JSObject: public HeapObject { ...@@ -1371,7 +1375,7 @@ class JSObject: public HeapObject {
static const int kMaxFastProperties = 8; static const int kMaxFastProperties = 8;
// Layout description. // Layout description.
static const int kPropertiesOffset = HeapObject::kSize; static const int kPropertiesOffset = HeapObject::kHeaderSize;
static const int kElementsOffset = kPropertiesOffset + kPointerSize; static const int kElementsOffset = kPropertiesOffset + kPointerSize;
static const int kHeaderSize = kElementsOffset + kPointerSize; static const int kHeaderSize = kElementsOffset + kPointerSize;
...@@ -1423,7 +1427,7 @@ class Array: public HeapObject { ...@@ -1423,7 +1427,7 @@ class Array: public HeapObject {
static inline bool IndexFromObject(Object* object, uint32_t* index); static inline bool IndexFromObject(Object* object, uint32_t* index);
// Layout descriptor. // Layout descriptor.
static const int kLengthOffset = HeapObject::kSize; static const int kLengthOffset = HeapObject::kHeaderSize;
static const int kHeaderSize = kLengthOffset + kIntSize; static const int kHeaderSize = kLengthOffset + kIntSize;
private: private:
...@@ -2180,7 +2184,7 @@ class Code: public HeapObject { ...@@ -2180,7 +2184,7 @@ class Code: public HeapObject {
#endif #endif
// Layout description. // Layout description.
static const int kInstructionSizeOffset = HeapObject::kSize; static const int kInstructionSizeOffset = HeapObject::kHeaderSize;
static const int kRelocationSizeOffset = kInstructionSizeOffset + kIntSize; static const int kRelocationSizeOffset = kInstructionSizeOffset + kIntSize;
static const int kSInfoSizeOffset = kRelocationSizeOffset + kIntSize; static const int kSInfoSizeOffset = kRelocationSizeOffset + kIntSize;
static const int kFlagsOffset = kSInfoSizeOffset + kIntSize; static const int kFlagsOffset = kSInfoSizeOffset + kIntSize;
...@@ -2360,7 +2364,7 @@ class Map: public HeapObject { ...@@ -2360,7 +2364,7 @@ class Map: public HeapObject {
#endif #endif
// Layout description. // Layout description.
static const int kInstanceAttributesOffset = HeapObject::kSize; static const int kInstanceAttributesOffset = HeapObject::kHeaderSize;
static const int kPrototypeOffset = kInstanceAttributesOffset + kIntSize; static const int kPrototypeOffset = kInstanceAttributesOffset + kIntSize;
static const int kConstructorOffset = kPrototypeOffset + kPointerSize; static const int kConstructorOffset = kPrototypeOffset + kPointerSize;
static const int kInstanceDescriptorsOffset = static const int kInstanceDescriptorsOffset =
...@@ -2435,7 +2439,7 @@ class Script: public Struct { ...@@ -2435,7 +2439,7 @@ class Script: public Struct {
void ScriptVerify(); void ScriptVerify();
#endif #endif
static const int kSourceOffset = HeapObject::kSize; static const int kSourceOffset = HeapObject::kHeaderSize;
static const int kNameOffset = kSourceOffset + kPointerSize; static const int kNameOffset = kSourceOffset + kPointerSize;
static const int kLineOffsetOffset = kNameOffset + kPointerSize; static const int kLineOffsetOffset = kNameOffset + kPointerSize;
static const int kColumnOffsetOffset = kLineOffsetOffset + kPointerSize; static const int kColumnOffsetOffset = kLineOffsetOffset + kPointerSize;
...@@ -2547,7 +2551,7 @@ class SharedFunctionInfo: public HeapObject { ...@@ -2547,7 +2551,7 @@ class SharedFunctionInfo: public HeapObject {
static const int kDontAdaptArgumentsSentinel = -1; static const int kDontAdaptArgumentsSentinel = -1;
// Layout description. // Layout description.
static const int kNameOffset = HeapObject::kSize; static const int kNameOffset = HeapObject::kHeaderSize;
static const int kCodeOffset = kNameOffset + kPointerSize; static const int kCodeOffset = kNameOffset + kPointerSize;
static const int kLengthOffset = kCodeOffset + kPointerSize; static const int kLengthOffset = kCodeOffset + kPointerSize;
static const int kFormalParameterCountOffset = kLengthOffset + kIntSize; static const int kFormalParameterCountOffset = kLengthOffset + kIntSize;
...@@ -2788,6 +2792,31 @@ class JSValue: public JSObject { ...@@ -2788,6 +2792,31 @@ class JSValue: public JSObject {
}; };
// Regular expressions
class JSRegExp: public JSObject {
public:
enum Type { JSCRE, INDEX_OF };
inline Type type_tag();
inline void set_type_tag(Type value);
DECL_ACCESSORS(type, Object)
DECL_ACCESSORS(data, Object)
static inline JSRegExp* cast(Object* obj);
// Dispatched behavior.
#ifdef DEBUG
void JSRegExpPrint();
void JSRegExpVerify();
#endif
static const int kTypeOffset = JSObject::kHeaderSize;
static const int kDataOffset = kTypeOffset + kIntSize;
static const int kSize = kDataOffset + kIntSize;
};
enum AllowNullsFlag {ALLOW_NULLS, DISALLOW_NULLS}; enum AllowNullsFlag {ALLOW_NULLS, DISALLOW_NULLS};
enum RobustnessFlag {ROBUST_STRING_TRAVERSAL, FAST_STRING_TRAVERSAL}; enum RobustnessFlag {ROBUST_STRING_TRAVERSAL, FAST_STRING_TRAVERSAL};
...@@ -2924,7 +2953,7 @@ class String: public HeapObject { ...@@ -2924,7 +2953,7 @@ class String: public HeapObject {
inline bool IsFlat(); inline bool IsFlat();
// Layout description. // Layout description.
static const int kLengthOffset = HeapObject::kSize; static const int kLengthOffset = HeapObject::kHeaderSize;
static const int kSize = kLengthOffset + kIntSize; static const int kSize = kLengthOffset + kIntSize;
// Limits on sizes of different types of strings. // Limits on sizes of different types of strings.
...@@ -3344,7 +3373,7 @@ class Oddball: public HeapObject { ...@@ -3344,7 +3373,7 @@ class Oddball: public HeapObject {
Object* Initialize(const char* to_string, Object* to_number); Object* Initialize(const char* to_string, Object* to_number);
// Layout description. // Layout description.
static const int kToStringOffset = HeapObject::kSize; static const int kToStringOffset = HeapObject::kHeaderSize;
static const int kToNumberOffset = kToStringOffset + kPointerSize; static const int kToNumberOffset = kToStringOffset + kPointerSize;
static const int kSize = kToNumberOffset + kPointerSize; static const int kSize = kToNumberOffset + kPointerSize;
...@@ -3374,7 +3403,7 @@ class Proxy: public HeapObject { ...@@ -3374,7 +3403,7 @@ class Proxy: public HeapObject {
// Layout description. // Layout description.
static const int kProxyOffset = HeapObject::kSize; static const int kProxyOffset = HeapObject::kHeaderSize;
static const int kSize = kProxyOffset + kPointerSize; static const int kSize = kProxyOffset + kPointerSize;
private: private:
...@@ -3457,7 +3486,7 @@ class AccessorInfo: public Struct { ...@@ -3457,7 +3486,7 @@ class AccessorInfo: public Struct {
void AccessorInfoVerify(); void AccessorInfoVerify();
#endif #endif
static const int kGetterOffset = HeapObject::kSize; static const int kGetterOffset = HeapObject::kHeaderSize;
static const int kSetterOffset = kGetterOffset + kPointerSize; static const int kSetterOffset = kGetterOffset + kPointerSize;
static const int kDataOffset = kSetterOffset + kPointerSize; static const int kDataOffset = kSetterOffset + kPointerSize;
static const int kNameOffset = kDataOffset + kPointerSize; static const int kNameOffset = kDataOffset + kPointerSize;
...@@ -3487,7 +3516,7 @@ class AccessCheckInfo: public Struct { ...@@ -3487,7 +3516,7 @@ class AccessCheckInfo: public Struct {
void AccessCheckInfoVerify(); void AccessCheckInfoVerify();
#endif #endif
static const int kNamedCallbackOffset = HeapObject::kSize; static const int kNamedCallbackOffset = HeapObject::kHeaderSize;
static const int kIndexedCallbackOffset = kNamedCallbackOffset + kPointerSize; static const int kIndexedCallbackOffset = kNamedCallbackOffset + kPointerSize;
static const int kDataOffset = kIndexedCallbackOffset + kPointerSize; static const int kDataOffset = kIndexedCallbackOffset + kPointerSize;
static const int kSize = kDataOffset + kPointerSize; static const int kSize = kDataOffset + kPointerSize;
...@@ -3513,7 +3542,7 @@ class InterceptorInfo: public Struct { ...@@ -3513,7 +3542,7 @@ class InterceptorInfo: public Struct {
void InterceptorInfoVerify(); void InterceptorInfoVerify();
#endif #endif
static const int kGetterOffset = HeapObject::kSize; static const int kGetterOffset = HeapObject::kHeaderSize;
static const int kSetterOffset = kGetterOffset + kPointerSize; static const int kSetterOffset = kGetterOffset + kPointerSize;
static const int kQueryOffset = kSetterOffset + kPointerSize; static const int kQueryOffset = kSetterOffset + kPointerSize;
static const int kDeleterOffset = kQueryOffset + kPointerSize; static const int kDeleterOffset = kQueryOffset + kPointerSize;
...@@ -3538,7 +3567,7 @@ class CallHandlerInfo: public Struct { ...@@ -3538,7 +3567,7 @@ class CallHandlerInfo: public Struct {
void CallHandlerInfoVerify(); void CallHandlerInfoVerify();
#endif #endif
static const int kCallbackOffset = HeapObject::kSize; static const int kCallbackOffset = HeapObject::kHeaderSize;
static const int kDataOffset = kCallbackOffset + kPointerSize; static const int kDataOffset = kCallbackOffset + kPointerSize;
static const int kSize = kDataOffset + kPointerSize; static const int kSize = kDataOffset + kPointerSize;
...@@ -3556,7 +3585,7 @@ class TemplateInfo: public Struct { ...@@ -3556,7 +3585,7 @@ class TemplateInfo: public Struct {
void TemplateInfoVerify(); void TemplateInfoVerify();
#endif #endif
static const int kTagOffset = HeapObject::kSize; static const int kTagOffset = HeapObject::kHeaderSize;
static const int kPropertyListOffset = kTagOffset + kPointerSize; static const int kPropertyListOffset = kTagOffset + kPointerSize;
static const int kHeaderSize = kPropertyListOffset + kPointerSize; static const int kHeaderSize = kPropertyListOffset + kPointerSize;
protected: protected:
...@@ -3657,7 +3686,7 @@ class SignatureInfo: public Struct { ...@@ -3657,7 +3686,7 @@ class SignatureInfo: public Struct {
void SignatureInfoVerify(); void SignatureInfoVerify();
#endif #endif
static const int kReceiverOffset = Struct::kSize; static const int kReceiverOffset = Struct::kHeaderSize;
static const int kArgsOffset = kReceiverOffset + kPointerSize; static const int kArgsOffset = kReceiverOffset + kPointerSize;
static const int kSize = kArgsOffset + kPointerSize; static const int kSize = kArgsOffset + kPointerSize;
...@@ -3677,7 +3706,7 @@ class TypeSwitchInfo: public Struct { ...@@ -3677,7 +3706,7 @@ class TypeSwitchInfo: public Struct {
void TypeSwitchInfoVerify(); void TypeSwitchInfoVerify();
#endif #endif
static const int kTypesOffset = Struct::kSize; static const int kTypesOffset = Struct::kHeaderSize;
static const int kSize = kTypesOffset + kPointerSize; static const int kSize = kTypesOffset + kPointerSize;
}; };
...@@ -3723,7 +3752,7 @@ class DebugInfo: public Struct { ...@@ -3723,7 +3752,7 @@ class DebugInfo: public Struct {
void DebugInfoVerify(); void DebugInfoVerify();
#endif #endif
static const int kSharedFunctionInfoIndex = Struct::kSize; static const int kSharedFunctionInfoIndex = Struct::kHeaderSize;
static const int kOriginalCodeIndex = kSharedFunctionInfoIndex + kPointerSize; static const int kOriginalCodeIndex = kSharedFunctionInfoIndex + kPointerSize;
static const int kPatchedCodeIndex = kOriginalCodeIndex + kPointerSize; static const int kPatchedCodeIndex = kOriginalCodeIndex + kPointerSize;
static const int kActiveBreakPointsCountIndex = static const int kActiveBreakPointsCountIndex =
...@@ -3776,7 +3805,7 @@ class BreakPointInfo: public Struct { ...@@ -3776,7 +3805,7 @@ class BreakPointInfo: public Struct {
void BreakPointInfoVerify(); void BreakPointInfoVerify();
#endif #endif
static const int kCodePositionIndex = Struct::kSize; static const int kCodePositionIndex = Struct::kHeaderSize;
static const int kSourcePositionIndex = kCodePositionIndex + kPointerSize; static const int kSourcePositionIndex = kCodePositionIndex + kPointerSize;
static const int kStatementPositionIndex = static const int kStatementPositionIndex =
kSourcePositionIndex + kPointerSize; kSourcePositionIndex + kPointerSize;
......
...@@ -212,8 +212,8 @@ static Object* Runtime_IsConstructCall(Arguments args) { ...@@ -212,8 +212,8 @@ static Object* Runtime_IsConstructCall(Arguments args) {
static Object* Runtime_RegExpCompile(Arguments args) { static Object* Runtime_RegExpCompile(Arguments args) {
HandleScope scope; // create a new handle scope HandleScope scope; // create a new handle scope
ASSERT(args.length() == 3); ASSERT(args.length() == 3);
CONVERT_CHECKED(JSValue, raw_re, args[0]); CONVERT_CHECKED(JSRegExp, raw_re, args[0]);
Handle<JSValue> re(raw_re); Handle<JSRegExp> re(raw_re);
CONVERT_CHECKED(String, raw_pattern, args[1]); CONVERT_CHECKED(String, raw_pattern, args[1]);
Handle<String> pattern(raw_pattern); Handle<String> pattern(raw_pattern);
CONVERT_CHECKED(String, raw_flags, args[2]); CONVERT_CHECKED(String, raw_flags, args[2]);
...@@ -665,8 +665,8 @@ static Object* Runtime_InitializeConstContextSlot(Arguments args) { ...@@ -665,8 +665,8 @@ static Object* Runtime_InitializeConstContextSlot(Arguments args) {
static Object* Runtime_RegExpExec(Arguments args) { static Object* Runtime_RegExpExec(Arguments args) {
HandleScope scope; HandleScope scope;
ASSERT(args.length() == 3); ASSERT(args.length() == 3);
CONVERT_CHECKED(JSValue, raw_regexp, args[0]); CONVERT_CHECKED(JSRegExp, raw_regexp, args[0]);
Handle<JSValue> regexp(raw_regexp); Handle<JSRegExp> regexp(raw_regexp);
CONVERT_CHECKED(String, raw_subject, args[1]); CONVERT_CHECKED(String, raw_subject, args[1]);
Handle<String> subject(raw_subject); Handle<String> subject(raw_subject);
Handle<Object> index(args[2]); Handle<Object> index(args[2]);
...@@ -678,8 +678,8 @@ static Object* Runtime_RegExpExec(Arguments args) { ...@@ -678,8 +678,8 @@ static Object* Runtime_RegExpExec(Arguments args) {
static Object* Runtime_RegExpExecGlobal(Arguments args) { static Object* Runtime_RegExpExecGlobal(Arguments args) {
HandleScope scope; HandleScope scope;
ASSERT(args.length() == 2); ASSERT(args.length() == 2);
CONVERT_CHECKED(JSValue, raw_regexp, args[0]); CONVERT_CHECKED(JSRegExp, raw_regexp, args[0]);
Handle<JSValue> regexp(raw_regexp); Handle<JSRegExp> regexp(raw_regexp);
CONVERT_CHECKED(String, raw_subject, args[1]); CONVERT_CHECKED(String, raw_subject, args[1]);
Handle<String> subject(raw_subject); Handle<String> subject(raw_subject);
return *RegExpImpl::JsreExecGlobal(regexp, subject); return *RegExpImpl::JsreExecGlobal(regexp, subject);
......
...@@ -52,6 +52,7 @@ POSSIBILITY OF SUCH DAMAGE. ...@@ -52,6 +52,7 @@ POSSIBILITY OF SUCH DAMAGE.
typedef uint16_t UChar; typedef uint16_t UChar;
struct JSRegExp; struct JSRegExp;
typedef struct JSRegExp JscreRegExp;
enum JSRegExpIgnoreCaseOption { JSRegExpDoNotIgnoreCase, JSRegExpIgnoreCase }; enum JSRegExpIgnoreCaseOption { JSRegExpDoNotIgnoreCase, JSRegExpIgnoreCase };
enum JSRegExpMultilineOption { JSRegExpSingleLine, JSRegExpMultiline }; enum JSRegExpMultilineOption { JSRegExpSingleLine, JSRegExpMultiline };
......
...@@ -30,9 +30,6 @@ prefix mjsunit ...@@ -30,9 +30,6 @@ prefix mjsunit
# All tests in the bug directory are expected to fail. # All tests in the bug directory are expected to fail.
bugs: FAIL bugs: FAIL
# This one fails in debug mode.
regexp-multiline-stack-trace: PASS IF $MODE==RELEASE, FAIL IF $MODE==DEBUG
# This one uses a built-in that's only present in debug mode. # This one uses a built-in that's only present in debug mode.
fuzz-natives: PASS, SKIP IF $MODE==RELEASE fuzz-natives: PASS, SKIP IF $MODE==RELEASE
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment