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

Side by Side Diff: src/parser.cc

Issue 6714040: Merge TemporaryScope with LexicalScope. (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Created 9 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« src/parser.h ('K') | « src/parser.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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 228 matching lines...) Expand 10 before | Expand all | Expand 10 after
239 } else { 239 } else {
240 // Only call immediately after adding an atom or character! 240 // Only call immediately after adding an atom or character!
241 UNREACHABLE(); 241 UNREACHABLE();
242 return; 242 return;
243 } 243 }
244 terms_.Add(new RegExpQuantifier(min, max, type, atom)); 244 terms_.Add(new RegExpQuantifier(min, max, type, atom));
245 LAST(ADD_TERM); 245 LAST(ADD_TERM);
246 } 246 }
247 247
248 248
249 // A temporary scope stores information during parsing, just like
250 // a plain scope. However, temporary scopes are not kept around
251 // after parsing or referenced by syntax trees so they can be stack-
252 // allocated and hence used by the pre-parser.
253 class TemporaryScope BASE_EMBEDDED {
254 public:
255 explicit TemporaryScope(TemporaryScope** variable);
256 ~TemporaryScope();
257
258 int NextMaterializedLiteralIndex() {
259 int next_index =
260 materialized_literal_count_ + JSFunction::kLiteralsPrefixSize;
261 materialized_literal_count_++;
262 return next_index;
263 }
264 int materialized_literal_count() { return materialized_literal_count_; }
265
266 void SetThisPropertyAssignmentInfo(
267 bool only_simple_this_property_assignments,
268 Handle<FixedArray> this_property_assignments) {
269 only_simple_this_property_assignments_ =
270 only_simple_this_property_assignments;
271 this_property_assignments_ = this_property_assignments;
272 }
273 bool only_simple_this_property_assignments() {
274 return only_simple_this_property_assignments_;
275 }
276 Handle<FixedArray> this_property_assignments() {
277 return this_property_assignments_;
278 }
279
280 void AddProperty() { expected_property_count_++; }
281 int expected_property_count() { return expected_property_count_; }
282
283 void AddLoop() { loop_count_++; }
284 bool ContainsLoops() const { return loop_count_ > 0; }
285
286 private:
287 // Captures the number of literals that need materialization in the
288 // function. Includes regexp literals, and boilerplate for object
289 // and array literals.
290 int materialized_literal_count_;
291
292 // Properties count estimation.
293 int expected_property_count_;
294
295 // Keeps track of assignments to properties of this. Used for
296 // optimizing constructors.
297 bool only_simple_this_property_assignments_;
298 Handle<FixedArray> this_property_assignments_;
299
300 // Captures the number of loops inside the scope.
301 int loop_count_;
302
303 // Bookkeeping
304 TemporaryScope** variable_;
305 TemporaryScope* parent_;
306 };
307
308
309 TemporaryScope::TemporaryScope(TemporaryScope** variable)
310 : materialized_literal_count_(0),
311 expected_property_count_(0),
312 only_simple_this_property_assignments_(false),
313 this_property_assignments_(
314 Isolate::Current()->factory()->empty_fixed_array()),
315 loop_count_(0),
316 variable_(variable),
317 parent_(*variable) {
318 *variable = this;
319 }
320
321
322 TemporaryScope::~TemporaryScope() {
323 *variable_ = parent_;
324 }
325
326
327 Handle<String> Parser::LookupSymbol(int symbol_id) { 249 Handle<String> Parser::LookupSymbol(int symbol_id) {
328 // Length of symbol cache is the number of identified symbols. 250 // Length of symbol cache is the number of identified symbols.
329 // If we are larger than that, or negative, it's not a cached symbol. 251 // If we are larger than that, or negative, it's not a cached symbol.
330 // This might also happen if there is no preparser symbol data, even 252 // This might also happen if there is no preparser symbol data, even
331 // if there is some preparser data. 253 // if there is some preparser data.
332 if (static_cast<unsigned>(symbol_id) 254 if (static_cast<unsigned>(symbol_id)
333 >= static_cast<unsigned>(symbol_cache_.length())) { 255 >= static_cast<unsigned>(symbol_cache_.length())) {
334 if (scanner().is_literal_ascii()) { 256 if (scanner().is_literal_ascii()) {
335 return isolate()->factory()->LookupAsciiSymbol( 257 return isolate()->factory()->LookupAsciiSymbol(
336 scanner().literal_ascii_string()); 258 scanner().literal_ascii_string());
(...skipping 195 matching lines...) Expand 10 before | Expand all | Expand 10 after
532 private: 454 private:
533 Target** variable_; 455 Target** variable_;
534 Target* previous_; 456 Target* previous_;
535 }; 457 };
536 458
537 459
538 // ---------------------------------------------------------------------------- 460 // ----------------------------------------------------------------------------
539 // LexicalScope is a support class to facilitate manipulation of the 461 // LexicalScope is a support class to facilitate manipulation of the
540 // Parser's scope stack. The constructor sets the parser's top scope 462 // Parser's scope stack. The constructor sets the parser's top scope
541 // to the incoming scope, and the destructor resets it. 463 // to the incoming scope, and the destructor resets it.
464 //
465 // Additionlaly, it stores transient information used during parsing.
466 // These scopes are not kept around after parsing or referenced by syntax
467 // trees so they can be stack-allocated and hence used by the pre-parser.
542 468
543 class LexicalScope BASE_EMBEDDED { 469 class LexicalScope BASE_EMBEDDED {
544 public: 470 public:
545 LexicalScope(Scope** scope_variable, 471 LexicalScope(Parser* parser, Scope* scope);
546 int* with_nesting_level_variable, 472 ~LexicalScope();
547 Scope* scope) 473
548 : scope_variable_(scope_variable), 474 int NextMaterializedLiteralIndex() {
549 with_nesting_level_variable_(with_nesting_level_variable), 475 int next_index =
550 prev_scope_(*scope_variable), 476 materialized_literal_count_ + JSFunction::kLiteralsPrefixSize;
551 prev_level_(*with_nesting_level_variable) { 477 materialized_literal_count_++;
552 *scope_variable = scope; 478 return next_index;
553 *with_nesting_level_variable = 0; 479 }
480 int materialized_literal_count() { return materialized_literal_count_; }
481
482 void SetThisPropertyAssignmentInfo(
483 bool only_simple_this_property_assignments,
484 Handle<FixedArray> this_property_assignments) {
485 only_simple_this_property_assignments_ =
486 only_simple_this_property_assignments;
487 this_property_assignments_ = this_property_assignments;
488 }
489 bool only_simple_this_property_assignments() {
490 return only_simple_this_property_assignments_;
491 }
492 Handle<FixedArray> this_property_assignments() {
493 return this_property_assignments_;
554 } 494 }
555 495
556 ~LexicalScope() { 496 void AddProperty() { expected_property_count_++; }
557 (*scope_variable_)->Leave(); 497 int expected_property_count() { return expected_property_count_; }
558 *scope_variable_ = prev_scope_; 498
559 *with_nesting_level_variable_ = prev_level_; 499 void AddLoop() { loop_count_++; }
560 } 500 bool ContainsLoops() const { return loop_count_ > 0; }
561 501
562 private: 502 private:
563 Scope** scope_variable_; 503 // Captures the number of literals that need materialization in the
564 int* with_nesting_level_variable_; 504 // function. Includes regexp literals, and boilerplate for object
565 Scope* prev_scope_; 505 // and array literals.
566 int prev_level_; 506 int materialized_literal_count_;
507
508 // Properties count estimation.
509 int expected_property_count_;
510
511 // Keeps track of assignments to properties of this. Used for
512 // optimizing constructors.
513 bool only_simple_this_property_assignments_;
514 Handle<FixedArray> this_property_assignments_;
515
516 // Captures the number of loops inside the scope.
517 int loop_count_;
518
519 // Bookkeeping
520 Parser* parser_;
521 // Previous values
522 LexicalScope* lexical_scope_parent_;
523 Scope* previous_scope_;
524 int previous_with_nesting_level_;
567 }; 525 };
568 526
527
528 LexicalScope::LexicalScope(Parser* parser, Scope* scope)
529 : materialized_literal_count_(0),
530 expected_property_count_(0),
531 only_simple_this_property_assignments_(false),
532 this_property_assignments_(
533 Isolate::Current()->factory()->empty_fixed_array()),
534 loop_count_(0),
535 parser_(parser),
536 lexical_scope_parent_(parser->lexical_scope_),
537 previous_scope_(parser->top_scope_),
538 previous_with_nesting_level_(parser->with_nesting_level_) {
539 parser->top_scope_ = scope;
540 parser->lexical_scope_ = this;
541 parser->with_nesting_level_ = 0;
542 }
543
544
545 LexicalScope::~LexicalScope() {
546 parser_->top_scope_->Leave();
547 parser_->top_scope_ = previous_scope_;
548 parser_->lexical_scope_ = lexical_scope_parent_;
549 parser_->with_nesting_level_ = previous_with_nesting_level_;
550 }
551
552
569 // ---------------------------------------------------------------------------- 553 // ----------------------------------------------------------------------------
570 // The CHECK_OK macro is a convenient macro to enforce error 554 // The CHECK_OK macro is a convenient macro to enforce error
571 // handling for functions that may fail (by returning !*ok). 555 // handling for functions that may fail (by returning !*ok).
572 // 556 //
573 // CAUTION: This macro appends extra statements after a call, 557 // CAUTION: This macro appends extra statements after a call,
574 // thus it must never be used where only a single statement 558 // thus it must never be used where only a single statement
575 // is correct (e.g. an if statement branch w/o braces)! 559 // is correct (e.g. an if statement branch w/o braces)!
576 560
577 #define CHECK_OK ok); \ 561 #define CHECK_OK ok); \
578 if (!*ok) return NULL; \ 562 if (!*ok) return NULL; \
(...skipping 13 matching lines...) Expand all
592 Parser::Parser(Handle<Script> script, 576 Parser::Parser(Handle<Script> script,
593 bool allow_natives_syntax, 577 bool allow_natives_syntax,
594 v8::Extension* extension, 578 v8::Extension* extension,
595 ScriptDataImpl* pre_data) 579 ScriptDataImpl* pre_data)
596 : isolate_(script->GetIsolate()), 580 : isolate_(script->GetIsolate()),
597 symbol_cache_(pre_data ? pre_data->symbol_count() : 0), 581 symbol_cache_(pre_data ? pre_data->symbol_count() : 0),
598 script_(script), 582 script_(script),
599 scanner_(isolate_), 583 scanner_(isolate_),
600 top_scope_(NULL), 584 top_scope_(NULL),
601 with_nesting_level_(0), 585 with_nesting_level_(0),
602 temp_scope_(NULL), 586 lexical_scope_(NULL),
603 target_stack_(NULL), 587 target_stack_(NULL),
604 allow_natives_syntax_(allow_natives_syntax), 588 allow_natives_syntax_(allow_natives_syntax),
605 extension_(extension), 589 extension_(extension),
606 pre_data_(pre_data), 590 pre_data_(pre_data),
607 fni_(NULL), 591 fni_(NULL),
608 stack_overflow_(false), 592 stack_overflow_(false),
609 parenthesized_function_(false) { 593 parenthesized_function_(false) {
610 AstNode::ResetIds(); 594 AstNode::ResetIds();
611 } 595 }
612 596
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after
650 if (allow_natives_syntax_ || extension_ != NULL) mode_ = PARSE_EAGERLY; 634 if (allow_natives_syntax_ || extension_ != NULL) mode_ = PARSE_EAGERLY;
651 635
652 Scope::Type type = 636 Scope::Type type =
653 in_global_context 637 in_global_context
654 ? Scope::GLOBAL_SCOPE 638 ? Scope::GLOBAL_SCOPE
655 : Scope::EVAL_SCOPE; 639 : Scope::EVAL_SCOPE;
656 Handle<String> no_name = isolate()->factory()->empty_symbol(); 640 Handle<String> no_name = isolate()->factory()->empty_symbol();
657 641
658 FunctionLiteral* result = NULL; 642 FunctionLiteral* result = NULL;
659 { Scope* scope = NewScope(top_scope_, type, inside_with()); 643 { Scope* scope = NewScope(top_scope_, type, inside_with());
660 LexicalScope lexical_scope(&this->top_scope_, &this->with_nesting_level_, 644 LexicalScope lexical_scope(this, scope);
661 scope);
662 TemporaryScope temp_scope(&this->temp_scope_);
663 if (strict_mode == kStrictMode) { 645 if (strict_mode == kStrictMode) {
664 top_scope_->EnableStrictMode(); 646 top_scope_->EnableStrictMode();
665 } 647 }
666 ZoneList<Statement*>* body = new ZoneList<Statement*>(16); 648 ZoneList<Statement*>* body = new ZoneList<Statement*>(16);
667 bool ok = true; 649 bool ok = true;
668 int beg_loc = scanner().location().beg_pos; 650 int beg_loc = scanner().location().beg_pos;
669 ParseSourceElements(body, Token::EOS, &ok); 651 ParseSourceElements(body, Token::EOS, &ok);
670 if (ok && top_scope_->is_strict_mode()) { 652 if (ok && top_scope_->is_strict_mode()) {
671 CheckOctalLiteral(beg_loc, scanner().location().end_pos, &ok); 653 CheckOctalLiteral(beg_loc, scanner().location().end_pos, &ok);
672 } 654 }
673 if (ok) { 655 if (ok) {
674 result = new FunctionLiteral( 656 result = new FunctionLiteral(
675 no_name, 657 no_name,
676 top_scope_, 658 top_scope_,
677 body, 659 body,
678 temp_scope.materialized_literal_count(), 660 lexical_scope.materialized_literal_count(),
679 temp_scope.expected_property_count(), 661 lexical_scope.expected_property_count(),
680 temp_scope.only_simple_this_property_assignments(), 662 lexical_scope.only_simple_this_property_assignments(),
681 temp_scope.this_property_assignments(), 663 lexical_scope.this_property_assignments(),
682 0, 664 0,
683 0, 665 0,
684 source->length(), 666 source->length(),
685 false, 667 false,
686 temp_scope.ContainsLoops()); 668 lexical_scope.ContainsLoops());
687 } else if (stack_overflow_) { 669 } else if (stack_overflow_) {
688 isolate()->StackOverflow(); 670 isolate()->StackOverflow();
689 } 671 }
690 } 672 }
691 673
692 // Make sure the target stack is empty. 674 // Make sure the target stack is empty.
693 ASSERT(target_stack_ == NULL); 675 ASSERT(target_stack_ == NULL);
694 676
695 // If there was a syntax error we have to get rid of the AST 677 // If there was a syntax error we have to get rid of the AST
696 // and it is not safe to do so before the scope has been deleted. 678 // and it is not safe to do so before the scope has been deleted.
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after
740 // Place holder for the result. 722 // Place holder for the result.
741 FunctionLiteral* result = NULL; 723 FunctionLiteral* result = NULL;
742 724
743 { 725 {
744 // Parse the function literal. 726 // Parse the function literal.
745 Handle<String> no_name = isolate()->factory()->empty_symbol(); 727 Handle<String> no_name = isolate()->factory()->empty_symbol();
746 Scope* scope = NewScope(top_scope_, Scope::GLOBAL_SCOPE, inside_with()); 728 Scope* scope = NewScope(top_scope_, Scope::GLOBAL_SCOPE, inside_with());
747 if (!info->closure().is_null()) { 729 if (!info->closure().is_null()) {
748 scope = Scope::DeserializeScopeChain(info, scope); 730 scope = Scope::DeserializeScopeChain(info, scope);
749 } 731 }
750 LexicalScope lexical_scope(&this->top_scope_, &this->with_nesting_level_, 732 LexicalScope lexical_scope(this, scope);
751 scope);
752 TemporaryScope temp_scope(&this->temp_scope_);
753 733
754 if (shared_info->strict_mode()) { 734 if (shared_info->strict_mode()) {
755 top_scope_->EnableStrictMode(); 735 top_scope_->EnableStrictMode();
756 } 736 }
757 737
758 FunctionLiteralType type = 738 FunctionLiteralType type =
759 shared_info->is_expression() ? EXPRESSION : DECLARATION; 739 shared_info->is_expression() ? EXPRESSION : DECLARATION;
760 bool ok = true; 740 bool ok = true;
761 result = ParseFunctionLiteral(name, 741 result = ParseFunctionLiteral(name,
762 false, // Strict mode name already checked. 742 false, // Strict mode name already checked.
(...skipping 404 matching lines...) Expand 10 before | Expand all | Expand 10 after
1167 } 1147 }
1168 processor->Add(stat); 1148 processor->Add(stat);
1169 } 1149 }
1170 1150
1171 // Propagate the collected information on this property assignments. 1151 // Propagate the collected information on this property assignments.
1172 if (top_scope_->is_function_scope()) { 1152 if (top_scope_->is_function_scope()) {
1173 bool only_simple_this_property_assignments = 1153 bool only_simple_this_property_assignments =
1174 this_property_assignment_finder.only_simple_this_property_assignments() 1154 this_property_assignment_finder.only_simple_this_property_assignments()
1175 && top_scope_->declarations()->length() == 0; 1155 && top_scope_->declarations()->length() == 0;
1176 if (only_simple_this_property_assignments) { 1156 if (only_simple_this_property_assignments) {
1177 temp_scope_->SetThisPropertyAssignmentInfo( 1157 lexical_scope_->SetThisPropertyAssignmentInfo(
1178 only_simple_this_property_assignments, 1158 only_simple_this_property_assignments,
1179 this_property_assignment_finder.GetThisPropertyAssignments()); 1159 this_property_assignment_finder.GetThisPropertyAssignments());
1180 } 1160 }
1181 } 1161 }
1182 return 0; 1162 return 0;
1183 } 1163 }
1184 1164
1185 1165
1186 Statement* Parser::ParseStatement(ZoneStringList* labels, bool* ok) { 1166 Statement* Parser::ParseStatement(ZoneStringList* labels, bool* ok) {
1187 // Statement :: 1167 // Statement ::
(...skipping 976 matching lines...) Expand 10 before | Expand all | Expand 10 after
2164 2144
2165 return result; 2145 return result;
2166 } 2146 }
2167 2147
2168 2148
2169 DoWhileStatement* Parser::ParseDoWhileStatement(ZoneStringList* labels, 2149 DoWhileStatement* Parser::ParseDoWhileStatement(ZoneStringList* labels,
2170 bool* ok) { 2150 bool* ok) {
2171 // DoStatement :: 2151 // DoStatement ::
2172 // 'do' Statement 'while' '(' Expression ')' ';' 2152 // 'do' Statement 'while' '(' Expression ')' ';'
2173 2153
2174 temp_scope_->AddLoop(); 2154 lexical_scope_->AddLoop();
2175 DoWhileStatement* loop = new DoWhileStatement(labels); 2155 DoWhileStatement* loop = new DoWhileStatement(labels);
2176 Target target(&this->target_stack_, loop); 2156 Target target(&this->target_stack_, loop);
2177 2157
2178 Expect(Token::DO, CHECK_OK); 2158 Expect(Token::DO, CHECK_OK);
2179 Statement* body = ParseStatement(NULL, CHECK_OK); 2159 Statement* body = ParseStatement(NULL, CHECK_OK);
2180 Expect(Token::WHILE, CHECK_OK); 2160 Expect(Token::WHILE, CHECK_OK);
2181 Expect(Token::LPAREN, CHECK_OK); 2161 Expect(Token::LPAREN, CHECK_OK);
2182 2162
2183 if (loop != NULL) { 2163 if (loop != NULL) {
2184 int position = scanner().location().beg_pos; 2164 int position = scanner().location().beg_pos;
(...skipping 12 matching lines...) Expand all
2197 2177
2198 if (loop != NULL) loop->Initialize(cond, body); 2178 if (loop != NULL) loop->Initialize(cond, body);
2199 return loop; 2179 return loop;
2200 } 2180 }
2201 2181
2202 2182
2203 WhileStatement* Parser::ParseWhileStatement(ZoneStringList* labels, bool* ok) { 2183 WhileStatement* Parser::ParseWhileStatement(ZoneStringList* labels, bool* ok) {
2204 // WhileStatement :: 2184 // WhileStatement ::
2205 // 'while' '(' Expression ')' Statement 2185 // 'while' '(' Expression ')' Statement
2206 2186
2207 temp_scope_->AddLoop(); 2187 lexical_scope_->AddLoop();
2208 WhileStatement* loop = new WhileStatement(labels); 2188 WhileStatement* loop = new WhileStatement(labels);
2209 Target target(&this->target_stack_, loop); 2189 Target target(&this->target_stack_, loop);
2210 2190
2211 Expect(Token::WHILE, CHECK_OK); 2191 Expect(Token::WHILE, CHECK_OK);
2212 Expect(Token::LPAREN, CHECK_OK); 2192 Expect(Token::LPAREN, CHECK_OK);
2213 Expression* cond = ParseExpression(true, CHECK_OK); 2193 Expression* cond = ParseExpression(true, CHECK_OK);
2214 if (cond != NULL) cond->set_is_loop_condition(true); 2194 if (cond != NULL) cond->set_is_loop_condition(true);
2215 Expect(Token::RPAREN, CHECK_OK); 2195 Expect(Token::RPAREN, CHECK_OK);
2216 Statement* body = ParseStatement(NULL, CHECK_OK); 2196 Statement* body = ParseStatement(NULL, CHECK_OK);
2217 2197
2218 if (loop != NULL) loop->Initialize(cond, body); 2198 if (loop != NULL) loop->Initialize(cond, body);
2219 return loop; 2199 return loop;
2220 } 2200 }
2221 2201
2222 2202
2223 Statement* Parser::ParseForStatement(ZoneStringList* labels, bool* ok) { 2203 Statement* Parser::ParseForStatement(ZoneStringList* labels, bool* ok) {
2224 // ForStatement :: 2204 // ForStatement ::
2225 // 'for' '(' Expression? ';' Expression? ';' Expression? ')' Statement 2205 // 'for' '(' Expression? ';' Expression? ';' Expression? ')' Statement
2226 2206
2227 temp_scope_->AddLoop(); 2207 lexical_scope_->AddLoop();
2228 Statement* init = NULL; 2208 Statement* init = NULL;
2229 2209
2230 Expect(Token::FOR, CHECK_OK); 2210 Expect(Token::FOR, CHECK_OK);
2231 Expect(Token::LPAREN, CHECK_OK); 2211 Expect(Token::LPAREN, CHECK_OK);
2232 if (peek() != Token::SEMICOLON) { 2212 if (peek() != Token::SEMICOLON) {
2233 if (peek() == Token::VAR || peek() == Token::CONST) { 2213 if (peek() == Token::VAR || peek() == Token::CONST) {
2234 Expression* each = NULL; 2214 Expression* each = NULL;
2235 Block* variable_statement = 2215 Block* variable_statement =
2236 ParseVariableDeclarations(false, &each, CHECK_OK); 2216 ParseVariableDeclarations(false, &each, CHECK_OK);
2237 if (peek() == Token::IN && each != NULL) { 2217 if (peek() == Token::IN && each != NULL) {
(...skipping 126 matching lines...) Expand 10 before | Expand all | Expand 10 after
2364 // TODO(1231235): We try to estimate the set of properties set by 2344 // TODO(1231235): We try to estimate the set of properties set by
2365 // constructors. We define a new property whenever there is an 2345 // constructors. We define a new property whenever there is an
2366 // assignment to a property of 'this'. We should probably only add 2346 // assignment to a property of 'this'. We should probably only add
2367 // properties if we haven't seen them before. Otherwise we'll 2347 // properties if we haven't seen them before. Otherwise we'll
2368 // probably overestimate the number of properties. 2348 // probably overestimate the number of properties.
2369 Property* property = expression ? expression->AsProperty() : NULL; 2349 Property* property = expression ? expression->AsProperty() : NULL;
2370 if (op == Token::ASSIGN && 2350 if (op == Token::ASSIGN &&
2371 property != NULL && 2351 property != NULL &&
2372 property->obj()->AsVariableProxy() != NULL && 2352 property->obj()->AsVariableProxy() != NULL &&
2373 property->obj()->AsVariableProxy()->is_this()) { 2353 property->obj()->AsVariableProxy()->is_this()) {
2374 temp_scope_->AddProperty(); 2354 lexical_scope_->AddProperty();
2375 } 2355 }
2376 2356
2377 // If we assign a function literal to a property we pretenure the 2357 // If we assign a function literal to a property we pretenure the
2378 // literal so it can be added as a constant function property. 2358 // literal so it can be added as a constant function property.
2379 if (property != NULL && right->AsFunctionLiteral() != NULL) { 2359 if (property != NULL && right->AsFunctionLiteral() != NULL) {
2380 right->AsFunctionLiteral()->set_pretenure(true); 2360 right->AsFunctionLiteral()->set_pretenure(true);
2381 } 2361 }
2382 2362
2383 if (fni_ != NULL) { 2363 if (fni_ != NULL) {
2384 // Check if the right hand side is a call to avoid inferring a 2364 // Check if the right hand side is a call to avoid inferring a
(...skipping 621 matching lines...) Expand 10 before | Expand all | Expand 10 after
3006 elem = ParseAssignmentExpression(true, CHECK_OK); 2986 elem = ParseAssignmentExpression(true, CHECK_OK);
3007 } 2987 }
3008 values->Add(elem); 2988 values->Add(elem);
3009 if (peek() != Token::RBRACK) { 2989 if (peek() != Token::RBRACK) {
3010 Expect(Token::COMMA, CHECK_OK); 2990 Expect(Token::COMMA, CHECK_OK);
3011 } 2991 }
3012 } 2992 }
3013 Expect(Token::RBRACK, CHECK_OK); 2993 Expect(Token::RBRACK, CHECK_OK);
3014 2994
3015 // Update the scope information before the pre-parsing bailout. 2995 // Update the scope information before the pre-parsing bailout.
3016 int literal_index = temp_scope_->NextMaterializedLiteralIndex(); 2996 int literal_index = lexical_scope_->NextMaterializedLiteralIndex();
3017 2997
3018 // Allocate a fixed array with all the literals. 2998 // Allocate a fixed array with all the literals.
3019 Handle<FixedArray> literals = 2999 Handle<FixedArray> literals =
3020 isolate()->factory()->NewFixedArray(values->length(), TENURED); 3000 isolate()->factory()->NewFixedArray(values->length(), TENURED);
3021 3001
3022 // Fill in the literals. 3002 // Fill in the literals.
3023 bool is_simple = true; 3003 bool is_simple = true;
3024 int depth = 1; 3004 int depth = 1;
3025 for (int i = 0, n = values->length(); i < n; i++) { 3005 for (int i = 0, n = values->length(); i < n; i++) {
3026 MaterializedLiteral* m_literal = values->at(i)->AsMaterializedLiteral(); 3006 MaterializedLiteral* m_literal = values->at(i)->AsMaterializedLiteral();
(...skipping 411 matching lines...) Expand 10 before | Expand all | Expand 10 after
3438 if (peek() != Token::RBRACE) Expect(Token::COMMA, CHECK_OK); 3418 if (peek() != Token::RBRACE) Expect(Token::COMMA, CHECK_OK);
3439 3419
3440 if (fni_ != NULL) { 3420 if (fni_ != NULL) {
3441 fni_->Infer(); 3421 fni_->Infer();
3442 fni_->Leave(); 3422 fni_->Leave();
3443 } 3423 }
3444 } 3424 }
3445 Expect(Token::RBRACE, CHECK_OK); 3425 Expect(Token::RBRACE, CHECK_OK);
3446 3426
3447 // Computation of literal_index must happen before pre parse bailout. 3427 // Computation of literal_index must happen before pre parse bailout.
3448 int literal_index = temp_scope_->NextMaterializedLiteralIndex(); 3428 int literal_index = lexical_scope_->NextMaterializedLiteralIndex();
3449 3429
3450 Handle<FixedArray> constant_properties = isolate()->factory()->NewFixedArray( 3430 Handle<FixedArray> constant_properties = isolate()->factory()->NewFixedArray(
3451 number_of_boilerplate_properties * 2, TENURED); 3431 number_of_boilerplate_properties * 2, TENURED);
3452 3432
3453 bool is_simple = true; 3433 bool is_simple = true;
3454 bool fast_elements = true; 3434 bool fast_elements = true;
3455 int depth = 1; 3435 int depth = 1;
3456 BuildObjectLiteralConstantProperties(properties, 3436 BuildObjectLiteralConstantProperties(properties,
3457 constant_properties, 3437 constant_properties,
3458 &is_simple, 3438 &is_simple,
3459 &fast_elements, 3439 &fast_elements,
3460 &depth); 3440 &depth);
3461 return new ObjectLiteral(constant_properties, 3441 return new ObjectLiteral(constant_properties,
3462 properties, 3442 properties,
3463 literal_index, 3443 literal_index,
3464 is_simple, 3444 is_simple,
3465 fast_elements, 3445 fast_elements,
3466 depth); 3446 depth);
3467 } 3447 }
3468 3448
3469 3449
3470 Expression* Parser::ParseRegExpLiteral(bool seen_equal, bool* ok) { 3450 Expression* Parser::ParseRegExpLiteral(bool seen_equal, bool* ok) {
3471 if (!scanner().ScanRegExpPattern(seen_equal)) { 3451 if (!scanner().ScanRegExpPattern(seen_equal)) {
3472 Next(); 3452 Next();
3473 ReportMessage("unterminated_regexp", Vector<const char*>::empty()); 3453 ReportMessage("unterminated_regexp", Vector<const char*>::empty());
3474 *ok = false; 3454 *ok = false;
3475 return NULL; 3455 return NULL;
3476 } 3456 }
3477 3457
3478 int literal_index = temp_scope_->NextMaterializedLiteralIndex(); 3458 int literal_index = lexical_scope_->NextMaterializedLiteralIndex();
3479 3459
3480 Handle<String> js_pattern = NextLiteralString(TENURED); 3460 Handle<String> js_pattern = NextLiteralString(TENURED);
3481 scanner().ScanRegExpFlags(); 3461 scanner().ScanRegExpFlags();
3482 Handle<String> js_flags = NextLiteralString(TENURED); 3462 Handle<String> js_flags = NextLiteralString(TENURED);
3483 Next(); 3463 Next();
3484 3464
3485 return new RegExpLiteral(js_pattern, js_flags, literal_index); 3465 return new RegExpLiteral(js_pattern, js_flags, literal_index);
3486 } 3466 }
3487 3467
3488 3468
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
3522 // The function name, if any. 3502 // The function name, if any.
3523 Handle<String> function_name = isolate()->factory()->empty_symbol(); 3503 Handle<String> function_name = isolate()->factory()->empty_symbol();
3524 if (is_named && (type == EXPRESSION || type == NESTED)) { 3504 if (is_named && (type == EXPRESSION || type == NESTED)) {
3525 function_name = name; 3505 function_name = name;
3526 } 3506 }
3527 3507
3528 int num_parameters = 0; 3508 int num_parameters = 0;
3529 // Parse function body. 3509 // Parse function body.
3530 { Scope* scope = 3510 { Scope* scope =
3531 NewScope(top_scope_, Scope::FUNCTION_SCOPE, inside_with()); 3511 NewScope(top_scope_, Scope::FUNCTION_SCOPE, inside_with());
3532 LexicalScope lexical_scope(&this->top_scope_, &this->with_nesting_level_, 3512 LexicalScope lexical_scope(this, scope);
3533 scope);
3534 TemporaryScope temp_scope(&this->temp_scope_);
3535 top_scope_->SetScopeName(name); 3513 top_scope_->SetScopeName(name);
3536 3514
3537 // FormalParameterList :: 3515 // FormalParameterList ::
3538 // '(' (Identifier)*[','] ')' 3516 // '(' (Identifier)*[','] ')'
3539 Expect(Token::LPAREN, CHECK_OK); 3517 Expect(Token::LPAREN, CHECK_OK);
3540 int start_pos = scanner().location().beg_pos; 3518 int start_pos = scanner().location().beg_pos;
3541 Scanner::Location name_loc = Scanner::NoLocation(); 3519 Scanner::Location name_loc = Scanner::NoLocation();
3542 Scanner::Location dupe_loc = Scanner::NoLocation(); 3520 Scanner::Location dupe_loc = Scanner::NoLocation();
3543 Scanner::Location reserved_loc = Scanner::NoLocation(); 3521 Scanner::Location reserved_loc = Scanner::NoLocation();
3544 3522
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after
3622 // Seek to position just before terminal '}'. 3600 // Seek to position just before terminal '}'.
3623 scanner().SeekForward(end_pos - 1); 3601 scanner().SeekForward(end_pos - 1);
3624 materialized_literal_count = entry.literal_count(); 3602 materialized_literal_count = entry.literal_count();
3625 expected_property_count = entry.property_count(); 3603 expected_property_count = entry.property_count();
3626 only_simple_this_property_assignments = false; 3604 only_simple_this_property_assignments = false;
3627 this_property_assignments = isolate()->factory()->empty_fixed_array(); 3605 this_property_assignments = isolate()->factory()->empty_fixed_array();
3628 Expect(Token::RBRACE, CHECK_OK); 3606 Expect(Token::RBRACE, CHECK_OK);
3629 } else { 3607 } else {
3630 ParseSourceElements(body, Token::RBRACE, CHECK_OK); 3608 ParseSourceElements(body, Token::RBRACE, CHECK_OK);
3631 3609
3632 materialized_literal_count = temp_scope.materialized_literal_count(); 3610 materialized_literal_count = lexical_scope.materialized_literal_count();
3633 expected_property_count = temp_scope.expected_property_count(); 3611 expected_property_count = lexical_scope.expected_property_count();
3634 only_simple_this_property_assignments = 3612 only_simple_this_property_assignments =
3635 temp_scope.only_simple_this_property_assignments(); 3613 lexical_scope.only_simple_this_property_assignments();
3636 this_property_assignments = temp_scope.this_property_assignments(); 3614 this_property_assignments = lexical_scope.this_property_assignments();
3637 3615
3638 Expect(Token::RBRACE, CHECK_OK); 3616 Expect(Token::RBRACE, CHECK_OK);
3639 end_pos = scanner().location().end_pos; 3617 end_pos = scanner().location().end_pos;
3640 } 3618 }
3641 3619
3642 // Validate strict mode. 3620 // Validate strict mode.
3643 if (top_scope_->is_strict_mode()) { 3621 if (top_scope_->is_strict_mode()) {
3644 if (IsEvalOrArguments(name)) { 3622 if (IsEvalOrArguments(name)) {
3645 int position = function_token_position != RelocInfo::kNoPosition 3623 int position = function_token_position != RelocInfo::kNoPosition
3646 ? function_token_position 3624 ? function_token_position
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after
3687 top_scope_, 3665 top_scope_,
3688 body, 3666 body,
3689 materialized_literal_count, 3667 materialized_literal_count,
3690 expected_property_count, 3668 expected_property_count,
3691 only_simple_this_property_assignments, 3669 only_simple_this_property_assignments,
3692 this_property_assignments, 3670 this_property_assignments,
3693 num_parameters, 3671 num_parameters,
3694 start_pos, 3672 start_pos,
3695 end_pos, 3673 end_pos,
3696 function_name->length() > 0, 3674 function_name->length() > 0,
3697 temp_scope.ContainsLoops()); 3675 lexical_scope.ContainsLoops());
3698 function_literal->set_function_token_position(function_token_position); 3676 function_literal->set_function_token_position(function_token_position);
3699 3677
3700 if (fni_ != NULL && !is_named) fni_->AddFunction(function_literal); 3678 if (fni_ != NULL && !is_named) fni_->AddFunction(function_literal);
3701 return function_literal; 3679 return function_literal;
3702 } 3680 }
3703 } 3681 }
3704 3682
3705 3683
3706 Expression* Parser::ParseV8Intrinsic(bool* ok) { 3684 Expression* Parser::ParseV8Intrinsic(bool* ok) {
3707 // CallRuntime :: 3685 // CallRuntime ::
(...skipping 1447 matching lines...) Expand 10 before | Expand all | Expand 10 after
5155 info->is_global(), 5133 info->is_global(),
5156 info->StrictMode()); 5134 info->StrictMode());
5157 } 5135 }
5158 } 5136 }
5159 5137
5160 info->SetFunction(result); 5138 info->SetFunction(result);
5161 return (result != NULL); 5139 return (result != NULL);
5162 } 5140 }
5163 5141
5164 } } // namespace v8::internal 5142 } } // namespace v8::internal
OLDNEW
« src/parser.h ('K') | « src/parser.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698