Micro-optimizing the json parser
Review URL: https://chromiumcodereview.appspot.com/11237002 git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@12779 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
This commit is contained in:
parent
4f40326fae
commit
d33cda9338
@ -149,6 +149,8 @@ class JsonParser BASE_EMBEDDED {
|
||||
}
|
||||
|
||||
inline Isolate* isolate() { return isolate_; }
|
||||
inline Factory* factory() { return factory_; }
|
||||
inline Handle<JSFunction> object_constructor() { return object_constructor_; }
|
||||
inline Zone* zone() const { return zone_; }
|
||||
|
||||
static const int kInitialSpecialStringLength = 1024;
|
||||
@ -160,6 +162,8 @@ class JsonParser BASE_EMBEDDED {
|
||||
Handle<SeqAsciiString> seq_source_;
|
||||
|
||||
Isolate* isolate_;
|
||||
Factory* factory_;
|
||||
Handle<JSFunction> object_constructor_;
|
||||
uc32 c0_;
|
||||
int position_;
|
||||
Zone* zone_;
|
||||
@ -169,6 +173,9 @@ template <bool seq_ascii>
|
||||
Handle<Object> JsonParser<seq_ascii>::ParseJson(Handle<String> source,
|
||||
Zone* zone) {
|
||||
isolate_ = source->map()->GetHeap()->isolate();
|
||||
factory_ = isolate_->factory();
|
||||
object_constructor_ =
|
||||
Handle<JSFunction>(isolate()->native_context()->object_function());
|
||||
zone_ = zone;
|
||||
FlattenString(source);
|
||||
source_ = source;
|
||||
@ -188,7 +195,7 @@ Handle<Object> JsonParser<seq_ascii>::ParseJson(Handle<String> source,
|
||||
// Parse failed. Current character is the unexpected token.
|
||||
|
||||
const char* message;
|
||||
Factory* factory = isolate()->factory();
|
||||
Factory* factory = this->factory();
|
||||
Handle<JSArray> array;
|
||||
|
||||
switch (c0_) {
|
||||
@ -237,52 +244,35 @@ Handle<Object> JsonParser<seq_ascii>::ParseJson(Handle<String> source,
|
||||
// Parse any JSON value.
|
||||
template <bool seq_ascii>
|
||||
Handle<Object> JsonParser<seq_ascii>::ParseJsonValue() {
|
||||
switch (c0_) {
|
||||
case '"':
|
||||
return ParseJsonString();
|
||||
case '-':
|
||||
case '0':
|
||||
case '1':
|
||||
case '2':
|
||||
case '3':
|
||||
case '4':
|
||||
case '5':
|
||||
case '6':
|
||||
case '7':
|
||||
case '8':
|
||||
case '9':
|
||||
return ParseJsonNumber();
|
||||
case 'f':
|
||||
if (AdvanceGetChar() == 'a' && AdvanceGetChar() == 'l' &&
|
||||
AdvanceGetChar() == 's' && AdvanceGetChar() == 'e') {
|
||||
AdvanceSkipWhitespace();
|
||||
return isolate()->factory()->false_value();
|
||||
} else {
|
||||
return ReportUnexpectedCharacter();
|
||||
}
|
||||
case 't':
|
||||
if (AdvanceGetChar() == 'r' && AdvanceGetChar() == 'u' &&
|
||||
AdvanceGetChar() == 'e') {
|
||||
AdvanceSkipWhitespace();
|
||||
return isolate()->factory()->true_value();
|
||||
} else {
|
||||
return ReportUnexpectedCharacter();
|
||||
}
|
||||
case 'n':
|
||||
if (AdvanceGetChar() == 'u' && AdvanceGetChar() == 'l' &&
|
||||
AdvanceGetChar() == 'l') {
|
||||
AdvanceSkipWhitespace();
|
||||
return isolate()->factory()->null_value();
|
||||
} else {
|
||||
return ReportUnexpectedCharacter();
|
||||
}
|
||||
case '{':
|
||||
return ParseJsonObject();
|
||||
case '[':
|
||||
return ParseJsonArray();
|
||||
default:
|
||||
return ReportUnexpectedCharacter();
|
||||
if (c0_ == '"') return ParseJsonString();
|
||||
if ((c0_ >= '0' && c0_ <= '9') || c0_ == '-') return ParseJsonNumber();
|
||||
if (c0_ == '{') return ParseJsonObject();
|
||||
if (c0_ == '[') return ParseJsonArray();
|
||||
if (c0_ == 'f') {
|
||||
if (AdvanceGetChar() == 'a' && AdvanceGetChar() == 'l' &&
|
||||
AdvanceGetChar() == 's' && AdvanceGetChar() == 'e') {
|
||||
AdvanceSkipWhitespace();
|
||||
return factory()->false_value();
|
||||
}
|
||||
return ReportUnexpectedCharacter();
|
||||
}
|
||||
if (c0_ == 't') {
|
||||
if (AdvanceGetChar() == 'r' && AdvanceGetChar() == 'u' &&
|
||||
AdvanceGetChar() == 'e') {
|
||||
AdvanceSkipWhitespace();
|
||||
return factory()->true_value();
|
||||
}
|
||||
return ReportUnexpectedCharacter();
|
||||
}
|
||||
if (c0_ == 'n') {
|
||||
if (AdvanceGetChar() == 'u' && AdvanceGetChar() == 'l' &&
|
||||
AdvanceGetChar() == 'l') {
|
||||
AdvanceSkipWhitespace();
|
||||
return factory()->null_value();
|
||||
}
|
||||
return ReportUnexpectedCharacter();
|
||||
}
|
||||
return ReportUnexpectedCharacter();
|
||||
}
|
||||
|
||||
|
||||
@ -290,10 +280,8 @@ Handle<Object> JsonParser<seq_ascii>::ParseJsonValue() {
|
||||
template <bool seq_ascii>
|
||||
Handle<Object> JsonParser<seq_ascii>::ParseJsonObject() {
|
||||
Handle<Object> prototype;
|
||||
Handle<JSFunction> object_constructor(
|
||||
isolate()->native_context()->object_function());
|
||||
Handle<JSObject> json_object =
|
||||
isolate()->factory()->NewJSObject(object_constructor);
|
||||
factory()->NewJSObject(object_constructor());
|
||||
ASSERT_EQ(c0_, '{');
|
||||
|
||||
AdvanceSkipWhitespace();
|
||||
@ -377,11 +365,11 @@ Handle<Object> JsonParser<seq_ascii>::ParseJsonArray() {
|
||||
AdvanceSkipWhitespace();
|
||||
// Allocate a fixed array with all the elements.
|
||||
Handle<FixedArray> fast_elements =
|
||||
isolate()->factory()->NewFixedArray(elements.length());
|
||||
factory()->NewFixedArray(elements.length());
|
||||
for (int i = 0, n = elements.length(); i < n; i++) {
|
||||
fast_elements->set(i, *elements[i]);
|
||||
}
|
||||
return isolate()->factory()->NewJSArrayWithElements(fast_elements);
|
||||
return factory()->NewJSArrayWithElements(fast_elements);
|
||||
}
|
||||
|
||||
|
||||
@ -448,7 +436,7 @@ Handle<Object> JsonParser<seq_ascii>::ParseJsonNumber() {
|
||||
buffer.Dispose();
|
||||
}
|
||||
SkipWhitespace();
|
||||
return isolate()->factory()->NewNumber(number);
|
||||
return factory()->NewNumber(number);
|
||||
}
|
||||
|
||||
|
||||
@ -489,8 +477,7 @@ Handle<String> JsonParser<seq_ascii>::SlowScanJsonString(
|
||||
int count = end - start;
|
||||
int max_length = count + source_length_ - position_;
|
||||
int length = Min(max_length, Max(kInitialSpecialStringLength, 2 * count));
|
||||
Handle<StringType> seq_str = NewRawString<StringType>(isolate()->factory(),
|
||||
length);
|
||||
Handle<StringType> seq_str = NewRawString<StringType>(factory(), length);
|
||||
// Copy prefix into seq_str.
|
||||
SinkChar* dest = seq_str->GetChars();
|
||||
String::WriteToFlat(*prefix, dest, start, end);
|
||||
@ -668,11 +655,11 @@ Handle<String> JsonParser<seq_ascii>::ScanJsonString() {
|
||||
int length = position_ - beg_pos;
|
||||
Handle<String> result;
|
||||
if (seq_ascii && is_symbol) {
|
||||
result = isolate()->factory()->LookupAsciiSymbol(seq_source_,
|
||||
result = factory()->LookupAsciiSymbol(seq_source_,
|
||||
beg_pos,
|
||||
length);
|
||||
} else {
|
||||
result = isolate()->factory()->NewRawAsciiString(length);
|
||||
result = factory()->NewRawAsciiString(length);
|
||||
char* dest = SeqAsciiString::cast(*result)->GetChars();
|
||||
String::WriteToFlat(*source_, dest, beg_pos, position_);
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user