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

Unified Diff: src/parser.cc

Issue 5862002: Version 3.0.2. (Closed)
Patch Set: Created 10 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
« ChangeLog ('K') | « src/parser.h ('k') | src/platform-linux.cc » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/parser.cc
diff --git a/src/parser.cc b/src/parser.cc
index 94ad57c9c28ba02a40b111562c56aa1f243129b1..056332b5b44ec8de7049aa392daa1ddda57e0ebb 100644
--- a/src/parser.cc
+++ b/src/parser.cc
@@ -609,25 +609,7 @@ FunctionLiteral* Parser::ParseProgram(Handle<String> source,
// Initialize parser state.
source->TryFlatten();
- if (source->IsExternalTwoByteString()) {
- // Notice that the stream is destroyed at the end of the branch block.
- // The last line of the blocks can't be moved outside, even though they're
- // identical calls.
- ExternalTwoByteStringUC16CharacterStream stream(
- Handle<ExternalTwoByteString>::cast(source), 0, source->length());
- scanner_.Initialize(&stream, JavaScriptScanner::kAllLiterals);
- return DoParseProgram(source, in_global_context, &zone_scope);
- } else {
- GenericStringUC16CharacterStream stream(source, 0, source->length());
- scanner_.Initialize(&stream, JavaScriptScanner::kAllLiterals);
- return DoParseProgram(source, in_global_context, &zone_scope);
- }
-}
-
-
-FunctionLiteral* Parser::DoParseProgram(Handle<String> source,
- bool in_global_context,
- ZoneScope* zone_scope) {
+ scanner_.Initialize(source);
ASSERT(target_stack_ == NULL);
if (pre_data_ != NULL) pre_data_->Initialize();
@@ -673,45 +655,25 @@ FunctionLiteral* Parser::DoParseProgram(Handle<String> source,
// If there was a syntax error we have to get rid of the AST
// and it is not safe to do so before the scope has been deleted.
- if (result == NULL) zone_scope->DeleteOnExit();
+ if (result == NULL) zone_scope.DeleteOnExit();
return result;
}
+
FunctionLiteral* Parser::ParseLazy(Handle<SharedFunctionInfo> info) {
CompilationZoneScope zone_scope(DONT_DELETE_ON_EXIT);
HistogramTimerScope timer(&Counters::parse_lazy);
Handle<String> source(String::cast(script_->source()));
Counters::total_parse_size.Increment(source->length());
- // Initialize parser state.
- source->TryFlatten();
- if (source->IsExternalTwoByteString()) {
- ExternalTwoByteStringUC16CharacterStream stream(
- Handle<ExternalTwoByteString>::cast(source),
- info->start_position(),
- info->end_position());
- FunctionLiteral* result = ParseLazy(info, &stream, &zone_scope);
- return result;
- } else {
- GenericStringUC16CharacterStream stream(source,
- info->start_position(),
- info->end_position());
- FunctionLiteral* result = ParseLazy(info, &stream, &zone_scope);
- return result;
- }
-}
-
-
-FunctionLiteral* Parser::ParseLazy(Handle<SharedFunctionInfo> info,
- UC16CharacterStream* source,
- ZoneScope* zone_scope) {
- scanner_.Initialize(source, JavaScriptScanner::kAllLiterals);
- ASSERT(target_stack_ == NULL);
-
Handle<String> name(String::cast(info->name()));
fni_ = new FuncNameInferrer();
fni_->PushEnclosingName(name);
+ // Initialize parser state.
+ source->TryFlatten();
+ scanner_.Initialize(source, info->start_position(), info->end_position());
+ ASSERT(target_stack_ == NULL);
mode_ = PARSE_EAGERLY;
// Place holder for the result.
@@ -743,7 +705,7 @@ FunctionLiteral* Parser::ParseLazy(Handle<SharedFunctionInfo> info,
// not safe to do before scope has been deleted.
if (result == NULL) {
Top::StackOverflow();
- zone_scope->DeleteOnExit();
+ zone_scope.DeleteOnExit();
} else {
Handle<String> inferred_name(info->inferred_name());
result->set_inferred_name(inferred_name);
@@ -757,12 +719,12 @@ Handle<String> Parser::GetSymbol(bool* ok) {
if (pre_data() != NULL) {
symbol_id = pre_data()->GetSymbolIdentifier();
}
- return LookupSymbol(symbol_id, scanner().literal());
+ return LookupSymbol(symbol_id, scanner_.literal());
}
void Parser::ReportMessage(const char* type, Vector<const char*> args) {
- Scanner::Location source_location = scanner().location();
+ Scanner::Location source_location = scanner_.location();
ReportMessageAt(source_location, type, args);
}
@@ -1679,7 +1641,7 @@ Statement* Parser::ParseContinueStatement(bool* ok) {
Expect(Token::CONTINUE, CHECK_OK);
Handle<String> label = Handle<String>::null();
Token::Value tok = peek();
- if (!scanner().has_line_terminator_before_next() &&
+ if (!scanner_.has_line_terminator_before_next() &&
tok != Token::SEMICOLON && tok != Token::RBRACE && tok != Token::EOS) {
label = ParseIdentifier(CHECK_OK);
}
@@ -1705,7 +1667,7 @@ Statement* Parser::ParseBreakStatement(ZoneStringList* labels, bool* ok) {
Expect(Token::BREAK, CHECK_OK);
Handle<String> label;
Token::Value tok = peek();
- if (!scanner().has_line_terminator_before_next() &&
+ if (!scanner_.has_line_terminator_before_next() &&
tok != Token::SEMICOLON && tok != Token::RBRACE && tok != Token::EOS) {
label = ParseIdentifier(CHECK_OK);
}
@@ -1750,7 +1712,7 @@ Statement* Parser::ParseReturnStatement(bool* ok) {
}
Token::Value tok = peek();
- if (scanner().has_line_terminator_before_next() ||
+ if (scanner_.has_line_terminator_before_next() ||
tok == Token::SEMICOLON ||
tok == Token::RBRACE ||
tok == Token::EOS) {
@@ -1882,7 +1844,7 @@ Statement* Parser::ParseThrowStatement(bool* ok) {
Expect(Token::THROW, CHECK_OK);
int pos = scanner().location().beg_pos;
- if (scanner().has_line_terminator_before_next()) {
+ if (scanner_.has_line_terminator_before_next()) {
ReportMessage("newline_after_throw", Vector<const char*>::empty());
*ok = false;
return NULL;
@@ -2446,8 +2408,7 @@ Expression* Parser::ParsePostfixExpression(bool* ok) {
// LeftHandSideExpression ('++' | '--')?
Expression* expression = ParseLeftHandSideExpression(CHECK_OK);
- if (!scanner().has_line_terminator_before_next() &&
- Token::IsCountOp(peek())) {
+ if (!scanner_.has_line_terminator_before_next() && Token::IsCountOp(peek())) {
// Signal a reference error if the expression is an invalid
// left-hand side expression. We could report this as a syntax
// error here but for compatibility with JSC we choose to report the
@@ -2716,7 +2677,7 @@ Expression* Parser::ParsePrimaryExpression(bool* ok) {
case Token::NUMBER: {
Consume(Token::NUMBER);
double value =
- StringToDouble(scanner().literal(), ALLOW_HEX | ALLOW_OCTALS);
+ StringToDouble(scanner_.literal(), ALLOW_HEX | ALLOW_OCTALS);
result = NewNumberLiteral(value);
break;
}
@@ -3067,7 +3028,7 @@ Expression* Parser::ParseObjectLiteral(bool* ok) {
case Token::NUMBER: {
Consume(Token::NUMBER);
double value =
- StringToDouble(scanner().literal(), ALLOW_HEX | ALLOW_OCTALS);
+ StringToDouble(scanner_.literal(), ALLOW_HEX | ALLOW_OCTALS);
key = NewNumberLiteral(value);
break;
}
@@ -3128,7 +3089,7 @@ Expression* Parser::ParseObjectLiteral(bool* ok) {
Expression* Parser::ParseRegExpLiteral(bool seen_equal, bool* ok) {
- if (!scanner().ScanRegExpPattern(seen_equal)) {
+ if (!scanner_.ScanRegExpPattern(seen_equal)) {
Next();
ReportMessage("unterminated_regexp", Vector<const char*>::empty());
*ok = false;
@@ -3138,10 +3099,10 @@ Expression* Parser::ParseRegExpLiteral(bool seen_equal, bool* ok) {
int literal_index = temp_scope_->NextMaterializedLiteralIndex();
Handle<String> js_pattern =
- Factory::NewStringFromUtf8(scanner().next_literal(), TENURED);
- scanner().ScanRegExpFlags();
+ Factory::NewStringFromUtf8(scanner_.next_literal(), TENURED);
+ scanner_.ScanRegExpFlags();
Handle<String> js_flags =
- Factory::NewStringFromUtf8(scanner().next_literal(), TENURED);
+ Factory::NewStringFromUtf8(scanner_.next_literal(), TENURED);
Next();
return new RegExpLiteral(js_pattern, js_flags, literal_index);
@@ -3197,7 +3158,7 @@ FunctionLiteral* Parser::ParseFunctionLiteral(Handle<String> var_name,
// FormalParameterList ::
// '(' (Identifier)*[','] ')'
Expect(Token::LPAREN, CHECK_OK);
- int start_pos = scanner().location().beg_pos;
+ int start_pos = scanner_.location().beg_pos;
bool done = (peek() == Token::RPAREN);
while (!done) {
Handle<String> param_name = ParseIdentifier(CHECK_OK);
@@ -3234,7 +3195,7 @@ FunctionLiteral* Parser::ParseFunctionLiteral(Handle<String> var_name,
bool is_lazily_compiled =
mode() == PARSE_LAZILY && top_scope_->HasTrivialOuterContext();
- int function_block_pos = scanner().location().beg_pos;
+ int function_block_pos = scanner_.location().beg_pos;
int materialized_literal_count;
int expected_property_count;
int end_pos;
@@ -3251,8 +3212,7 @@ FunctionLiteral* Parser::ParseFunctionLiteral(Handle<String> var_name,
ReportInvalidPreparseData(name, CHECK_OK);
}
Counters::total_preparse_skipped.Increment(end_pos - function_block_pos);
- // Seek to position just before terminal '}'.
- scanner().SeekForward(end_pos - 1);
+ scanner_.SeekForward(end_pos);
materialized_literal_count = entry.literal_count();
expected_property_count = entry.property_count();
only_simple_this_property_assignments = false;
@@ -3268,7 +3228,7 @@ FunctionLiteral* Parser::ParseFunctionLiteral(Handle<String> var_name,
this_property_assignments = temp_scope.this_property_assignments();
Expect(Token::RBRACE, CHECK_OK);
- end_pos = scanner().location().end_pos;
+ end_pos = scanner_.location().end_pos;
}
FunctionLiteral* function_literal =
@@ -3372,7 +3332,7 @@ void Parser::ExpectSemicolon(bool* ok) {
Next();
return;
}
- if (scanner().has_line_terminator_before_next() ||
+ if (scanner_.has_line_terminator_before_next() ||
tok == Token::RBRACE ||
tok == Token::EOS) {
return;
@@ -3423,8 +3383,8 @@ Handle<String> Parser::ParseIdentifierOrGetOrSet(bool* is_get,
bool* ok) {
Expect(Token::IDENTIFIER, ok);
if (!*ok) return Handle<String>();
- if (scanner().literal_length() == 3) {
- const char* token = scanner().literal_string();
+ if (scanner_.literal_length() == 3) {
+ const char* token = scanner_.literal_string();
*is_get = strcmp(token, "get") == 0;
*is_set = !*is_get && strcmp(token, "set") == 0;
}
@@ -3543,8 +3503,8 @@ Expression* Parser::NewThrowError(Handle<String> constructor,
// ----------------------------------------------------------------------------
// JSON
-Handle<Object> JsonParser::ParseJson(Handle<String> script,
- UC16CharacterStream* source) {
+Handle<Object> JsonParser::ParseJson(Handle<String> source) {
+ source->TryFlatten();
scanner_.Initialize(source);
stack_overflow_ = false;
Handle<Object> result = ParseJsonValue();
@@ -3580,7 +3540,7 @@ Handle<Object> JsonParser::ParseJson(Handle<String> script,
}
Scanner::Location source_location = scanner_.location();
- MessageLocation location(Factory::NewScript(script),
+ MessageLocation location(Factory::NewScript(source),
source_location.beg_pos,
source_location.end_pos);
int argc = (name_opt == NULL) ? 0 : 1;
@@ -4449,25 +4409,10 @@ CharacterRange RegExpParser::ParseClassAtom(uc16* char_class) {
}
-static const uc16 kNoCharClass = 0;
-
-// Adds range or pre-defined character class to character ranges.
-// If char_class is not kInvalidClass, it's interpreted as a class
-// escape (i.e., 's' means whitespace, from '\s').
-static inline void AddRangeOrEscape(ZoneList<CharacterRange>* ranges,
- uc16 char_class,
- CharacterRange range) {
- if (char_class != kNoCharClass) {
- CharacterRange::AddClassEscape(char_class, ranges);
- } else {
- ranges->Add(range);
- }
-}
-
-
RegExpTree* RegExpParser::ParseCharacterClass() {
static const char* kUnterminated = "Unterminated character class";
static const char* kRangeOutOfOrder = "Range out of order in character class";
+ static const char* kInvalidRange = "Invalid character range";
ASSERT_EQ(current(), '[');
Advance();
@@ -4476,10 +4421,30 @@ RegExpTree* RegExpParser::ParseCharacterClass() {
is_negated = true;
Advance();
}
+ // A CharacterClass is a sequence of single characters, character class
+ // escapes or ranges. Ranges are on the form "x-y" where x and y are
+ // single characters (and not character class escapes like \s).
+ // A "-" may occur at the start or end of the character class (just after
+ // "[" or "[^", or just before "]") without being considered part of a
+ // range. A "-" may also appear as the beginning or end of a range.
+ // I.e., [--+] is valid, so is [!--].
+
ZoneList<CharacterRange>* ranges = new ZoneList<CharacterRange>(2);
while (has_more() && current() != ']') {
- uc16 char_class = kNoCharClass;
+ uc16 char_class = 0;
CharacterRange first = ParseClassAtom(&char_class CHECK_FAILED);
+ if (char_class) {
+ CharacterRange::AddClassEscape(char_class, ranges);
+ if (current() == '-') {
+ Advance();
+ ranges->Add(CharacterRange::Singleton('-'));
+ if (current() != ']') {
+ ReportError(CStrVector(kInvalidRange) CHECK_FAILED);
+ }
+ break;
+ }
+ continue;
+ }
if (current() == '-') {
Advance();
if (current() == kEndMarker) {
@@ -4487,25 +4452,20 @@ RegExpTree* RegExpParser::ParseCharacterClass() {
// following code report an error.
break;
} else if (current() == ']') {
- AddRangeOrEscape(ranges, char_class, first);
+ ranges->Add(first);
ranges->Add(CharacterRange::Singleton('-'));
break;
}
- uc16 char_class_2 = kNoCharClass;
- CharacterRange next = ParseClassAtom(&char_class_2 CHECK_FAILED);
- if (char_class != kNoCharClass || char_class_2 != kNoCharClass) {
- // Either end is an escaped character class. Treat the '-' verbatim.
- AddRangeOrEscape(ranges, char_class, first);
- ranges->Add(CharacterRange::Singleton('-'));
- AddRangeOrEscape(ranges, char_class_2, next);
- continue;
+ CharacterRange next = ParseClassAtom(&char_class CHECK_FAILED);
+ if (char_class) {
+ ReportError(CStrVector(kInvalidRange) CHECK_FAILED);
}
if (first.from() > next.to()) {
return ReportError(CStrVector(kRangeOutOfOrder) CHECK_FAILED);
}
ranges->Add(CharacterRange::Range(first.from(), next.to()));
} else {
- AddRangeOrEscape(ranges, char_class, first);
+ ranges->Add(first);
}
}
if (!has_more()) {
@@ -4595,12 +4555,13 @@ int ScriptDataImpl::ReadNumber(byte** source) {
// Create a Scanner for the preparser to use as input, and preparse the source.
-static ScriptDataImpl* DoPreParse(UC16CharacterStream* source,
+static ScriptDataImpl* DoPreParse(Handle<String> source,
+ unibrow::CharacterStream* stream,
bool allow_lazy,
ParserRecorder* recorder,
int literal_flags) {
V8JavaScriptScanner scanner;
- scanner.Initialize(source, literal_flags);
+ scanner.Initialize(source, stream, literal_flags);
intptr_t stack_limit = StackGuard::real_climit();
if (!preparser::PreParser::PreParseProgram(&scanner,
recorder,
@@ -4619,7 +4580,8 @@ static ScriptDataImpl* DoPreParse(UC16CharacterStream* source,
// Preparse, but only collect data that is immediately useful,
// even if the preparser data is only used once.
-ScriptDataImpl* ParserApi::PartialPreParse(UC16CharacterStream* source,
+ScriptDataImpl* ParserApi::PartialPreParse(Handle<String> source,
+ unibrow::CharacterStream* stream,
v8::Extension* extension) {
bool allow_lazy = FLAG_lazy && (extension == NULL);
if (!allow_lazy) {
@@ -4628,19 +4590,22 @@ ScriptDataImpl* ParserApi::PartialPreParse(UC16CharacterStream* source,
return NULL;
}
PartialParserRecorder recorder;
- return DoPreParse(source, allow_lazy, &recorder,
+
+ return DoPreParse(source, stream, allow_lazy, &recorder,
JavaScriptScanner::kNoLiterals);
}
-ScriptDataImpl* ParserApi::PreParse(UC16CharacterStream* source,
+ScriptDataImpl* ParserApi::PreParse(Handle<String> source,
+ unibrow::CharacterStream* stream,
v8::Extension* extension) {
Handle<Script> no_script;
bool allow_lazy = FLAG_lazy && (extension == NULL);
CompleteParserRecorder recorder;
int kPreParseLiteralsFlags =
JavaScriptScanner::kLiteralString | JavaScriptScanner::kLiteralIdentifier;
- return DoPreParse(source, allow_lazy, &recorder, kPreParseLiteralsFlags);
+ return DoPreParse(source, stream, allow_lazy,
+ &recorder, kPreParseLiteralsFlags);
}
« ChangeLog ('K') | « src/parser.h ('k') | src/platform-linux.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698