OLD | NEW |
---|---|
1 // Copyright 2010 the V8 project authors. All rights reserved. | 1 // Copyright 2010 the V8 project authors. All rights reserved. |
2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
4 // met: | 4 // met: |
5 // | 5 // |
6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
81 | 81 |
82 private: | 82 private: |
83 Element* top() { return top_; } | 83 Element* top() { return top_; } |
84 void set_top(Element* value) { top_ = value; } | 84 void set_top(Element* value) { top_ = value; } |
85 Element* top_; | 85 Element* top_; |
86 bool* ok_; | 86 bool* ok_; |
87 }; | 87 }; |
88 | 88 |
89 | 89 |
90 RegExpBuilder::RegExpBuilder() | 90 RegExpBuilder::RegExpBuilder() |
91 : pending_empty_(false), | 91 : zone_(Isolate::Current()->zone()), |
92 characters_(NULL), | 92 pending_empty_(false), |
93 terms_(), | 93 characters_(NULL), |
94 alternatives_() | 94 terms_(), |
95 alternatives_() | |
95 #ifdef DEBUG | 96 #ifdef DEBUG |
96 , last_added_(ADD_NONE) | 97 , last_added_(ADD_NONE) |
97 #endif | 98 #endif |
98 {} | 99 {} |
99 | 100 |
100 | 101 |
101 void RegExpBuilder::FlushCharacters() { | 102 void RegExpBuilder::FlushCharacters() { |
102 pending_empty_ = false; | 103 pending_empty_ = false; |
103 if (characters_ != NULL) { | 104 if (characters_ != NULL) { |
104 RegExpTree* atom = new RegExpAtom(characters_->ToConstVector()); | 105 RegExpTree* atom = new(zone()) RegExpAtom(characters_->ToConstVector()); |
Mads Ager (chromium)
2011/04/01 17:08:38
We have to decide whether we want a space between
| |
105 characters_ = NULL; | 106 characters_ = NULL; |
106 text_.Add(atom); | 107 text_.Add(atom); |
107 LAST(ADD_ATOM); | 108 LAST(ADD_ATOM); |
108 } | 109 } |
109 } | 110 } |
110 | 111 |
111 | 112 |
112 void RegExpBuilder::FlushText() { | 113 void RegExpBuilder::FlushText() { |
113 FlushCharacters(); | 114 FlushCharacters(); |
114 int num_text = text_.length(); | 115 int num_text = text_.length(); |
115 if (num_text == 0) { | 116 if (num_text == 0) { |
116 return; | 117 return; |
117 } else if (num_text == 1) { | 118 } else if (num_text == 1) { |
118 terms_.Add(text_.last()); | 119 terms_.Add(text_.last()); |
119 } else { | 120 } else { |
120 RegExpText* text = new RegExpText(); | 121 RegExpText* text = new(zone()) RegExpText(); |
121 for (int i = 0; i < num_text; i++) | 122 for (int i = 0; i < num_text; i++) |
122 text_.Get(i)->AppendToText(text); | 123 text_.Get(i)->AppendToText(text); |
123 terms_.Add(text); | 124 terms_.Add(text); |
124 } | 125 } |
125 text_.Clear(); | 126 text_.Clear(); |
126 } | 127 } |
127 | 128 |
128 | 129 |
129 void RegExpBuilder::AddCharacter(uc16 c) { | 130 void RegExpBuilder::AddCharacter(uc16 c) { |
130 pending_empty_ = false; | 131 pending_empty_ = false; |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
171 | 172 |
172 void RegExpBuilder::FlushTerms() { | 173 void RegExpBuilder::FlushTerms() { |
173 FlushText(); | 174 FlushText(); |
174 int num_terms = terms_.length(); | 175 int num_terms = terms_.length(); |
175 RegExpTree* alternative; | 176 RegExpTree* alternative; |
176 if (num_terms == 0) { | 177 if (num_terms == 0) { |
177 alternative = RegExpEmpty::GetInstance(); | 178 alternative = RegExpEmpty::GetInstance(); |
178 } else if (num_terms == 1) { | 179 } else if (num_terms == 1) { |
179 alternative = terms_.last(); | 180 alternative = terms_.last(); |
180 } else { | 181 } else { |
181 alternative = new RegExpAlternative(terms_.GetList()); | 182 alternative = new(zone()) RegExpAlternative(terms_.GetList()); |
182 } | 183 } |
183 alternatives_.Add(alternative); | 184 alternatives_.Add(alternative); |
184 terms_.Clear(); | 185 terms_.Clear(); |
185 LAST(ADD_NONE); | 186 LAST(ADD_NONE); |
186 } | 187 } |
187 | 188 |
188 | 189 |
189 RegExpTree* RegExpBuilder::ToRegExp() { | 190 RegExpTree* RegExpBuilder::ToRegExp() { |
190 FlushTerms(); | 191 FlushTerms(); |
191 int num_alternatives = alternatives_.length(); | 192 int num_alternatives = alternatives_.length(); |
192 if (num_alternatives == 0) { | 193 if (num_alternatives == 0) { |
193 return RegExpEmpty::GetInstance(); | 194 return RegExpEmpty::GetInstance(); |
194 } | 195 } |
195 if (num_alternatives == 1) { | 196 if (num_alternatives == 1) { |
196 return alternatives_.last(); | 197 return alternatives_.last(); |
197 } | 198 } |
198 return new RegExpDisjunction(alternatives_.GetList()); | 199 return new(zone()) RegExpDisjunction(alternatives_.GetList()); |
199 } | 200 } |
200 | 201 |
201 | 202 |
202 void RegExpBuilder::AddQuantifierToAtom(int min, | 203 void RegExpBuilder::AddQuantifierToAtom(int min, |
203 int max, | 204 int max, |
204 RegExpQuantifier::Type type) { | 205 RegExpQuantifier::Type type) { |
205 if (pending_empty_) { | 206 if (pending_empty_) { |
206 pending_empty_ = false; | 207 pending_empty_ = false; |
207 return; | 208 return; |
208 } | 209 } |
209 RegExpTree* atom; | 210 RegExpTree* atom; |
210 if (characters_ != NULL) { | 211 if (characters_ != NULL) { |
211 ASSERT(last_added_ == ADD_CHAR); | 212 ASSERT(last_added_ == ADD_CHAR); |
212 // Last atom was character. | 213 // Last atom was character. |
213 Vector<const uc16> char_vector = characters_->ToConstVector(); | 214 Vector<const uc16> char_vector = characters_->ToConstVector(); |
214 int num_chars = char_vector.length(); | 215 int num_chars = char_vector.length(); |
215 if (num_chars > 1) { | 216 if (num_chars > 1) { |
216 Vector<const uc16> prefix = char_vector.SubVector(0, num_chars - 1); | 217 Vector<const uc16> prefix = char_vector.SubVector(0, num_chars - 1); |
217 text_.Add(new RegExpAtom(prefix)); | 218 text_.Add(new(zone()) RegExpAtom(prefix)); |
218 char_vector = char_vector.SubVector(num_chars - 1, num_chars); | 219 char_vector = char_vector.SubVector(num_chars - 1, num_chars); |
219 } | 220 } |
220 characters_ = NULL; | 221 characters_ = NULL; |
221 atom = new RegExpAtom(char_vector); | 222 atom = new(zone()) RegExpAtom(char_vector); |
222 FlushText(); | 223 FlushText(); |
223 } else if (text_.length() > 0) { | 224 } else if (text_.length() > 0) { |
224 ASSERT(last_added_ == ADD_ATOM); | 225 ASSERT(last_added_ == ADD_ATOM); |
225 atom = text_.RemoveLast(); | 226 atom = text_.RemoveLast(); |
226 FlushText(); | 227 FlushText(); |
227 } else if (terms_.length() > 0) { | 228 } else if (terms_.length() > 0) { |
228 ASSERT(last_added_ == ADD_ATOM); | 229 ASSERT(last_added_ == ADD_ATOM); |
229 atom = terms_.RemoveLast(); | 230 atom = terms_.RemoveLast(); |
230 if (atom->max_match() == 0) { | 231 if (atom->max_match() == 0) { |
231 // Guaranteed to only match an empty string. | 232 // Guaranteed to only match an empty string. |
232 LAST(ADD_TERM); | 233 LAST(ADD_TERM); |
233 if (min == 0) { | 234 if (min == 0) { |
234 return; | 235 return; |
235 } | 236 } |
236 terms_.Add(atom); | 237 terms_.Add(atom); |
237 return; | 238 return; |
238 } | 239 } |
239 } else { | 240 } else { |
240 // Only call immediately after adding an atom or character! | 241 // Only call immediately after adding an atom or character! |
241 UNREACHABLE(); | 242 UNREACHABLE(); |
242 return; | 243 return; |
243 } | 244 } |
244 terms_.Add(new RegExpQuantifier(min, max, type, atom)); | 245 terms_.Add(new(zone()) RegExpQuantifier(min, max, type, atom)); |
245 LAST(ADD_TERM); | 246 LAST(ADD_TERM); |
246 } | 247 } |
247 | 248 |
248 | 249 |
249 Handle<String> Parser::LookupSymbol(int symbol_id) { | 250 Handle<String> Parser::LookupSymbol(int symbol_id) { |
250 // Length of symbol cache is the number of identified symbols. | 251 // Length of symbol cache is the number of identified symbols. |
251 // If we are larger than that, or negative, it's not a cached symbol. | 252 // If we are larger than that, or negative, it's not a cached symbol. |
252 // This might also happen if there is no preparser symbol data, even | 253 // This might also happen if there is no preparser symbol data, even |
253 // if there is some preparser data. | 254 // if there is some preparser data. |
254 if (static_cast<unsigned>(symbol_id) | 255 if (static_cast<unsigned>(symbol_id) |
(...skipping 146 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
401 return store_[PreparseDataConstants::kHeaderSize + position]; | 402 return store_[PreparseDataConstants::kHeaderSize + position]; |
402 } | 403 } |
403 | 404 |
404 | 405 |
405 unsigned* ScriptDataImpl::ReadAddress(int position) { | 406 unsigned* ScriptDataImpl::ReadAddress(int position) { |
406 return &store_[PreparseDataConstants::kHeaderSize + position]; | 407 return &store_[PreparseDataConstants::kHeaderSize + position]; |
407 } | 408 } |
408 | 409 |
409 | 410 |
410 Scope* Parser::NewScope(Scope* parent, Scope::Type type, bool inside_with) { | 411 Scope* Parser::NewScope(Scope* parent, Scope::Type type, bool inside_with) { |
411 Scope* result = new Scope(parent, type); | 412 Scope* result = new(zone()) Scope(parent, type); |
412 result->Initialize(inside_with); | 413 result->Initialize(inside_with); |
413 return result; | 414 return result; |
414 } | 415 } |
415 | 416 |
416 // ---------------------------------------------------------------------------- | 417 // ---------------------------------------------------------------------------- |
417 // Target is a support class to facilitate manipulation of the | 418 // Target is a support class to facilitate manipulation of the |
418 // Parser's target_stack_ (the stack of potential 'break' and | 419 // Parser's target_stack_ (the stack of potential 'break' and |
419 // 'continue' statement targets). Upon construction, a new target is | 420 // 'continue' statement targets). Upon construction, a new target is |
420 // added; it is removed upon destruction. | 421 // added; it is removed upon destruction. |
421 | 422 |
(...skipping 172 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
594 } | 595 } |
595 | 596 |
596 | 597 |
597 FunctionLiteral* Parser::ParseProgram(Handle<String> source, | 598 FunctionLiteral* Parser::ParseProgram(Handle<String> source, |
598 bool in_global_context, | 599 bool in_global_context, |
599 StrictModeFlag strict_mode) { | 600 StrictModeFlag strict_mode) { |
600 CompilationZoneScope zone_scope(DONT_DELETE_ON_EXIT); | 601 CompilationZoneScope zone_scope(DONT_DELETE_ON_EXIT); |
601 | 602 |
602 HistogramTimerScope timer(isolate()->counters()->parse()); | 603 HistogramTimerScope timer(isolate()->counters()->parse()); |
603 isolate()->counters()->total_parse_size()->Increment(source->length()); | 604 isolate()->counters()->total_parse_size()->Increment(source->length()); |
604 fni_ = new FuncNameInferrer(); | 605 fni_ = new(zone()) FuncNameInferrer(); |
605 | 606 |
606 // Initialize parser state. | 607 // Initialize parser state. |
607 source->TryFlatten(); | 608 source->TryFlatten(); |
608 if (source->IsExternalTwoByteString()) { | 609 if (source->IsExternalTwoByteString()) { |
609 // Notice that the stream is destroyed at the end of the branch block. | 610 // Notice that the stream is destroyed at the end of the branch block. |
610 // The last line of the blocks can't be moved outside, even though they're | 611 // The last line of the blocks can't be moved outside, even though they're |
611 // identical calls. | 612 // identical calls. |
612 ExternalTwoByteStringUC16CharacterStream stream( | 613 ExternalTwoByteStringUC16CharacterStream stream( |
613 Handle<ExternalTwoByteString>::cast(source), 0, source->length()); | 614 Handle<ExternalTwoByteString>::cast(source), 0, source->length()); |
614 scanner_.Initialize(&stream); | 615 scanner_.Initialize(&stream); |
(...skipping 30 matching lines...) Expand all Loading... | |
645 top_scope_->EnableStrictMode(); | 646 top_scope_->EnableStrictMode(); |
646 } | 647 } |
647 ZoneList<Statement*>* body = new ZoneList<Statement*>(16); | 648 ZoneList<Statement*>* body = new ZoneList<Statement*>(16); |
648 bool ok = true; | 649 bool ok = true; |
649 int beg_loc = scanner().location().beg_pos; | 650 int beg_loc = scanner().location().beg_pos; |
650 ParseSourceElements(body, Token::EOS, &ok); | 651 ParseSourceElements(body, Token::EOS, &ok); |
651 if (ok && top_scope_->is_strict_mode()) { | 652 if (ok && top_scope_->is_strict_mode()) { |
652 CheckOctalLiteral(beg_loc, scanner().location().end_pos, &ok); | 653 CheckOctalLiteral(beg_loc, scanner().location().end_pos, &ok); |
653 } | 654 } |
654 if (ok) { | 655 if (ok) { |
655 result = new FunctionLiteral( | 656 result = new(zone()) FunctionLiteral( |
656 no_name, | 657 no_name, |
657 top_scope_, | 658 top_scope_, |
658 body, | 659 body, |
659 lexical_scope.materialized_literal_count(), | 660 lexical_scope.materialized_literal_count(), |
660 lexical_scope.expected_property_count(), | 661 lexical_scope.expected_property_count(), |
661 lexical_scope.only_simple_this_property_assignments(), | 662 lexical_scope.only_simple_this_property_assignments(), |
662 lexical_scope.this_property_assignments(), | 663 lexical_scope.this_property_assignments(), |
663 0, | 664 0, |
664 0, | 665 0, |
665 source->length(), | 666 source->length(), |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
706 | 707 |
707 | 708 |
708 FunctionLiteral* Parser::ParseLazy(CompilationInfo* info, | 709 FunctionLiteral* Parser::ParseLazy(CompilationInfo* info, |
709 UC16CharacterStream* source, | 710 UC16CharacterStream* source, |
710 ZoneScope* zone_scope) { | 711 ZoneScope* zone_scope) { |
711 Handle<SharedFunctionInfo> shared_info = info->shared_info(); | 712 Handle<SharedFunctionInfo> shared_info = info->shared_info(); |
712 scanner_.Initialize(source); | 713 scanner_.Initialize(source); |
713 ASSERT(target_stack_ == NULL); | 714 ASSERT(target_stack_ == NULL); |
714 | 715 |
715 Handle<String> name(String::cast(shared_info->name())); | 716 Handle<String> name(String::cast(shared_info->name())); |
716 fni_ = new FuncNameInferrer(); | 717 fni_ = new(zone()) FuncNameInferrer(); |
717 fni_->PushEnclosingName(name); | 718 fni_->PushEnclosingName(name); |
718 | 719 |
719 mode_ = PARSE_EAGERLY; | 720 mode_ = PARSE_EAGERLY; |
720 | 721 |
721 // Place holder for the result. | 722 // Place holder for the result. |
722 FunctionLiteral* result = NULL; | 723 FunctionLiteral* result = NULL; |
723 | 724 |
724 { | 725 { |
725 // Parse the function literal. | 726 // Parse the function literal. |
726 Handle<String> no_name = isolate()->factory()->empty_symbol(); | 727 Handle<String> no_name = isolate()->factory()->empty_symbol(); |
(...skipping 518 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1245 case Token::THROW: | 1246 case Token::THROW: |
1246 stmt = ParseThrowStatement(ok); | 1247 stmt = ParseThrowStatement(ok); |
1247 break; | 1248 break; |
1248 | 1249 |
1249 case Token::TRY: { | 1250 case Token::TRY: { |
1250 // NOTE: It is somewhat complicated to have labels on | 1251 // NOTE: It is somewhat complicated to have labels on |
1251 // try-statements. When breaking out of a try-finally statement, | 1252 // try-statements. When breaking out of a try-finally statement, |
1252 // one must take great care not to treat it as a | 1253 // one must take great care not to treat it as a |
1253 // fall-through. It is much easier just to wrap the entire | 1254 // fall-through. It is much easier just to wrap the entire |
1254 // try-statement in a statement block and put the labels there | 1255 // try-statement in a statement block and put the labels there |
1255 Block* result = new Block(labels, 1, false); | 1256 Block* result = new(zone()) Block(labels, 1, false); |
1256 Target target(&this->target_stack_, result); | 1257 Target target(&this->target_stack_, result); |
1257 TryStatement* statement = ParseTryStatement(CHECK_OK); | 1258 TryStatement* statement = ParseTryStatement(CHECK_OK); |
1258 if (statement) { | 1259 if (statement) { |
1259 statement->set_statement_pos(statement_pos); | 1260 statement->set_statement_pos(statement_pos); |
1260 } | 1261 } |
1261 if (result) result->AddStatement(statement); | 1262 if (result) result->AddStatement(statement); |
1262 return result; | 1263 return result; |
1263 } | 1264 } |
1264 | 1265 |
1265 case Token::FUNCTION: { | 1266 case Token::FUNCTION: { |
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1343 // parameters) if the proxy is needed or not. The proxy will be | 1344 // parameters) if the proxy is needed or not. The proxy will be |
1344 // bound during variable resolution time unless it was pre-bound | 1345 // bound during variable resolution time unless it was pre-bound |
1345 // below. | 1346 // below. |
1346 // | 1347 // |
1347 // WARNING: This will lead to multiple declaration nodes for the | 1348 // WARNING: This will lead to multiple declaration nodes for the |
1348 // same variable if it is declared several times. This is not a | 1349 // same variable if it is declared several times. This is not a |
1349 // semantic issue as long as we keep the source order, but it may be | 1350 // semantic issue as long as we keep the source order, but it may be |
1350 // a performance issue since it may lead to repeated | 1351 // a performance issue since it may lead to repeated |
1351 // Runtime::DeclareContextSlot() calls. | 1352 // Runtime::DeclareContextSlot() calls. |
1352 VariableProxy* proxy = top_scope_->NewUnresolved(name, inside_with()); | 1353 VariableProxy* proxy = top_scope_->NewUnresolved(name, inside_with()); |
1353 top_scope_->AddDeclaration(new Declaration(proxy, mode, fun)); | 1354 top_scope_->AddDeclaration(new(zone()) Declaration(proxy, mode, fun)); |
1354 | 1355 |
1355 // For global const variables we bind the proxy to a variable. | 1356 // For global const variables we bind the proxy to a variable. |
1356 if (mode == Variable::CONST && top_scope_->is_global_scope()) { | 1357 if (mode == Variable::CONST && top_scope_->is_global_scope()) { |
1357 ASSERT(resolve); // should be set by all callers | 1358 ASSERT(resolve); // should be set by all callers |
1358 Variable::Kind kind = Variable::NORMAL; | 1359 Variable::Kind kind = Variable::NORMAL; |
1359 var = new Variable(top_scope_, name, Variable::CONST, true, kind); | 1360 var = new(zone()) Variable(top_scope_, name, Variable::CONST, true, kind); |
1360 } | 1361 } |
1361 | 1362 |
1362 // If requested and we have a local variable, bind the proxy to the variable | 1363 // If requested and we have a local variable, bind the proxy to the variable |
1363 // at parse-time. This is used for functions (and consts) declared inside | 1364 // at parse-time. This is used for functions (and consts) declared inside |
1364 // statements: the corresponding function (or const) variable must be in the | 1365 // statements: the corresponding function (or const) variable must be in the |
1365 // function scope and not a statement-local scope, e.g. as provided with a | 1366 // function scope and not a statement-local scope, e.g. as provided with a |
1366 // 'with' statement: | 1367 // 'with' statement: |
1367 // | 1368 // |
1368 // with (obj) { | 1369 // with (obj) { |
1369 // function f() {} | 1370 // function f() {} |
(...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1437 shared->set_construct_stub(*construct_stub); | 1438 shared->set_construct_stub(*construct_stub); |
1438 | 1439 |
1439 // Copy the function data to the shared function info. | 1440 // Copy the function data to the shared function info. |
1440 shared->set_function_data(fun->shared()->function_data()); | 1441 shared->set_function_data(fun->shared()->function_data()); |
1441 int parameters = fun->shared()->formal_parameter_count(); | 1442 int parameters = fun->shared()->formal_parameter_count(); |
1442 shared->set_formal_parameter_count(parameters); | 1443 shared->set_formal_parameter_count(parameters); |
1443 | 1444 |
1444 // TODO(1240846): It's weird that native function declarations are | 1445 // TODO(1240846): It's weird that native function declarations are |
1445 // introduced dynamically when we meet their declarations, whereas | 1446 // introduced dynamically when we meet their declarations, whereas |
1446 // other functions are setup when entering the surrounding scope. | 1447 // other functions are setup when entering the surrounding scope. |
1447 SharedFunctionInfoLiteral* lit = new SharedFunctionInfoLiteral(shared); | 1448 SharedFunctionInfoLiteral* lit = |
1449 new(zone()) SharedFunctionInfoLiteral(shared); | |
1448 VariableProxy* var = Declare(name, Variable::VAR, NULL, true, CHECK_OK); | 1450 VariableProxy* var = Declare(name, Variable::VAR, NULL, true, CHECK_OK); |
1449 return new ExpressionStatement( | 1451 return new(zone()) ExpressionStatement(new(zone()) Assignment( |
1450 new Assignment(Token::INIT_VAR, var, lit, RelocInfo::kNoPosition)); | 1452 Token::INIT_VAR, var, lit, RelocInfo::kNoPosition)); |
1451 } | 1453 } |
1452 | 1454 |
1453 | 1455 |
1454 Statement* Parser::ParseFunctionDeclaration(bool* ok) { | 1456 Statement* Parser::ParseFunctionDeclaration(bool* ok) { |
1455 // FunctionDeclaration :: | 1457 // FunctionDeclaration :: |
1456 // 'function' Identifier '(' FormalParameterListopt ')' '{' FunctionBody '}' | 1458 // 'function' Identifier '(' FormalParameterListopt ')' '{' FunctionBody '}' |
1457 Expect(Token::FUNCTION, CHECK_OK); | 1459 Expect(Token::FUNCTION, CHECK_OK); |
1458 int function_token_position = scanner().location().beg_pos; | 1460 int function_token_position = scanner().location().beg_pos; |
1459 bool is_reserved = false; | 1461 bool is_reserved = false; |
1460 Handle<String> name = ParseIdentifierOrReservedWord(&is_reserved, CHECK_OK); | 1462 Handle<String> name = ParseIdentifierOrReservedWord(&is_reserved, CHECK_OK); |
(...skipping 11 matching lines...) Expand all Loading... | |
1472 | 1474 |
1473 | 1475 |
1474 Block* Parser::ParseBlock(ZoneStringList* labels, bool* ok) { | 1476 Block* Parser::ParseBlock(ZoneStringList* labels, bool* ok) { |
1475 // Block :: | 1477 // Block :: |
1476 // '{' Statement* '}' | 1478 // '{' Statement* '}' |
1477 | 1479 |
1478 // Note that a Block does not introduce a new execution scope! | 1480 // Note that a Block does not introduce a new execution scope! |
1479 // (ECMA-262, 3rd, 12.2) | 1481 // (ECMA-262, 3rd, 12.2) |
1480 // | 1482 // |
1481 // Construct block expecting 16 statements. | 1483 // Construct block expecting 16 statements. |
1482 Block* result = new Block(labels, 16, false); | 1484 Block* result = new(zone()) Block(labels, 16, false); |
1483 Target target(&this->target_stack_, result); | 1485 Target target(&this->target_stack_, result); |
1484 Expect(Token::LBRACE, CHECK_OK); | 1486 Expect(Token::LBRACE, CHECK_OK); |
1485 while (peek() != Token::RBRACE) { | 1487 while (peek() != Token::RBRACE) { |
1486 Statement* stat = ParseStatement(NULL, CHECK_OK); | 1488 Statement* stat = ParseStatement(NULL, CHECK_OK); |
1487 if (stat && !stat->IsEmpty()) result->AddStatement(stat); | 1489 if (stat && !stat->IsEmpty()) result->AddStatement(stat); |
1488 } | 1490 } |
1489 Expect(Token::RBRACE, CHECK_OK); | 1491 Expect(Token::RBRACE, CHECK_OK); |
1490 return result; | 1492 return result; |
1491 } | 1493 } |
1492 | 1494 |
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1542 // Scope declaration, and rewrite the source-level initialization into an | 1544 // Scope declaration, and rewrite the source-level initialization into an |
1543 // assignment statement. We use a block to collect multiple assignments. | 1545 // assignment statement. We use a block to collect multiple assignments. |
1544 // | 1546 // |
1545 // We mark the block as initializer block because we don't want the | 1547 // We mark the block as initializer block because we don't want the |
1546 // rewriter to add a '.result' assignment to such a block (to get compliant | 1548 // rewriter to add a '.result' assignment to such a block (to get compliant |
1547 // behavior for code such as print(eval('var x = 7')), and for cosmetic | 1549 // behavior for code such as print(eval('var x = 7')), and for cosmetic |
1548 // reasons when pretty-printing. Also, unless an assignment (initialization) | 1550 // reasons when pretty-printing. Also, unless an assignment (initialization) |
1549 // is inside an initializer block, it is ignored. | 1551 // is inside an initializer block, it is ignored. |
1550 // | 1552 // |
1551 // Create new block with one expected declaration. | 1553 // Create new block with one expected declaration. |
1552 Block* block = new Block(NULL, 1, true); | 1554 Block* block = new(zone()) Block(NULL, 1, true); |
1553 VariableProxy* last_var = NULL; // the last variable declared | 1555 VariableProxy* last_var = NULL; // the last variable declared |
1554 int nvars = 0; // the number of variables declared | 1556 int nvars = 0; // the number of variables declared |
1555 do { | 1557 do { |
1556 if (fni_ != NULL) fni_->Enter(); | 1558 if (fni_ != NULL) fni_->Enter(); |
1557 | 1559 |
1558 // Parse variable name. | 1560 // Parse variable name. |
1559 if (nvars > 0) Consume(Token::COMMA); | 1561 if (nvars > 0) Consume(Token::COMMA); |
1560 Handle<String> name = ParseIdentifier(CHECK_OK); | 1562 Handle<String> name = ParseIdentifier(CHECK_OK); |
1561 if (fni_ != NULL) fni_->PushVariableName(name); | 1563 if (fni_ != NULL) fni_->PushVariableName(name); |
1562 | 1564 |
(...skipping 80 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1643 // variable defined in the global object and not in any | 1645 // variable defined in the global object and not in any |
1644 // prototype. This way, global variable declarations can shadow | 1646 // prototype. This way, global variable declarations can shadow |
1645 // properties in the prototype chain, but only after the variable | 1647 // properties in the prototype chain, but only after the variable |
1646 // declaration statement has been executed. This is important in | 1648 // declaration statement has been executed. This is important in |
1647 // browsers where the global object (window) has lots of | 1649 // browsers where the global object (window) has lots of |
1648 // properties defined in prototype objects. | 1650 // properties defined in prototype objects. |
1649 | 1651 |
1650 if (top_scope_->is_global_scope()) { | 1652 if (top_scope_->is_global_scope()) { |
1651 // Compute the arguments for the runtime call. | 1653 // Compute the arguments for the runtime call. |
1652 ZoneList<Expression*>* arguments = new ZoneList<Expression*>(3); | 1654 ZoneList<Expression*>* arguments = new ZoneList<Expression*>(3); |
1653 arguments->Add(new Literal(name)); // we have at least 1 parameter | 1655 // We have at least 1 parameter. |
1656 arguments->Add(new(zone()) Literal(name)); | |
1654 CallRuntime* initialize; | 1657 CallRuntime* initialize; |
1655 | 1658 |
1656 if (is_const) { | 1659 if (is_const) { |
1657 arguments->Add(value); | 1660 arguments->Add(value); |
1658 value = NULL; // zap the value to avoid the unnecessary assignment | 1661 value = NULL; // zap the value to avoid the unnecessary assignment |
1659 | 1662 |
1660 // Construct the call to Runtime_InitializeConstGlobal | 1663 // Construct the call to Runtime_InitializeConstGlobal |
1661 // and add it to the initialization statement block. | 1664 // and add it to the initialization statement block. |
1662 // Note that the function does different things depending on | 1665 // Note that the function does different things depending on |
1663 // the number of arguments (1 or 2). | 1666 // the number of arguments (1 or 2). |
1664 initialize = | 1667 initialize = |
1665 new CallRuntime( | 1668 new(zone()) CallRuntime( |
1666 isolate()->factory()->InitializeConstGlobal_symbol(), | 1669 isolate()->factory()->InitializeConstGlobal_symbol(), |
1667 Runtime::FunctionForId(Runtime::kInitializeConstGlobal), | 1670 Runtime::FunctionForId(Runtime::kInitializeConstGlobal), |
1668 arguments); | 1671 arguments); |
1669 } else { | 1672 } else { |
1670 // Add strict mode. | 1673 // Add strict mode. |
1671 // We may want to pass singleton to avoid Literal allocations. | 1674 // We may want to pass singleton to avoid Literal allocations. |
1672 arguments->Add(NewNumberLiteral( | 1675 arguments->Add(NewNumberLiteral( |
1673 top_scope_->is_strict_mode() ? kStrictMode : kNonStrictMode)); | 1676 top_scope_->is_strict_mode() ? kStrictMode : kNonStrictMode)); |
1674 | 1677 |
1675 // Be careful not to assign a value to the global variable if | 1678 // Be careful not to assign a value to the global variable if |
1676 // we're in a with. The initialization value should not | 1679 // we're in a with. The initialization value should not |
1677 // necessarily be stored in the global object in that case, | 1680 // necessarily be stored in the global object in that case, |
1678 // which is why we need to generate a separate assignment node. | 1681 // which is why we need to generate a separate assignment node. |
1679 if (value != NULL && !inside_with()) { | 1682 if (value != NULL && !inside_with()) { |
1680 arguments->Add(value); | 1683 arguments->Add(value); |
1681 value = NULL; // zap the value to avoid the unnecessary assignment | 1684 value = NULL; // zap the value to avoid the unnecessary assignment |
1682 } | 1685 } |
1683 | 1686 |
1684 // Construct the call to Runtime_InitializeVarGlobal | 1687 // Construct the call to Runtime_InitializeVarGlobal |
1685 // and add it to the initialization statement block. | 1688 // and add it to the initialization statement block. |
1686 // Note that the function does different things depending on | 1689 // Note that the function does different things depending on |
1687 // the number of arguments (2 or 3). | 1690 // the number of arguments (2 or 3). |
1688 initialize = | 1691 initialize = |
1689 new CallRuntime( | 1692 new(zone()) CallRuntime( |
1690 isolate()->factory()->InitializeVarGlobal_symbol(), | 1693 isolate()->factory()->InitializeVarGlobal_symbol(), |
1691 Runtime::FunctionForId(Runtime::kInitializeVarGlobal), | 1694 Runtime::FunctionForId(Runtime::kInitializeVarGlobal), |
1692 arguments); | 1695 arguments); |
1693 } | 1696 } |
1694 | 1697 |
1695 block->AddStatement(new ExpressionStatement(initialize)); | 1698 block->AddStatement(new(zone()) ExpressionStatement(initialize)); |
1696 } | 1699 } |
1697 | 1700 |
1698 // Add an assignment node to the initialization statement block if | 1701 // Add an assignment node to the initialization statement block if |
1699 // we still have a pending initialization value. We must distinguish | 1702 // we still have a pending initialization value. We must distinguish |
1700 // between variables and constants: Variable initializations are simply | 1703 // between variables and constants: Variable initializations are simply |
1701 // assignments (with all the consequences if they are inside a 'with' | 1704 // assignments (with all the consequences if they are inside a 'with' |
1702 // statement - they may change a 'with' object property). Constant | 1705 // statement - they may change a 'with' object property). Constant |
1703 // initializations always assign to the declared constant which is | 1706 // initializations always assign to the declared constant which is |
1704 // always at the function scope level. This is only relevant for | 1707 // always at the function scope level. This is only relevant for |
1705 // dynamically looked-up variables and constants (the start context | 1708 // dynamically looked-up variables and constants (the start context |
1706 // for constant lookups is always the function context, while it is | 1709 // for constant lookups is always the function context, while it is |
1707 // the top context for variables). Sigh... | 1710 // the top context for variables). Sigh... |
1708 if (value != NULL) { | 1711 if (value != NULL) { |
1709 Token::Value op = (is_const ? Token::INIT_CONST : Token::INIT_VAR); | 1712 Token::Value op = (is_const ? Token::INIT_CONST : Token::INIT_VAR); |
1710 Assignment* assignment = new Assignment(op, last_var, value, position); | 1713 Assignment* assignment = |
1711 if (block) block->AddStatement(new ExpressionStatement(assignment)); | 1714 new(zone()) Assignment(op, last_var, value, position); |
1715 if (block) { | |
1716 block->AddStatement(new(zone()) ExpressionStatement(assignment)); | |
1717 } | |
1712 } | 1718 } |
1713 | 1719 |
1714 if (fni_ != NULL) fni_->Leave(); | 1720 if (fni_ != NULL) fni_->Leave(); |
1715 } while (peek() == Token::COMMA); | 1721 } while (peek() == Token::COMMA); |
1716 | 1722 |
1717 if (!is_const && nvars == 1) { | 1723 if (!is_const && nvars == 1) { |
1718 // We have a single, non-const variable. | 1724 // We have a single, non-const variable. |
1719 ASSERT(last_var != NULL); | 1725 ASSERT(last_var != NULL); |
1720 *var = last_var; | 1726 *var = last_var; |
1721 } | 1727 } |
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1767 // Remove the "ghost" variable that turned out to be a label | 1773 // Remove the "ghost" variable that turned out to be a label |
1768 // from the top scope. This way, we don't try to resolve it | 1774 // from the top scope. This way, we don't try to resolve it |
1769 // during the scope processing. | 1775 // during the scope processing. |
1770 top_scope_->RemoveUnresolved(var); | 1776 top_scope_->RemoveUnresolved(var); |
1771 Expect(Token::COLON, CHECK_OK); | 1777 Expect(Token::COLON, CHECK_OK); |
1772 return ParseStatement(labels, ok); | 1778 return ParseStatement(labels, ok); |
1773 } | 1779 } |
1774 | 1780 |
1775 // Parsed expression statement. | 1781 // Parsed expression statement. |
1776 ExpectSemicolon(CHECK_OK); | 1782 ExpectSemicolon(CHECK_OK); |
1777 return new ExpressionStatement(expr); | 1783 return new(zone()) ExpressionStatement(expr); |
1778 } | 1784 } |
1779 | 1785 |
1780 | 1786 |
1781 IfStatement* Parser::ParseIfStatement(ZoneStringList* labels, bool* ok) { | 1787 IfStatement* Parser::ParseIfStatement(ZoneStringList* labels, bool* ok) { |
1782 // IfStatement :: | 1788 // IfStatement :: |
1783 // 'if' '(' Expression ')' Statement ('else' Statement)? | 1789 // 'if' '(' Expression ')' Statement ('else' Statement)? |
1784 | 1790 |
1785 Expect(Token::IF, CHECK_OK); | 1791 Expect(Token::IF, CHECK_OK); |
1786 Expect(Token::LPAREN, CHECK_OK); | 1792 Expect(Token::LPAREN, CHECK_OK); |
1787 Expression* condition = ParseExpression(true, CHECK_OK); | 1793 Expression* condition = ParseExpression(true, CHECK_OK); |
1788 Expect(Token::RPAREN, CHECK_OK); | 1794 Expect(Token::RPAREN, CHECK_OK); |
1789 Statement* then_statement = ParseStatement(labels, CHECK_OK); | 1795 Statement* then_statement = ParseStatement(labels, CHECK_OK); |
1790 Statement* else_statement = NULL; | 1796 Statement* else_statement = NULL; |
1791 if (peek() == Token::ELSE) { | 1797 if (peek() == Token::ELSE) { |
1792 Next(); | 1798 Next(); |
1793 else_statement = ParseStatement(labels, CHECK_OK); | 1799 else_statement = ParseStatement(labels, CHECK_OK); |
1794 } else { | 1800 } else { |
1795 else_statement = EmptyStatement(); | 1801 else_statement = EmptyStatement(); |
1796 } | 1802 } |
1797 return new IfStatement(condition, then_statement, else_statement); | 1803 return new(zone()) IfStatement(condition, then_statement, else_statement); |
1798 } | 1804 } |
1799 | 1805 |
1800 | 1806 |
1801 Statement* Parser::ParseContinueStatement(bool* ok) { | 1807 Statement* Parser::ParseContinueStatement(bool* ok) { |
1802 // ContinueStatement :: | 1808 // ContinueStatement :: |
1803 // 'continue' Identifier? ';' | 1809 // 'continue' Identifier? ';' |
1804 | 1810 |
1805 Expect(Token::CONTINUE, CHECK_OK); | 1811 Expect(Token::CONTINUE, CHECK_OK); |
1806 Handle<String> label = Handle<String>::null(); | 1812 Handle<String> label = Handle<String>::null(); |
1807 Token::Value tok = peek(); | 1813 Token::Value tok = peek(); |
1808 if (!scanner().has_line_terminator_before_next() && | 1814 if (!scanner().has_line_terminator_before_next() && |
1809 tok != Token::SEMICOLON && tok != Token::RBRACE && tok != Token::EOS) { | 1815 tok != Token::SEMICOLON && tok != Token::RBRACE && tok != Token::EOS) { |
1810 label = ParseIdentifier(CHECK_OK); | 1816 label = ParseIdentifier(CHECK_OK); |
1811 } | 1817 } |
1812 IterationStatement* target = NULL; | 1818 IterationStatement* target = NULL; |
1813 target = LookupContinueTarget(label, CHECK_OK); | 1819 target = LookupContinueTarget(label, CHECK_OK); |
1814 if (target == NULL) { | 1820 if (target == NULL) { |
1815 // Illegal continue statement. | 1821 // Illegal continue statement. |
1816 const char* message = "illegal_continue"; | 1822 const char* message = "illegal_continue"; |
1817 Vector<Handle<String> > args; | 1823 Vector<Handle<String> > args; |
1818 if (!label.is_null()) { | 1824 if (!label.is_null()) { |
1819 message = "unknown_label"; | 1825 message = "unknown_label"; |
1820 args = Vector<Handle<String> >(&label, 1); | 1826 args = Vector<Handle<String> >(&label, 1); |
1821 } | 1827 } |
1822 ReportMessageAt(scanner().location(), message, args); | 1828 ReportMessageAt(scanner().location(), message, args); |
1823 *ok = false; | 1829 *ok = false; |
1824 return NULL; | 1830 return NULL; |
1825 } | 1831 } |
1826 ExpectSemicolon(CHECK_OK); | 1832 ExpectSemicolon(CHECK_OK); |
1827 return new ContinueStatement(target); | 1833 return new(zone()) ContinueStatement(target); |
1828 } | 1834 } |
1829 | 1835 |
1830 | 1836 |
1831 Statement* Parser::ParseBreakStatement(ZoneStringList* labels, bool* ok) { | 1837 Statement* Parser::ParseBreakStatement(ZoneStringList* labels, bool* ok) { |
1832 // BreakStatement :: | 1838 // BreakStatement :: |
1833 // 'break' Identifier? ';' | 1839 // 'break' Identifier? ';' |
1834 | 1840 |
1835 Expect(Token::BREAK, CHECK_OK); | 1841 Expect(Token::BREAK, CHECK_OK); |
1836 Handle<String> label; | 1842 Handle<String> label; |
1837 Token::Value tok = peek(); | 1843 Token::Value tok = peek(); |
(...skipping 14 matching lines...) Expand all Loading... | |
1852 Vector<Handle<String> > args; | 1858 Vector<Handle<String> > args; |
1853 if (!label.is_null()) { | 1859 if (!label.is_null()) { |
1854 message = "unknown_label"; | 1860 message = "unknown_label"; |
1855 args = Vector<Handle<String> >(&label, 1); | 1861 args = Vector<Handle<String> >(&label, 1); |
1856 } | 1862 } |
1857 ReportMessageAt(scanner().location(), message, args); | 1863 ReportMessageAt(scanner().location(), message, args); |
1858 *ok = false; | 1864 *ok = false; |
1859 return NULL; | 1865 return NULL; |
1860 } | 1866 } |
1861 ExpectSemicolon(CHECK_OK); | 1867 ExpectSemicolon(CHECK_OK); |
1862 return new BreakStatement(target); | 1868 return new(zone()) BreakStatement(target); |
1863 } | 1869 } |
1864 | 1870 |
1865 | 1871 |
1866 Statement* Parser::ParseReturnStatement(bool* ok) { | 1872 Statement* Parser::ParseReturnStatement(bool* ok) { |
1867 // ReturnStatement :: | 1873 // ReturnStatement :: |
1868 // 'return' Expression? ';' | 1874 // 'return' Expression? ';' |
1869 | 1875 |
1870 // Consume the return token. It is necessary to do the before | 1876 // Consume the return token. It is necessary to do the before |
1871 // reporting any errors on it, because of the way errors are | 1877 // reporting any errors on it, because of the way errors are |
1872 // reported (underlining). | 1878 // reported (underlining). |
1873 Expect(Token::RETURN, CHECK_OK); | 1879 Expect(Token::RETURN, CHECK_OK); |
1874 | 1880 |
1875 // An ECMAScript program is considered syntactically incorrect if it | 1881 // An ECMAScript program is considered syntactically incorrect if it |
1876 // contains a return statement that is not within the body of a | 1882 // contains a return statement that is not within the body of a |
1877 // function. See ECMA-262, section 12.9, page 67. | 1883 // function. See ECMA-262, section 12.9, page 67. |
1878 // | 1884 // |
1879 // To be consistent with KJS we report the syntax error at runtime. | 1885 // To be consistent with KJS we report the syntax error at runtime. |
1880 if (!top_scope_->is_function_scope()) { | 1886 if (!top_scope_->is_function_scope()) { |
1881 Handle<String> type = isolate()->factory()->illegal_return_symbol(); | 1887 Handle<String> type = isolate()->factory()->illegal_return_symbol(); |
1882 Expression* throw_error = NewThrowSyntaxError(type, Handle<Object>::null()); | 1888 Expression* throw_error = NewThrowSyntaxError(type, Handle<Object>::null()); |
1883 return new ExpressionStatement(throw_error); | 1889 return new(zone()) ExpressionStatement(throw_error); |
1884 } | 1890 } |
1885 | 1891 |
1886 Token::Value tok = peek(); | 1892 Token::Value tok = peek(); |
1887 if (scanner().has_line_terminator_before_next() || | 1893 if (scanner().has_line_terminator_before_next() || |
1888 tok == Token::SEMICOLON || | 1894 tok == Token::SEMICOLON || |
1889 tok == Token::RBRACE || | 1895 tok == Token::RBRACE || |
1890 tok == Token::EOS) { | 1896 tok == Token::EOS) { |
1891 ExpectSemicolon(CHECK_OK); | 1897 ExpectSemicolon(CHECK_OK); |
1892 return new ReturnStatement(GetLiteralUndefined()); | 1898 return new(zone()) ReturnStatement(GetLiteralUndefined()); |
1893 } | 1899 } |
1894 | 1900 |
1895 Expression* expr = ParseExpression(true, CHECK_OK); | 1901 Expression* expr = ParseExpression(true, CHECK_OK); |
1896 ExpectSemicolon(CHECK_OK); | 1902 ExpectSemicolon(CHECK_OK); |
1897 return new ReturnStatement(expr); | 1903 return new(zone()) ReturnStatement(expr); |
1898 } | 1904 } |
1899 | 1905 |
1900 | 1906 |
1901 Block* Parser::WithHelper(Expression* obj, | 1907 Block* Parser::WithHelper(Expression* obj, |
1902 ZoneStringList* labels, | 1908 ZoneStringList* labels, |
1903 bool is_catch_block, | 1909 bool is_catch_block, |
1904 bool* ok) { | 1910 bool* ok) { |
1905 // Parse the statement and collect escaping labels. | 1911 // Parse the statement and collect escaping labels. |
1906 ZoneList<BreakTarget*>* target_list = new ZoneList<BreakTarget*>(0); | 1912 ZoneList<BreakTarget*>* target_list = new ZoneList<BreakTarget*>(0); |
1907 TargetCollector collector(target_list); | 1913 TargetCollector collector(target_list); |
1908 Statement* stat; | 1914 Statement* stat; |
1909 { Target target(&this->target_stack_, &collector); | 1915 { Target target(&this->target_stack_, &collector); |
1910 with_nesting_level_++; | 1916 with_nesting_level_++; |
1911 top_scope_->RecordWithStatement(); | 1917 top_scope_->RecordWithStatement(); |
1912 stat = ParseStatement(labels, CHECK_OK); | 1918 stat = ParseStatement(labels, CHECK_OK); |
1913 with_nesting_level_--; | 1919 with_nesting_level_--; |
1914 } | 1920 } |
1915 // Create resulting block with two statements. | 1921 // Create resulting block with two statements. |
1916 // 1: Evaluate the with expression. | 1922 // 1: Evaluate the with expression. |
1917 // 2: The try-finally block evaluating the body. | 1923 // 2: The try-finally block evaluating the body. |
1918 Block* result = new Block(NULL, 2, false); | 1924 Block* result = new(zone()) Block(NULL, 2, false); |
1919 | 1925 |
1920 if (result != NULL) { | 1926 if (result != NULL) { |
1921 result->AddStatement(new WithEnterStatement(obj, is_catch_block)); | 1927 result->AddStatement(new(zone()) WithEnterStatement(obj, is_catch_block)); |
1922 | 1928 |
1923 // Create body block. | 1929 // Create body block. |
1924 Block* body = new Block(NULL, 1, false); | 1930 Block* body = new(zone()) Block(NULL, 1, false); |
1925 body->AddStatement(stat); | 1931 body->AddStatement(stat); |
1926 | 1932 |
1927 // Create exit block. | 1933 // Create exit block. |
1928 Block* exit = new Block(NULL, 1, false); | 1934 Block* exit = new(zone()) Block(NULL, 1, false); |
1929 exit->AddStatement(new WithExitStatement()); | 1935 exit->AddStatement(new(zone()) WithExitStatement()); |
1930 | 1936 |
1931 // Return a try-finally statement. | 1937 // Return a try-finally statement. |
1932 TryFinallyStatement* wrapper = new TryFinallyStatement(body, exit); | 1938 TryFinallyStatement* wrapper = new(zone()) TryFinallyStatement(body, exit); |
1933 wrapper->set_escaping_targets(collector.targets()); | 1939 wrapper->set_escaping_targets(collector.targets()); |
1934 result->AddStatement(wrapper); | 1940 result->AddStatement(wrapper); |
1935 } | 1941 } |
1936 return result; | 1942 return result; |
1937 } | 1943 } |
1938 | 1944 |
1939 | 1945 |
1940 Statement* Parser::ParseWithStatement(ZoneStringList* labels, bool* ok) { | 1946 Statement* Parser::ParseWithStatement(ZoneStringList* labels, bool* ok) { |
1941 // WithStatement :: | 1947 // WithStatement :: |
1942 // 'with' '(' Expression ')' Statement | 1948 // 'with' '(' Expression ')' Statement |
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1979 Expect(Token::COLON, CHECK_OK); | 1985 Expect(Token::COLON, CHECK_OK); |
1980 int pos = scanner().location().beg_pos; | 1986 int pos = scanner().location().beg_pos; |
1981 ZoneList<Statement*>* statements = new ZoneList<Statement*>(5); | 1987 ZoneList<Statement*>* statements = new ZoneList<Statement*>(5); |
1982 while (peek() != Token::CASE && | 1988 while (peek() != Token::CASE && |
1983 peek() != Token::DEFAULT && | 1989 peek() != Token::DEFAULT && |
1984 peek() != Token::RBRACE) { | 1990 peek() != Token::RBRACE) { |
1985 Statement* stat = ParseStatement(NULL, CHECK_OK); | 1991 Statement* stat = ParseStatement(NULL, CHECK_OK); |
1986 statements->Add(stat); | 1992 statements->Add(stat); |
1987 } | 1993 } |
1988 | 1994 |
1989 return new CaseClause(label, statements, pos); | 1995 return new(zone()) CaseClause(label, statements, pos); |
1990 } | 1996 } |
1991 | 1997 |
1992 | 1998 |
1993 SwitchStatement* Parser::ParseSwitchStatement(ZoneStringList* labels, | 1999 SwitchStatement* Parser::ParseSwitchStatement(ZoneStringList* labels, |
1994 bool* ok) { | 2000 bool* ok) { |
1995 // SwitchStatement :: | 2001 // SwitchStatement :: |
1996 // 'switch' '(' Expression ')' '{' CaseClause* '}' | 2002 // 'switch' '(' Expression ')' '{' CaseClause* '}' |
1997 | 2003 |
1998 SwitchStatement* statement = new SwitchStatement(labels); | 2004 SwitchStatement* statement = new(zone()) SwitchStatement(labels); |
1999 Target target(&this->target_stack_, statement); | 2005 Target target(&this->target_stack_, statement); |
2000 | 2006 |
2001 Expect(Token::SWITCH, CHECK_OK); | 2007 Expect(Token::SWITCH, CHECK_OK); |
2002 Expect(Token::LPAREN, CHECK_OK); | 2008 Expect(Token::LPAREN, CHECK_OK); |
2003 Expression* tag = ParseExpression(true, CHECK_OK); | 2009 Expression* tag = ParseExpression(true, CHECK_OK); |
2004 Expect(Token::RPAREN, CHECK_OK); | 2010 Expect(Token::RPAREN, CHECK_OK); |
2005 | 2011 |
2006 bool default_seen = false; | 2012 bool default_seen = false; |
2007 ZoneList<CaseClause*>* cases = new ZoneList<CaseClause*>(4); | 2013 ZoneList<CaseClause*>* cases = new ZoneList<CaseClause*>(4); |
2008 Expect(Token::LBRACE, CHECK_OK); | 2014 Expect(Token::LBRACE, CHECK_OK); |
(...skipping 15 matching lines...) Expand all Loading... | |
2024 Expect(Token::THROW, CHECK_OK); | 2030 Expect(Token::THROW, CHECK_OK); |
2025 int pos = scanner().location().beg_pos; | 2031 int pos = scanner().location().beg_pos; |
2026 if (scanner().has_line_terminator_before_next()) { | 2032 if (scanner().has_line_terminator_before_next()) { |
2027 ReportMessage("newline_after_throw", Vector<const char*>::empty()); | 2033 ReportMessage("newline_after_throw", Vector<const char*>::empty()); |
2028 *ok = false; | 2034 *ok = false; |
2029 return NULL; | 2035 return NULL; |
2030 } | 2036 } |
2031 Expression* exception = ParseExpression(true, CHECK_OK); | 2037 Expression* exception = ParseExpression(true, CHECK_OK); |
2032 ExpectSemicolon(CHECK_OK); | 2038 ExpectSemicolon(CHECK_OK); |
2033 | 2039 |
2034 return new ExpressionStatement(new Throw(exception, pos)); | 2040 return new(zone()) ExpressionStatement(new(zone()) Throw(exception, pos)); |
2035 } | 2041 } |
2036 | 2042 |
2037 | 2043 |
2038 TryStatement* Parser::ParseTryStatement(bool* ok) { | 2044 TryStatement* Parser::ParseTryStatement(bool* ok) { |
2039 // TryStatement :: | 2045 // TryStatement :: |
2040 // 'try' Block Catch | 2046 // 'try' Block Catch |
2041 // 'try' Block Finally | 2047 // 'try' Block Finally |
2042 // 'try' Block Catch Finally | 2048 // 'try' Block Catch Finally |
2043 // | 2049 // |
2044 // Catch :: | 2050 // Catch :: |
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2088 return NULL; | 2094 return NULL; |
2089 } | 2095 } |
2090 | 2096 |
2091 Expect(Token::RPAREN, CHECK_OK); | 2097 Expect(Token::RPAREN, CHECK_OK); |
2092 | 2098 |
2093 if (peek() == Token::LBRACE) { | 2099 if (peek() == Token::LBRACE) { |
2094 // Allocate a temporary for holding the finally state while | 2100 // Allocate a temporary for holding the finally state while |
2095 // executing the finally block. | 2101 // executing the finally block. |
2096 catch_var = | 2102 catch_var = |
2097 top_scope_->NewTemporary(isolate()->factory()->catch_var_symbol()); | 2103 top_scope_->NewTemporary(isolate()->factory()->catch_var_symbol()); |
2098 Literal* name_literal = new Literal(name); | 2104 Literal* name_literal = new(zone()) Literal(name); |
2099 VariableProxy* catch_var_use = new VariableProxy(catch_var); | 2105 VariableProxy* catch_var_use = new(zone()) VariableProxy(catch_var); |
2100 Expression* obj = new CatchExtensionObject(name_literal, catch_var_use); | 2106 Expression* obj = |
2107 new(zone()) CatchExtensionObject(name_literal, catch_var_use); | |
2101 { Target target(&this->target_stack_, &catch_collector); | 2108 { Target target(&this->target_stack_, &catch_collector); |
2102 catch_block = WithHelper(obj, NULL, true, CHECK_OK); | 2109 catch_block = WithHelper(obj, NULL, true, CHECK_OK); |
2103 } | 2110 } |
2104 } else { | 2111 } else { |
2105 Expect(Token::LBRACE, CHECK_OK); | 2112 Expect(Token::LBRACE, CHECK_OK); |
2106 } | 2113 } |
2107 | 2114 |
2108 tok = peek(); | 2115 tok = peek(); |
2109 } | 2116 } |
2110 | 2117 |
2111 if (tok == Token::FINALLY || !has_catch) { | 2118 if (tok == Token::FINALLY || !has_catch) { |
2112 Consume(Token::FINALLY); | 2119 Consume(Token::FINALLY); |
2113 // Declare a variable for holding the finally state while | 2120 // Declare a variable for holding the finally state while |
2114 // executing the finally block. | 2121 // executing the finally block. |
2115 finally_block = ParseBlock(NULL, CHECK_OK); | 2122 finally_block = ParseBlock(NULL, CHECK_OK); |
2116 } | 2123 } |
2117 | 2124 |
2118 // Simplify the AST nodes by converting: | 2125 // Simplify the AST nodes by converting: |
2119 // 'try { } catch { } finally { }' | 2126 // 'try { } catch { } finally { }' |
2120 // to: | 2127 // to: |
2121 // 'try { try { } catch { } } finally { }' | 2128 // 'try { try { } catch { } } finally { }' |
2122 | 2129 |
2123 if (catch_block != NULL && finally_block != NULL) { | 2130 if (catch_block != NULL && finally_block != NULL) { |
2124 VariableProxy* catch_var_defn = new VariableProxy(catch_var); | 2131 VariableProxy* catch_var_defn = new(zone()) VariableProxy(catch_var); |
2125 TryCatchStatement* statement = | 2132 TryCatchStatement* statement = |
2126 new TryCatchStatement(try_block, catch_var_defn, catch_block); | 2133 new(zone()) TryCatchStatement(try_block, catch_var_defn, catch_block); |
2127 statement->set_escaping_targets(collector.targets()); | 2134 statement->set_escaping_targets(collector.targets()); |
2128 try_block = new Block(NULL, 1, false); | 2135 try_block = new(zone()) Block(NULL, 1, false); |
2129 try_block->AddStatement(statement); | 2136 try_block->AddStatement(statement); |
2130 catch_block = NULL; | 2137 catch_block = NULL; |
2131 } | 2138 } |
2132 | 2139 |
2133 TryStatement* result = NULL; | 2140 TryStatement* result = NULL; |
2134 if (catch_block != NULL) { | 2141 if (catch_block != NULL) { |
2135 ASSERT(finally_block == NULL); | 2142 ASSERT(finally_block == NULL); |
2136 VariableProxy* catch_var_defn = new VariableProxy(catch_var); | 2143 VariableProxy* catch_var_defn = new(zone()) VariableProxy(catch_var); |
2137 result = new TryCatchStatement(try_block, catch_var_defn, catch_block); | 2144 result = |
2145 new(zone()) TryCatchStatement(try_block, catch_var_defn, catch_block); | |
2138 result->set_escaping_targets(collector.targets()); | 2146 result->set_escaping_targets(collector.targets()); |
2139 } else { | 2147 } else { |
2140 ASSERT(finally_block != NULL); | 2148 ASSERT(finally_block != NULL); |
2141 result = new TryFinallyStatement(try_block, finally_block); | 2149 result = new(zone()) TryFinallyStatement(try_block, finally_block); |
2142 // Add the jump targets of the try block and the catch block. | 2150 // Add the jump targets of the try block and the catch block. |
2143 for (int i = 0; i < collector.targets()->length(); i++) { | 2151 for (int i = 0; i < collector.targets()->length(); i++) { |
2144 catch_collector.AddTarget(collector.targets()->at(i)); | 2152 catch_collector.AddTarget(collector.targets()->at(i)); |
2145 } | 2153 } |
2146 result->set_escaping_targets(catch_collector.targets()); | 2154 result->set_escaping_targets(catch_collector.targets()); |
2147 } | 2155 } |
2148 | 2156 |
2149 return result; | 2157 return result; |
2150 } | 2158 } |
2151 | 2159 |
2152 | 2160 |
2153 DoWhileStatement* Parser::ParseDoWhileStatement(ZoneStringList* labels, | 2161 DoWhileStatement* Parser::ParseDoWhileStatement(ZoneStringList* labels, |
2154 bool* ok) { | 2162 bool* ok) { |
2155 // DoStatement :: | 2163 // DoStatement :: |
2156 // 'do' Statement 'while' '(' Expression ')' ';' | 2164 // 'do' Statement 'while' '(' Expression ')' ';' |
2157 | 2165 |
2158 lexical_scope_->AddLoop(); | 2166 lexical_scope_->AddLoop(); |
2159 DoWhileStatement* loop = new DoWhileStatement(labels); | 2167 DoWhileStatement* loop = new(zone()) DoWhileStatement(labels); |
2160 Target target(&this->target_stack_, loop); | 2168 Target target(&this->target_stack_, loop); |
2161 | 2169 |
2162 Expect(Token::DO, CHECK_OK); | 2170 Expect(Token::DO, CHECK_OK); |
2163 Statement* body = ParseStatement(NULL, CHECK_OK); | 2171 Statement* body = ParseStatement(NULL, CHECK_OK); |
2164 Expect(Token::WHILE, CHECK_OK); | 2172 Expect(Token::WHILE, CHECK_OK); |
2165 Expect(Token::LPAREN, CHECK_OK); | 2173 Expect(Token::LPAREN, CHECK_OK); |
2166 | 2174 |
2167 if (loop != NULL) { | 2175 if (loop != NULL) { |
2168 int position = scanner().location().beg_pos; | 2176 int position = scanner().location().beg_pos; |
2169 loop->set_condition_position(position); | 2177 loop->set_condition_position(position); |
(...skipping 12 matching lines...) Expand all Loading... | |
2182 if (loop != NULL) loop->Initialize(cond, body); | 2190 if (loop != NULL) loop->Initialize(cond, body); |
2183 return loop; | 2191 return loop; |
2184 } | 2192 } |
2185 | 2193 |
2186 | 2194 |
2187 WhileStatement* Parser::ParseWhileStatement(ZoneStringList* labels, bool* ok) { | 2195 WhileStatement* Parser::ParseWhileStatement(ZoneStringList* labels, bool* ok) { |
2188 // WhileStatement :: | 2196 // WhileStatement :: |
2189 // 'while' '(' Expression ')' Statement | 2197 // 'while' '(' Expression ')' Statement |
2190 | 2198 |
2191 lexical_scope_->AddLoop(); | 2199 lexical_scope_->AddLoop(); |
2192 WhileStatement* loop = new WhileStatement(labels); | 2200 WhileStatement* loop = new(zone()) WhileStatement(labels); |
2193 Target target(&this->target_stack_, loop); | 2201 Target target(&this->target_stack_, loop); |
2194 | 2202 |
2195 Expect(Token::WHILE, CHECK_OK); | 2203 Expect(Token::WHILE, CHECK_OK); |
2196 Expect(Token::LPAREN, CHECK_OK); | 2204 Expect(Token::LPAREN, CHECK_OK); |
2197 Expression* cond = ParseExpression(true, CHECK_OK); | 2205 Expression* cond = ParseExpression(true, CHECK_OK); |
2198 if (cond != NULL) cond->set_is_loop_condition(true); | 2206 if (cond != NULL) cond->set_is_loop_condition(true); |
2199 Expect(Token::RPAREN, CHECK_OK); | 2207 Expect(Token::RPAREN, CHECK_OK); |
2200 Statement* body = ParseStatement(NULL, CHECK_OK); | 2208 Statement* body = ParseStatement(NULL, CHECK_OK); |
2201 | 2209 |
2202 if (loop != NULL) loop->Initialize(cond, body); | 2210 if (loop != NULL) loop->Initialize(cond, body); |
2203 return loop; | 2211 return loop; |
2204 } | 2212 } |
2205 | 2213 |
2206 | 2214 |
2207 Statement* Parser::ParseForStatement(ZoneStringList* labels, bool* ok) { | 2215 Statement* Parser::ParseForStatement(ZoneStringList* labels, bool* ok) { |
2208 // ForStatement :: | 2216 // ForStatement :: |
2209 // 'for' '(' Expression? ';' Expression? ';' Expression? ')' Statement | 2217 // 'for' '(' Expression? ';' Expression? ';' Expression? ')' Statement |
2210 | 2218 |
2211 lexical_scope_->AddLoop(); | 2219 lexical_scope_->AddLoop(); |
2212 Statement* init = NULL; | 2220 Statement* init = NULL; |
2213 | 2221 |
2214 Expect(Token::FOR, CHECK_OK); | 2222 Expect(Token::FOR, CHECK_OK); |
2215 Expect(Token::LPAREN, CHECK_OK); | 2223 Expect(Token::LPAREN, CHECK_OK); |
2216 if (peek() != Token::SEMICOLON) { | 2224 if (peek() != Token::SEMICOLON) { |
2217 if (peek() == Token::VAR || peek() == Token::CONST) { | 2225 if (peek() == Token::VAR || peek() == Token::CONST) { |
2218 Expression* each = NULL; | 2226 Expression* each = NULL; |
2219 Block* variable_statement = | 2227 Block* variable_statement = |
2220 ParseVariableDeclarations(false, &each, CHECK_OK); | 2228 ParseVariableDeclarations(false, &each, CHECK_OK); |
2221 if (peek() == Token::IN && each != NULL) { | 2229 if (peek() == Token::IN && each != NULL) { |
2222 ForInStatement* loop = new ForInStatement(labels); | 2230 ForInStatement* loop = new(zone()) ForInStatement(labels); |
2223 Target target(&this->target_stack_, loop); | 2231 Target target(&this->target_stack_, loop); |
2224 | 2232 |
2225 Expect(Token::IN, CHECK_OK); | 2233 Expect(Token::IN, CHECK_OK); |
2226 Expression* enumerable = ParseExpression(true, CHECK_OK); | 2234 Expression* enumerable = ParseExpression(true, CHECK_OK); |
2227 Expect(Token::RPAREN, CHECK_OK); | 2235 Expect(Token::RPAREN, CHECK_OK); |
2228 | 2236 |
2229 Statement* body = ParseStatement(NULL, CHECK_OK); | 2237 Statement* body = ParseStatement(NULL, CHECK_OK); |
2230 loop->Initialize(each, enumerable, body); | 2238 loop->Initialize(each, enumerable, body); |
2231 Block* result = new Block(NULL, 2, false); | 2239 Block* result = new(zone()) Block(NULL, 2, false); |
2232 result->AddStatement(variable_statement); | 2240 result->AddStatement(variable_statement); |
2233 result->AddStatement(loop); | 2241 result->AddStatement(loop); |
2234 // Parsed for-in loop w/ variable/const declaration. | 2242 // Parsed for-in loop w/ variable/const declaration. |
2235 return result; | 2243 return result; |
2236 } else { | 2244 } else { |
2237 init = variable_statement; | 2245 init = variable_statement; |
2238 } | 2246 } |
2239 | 2247 |
2240 } else { | 2248 } else { |
2241 Expression* expression = ParseExpression(false, CHECK_OK); | 2249 Expression* expression = ParseExpression(false, CHECK_OK); |
2242 if (peek() == Token::IN) { | 2250 if (peek() == Token::IN) { |
2243 // Signal a reference error if the expression is an invalid | 2251 // Signal a reference error if the expression is an invalid |
2244 // left-hand side expression. We could report this as a syntax | 2252 // left-hand side expression. We could report this as a syntax |
2245 // error here but for compatibility with JSC we choose to report | 2253 // error here but for compatibility with JSC we choose to report |
2246 // the error at runtime. | 2254 // the error at runtime. |
2247 if (expression == NULL || !expression->IsValidLeftHandSide()) { | 2255 if (expression == NULL || !expression->IsValidLeftHandSide()) { |
2248 Handle<String> type = | 2256 Handle<String> type = |
2249 isolate()->factory()->invalid_lhs_in_for_in_symbol(); | 2257 isolate()->factory()->invalid_lhs_in_for_in_symbol(); |
2250 expression = NewThrowReferenceError(type); | 2258 expression = NewThrowReferenceError(type); |
2251 } | 2259 } |
2252 ForInStatement* loop = new ForInStatement(labels); | 2260 ForInStatement* loop = new(zone()) ForInStatement(labels); |
2253 Target target(&this->target_stack_, loop); | 2261 Target target(&this->target_stack_, loop); |
2254 | 2262 |
2255 Expect(Token::IN, CHECK_OK); | 2263 Expect(Token::IN, CHECK_OK); |
2256 Expression* enumerable = ParseExpression(true, CHECK_OK); | 2264 Expression* enumerable = ParseExpression(true, CHECK_OK); |
2257 Expect(Token::RPAREN, CHECK_OK); | 2265 Expect(Token::RPAREN, CHECK_OK); |
2258 | 2266 |
2259 Statement* body = ParseStatement(NULL, CHECK_OK); | 2267 Statement* body = ParseStatement(NULL, CHECK_OK); |
2260 if (loop) loop->Initialize(expression, enumerable, body); | 2268 if (loop) loop->Initialize(expression, enumerable, body); |
2261 // Parsed for-in loop. | 2269 // Parsed for-in loop. |
2262 return loop; | 2270 return loop; |
2263 | 2271 |
2264 } else { | 2272 } else { |
2265 init = new ExpressionStatement(expression); | 2273 init = new(zone()) ExpressionStatement(expression); |
2266 } | 2274 } |
2267 } | 2275 } |
2268 } | 2276 } |
2269 | 2277 |
2270 // Standard 'for' loop | 2278 // Standard 'for' loop |
2271 ForStatement* loop = new ForStatement(labels); | 2279 ForStatement* loop = new(zone()) ForStatement(labels); |
2272 Target target(&this->target_stack_, loop); | 2280 Target target(&this->target_stack_, loop); |
2273 | 2281 |
2274 // Parsed initializer at this point. | 2282 // Parsed initializer at this point. |
2275 Expect(Token::SEMICOLON, CHECK_OK); | 2283 Expect(Token::SEMICOLON, CHECK_OK); |
2276 | 2284 |
2277 Expression* cond = NULL; | 2285 Expression* cond = NULL; |
2278 if (peek() != Token::SEMICOLON) { | 2286 if (peek() != Token::SEMICOLON) { |
2279 cond = ParseExpression(true, CHECK_OK); | 2287 cond = ParseExpression(true, CHECK_OK); |
2280 if (cond != NULL) cond->set_is_loop_condition(true); | 2288 if (cond != NULL) cond->set_is_loop_condition(true); |
2281 } | 2289 } |
2282 Expect(Token::SEMICOLON, CHECK_OK); | 2290 Expect(Token::SEMICOLON, CHECK_OK); |
2283 | 2291 |
2284 Statement* next = NULL; | 2292 Statement* next = NULL; |
2285 if (peek() != Token::RPAREN) { | 2293 if (peek() != Token::RPAREN) { |
2286 Expression* exp = ParseExpression(true, CHECK_OK); | 2294 Expression* exp = ParseExpression(true, CHECK_OK); |
2287 next = new ExpressionStatement(exp); | 2295 next = new(zone()) ExpressionStatement(exp); |
2288 } | 2296 } |
2289 Expect(Token::RPAREN, CHECK_OK); | 2297 Expect(Token::RPAREN, CHECK_OK); |
2290 | 2298 |
2291 Statement* body = ParseStatement(NULL, CHECK_OK); | 2299 Statement* body = ParseStatement(NULL, CHECK_OK); |
2292 if (loop) loop->Initialize(init, cond, next, body); | 2300 if (loop) loop->Initialize(init, cond, next, body); |
2293 return loop; | 2301 return loop; |
2294 } | 2302 } |
2295 | 2303 |
2296 | 2304 |
2297 // Precedence = 1 | 2305 // Precedence = 1 |
2298 Expression* Parser::ParseExpression(bool accept_IN, bool* ok) { | 2306 Expression* Parser::ParseExpression(bool accept_IN, bool* ok) { |
2299 // Expression :: | 2307 // Expression :: |
2300 // AssignmentExpression | 2308 // AssignmentExpression |
2301 // Expression ',' AssignmentExpression | 2309 // Expression ',' AssignmentExpression |
2302 | 2310 |
2303 Expression* result = ParseAssignmentExpression(accept_IN, CHECK_OK); | 2311 Expression* result = ParseAssignmentExpression(accept_IN, CHECK_OK); |
2304 while (peek() == Token::COMMA) { | 2312 while (peek() == Token::COMMA) { |
2305 Expect(Token::COMMA, CHECK_OK); | 2313 Expect(Token::COMMA, CHECK_OK); |
2306 int position = scanner().location().beg_pos; | 2314 int position = scanner().location().beg_pos; |
2307 Expression* right = ParseAssignmentExpression(accept_IN, CHECK_OK); | 2315 Expression* right = ParseAssignmentExpression(accept_IN, CHECK_OK); |
2308 result = new BinaryOperation(Token::COMMA, result, right, position); | 2316 result = new(zone()) BinaryOperation(Token::COMMA, result, right, position); |
2309 } | 2317 } |
2310 return result; | 2318 return result; |
2311 } | 2319 } |
2312 | 2320 |
2313 | 2321 |
2314 // Precedence = 2 | 2322 // Precedence = 2 |
2315 Expression* Parser::ParseAssignmentExpression(bool accept_IN, bool* ok) { | 2323 Expression* Parser::ParseAssignmentExpression(bool accept_IN, bool* ok) { |
2316 // AssignmentExpression :: | 2324 // AssignmentExpression :: |
2317 // ConditionalExpression | 2325 // ConditionalExpression |
2318 // LeftHandSideExpression AssignmentOperator AssignmentExpression | 2326 // LeftHandSideExpression AssignmentOperator AssignmentExpression |
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2370 // expression. | 2378 // expression. |
2371 if ((op == Token::INIT_VAR | 2379 if ((op == Token::INIT_VAR |
2372 || op == Token::INIT_CONST | 2380 || op == Token::INIT_CONST |
2373 || op == Token::ASSIGN) | 2381 || op == Token::ASSIGN) |
2374 && (right->AsCall() == NULL)) { | 2382 && (right->AsCall() == NULL)) { |
2375 fni_->Infer(); | 2383 fni_->Infer(); |
2376 } | 2384 } |
2377 fni_->Leave(); | 2385 fni_->Leave(); |
2378 } | 2386 } |
2379 | 2387 |
2380 return new Assignment(op, expression, right, pos); | 2388 return new(zone()) Assignment(op, expression, right, pos); |
2381 } | 2389 } |
2382 | 2390 |
2383 | 2391 |
2384 // Precedence = 3 | 2392 // Precedence = 3 |
2385 Expression* Parser::ParseConditionalExpression(bool accept_IN, bool* ok) { | 2393 Expression* Parser::ParseConditionalExpression(bool accept_IN, bool* ok) { |
2386 // ConditionalExpression :: | 2394 // ConditionalExpression :: |
2387 // LogicalOrExpression | 2395 // LogicalOrExpression |
2388 // LogicalOrExpression '?' AssignmentExpression ':' AssignmentExpression | 2396 // LogicalOrExpression '?' AssignmentExpression ':' AssignmentExpression |
2389 | 2397 |
2390 // We start using the binary expression parser for prec >= 4 only! | 2398 // We start using the binary expression parser for prec >= 4 only! |
2391 Expression* expression = ParseBinaryExpression(4, accept_IN, CHECK_OK); | 2399 Expression* expression = ParseBinaryExpression(4, accept_IN, CHECK_OK); |
2392 if (peek() != Token::CONDITIONAL) return expression; | 2400 if (peek() != Token::CONDITIONAL) return expression; |
2393 Consume(Token::CONDITIONAL); | 2401 Consume(Token::CONDITIONAL); |
2394 // In parsing the first assignment expression in conditional | 2402 // In parsing the first assignment expression in conditional |
2395 // expressions we always accept the 'in' keyword; see ECMA-262, | 2403 // expressions we always accept the 'in' keyword; see ECMA-262, |
2396 // section 11.12, page 58. | 2404 // section 11.12, page 58. |
2397 int left_position = scanner().peek_location().beg_pos; | 2405 int left_position = scanner().peek_location().beg_pos; |
2398 Expression* left = ParseAssignmentExpression(true, CHECK_OK); | 2406 Expression* left = ParseAssignmentExpression(true, CHECK_OK); |
2399 Expect(Token::COLON, CHECK_OK); | 2407 Expect(Token::COLON, CHECK_OK); |
2400 int right_position = scanner().peek_location().beg_pos; | 2408 int right_position = scanner().peek_location().beg_pos; |
2401 Expression* right = ParseAssignmentExpression(accept_IN, CHECK_OK); | 2409 Expression* right = ParseAssignmentExpression(accept_IN, CHECK_OK); |
2402 return new Conditional(expression, left, right, | 2410 return new(zone()) Conditional(expression, left, right, |
2403 left_position, right_position); | 2411 left_position, right_position); |
2404 } | 2412 } |
2405 | 2413 |
2406 | 2414 |
2407 static int Precedence(Token::Value tok, bool accept_IN) { | 2415 static int Precedence(Token::Value tok, bool accept_IN) { |
2408 if (tok == Token::IN && !accept_IN) | 2416 if (tok == Token::IN && !accept_IN) |
2409 return 0; // 0 precedence will terminate binary expression parsing | 2417 return 0; // 0 precedence will terminate binary expression parsing |
2410 | 2418 |
2411 return Token::Precedence(tok); | 2419 return Token::Precedence(tok); |
2412 } | 2420 } |
(...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2480 // We have a comparison. | 2488 // We have a comparison. |
2481 Token::Value cmp = op; | 2489 Token::Value cmp = op; |
2482 switch (op) { | 2490 switch (op) { |
2483 case Token::NE: cmp = Token::EQ; break; | 2491 case Token::NE: cmp = Token::EQ; break; |
2484 case Token::NE_STRICT: cmp = Token::EQ_STRICT; break; | 2492 case Token::NE_STRICT: cmp = Token::EQ_STRICT; break; |
2485 default: break; | 2493 default: break; |
2486 } | 2494 } |
2487 x = NewCompareNode(cmp, x, y, position); | 2495 x = NewCompareNode(cmp, x, y, position); |
2488 if (cmp != op) { | 2496 if (cmp != op) { |
2489 // The comparison was negated - add a NOT. | 2497 // The comparison was negated - add a NOT. |
2490 x = new UnaryOperation(Token::NOT, x); | 2498 x = new(zone()) UnaryOperation(Token::NOT, x); |
2491 } | 2499 } |
2492 | 2500 |
2493 } else { | 2501 } else { |
2494 // We have a "normal" binary operation. | 2502 // We have a "normal" binary operation. |
2495 x = new BinaryOperation(op, x, y, position); | 2503 x = new(zone()) BinaryOperation(op, x, y, position); |
2496 } | 2504 } |
2497 } | 2505 } |
2498 } | 2506 } |
2499 return x; | 2507 return x; |
2500 } | 2508 } |
2501 | 2509 |
2502 | 2510 |
2503 Expression* Parser::NewCompareNode(Token::Value op, | 2511 Expression* Parser::NewCompareNode(Token::Value op, |
2504 Expression* x, | 2512 Expression* x, |
2505 Expression* y, | 2513 Expression* y, |
2506 int position) { | 2514 int position) { |
2507 ASSERT(op != Token::NE && op != Token::NE_STRICT); | 2515 ASSERT(op != Token::NE && op != Token::NE_STRICT); |
2508 if (op == Token::EQ || op == Token::EQ_STRICT) { | 2516 if (op == Token::EQ || op == Token::EQ_STRICT) { |
2509 bool is_strict = (op == Token::EQ_STRICT); | 2517 bool is_strict = (op == Token::EQ_STRICT); |
2510 Literal* x_literal = x->AsLiteral(); | 2518 Literal* x_literal = x->AsLiteral(); |
2511 if (x_literal != NULL && x_literal->IsNull()) { | 2519 if (x_literal != NULL && x_literal->IsNull()) { |
2512 return new CompareToNull(is_strict, y); | 2520 return new(zone()) CompareToNull(is_strict, y); |
2513 } | 2521 } |
2514 | 2522 |
2515 Literal* y_literal = y->AsLiteral(); | 2523 Literal* y_literal = y->AsLiteral(); |
2516 if (y_literal != NULL && y_literal->IsNull()) { | 2524 if (y_literal != NULL && y_literal->IsNull()) { |
2517 return new CompareToNull(is_strict, x); | 2525 return new(zone()) CompareToNull(is_strict, x); |
2518 } | 2526 } |
2519 } | 2527 } |
2520 return new CompareOperation(op, x, y, position); | 2528 return new(zone()) CompareOperation(op, x, y, position); |
2521 } | 2529 } |
2522 | 2530 |
2523 | 2531 |
2524 Expression* Parser::ParseUnaryExpression(bool* ok) { | 2532 Expression* Parser::ParseUnaryExpression(bool* ok) { |
2525 // UnaryExpression :: | 2533 // UnaryExpression :: |
2526 // PostfixExpression | 2534 // PostfixExpression |
2527 // 'delete' UnaryExpression | 2535 // 'delete' UnaryExpression |
2528 // 'void' UnaryExpression | 2536 // 'void' UnaryExpression |
2529 // 'typeof' UnaryExpression | 2537 // 'typeof' UnaryExpression |
2530 // '++' UnaryExpression | 2538 // '++' UnaryExpression |
(...skipping 26 matching lines...) Expand all Loading... | |
2557 // "delete identifier" is a syntax error in strict mode. | 2565 // "delete identifier" is a syntax error in strict mode. |
2558 if (op == Token::DELETE && top_scope_->is_strict_mode()) { | 2566 if (op == Token::DELETE && top_scope_->is_strict_mode()) { |
2559 VariableProxy* operand = expression->AsVariableProxy(); | 2567 VariableProxy* operand = expression->AsVariableProxy(); |
2560 if (operand != NULL && !operand->is_this()) { | 2568 if (operand != NULL && !operand->is_this()) { |
2561 ReportMessage("strict_delete", Vector<const char*>::empty()); | 2569 ReportMessage("strict_delete", Vector<const char*>::empty()); |
2562 *ok = false; | 2570 *ok = false; |
2563 return NULL; | 2571 return NULL; |
2564 } | 2572 } |
2565 } | 2573 } |
2566 | 2574 |
2567 return new UnaryOperation(op, expression); | 2575 return new(zone()) UnaryOperation(op, expression); |
2568 | 2576 |
2569 } else if (Token::IsCountOp(op)) { | 2577 } else if (Token::IsCountOp(op)) { |
2570 op = Next(); | 2578 op = Next(); |
2571 Expression* expression = ParseUnaryExpression(CHECK_OK); | 2579 Expression* expression = ParseUnaryExpression(CHECK_OK); |
2572 // Signal a reference error if the expression is an invalid | 2580 // Signal a reference error if the expression is an invalid |
2573 // left-hand side expression. We could report this as a syntax | 2581 // left-hand side expression. We could report this as a syntax |
2574 // error here but for compatibility with JSC we choose to report the | 2582 // error here but for compatibility with JSC we choose to report the |
2575 // error at runtime. | 2583 // error at runtime. |
2576 if (expression == NULL || !expression->IsValidLeftHandSide()) { | 2584 if (expression == NULL || !expression->IsValidLeftHandSide()) { |
2577 Handle<String> type = | 2585 Handle<String> type = |
2578 isolate()->factory()->invalid_lhs_in_prefix_op_symbol(); | 2586 isolate()->factory()->invalid_lhs_in_prefix_op_symbol(); |
2579 expression = NewThrowReferenceError(type); | 2587 expression = NewThrowReferenceError(type); |
2580 } | 2588 } |
2581 | 2589 |
2582 if (top_scope_->is_strict_mode()) { | 2590 if (top_scope_->is_strict_mode()) { |
2583 // Prefix expression operand in strict mode may not be eval or arguments. | 2591 // Prefix expression operand in strict mode may not be eval or arguments. |
2584 CheckStrictModeLValue(expression, "strict_lhs_prefix", CHECK_OK); | 2592 CheckStrictModeLValue(expression, "strict_lhs_prefix", CHECK_OK); |
2585 } | 2593 } |
2586 | 2594 |
2587 int position = scanner().location().beg_pos; | 2595 int position = scanner().location().beg_pos; |
2588 IncrementOperation* increment = new IncrementOperation(op, expression); | 2596 IncrementOperation* increment = |
2589 return new CountOperation(true /* prefix */, increment, position); | 2597 new(zone()) IncrementOperation(op, expression); |
2598 return new(zone()) CountOperation(true /* prefix */, increment, position); | |
2590 | 2599 |
2591 } else { | 2600 } else { |
2592 return ParsePostfixExpression(ok); | 2601 return ParsePostfixExpression(ok); |
2593 } | 2602 } |
2594 } | 2603 } |
2595 | 2604 |
2596 | 2605 |
2597 Expression* Parser::ParsePostfixExpression(bool* ok) { | 2606 Expression* Parser::ParsePostfixExpression(bool* ok) { |
2598 // PostfixExpression :: | 2607 // PostfixExpression :: |
2599 // LeftHandSideExpression ('++' | '--')? | 2608 // LeftHandSideExpression ('++' | '--')? |
(...skipping 11 matching lines...) Expand all Loading... | |
2611 expression = NewThrowReferenceError(type); | 2620 expression = NewThrowReferenceError(type); |
2612 } | 2621 } |
2613 | 2622 |
2614 if (top_scope_->is_strict_mode()) { | 2623 if (top_scope_->is_strict_mode()) { |
2615 // Postfix expression operand in strict mode may not be eval or arguments. | 2624 // Postfix expression operand in strict mode may not be eval or arguments. |
2616 CheckStrictModeLValue(expression, "strict_lhs_prefix", CHECK_OK); | 2625 CheckStrictModeLValue(expression, "strict_lhs_prefix", CHECK_OK); |
2617 } | 2626 } |
2618 | 2627 |
2619 Token::Value next = Next(); | 2628 Token::Value next = Next(); |
2620 int position = scanner().location().beg_pos; | 2629 int position = scanner().location().beg_pos; |
2621 IncrementOperation* increment = new IncrementOperation(next, expression); | 2630 IncrementOperation* increment = |
2622 expression = new CountOperation(false /* postfix */, increment, position); | 2631 new(zone()) IncrementOperation(next, expression); |
2632 expression = | |
2633 new(zone()) CountOperation(false /* postfix */, increment, position); | |
2623 } | 2634 } |
2624 return expression; | 2635 return expression; |
2625 } | 2636 } |
2626 | 2637 |
2627 | 2638 |
2628 Expression* Parser::ParseLeftHandSideExpression(bool* ok) { | 2639 Expression* Parser::ParseLeftHandSideExpression(bool* ok) { |
2629 // LeftHandSideExpression :: | 2640 // LeftHandSideExpression :: |
2630 // (NewExpression | MemberExpression) ... | 2641 // (NewExpression | MemberExpression) ... |
2631 | 2642 |
2632 Expression* result; | 2643 Expression* result; |
2633 if (peek() == Token::NEW) { | 2644 if (peek() == Token::NEW) { |
2634 result = ParseNewExpression(CHECK_OK); | 2645 result = ParseNewExpression(CHECK_OK); |
2635 } else { | 2646 } else { |
2636 result = ParseMemberExpression(CHECK_OK); | 2647 result = ParseMemberExpression(CHECK_OK); |
2637 } | 2648 } |
2638 | 2649 |
2639 while (true) { | 2650 while (true) { |
2640 switch (peek()) { | 2651 switch (peek()) { |
2641 case Token::LBRACK: { | 2652 case Token::LBRACK: { |
2642 Consume(Token::LBRACK); | 2653 Consume(Token::LBRACK); |
2643 int pos = scanner().location().beg_pos; | 2654 int pos = scanner().location().beg_pos; |
2644 Expression* index = ParseExpression(true, CHECK_OK); | 2655 Expression* index = ParseExpression(true, CHECK_OK); |
2645 result = new Property(result, index, pos); | 2656 result = new(zone()) Property(result, index, pos); |
2646 Expect(Token::RBRACK, CHECK_OK); | 2657 Expect(Token::RBRACK, CHECK_OK); |
2647 break; | 2658 break; |
2648 } | 2659 } |
2649 | 2660 |
2650 case Token::LPAREN: { | 2661 case Token::LPAREN: { |
2651 int pos = scanner().location().beg_pos; | 2662 int pos = scanner().location().beg_pos; |
2652 ZoneList<Expression*>* args = ParseArguments(CHECK_OK); | 2663 ZoneList<Expression*>* args = ParseArguments(CHECK_OK); |
2653 | 2664 |
2654 // Keep track of eval() calls since they disable all local variable | 2665 // Keep track of eval() calls since they disable all local variable |
2655 // optimizations. | 2666 // optimizations. |
(...skipping 17 matching lines...) Expand all Loading... | |
2673 } | 2684 } |
2674 } | 2685 } |
2675 result = NewCall(result, args, pos); | 2686 result = NewCall(result, args, pos); |
2676 break; | 2687 break; |
2677 } | 2688 } |
2678 | 2689 |
2679 case Token::PERIOD: { | 2690 case Token::PERIOD: { |
2680 Consume(Token::PERIOD); | 2691 Consume(Token::PERIOD); |
2681 int pos = scanner().location().beg_pos; | 2692 int pos = scanner().location().beg_pos; |
2682 Handle<String> name = ParseIdentifierName(CHECK_OK); | 2693 Handle<String> name = ParseIdentifierName(CHECK_OK); |
2683 result = new Property(result, new Literal(name), pos); | 2694 result = new(zone()) Property(result, new(zone()) Literal(name), pos); |
2684 if (fni_ != NULL) fni_->PushLiteralName(name); | 2695 if (fni_ != NULL) fni_->PushLiteralName(name); |
2685 break; | 2696 break; |
2686 } | 2697 } |
2687 | 2698 |
2688 default: | 2699 default: |
2689 return result; | 2700 return result; |
2690 } | 2701 } |
2691 } | 2702 } |
2692 } | 2703 } |
2693 | 2704 |
(...skipping 15 matching lines...) Expand all Loading... | |
2709 | 2720 |
2710 Expression* result; | 2721 Expression* result; |
2711 if (peek() == Token::NEW) { | 2722 if (peek() == Token::NEW) { |
2712 result = ParseNewPrefix(stack, CHECK_OK); | 2723 result = ParseNewPrefix(stack, CHECK_OK); |
2713 } else { | 2724 } else { |
2714 result = ParseMemberWithNewPrefixesExpression(stack, CHECK_OK); | 2725 result = ParseMemberWithNewPrefixesExpression(stack, CHECK_OK); |
2715 } | 2726 } |
2716 | 2727 |
2717 if (!stack->is_empty()) { | 2728 if (!stack->is_empty()) { |
2718 int last = stack->pop(); | 2729 int last = stack->pop(); |
2719 result = new CallNew(result, new ZoneList<Expression*>(0), last); | 2730 result = new(zone()) CallNew(result, new ZoneList<Expression*>(0), last); |
2720 } | 2731 } |
2721 return result; | 2732 return result; |
2722 } | 2733 } |
2723 | 2734 |
2724 | 2735 |
2725 Expression* Parser::ParseNewExpression(bool* ok) { | 2736 Expression* Parser::ParseNewExpression(bool* ok) { |
2726 PositionStack stack(ok); | 2737 PositionStack stack(ok); |
2727 return ParseNewPrefix(&stack, ok); | 2738 return ParseNewPrefix(&stack, ok); |
2728 } | 2739 } |
2729 | 2740 |
(...skipping 24 matching lines...) Expand all Loading... | |
2754 } else { | 2765 } else { |
2755 result = ParsePrimaryExpression(CHECK_OK); | 2766 result = ParsePrimaryExpression(CHECK_OK); |
2756 } | 2767 } |
2757 | 2768 |
2758 while (true) { | 2769 while (true) { |
2759 switch (peek()) { | 2770 switch (peek()) { |
2760 case Token::LBRACK: { | 2771 case Token::LBRACK: { |
2761 Consume(Token::LBRACK); | 2772 Consume(Token::LBRACK); |
2762 int pos = scanner().location().beg_pos; | 2773 int pos = scanner().location().beg_pos; |
2763 Expression* index = ParseExpression(true, CHECK_OK); | 2774 Expression* index = ParseExpression(true, CHECK_OK); |
2764 result = new Property(result, index, pos); | 2775 result = new(zone()) Property(result, index, pos); |
2765 Expect(Token::RBRACK, CHECK_OK); | 2776 Expect(Token::RBRACK, CHECK_OK); |
2766 break; | 2777 break; |
2767 } | 2778 } |
2768 case Token::PERIOD: { | 2779 case Token::PERIOD: { |
2769 Consume(Token::PERIOD); | 2780 Consume(Token::PERIOD); |
2770 int pos = scanner().location().beg_pos; | 2781 int pos = scanner().location().beg_pos; |
2771 Handle<String> name = ParseIdentifierName(CHECK_OK); | 2782 Handle<String> name = ParseIdentifierName(CHECK_OK); |
2772 result = new Property(result, new Literal(name), pos); | 2783 result = new(zone()) Property(result, new(zone()) Literal(name), pos); |
2773 if (fni_ != NULL) fni_->PushLiteralName(name); | 2784 if (fni_ != NULL) fni_->PushLiteralName(name); |
2774 break; | 2785 break; |
2775 } | 2786 } |
2776 case Token::LPAREN: { | 2787 case Token::LPAREN: { |
2777 if ((stack == NULL) || stack->is_empty()) return result; | 2788 if ((stack == NULL) || stack->is_empty()) return result; |
2778 // Consume one of the new prefixes (already parsed). | 2789 // Consume one of the new prefixes (already parsed). |
2779 ZoneList<Expression*>* args = ParseArguments(CHECK_OK); | 2790 ZoneList<Expression*>* args = ParseArguments(CHECK_OK); |
2780 int last = stack->pop(); | 2791 int last = stack->pop(); |
2781 result = new CallNew(result, args, last); | 2792 result = new CallNew(result, args, last); |
2782 break; | 2793 break; |
2783 } | 2794 } |
2784 default: | 2795 default: |
2785 return result; | 2796 return result; |
2786 } | 2797 } |
2787 } | 2798 } |
2788 } | 2799 } |
2789 | 2800 |
2790 | 2801 |
2791 DebuggerStatement* Parser::ParseDebuggerStatement(bool* ok) { | 2802 DebuggerStatement* Parser::ParseDebuggerStatement(bool* ok) { |
2792 // In ECMA-262 'debugger' is defined as a reserved keyword. In some browser | 2803 // In ECMA-262 'debugger' is defined as a reserved keyword. In some browser |
2793 // contexts this is used as a statement which invokes the debugger as i a | 2804 // contexts this is used as a statement which invokes the debugger as i a |
2794 // break point is present. | 2805 // break point is present. |
2795 // DebuggerStatement :: | 2806 // DebuggerStatement :: |
2796 // 'debugger' ';' | 2807 // 'debugger' ';' |
2797 | 2808 |
2798 Expect(Token::DEBUGGER, CHECK_OK); | 2809 Expect(Token::DEBUGGER, CHECK_OK); |
2799 ExpectSemicolon(CHECK_OK); | 2810 ExpectSemicolon(CHECK_OK); |
2800 return new DebuggerStatement(); | 2811 return new(zone()) DebuggerStatement(); |
2801 } | 2812 } |
2802 | 2813 |
2803 | 2814 |
2804 void Parser::ReportUnexpectedToken(Token::Value token) { | 2815 void Parser::ReportUnexpectedToken(Token::Value token) { |
2805 // We don't report stack overflows here, to avoid increasing the | 2816 // We don't report stack overflows here, to avoid increasing the |
2806 // stack depth even further. Instead we report it after parsing is | 2817 // stack depth even further. Instead we report it after parsing is |
2807 // over, in ParseProgram/ParseJson. | 2818 // over, in ParseProgram/ParseJson. |
2808 if (token == Token::ILLEGAL && stack_overflow_) return; | 2819 if (token == Token::ILLEGAL && stack_overflow_) return; |
2809 // Four of the tokens are treated specially | 2820 // Four of the tokens are treated specially |
2810 switch (token) { | 2821 switch (token) { |
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2859 switch (peek()) { | 2870 switch (peek()) { |
2860 case Token::THIS: { | 2871 case Token::THIS: { |
2861 Consume(Token::THIS); | 2872 Consume(Token::THIS); |
2862 VariableProxy* recv = top_scope_->receiver(); | 2873 VariableProxy* recv = top_scope_->receiver(); |
2863 result = recv; | 2874 result = recv; |
2864 break; | 2875 break; |
2865 } | 2876 } |
2866 | 2877 |
2867 case Token::NULL_LITERAL: | 2878 case Token::NULL_LITERAL: |
2868 Consume(Token::NULL_LITERAL); | 2879 Consume(Token::NULL_LITERAL); |
2869 result = new Literal(isolate()->factory()->null_value()); | 2880 result = new(zone()) Literal(isolate()->factory()->null_value()); |
2870 break; | 2881 break; |
2871 | 2882 |
2872 case Token::TRUE_LITERAL: | 2883 case Token::TRUE_LITERAL: |
2873 Consume(Token::TRUE_LITERAL); | 2884 Consume(Token::TRUE_LITERAL); |
2874 result = new Literal(isolate()->factory()->true_value()); | 2885 result = new(zone()) Literal(isolate()->factory()->true_value()); |
2875 break; | 2886 break; |
2876 | 2887 |
2877 case Token::FALSE_LITERAL: | 2888 case Token::FALSE_LITERAL: |
2878 Consume(Token::FALSE_LITERAL); | 2889 Consume(Token::FALSE_LITERAL); |
2879 result = new Literal(isolate()->factory()->false_value()); | 2890 result = new(zone()) Literal(isolate()->factory()->false_value()); |
2880 break; | 2891 break; |
2881 | 2892 |
2882 case Token::IDENTIFIER: | 2893 case Token::IDENTIFIER: |
2883 case Token::FUTURE_RESERVED_WORD: { | 2894 case Token::FUTURE_RESERVED_WORD: { |
2884 Handle<String> name = ParseIdentifier(CHECK_OK); | 2895 Handle<String> name = ParseIdentifier(CHECK_OK); |
2885 if (fni_ != NULL) fni_->PushVariableName(name); | 2896 if (fni_ != NULL) fni_->PushVariableName(name); |
2886 result = top_scope_->NewUnresolved(name, | 2897 result = top_scope_->NewUnresolved(name, |
2887 inside_with(), | 2898 inside_with(), |
2888 scanner().location().beg_pos); | 2899 scanner().location().beg_pos); |
2889 break; | 2900 break; |
2890 } | 2901 } |
2891 | 2902 |
2892 case Token::NUMBER: { | 2903 case Token::NUMBER: { |
2893 Consume(Token::NUMBER); | 2904 Consume(Token::NUMBER); |
2894 ASSERT(scanner().is_literal_ascii()); | 2905 ASSERT(scanner().is_literal_ascii()); |
2895 double value = StringToDouble(scanner().literal_ascii_string(), | 2906 double value = StringToDouble(scanner().literal_ascii_string(), |
2896 ALLOW_HEX | ALLOW_OCTALS); | 2907 ALLOW_HEX | ALLOW_OCTALS); |
2897 result = NewNumberLiteral(value); | 2908 result = NewNumberLiteral(value); |
2898 break; | 2909 break; |
2899 } | 2910 } |
2900 | 2911 |
2901 case Token::STRING: { | 2912 case Token::STRING: { |
2902 Consume(Token::STRING); | 2913 Consume(Token::STRING); |
2903 Handle<String> symbol = GetSymbol(CHECK_OK); | 2914 Handle<String> symbol = GetSymbol(CHECK_OK); |
2904 result = new Literal(symbol); | 2915 result = new(zone()) Literal(symbol); |
2905 if (fni_ != NULL) fni_->PushLiteralName(symbol); | 2916 if (fni_ != NULL) fni_->PushLiteralName(symbol); |
2906 break; | 2917 break; |
2907 } | 2918 } |
2908 | 2919 |
2909 case Token::ASSIGN_DIV: | 2920 case Token::ASSIGN_DIV: |
2910 result = ParseRegExpLiteral(true, CHECK_OK); | 2921 result = ParseRegExpLiteral(true, CHECK_OK); |
2911 break; | 2922 break; |
2912 | 2923 |
2913 case Token::DIV: | 2924 case Token::DIV: |
2914 result = ParseRegExpLiteral(false, CHECK_OK); | 2925 result = ParseRegExpLiteral(false, CHECK_OK); |
(...skipping 106 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3021 literals->set(i, *boilerplate_value); | 3032 literals->set(i, *boilerplate_value); |
3022 } | 3033 } |
3023 } | 3034 } |
3024 | 3035 |
3025 // Simple and shallow arrays can be lazily copied, we transform the | 3036 // Simple and shallow arrays can be lazily copied, we transform the |
3026 // elements array to a copy-on-write array. | 3037 // elements array to a copy-on-write array. |
3027 if (is_simple && depth == 1 && values->length() > 0) { | 3038 if (is_simple && depth == 1 && values->length() > 0) { |
3028 literals->set_map(isolate()->heap()->fixed_cow_array_map()); | 3039 literals->set_map(isolate()->heap()->fixed_cow_array_map()); |
3029 } | 3040 } |
3030 | 3041 |
3031 return new ArrayLiteral(literals, values, | 3042 return new(zone()) ArrayLiteral(literals, values, |
3032 literal_index, is_simple, depth); | 3043 literal_index, is_simple, depth); |
3033 } | 3044 } |
3034 | 3045 |
3035 | 3046 |
3036 bool Parser::IsBoilerplateProperty(ObjectLiteral::Property* property) { | 3047 bool Parser::IsBoilerplateProperty(ObjectLiteral::Property* property) { |
3037 return property != NULL && | 3048 return property != NULL && |
3038 property->kind() != ObjectLiteral::Property::PROTOTYPE; | 3049 property->kind() != ObjectLiteral::Property::PROTOTYPE; |
3039 } | 3050 } |
3040 | 3051 |
3041 | 3052 |
(...skipping 257 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3299 } | 3310 } |
3300 FunctionLiteral* value = | 3311 FunctionLiteral* value = |
3301 ParseFunctionLiteral(name, | 3312 ParseFunctionLiteral(name, |
3302 false, // reserved words are allowed here | 3313 false, // reserved words are allowed here |
3303 RelocInfo::kNoPosition, | 3314 RelocInfo::kNoPosition, |
3304 DECLARATION, | 3315 DECLARATION, |
3305 CHECK_OK); | 3316 CHECK_OK); |
3306 // Allow any number of parameters for compatiabilty with JSC. | 3317 // Allow any number of parameters for compatiabilty with JSC. |
3307 // Specification only allows zero parameters for get and one for set. | 3318 // Specification only allows zero parameters for get and one for set. |
3308 ObjectLiteral::Property* property = | 3319 ObjectLiteral::Property* property = |
3309 new ObjectLiteral::Property(is_getter, value); | 3320 new(zone()) ObjectLiteral::Property(is_getter, value); |
3310 return property; | 3321 return property; |
3311 } else { | 3322 } else { |
3312 ReportUnexpectedToken(next); | 3323 ReportUnexpectedToken(next); |
3313 *ok = false; | 3324 *ok = false; |
3314 return NULL; | 3325 return NULL; |
3315 } | 3326 } |
3316 } | 3327 } |
3317 | 3328 |
3318 | 3329 |
3319 Expression* Parser::ParseObjectLiteral(bool* ok) { | 3330 Expression* Parser::ParseObjectLiteral(bool* ok) { |
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3365 if (peek() != Token::RBRACE) Expect(Token::COMMA, CHECK_OK); | 3376 if (peek() != Token::RBRACE) Expect(Token::COMMA, CHECK_OK); |
3366 | 3377 |
3367 if (fni_ != NULL) { | 3378 if (fni_ != NULL) { |
3368 fni_->Infer(); | 3379 fni_->Infer(); |
3369 fni_->Leave(); | 3380 fni_->Leave(); |
3370 } | 3381 } |
3371 continue; // restart the while | 3382 continue; // restart the while |
3372 } | 3383 } |
3373 // Failed to parse as get/set property, so it's just a property | 3384 // Failed to parse as get/set property, so it's just a property |
3374 // called "get" or "set". | 3385 // called "get" or "set". |
3375 key = new Literal(id); | 3386 key = new(zone()) Literal(id); |
3376 break; | 3387 break; |
3377 } | 3388 } |
3378 case Token::STRING: { | 3389 case Token::STRING: { |
3379 Consume(Token::STRING); | 3390 Consume(Token::STRING); |
3380 Handle<String> string = GetSymbol(CHECK_OK); | 3391 Handle<String> string = GetSymbol(CHECK_OK); |
3381 if (fni_ != NULL) fni_->PushLiteralName(string); | 3392 if (fni_ != NULL) fni_->PushLiteralName(string); |
3382 uint32_t index; | 3393 uint32_t index; |
3383 if (!string.is_null() && string->AsArrayIndex(&index)) { | 3394 if (!string.is_null() && string->AsArrayIndex(&index)) { |
3384 key = NewNumberLiteral(index); | 3395 key = NewNumberLiteral(index); |
3385 break; | 3396 break; |
3386 } | 3397 } |
3387 key = new Literal(string); | 3398 key = new(zone()) Literal(string); |
3388 break; | 3399 break; |
3389 } | 3400 } |
3390 case Token::NUMBER: { | 3401 case Token::NUMBER: { |
3391 Consume(Token::NUMBER); | 3402 Consume(Token::NUMBER); |
3392 ASSERT(scanner().is_literal_ascii()); | 3403 ASSERT(scanner().is_literal_ascii()); |
3393 double value = StringToDouble(scanner().literal_ascii_string(), | 3404 double value = StringToDouble(scanner().literal_ascii_string(), |
3394 ALLOW_HEX | ALLOW_OCTALS); | 3405 ALLOW_HEX | ALLOW_OCTALS); |
3395 key = NewNumberLiteral(value); | 3406 key = NewNumberLiteral(value); |
3396 break; | 3407 break; |
3397 } | 3408 } |
3398 default: | 3409 default: |
3399 if (Token::IsKeyword(next)) { | 3410 if (Token::IsKeyword(next)) { |
3400 Consume(next); | 3411 Consume(next); |
3401 Handle<String> string = GetSymbol(CHECK_OK); | 3412 Handle<String> string = GetSymbol(CHECK_OK); |
3402 key = new Literal(string); | 3413 key = new(zone()) Literal(string); |
3403 } else { | 3414 } else { |
3404 // Unexpected token. | 3415 // Unexpected token. |
3405 Token::Value next = Next(); | 3416 Token::Value next = Next(); |
3406 ReportUnexpectedToken(next); | 3417 ReportUnexpectedToken(next); |
3407 *ok = false; | 3418 *ok = false; |
3408 return NULL; | 3419 return NULL; |
3409 } | 3420 } |
3410 } | 3421 } |
3411 | 3422 |
3412 Expect(Token::COLON, CHECK_OK); | 3423 Expect(Token::COLON, CHECK_OK); |
3413 Expression* value = ParseAssignmentExpression(true, CHECK_OK); | 3424 Expression* value = ParseAssignmentExpression(true, CHECK_OK); |
3414 | 3425 |
3415 ObjectLiteral::Property* property = | 3426 ObjectLiteral::Property* property = |
3416 new ObjectLiteral::Property(key, value); | 3427 new(zone()) ObjectLiteral::Property(key, value); |
3417 | 3428 |
3418 // Mark object literals that contain function literals and pretenure the | 3429 // Mark object literals that contain function literals and pretenure the |
3419 // literal so it can be added as a constant function property. | 3430 // literal so it can be added as a constant function property. |
3420 if (value->AsFunctionLiteral() != NULL) { | 3431 if (value->AsFunctionLiteral() != NULL) { |
3421 has_function = true; | 3432 has_function = true; |
3422 value->AsFunctionLiteral()->set_pretenure(true); | 3433 value->AsFunctionLiteral()->set_pretenure(true); |
3423 } | 3434 } |
3424 | 3435 |
3425 // Count CONSTANT or COMPUTED properties to maintain the enumeration order. | 3436 // Count CONSTANT or COMPUTED properties to maintain the enumeration order. |
3426 if (IsBoilerplateProperty(property)) number_of_boilerplate_properties++; | 3437 if (IsBoilerplateProperty(property)) number_of_boilerplate_properties++; |
(...skipping 18 matching lines...) Expand all Loading... | |
3445 number_of_boilerplate_properties * 2, TENURED); | 3456 number_of_boilerplate_properties * 2, TENURED); |
3446 | 3457 |
3447 bool is_simple = true; | 3458 bool is_simple = true; |
3448 bool fast_elements = true; | 3459 bool fast_elements = true; |
3449 int depth = 1; | 3460 int depth = 1; |
3450 BuildObjectLiteralConstantProperties(properties, | 3461 BuildObjectLiteralConstantProperties(properties, |
3451 constant_properties, | 3462 constant_properties, |
3452 &is_simple, | 3463 &is_simple, |
3453 &fast_elements, | 3464 &fast_elements, |
3454 &depth); | 3465 &depth); |
3455 return new ObjectLiteral(constant_properties, | 3466 return new(zone()) ObjectLiteral(constant_properties, |
3456 properties, | 3467 properties, |
3457 literal_index, | 3468 literal_index, |
3458 is_simple, | 3469 is_simple, |
3459 fast_elements, | 3470 fast_elements, |
3460 depth, | 3471 depth, |
3461 has_function); | 3472 has_function); |
3462 } | 3473 } |
3463 | 3474 |
3464 | 3475 |
3465 Expression* Parser::ParseRegExpLiteral(bool seen_equal, bool* ok) { | 3476 Expression* Parser::ParseRegExpLiteral(bool seen_equal, bool* ok) { |
3466 if (!scanner().ScanRegExpPattern(seen_equal)) { | 3477 if (!scanner().ScanRegExpPattern(seen_equal)) { |
3467 Next(); | 3478 Next(); |
3468 ReportMessage("unterminated_regexp", Vector<const char*>::empty()); | 3479 ReportMessage("unterminated_regexp", Vector<const char*>::empty()); |
3469 *ok = false; | 3480 *ok = false; |
3470 return NULL; | 3481 return NULL; |
3471 } | 3482 } |
3472 | 3483 |
3473 int literal_index = lexical_scope_->NextMaterializedLiteralIndex(); | 3484 int literal_index = lexical_scope_->NextMaterializedLiteralIndex(); |
3474 | 3485 |
3475 Handle<String> js_pattern = NextLiteralString(TENURED); | 3486 Handle<String> js_pattern = NextLiteralString(TENURED); |
3476 scanner().ScanRegExpFlags(); | 3487 scanner().ScanRegExpFlags(); |
3477 Handle<String> js_flags = NextLiteralString(TENURED); | 3488 Handle<String> js_flags = NextLiteralString(TENURED); |
3478 Next(); | 3489 Next(); |
3479 | 3490 |
3480 return new RegExpLiteral(js_pattern, js_flags, literal_index); | 3491 return new(zone()) RegExpLiteral(js_pattern, js_flags, literal_index); |
3481 } | 3492 } |
3482 | 3493 |
3483 | 3494 |
3484 ZoneList<Expression*>* Parser::ParseArguments(bool* ok) { | 3495 ZoneList<Expression*>* Parser::ParseArguments(bool* ok) { |
3485 // Arguments :: | 3496 // Arguments :: |
3486 // '(' (AssignmentExpression)*[','] ')' | 3497 // '(' (AssignmentExpression)*[','] ')' |
3487 | 3498 |
3488 ZoneList<Expression*>* result = new ZoneList<Expression*>(4); | 3499 ZoneList<Expression*>* result = new ZoneList<Expression*>(4); |
3489 Expect(Token::LPAREN, CHECK_OK); | 3500 Expect(Token::LPAREN, CHECK_OK); |
3490 bool done = (peek() == Token::RPAREN); | 3501 bool done = (peek() == Token::RPAREN); |
(...skipping 82 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3573 // declaration to the body of the function with the name of the | 3584 // declaration to the body of the function with the name of the |
3574 // function and let it refer to the function itself (closure). | 3585 // function and let it refer to the function itself (closure). |
3575 // NOTE: We create a proxy and resolve it here so that in the | 3586 // NOTE: We create a proxy and resolve it here so that in the |
3576 // future we can change the AST to only refer to VariableProxies | 3587 // future we can change the AST to only refer to VariableProxies |
3577 // instead of Variables and Proxis as is the case now. | 3588 // instead of Variables and Proxis as is the case now. |
3578 if (!function_name.is_null() && function_name->length() > 0) { | 3589 if (!function_name.is_null() && function_name->length() > 0) { |
3579 Variable* fvar = top_scope_->DeclareFunctionVar(function_name); | 3590 Variable* fvar = top_scope_->DeclareFunctionVar(function_name); |
3580 VariableProxy* fproxy = | 3591 VariableProxy* fproxy = |
3581 top_scope_->NewUnresolved(function_name, inside_with()); | 3592 top_scope_->NewUnresolved(function_name, inside_with()); |
3582 fproxy->BindTo(fvar); | 3593 fproxy->BindTo(fvar); |
3583 body->Add(new ExpressionStatement( | 3594 body->Add(new(zone()) ExpressionStatement( |
3584 new Assignment(Token::INIT_CONST, fproxy, | 3595 new(zone()) Assignment(Token::INIT_CONST, fproxy, |
3585 new ThisFunction(), | 3596 new(zone()) ThisFunction(), |
3586 RelocInfo::kNoPosition))); | 3597 RelocInfo::kNoPosition))); |
3587 } | 3598 } |
3588 | 3599 |
3589 // Determine if the function will be lazily compiled. The mode can | 3600 // Determine if the function will be lazily compiled. The mode can |
3590 // only be PARSE_LAZILY if the --lazy flag is true. | 3601 // only be PARSE_LAZILY if the --lazy flag is true. |
3591 bool is_lazily_compiled = (mode() == PARSE_LAZILY && | 3602 bool is_lazily_compiled = (mode() == PARSE_LAZILY && |
3592 top_scope_->outer_scope()->is_global_scope() && | 3603 top_scope_->outer_scope()->is_global_scope() && |
3593 top_scope_->HasTrivialOuterContext() && | 3604 top_scope_->HasTrivialOuterContext() && |
3594 !parenthesized_function_); | 3605 !parenthesized_function_); |
3595 parenthesized_function_ = false; // The bit was set for this function only. | 3606 parenthesized_function_ = false; // The bit was set for this function only. |
(...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3669 if (reserved_loc.IsValid()) { | 3680 if (reserved_loc.IsValid()) { |
3670 ReportMessageAt(reserved_loc, "strict_reserved_word", | 3681 ReportMessageAt(reserved_loc, "strict_reserved_word", |
3671 Vector<const char*>::empty()); | 3682 Vector<const char*>::empty()); |
3672 *ok = false; | 3683 *ok = false; |
3673 return NULL; | 3684 return NULL; |
3674 } | 3685 } |
3675 CheckOctalLiteral(start_pos, end_pos, CHECK_OK); | 3686 CheckOctalLiteral(start_pos, end_pos, CHECK_OK); |
3676 } | 3687 } |
3677 | 3688 |
3678 FunctionLiteral* function_literal = | 3689 FunctionLiteral* function_literal = |
3679 new FunctionLiteral(name, | 3690 new(zone()) FunctionLiteral(name, |
3680 top_scope_, | 3691 top_scope_, |
3681 body, | 3692 body, |
3682 materialized_literal_count, | 3693 materialized_literal_count, |
3683 expected_property_count, | 3694 expected_property_count, |
3684 only_simple_this_property_assignments, | 3695 only_simple_this_property_assignments, |
3685 this_property_assignments, | 3696 this_property_assignments, |
3686 num_parameters, | 3697 num_parameters, |
3687 start_pos, | 3698 start_pos, |
3688 end_pos, | 3699 end_pos, |
3689 function_name->length() > 0, | 3700 function_name->length() > 0, |
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3731 // Check that the expected number of arguments are being passed. | 3742 // Check that the expected number of arguments are being passed. |
3732 if (function != NULL && | 3743 if (function != NULL && |
3733 function->nargs != -1 && | 3744 function->nargs != -1 && |
3734 function->nargs != args->length()) { | 3745 function->nargs != args->length()) { |
3735 ReportMessage("illegal_access", Vector<const char*>::empty()); | 3746 ReportMessage("illegal_access", Vector<const char*>::empty()); |
3736 *ok = false; | 3747 *ok = false; |
3737 return NULL; | 3748 return NULL; |
3738 } | 3749 } |
3739 | 3750 |
3740 // We have a valid intrinsics call or a call to a builtin. | 3751 // We have a valid intrinsics call or a call to a builtin. |
3741 return new CallRuntime(name, function, args); | 3752 return new(zone()) CallRuntime(name, function, args); |
3742 } | 3753 } |
3743 | 3754 |
3744 | 3755 |
3745 bool Parser::peek_any_identifier() { | 3756 bool Parser::peek_any_identifier() { |
3746 Token::Value next = peek(); | 3757 Token::Value next = peek(); |
3747 return next == Token::IDENTIFIER || | 3758 return next == Token::IDENTIFIER || |
3748 next == Token::FUTURE_RESERVED_WORD; | 3759 next == Token::FUTURE_RESERVED_WORD; |
3749 } | 3760 } |
3750 | 3761 |
3751 | 3762 |
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3786 if (scanner().has_line_terminator_before_next() || | 3797 if (scanner().has_line_terminator_before_next() || |
3787 tok == Token::RBRACE || | 3798 tok == Token::RBRACE || |
3788 tok == Token::EOS) { | 3799 tok == Token::EOS) { |
3789 return; | 3800 return; |
3790 } | 3801 } |
3791 Expect(Token::SEMICOLON, ok); | 3802 Expect(Token::SEMICOLON, ok); |
3792 } | 3803 } |
3793 | 3804 |
3794 | 3805 |
3795 Literal* Parser::GetLiteralUndefined() { | 3806 Literal* Parser::GetLiteralUndefined() { |
3796 return new Literal(isolate()->factory()->undefined_value()); | 3807 return new(zone()) Literal(isolate()->factory()->undefined_value()); |
3797 } | 3808 } |
3798 | 3809 |
3799 | 3810 |
3800 Literal* Parser::GetLiteralTheHole() { | 3811 Literal* Parser::GetLiteralTheHole() { |
3801 return new Literal(isolate()->factory()->the_hole_value()); | 3812 return new(zone()) Literal(isolate()->factory()->the_hole_value()); |
3802 } | 3813 } |
3803 | 3814 |
3804 | 3815 |
3805 Literal* Parser::GetLiteralNumber(double value) { | 3816 Literal* Parser::GetLiteralNumber(double value) { |
3806 return NewNumberLiteral(value); | 3817 return NewNumberLiteral(value); |
3807 } | 3818 } |
3808 | 3819 |
3809 | 3820 |
3810 Handle<String> Parser::ParseIdentifier(bool* ok) { | 3821 Handle<String> Parser::ParseIdentifier(bool* ok) { |
3811 bool is_reserved; | 3822 bool is_reserved; |
(...skipping 127 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3939 // target stack has been used from the top of the target stack. Add | 3950 // target stack has been used from the top of the target stack. Add |
3940 // the break target to any TargetCollectors passed on the stack. | 3951 // the break target to any TargetCollectors passed on the stack. |
3941 for (Target* t = target_stack_; t != stop; t = t->previous()) { | 3952 for (Target* t = target_stack_; t != stop; t = t->previous()) { |
3942 TargetCollector* collector = t->node()->AsTargetCollector(); | 3953 TargetCollector* collector = t->node()->AsTargetCollector(); |
3943 if (collector != NULL) collector->AddTarget(target); | 3954 if (collector != NULL) collector->AddTarget(target); |
3944 } | 3955 } |
3945 } | 3956 } |
3946 | 3957 |
3947 | 3958 |
3948 Literal* Parser::NewNumberLiteral(double number) { | 3959 Literal* Parser::NewNumberLiteral(double number) { |
3949 return new Literal(isolate()->factory()->NewNumber(number, TENURED)); | 3960 return new(zone()) Literal(isolate()->factory()->NewNumber(number, TENURED)); |
3950 } | 3961 } |
3951 | 3962 |
3952 | 3963 |
3953 Expression* Parser::NewThrowReferenceError(Handle<String> type) { | 3964 Expression* Parser::NewThrowReferenceError(Handle<String> type) { |
3954 return NewThrowError(isolate()->factory()->MakeReferenceError_symbol(), | 3965 return NewThrowError(isolate()->factory()->MakeReferenceError_symbol(), |
3955 type, HandleVector<Object>(NULL, 0)); | 3966 type, HandleVector<Object>(NULL, 0)); |
3956 } | 3967 } |
3957 | 3968 |
3958 | 3969 |
3959 Expression* Parser::NewThrowSyntaxError(Handle<String> type, | 3970 Expression* Parser::NewThrowSyntaxError(Handle<String> type, |
(...skipping 26 matching lines...) Expand all Loading... | |
3986 for (int i = 0; i < argc; i++) { | 3997 for (int i = 0; i < argc; i++) { |
3987 Handle<Object> element = arguments[i]; | 3998 Handle<Object> element = arguments[i]; |
3988 if (!element.is_null()) { | 3999 if (!element.is_null()) { |
3989 elements->set(i, *element); | 4000 elements->set(i, *element); |
3990 } | 4001 } |
3991 } | 4002 } |
3992 Handle<JSArray> array = isolate()->factory()->NewJSArrayWithElements(elements, | 4003 Handle<JSArray> array = isolate()->factory()->NewJSArrayWithElements(elements, |
3993 TENURED); | 4004 TENURED); |
3994 | 4005 |
3995 ZoneList<Expression*>* args = new ZoneList<Expression*>(2); | 4006 ZoneList<Expression*>* args = new ZoneList<Expression*>(2); |
3996 args->Add(new Literal(type)); | 4007 args->Add(new(zone()) Literal(type)); |
3997 args->Add(new Literal(array)); | 4008 args->Add(new(zone()) Literal(array)); |
3998 return new Throw(new CallRuntime(constructor, NULL, args), | 4009 return new(zone()) Throw(new(zone()) CallRuntime(constructor, NULL, args), |
3999 scanner().location().beg_pos); | 4010 scanner().location().beg_pos); |
4000 } | 4011 } |
4001 | 4012 |
4002 // ---------------------------------------------------------------------------- | 4013 // ---------------------------------------------------------------------------- |
4003 // JSON | 4014 // JSON |
4004 | 4015 |
4005 Handle<Object> JsonParser::ParseJson(Handle<String> script, | 4016 Handle<Object> JsonParser::ParseJson(Handle<String> script, |
4006 UC16CharacterStream* source) { | 4017 UC16CharacterStream* source) { |
4007 scanner_.Initialize(source); | 4018 scanner_.Initialize(source); |
4008 stack_overflow_ = false; | 4019 stack_overflow_ = false; |
(...skipping 302 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
4311 | 4322 |
4312 int capture_index = stored_state->capture_index(); | 4323 int capture_index = stored_state->capture_index(); |
4313 SubexpressionType type = stored_state->group_type(); | 4324 SubexpressionType type = stored_state->group_type(); |
4314 | 4325 |
4315 // Restore previous state. | 4326 // Restore previous state. |
4316 stored_state = stored_state->previous_state(); | 4327 stored_state = stored_state->previous_state(); |
4317 builder = stored_state->builder(); | 4328 builder = stored_state->builder(); |
4318 | 4329 |
4319 // Build result of subexpression. | 4330 // Build result of subexpression. |
4320 if (type == CAPTURE) { | 4331 if (type == CAPTURE) { |
4321 RegExpCapture* capture = new RegExpCapture(body, capture_index); | 4332 RegExpCapture* capture = new(zone()) RegExpCapture(body, capture_index); |
4322 captures_->at(capture_index - 1) = capture; | 4333 captures_->at(capture_index - 1) = capture; |
4323 body = capture; | 4334 body = capture; |
4324 } else if (type != GROUPING) { | 4335 } else if (type != GROUPING) { |
4325 ASSERT(type == POSITIVE_LOOKAHEAD || type == NEGATIVE_LOOKAHEAD); | 4336 ASSERT(type == POSITIVE_LOOKAHEAD || type == NEGATIVE_LOOKAHEAD); |
4326 bool is_positive = (type == POSITIVE_LOOKAHEAD); | 4337 bool is_positive = (type == POSITIVE_LOOKAHEAD); |
4327 body = new RegExpLookahead(body, | 4338 body = new(zone()) RegExpLookahead(body, |
4328 is_positive, | 4339 is_positive, |
4329 end_capture_index - capture_index, | 4340 end_capture_index - capture_index, |
4330 capture_index); | 4341 capture_index); |
4331 } | 4342 } |
4332 builder->AddAtom(body); | 4343 builder->AddAtom(body); |
4333 // For compatability with JSC and ES3, we allow quantifiers after | 4344 // For compatability with JSC and ES3, we allow quantifiers after |
4334 // lookaheads, and break in all cases. | 4345 // lookaheads, and break in all cases. |
4335 break; | 4346 break; |
4336 } | 4347 } |
4337 case '|': { | 4348 case '|': { |
4338 Advance(); | 4349 Advance(); |
4339 builder->NewAlternative(); | 4350 builder->NewAlternative(); |
4340 continue; | 4351 continue; |
4341 } | 4352 } |
4342 case '*': | 4353 case '*': |
4343 case '+': | 4354 case '+': |
4344 case '?': | 4355 case '?': |
4345 return ReportError(CStrVector("Nothing to repeat")); | 4356 return ReportError(CStrVector("Nothing to repeat")); |
4346 case '^': { | 4357 case '^': { |
4347 Advance(); | 4358 Advance(); |
4348 if (multiline_) { | 4359 if (multiline_) { |
4349 builder->AddAssertion( | 4360 builder->AddAssertion( |
4350 new RegExpAssertion(RegExpAssertion::START_OF_LINE)); | 4361 new(zone()) RegExpAssertion(RegExpAssertion::START_OF_LINE)); |
4351 } else { | 4362 } else { |
4352 builder->AddAssertion( | 4363 builder->AddAssertion( |
4353 new RegExpAssertion(RegExpAssertion::START_OF_INPUT)); | 4364 new(zone()) RegExpAssertion(RegExpAssertion::START_OF_INPUT)); |
4354 set_contains_anchor(); | 4365 set_contains_anchor(); |
4355 } | 4366 } |
4356 continue; | 4367 continue; |
4357 } | 4368 } |
4358 case '$': { | 4369 case '$': { |
4359 Advance(); | 4370 Advance(); |
4360 RegExpAssertion::Type type = | 4371 RegExpAssertion::Type type = |
4361 multiline_ ? RegExpAssertion::END_OF_LINE : | 4372 multiline_ ? RegExpAssertion::END_OF_LINE : |
4362 RegExpAssertion::END_OF_INPUT; | 4373 RegExpAssertion::END_OF_INPUT; |
4363 builder->AddAssertion(new RegExpAssertion(type)); | 4374 builder->AddAssertion(new(zone()) RegExpAssertion(type)); |
4364 continue; | 4375 continue; |
4365 } | 4376 } |
4366 case '.': { | 4377 case '.': { |
4367 Advance(); | 4378 Advance(); |
4368 // everything except \x0a, \x0d, \u2028 and \u2029 | 4379 // everything except \x0a, \x0d, \u2028 and \u2029 |
4369 ZoneList<CharacterRange>* ranges = new ZoneList<CharacterRange>(2); | 4380 ZoneList<CharacterRange>* ranges = new ZoneList<CharacterRange>(2); |
4370 CharacterRange::AddClassEscape('.', ranges); | 4381 CharacterRange::AddClassEscape('.', ranges); |
4371 RegExpTree* atom = new RegExpCharacterClass(ranges, false); | 4382 RegExpTree* atom = new(zone()) RegExpCharacterClass(ranges, false); |
4372 builder->AddAtom(atom); | 4383 builder->AddAtom(atom); |
4373 break; | 4384 break; |
4374 } | 4385 } |
4375 case '(': { | 4386 case '(': { |
4376 SubexpressionType type = CAPTURE; | 4387 SubexpressionType type = CAPTURE; |
4377 Advance(); | 4388 Advance(); |
4378 if (current() == '?') { | 4389 if (current() == '?') { |
4379 switch (Next()) { | 4390 switch (Next()) { |
4380 case ':': | 4391 case ':': |
4381 type = GROUPING; | 4392 type = GROUPING; |
(...skipping 12 matching lines...) Expand all Loading... | |
4394 } else { | 4405 } else { |
4395 if (captures_ == NULL) { | 4406 if (captures_ == NULL) { |
4396 captures_ = new ZoneList<RegExpCapture*>(2); | 4407 captures_ = new ZoneList<RegExpCapture*>(2); |
4397 } | 4408 } |
4398 if (captures_started() >= kMaxCaptures) { | 4409 if (captures_started() >= kMaxCaptures) { |
4399 ReportError(CStrVector("Too many captures") CHECK_FAILED); | 4410 ReportError(CStrVector("Too many captures") CHECK_FAILED); |
4400 } | 4411 } |
4401 captures_->Add(NULL); | 4412 captures_->Add(NULL); |
4402 } | 4413 } |
4403 // Store current state and begin new disjunction parsing. | 4414 // Store current state and begin new disjunction parsing. |
4404 stored_state = new RegExpParserState(stored_state, | 4415 stored_state = new(zone()) RegExpParserState(stored_state, |
4405 type, | 4416 type, |
4406 captures_started()); | 4417 captures_started()); |
4407 builder = stored_state->builder(); | 4418 builder = stored_state->builder(); |
4408 continue; | 4419 continue; |
4409 } | 4420 } |
4410 case '[': { | 4421 case '[': { |
4411 RegExpTree* atom = ParseCharacterClass(CHECK_FAILED); | 4422 RegExpTree* atom = ParseCharacterClass(CHECK_FAILED); |
4412 builder->AddAtom(atom); | 4423 builder->AddAtom(atom); |
4413 break; | 4424 break; |
4414 } | 4425 } |
4415 // Atom :: | 4426 // Atom :: |
4416 // \ AtomEscape | 4427 // \ AtomEscape |
4417 case '\\': | 4428 case '\\': |
4418 switch (Next()) { | 4429 switch (Next()) { |
4419 case kEndMarker: | 4430 case kEndMarker: |
4420 return ReportError(CStrVector("\\ at end of pattern")); | 4431 return ReportError(CStrVector("\\ at end of pattern")); |
4421 case 'b': | 4432 case 'b': |
4422 Advance(2); | 4433 Advance(2); |
4423 builder->AddAssertion( | 4434 builder->AddAssertion( |
4424 new RegExpAssertion(RegExpAssertion::BOUNDARY)); | 4435 new(zone()) RegExpAssertion(RegExpAssertion::BOUNDARY)); |
4425 continue; | 4436 continue; |
4426 case 'B': | 4437 case 'B': |
4427 Advance(2); | 4438 Advance(2); |
4428 builder->AddAssertion( | 4439 builder->AddAssertion( |
4429 new RegExpAssertion(RegExpAssertion::NON_BOUNDARY)); | 4440 new(zone()) RegExpAssertion(RegExpAssertion::NON_BOUNDARY)); |
4430 continue; | 4441 continue; |
4431 // AtomEscape :: | 4442 // AtomEscape :: |
4432 // CharacterClassEscape | 4443 // CharacterClassEscape |
4433 // | 4444 // |
4434 // CharacterClassEscape :: one of | 4445 // CharacterClassEscape :: one of |
4435 // d D s S w W | 4446 // d D s S w W |
4436 case 'd': case 'D': case 's': case 'S': case 'w': case 'W': { | 4447 case 'd': case 'D': case 's': case 'S': case 'w': case 'W': { |
4437 uc32 c = Next(); | 4448 uc32 c = Next(); |
4438 Advance(2); | 4449 Advance(2); |
4439 ZoneList<CharacterRange>* ranges = new ZoneList<CharacterRange>(2); | 4450 ZoneList<CharacterRange>* ranges = new ZoneList<CharacterRange>(2); |
4440 CharacterRange::AddClassEscape(c, ranges); | 4451 CharacterRange::AddClassEscape(c, ranges); |
4441 RegExpTree* atom = new RegExpCharacterClass(ranges, false); | 4452 RegExpTree* atom = new(zone()) RegExpCharacterClass(ranges, false); |
4442 builder->AddAtom(atom); | 4453 builder->AddAtom(atom); |
4443 break; | 4454 break; |
4444 } | 4455 } |
4445 case '1': case '2': case '3': case '4': case '5': case '6': | 4456 case '1': case '2': case '3': case '4': case '5': case '6': |
4446 case '7': case '8': case '9': { | 4457 case '7': case '8': case '9': { |
4447 int index = 0; | 4458 int index = 0; |
4448 if (ParseBackReferenceIndex(&index)) { | 4459 if (ParseBackReferenceIndex(&index)) { |
4449 RegExpCapture* capture = NULL; | 4460 RegExpCapture* capture = NULL; |
4450 if (captures_ != NULL && index <= captures_->length()) { | 4461 if (captures_ != NULL && index <= captures_->length()) { |
4451 capture = captures_->at(index - 1); | 4462 capture = captures_->at(index - 1); |
4452 } | 4463 } |
4453 if (capture == NULL) { | 4464 if (capture == NULL) { |
4454 builder->AddEmpty(); | 4465 builder->AddEmpty(); |
4455 break; | 4466 break; |
4456 } | 4467 } |
4457 RegExpTree* atom = new RegExpBackReference(capture); | 4468 RegExpTree* atom = new(zone()) RegExpBackReference(capture); |
4458 builder->AddAtom(atom); | 4469 builder->AddAtom(atom); |
4459 break; | 4470 break; |
4460 } | 4471 } |
4461 uc32 first_digit = Next(); | 4472 uc32 first_digit = Next(); |
4462 if (first_digit == '8' || first_digit == '9') { | 4473 if (first_digit == '8' || first_digit == '9') { |
4463 // Treat as identity escape | 4474 // Treat as identity escape |
4464 builder->AddCharacter(first_digit); | 4475 builder->AddCharacter(first_digit); |
4465 Advance(2); | 4476 Advance(2); |
4466 break; | 4477 break; |
4467 } | 4478 } |
(...skipping 497 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
4965 } | 4976 } |
4966 } | 4977 } |
4967 if (!has_more()) { | 4978 if (!has_more()) { |
4968 return ReportError(CStrVector(kUnterminated) CHECK_FAILED); | 4979 return ReportError(CStrVector(kUnterminated) CHECK_FAILED); |
4969 } | 4980 } |
4970 Advance(); | 4981 Advance(); |
4971 if (ranges->length() == 0) { | 4982 if (ranges->length() == 0) { |
4972 ranges->Add(CharacterRange::Everything()); | 4983 ranges->Add(CharacterRange::Everything()); |
4973 is_negated = !is_negated; | 4984 is_negated = !is_negated; |
4974 } | 4985 } |
4975 return new RegExpCharacterClass(ranges, is_negated); | 4986 return new(zone()) RegExpCharacterClass(ranges, is_negated); |
4976 } | 4987 } |
4977 | 4988 |
4978 | 4989 |
4979 // ---------------------------------------------------------------------------- | 4990 // ---------------------------------------------------------------------------- |
4980 // The Parser interface. | 4991 // The Parser interface. |
4981 | 4992 |
4982 ParserMessage::~ParserMessage() { | 4993 ParserMessage::~ParserMessage() { |
4983 for (int i = 0; i < args().length(); i++) | 4994 for (int i = 0; i < args().length(); i++) |
4984 DeleteArray(args()[i]); | 4995 DeleteArray(args()[i]); |
4985 DeleteArray(args().start()); | 4996 DeleteArray(args().start()); |
(...skipping 162 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
5148 info->is_global(), | 5159 info->is_global(), |
5149 info->StrictMode()); | 5160 info->StrictMode()); |
5150 } | 5161 } |
5151 } | 5162 } |
5152 | 5163 |
5153 info->SetFunction(result); | 5164 info->SetFunction(result); |
5154 return (result != NULL); | 5165 return (result != NULL); |
5155 } | 5166 } |
5156 | 5167 |
5157 } } // namespace v8::internal | 5168 } } // namespace v8::internal |
OLD | NEW |