1 // Copyright 2012 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are
6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided
11 // with the distribution.
12 // * Neither the name of Google Inc. nor the names of its
13 // contributors may be used to endorse or promote products derived
14 // from this software without specific prior written permission.
16 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
17 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
18 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
19 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
20 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
26 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32 #include "bootstrapper.h"
33 #include "char-predicates-inl.h"
36 #include "func-name-inferrer.h"
40 #include "preparser.h"
42 #include "scanner-character-streams.h"
43 #include "scopeinfo.h"
44 #include "string-stream.h"
49 // PositionStack is used for on-stack allocation of token positions for
50 // new expressions. Please look at ParseNewExpression.
54 explicit PositionStack(bool* ok) : top_(NULL), ok_(ok) {}
55 ~PositionStack() { ASSERT(!*ok_ || is_empty()); }
59 Element(PositionStack* stack, int value) {
60 previous_ = stack->top();
66 Element* previous() { return previous_; }
67 int value() { return value_; }
68 friend class PositionStack;
73 bool is_empty() { return top_ == NULL; }
76 int result = top_->value();
77 top_ = top_->previous();
82 Element* top() { return top_; }
83 void set_top(Element* value) { top_ = value; }
89 RegExpBuilder::RegExpBuilder()
90 : zone_(Isolate::Current()->zone()),
91 pending_empty_(false),
96 , last_added_(ADD_NONE)
101 void RegExpBuilder::FlushCharacters() {
102 pending_empty_ = false;
103 if (characters_ != NULL) {
104 RegExpTree* atom = new(zone()) RegExpAtom(characters_->ToConstVector());
112 void RegExpBuilder::FlushText() {
114 int num_text = text_.length();
117 } else if (num_text == 1) {
118 terms_.Add(text_.last());
120 RegExpText* text = new(zone()) RegExpText();
121 for (int i = 0; i < num_text; i++)
122 text_.Get(i)->AppendToText(text);
129 void RegExpBuilder::AddCharacter(uc16 c) {
130 pending_empty_ = false;
131 if (characters_ == NULL) {
132 characters_ = new(zone()) ZoneList<uc16>(4);
139 void RegExpBuilder::AddEmpty() {
140 pending_empty_ = true;
144 void RegExpBuilder::AddAtom(RegExpTree* term) {
145 if (term->IsEmpty()) {
149 if (term->IsTextElement()) {
160 void RegExpBuilder::AddAssertion(RegExpTree* assert) {
167 void RegExpBuilder::NewAlternative() {
172 void RegExpBuilder::FlushTerms() {
174 int num_terms = terms_.length();
175 RegExpTree* alternative;
176 if (num_terms == 0) {
177 alternative = RegExpEmpty::GetInstance();
178 } else if (num_terms == 1) {
179 alternative = terms_.last();
181 alternative = new(zone()) RegExpAlternative(terms_.GetList());
183 alternatives_.Add(alternative);
189 RegExpTree* RegExpBuilder::ToRegExp() {
191 int num_alternatives = alternatives_.length();
192 if (num_alternatives == 0) {
193 return RegExpEmpty::GetInstance();
195 if (num_alternatives == 1) {
196 return alternatives_.last();
198 return new(zone()) RegExpDisjunction(alternatives_.GetList());
202 void RegExpBuilder::AddQuantifierToAtom(int min,
204 RegExpQuantifier::Type type) {
205 if (pending_empty_) {
206 pending_empty_ = false;
210 if (characters_ != NULL) {
211 ASSERT(last_added_ == ADD_CHAR);
212 // Last atom was character.
213 Vector<const uc16> char_vector = characters_->ToConstVector();
214 int num_chars = char_vector.length();
216 Vector<const uc16> prefix = char_vector.SubVector(0, num_chars - 1);
217 text_.Add(new(zone()) RegExpAtom(prefix));
218 char_vector = char_vector.SubVector(num_chars - 1, num_chars);
221 atom = new(zone()) RegExpAtom(char_vector);
223 } else if (text_.length() > 0) {
224 ASSERT(last_added_ == ADD_ATOM);
225 atom = text_.RemoveLast();
227 } else if (terms_.length() > 0) {
228 ASSERT(last_added_ == ADD_ATOM);
229 atom = terms_.RemoveLast();
230 if (atom->max_match() == 0) {
231 // Guaranteed to only match an empty string.
240 // Only call immediately after adding an atom or character!
244 terms_.Add(new(zone()) RegExpQuantifier(min, max, type, atom));
249 Handle<String> Parser::LookupSymbol(int symbol_id) {
250 // 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 // This might also happen if there is no preparser symbol data, even
253 // if there is some preparser data.
254 if (static_cast<unsigned>(symbol_id)
255 >= static_cast<unsigned>(symbol_cache_.length())) {
256 if (scanner().is_literal_ascii()) {
257 return isolate()->factory()->LookupAsciiSymbol(
258 scanner().literal_ascii_string());
260 return isolate()->factory()->LookupTwoByteSymbol(
261 scanner().literal_utf16_string());
264 return LookupCachedSymbol(symbol_id);
268 Handle<String> Parser::LookupCachedSymbol(int symbol_id) {
269 // Make sure the cache is large enough to hold the symbol identifier.
270 if (symbol_cache_.length() <= symbol_id) {
271 // Increase length to index + 1.
272 symbol_cache_.AddBlock(Handle<String>::null(),
273 symbol_id + 1 - symbol_cache_.length());
275 Handle<String> result = symbol_cache_.at(symbol_id);
276 if (result.is_null()) {
277 if (scanner().is_literal_ascii()) {
278 result = isolate()->factory()->LookupAsciiSymbol(
279 scanner().literal_ascii_string());
281 result = isolate()->factory()->LookupTwoByteSymbol(
282 scanner().literal_utf16_string());
284 symbol_cache_.at(symbol_id) = result;
287 isolate()->counters()->total_preparse_symbols_skipped()->Increment();
292 FunctionEntry ScriptDataImpl::GetFunctionEntry(int start) {
293 // The current pre-data entry must be a FunctionEntry with the given
295 if ((function_index_ + FunctionEntry::kSize <= store_.length())
296 && (static_cast<int>(store_[function_index_]) == start)) {
297 int index = function_index_;
298 function_index_ += FunctionEntry::kSize;
299 return FunctionEntry(store_.SubVector(index,
300 index + FunctionEntry::kSize));
302 return FunctionEntry();
306 int ScriptDataImpl::GetSymbolIdentifier() {
307 return ReadNumber(&symbol_data_);
311 bool ScriptDataImpl::SanityCheck() {
312 // Check that the header data is valid and doesn't specify
313 // point to positions outside the store.
314 if (store_.length() < PreparseDataConstants::kHeaderSize) return false;
315 if (magic() != PreparseDataConstants::kMagicNumber) return false;
316 if (version() != PreparseDataConstants::kCurrentVersion) return false;
318 // Extra sane sanity check for error message encoding.
319 if (store_.length() <= PreparseDataConstants::kHeaderSize
320 + PreparseDataConstants::kMessageTextPos) {
323 if (Read(PreparseDataConstants::kMessageStartPos) >
324 Read(PreparseDataConstants::kMessageEndPos)) {
327 unsigned arg_count = Read(PreparseDataConstants::kMessageArgCountPos);
328 int pos = PreparseDataConstants::kMessageTextPos;
329 for (unsigned int i = 0; i <= arg_count; i++) {
330 if (store_.length() <= PreparseDataConstants::kHeaderSize + pos) {
333 int length = static_cast<int>(Read(pos));
334 if (length < 0) return false;
337 if (store_.length() < PreparseDataConstants::kHeaderSize + pos) {
342 // Check that the space allocated for function entries is sane.
344 static_cast<int>(store_[PreparseDataConstants::kFunctionsSizeOffset]);
345 if (functions_size < 0) return false;
346 if (functions_size % FunctionEntry::kSize != 0) return false;
347 // Check that the count of symbols is non-negative.
349 static_cast<int>(store_[PreparseDataConstants::kSymbolCountOffset]);
350 if (symbol_count < 0) return false;
351 // Check that the total size has room for header and function entries.
353 PreparseDataConstants::kHeaderSize + functions_size;
354 if (store_.length() < minimum_size) return false;
360 const char* ScriptDataImpl::ReadString(unsigned* start, int* chars) {
361 int length = start[0];
362 char* result = NewArray<char>(length + 1);
363 for (int i = 0; i < length; i++) {
364 result[i] = start[i + 1];
366 result[length] = '\0';
367 if (chars != NULL) *chars = length;
371 Scanner::Location ScriptDataImpl::MessageLocation() {
372 int beg_pos = Read(PreparseDataConstants::kMessageStartPos);
373 int end_pos = Read(PreparseDataConstants::kMessageEndPos);
374 return Scanner::Location(beg_pos, end_pos);
378 const char* ScriptDataImpl::BuildMessage() {
379 unsigned* start = ReadAddress(PreparseDataConstants::kMessageTextPos);
380 return ReadString(start, NULL);
384 Vector<const char*> ScriptDataImpl::BuildArgs() {
385 int arg_count = Read(PreparseDataConstants::kMessageArgCountPos);
386 const char** array = NewArray<const char*>(arg_count);
387 // Position after text found by skipping past length field and
388 // length field content words.
389 int pos = PreparseDataConstants::kMessageTextPos + 1
390 + Read(PreparseDataConstants::kMessageTextPos);
391 for (int i = 0; i < arg_count; i++) {
393 array[i] = ReadString(ReadAddress(pos), &count);
396 return Vector<const char*>(array, arg_count);
400 unsigned ScriptDataImpl::Read(int position) {
401 return store_[PreparseDataConstants::kHeaderSize + position];
405 unsigned* ScriptDataImpl::ReadAddress(int position) {
406 return &store_[PreparseDataConstants::kHeaderSize + position];
410 Scope* Parser::NewScope(Scope* parent, ScopeType type) {
411 Scope* result = new(zone()) Scope(parent, type);
412 result->Initialize();
417 // ----------------------------------------------------------------------------
418 // Target is a support class to facilitate manipulation of the
419 // Parser's target_stack_ (the stack of potential 'break' and
420 // 'continue' statement targets). Upon construction, a new target is
421 // added; it is removed upon destruction.
423 class Target BASE_EMBEDDED {
425 Target(Target** variable, AstNode* node)
426 : variable_(variable), node_(node), previous_(*variable) {
431 *variable_ = previous_;
434 Target* previous() { return previous_; }
435 AstNode* node() { return node_; }
444 class TargetScope BASE_EMBEDDED {
446 explicit TargetScope(Target** variable)
447 : variable_(variable), previous_(*variable) {
452 *variable_ = previous_;
461 // ----------------------------------------------------------------------------
462 // FunctionState and BlockState together implement the parser's scope stack.
463 // The parser's current scope is in top_scope_. The BlockState and
464 // FunctionState constructors push on the scope stack and the destructors
465 // pop. They are also used to hold the parser's per-function and per-block
468 class Parser::BlockState BASE_EMBEDDED {
470 BlockState(Parser* parser, Scope* scope)
472 outer_scope_(parser->top_scope_) {
473 parser->top_scope_ = scope;
476 ~BlockState() { parser_->top_scope_ = outer_scope_; }
484 Parser::FunctionState::FunctionState(Parser* parser,
487 : next_materialized_literal_index_(JSFunction::kLiteralsPrefixSize),
488 next_handler_index_(0),
489 expected_property_count_(0),
490 only_simple_this_property_assignments_(false),
491 this_property_assignments_(isolate->factory()->empty_fixed_array()),
493 outer_function_state_(parser->current_function_state_),
494 outer_scope_(parser->top_scope_),
495 saved_ast_node_id_(isolate->ast_node_id()),
497 parser->top_scope_ = scope;
498 parser->current_function_state_ = this;
499 isolate->set_ast_node_id(AstNode::kDeclarationsId + 1);
503 Parser::FunctionState::~FunctionState() {
504 parser_->top_scope_ = outer_scope_;
505 parser_->current_function_state_ = outer_function_state_;
506 if (outer_function_state_ != NULL) {
507 parser_->isolate()->set_ast_node_id(saved_ast_node_id_);
512 // ----------------------------------------------------------------------------
513 // The CHECK_OK macro is a convenient macro to enforce error
514 // handling for functions that may fail (by returning !*ok).
516 // CAUTION: This macro appends extra statements after a call,
517 // thus it must never be used where only a single statement
518 // is correct (e.g. an if statement branch w/o braces)!
520 #define CHECK_OK ok); \
521 if (!*ok) return NULL; \
523 #define DUMMY ) // to make indentation work
526 #define CHECK_FAILED /**/); \
527 if (failed_) return NULL; \
529 #define DUMMY ) // to make indentation work
532 // ----------------------------------------------------------------------------
533 // Implementation of Parser
535 Parser::Parser(Handle<Script> script,
537 v8::Extension* extension,
538 ScriptDataImpl* pre_data)
539 : isolate_(script->GetIsolate()),
540 symbol_cache_(pre_data ? pre_data->symbol_count() : 0),
542 scanner_(isolate_->unicode_cache()),
543 reusable_preparser_(NULL),
545 current_function_state_(NULL),
547 extension_(extension),
550 allow_natives_syntax_((parser_flags & kAllowNativesSyntax) != 0),
551 allow_lazy_((parser_flags & kAllowLazy) != 0),
552 allow_modules_((parser_flags & kAllowModules) != 0),
553 stack_overflow_(false),
554 parenthesized_function_(false) {
555 isolate_->set_ast_node_id(0);
556 if ((parser_flags & kLanguageModeMask) == EXTENDED_MODE) {
557 scanner().SetHarmonyScoping(true);
559 if ((parser_flags & kAllowModules) != 0) {
560 scanner().SetHarmonyModules(true);
565 FunctionLiteral* Parser::ParseProgram(CompilationInfo* info) {
566 ZoneScope zone_scope(isolate(), DONT_DELETE_ON_EXIT);
568 HistogramTimerScope timer(isolate()->counters()->parse());
569 Handle<String> source(String::cast(script_->source()));
570 isolate()->counters()->total_parse_size()->Increment(source->length());
571 fni_ = new(zone()) FuncNameInferrer(isolate());
573 // Initialize parser state.
574 source->TryFlatten();
575 if (source->IsExternalTwoByteString()) {
576 // Notice that the stream is destroyed at the end of the branch block.
577 // The last line of the blocks can't be moved outside, even though they're
579 ExternalTwoByteStringUtf16CharacterStream stream(
580 Handle<ExternalTwoByteString>::cast(source), 0, source->length());
581 scanner_.Initialize(&stream);
582 return DoParseProgram(info, source, &zone_scope);
584 GenericStringUtf16CharacterStream stream(source, 0, source->length());
585 scanner_.Initialize(&stream);
586 return DoParseProgram(info, source, &zone_scope);
591 FunctionLiteral* Parser::DoParseProgram(CompilationInfo* info,
592 Handle<String> source,
593 ZoneScope* zone_scope) {
594 ASSERT(top_scope_ == NULL);
595 ASSERT(target_stack_ == NULL);
596 if (pre_data_ != NULL) pre_data_->Initialize();
598 // Compute the parsing mode.
599 mode_ = (FLAG_lazy && allow_lazy_) ? PARSE_LAZILY : PARSE_EAGERLY;
600 if (allow_natives_syntax_ || extension_ != NULL) mode_ = PARSE_EAGERLY;
602 Handle<String> no_name = isolate()->factory()->empty_symbol();
604 FunctionLiteral* result = NULL;
605 { Scope* scope = NewScope(top_scope_, GLOBAL_SCOPE);
606 info->SetGlobalScope(scope);
607 if (info->is_eval()) {
608 Handle<SharedFunctionInfo> shared = info->shared_info();
609 if (!info->is_global() && (shared.is_null() || shared->is_function())) {
610 scope = Scope::DeserializeScopeChain(*info->calling_context(), scope);
612 if (!scope->is_global_scope() || info->language_mode() != CLASSIC_MODE) {
613 scope = NewScope(scope, EVAL_SCOPE);
616 scope->set_start_position(0);
617 scope->set_end_position(source->length());
618 FunctionState function_state(this, scope, isolate());
619 top_scope_->SetLanguageMode(info->language_mode());
620 if (info->is_qml_mode()) {
621 scope->EnableQmlModeFlag();
623 ZoneList<Statement*>* body = new(zone()) ZoneList<Statement*>(16);
625 int beg_loc = scanner().location().beg_pos;
626 ParseSourceElements(body, Token::EOS, info->is_eval(), &ok);
627 if (ok && !top_scope_->is_classic_mode()) {
628 CheckOctalLiteral(beg_loc, scanner().location().end_pos, &ok);
631 if (ok && is_extended_mode()) {
632 CheckConflictingVarDeclarations(top_scope_, &ok);
636 result = factory()->NewFunctionLiteral(
640 function_state.materialized_literal_count(),
641 function_state.expected_property_count(),
642 function_state.handler_count(),
643 function_state.only_simple_this_property_assignments(),
644 function_state.this_property_assignments(),
646 FunctionLiteral::kNoDuplicateParameters,
647 FunctionLiteral::ANONYMOUS_EXPRESSION,
648 FunctionLiteral::kGlobalOrEval);
649 result->set_ast_properties(factory()->visitor()->ast_properties());
650 } else if (stack_overflow_) {
651 isolate()->StackOverflow();
655 // Make sure the target stack is empty.
656 ASSERT(target_stack_ == NULL);
658 // If there was a syntax error we have to get rid of the AST
659 // and it is not safe to do so before the scope has been deleted.
660 if (result == NULL) zone_scope->DeleteOnExit();
665 FunctionLiteral* Parser::ParseLazy(CompilationInfo* info) {
666 ZoneScope zone_scope(isolate(), DONT_DELETE_ON_EXIT);
667 HistogramTimerScope timer(isolate()->counters()->parse_lazy());
668 Handle<String> source(String::cast(script_->source()));
669 isolate()->counters()->total_parse_size()->Increment(source->length());
671 Handle<SharedFunctionInfo> shared_info = info->shared_info();
672 // Initialize parser state.
673 source->TryFlatten();
674 if (source->IsExternalTwoByteString()) {
675 ExternalTwoByteStringUtf16CharacterStream stream(
676 Handle<ExternalTwoByteString>::cast(source),
677 shared_info->start_position(),
678 shared_info->end_position());
679 FunctionLiteral* result = ParseLazy(info, &stream, &zone_scope);
682 GenericStringUtf16CharacterStream stream(source,
683 shared_info->start_position(),
684 shared_info->end_position());
685 FunctionLiteral* result = ParseLazy(info, &stream, &zone_scope);
691 FunctionLiteral* Parser::ParseLazy(CompilationInfo* info,
692 Utf16CharacterStream* source,
693 ZoneScope* zone_scope) {
694 Handle<SharedFunctionInfo> shared_info = info->shared_info();
695 scanner_.Initialize(source);
696 ASSERT(top_scope_ == NULL);
697 ASSERT(target_stack_ == NULL);
699 Handle<String> name(String::cast(shared_info->name()));
700 fni_ = new(zone()) FuncNameInferrer(isolate());
701 fni_->PushEnclosingName(name);
703 mode_ = PARSE_EAGERLY;
705 // Place holder for the result.
706 FunctionLiteral* result = NULL;
709 // Parse the function literal.
710 Scope* scope = NewScope(top_scope_, GLOBAL_SCOPE);
711 info->SetGlobalScope(scope);
712 if (!info->closure().is_null()) {
713 scope = Scope::DeserializeScopeChain(info->closure()->context(), scope);
715 FunctionState function_state(this, scope, isolate());
716 ASSERT(scope->language_mode() != STRICT_MODE || !info->is_classic_mode());
717 ASSERT(scope->language_mode() != EXTENDED_MODE ||
718 info->is_extended_mode());
719 ASSERT(info->language_mode() == shared_info->language_mode());
720 scope->SetLanguageMode(shared_info->language_mode());
721 if (shared_info->qml_mode()) {
722 top_scope_->EnableQmlModeFlag();
724 FunctionLiteral::Type type = shared_info->is_expression()
725 ? (shared_info->is_anonymous()
726 ? FunctionLiteral::ANONYMOUS_EXPRESSION
727 : FunctionLiteral::NAMED_EXPRESSION)
728 : FunctionLiteral::DECLARATION;
730 result = ParseFunctionLiteral(name,
731 false, // Strict mode name already checked.
732 RelocInfo::kNoPosition,
735 // Make sure the results agree.
736 ASSERT(ok == (result != NULL));
739 // Make sure the target stack is empty.
740 ASSERT(target_stack_ == NULL);
742 // If there was a stack overflow we have to get rid of AST and it is
743 // not safe to do before scope has been deleted.
744 if (result == NULL) {
745 zone_scope->DeleteOnExit();
746 if (stack_overflow_) isolate()->StackOverflow();
748 Handle<String> inferred_name(shared_info->inferred_name());
749 result->set_inferred_name(inferred_name);
755 Handle<String> Parser::GetSymbol(bool* ok) {
757 if (pre_data() != NULL) {
758 symbol_id = pre_data()->GetSymbolIdentifier();
760 return LookupSymbol(symbol_id);
764 void Parser::ReportMessage(const char* type, Vector<const char*> args) {
765 Scanner::Location source_location = scanner().location();
766 ReportMessageAt(source_location, type, args);
770 void Parser::ReportMessage(const char* type, Vector<Handle<String> > args) {
771 Scanner::Location source_location = scanner().location();
772 ReportMessageAt(source_location, type, args);
776 void Parser::ReportMessageAt(Scanner::Location source_location,
778 Vector<const char*> args) {
779 MessageLocation location(script_,
780 source_location.beg_pos,
781 source_location.end_pos);
782 Factory* factory = isolate()->factory();
783 Handle<FixedArray> elements = factory->NewFixedArray(args.length());
784 for (int i = 0; i < args.length(); i++) {
785 Handle<String> arg_string = factory->NewStringFromUtf8(CStrVector(args[i]));
786 elements->set(i, *arg_string);
788 Handle<JSArray> array = factory->NewJSArrayWithElements(elements);
789 Handle<Object> result = factory->NewSyntaxError(type, array);
790 isolate()->Throw(*result, &location);
794 void Parser::ReportMessageAt(Scanner::Location source_location,
796 Vector<Handle<String> > args) {
797 MessageLocation location(script_,
798 source_location.beg_pos,
799 source_location.end_pos);
800 Factory* factory = isolate()->factory();
801 Handle<FixedArray> elements = factory->NewFixedArray(args.length());
802 for (int i = 0; i < args.length(); i++) {
803 elements->set(i, *args[i]);
805 Handle<JSArray> array = factory->NewJSArrayWithElements(elements);
806 Handle<Object> result = factory->NewSyntaxError(type, array);
807 isolate()->Throw(*result, &location);
811 // Base class containing common code for the different finder classes used by
816 static Assignment* AsAssignment(Statement* stat) {
817 if (stat == NULL) return NULL;
818 ExpressionStatement* exp_stat = stat->AsExpressionStatement();
819 if (exp_stat == NULL) return NULL;
820 return exp_stat->expression()->AsAssignment();
825 // An InitializationBlockFinder finds and marks sequences of statements of the
826 // form expr.a = ...; expr.b = ...; etc.
827 class InitializationBlockFinder : public ParserFinder {
829 // We find and mark the initialization blocks in top level
830 // non-looping code only. This is because the optimization prevents
831 // reuse of the map transitions, so it should be used only for code
832 // that will only be run once.
833 InitializationBlockFinder(Scope* top_scope, Target* target)
834 : enabled_(top_scope->DeclarationScope()->is_global_scope() &&
835 !IsLoopTarget(target)),
836 first_in_block_(NULL),
837 last_in_block_(NULL),
840 ~InitializationBlockFinder() {
841 if (!enabled_) return;
842 if (InBlock()) EndBlock();
845 void Update(Statement* stat) {
846 if (!enabled_) return;
847 Assignment* assignment = AsAssignment(stat);
849 if (BlockContinues(assignment)) {
850 UpdateBlock(assignment);
855 if (!InBlock() && (assignment != NULL) &&
856 (assignment->op() == Token::ASSIGN)) {
857 StartBlock(assignment);
862 // The minimum number of contiguous assignment that will
863 // be treated as an initialization block. Benchmarks show that
864 // the overhead exceeds the savings below this limit.
865 static const int kMinInitializationBlock = 3;
867 static bool IsLoopTarget(Target* target) {
868 while (target != NULL) {
869 if (target->node()->AsIterationStatement() != NULL) return true;
870 target = target->previous();
875 // Returns true if the expressions appear to denote the same object.
876 // In the context of initialization blocks, we only consider expressions
877 // of the form 'expr.x' or expr["x"].
878 static bool SameObject(Expression* e1, Expression* e2) {
879 VariableProxy* v1 = e1->AsVariableProxy();
880 VariableProxy* v2 = e2->AsVariableProxy();
881 if (v1 != NULL && v2 != NULL) {
882 return v1->name()->Equals(*v2->name());
884 Property* p1 = e1->AsProperty();
885 Property* p2 = e2->AsProperty();
886 if ((p1 == NULL) || (p2 == NULL)) return false;
887 Literal* key1 = p1->key()->AsLiteral();
888 Literal* key2 = p2->key()->AsLiteral();
889 if ((key1 == NULL) || (key2 == NULL)) return false;
890 if (!key1->handle()->IsString() || !key2->handle()->IsString()) {
893 String* name1 = String::cast(*key1->handle());
894 String* name2 = String::cast(*key2->handle());
895 if (!name1->Equals(name2)) return false;
896 return SameObject(p1->obj(), p2->obj());
899 // Returns true if the expressions appear to denote different properties
900 // of the same object.
901 static bool PropertyOfSameObject(Expression* e1, Expression* e2) {
902 Property* p1 = e1->AsProperty();
903 Property* p2 = e2->AsProperty();
904 if ((p1 == NULL) || (p2 == NULL)) return false;
905 return SameObject(p1->obj(), p2->obj());
908 bool BlockContinues(Assignment* assignment) {
909 if ((assignment == NULL) || (first_in_block_ == NULL)) return false;
910 if (assignment->op() != Token::ASSIGN) return false;
911 return PropertyOfSameObject(first_in_block_->target(),
912 assignment->target());
915 void StartBlock(Assignment* assignment) {
916 first_in_block_ = assignment;
917 last_in_block_ = assignment;
921 void UpdateBlock(Assignment* assignment) {
922 last_in_block_ = assignment;
927 if (block_size_ >= kMinInitializationBlock) {
928 first_in_block_->mark_block_start();
929 last_in_block_->mark_block_end();
931 last_in_block_ = first_in_block_ = NULL;
935 bool InBlock() { return first_in_block_ != NULL; }
938 Assignment* first_in_block_;
939 Assignment* last_in_block_;
942 DISALLOW_COPY_AND_ASSIGN(InitializationBlockFinder);
946 // A ThisNamedPropertyAssignmentFinder finds and marks statements of the form
947 // this.x = ...;, where x is a named property. It also determines whether a
948 // function contains only assignments of this type.
949 class ThisNamedPropertyAssignmentFinder : public ParserFinder {
951 explicit ThisNamedPropertyAssignmentFinder(Isolate* isolate)
953 only_simple_this_property_assignments_(true),
955 assigned_arguments_(0),
956 assigned_constants_(0) {
959 void Update(Scope* scope, Statement* stat) {
960 // Bail out if function already has property assignment that are
961 // not simple this property assignments.
962 if (!only_simple_this_property_assignments_) {
966 // Check whether this statement is of the form this.x = ...;
967 Assignment* assignment = AsAssignment(stat);
968 if (IsThisPropertyAssignment(assignment)) {
969 HandleThisPropertyAssignment(scope, assignment);
971 only_simple_this_property_assignments_ = false;
975 // Returns whether only statements of the form this.x = y; where y is either a
976 // constant or a function argument was encountered.
977 bool only_simple_this_property_assignments() {
978 return only_simple_this_property_assignments_;
981 // Returns a fixed array containing three elements for each assignment of the
983 Handle<FixedArray> GetThisPropertyAssignments() {
984 if (names_.is_empty()) {
985 return isolate_->factory()->empty_fixed_array();
987 ASSERT_EQ(names_.length(), assigned_arguments_.length());
988 ASSERT_EQ(names_.length(), assigned_constants_.length());
989 Handle<FixedArray> assignments =
990 isolate_->factory()->NewFixedArray(names_.length() * 3);
991 for (int i = 0; i < names_.length(); ++i) {
992 assignments->set(i * 3, *names_[i]);
993 assignments->set(i * 3 + 1, Smi::FromInt(assigned_arguments_[i]));
994 assignments->set(i * 3 + 2, *assigned_constants_[i]);
1000 bool IsThisPropertyAssignment(Assignment* assignment) {
1001 if (assignment != NULL) {
1002 Property* property = assignment->target()->AsProperty();
1003 return assignment->op() == Token::ASSIGN
1005 && property->obj()->AsVariableProxy() != NULL
1006 && property->obj()->AsVariableProxy()->is_this();
1011 void HandleThisPropertyAssignment(Scope* scope, Assignment* assignment) {
1012 // Check that the property assigned to is a named property, which is not
1014 Property* property = assignment->target()->AsProperty();
1015 ASSERT(property != NULL);
1016 Literal* literal = property->key()->AsLiteral();
1018 if (literal != NULL &&
1019 literal->handle()->IsString() &&
1020 !String::cast(*(literal->handle()))->Equals(
1021 isolate_->heap()->Proto_symbol()) &&
1022 !String::cast(*(literal->handle()))->AsArrayIndex(&dummy)) {
1023 Handle<String> key = Handle<String>::cast(literal->handle());
1025 // Check whether the value assigned is either a constant or matches the
1026 // name of one of the arguments to the function.
1027 if (assignment->value()->AsLiteral() != NULL) {
1028 // Constant assigned.
1029 Literal* literal = assignment->value()->AsLiteral();
1030 AssignmentFromConstant(key, literal->handle());
1032 } else if (assignment->value()->AsVariableProxy() != NULL) {
1033 // Variable assigned.
1034 Handle<String> name =
1035 assignment->value()->AsVariableProxy()->name();
1036 // Check whether the variable assigned matches an argument name.
1037 for (int i = 0; i < scope->num_parameters(); i++) {
1038 if (*scope->parameter(i)->name() == *name) {
1039 // Assigned from function argument.
1040 AssignmentFromParameter(key, i);
1046 // It is not a simple "this.x = value;" assignment with a constant
1047 // or parameter value.
1048 AssignmentFromSomethingElse();
1054 // We will potentially reorder the property assignments, so they must be
1055 // simple enough that the ordering does not matter.
1056 void AssignmentFromParameter(Handle<String> name, int index) {
1057 EnsureInitialized();
1058 for (int i = 0; i < names_.length(); ++i) {
1059 if (name->Equals(*names_[i])) {
1060 assigned_arguments_[i] = index;
1061 assigned_constants_[i] = isolate_->factory()->undefined_value();
1066 assigned_arguments_.Add(index);
1067 assigned_constants_.Add(isolate_->factory()->undefined_value());
1070 void AssignmentFromConstant(Handle<String> name, Handle<Object> value) {
1071 EnsureInitialized();
1072 for (int i = 0; i < names_.length(); ++i) {
1073 if (name->Equals(*names_[i])) {
1074 assigned_arguments_[i] = -1;
1075 assigned_constants_[i] = value;
1080 assigned_arguments_.Add(-1);
1081 assigned_constants_.Add(value);
1084 void AssignmentFromSomethingElse() {
1085 // The this assignment is not a simple one.
1086 only_simple_this_property_assignments_ = false;
1089 void EnsureInitialized() {
1090 if (names_.capacity() == 0) {
1091 ASSERT(assigned_arguments_.capacity() == 0);
1092 ASSERT(assigned_constants_.capacity() == 0);
1093 names_.Initialize(4);
1094 assigned_arguments_.Initialize(4);
1095 assigned_constants_.Initialize(4);
1100 bool only_simple_this_property_assignments_;
1101 ZoneStringList names_;
1102 ZoneList<int> assigned_arguments_;
1103 ZoneObjectList assigned_constants_;
1107 void* Parser::ParseSourceElements(ZoneList<Statement*>* processor,
1111 // SourceElements ::
1112 // (ModuleElement)* <end_token>
1114 // Allocate a target stack to use for this set of source
1115 // elements. This way, all scripts and functions get their own
1116 // target stack thus avoiding illegal breaks and continues across
1118 TargetScope scope(&this->target_stack_);
1120 ASSERT(processor != NULL);
1121 InitializationBlockFinder block_finder(top_scope_, target_stack_);
1122 ThisNamedPropertyAssignmentFinder this_property_assignment_finder(isolate());
1123 bool directive_prologue = true; // Parsing directive prologue.
1125 while (peek() != end_token) {
1126 if (directive_prologue && peek() != Token::STRING) {
1127 directive_prologue = false;
1130 Scanner::Location token_loc = scanner().peek_location();
1131 Statement* stat = ParseModuleElement(NULL, CHECK_OK);
1132 if (stat == NULL || stat->IsEmpty()) {
1133 directive_prologue = false; // End of directive prologue.
1137 if (directive_prologue) {
1138 // A shot at a directive.
1139 ExpressionStatement* e_stat;
1141 // Still processing directive prologue?
1142 if ((e_stat = stat->AsExpressionStatement()) != NULL &&
1143 (literal = e_stat->expression()->AsLiteral()) != NULL &&
1144 literal->handle()->IsString()) {
1145 Handle<String> directive = Handle<String>::cast(literal->handle());
1147 // Check "use strict" directive (ES5 14.1).
1148 if (top_scope_->is_classic_mode() &&
1149 directive->Equals(isolate()->heap()->use_strict()) &&
1150 token_loc.end_pos - token_loc.beg_pos ==
1151 isolate()->heap()->use_strict()->length() + 2) {
1152 // TODO(mstarzinger): Global strict eval calls, need their own scope
1153 // as specified in ES5 10.4.2(3). The correct fix would be to always
1154 // add this scope in DoParseProgram(), but that requires adaptations
1155 // all over the code base, so we go with a quick-fix for now.
1156 if (is_eval && !top_scope_->is_eval_scope()) {
1157 ASSERT(top_scope_->is_global_scope());
1158 Scope* scope = NewScope(top_scope_, EVAL_SCOPE);
1159 scope->set_start_position(top_scope_->start_position());
1160 scope->set_end_position(top_scope_->end_position());
1163 // TODO(ES6): Fix entering extended mode, once it is specified.
1164 top_scope_->SetLanguageMode(FLAG_harmony_scoping
1165 ? EXTENDED_MODE : STRICT_MODE);
1166 // "use strict" is the only directive for now.
1167 directive_prologue = false;
1170 // End of the directive prologue.
1171 directive_prologue = false;
1175 block_finder.Update(stat);
1176 // Find and mark all assignments to named properties in this (this.x =)
1177 if (top_scope_->is_function_scope()) {
1178 this_property_assignment_finder.Update(top_scope_, stat);
1180 processor->Add(stat);
1183 // Propagate the collected information on this property assignments.
1184 if (top_scope_->is_function_scope()) {
1185 bool only_simple_this_property_assignments =
1186 this_property_assignment_finder.only_simple_this_property_assignments()
1187 && top_scope_->declarations()->length() == 0;
1188 if (only_simple_this_property_assignments) {
1189 current_function_state_->SetThisPropertyAssignmentInfo(
1190 only_simple_this_property_assignments,
1191 this_property_assignment_finder.GetThisPropertyAssignments());
1199 Statement* Parser::ParseModuleElement(ZoneStringList* labels,
1201 // (Ecma 262 5th Edition, clause 14):
1204 // FunctionDeclaration
1206 // In harmony mode we allow additionally the following productions
1210 // ModuleDeclaration
1211 // ImportDeclaration
1212 // ExportDeclaration
1215 case Token::FUNCTION:
1216 return ParseFunctionDeclaration(NULL, ok);
1219 return ParseVariableStatement(kModuleElement, NULL, ok);
1221 return ParseImportDeclaration(ok);
1223 return ParseExportDeclaration(ok);
1225 Statement* stmt = ParseStatement(labels, CHECK_OK);
1226 // Handle 'module' as a context-sensitive keyword.
1227 if (FLAG_harmony_modules &&
1228 peek() == Token::IDENTIFIER &&
1229 !scanner().HasAnyLineTerminatorBeforeNext() &&
1231 ExpressionStatement* estmt = stmt->AsExpressionStatement();
1232 if (estmt != NULL &&
1233 estmt->expression()->AsVariableProxy() != NULL &&
1234 estmt->expression()->AsVariableProxy()->name()->Equals(
1235 isolate()->heap()->module_symbol()) &&
1236 !scanner().literal_contains_escapes()) {
1237 return ParseModuleDeclaration(NULL, ok);
1246 Block* Parser::ParseModuleDeclaration(ZoneStringList* names, bool* ok) {
1247 // ModuleDeclaration:
1248 // 'module' Identifier Module
1250 // Create new block with one expected declaration.
1251 Block* block = factory()->NewBlock(NULL, 1, true);
1252 Handle<String> name = ParseIdentifier(CHECK_OK);
1255 if (FLAG_print_interface_details)
1256 PrintF("# Module %s...\n", name->ToAsciiArray());
1259 Module* module = ParseModule(CHECK_OK);
1260 VariableProxy* proxy = NewUnresolved(name, LET, module->interface());
1261 Declaration* declaration =
1262 factory()->NewModuleDeclaration(proxy, module, top_scope_);
1263 Declare(declaration, true, CHECK_OK);
1266 if (FLAG_print_interface_details)
1267 PrintF("# Module %s.\n", name->ToAsciiArray());
1269 if (FLAG_print_interfaces) {
1270 PrintF("module %s : ", name->ToAsciiArray());
1271 module->interface()->Print();
1275 // TODO(rossberg): Add initialization statement to block.
1277 if (names) names->Add(name);
1282 Module* Parser::ParseModule(bool* ok) {
1284 // '{' ModuleElement '}'
1285 // '=' ModulePath ';'
1290 return ParseModuleLiteral(ok);
1292 case Token::ASSIGN: {
1293 Expect(Token::ASSIGN, CHECK_OK);
1294 Module* result = ParseModulePath(CHECK_OK);
1295 ExpectSemicolon(CHECK_OK);
1300 ExpectContextualKeyword("at", CHECK_OK);
1301 Module* result = ParseModuleUrl(CHECK_OK);
1302 ExpectSemicolon(CHECK_OK);
1309 Module* Parser::ParseModuleLiteral(bool* ok) {
1311 // '{' ModuleElement '}'
1313 // Construct block expecting 16 statements.
1314 Block* body = factory()->NewBlock(NULL, 16, false);
1316 if (FLAG_print_interface_details) PrintF("# Literal ");
1318 Scope* scope = NewScope(top_scope_, MODULE_SCOPE);
1320 Expect(Token::LBRACE, CHECK_OK);
1321 scope->set_start_position(scanner().location().beg_pos);
1322 scope->SetLanguageMode(EXTENDED_MODE);
1325 BlockState block_state(this, scope);
1326 TargetCollector collector;
1327 Target target(&this->target_stack_, &collector);
1328 Target target_body(&this->target_stack_, body);
1329 InitializationBlockFinder block_finder(top_scope_, target_stack_);
1331 while (peek() != Token::RBRACE) {
1332 Statement* stat = ParseModuleElement(NULL, CHECK_OK);
1333 if (stat && !stat->IsEmpty()) {
1334 body->AddStatement(stat);
1335 block_finder.Update(stat);
1340 Expect(Token::RBRACE, CHECK_OK);
1341 scope->set_end_position(scanner().location().end_pos);
1342 body->set_scope(scope);
1344 // Instance objects have to be created ahead of time (before code generation
1345 // linking them) because of potentially cyclic references between them.
1346 // We create them here, to avoid another pass over the AST.
1347 Interface* interface = scope->interface();
1348 interface->MakeModule(ok);
1350 interface->MakeSingleton(Isolate::Current()->factory()->NewJSModule(), ok);
1352 interface->Freeze(ok);
1354 return factory()->NewModuleLiteral(body, interface);
1358 Module* Parser::ParseModulePath(bool* ok) {
1361 // ModulePath '.' Identifier
1363 Module* result = ParseModuleVariable(CHECK_OK);
1364 while (Check(Token::PERIOD)) {
1365 Handle<String> name = ParseIdentifierName(CHECK_OK);
1367 if (FLAG_print_interface_details)
1368 PrintF("# Path .%s ", name->ToAsciiArray());
1370 Module* member = factory()->NewModulePath(result, name);
1371 result->interface()->Add(name, member->interface(), ok);
1374 if (FLAG_print_interfaces) {
1375 PrintF("PATH TYPE ERROR at '%s'\n", name->ToAsciiArray());
1377 result->interface()->Print();
1379 member->interface()->Print();
1382 ReportMessage("invalid_module_path", Vector<Handle<String> >(&name, 1));
1392 Module* Parser::ParseModuleVariable(bool* ok) {
1396 Handle<String> name = ParseIdentifier(CHECK_OK);
1398 if (FLAG_print_interface_details)
1399 PrintF("# Module variable %s ", name->ToAsciiArray());
1401 VariableProxy* proxy = top_scope_->NewUnresolved(
1402 factory(), name, scanner().location().beg_pos, Interface::NewModule());
1404 return factory()->NewModuleVariable(proxy);
1408 Module* Parser::ParseModuleUrl(bool* ok) {
1412 Expect(Token::STRING, CHECK_OK);
1413 Handle<String> symbol = GetSymbol(CHECK_OK);
1415 // TODO(ES6): Request JS resource from environment...
1418 if (FLAG_print_interface_details) PrintF("# Url ");
1421 Module* result = factory()->NewModuleUrl(symbol);
1422 Interface* interface = result->interface();
1423 interface->MakeSingleton(Isolate::Current()->factory()->NewJSModule(), ok);
1425 interface->Freeze(ok);
1431 Module* Parser::ParseModuleSpecifier(bool* ok) {
1436 if (peek() == Token::STRING) {
1437 return ParseModuleUrl(ok);
1439 return ParseModulePath(ok);
1444 Block* Parser::ParseImportDeclaration(bool* ok) {
1445 // ImportDeclaration:
1446 // 'import' IdentifierName (',' IdentifierName)* 'from' ModuleSpecifier ';'
1448 // TODO(ES6): implement destructuring ImportSpecifiers
1450 Expect(Token::IMPORT, CHECK_OK);
1451 ZoneStringList names(1);
1453 Handle<String> name = ParseIdentifierName(CHECK_OK);
1455 while (peek() == Token::COMMA) {
1456 Consume(Token::COMMA);
1457 name = ParseIdentifierName(CHECK_OK);
1461 ExpectContextualKeyword("from", CHECK_OK);
1462 Module* module = ParseModuleSpecifier(CHECK_OK);
1463 ExpectSemicolon(CHECK_OK);
1465 // Generate a separate declaration for each identifier.
1466 // TODO(ES6): once we implement destructuring, make that one declaration.
1467 Block* block = factory()->NewBlock(NULL, 1, true);
1468 for (int i = 0; i < names.length(); ++i) {
1470 if (FLAG_print_interface_details)
1471 PrintF("# Import %s ", names[i]->ToAsciiArray());
1473 Interface* interface = Interface::NewUnknown();
1474 module->interface()->Add(names[i], interface, ok);
1477 if (FLAG_print_interfaces) {
1478 PrintF("IMPORT TYPE ERROR at '%s'\n", names[i]->ToAsciiArray());
1480 module->interface()->Print();
1483 ReportMessage("invalid_module_path", Vector<Handle<String> >(&name, 1));
1486 VariableProxy* proxy = NewUnresolved(names[i], LET, interface);
1487 Declaration* declaration =
1488 factory()->NewImportDeclaration(proxy, module, top_scope_);
1489 Declare(declaration, true, CHECK_OK);
1490 // TODO(rossberg): Add initialization statement to block.
1497 Statement* Parser::ParseExportDeclaration(bool* ok) {
1498 // ExportDeclaration:
1499 // 'export' Identifier (',' Identifier)* ';'
1500 // 'export' VariableDeclaration
1501 // 'export' FunctionDeclaration
1502 // 'export' ModuleDeclaration
1504 // TODO(ES6): implement structuring ExportSpecifiers
1506 Expect(Token::EXPORT, CHECK_OK);
1508 Statement* result = NULL;
1509 ZoneStringList names(1);
1511 case Token::IDENTIFIER: {
1512 Handle<String> name = ParseIdentifier(CHECK_OK);
1513 // Handle 'module' as a context-sensitive keyword.
1514 if (!name->IsEqualTo(CStrVector("module"))) {
1516 while (peek() == Token::COMMA) {
1517 Consume(Token::COMMA);
1518 name = ParseIdentifier(CHECK_OK);
1521 ExpectSemicolon(CHECK_OK);
1522 result = factory()->NewEmptyStatement();
1524 result = ParseModuleDeclaration(&names, CHECK_OK);
1529 case Token::FUNCTION:
1530 result = ParseFunctionDeclaration(&names, CHECK_OK);
1536 result = ParseVariableStatement(kModuleElement, &names, CHECK_OK);
1541 ReportUnexpectedToken(scanner().current_token());
1545 // Extract declared names into export declarations and interface.
1546 Interface* interface = top_scope_->interface();
1547 for (int i = 0; i < names.length(); ++i) {
1549 if (FLAG_print_interface_details)
1550 PrintF("# Export %s ", names[i]->ToAsciiArray());
1552 Interface* inner = Interface::NewUnknown();
1553 interface->Add(names[i], inner, CHECK_OK);
1554 VariableProxy* proxy = NewUnresolved(names[i], LET, inner);
1556 // TODO(rossberg): Rethink whether we actually need to store export
1557 // declarations (for compilation?).
1558 // ExportDeclaration* declaration =
1559 // factory()->NewExportDeclaration(proxy, top_scope_);
1560 // top_scope_->AddDeclaration(declaration);
1563 ASSERT(result != NULL);
1568 Statement* Parser::ParseBlockElement(ZoneStringList* labels,
1570 // (Ecma 262 5th Edition, clause 14):
1573 // FunctionDeclaration
1575 // In harmony mode we allow additionally the following productions
1576 // BlockElement (aka SourceElement):
1581 case Token::FUNCTION:
1582 return ParseFunctionDeclaration(NULL, ok);
1585 return ParseVariableStatement(kModuleElement, NULL, ok);
1587 return ParseStatement(labels, ok);
1592 Statement* Parser::ParseStatement(ZoneStringList* labels, bool* ok) {
1595 // VariableStatement
1597 // ExpressionStatement
1599 // IterationStatement
1600 // ContinueStatement
1604 // LabelledStatement
1608 // DebuggerStatement
1610 // Note: Since labels can only be used by 'break' and 'continue'
1611 // statements, which themselves are only valid within blocks,
1612 // iterations or 'switch' statements (i.e., BreakableStatements),
1613 // labels can be simply ignored in all other cases; except for
1614 // trivial labeled break statements 'label: break label' which is
1615 // parsed into an empty statement.
1617 // Keep the source position of the statement
1618 int statement_pos = scanner().peek_location().beg_pos;
1619 Statement* stmt = NULL;
1622 return ParseBlock(labels, ok);
1624 case Token::CONST: // fall through
1627 stmt = ParseVariableStatement(kStatement, NULL, ok);
1630 case Token::SEMICOLON:
1632 return factory()->NewEmptyStatement();
1635 stmt = ParseIfStatement(labels, ok);
1639 stmt = ParseDoWhileStatement(labels, ok);
1643 stmt = ParseWhileStatement(labels, ok);
1647 stmt = ParseForStatement(labels, ok);
1650 case Token::CONTINUE:
1651 stmt = ParseContinueStatement(ok);
1655 stmt = ParseBreakStatement(labels, ok);
1659 stmt = ParseReturnStatement(ok);
1663 stmt = ParseWithStatement(labels, ok);
1667 stmt = ParseSwitchStatement(labels, ok);
1671 stmt = ParseThrowStatement(ok);
1675 // NOTE: It is somewhat complicated to have labels on
1676 // try-statements. When breaking out of a try-finally statement,
1677 // one must take great care not to treat it as a
1678 // fall-through. It is much easier just to wrap the entire
1679 // try-statement in a statement block and put the labels there
1680 Block* result = factory()->NewBlock(labels, 1, false);
1681 Target target(&this->target_stack_, result);
1682 TryStatement* statement = ParseTryStatement(CHECK_OK);
1684 statement->set_statement_pos(statement_pos);
1686 if (result) result->AddStatement(statement);
1690 case Token::FUNCTION: {
1691 // FunctionDeclaration is only allowed in the context of SourceElements
1692 // (Ecma 262 5th Edition, clause 14):
1695 // FunctionDeclaration
1696 // Common language extension is to allow function declaration in place
1697 // of any statement. This language extension is disabled in strict mode.
1698 if (!top_scope_->is_classic_mode()) {
1699 ReportMessageAt(scanner().peek_location(), "strict_function",
1700 Vector<const char*>::empty());
1704 return ParseFunctionDeclaration(NULL, ok);
1707 case Token::DEBUGGER:
1708 stmt = ParseDebuggerStatement(ok);
1712 stmt = ParseExpressionOrLabelledStatement(labels, ok);
1715 // Store the source position of the statement
1716 if (stmt != NULL) stmt->set_statement_pos(statement_pos);
1721 VariableProxy* Parser::NewUnresolved(
1722 Handle<String> name, VariableMode mode, Interface* interface) {
1723 // If we are inside a function, a declaration of a var/const variable is a
1724 // truly local variable, and the scope of the variable is always the function
1726 // Let/const variables in harmony mode are always added to the immediately
1728 return DeclarationScope(mode)->NewUnresolved(
1729 factory(), name, scanner().location().beg_pos, interface);
1733 void Parser::Declare(Declaration* declaration, bool resolve, bool* ok) {
1734 VariableProxy* proxy = declaration->proxy();
1735 Handle<String> name = proxy->name();
1736 VariableMode mode = declaration->mode();
1737 Scope* declaration_scope = DeclarationScope(mode);
1738 Variable* var = NULL;
1740 // If a function scope exists, then we can statically declare this
1741 // variable and also set its mode. In any case, a Declaration node
1742 // will be added to the scope so that the declaration can be added
1743 // to the corresponding activation frame at runtime if necessary.
1744 // For instance declarations inside an eval scope need to be added
1745 // to the calling function context.
1746 // Similarly, strict mode eval scope does not leak variable declarations to
1747 // the caller's scope so we declare all locals, too.
1748 // Also for block scoped let/const bindings the variable can be
1749 // statically declared.
1750 if (declaration_scope->is_function_scope() ||
1751 declaration_scope->is_strict_or_extended_eval_scope() ||
1752 declaration_scope->is_block_scope() ||
1753 declaration_scope->is_module_scope() ||
1754 declaration->AsModuleDeclaration() != NULL) {
1755 // Declare the variable in the function scope.
1756 var = declaration_scope->LocalLookup(name);
1758 // Declare the name.
1759 var = declaration_scope->DeclareLocal(
1760 name, mode, declaration->initialization(), proxy->interface());
1762 // The name was declared in this scope before; check for conflicting
1763 // re-declarations. We have a conflict if either of the declarations is
1764 // not a var. There is similar code in runtime.cc in the Declare
1765 // functions. The function CheckNonConflictingScope checks for conflicting
1766 // var and let bindings from different scopes whereas this is a check for
1767 // conflicting declarations within the same scope. This check also covers
1769 // function () { let x; { var x; } }
1771 // because the var declaration is hoisted to the function scope where 'x'
1772 // is already bound.
1773 if ((mode != VAR) || (var->mode() != VAR)) {
1774 // We only have vars, consts and lets in declarations.
1775 ASSERT(var->mode() == VAR ||
1776 var->mode() == CONST ||
1777 var->mode() == CONST_HARMONY ||
1778 var->mode() == LET);
1779 if (is_extended_mode()) {
1780 // In harmony mode we treat re-declarations as early errors. See
1781 // ES5 16 for a definition of early errors.
1782 SmartArrayPointer<char> c_string = name->ToCString(DISALLOW_NULLS);
1783 const char* elms[2] = { "Variable", *c_string };
1784 Vector<const char*> args(elms, 2);
1785 ReportMessage("redeclaration", args);
1789 const char* type = (var->mode() == VAR)
1790 ? "var" : var->is_const_mode() ? "const" : "let";
1791 Handle<String> type_string =
1792 isolate()->factory()->NewStringFromUtf8(CStrVector(type), TENURED);
1793 Expression* expression =
1794 NewThrowTypeError(isolate()->factory()->redeclaration_symbol(),
1796 declaration_scope->SetIllegalRedeclaration(expression);
1801 // We add a declaration node for every declaration. The compiler
1802 // will only generate code if necessary. In particular, declarations
1803 // for inner local variables that do not represent functions won't
1804 // result in any generated code.
1806 // Note that we always add an unresolved proxy even if it's not
1807 // used, simply because we don't know in this method (w/o extra
1808 // parameters) if the proxy is needed or not. The proxy will be
1809 // bound during variable resolution time unless it was pre-bound
1812 // WARNING: This will lead to multiple declaration nodes for the
1813 // same variable if it is declared several times. This is not a
1814 // semantic issue as long as we keep the source order, but it may be
1815 // a performance issue since it may lead to repeated
1816 // Runtime::DeclareContextSlot() calls.
1817 declaration_scope->AddDeclaration(declaration);
1819 if ((mode == CONST || mode == CONST_HARMONY) &&
1820 declaration_scope->is_global_scope()) {
1821 // For global const variables we bind the proxy to a variable.
1822 ASSERT(resolve); // should be set by all callers
1823 Variable::Kind kind = Variable::NORMAL;
1824 var = new(zone()) Variable(declaration_scope,
1829 kNeedsInitialization);
1830 } else if (declaration_scope->is_eval_scope() &&
1831 declaration_scope->is_classic_mode()) {
1832 // For variable declarations in a non-strict eval scope the proxy is bound
1833 // to a lookup variable to force a dynamic declaration using the
1834 // DeclareContextSlot runtime function.
1835 Variable::Kind kind = Variable::NORMAL;
1836 var = new(zone()) Variable(declaration_scope,
1841 declaration->initialization());
1842 var->AllocateTo(Variable::LOOKUP, -1);
1846 // If requested and we have a local variable, bind the proxy to the variable
1847 // at parse-time. This is used for functions (and consts) declared inside
1848 // statements: the corresponding function (or const) variable must be in the
1849 // function scope and not a statement-local scope, e.g. as provided with a
1850 // 'with' statement:
1856 // which is translated into:
1859 // // in this case this is not: 'var f; f = function () {};'
1860 // var f = function () {};
1863 // Note that if 'f' is accessed from inside the 'with' statement, it
1864 // will be allocated in the context (because we must be able to look
1865 // it up dynamically) but it will also be accessed statically, i.e.,
1866 // with a context slot index and a context chain length for this
1867 // initialization code. Thus, inside the 'with' statement, we need
1868 // both access to the static and the dynamic context chain; the
1869 // runtime needs to provide both.
1870 if (resolve && var != NULL) {
1873 if (FLAG_harmony_modules) {
1876 if (FLAG_print_interface_details)
1877 PrintF("# Declare %s\n", var->name()->ToAsciiArray());
1879 proxy->interface()->Unify(var->interface(), &ok);
1882 if (FLAG_print_interfaces) {
1883 PrintF("DECLARE TYPE ERROR\n");
1885 proxy->interface()->Print();
1887 var->interface()->Print();
1890 ReportMessage("module_type_error", Vector<Handle<String> >(&name, 1));
1897 // Language extension which is only enabled for source files loaded
1898 // through the API's extension mechanism. A native function
1899 // declaration is resolved by looking up the function through a
1900 // callback provided by the extension.
1901 Statement* Parser::ParseNativeDeclaration(bool* ok) {
1902 Expect(Token::FUNCTION, CHECK_OK);
1903 Handle<String> name = ParseIdentifier(CHECK_OK);
1904 Expect(Token::LPAREN, CHECK_OK);
1905 bool done = (peek() == Token::RPAREN);
1907 ParseIdentifier(CHECK_OK);
1908 done = (peek() == Token::RPAREN);
1910 Expect(Token::COMMA, CHECK_OK);
1913 Expect(Token::RPAREN, CHECK_OK);
1914 Expect(Token::SEMICOLON, CHECK_OK);
1916 // Make sure that the function containing the native declaration
1917 // isn't lazily compiled. The extension structures are only
1918 // accessible while parsing the first time not when reparsing
1919 // because of lazy compilation.
1920 DeclarationScope(VAR)->ForceEagerCompilation();
1922 // Compute the function template for the native function.
1923 v8::Handle<v8::FunctionTemplate> fun_template =
1924 extension_->GetNativeFunction(v8::Utils::ToLocal(name));
1925 ASSERT(!fun_template.IsEmpty());
1927 // Instantiate the function and create a shared function info from it.
1928 Handle<JSFunction> fun = Utils::OpenHandle(*fun_template->GetFunction());
1929 const int literals = fun->NumberOfLiterals();
1930 Handle<Code> code = Handle<Code>(fun->shared()->code());
1931 Handle<Code> construct_stub = Handle<Code>(fun->shared()->construct_stub());
1932 Handle<SharedFunctionInfo> shared =
1933 isolate()->factory()->NewSharedFunctionInfo(name, literals, code,
1934 Handle<ScopeInfo>(fun->shared()->scope_info()));
1935 shared->set_construct_stub(*construct_stub);
1937 // Copy the function data to the shared function info.
1938 shared->set_function_data(fun->shared()->function_data());
1939 int parameters = fun->shared()->formal_parameter_count();
1940 shared->set_formal_parameter_count(parameters);
1942 // TODO(1240846): It's weird that native function declarations are
1943 // introduced dynamically when we meet their declarations, whereas
1944 // other functions are set up when entering the surrounding scope.
1945 VariableProxy* proxy = NewUnresolved(name, VAR);
1946 Declaration* declaration =
1947 factory()->NewVariableDeclaration(proxy, VAR, top_scope_);
1948 Declare(declaration, true, CHECK_OK);
1949 SharedFunctionInfoLiteral* lit =
1950 factory()->NewSharedFunctionInfoLiteral(shared);
1951 return factory()->NewExpressionStatement(
1952 factory()->NewAssignment(
1953 Token::INIT_VAR, proxy, lit, RelocInfo::kNoPosition));
1957 Statement* Parser::ParseFunctionDeclaration(ZoneStringList* names, bool* ok) {
1958 // FunctionDeclaration ::
1959 // 'function' Identifier '(' FormalParameterListopt ')' '{' FunctionBody '}'
1960 Expect(Token::FUNCTION, CHECK_OK);
1961 int function_token_position = scanner().location().beg_pos;
1962 bool is_strict_reserved = false;
1963 Handle<String> name = ParseIdentifierOrStrictReservedWord(
1964 &is_strict_reserved, CHECK_OK);
1965 FunctionLiteral* fun = ParseFunctionLiteral(name,
1967 function_token_position,
1968 FunctionLiteral::DECLARATION,
1970 // Even if we're not at the top-level of the global or a function
1971 // scope, we treat is as such and introduce the function with it's
1972 // initial value upon entering the corresponding scope.
1973 VariableMode mode = is_extended_mode() ? LET : VAR;
1974 VariableProxy* proxy = NewUnresolved(name, mode);
1975 Declaration* declaration =
1976 factory()->NewFunctionDeclaration(proxy, mode, fun, top_scope_);
1977 Declare(declaration, true, CHECK_OK);
1978 if (names) names->Add(name);
1979 return factory()->NewEmptyStatement();
1983 Block* Parser::ParseBlock(ZoneStringList* labels, bool* ok) {
1984 if (top_scope_->is_extended_mode()) return ParseScopedBlock(labels, ok);
1987 // '{' Statement* '}'
1989 // Note that a Block does not introduce a new execution scope!
1990 // (ECMA-262, 3rd, 12.2)
1992 // Construct block expecting 16 statements.
1993 Block* result = factory()->NewBlock(labels, 16, false);
1994 Target target(&this->target_stack_, result);
1995 Expect(Token::LBRACE, CHECK_OK);
1996 InitializationBlockFinder block_finder(top_scope_, target_stack_);
1997 while (peek() != Token::RBRACE) {
1998 Statement* stat = ParseStatement(NULL, CHECK_OK);
1999 if (stat && !stat->IsEmpty()) {
2000 result->AddStatement(stat);
2001 block_finder.Update(stat);
2004 Expect(Token::RBRACE, CHECK_OK);
2009 Block* Parser::ParseScopedBlock(ZoneStringList* labels, bool* ok) {
2010 // The harmony mode uses block elements instead of statements.
2013 // '{' BlockElement* '}'
2015 // Construct block expecting 16 statements.
2016 Block* body = factory()->NewBlock(labels, 16, false);
2017 Scope* block_scope = NewScope(top_scope_, BLOCK_SCOPE);
2019 // Parse the statements and collect escaping labels.
2020 Expect(Token::LBRACE, CHECK_OK);
2021 block_scope->set_start_position(scanner().location().beg_pos);
2022 { BlockState block_state(this, block_scope);
2023 TargetCollector collector;
2024 Target target(&this->target_stack_, &collector);
2025 Target target_body(&this->target_stack_, body);
2026 InitializationBlockFinder block_finder(top_scope_, target_stack_);
2028 while (peek() != Token::RBRACE) {
2029 Statement* stat = ParseBlockElement(NULL, CHECK_OK);
2030 if (stat && !stat->IsEmpty()) {
2031 body->AddStatement(stat);
2032 block_finder.Update(stat);
2036 Expect(Token::RBRACE, CHECK_OK);
2037 block_scope->set_end_position(scanner().location().end_pos);
2038 block_scope = block_scope->FinalizeBlockScope();
2039 body->set_scope(block_scope);
2044 Block* Parser::ParseVariableStatement(VariableDeclarationContext var_context,
2045 ZoneStringList* names,
2047 // VariableStatement ::
2048 // VariableDeclarations ';'
2050 Handle<String> ignore;
2052 ParseVariableDeclarations(var_context, NULL, names, &ignore, CHECK_OK);
2053 ExpectSemicolon(CHECK_OK);
2058 bool Parser::IsEvalOrArguments(Handle<String> string) {
2059 return string.is_identical_to(isolate()->factory()->eval_symbol()) ||
2060 string.is_identical_to(isolate()->factory()->arguments_symbol());
2064 // If the variable declaration declares exactly one non-const
2065 // variable, then *out is set to that variable. In all other cases,
2066 // *out is untouched; in particular, it is the caller's responsibility
2067 // to initialize it properly. This mechanism is used for the parsing
2068 // of 'for-in' loops.
2069 Block* Parser::ParseVariableDeclarations(
2070 VariableDeclarationContext var_context,
2071 VariableDeclarationProperties* decl_props,
2072 ZoneStringList* names,
2073 Handle<String>* out,
2075 // VariableDeclarations ::
2076 // ('var' | 'const' | 'let') (Identifier ('=' AssignmentExpression)?)+[',']
2078 // The ES6 Draft Rev3 specifies the following grammar for const declarations
2080 // ConstDeclaration ::
2081 // const ConstBinding (',' ConstBinding)* ';'
2083 // Identifier '=' AssignmentExpression
2087 // BindingPattern '=' AssignmentExpression
2088 VariableMode mode = VAR;
2089 // True if the binding needs initialization. 'let' and 'const' declared
2090 // bindings are created uninitialized by their declaration nodes and
2091 // need initialization. 'var' declared bindings are always initialized
2092 // immediately by their declaration nodes.
2093 bool needs_init = false;
2094 bool is_const = false;
2095 Token::Value init_op = Token::INIT_VAR;
2096 if (peek() == Token::VAR) {
2097 Consume(Token::VAR);
2098 } else if (peek() == Token::CONST) {
2099 // TODO(ES6): The ES6 Draft Rev4 section 12.2.2 reads:
2101 // ConstDeclaration : const ConstBinding (',' ConstBinding)* ';'
2103 // * It is a Syntax Error if the code that matches this production is not
2104 // contained in extended code.
2106 // However disallowing const in classic mode will break compatibility with
2107 // existing pages. Therefore we keep allowing const with the old
2108 // non-harmony semantics in classic mode.
2109 Consume(Token::CONST);
2110 switch (top_scope_->language_mode()) {
2113 init_op = Token::INIT_CONST;
2116 ReportMessage("strict_const", Vector<const char*>::empty());
2120 if (var_context == kStatement) {
2121 // In extended mode 'const' declarations are only allowed in source
2122 // element positions.
2123 ReportMessage("unprotected_const", Vector<const char*>::empty());
2127 mode = CONST_HARMONY;
2128 init_op = Token::INIT_CONST_HARMONY;
2132 } else if (peek() == Token::LET) {
2133 // ES6 Draft Rev4 section 12.2.1:
2135 // LetDeclaration : let LetBindingList ;
2137 // * It is a Syntax Error if the code that matches this production is not
2138 // contained in extended code.
2139 if (!is_extended_mode()) {
2140 ReportMessage("illegal_let", Vector<const char*>::empty());
2144 Consume(Token::LET);
2145 if (var_context == kStatement) {
2146 // Let declarations are only allowed in source element positions.
2147 ReportMessage("unprotected_let", Vector<const char*>::empty());
2153 init_op = Token::INIT_LET;
2155 UNREACHABLE(); // by current callers
2158 Scope* declaration_scope = DeclarationScope(mode);
2160 // The scope of a var/const declared variable anywhere inside a function
2161 // is the entire function (ECMA-262, 3rd, 10.1.3, and 12.2). Thus we can
2162 // transform a source-level var/const declaration into a (Function)
2163 // Scope declaration, and rewrite the source-level initialization into an
2164 // assignment statement. We use a block to collect multiple assignments.
2166 // We mark the block as initializer block because we don't want the
2167 // rewriter to add a '.result' assignment to such a block (to get compliant
2168 // behavior for code such as print(eval('var x = 7')), and for cosmetic
2169 // reasons when pretty-printing. Also, unless an assignment (initialization)
2170 // is inside an initializer block, it is ignored.
2172 // Create new block with one expected declaration.
2173 Block* block = factory()->NewBlock(NULL, 1, true);
2174 int nvars = 0; // the number of variables declared
2175 Handle<String> name;
2177 if (fni_ != NULL) fni_->Enter();
2179 // Parse variable name.
2180 if (nvars > 0) Consume(Token::COMMA);
2181 name = ParseIdentifier(CHECK_OK);
2182 if (fni_ != NULL) fni_->PushVariableName(name);
2184 // Strict mode variables may not be named eval or arguments
2185 if (!declaration_scope->is_classic_mode() && IsEvalOrArguments(name)) {
2186 ReportMessage("strict_var_name", Vector<const char*>::empty());
2191 // Declare variable.
2192 // Note that we *always* must treat the initial value via a separate init
2193 // assignment for variables and constants because the value must be assigned
2194 // when the variable is encountered in the source. But the variable/constant
2195 // is declared (and set to 'undefined') upon entering the function within
2196 // which the variable or constant is declared. Only function variables have
2197 // an initial value in the declaration (because they are initialized upon
2198 // entering the function).
2200 // If we have a const declaration, in an inner scope, the proxy is always
2201 // bound to the declared variable (independent of possibly surrounding with
2203 // For let/const declarations in harmony mode, we can also immediately
2204 // pre-resolve the proxy because it resides in the same scope as the
2206 VariableProxy* proxy = NewUnresolved(name, mode);
2207 Declaration* declaration =
2208 factory()->NewVariableDeclaration(proxy, mode, top_scope_);
2209 Declare(declaration, mode != VAR, CHECK_OK);
2211 if (declaration_scope->num_var_or_const() > kMaxNumFunctionLocals) {
2212 ReportMessageAt(scanner().location(), "too_many_variables",
2213 Vector<const char*>::empty());
2217 if (names) names->Add(name);
2219 // Parse initialization expression if present and/or needed. A
2220 // declaration of the form:
2224 // is syntactic sugar for:
2228 // In particular, we need to re-lookup 'v' (in top_scope_, not
2229 // declaration_scope) as it may be a different 'v' than the 'v' in the
2230 // declaration (e.g., if we are inside a 'with' statement or 'catch'
2233 // However, note that const declarations are different! A const
2234 // declaration of the form:
2238 // is *not* syntactic sugar for:
2242 // The "variable" c initialized to x is the same as the declared
2243 // one - there is no re-lookup (see the last parameter of the
2244 // Declare() call above).
2246 Scope* initialization_scope = is_const ? declaration_scope : top_scope_;
2247 Expression* value = NULL;
2249 // Harmony consts have non-optional initializers.
2250 if (peek() == Token::ASSIGN || mode == CONST_HARMONY) {
2251 Expect(Token::ASSIGN, CHECK_OK);
2252 position = scanner().location().beg_pos;
2253 value = ParseAssignmentExpression(var_context != kForStatement, CHECK_OK);
2254 // Don't infer if it is "a = function(){...}();"-like expression.
2256 value->AsCall() == NULL &&
2257 value->AsCallNew() == NULL) {
2260 fni_->RemoveLastFunction();
2262 if (decl_props != NULL) *decl_props = kHasInitializers;
2265 // Record the end position of the initializer.
2266 if (proxy->var() != NULL) {
2267 proxy->var()->set_initializer_position(scanner().location().end_pos);
2270 // Make sure that 'const x' and 'let x' initialize 'x' to undefined.
2271 if (value == NULL && needs_init) {
2272 value = GetLiteralUndefined();
2275 // Global variable declarations must be compiled in a specific
2276 // way. When the script containing the global variable declaration
2277 // is entered, the global variable must be declared, so that if it
2278 // doesn't exist (on the global object itself, see ES5 errata) it
2279 // gets created with an initial undefined value. This is handled
2280 // by the declarations part of the function representing the
2281 // top-level global code; see Runtime::DeclareGlobalVariable. If
2282 // it already exists (in the object or in a prototype), it is
2283 // *not* touched until the variable declaration statement is
2286 // Executing the variable declaration statement will always
2287 // guarantee to give the global object a "local" variable; a
2288 // variable defined in the global object and not in any
2289 // prototype. This way, global variable declarations can shadow
2290 // properties in the prototype chain, but only after the variable
2291 // declaration statement has been executed. This is important in
2292 // browsers where the global object (window) has lots of
2293 // properties defined in prototype objects.
2294 if (initialization_scope->is_global_scope()) {
2295 // Compute the arguments for the runtime call.
2296 ZoneList<Expression*>* arguments = new(zone()) ZoneList<Expression*>(3);
2297 // We have at least 1 parameter.
2298 arguments->Add(factory()->NewLiteral(name));
2299 CallRuntime* initialize;
2302 arguments->Add(value);
2303 value = NULL; // zap the value to avoid the unnecessary assignment
2306 if (top_scope_->is_qml_mode() && !Isolate::Current()->global()->HasProperty(*name))
2308 arguments->Add(factory()->NewNumberLiteral(qml_mode));
2310 // Construct the call to Runtime_InitializeConstGlobal
2311 // and add it to the initialization statement block.
2312 // Note that the function does different things depending on
2313 // the number of arguments (1 or 2).
2314 initialize = factory()->NewCallRuntime(
2315 isolate()->factory()->InitializeConstGlobal_symbol(),
2316 Runtime::FunctionForId(Runtime::kInitializeConstGlobal),
2320 // We may want to pass singleton to avoid Literal allocations.
2321 LanguageMode language_mode = initialization_scope->language_mode();
2322 arguments->Add(factory()->NewNumberLiteral(language_mode));
2325 if (top_scope_->is_qml_mode() && !Isolate::Current()->global()->HasProperty(*name))
2327 arguments->Add(factory()->NewNumberLiteral(qml_mode));
2329 // Be careful not to assign a value to the global variable if
2330 // we're in a with. The initialization value should not
2331 // necessarily be stored in the global object in that case,
2332 // which is why we need to generate a separate assignment node.
2333 if (value != NULL && !inside_with()) {
2334 arguments->Add(value);
2335 value = NULL; // zap the value to avoid the unnecessary assignment
2338 // Construct the call to Runtime_InitializeVarGlobal
2339 // and add it to the initialization statement block.
2340 // Note that the function does different things depending on
2341 // the number of arguments (2 or 3).
2342 initialize = factory()->NewCallRuntime(
2343 isolate()->factory()->InitializeVarGlobal_symbol(),
2344 Runtime::FunctionForId(Runtime::kInitializeVarGlobal),
2348 block->AddStatement(factory()->NewExpressionStatement(initialize));
2349 } else if (needs_init) {
2350 // Constant initializations always assign to the declared constant which
2351 // is always at the function scope level. This is only relevant for
2352 // dynamically looked-up variables and constants (the start context for
2353 // constant lookups is always the function context, while it is the top
2354 // context for var declared variables). Sigh...
2355 // For 'let' and 'const' declared variables in harmony mode the
2356 // initialization also always assigns to the declared variable.
2357 ASSERT(proxy != NULL);
2358 ASSERT(proxy->var() != NULL);
2359 ASSERT(value != NULL);
2360 Assignment* assignment =
2361 factory()->NewAssignment(init_op, proxy, value, position);
2362 block->AddStatement(factory()->NewExpressionStatement(assignment));
2366 // Add an assignment node to the initialization statement block if we still
2367 // have a pending initialization value.
2368 if (value != NULL) {
2369 ASSERT(mode == VAR);
2370 // 'var' initializations are simply assignments (with all the consequences
2371 // if they are inside a 'with' statement - they may change a 'with' object
2373 VariableProxy* proxy =
2374 initialization_scope->NewUnresolved(factory(), name);
2375 Assignment* assignment =
2376 factory()->NewAssignment(init_op, proxy, value, position);
2377 block->AddStatement(factory()->NewExpressionStatement(assignment));
2380 if (fni_ != NULL) fni_->Leave();
2381 } while (peek() == Token::COMMA);
2383 // If there was a single non-const declaration, return it in the output
2384 // parameter for possible use by for/in.
2385 if (nvars == 1 && !is_const) {
2393 static bool ContainsLabel(ZoneStringList* labels, Handle<String> label) {
2394 ASSERT(!label.is_null());
2396 for (int i = labels->length(); i-- > 0; )
2397 if (labels->at(i).is_identical_to(label))
2404 Statement* Parser::ParseExpressionOrLabelledStatement(ZoneStringList* labels,
2406 // ExpressionStatement | LabelledStatement ::
2408 // Identifier ':' Statement
2409 bool starts_with_idenfifier = peek_any_identifier();
2410 Expression* expr = ParseExpression(true, CHECK_OK);
2411 if (peek() == Token::COLON && starts_with_idenfifier && expr != NULL &&
2412 expr->AsVariableProxy() != NULL &&
2413 !expr->AsVariableProxy()->is_this()) {
2414 // Expression is a single identifier, and not, e.g., a parenthesized
2416 VariableProxy* var = expr->AsVariableProxy();
2417 Handle<String> label = var->name();
2418 // TODO(1240780): We don't check for redeclaration of labels
2419 // during preparsing since keeping track of the set of active
2420 // labels requires nontrivial changes to the way scopes are
2421 // structured. However, these are probably changes we want to
2422 // make later anyway so we should go back and fix this then.
2423 if (ContainsLabel(labels, label) || TargetStackContainsLabel(label)) {
2424 SmartArrayPointer<char> c_string = label->ToCString(DISALLOW_NULLS);
2425 const char* elms[2] = { "Label", *c_string };
2426 Vector<const char*> args(elms, 2);
2427 ReportMessage("redeclaration", args);
2431 if (labels == NULL) labels = new(zone()) ZoneStringList(4);
2433 // Remove the "ghost" variable that turned out to be a label
2434 // from the top scope. This way, we don't try to resolve it
2435 // during the scope processing.
2436 top_scope_->RemoveUnresolved(var);
2437 Expect(Token::COLON, CHECK_OK);
2438 return ParseStatement(labels, ok);
2441 // If we have an extension, we allow a native function declaration.
2442 // A native function declaration starts with "native function" with
2443 // no line-terminator between the two words.
2444 if (extension_ != NULL &&
2445 peek() == Token::FUNCTION &&
2446 !scanner().HasAnyLineTerminatorBeforeNext() &&
2448 expr->AsVariableProxy() != NULL &&
2449 expr->AsVariableProxy()->name()->Equals(
2450 isolate()->heap()->native_symbol()) &&
2451 !scanner().literal_contains_escapes()) {
2452 return ParseNativeDeclaration(ok);
2455 // Parsed expression statement, or the context-sensitive 'module' keyword.
2456 // Only expect semicolon in the former case.
2457 if (!FLAG_harmony_modules ||
2458 peek() != Token::IDENTIFIER ||
2459 scanner().HasAnyLineTerminatorBeforeNext() ||
2460 expr->AsVariableProxy() == NULL ||
2461 !expr->AsVariableProxy()->name()->Equals(
2462 isolate()->heap()->module_symbol()) ||
2463 scanner().literal_contains_escapes()) {
2464 ExpectSemicolon(CHECK_OK);
2466 return factory()->NewExpressionStatement(expr);
2470 IfStatement* Parser::ParseIfStatement(ZoneStringList* labels, bool* ok) {
2472 // 'if' '(' Expression ')' Statement ('else' Statement)?
2474 Expect(Token::IF, CHECK_OK);
2475 Expect(Token::LPAREN, CHECK_OK);
2476 Expression* condition = ParseExpression(true, CHECK_OK);
2477 Expect(Token::RPAREN, CHECK_OK);
2478 Statement* then_statement = ParseStatement(labels, CHECK_OK);
2479 Statement* else_statement = NULL;
2480 if (peek() == Token::ELSE) {
2482 else_statement = ParseStatement(labels, CHECK_OK);
2484 else_statement = factory()->NewEmptyStatement();
2486 return factory()->NewIfStatement(condition, then_statement, else_statement);
2490 Statement* Parser::ParseContinueStatement(bool* ok) {
2491 // ContinueStatement ::
2492 // 'continue' Identifier? ';'
2494 Expect(Token::CONTINUE, CHECK_OK);
2495 Handle<String> label = Handle<String>::null();
2496 Token::Value tok = peek();
2497 if (!scanner().HasAnyLineTerminatorBeforeNext() &&
2498 tok != Token::SEMICOLON && tok != Token::RBRACE && tok != Token::EOS) {
2499 label = ParseIdentifier(CHECK_OK);
2501 IterationStatement* target = NULL;
2502 target = LookupContinueTarget(label, CHECK_OK);
2503 if (target == NULL) {
2504 // Illegal continue statement.
2505 const char* message = "illegal_continue";
2506 Vector<Handle<String> > args;
2507 if (!label.is_null()) {
2508 message = "unknown_label";
2509 args = Vector<Handle<String> >(&label, 1);
2511 ReportMessageAt(scanner().location(), message, args);
2515 ExpectSemicolon(CHECK_OK);
2516 return factory()->NewContinueStatement(target);
2520 Statement* Parser::ParseBreakStatement(ZoneStringList* labels, bool* ok) {
2521 // BreakStatement ::
2522 // 'break' Identifier? ';'
2524 Expect(Token::BREAK, CHECK_OK);
2525 Handle<String> label;
2526 Token::Value tok = peek();
2527 if (!scanner().HasAnyLineTerminatorBeforeNext() &&
2528 tok != Token::SEMICOLON && tok != Token::RBRACE && tok != Token::EOS) {
2529 label = ParseIdentifier(CHECK_OK);
2531 // Parse labeled break statements that target themselves into
2532 // empty statements, e.g. 'l1: l2: l3: break l2;'
2533 if (!label.is_null() && ContainsLabel(labels, label)) {
2534 ExpectSemicolon(CHECK_OK);
2535 return factory()->NewEmptyStatement();
2537 BreakableStatement* target = NULL;
2538 target = LookupBreakTarget(label, CHECK_OK);
2539 if (target == NULL) {
2540 // Illegal break statement.
2541 const char* message = "illegal_break";
2542 Vector<Handle<String> > args;
2543 if (!label.is_null()) {
2544 message = "unknown_label";
2545 args = Vector<Handle<String> >(&label, 1);
2547 ReportMessageAt(scanner().location(), message, args);
2551 ExpectSemicolon(CHECK_OK);
2552 return factory()->NewBreakStatement(target);
2556 Statement* Parser::ParseReturnStatement(bool* ok) {
2557 // ReturnStatement ::
2558 // 'return' Expression? ';'
2560 // Consume the return token. It is necessary to do the before
2561 // reporting any errors on it, because of the way errors are
2562 // reported (underlining).
2563 Expect(Token::RETURN, CHECK_OK);
2565 Token::Value tok = peek();
2567 if (scanner().HasAnyLineTerminatorBeforeNext() ||
2568 tok == Token::SEMICOLON ||
2569 tok == Token::RBRACE ||
2570 tok == Token::EOS) {
2571 ExpectSemicolon(CHECK_OK);
2572 result = factory()->NewReturnStatement(GetLiteralUndefined());
2574 Expression* expr = ParseExpression(true, CHECK_OK);
2575 ExpectSemicolon(CHECK_OK);
2576 result = factory()->NewReturnStatement(expr);
2579 // An ECMAScript program is considered syntactically incorrect if it
2580 // contains a return statement that is not within the body of a
2581 // function. See ECMA-262, section 12.9, page 67.
2583 // To be consistent with KJS we report the syntax error at runtime.
2584 Scope* declaration_scope = top_scope_->DeclarationScope();
2585 if (declaration_scope->is_global_scope() ||
2586 declaration_scope->is_eval_scope()) {
2587 Handle<String> type = isolate()->factory()->illegal_return_symbol();
2588 Expression* throw_error = NewThrowSyntaxError(type, Handle<Object>::null());
2589 return factory()->NewExpressionStatement(throw_error);
2595 Statement* Parser::ParseWithStatement(ZoneStringList* labels, bool* ok) {
2597 // 'with' '(' Expression ')' Statement
2599 Expect(Token::WITH, CHECK_OK);
2601 if (!top_scope_->is_classic_mode()) {
2602 ReportMessage("strict_mode_with", Vector<const char*>::empty());
2607 Expect(Token::LPAREN, CHECK_OK);
2608 Expression* expr = ParseExpression(true, CHECK_OK);
2609 Expect(Token::RPAREN, CHECK_OK);
2611 top_scope_->DeclarationScope()->RecordWithStatement();
2612 Scope* with_scope = NewScope(top_scope_, WITH_SCOPE);
2614 { BlockState block_state(this, with_scope);
2615 with_scope->set_start_position(scanner().peek_location().beg_pos);
2616 stmt = ParseStatement(labels, CHECK_OK);
2617 with_scope->set_end_position(scanner().location().end_pos);
2619 return factory()->NewWithStatement(expr, stmt);
2623 CaseClause* Parser::ParseCaseClause(bool* default_seen_ptr, bool* ok) {
2625 // 'case' Expression ':' Statement*
2626 // 'default' ':' Statement*
2628 Expression* label = NULL; // NULL expression indicates default case
2629 if (peek() == Token::CASE) {
2630 Expect(Token::CASE, CHECK_OK);
2631 label = ParseExpression(true, CHECK_OK);
2633 Expect(Token::DEFAULT, CHECK_OK);
2634 if (*default_seen_ptr) {
2635 ReportMessage("multiple_defaults_in_switch",
2636 Vector<const char*>::empty());
2640 *default_seen_ptr = true;
2642 Expect(Token::COLON, CHECK_OK);
2643 int pos = scanner().location().beg_pos;
2644 ZoneList<Statement*>* statements = new(zone()) ZoneList<Statement*>(5);
2645 while (peek() != Token::CASE &&
2646 peek() != Token::DEFAULT &&
2647 peek() != Token::RBRACE) {
2648 Statement* stat = ParseStatement(NULL, CHECK_OK);
2649 statements->Add(stat);
2652 return new(zone()) CaseClause(isolate(), label, statements, pos);
2656 SwitchStatement* Parser::ParseSwitchStatement(ZoneStringList* labels,
2658 // SwitchStatement ::
2659 // 'switch' '(' Expression ')' '{' CaseClause* '}'
2661 SwitchStatement* statement = factory()->NewSwitchStatement(labels);
2662 Target target(&this->target_stack_, statement);
2664 Expect(Token::SWITCH, CHECK_OK);
2665 Expect(Token::LPAREN, CHECK_OK);
2666 Expression* tag = ParseExpression(true, CHECK_OK);
2667 Expect(Token::RPAREN, CHECK_OK);
2669 bool default_seen = false;
2670 ZoneList<CaseClause*>* cases = new(zone()) ZoneList<CaseClause*>(4);
2671 Expect(Token::LBRACE, CHECK_OK);
2672 while (peek() != Token::RBRACE) {
2673 CaseClause* clause = ParseCaseClause(&default_seen, CHECK_OK);
2676 Expect(Token::RBRACE, CHECK_OK);
2678 if (statement) statement->Initialize(tag, cases);
2683 Statement* Parser::ParseThrowStatement(bool* ok) {
2684 // ThrowStatement ::
2685 // 'throw' Expression ';'
2687 Expect(Token::THROW, CHECK_OK);
2688 int pos = scanner().location().beg_pos;
2689 if (scanner().HasAnyLineTerminatorBeforeNext()) {
2690 ReportMessage("newline_after_throw", Vector<const char*>::empty());
2694 Expression* exception = ParseExpression(true, CHECK_OK);
2695 ExpectSemicolon(CHECK_OK);
2697 return factory()->NewExpressionStatement(factory()->NewThrow(exception, pos));
2701 TryStatement* Parser::ParseTryStatement(bool* ok) {
2703 // 'try' Block Catch
2704 // 'try' Block Finally
2705 // 'try' Block Catch Finally
2708 // 'catch' '(' Identifier ')' Block
2713 Expect(Token::TRY, CHECK_OK);
2715 TargetCollector try_collector;
2718 { Target target(&this->target_stack_, &try_collector);
2719 try_block = ParseBlock(NULL, CHECK_OK);
2722 Token::Value tok = peek();
2723 if (tok != Token::CATCH && tok != Token::FINALLY) {
2724 ReportMessage("no_catch_or_finally", Vector<const char*>::empty());
2729 // If we can break out from the catch block and there is a finally block,
2730 // then we will need to collect escaping targets from the catch
2731 // block. Since we don't know yet if there will be a finally block, we
2732 // always collect the targets.
2733 TargetCollector catch_collector;
2734 Scope* catch_scope = NULL;
2735 Variable* catch_variable = NULL;
2736 Block* catch_block = NULL;
2737 Handle<String> name;
2738 if (tok == Token::CATCH) {
2739 Consume(Token::CATCH);
2741 Expect(Token::LPAREN, CHECK_OK);
2742 catch_scope = NewScope(top_scope_, CATCH_SCOPE);
2743 catch_scope->set_start_position(scanner().location().beg_pos);
2744 name = ParseIdentifier(CHECK_OK);
2746 if (!top_scope_->is_classic_mode() && IsEvalOrArguments(name)) {
2747 ReportMessage("strict_catch_variable", Vector<const char*>::empty());
2752 Expect(Token::RPAREN, CHECK_OK);
2754 if (peek() == Token::LBRACE) {
2755 Target target(&this->target_stack_, &catch_collector);
2756 VariableMode mode = is_extended_mode() ? LET : VAR;
2758 catch_scope->DeclareLocal(name, mode, kCreatedInitialized);
2760 BlockState block_state(this, catch_scope);
2761 catch_block = ParseBlock(NULL, CHECK_OK);
2763 Expect(Token::LBRACE, CHECK_OK);
2765 catch_scope->set_end_position(scanner().location().end_pos);
2769 Block* finally_block = NULL;
2770 if (tok == Token::FINALLY || catch_block == NULL) {
2771 Consume(Token::FINALLY);
2772 finally_block = ParseBlock(NULL, CHECK_OK);
2775 // Simplify the AST nodes by converting:
2776 // 'try B0 catch B1 finally B2'
2778 // 'try { try B0 catch B1 } finally B2'
2780 if (catch_block != NULL && finally_block != NULL) {
2781 // If we have both, create an inner try/catch.
2782 ASSERT(catch_scope != NULL && catch_variable != NULL);
2783 int index = current_function_state_->NextHandlerIndex();
2784 TryCatchStatement* statement = factory()->NewTryCatchStatement(
2785 index, try_block, catch_scope, catch_variable, catch_block);
2786 statement->set_escaping_targets(try_collector.targets());
2787 try_block = factory()->NewBlock(NULL, 1, false);
2788 try_block->AddStatement(statement);
2789 catch_block = NULL; // Clear to indicate it's been handled.
2792 TryStatement* result = NULL;
2793 if (catch_block != NULL) {
2794 ASSERT(finally_block == NULL);
2795 ASSERT(catch_scope != NULL && catch_variable != NULL);
2796 int index = current_function_state_->NextHandlerIndex();
2797 result = factory()->NewTryCatchStatement(
2798 index, try_block, catch_scope, catch_variable, catch_block);
2800 ASSERT(finally_block != NULL);
2801 int index = current_function_state_->NextHandlerIndex();
2802 result = factory()->NewTryFinallyStatement(index, try_block, finally_block);
2803 // Combine the jump targets of the try block and the possible catch block.
2804 try_collector.targets()->AddAll(*catch_collector.targets());
2807 result->set_escaping_targets(try_collector.targets());
2812 DoWhileStatement* Parser::ParseDoWhileStatement(ZoneStringList* labels,
2815 // 'do' Statement 'while' '(' Expression ')' ';'
2817 DoWhileStatement* loop = factory()->NewDoWhileStatement(labels);
2818 Target target(&this->target_stack_, loop);
2820 Expect(Token::DO, CHECK_OK);
2821 Statement* body = ParseStatement(NULL, CHECK_OK);
2822 Expect(Token::WHILE, CHECK_OK);
2823 Expect(Token::LPAREN, CHECK_OK);
2826 int position = scanner().location().beg_pos;
2827 loop->set_condition_position(position);
2830 Expression* cond = ParseExpression(true, CHECK_OK);
2831 Expect(Token::RPAREN, CHECK_OK);
2833 // Allow do-statements to be terminated with and without
2834 // semi-colons. This allows code such as 'do;while(0)return' to
2835 // parse, which would not be the case if we had used the
2836 // ExpectSemicolon() functionality here.
2837 if (peek() == Token::SEMICOLON) Consume(Token::SEMICOLON);
2839 if (loop != NULL) loop->Initialize(cond, body);
2844 WhileStatement* Parser::ParseWhileStatement(ZoneStringList* labels, bool* ok) {
2845 // WhileStatement ::
2846 // 'while' '(' Expression ')' Statement
2848 WhileStatement* loop = factory()->NewWhileStatement(labels);
2849 Target target(&this->target_stack_, loop);
2851 Expect(Token::WHILE, CHECK_OK);
2852 Expect(Token::LPAREN, CHECK_OK);
2853 Expression* cond = ParseExpression(true, CHECK_OK);
2854 Expect(Token::RPAREN, CHECK_OK);
2855 Statement* body = ParseStatement(NULL, CHECK_OK);
2857 if (loop != NULL) loop->Initialize(cond, body);
2862 Statement* Parser::ParseForStatement(ZoneStringList* labels, bool* ok) {
2864 // 'for' '(' Expression? ';' Expression? ';' Expression? ')' Statement
2866 Statement* init = NULL;
2868 // Create an in-between scope for let-bound iteration variables.
2869 Scope* saved_scope = top_scope_;
2870 Scope* for_scope = NewScope(top_scope_, BLOCK_SCOPE);
2871 top_scope_ = for_scope;
2873 Expect(Token::FOR, CHECK_OK);
2874 Expect(Token::LPAREN, CHECK_OK);
2875 for_scope->set_start_position(scanner().location().beg_pos);
2876 if (peek() != Token::SEMICOLON) {
2877 if (peek() == Token::VAR || peek() == Token::CONST) {
2878 Handle<String> name;
2879 Block* variable_statement =
2880 ParseVariableDeclarations(kForStatement, NULL, NULL, &name, CHECK_OK);
2882 if (peek() == Token::IN && !name.is_null()) {
2883 VariableProxy* each = top_scope_->NewUnresolved(factory(), name);
2884 ForInStatement* loop = factory()->NewForInStatement(labels);
2885 Target target(&this->target_stack_, loop);
2887 Expect(Token::IN, CHECK_OK);
2888 Expression* enumerable = ParseExpression(true, CHECK_OK);
2889 Expect(Token::RPAREN, CHECK_OK);
2891 Statement* body = ParseStatement(NULL, CHECK_OK);
2892 loop->Initialize(each, enumerable, body);
2893 Block* result = factory()->NewBlock(NULL, 2, false);
2894 result->AddStatement(variable_statement);
2895 result->AddStatement(loop);
2896 top_scope_ = saved_scope;
2897 for_scope->set_end_position(scanner().location().end_pos);
2898 for_scope = for_scope->FinalizeBlockScope();
2899 ASSERT(for_scope == NULL);
2900 // Parsed for-in loop w/ variable/const declaration.
2903 init = variable_statement;
2905 } else if (peek() == Token::LET) {
2906 Handle<String> name;
2907 VariableDeclarationProperties decl_props = kHasNoInitializers;
2908 Block* variable_statement =
2909 ParseVariableDeclarations(kForStatement, &decl_props, NULL, &name,
2911 bool accept_IN = !name.is_null() && decl_props != kHasInitializers;
2912 if (peek() == Token::IN && accept_IN) {
2913 // Rewrite a for-in statement of the form
2915 // for (let x in e) b
2919 // <let x' be a temporary variable>
2926 // TODO(keuchel): Move the temporary variable to the block scope, after
2927 // implementing stack allocated block scoped variables.
2928 Variable* temp = top_scope_->DeclarationScope()->NewTemporary(name);
2929 VariableProxy* temp_proxy = factory()->NewVariableProxy(temp);
2930 VariableProxy* each = top_scope_->NewUnresolved(factory(), name);
2931 ForInStatement* loop = factory()->NewForInStatement(labels);
2932 Target target(&this->target_stack_, loop);
2934 Expect(Token::IN, CHECK_OK);
2935 Expression* enumerable = ParseExpression(true, CHECK_OK);
2936 Expect(Token::RPAREN, CHECK_OK);
2938 Statement* body = ParseStatement(NULL, CHECK_OK);
2939 Block* body_block = factory()->NewBlock(NULL, 3, false);
2940 Assignment* assignment = factory()->NewAssignment(
2941 Token::ASSIGN, each, temp_proxy, RelocInfo::kNoPosition);
2942 Statement* assignment_statement =
2943 factory()->NewExpressionStatement(assignment);
2944 body_block->AddStatement(variable_statement);
2945 body_block->AddStatement(assignment_statement);
2946 body_block->AddStatement(body);
2947 loop->Initialize(temp_proxy, enumerable, body_block);
2948 top_scope_ = saved_scope;
2949 for_scope->set_end_position(scanner().location().end_pos);
2950 for_scope = for_scope->FinalizeBlockScope();
2951 body_block->set_scope(for_scope);
2952 // Parsed for-in loop w/ let declaration.
2956 init = variable_statement;
2959 Expression* expression = ParseExpression(false, CHECK_OK);
2960 if (peek() == Token::IN) {
2961 // Signal a reference error if the expression is an invalid
2962 // left-hand side expression. We could report this as a syntax
2963 // error here but for compatibility with JSC we choose to report
2964 // the error at runtime.
2965 if (expression == NULL || !expression->IsValidLeftHandSide()) {
2966 Handle<String> type =
2967 isolate()->factory()->invalid_lhs_in_for_in_symbol();
2968 expression = NewThrowReferenceError(type);
2970 ForInStatement* loop = factory()->NewForInStatement(labels);
2971 Target target(&this->target_stack_, loop);
2973 Expect(Token::IN, CHECK_OK);
2974 Expression* enumerable = ParseExpression(true, CHECK_OK);
2975 Expect(Token::RPAREN, CHECK_OK);
2977 Statement* body = ParseStatement(NULL, CHECK_OK);
2978 if (loop) loop->Initialize(expression, enumerable, body);
2979 top_scope_ = saved_scope;
2980 for_scope->set_end_position(scanner().location().end_pos);
2981 for_scope = for_scope->FinalizeBlockScope();
2982 ASSERT(for_scope == NULL);
2983 // Parsed for-in loop.
2987 init = factory()->NewExpressionStatement(expression);
2992 // Standard 'for' loop
2993 ForStatement* loop = factory()->NewForStatement(labels);
2994 Target target(&this->target_stack_, loop);
2996 // Parsed initializer at this point.
2997 Expect(Token::SEMICOLON, CHECK_OK);
2999 Expression* cond = NULL;
3000 if (peek() != Token::SEMICOLON) {
3001 cond = ParseExpression(true, CHECK_OK);
3003 Expect(Token::SEMICOLON, CHECK_OK);
3005 Statement* next = NULL;
3006 if (peek() != Token::RPAREN) {
3007 Expression* exp = ParseExpression(true, CHECK_OK);
3008 next = factory()->NewExpressionStatement(exp);
3010 Expect(Token::RPAREN, CHECK_OK);
3012 Statement* body = ParseStatement(NULL, CHECK_OK);
3013 top_scope_ = saved_scope;
3014 for_scope->set_end_position(scanner().location().end_pos);
3015 for_scope = for_scope->FinalizeBlockScope();
3016 if (for_scope != NULL) {
3017 // Rewrite a for statement of the form
3019 // for (let x = i; c; n) b
3027 ASSERT(init != NULL);
3028 Block* result = factory()->NewBlock(NULL, 2, false);
3029 result->AddStatement(init);
3030 result->AddStatement(loop);
3031 result->set_scope(for_scope);
3032 if (loop) loop->Initialize(NULL, cond, next, body);
3035 if (loop) loop->Initialize(init, cond, next, body);
3042 Expression* Parser::ParseExpression(bool accept_IN, bool* ok) {
3044 // AssignmentExpression
3045 // Expression ',' AssignmentExpression
3047 Expression* result = ParseAssignmentExpression(accept_IN, CHECK_OK);
3048 while (peek() == Token::COMMA) {
3049 Expect(Token::COMMA, CHECK_OK);
3050 int position = scanner().location().beg_pos;
3051 Expression* right = ParseAssignmentExpression(accept_IN, CHECK_OK);
3053 factory()->NewBinaryOperation(Token::COMMA, result, right, position);
3060 Expression* Parser::ParseAssignmentExpression(bool accept_IN, bool* ok) {
3061 // AssignmentExpression ::
3062 // ConditionalExpression
3063 // LeftHandSideExpression AssignmentOperator AssignmentExpression
3065 if (fni_ != NULL) fni_->Enter();
3066 Expression* expression = ParseConditionalExpression(accept_IN, CHECK_OK);
3068 if (!Token::IsAssignmentOp(peek())) {
3069 if (fni_ != NULL) fni_->Leave();
3070 // Parsed conditional expression only (no assignment).
3074 // Signal a reference error if the expression is an invalid left-hand
3075 // side expression. We could report this as a syntax error here but
3076 // for compatibility with JSC we choose to report the error at
3078 if (expression == NULL || !expression->IsValidLeftHandSide()) {
3079 Handle<String> type =
3080 isolate()->factory()->invalid_lhs_in_assignment_symbol();
3081 expression = NewThrowReferenceError(type);
3084 if (!top_scope_->is_classic_mode()) {
3085 // Assignment to eval or arguments is disallowed in strict mode.
3086 CheckStrictModeLValue(expression, "strict_lhs_assignment", CHECK_OK);
3088 MarkAsLValue(expression);
3090 Token::Value op = Next(); // Get assignment operator.
3091 int pos = scanner().location().beg_pos;
3092 Expression* right = ParseAssignmentExpression(accept_IN, CHECK_OK);
3094 // TODO(1231235): We try to estimate the set of properties set by
3095 // constructors. We define a new property whenever there is an
3096 // assignment to a property of 'this'. We should probably only add
3097 // properties if we haven't seen them before. Otherwise we'll
3098 // probably overestimate the number of properties.
3099 Property* property = expression ? expression->AsProperty() : NULL;
3100 if (op == Token::ASSIGN &&
3102 property->obj()->AsVariableProxy() != NULL &&
3103 property->obj()->AsVariableProxy()->is_this()) {
3104 current_function_state_->AddProperty();
3107 // If we assign a function literal to a property we pretenure the
3108 // literal so it can be added as a constant function property.
3109 if (property != NULL && right->AsFunctionLiteral() != NULL) {
3110 right->AsFunctionLiteral()->set_pretenure();
3114 // Check if the right hand side is a call to avoid inferring a
3115 // name if we're dealing with "a = function(){...}();"-like
3117 if ((op == Token::INIT_VAR
3118 || op == Token::INIT_CONST
3119 || op == Token::ASSIGN)
3120 && (right->AsCall() == NULL && right->AsCallNew() == NULL)) {
3123 fni_->RemoveLastFunction();
3128 return factory()->NewAssignment(op, expression, right, pos);
3133 Expression* Parser::ParseConditionalExpression(bool accept_IN, bool* ok) {
3134 // ConditionalExpression ::
3135 // LogicalOrExpression
3136 // LogicalOrExpression '?' AssignmentExpression ':' AssignmentExpression
3138 // We start using the binary expression parser for prec >= 4 only!
3139 Expression* expression = ParseBinaryExpression(4, accept_IN, CHECK_OK);
3140 if (peek() != Token::CONDITIONAL) return expression;
3141 Consume(Token::CONDITIONAL);
3142 // In parsing the first assignment expression in conditional
3143 // expressions we always accept the 'in' keyword; see ECMA-262,
3144 // section 11.12, page 58.
3145 int left_position = scanner().peek_location().beg_pos;
3146 Expression* left = ParseAssignmentExpression(true, CHECK_OK);
3147 Expect(Token::COLON, CHECK_OK);
3148 int right_position = scanner().peek_location().beg_pos;
3149 Expression* right = ParseAssignmentExpression(accept_IN, CHECK_OK);
3150 return factory()->NewConditional(
3151 expression, left, right, left_position, right_position);
3155 static int Precedence(Token::Value tok, bool accept_IN) {
3156 if (tok == Token::IN && !accept_IN)
3157 return 0; // 0 precedence will terminate binary expression parsing
3159 return Token::Precedence(tok);
3164 Expression* Parser::ParseBinaryExpression(int prec, bool accept_IN, bool* ok) {
3166 Expression* x = ParseUnaryExpression(CHECK_OK);
3167 for (int prec1 = Precedence(peek(), accept_IN); prec1 >= prec; prec1--) {
3169 while (Precedence(peek(), accept_IN) == prec1) {
3170 Token::Value op = Next();
3171 int position = scanner().location().beg_pos;
3172 Expression* y = ParseBinaryExpression(prec1 + 1, accept_IN, CHECK_OK);
3174 // Compute some expressions involving only number literals.
3175 if (x && x->AsLiteral() && x->AsLiteral()->handle()->IsNumber() &&
3176 y && y->AsLiteral() && y->AsLiteral()->handle()->IsNumber()) {
3177 double x_val = x->AsLiteral()->handle()->Number();
3178 double y_val = y->AsLiteral()->handle()->Number();
3182 x = factory()->NewNumberLiteral(x_val + y_val);
3185 x = factory()->NewNumberLiteral(x_val - y_val);
3188 x = factory()->NewNumberLiteral(x_val * y_val);
3191 x = factory()->NewNumberLiteral(x_val / y_val);
3193 case Token::BIT_OR: {
3194 int value = DoubleToInt32(x_val) | DoubleToInt32(y_val);
3195 x = factory()->NewNumberLiteral(value);
3198 case Token::BIT_AND: {
3199 int value = DoubleToInt32(x_val) & DoubleToInt32(y_val);
3200 x = factory()->NewNumberLiteral(value);
3203 case Token::BIT_XOR: {
3204 int value = DoubleToInt32(x_val) ^ DoubleToInt32(y_val);
3205 x = factory()->NewNumberLiteral(value);
3209 int value = DoubleToInt32(x_val) << (DoubleToInt32(y_val) & 0x1f);
3210 x = factory()->NewNumberLiteral(value);
3214 uint32_t shift = DoubleToInt32(y_val) & 0x1f;
3215 uint32_t value = DoubleToUint32(x_val) >> shift;
3216 x = factory()->NewNumberLiteral(value);
3220 uint32_t shift = DoubleToInt32(y_val) & 0x1f;
3221 int value = ArithmeticShiftRight(DoubleToInt32(x_val), shift);
3222 x = factory()->NewNumberLiteral(value);
3230 // For now we distinguish between comparisons and other binary
3231 // operations. (We could combine the two and get rid of this
3232 // code and AST node eventually.)
3233 if (Token::IsCompareOp(op)) {
3234 // We have a comparison.
3235 Token::Value cmp = op;
3237 case Token::NE: cmp = Token::EQ; break;
3238 case Token::NE_STRICT: cmp = Token::EQ_STRICT; break;
3241 x = factory()->NewCompareOperation(cmp, x, y, position);
3243 // The comparison was negated - add a NOT.
3244 x = factory()->NewUnaryOperation(Token::NOT, x, position);
3248 // We have a "normal" binary operation.
3249 x = factory()->NewBinaryOperation(op, x, y, position);
3257 Expression* Parser::ParseUnaryExpression(bool* ok) {
3258 // UnaryExpression ::
3259 // PostfixExpression
3260 // 'delete' UnaryExpression
3261 // 'void' UnaryExpression
3262 // 'typeof' UnaryExpression
3263 // '++' UnaryExpression
3264 // '--' UnaryExpression
3265 // '+' UnaryExpression
3266 // '-' UnaryExpression
3267 // '~' UnaryExpression
3268 // '!' UnaryExpression
3270 Token::Value op = peek();
3271 if (Token::IsUnaryOp(op)) {
3273 int position = scanner().location().beg_pos;
3274 Expression* expression = ParseUnaryExpression(CHECK_OK);
3276 if (expression != NULL && (expression->AsLiteral() != NULL)) {
3277 Handle<Object> literal = expression->AsLiteral()->handle();
3278 if (op == Token::NOT) {
3279 // Convert the literal to a boolean condition and negate it.
3280 bool condition = literal->ToBoolean()->IsTrue();
3281 Handle<Object> result(isolate()->heap()->ToBoolean(!condition));
3282 return factory()->NewLiteral(result);
3283 } else if (literal->IsNumber()) {
3284 // Compute some expressions involving only number literals.
3285 double value = literal->Number();
3290 return factory()->NewNumberLiteral(-value);
3291 case Token::BIT_NOT:
3292 return factory()->NewNumberLiteral(~DoubleToInt32(value));
3299 // "delete identifier" is a syntax error in strict mode.
3300 if (op == Token::DELETE && !top_scope_->is_classic_mode()) {
3301 VariableProxy* operand = expression->AsVariableProxy();
3302 if (operand != NULL && !operand->is_this()) {
3303 ReportMessage("strict_delete", Vector<const char*>::empty());
3309 return factory()->NewUnaryOperation(op, expression, position);
3311 } else if (Token::IsCountOp(op)) {
3313 Expression* expression = ParseUnaryExpression(CHECK_OK);
3314 // Signal a reference error if the expression is an invalid
3315 // left-hand side expression. We could report this as a syntax
3316 // error here but for compatibility with JSC we choose to report the
3317 // error at runtime.
3318 if (expression == NULL || !expression->IsValidLeftHandSide()) {
3319 Handle<String> type =
3320 isolate()->factory()->invalid_lhs_in_prefix_op_symbol();
3321 expression = NewThrowReferenceError(type);
3324 if (!top_scope_->is_classic_mode()) {
3325 // Prefix expression operand in strict mode may not be eval or arguments.
3326 CheckStrictModeLValue(expression, "strict_lhs_prefix", CHECK_OK);
3328 MarkAsLValue(expression);
3330 int position = scanner().location().beg_pos;
3331 return factory()->NewCountOperation(op,
3337 return ParsePostfixExpression(ok);
3342 Expression* Parser::ParsePostfixExpression(bool* ok) {
3343 // PostfixExpression ::
3344 // LeftHandSideExpression ('++' | '--')?
3346 Expression* expression = ParseLeftHandSideExpression(CHECK_OK);
3347 if (!scanner().HasAnyLineTerminatorBeforeNext() &&
3348 Token::IsCountOp(peek())) {
3349 // Signal a reference error if the expression is an invalid
3350 // left-hand side expression. We could report this as a syntax
3351 // error here but for compatibility with JSC we choose to report the
3352 // error at runtime.
3353 if (expression == NULL || !expression->IsValidLeftHandSide()) {
3354 Handle<String> type =
3355 isolate()->factory()->invalid_lhs_in_postfix_op_symbol();
3356 expression = NewThrowReferenceError(type);
3359 if (!top_scope_->is_classic_mode()) {
3360 // Postfix expression operand in strict mode may not be eval or arguments.
3361 CheckStrictModeLValue(expression, "strict_lhs_prefix", CHECK_OK);
3363 MarkAsLValue(expression);
3365 Token::Value next = Next();
3366 int position = scanner().location().beg_pos;
3368 factory()->NewCountOperation(next,
3369 false /* postfix */,
3377 Expression* Parser::ParseLeftHandSideExpression(bool* ok) {
3378 // LeftHandSideExpression ::
3379 // (NewExpression | MemberExpression) ...
3382 if (peek() == Token::NEW) {
3383 result = ParseNewExpression(CHECK_OK);
3385 result = ParseMemberExpression(CHECK_OK);
3390 case Token::LBRACK: {
3391 Consume(Token::LBRACK);
3392 int pos = scanner().location().beg_pos;
3393 Expression* index = ParseExpression(true, CHECK_OK);
3394 result = factory()->NewProperty(result, index, pos);
3395 Expect(Token::RBRACK, CHECK_OK);
3399 case Token::LPAREN: {
3401 if (scanner().current_token() == Token::IDENTIFIER) {
3402 // For call of an identifier we want to report position of
3403 // the identifier as position of the call in the stack trace.
3404 pos = scanner().location().beg_pos;
3406 // For other kinds of calls we record position of the parenthesis as
3407 // position of the call. Note that this is extremely important for
3408 // expressions of the form function(){...}() for which call position
3409 // should not point to the closing brace otherwise it will intersect
3410 // with positions recorded for function literal and confuse debugger.
3411 pos = scanner().peek_location().beg_pos;
3413 ZoneList<Expression*>* args = ParseArguments(CHECK_OK);
3415 // Keep track of eval() calls since they disable all local variable
3417 // The calls that need special treatment are the
3418 // direct eval calls. These calls are all of the form eval(...), with
3419 // no explicit receiver.
3420 // These calls are marked as potentially direct eval calls. Whether
3421 // they are actually direct calls to eval is determined at run time.
3422 VariableProxy* callee = result->AsVariableProxy();
3423 if (callee != NULL &&
3424 callee->IsVariable(isolate()->factory()->eval_symbol())) {
3425 top_scope_->DeclarationScope()->RecordEvalCall();
3427 result = factory()->NewCall(result, args, pos);
3431 case Token::PERIOD: {
3432 Consume(Token::PERIOD);
3433 int pos = scanner().location().beg_pos;
3434 Handle<String> name = ParseIdentifierName(CHECK_OK);
3436 factory()->NewProperty(result, factory()->NewLiteral(name), pos);
3437 if (fni_ != NULL) fni_->PushLiteralName(name);
3448 Expression* Parser::ParseNewPrefix(PositionStack* stack, bool* ok) {
3450 // ('new')+ MemberExpression
3452 // The grammar for new expressions is pretty warped. The keyword
3453 // 'new' can either be a part of the new expression (where it isn't
3454 // followed by an argument list) or a part of the member expression,
3455 // where it must be followed by an argument list. To accommodate
3456 // this, we parse the 'new' keywords greedily and keep track of how
3457 // many we have parsed. This information is then passed on to the
3458 // member expression parser, which is only allowed to match argument
3459 // lists as long as it has 'new' prefixes left
3460 Expect(Token::NEW, CHECK_OK);
3461 PositionStack::Element pos(stack, scanner().location().beg_pos);
3464 if (peek() == Token::NEW) {
3465 result = ParseNewPrefix(stack, CHECK_OK);
3467 result = ParseMemberWithNewPrefixesExpression(stack, CHECK_OK);
3470 if (!stack->is_empty()) {
3471 int last = stack->pop();
3472 result = factory()->NewCallNew(
3473 result, new(zone()) ZoneList<Expression*>(0), last);
3479 Expression* Parser::ParseNewExpression(bool* ok) {
3480 PositionStack stack(ok);
3481 return ParseNewPrefix(&stack, ok);
3485 Expression* Parser::ParseMemberExpression(bool* ok) {
3486 return ParseMemberWithNewPrefixesExpression(NULL, ok);
3490 Expression* Parser::ParseMemberWithNewPrefixesExpression(PositionStack* stack,
3492 // MemberExpression ::
3493 // (PrimaryExpression | FunctionLiteral)
3494 // ('[' Expression ']' | '.' Identifier | Arguments)*
3496 // Parse the initial primary or function expression.
3497 Expression* result = NULL;
3498 if (peek() == Token::FUNCTION) {
3499 Expect(Token::FUNCTION, CHECK_OK);
3500 int function_token_position = scanner().location().beg_pos;
3501 Handle<String> name;
3502 bool is_strict_reserved_name = false;
3503 if (peek_any_identifier()) {
3504 name = ParseIdentifierOrStrictReservedWord(&is_strict_reserved_name,
3507 FunctionLiteral::Type type = name.is_null()
3508 ? FunctionLiteral::ANONYMOUS_EXPRESSION
3509 : FunctionLiteral::NAMED_EXPRESSION;
3510 result = ParseFunctionLiteral(name,
3511 is_strict_reserved_name,
3512 function_token_position,
3516 result = ParsePrimaryExpression(CHECK_OK);
3521 case Token::LBRACK: {
3522 Consume(Token::LBRACK);
3523 int pos = scanner().location().beg_pos;
3524 Expression* index = ParseExpression(true, CHECK_OK);
3525 result = factory()->NewProperty(result, index, pos);
3527 if (index->IsPropertyName()) {
3528 fni_->PushLiteralName(index->AsLiteral()->AsPropertyName());
3530 fni_->PushLiteralName(
3531 isolate()->factory()->anonymous_function_symbol());
3534 Expect(Token::RBRACK, CHECK_OK);
3537 case Token::PERIOD: {
3538 Consume(Token::PERIOD);
3539 int pos = scanner().location().beg_pos;
3540 Handle<String> name = ParseIdentifierName(CHECK_OK);
3542 factory()->NewProperty(result, factory()->NewLiteral(name), pos);
3543 if (fni_ != NULL) fni_->PushLiteralName(name);
3546 case Token::LPAREN: {
3547 if ((stack == NULL) || stack->is_empty()) return result;
3548 // Consume one of the new prefixes (already parsed).
3549 ZoneList<Expression*>* args = ParseArguments(CHECK_OK);
3550 int last = stack->pop();
3551 result = factory()->NewCallNew(result, args, last);
3561 DebuggerStatement* Parser::ParseDebuggerStatement(bool* ok) {
3562 // In ECMA-262 'debugger' is defined as a reserved keyword. In some browser
3563 // contexts this is used as a statement which invokes the debugger as i a
3564 // break point is present.
3565 // DebuggerStatement ::
3568 Expect(Token::DEBUGGER, CHECK_OK);
3569 ExpectSemicolon(CHECK_OK);
3570 return factory()->NewDebuggerStatement();
3574 void Parser::ReportUnexpectedToken(Token::Value token) {
3575 // We don't report stack overflows here, to avoid increasing the
3576 // stack depth even further. Instead we report it after parsing is
3577 // over, in ParseProgram/ParseJson.
3578 if (token == Token::ILLEGAL && stack_overflow_) return;
3579 // Four of the tokens are treated specially
3582 return ReportMessage("unexpected_eos", Vector<const char*>::empty());
3584 return ReportMessage("unexpected_token_number",
3585 Vector<const char*>::empty());
3587 return ReportMessage("unexpected_token_string",
3588 Vector<const char*>::empty());
3589 case Token::IDENTIFIER:
3590 return ReportMessage("unexpected_token_identifier",
3591 Vector<const char*>::empty());
3592 case Token::FUTURE_RESERVED_WORD:
3593 return ReportMessage("unexpected_reserved",
3594 Vector<const char*>::empty());
3595 case Token::FUTURE_STRICT_RESERVED_WORD:
3596 return ReportMessage(top_scope_->is_classic_mode() ?
3597 "unexpected_token_identifier" :
3598 "unexpected_strict_reserved",
3599 Vector<const char*>::empty());
3601 const char* name = Token::String(token);
3602 ASSERT(name != NULL);
3603 ReportMessage("unexpected_token", Vector<const char*>(&name, 1));
3608 void Parser::ReportInvalidPreparseData(Handle<String> name, bool* ok) {
3609 SmartArrayPointer<char> name_string = name->ToCString(DISALLOW_NULLS);
3610 const char* element[1] = { *name_string };
3611 ReportMessage("invalid_preparser_data",
3612 Vector<const char*>(element, 1));
3617 Expression* Parser::ParsePrimaryExpression(bool* ok) {
3618 // PrimaryExpression ::
3629 // '(' Expression ')'
3631 Expression* result = NULL;
3634 Consume(Token::THIS);
3635 result = factory()->NewVariableProxy(top_scope_->receiver());
3639 case Token::NULL_LITERAL:
3640 Consume(Token::NULL_LITERAL);
3641 result = factory()->NewLiteral(isolate()->factory()->null_value());
3644 case Token::TRUE_LITERAL:
3645 Consume(Token::TRUE_LITERAL);
3646 result = factory()->NewLiteral(isolate()->factory()->true_value());
3649 case Token::FALSE_LITERAL:
3650 Consume(Token::FALSE_LITERAL);
3651 result = factory()->NewLiteral(isolate()->factory()->false_value());
3654 case Token::IDENTIFIER:
3655 case Token::FUTURE_STRICT_RESERVED_WORD: {
3656 Handle<String> name = ParseIdentifier(CHECK_OK);
3657 if (fni_ != NULL) fni_->PushVariableName(name);
3658 // The name may refer to a module instance object, so its type is unknown.
3660 if (FLAG_print_interface_details)
3661 PrintF("# Variable %s ", name->ToAsciiArray());
3663 Interface* interface = Interface::NewUnknown();
3664 result = top_scope_->NewUnresolved(
3665 factory(), name, scanner().location().beg_pos, interface);
3669 case Token::NUMBER: {
3670 Consume(Token::NUMBER);
3671 ASSERT(scanner().is_literal_ascii());
3672 double value = StringToDouble(isolate()->unicode_cache(),
3673 scanner().literal_ascii_string(),
3674 ALLOW_HEX | ALLOW_OCTALS);
3675 result = factory()->NewNumberLiteral(value);
3679 case Token::STRING: {
3680 Consume(Token::STRING);
3681 Handle<String> symbol = GetSymbol(CHECK_OK);
3682 result = factory()->NewLiteral(symbol);
3683 if (fni_ != NULL) fni_->PushLiteralName(symbol);
3687 case Token::ASSIGN_DIV:
3688 result = ParseRegExpLiteral(true, CHECK_OK);
3692 result = ParseRegExpLiteral(false, CHECK_OK);
3696 result = ParseArrayLiteral(CHECK_OK);
3700 result = ParseObjectLiteral(CHECK_OK);
3704 Consume(Token::LPAREN);
3705 // Heuristically try to detect immediately called functions before
3706 // seeing the call parentheses.
3707 parenthesized_function_ = (peek() == Token::FUNCTION);
3708 result = ParseExpression(true, CHECK_OK);
3709 Expect(Token::RPAREN, CHECK_OK);
3713 if (allow_natives_syntax_ || extension_ != NULL) {
3714 result = ParseV8Intrinsic(CHECK_OK);
3717 // If we're not allowing special syntax we fall-through to the
3721 Token::Value tok = Next();
3722 ReportUnexpectedToken(tok);
3732 void Parser::BuildArrayLiteralBoilerplateLiterals(ZoneList<Expression*>* values,
3733 Handle<FixedArray> literals,
3736 // Fill in the literals.
3737 // Accumulate output values in local variables.
3738 bool is_simple_acc = true;
3740 for (int i = 0; i < values->length(); i++) {
3741 MaterializedLiteral* m_literal = values->at(i)->AsMaterializedLiteral();
3742 if (m_literal != NULL && m_literal->depth() >= depth_acc) {
3743 depth_acc = m_literal->depth() + 1;
3745 Handle<Object> boilerplate_value = GetBoilerplateValue(values->at(i));
3746 if (boilerplate_value->IsUndefined()) {
3747 literals->set_the_hole(i);
3748 is_simple_acc = false;
3750 literals->set(i, *boilerplate_value);
3754 *is_simple = is_simple_acc;
3759 Expression* Parser::ParseArrayLiteral(bool* ok) {
3761 // '[' Expression? (',' Expression?)* ']'
3763 ZoneList<Expression*>* values = new(zone()) ZoneList<Expression*>(4);
3764 Expect(Token::LBRACK, CHECK_OK);
3765 while (peek() != Token::RBRACK) {
3767 if (peek() == Token::COMMA) {
3768 elem = GetLiteralTheHole();
3770 elem = ParseAssignmentExpression(true, CHECK_OK);
3773 if (peek() != Token::RBRACK) {
3774 Expect(Token::COMMA, CHECK_OK);
3777 Expect(Token::RBRACK, CHECK_OK);
3779 // Update the scope information before the pre-parsing bailout.
3780 int literal_index = current_function_state_->NextMaterializedLiteralIndex();
3782 // Allocate a fixed array to hold all the object literals.
3783 Handle<FixedArray> object_literals =
3784 isolate()->factory()->NewFixedArray(values->length(), TENURED);
3785 Handle<FixedDoubleArray> double_literals;
3786 ElementsKind elements_kind = FAST_SMI_ONLY_ELEMENTS;
3787 bool has_only_undefined_values = true;
3789 // Fill in the literals.
3790 bool is_simple = true;
3792 for (int i = 0, n = values->length(); i < n; i++) {
3793 MaterializedLiteral* m_literal = values->at(i)->AsMaterializedLiteral();
3794 if (m_literal != NULL && m_literal->depth() + 1 > depth) {
3795 depth = m_literal->depth() + 1;
3797 Handle<Object> boilerplate_value = GetBoilerplateValue(values->at(i));
3798 if (boilerplate_value->IsUndefined()) {
3799 object_literals->set_the_hole(i);
3800 if (elements_kind == FAST_DOUBLE_ELEMENTS) {
3801 double_literals->set_the_hole(i);
3805 // Examine each literal element, and adjust the ElementsKind if the
3806 // literal element is not of a type that can be stored in the current
3807 // ElementsKind. Start with FAST_SMI_ONLY_ELEMENTS, and transition to
3808 // FAST_DOUBLE_ELEMENTS and FAST_ELEMENTS as necessary. Always remember
3809 // the tagged value, no matter what the ElementsKind is in case we
3810 // ultimately end up in FAST_ELEMENTS.
3811 has_only_undefined_values = false;
3812 object_literals->set(i, *boilerplate_value);
3813 if (elements_kind == FAST_SMI_ONLY_ELEMENTS) {
3814 // Smi only elements. Notice if a transition to FAST_DOUBLE_ELEMENTS or
3815 // FAST_ELEMENTS is required.
3816 if (!boilerplate_value->IsSmi()) {
3817 if (boilerplate_value->IsNumber() && FLAG_smi_only_arrays) {
3818 // Allocate a double array on the FAST_DOUBLE_ELEMENTS transition to
3819 // avoid over-allocating in TENURED space.
3820 double_literals = isolate()->factory()->NewFixedDoubleArray(
3821 values->length(), TENURED);
3822 // Copy the contents of the FAST_SMI_ONLY_ELEMENT array to the
3823 // FAST_DOUBLE_ELEMENTS array so that they are in sync.
3824 for (int j = 0; j < i; ++j) {
3825 Object* smi_value = object_literals->get(j);
3826 if (smi_value->IsTheHole()) {
3827 double_literals->set_the_hole(j);
3829 double_literals->set(j, Smi::cast(smi_value)->value());
3832 double_literals->set(i, boilerplate_value->Number());
3833 elements_kind = FAST_DOUBLE_ELEMENTS;
3835 elements_kind = FAST_ELEMENTS;
3838 } else if (elements_kind == FAST_DOUBLE_ELEMENTS) {
3839 // Continue to store double values in to FAST_DOUBLE_ELEMENTS arrays
3840 // until the first value is seen that can't be stored as a double.
3841 if (boilerplate_value->IsNumber()) {
3842 double_literals->set(i, boilerplate_value->Number());
3844 elements_kind = FAST_ELEMENTS;
3850 // Very small array literals that don't have a concrete hint about their type
3851 // from a constant value should default to the slow case to avoid lots of
3852 // elements transitions on really small objects.
3853 if (has_only_undefined_values && values->length() <= 2) {
3854 elements_kind = FAST_ELEMENTS;
3857 // Simple and shallow arrays can be lazily copied, we transform the
3858 // elements array to a copy-on-write array.
3859 if (is_simple && depth == 1 && values->length() > 0 &&
3860 elements_kind != FAST_DOUBLE_ELEMENTS) {
3861 object_literals->set_map(isolate()->heap()->fixed_cow_array_map());
3864 Handle<FixedArrayBase> element_values = elements_kind == FAST_DOUBLE_ELEMENTS
3865 ? Handle<FixedArrayBase>(double_literals)
3866 : Handle<FixedArrayBase>(object_literals);
3868 // Remember both the literal's constant values as well as the ElementsKind
3869 // in a 2-element FixedArray.
3870 Handle<FixedArray> literals =
3871 isolate()->factory()->NewFixedArray(2, TENURED);
3873 literals->set(0, Smi::FromInt(elements_kind));
3874 literals->set(1, *element_values);
3876 return factory()->NewArrayLiteral(
3877 literals, values, literal_index, is_simple, depth);
3881 bool Parser::IsBoilerplateProperty(ObjectLiteral::Property* property) {
3882 return property != NULL &&
3883 property->kind() != ObjectLiteral::Property::PROTOTYPE;
3887 bool CompileTimeValue::IsCompileTimeValue(Expression* expression) {
3888 if (expression->AsLiteral() != NULL) return true;
3889 MaterializedLiteral* lit = expression->AsMaterializedLiteral();
3890 return lit != NULL && lit->is_simple();
3894 bool CompileTimeValue::ArrayLiteralElementNeedsInitialization(
3895 Expression* value) {
3896 // If value is a literal the property value is already set in the
3897 // boilerplate object.
3898 if (value->AsLiteral() != NULL) return false;
3899 // If value is a materialized literal the property value is already set
3900 // in the boilerplate object if it is simple.
3901 if (CompileTimeValue::IsCompileTimeValue(value)) return false;
3906 Handle<FixedArray> CompileTimeValue::GetValue(Expression* expression) {
3907 ASSERT(IsCompileTimeValue(expression));
3908 Handle<FixedArray> result = FACTORY->NewFixedArray(2, TENURED);
3909 ObjectLiteral* object_literal = expression->AsObjectLiteral();
3910 if (object_literal != NULL) {
3911 ASSERT(object_literal->is_simple());
3912 if (object_literal->fast_elements()) {
3913 result->set(kTypeSlot, Smi::FromInt(OBJECT_LITERAL_FAST_ELEMENTS));
3915 result->set(kTypeSlot, Smi::FromInt(OBJECT_LITERAL_SLOW_ELEMENTS));
3917 result->set(kElementsSlot, *object_literal->constant_properties());
3919 ArrayLiteral* array_literal = expression->AsArrayLiteral();
3920 ASSERT(array_literal != NULL && array_literal->is_simple());
3921 result->set(kTypeSlot, Smi::FromInt(ARRAY_LITERAL));
3922 result->set(kElementsSlot, *array_literal->constant_elements());
3928 CompileTimeValue::Type CompileTimeValue::GetType(Handle<FixedArray> value) {
3929 Smi* type_value = Smi::cast(value->get(kTypeSlot));
3930 return static_cast<Type>(type_value->value());
3934 Handle<FixedArray> CompileTimeValue::GetElements(Handle<FixedArray> value) {
3935 return Handle<FixedArray>(FixedArray::cast(value->get(kElementsSlot)));
3939 Handle<Object> Parser::GetBoilerplateValue(Expression* expression) {
3940 if (expression->AsLiteral() != NULL) {
3941 return expression->AsLiteral()->handle();
3943 if (CompileTimeValue::IsCompileTimeValue(expression)) {
3944 return CompileTimeValue::GetValue(expression);
3946 return isolate()->factory()->undefined_value();
3949 // Validation per 11.1.5 Object Initialiser
3950 class ObjectLiteralPropertyChecker {
3952 ObjectLiteralPropertyChecker(Parser* parser, LanguageMode language_mode) :
3953 props_(Literal::Match),
3955 language_mode_(language_mode) {
3959 ObjectLiteral::Property* property,
3960 Scanner::Location loc,
3965 kGetAccessor = 0x01,
3966 kSetAccessor = 0x02,
3967 kAccessor = kGetAccessor | kSetAccessor,
3971 static intptr_t GetPropertyKind(ObjectLiteral::Property* property) {
3972 switch (property->kind()) {
3973 case ObjectLiteral::Property::GETTER:
3974 return kGetAccessor;
3975 case ObjectLiteral::Property::SETTER:
3976 return kSetAccessor;
3984 LanguageMode language_mode_;
3988 void ObjectLiteralPropertyChecker::CheckProperty(
3989 ObjectLiteral::Property* property,
3990 Scanner::Location loc,
3992 ASSERT(property != NULL);
3993 Literal* literal = property->key();
3994 HashMap::Entry* entry = props_.Lookup(literal, literal->Hash(), true);
3995 intptr_t prev = reinterpret_cast<intptr_t> (entry->value);
3996 intptr_t curr = GetPropertyKind(property);
3998 // Duplicate data properties are illegal in strict or extended mode.
3999 if (language_mode_ != CLASSIC_MODE && (curr & prev & kData) != 0) {
4000 parser_->ReportMessageAt(loc, "strict_duplicate_property",
4001 Vector<const char*>::empty());
4005 // Data property conflicting with an accessor.
4006 if (((curr & kData) && (prev & kAccessor)) ||
4007 ((prev & kData) && (curr & kAccessor))) {
4008 parser_->ReportMessageAt(loc, "accessor_data_property",
4009 Vector<const char*>::empty());
4013 // Two accessors of the same type conflicting
4014 if ((curr & prev & kAccessor) != 0) {
4015 parser_->ReportMessageAt(loc, "accessor_get_set",
4016 Vector<const char*>::empty());
4022 entry->value = reinterpret_cast<void*> (prev | curr);
4027 void Parser::BuildObjectLiteralConstantProperties(
4028 ZoneList<ObjectLiteral::Property*>* properties,
4029 Handle<FixedArray> constant_properties,
4031 bool* fast_elements,
4034 // Accumulate the value in local variables and store it at the end.
4035 bool is_simple_acc = true;
4037 uint32_t max_element_index = 0;
4038 uint32_t elements = 0;
4039 for (int i = 0; i < properties->length(); i++) {
4040 ObjectLiteral::Property* property = properties->at(i);
4041 if (!IsBoilerplateProperty(property)) {
4042 is_simple_acc = false;
4045 MaterializedLiteral* m_literal = property->value()->AsMaterializedLiteral();
4046 if (m_literal != NULL && m_literal->depth() >= depth_acc) {
4047 depth_acc = m_literal->depth() + 1;
4050 // Add CONSTANT and COMPUTED properties to boilerplate. Use undefined
4051 // value for COMPUTED properties, the real value is filled in at
4052 // runtime. The enumeration order is maintained.
4053 Handle<Object> key = property->key()->handle();
4054 Handle<Object> value = GetBoilerplateValue(property->value());
4055 is_simple_acc = is_simple_acc && !value->IsUndefined();
4057 // Keep track of the number of elements in the object literal and
4058 // the largest element index. If the largest element index is
4059 // much larger than the number of elements, creating an object
4060 // literal with fast elements will be a waste of space.
4061 uint32_t element_index = 0;
4063 && Handle<String>::cast(key)->AsArrayIndex(&element_index)
4064 && element_index > max_element_index) {
4065 max_element_index = element_index;
4067 } else if (key->IsSmi()) {
4068 int key_value = Smi::cast(*key)->value();
4070 && static_cast<uint32_t>(key_value) > max_element_index) {
4071 max_element_index = key_value;
4076 // Add name, value pair to the fixed array.
4077 constant_properties->set(position++, *key);
4078 constant_properties->set(position++, *value);
4081 (max_element_index <= 32) || ((2 * elements) >= max_element_index);
4082 *is_simple = is_simple_acc;
4087 ObjectLiteral::Property* Parser::ParseObjectLiteralGetSet(bool is_getter,
4089 // Special handling of getter and setter syntax:
4090 // { ... , get foo() { ... }, ... , set foo(v) { ... v ... } , ... }
4091 // We have already read the "get" or "set" keyword.
4092 Token::Value next = Next();
4093 bool is_keyword = Token::IsKeyword(next);
4094 if (next == Token::IDENTIFIER || next == Token::NUMBER ||
4095 next == Token::FUTURE_RESERVED_WORD ||
4096 next == Token::FUTURE_STRICT_RESERVED_WORD ||
4097 next == Token::STRING || is_keyword) {
4098 Handle<String> name;
4100 name = isolate_->factory()->LookupAsciiSymbol(Token::String(next));
4102 name = GetSymbol(CHECK_OK);
4104 FunctionLiteral* value =
4105 ParseFunctionLiteral(name,
4106 false, // reserved words are allowed here
4107 RelocInfo::kNoPosition,
4108 FunctionLiteral::ANONYMOUS_EXPRESSION,
4110 // Allow any number of parameters for compatibilty with JSC.
4111 // Specification only allows zero parameters for get and one for set.
4112 return factory()->NewObjectLiteralProperty(is_getter, value);
4114 ReportUnexpectedToken(next);
4121 Expression* Parser::ParseObjectLiteral(bool* ok) {
4124 // ((IdentifierName | String | Number) ':' AssignmentExpression)
4125 // | (('get' | 'set') (IdentifierName | String | Number) FunctionLiteral)
4128 ZoneList<ObjectLiteral::Property*>* properties =
4129 new(zone()) ZoneList<ObjectLiteral::Property*>(4);
4130 int number_of_boilerplate_properties = 0;
4131 bool has_function = false;
4133 ObjectLiteralPropertyChecker checker(this, top_scope_->language_mode());
4135 Expect(Token::LBRACE, CHECK_OK);
4137 while (peek() != Token::RBRACE) {
4138 if (fni_ != NULL) fni_->Enter();
4140 Literal* key = NULL;
4141 Token::Value next = peek();
4143 // Location of the property name token
4144 Scanner::Location loc = scanner().peek_location();
4147 case Token::FUTURE_RESERVED_WORD:
4148 case Token::FUTURE_STRICT_RESERVED_WORD:
4149 case Token::IDENTIFIER: {
4150 bool is_getter = false;
4151 bool is_setter = false;
4153 ParseIdentifierNameOrGetOrSet(&is_getter, &is_setter, CHECK_OK);
4154 if (fni_ != NULL) fni_->PushLiteralName(id);
4156 if ((is_getter || is_setter) && peek() != Token::COLON) {
4157 // Update loc to point to the identifier
4158 loc = scanner().peek_location();
4159 ObjectLiteral::Property* property =
4160 ParseObjectLiteralGetSet(is_getter, CHECK_OK);
4161 if (IsBoilerplateProperty(property)) {
4162 number_of_boilerplate_properties++;
4164 // Validate the property.
4165 checker.CheckProperty(property, loc, CHECK_OK);
4166 properties->Add(property);
4167 if (peek() != Token::RBRACE) Expect(Token::COMMA, CHECK_OK);
4173 continue; // restart the while
4175 // Failed to parse as get/set property, so it's just a property
4176 // called "get" or "set".
4177 key = factory()->NewLiteral(id);
4180 case Token::STRING: {
4181 Consume(Token::STRING);
4182 Handle<String> string = GetSymbol(CHECK_OK);
4183 if (fni_ != NULL) fni_->PushLiteralName(string);
4185 if (!string.is_null() && string->AsArrayIndex(&index)) {
4186 key = factory()->NewNumberLiteral(index);
4189 key = factory()->NewLiteral(string);
4192 case Token::NUMBER: {
4193 Consume(Token::NUMBER);
4194 ASSERT(scanner().is_literal_ascii());
4195 double value = StringToDouble(isolate()->unicode_cache(),
4196 scanner().literal_ascii_string(),
4197 ALLOW_HEX | ALLOW_OCTALS);
4198 key = factory()->NewNumberLiteral(value);
4202 if (Token::IsKeyword(next)) {
4204 Handle<String> string = GetSymbol(CHECK_OK);
4205 key = factory()->NewLiteral(string);
4207 // Unexpected token.
4208 Token::Value next = Next();
4209 ReportUnexpectedToken(next);
4215 Expect(Token::COLON, CHECK_OK);
4216 Expression* value = ParseAssignmentExpression(true, CHECK_OK);
4218 ObjectLiteral::Property* property =
4219 new(zone()) ObjectLiteral::Property(key, value, isolate());
4221 // Mark top-level object literals that contain function literals and
4222 // pretenure the literal so it can be added as a constant function
4224 if (top_scope_->DeclarationScope()->is_global_scope() &&
4225 value->AsFunctionLiteral() != NULL) {
4226 has_function = true;
4227 value->AsFunctionLiteral()->set_pretenure();
4230 // Count CONSTANT or COMPUTED properties to maintain the enumeration order.
4231 if (IsBoilerplateProperty(property)) number_of_boilerplate_properties++;
4232 // Validate the property
4233 checker.CheckProperty(property, loc, CHECK_OK);
4234 properties->Add(property);
4236 // TODO(1240767): Consider allowing trailing comma.
4237 if (peek() != Token::RBRACE) Expect(Token::COMMA, CHECK_OK);
4244 Expect(Token::RBRACE, CHECK_OK);
4246 // Computation of literal_index must happen before pre parse bailout.
4247 int literal_index = current_function_state_->NextMaterializedLiteralIndex();
4249 Handle<FixedArray> constant_properties = isolate()->factory()->NewFixedArray(
4250 number_of_boilerplate_properties * 2, TENURED);
4252 bool is_simple = true;
4253 bool fast_elements = true;
4255 BuildObjectLiteralConstantProperties(properties,
4256 constant_properties,
4260 return factory()->NewObjectLiteral(constant_properties,
4270 Expression* Parser::ParseRegExpLiteral(bool seen_equal, bool* ok) {
4271 if (!scanner().ScanRegExpPattern(seen_equal)) {
4273 ReportMessage("unterminated_regexp", Vector<const char*>::empty());
4278 int literal_index = current_function_state_->NextMaterializedLiteralIndex();
4280 Handle<String> js_pattern = NextLiteralString(TENURED);
4281 scanner().ScanRegExpFlags();
4282 Handle<String> js_flags = NextLiteralString(TENURED);
4285 return factory()->NewRegExpLiteral(js_pattern, js_flags, literal_index);
4289 ZoneList<Expression*>* Parser::ParseArguments(bool* ok) {
4291 // '(' (AssignmentExpression)*[','] ')'
4293 ZoneList<Expression*>* result = new(zone()) ZoneList<Expression*>(4);
4294 Expect(Token::LPAREN, CHECK_OK);
4295 bool done = (peek() == Token::RPAREN);
4297 Expression* argument = ParseAssignmentExpression(true, CHECK_OK);
4298 result->Add(argument);
4299 if (result->length() > kMaxNumFunctionParameters) {
4300 ReportMessageAt(scanner().location(), "too_many_arguments",
4301 Vector<const char*>::empty());
4305 done = (peek() == Token::RPAREN);
4306 if (!done) Expect(Token::COMMA, CHECK_OK);
4308 Expect(Token::RPAREN, CHECK_OK);
4313 class SingletonLogger : public ParserRecorder {
4315 SingletonLogger() : has_error_(false), start_(-1), end_(-1) { }
4316 virtual ~SingletonLogger() { }
4318 void Reset() { has_error_ = false; }
4320 virtual void LogFunction(int start,
4324 LanguageMode mode) {
4325 ASSERT(!has_error_);
4328 literals_ = literals;
4329 properties_ = properties;
4333 // Logs a symbol creation of a literal or identifier.
4334 virtual void LogAsciiSymbol(int start, Vector<const char> literal) { }
4335 virtual void LogUtf16Symbol(int start, Vector<const uc16> literal) { }
4337 // Logs an error message and marks the log as containing an error.
4338 // Further logging will be ignored, and ExtractData will return a vector
4339 // representing the error only.
4340 virtual void LogMessage(int start,
4342 const char* message,
4343 const char* argument_opt) {
4348 argument_opt_ = argument_opt;
4351 virtual int function_position() { return 0; }
4353 virtual int symbol_position() { return 0; }
4355 virtual int symbol_ids() { return -1; }
4357 virtual Vector<unsigned> ExtractData() {
4359 return Vector<unsigned>();
4362 virtual void PauseRecording() { }
4364 virtual void ResumeRecording() { }
4366 bool has_error() { return has_error_; }
4368 int start() { return start_; }
4369 int end() { return end_; }
4371 ASSERT(!has_error_);
4375 ASSERT(!has_error_);
4378 LanguageMode language_mode() {
4379 ASSERT(!has_error_);
4382 const char* message() {
4386 const char* argument_opt() {
4388 return argument_opt_;
4395 // For function entries.
4399 // For error messages.
4400 const char* message_;
4401 const char* argument_opt_;
4405 FunctionLiteral* Parser::ParseFunctionLiteral(Handle<String> function_name,
4406 bool name_is_strict_reserved,
4407 int function_token_position,
4408 FunctionLiteral::Type type,
4411 // '(' FormalParameterList? ')' '{' FunctionBody '}'
4413 // Anonymous functions were passed either the empty symbol or a null
4414 // handle as the function name. Remember if we were passed a non-empty
4415 // handle to decide whether to invoke function name inference.
4416 bool should_infer_name = function_name.is_null();
4418 // We want a non-null handle as the function name.
4419 if (should_infer_name) {
4420 function_name = isolate()->factory()->empty_symbol();
4423 int num_parameters = 0;
4424 // Function declarations are function scoped in normal mode, so they are
4425 // hoisted. In harmony block scoping mode they are block scoped, so they
4427 Scope* scope = (type == FunctionLiteral::DECLARATION && !is_extended_mode())
4428 ? NewScope(top_scope_->DeclarationScope(), FUNCTION_SCOPE)
4429 : NewScope(top_scope_, FUNCTION_SCOPE);
4430 ZoneList<Statement*>* body = NULL;
4431 int materialized_literal_count = -1;
4432 int expected_property_count = -1;
4433 int handler_count = 0;
4434 bool only_simple_this_property_assignments;
4435 Handle<FixedArray> this_property_assignments;
4436 FunctionLiteral::ParameterFlag duplicate_parameters =
4437 FunctionLiteral::kNoDuplicateParameters;
4438 AstProperties ast_properties;
4439 // Parse function body.
4440 { FunctionState function_state(this, scope, isolate());
4441 top_scope_->SetScopeName(function_name);
4443 // FormalParameterList ::
4444 // '(' (Identifier)*[','] ')'
4445 Expect(Token::LPAREN, CHECK_OK);
4446 scope->set_start_position(scanner().location().beg_pos);
4447 Scanner::Location name_loc = Scanner::Location::invalid();
4448 Scanner::Location dupe_loc = Scanner::Location::invalid();
4449 Scanner::Location reserved_loc = Scanner::Location::invalid();
4451 bool done = (peek() == Token::RPAREN);
4453 bool is_strict_reserved = false;
4454 Handle<String> param_name =
4455 ParseIdentifierOrStrictReservedWord(&is_strict_reserved,
4458 // Store locations for possible future error reports.
4459 if (!name_loc.IsValid() && IsEvalOrArguments(param_name)) {
4460 name_loc = scanner().location();
4462 if (!dupe_loc.IsValid() && top_scope_->IsDeclared(param_name)) {
4463 duplicate_parameters = FunctionLiteral::kHasDuplicateParameters;
4464 dupe_loc = scanner().location();
4466 if (!reserved_loc.IsValid() && is_strict_reserved) {
4467 reserved_loc = scanner().location();
4470 top_scope_->DeclareParameter(param_name, VAR);
4472 if (num_parameters > kMaxNumFunctionParameters) {
4473 ReportMessageAt(scanner().location(), "too_many_parameters",
4474 Vector<const char*>::empty());
4478 done = (peek() == Token::RPAREN);
4479 if (!done) Expect(Token::COMMA, CHECK_OK);
4481 Expect(Token::RPAREN, CHECK_OK);
4483 Expect(Token::LBRACE, CHECK_OK);
4485 // If we have a named function expression, we add a local variable
4486 // declaration to the body of the function with the name of the
4487 // function and let it refer to the function itself (closure).
4488 // NOTE: We create a proxy and resolve it here so that in the
4489 // future we can change the AST to only refer to VariableProxies
4490 // instead of Variables and Proxis as is the case now.
4491 Variable* fvar = NULL;
4492 Token::Value fvar_init_op = Token::INIT_CONST;
4493 if (type == FunctionLiteral::NAMED_EXPRESSION) {
4494 if (is_extended_mode()) fvar_init_op = Token::INIT_CONST_HARMONY;
4495 VariableMode fvar_mode = is_extended_mode() ? CONST_HARMONY : CONST;
4496 fvar = new(zone()) Variable(top_scope_,
4497 function_name, fvar_mode, true /* is valid LHS */,
4498 Variable::NORMAL, kCreatedInitialized);
4499 VariableProxy* proxy = factory()->NewVariableProxy(fvar);
4500 VariableDeclaration* fvar_declaration =
4501 factory()->NewVariableDeclaration(proxy, fvar_mode, top_scope_);
4502 top_scope_->DeclareFunctionVar(fvar_declaration);
4505 // Determine whether the function will be lazily compiled.
4506 // The heuristics are:
4507 // - It must not have been prohibited by the caller to Parse (some callers
4508 // need a full AST).
4509 // - The outer scope must be trivial (only global variables in scope).
4510 // - The function mustn't be a function expression with an open parenthesis
4511 // before; we consider that a hint that the function will be called
4512 // immediately, and it would be a waste of time to make it lazily
4514 // These are all things we can know at this point, without looking at the
4516 bool is_lazily_compiled = (mode() == PARSE_LAZILY &&
4517 top_scope_->outer_scope()->is_global_scope() &&
4518 top_scope_->HasTrivialOuterContext() &&
4519 !parenthesized_function_);
4520 parenthesized_function_ = false; // The bit was set for this function only.
4522 if (is_lazily_compiled) {
4523 int function_block_pos = scanner().location().beg_pos;
4524 FunctionEntry entry;
4525 if (pre_data_ != NULL) {
4526 // If we have pre_data_, we use it to skip parsing the function body.
4527 // the preparser data contains the information we need to construct the
4529 entry = pre_data()->GetFunctionEntry(function_block_pos);
4530 if (entry.is_valid()) {
4531 if (entry.end_pos() <= function_block_pos) {
4532 // End position greater than end of stream is safe, and hard
4534 ReportInvalidPreparseData(function_name, CHECK_OK);
4536 scanner().SeekForward(entry.end_pos() - 1);
4538 scope->set_end_position(entry.end_pos());
4539 Expect(Token::RBRACE, CHECK_OK);
4540 isolate()->counters()->total_preparse_skipped()->Increment(
4541 scope->end_position() - function_block_pos);
4542 materialized_literal_count = entry.literal_count();
4543 expected_property_count = entry.property_count();
4544 top_scope_->SetLanguageMode(entry.language_mode());
4545 only_simple_this_property_assignments = false;
4546 this_property_assignments = isolate()->factory()->empty_fixed_array();
4548 is_lazily_compiled = false;
4551 // With no preparser data, we partially parse the function, without
4552 // building an AST. This gathers the data needed to build a lazy
4554 SingletonLogger logger;
4555 preparser::PreParser::PreParseResult result =
4556 LazyParseFunctionLiteral(&logger);
4557 if (result == preparser::PreParser::kPreParseStackOverflow) {
4558 // Propagate stack overflow.
4559 stack_overflow_ = true;
4563 if (logger.has_error()) {
4564 const char* arg = logger.argument_opt();
4565 Vector<const char*> args;
4567 args = Vector<const char*>(&arg, 1);
4569 ReportMessageAt(Scanner::Location(logger.start(), logger.end()),
4570 logger.message(), args);
4574 scope->set_end_position(logger.end());
4575 Expect(Token::RBRACE, CHECK_OK);
4576 isolate()->counters()->total_preparse_skipped()->Increment(
4577 scope->end_position() - function_block_pos);
4578 materialized_literal_count = logger.literals();
4579 expected_property_count = logger.properties();
4580 top_scope_->SetLanguageMode(logger.language_mode());
4581 only_simple_this_property_assignments = false;
4582 this_property_assignments = isolate()->factory()->empty_fixed_array();
4586 if (!is_lazily_compiled) {
4587 body = new(zone()) ZoneList<Statement*>(8);
4589 VariableProxy* fproxy =
4590 top_scope_->NewUnresolved(factory(), function_name);
4591 fproxy->BindTo(fvar);
4592 body->Add(factory()->NewExpressionStatement(
4593 factory()->NewAssignment(fvar_init_op,
4595 factory()->NewThisFunction(),
4596 RelocInfo::kNoPosition)));
4598 ParseSourceElements(body, Token::RBRACE, false, CHECK_OK);
4600 materialized_literal_count = function_state.materialized_literal_count();
4601 expected_property_count = function_state.expected_property_count();
4602 handler_count = function_state.handler_count();
4603 only_simple_this_property_assignments =
4604 function_state.only_simple_this_property_assignments();
4605 this_property_assignments = function_state.this_property_assignments();
4607 Expect(Token::RBRACE, CHECK_OK);
4608 scope->set_end_position(scanner().location().end_pos);
4611 // Validate strict mode.
4612 if (!top_scope_->is_classic_mode()) {
4613 if (IsEvalOrArguments(function_name)) {
4614 int start_pos = scope->start_position();
4615 int position = function_token_position != RelocInfo::kNoPosition
4616 ? function_token_position
4617 : (start_pos > 0 ? start_pos - 1 : start_pos);
4618 Scanner::Location location = Scanner::Location(position, start_pos);
4619 ReportMessageAt(location,
4620 "strict_function_name", Vector<const char*>::empty());
4624 if (name_loc.IsValid()) {
4625 ReportMessageAt(name_loc, "strict_param_name",
4626 Vector<const char*>::empty());
4630 if (dupe_loc.IsValid()) {
4631 ReportMessageAt(dupe_loc, "strict_param_dupe",
4632 Vector<const char*>::empty());
4636 if (name_is_strict_reserved) {
4637 int start_pos = scope->start_position();
4638 int position = function_token_position != RelocInfo::kNoPosition
4639 ? function_token_position
4640 : (start_pos > 0 ? start_pos - 1 : start_pos);
4641 Scanner::Location location = Scanner::Location(position, start_pos);
4642 ReportMessageAt(location, "strict_reserved_word",
4643 Vector<const char*>::empty());
4647 if (reserved_loc.IsValid()) {
4648 ReportMessageAt(reserved_loc, "strict_reserved_word",
4649 Vector<const char*>::empty());
4653 CheckOctalLiteral(scope->start_position(),
4654 scope->end_position(),
4657 ast_properties = *factory()->visitor()->ast_properties();
4660 if (is_extended_mode()) {
4661 CheckConflictingVarDeclarations(scope, CHECK_OK);
4664 FunctionLiteral* function_literal =
4665 factory()->NewFunctionLiteral(function_name,
4668 materialized_literal_count,
4669 expected_property_count,
4671 only_simple_this_property_assignments,
4672 this_property_assignments,
4674 duplicate_parameters,
4676 FunctionLiteral::kIsFunction);
4677 function_literal->set_function_token_position(function_token_position);
4678 function_literal->set_ast_properties(&ast_properties);
4680 if (fni_ != NULL && should_infer_name) fni_->AddFunction(function_literal);
4681 return function_literal;
4685 preparser::PreParser::PreParseResult Parser::LazyParseFunctionLiteral(
4686 SingletonLogger* logger) {
4687 HistogramTimerScope preparse_scope(isolate()->counters()->pre_parse());
4688 ASSERT_EQ(Token::LBRACE, scanner().current_token());
4690 if (reusable_preparser_ == NULL) {
4691 intptr_t stack_limit = isolate()->stack_guard()->real_climit();
4692 bool do_allow_lazy = true;
4693 reusable_preparser_ = new preparser::PreParser(&scanner_,
4697 allow_natives_syntax_,
4700 preparser::PreParser::PreParseResult result =
4701 reusable_preparser_->PreParseLazyFunction(top_scope_->language_mode(),
4707 Expression* Parser::ParseV8Intrinsic(bool* ok) {
4709 // '%' Identifier Arguments
4711 Expect(Token::MOD, CHECK_OK);
4712 Handle<String> name = ParseIdentifier(CHECK_OK);
4713 ZoneList<Expression*>* args = ParseArguments(CHECK_OK);
4715 if (extension_ != NULL) {
4716 // The extension structures are only accessible while parsing the
4717 // very first time not when reparsing because of lazy compilation.
4718 top_scope_->DeclarationScope()->ForceEagerCompilation();
4721 const Runtime::Function* function = Runtime::FunctionForSymbol(name);
4723 // Check for built-in IS_VAR macro.
4724 if (function != NULL &&
4725 function->intrinsic_type == Runtime::RUNTIME &&
4726 function->function_id == Runtime::kIS_VAR) {
4727 // %IS_VAR(x) evaluates to x if x is a variable,
4728 // leads to a parse error otherwise. Could be implemented as an
4729 // inline function %_IS_VAR(x) to eliminate this special case.
4730 if (args->length() == 1 && args->at(0)->AsVariableProxy() != NULL) {
4733 ReportMessage("unable_to_parse", Vector<const char*>::empty());
4739 // Check that the expected number of arguments are being passed.
4740 if (function != NULL &&
4741 function->nargs != -1 &&
4742 function->nargs != args->length()) {
4743 ReportMessage("illegal_access", Vector<const char*>::empty());
4748 // We have a valid intrinsics call or a call to a builtin.
4749 return factory()->NewCallRuntime(name, function, args);
4753 bool Parser::peek_any_identifier() {
4754 Token::Value next = peek();
4755 return next == Token::IDENTIFIER ||
4756 next == Token::FUTURE_RESERVED_WORD ||
4757 next == Token::FUTURE_STRICT_RESERVED_WORD;
4761 void Parser::Consume(Token::Value token) {
4762 Token::Value next = Next();
4765 ASSERT(next == token);
4769 void Parser::Expect(Token::Value token, bool* ok) {
4770 Token::Value next = Next();
4771 if (next == token) return;
4772 ReportUnexpectedToken(next);
4777 bool Parser::Check(Token::Value token) {
4778 Token::Value next = peek();
4779 if (next == token) {
4787 void Parser::ExpectSemicolon(bool* ok) {
4788 // Check for automatic semicolon insertion according to
4789 // the rules given in ECMA-262, section 7.9, page 21.
4790 Token::Value tok = peek();
4791 if (tok == Token::SEMICOLON) {
4795 if (scanner().HasAnyLineTerminatorBeforeNext() ||
4796 tok == Token::RBRACE ||
4797 tok == Token::EOS) {
4800 Expect(Token::SEMICOLON, ok);
4804 void Parser::ExpectContextualKeyword(const char* keyword, bool* ok) {
4805 Expect(Token::IDENTIFIER, ok);
4807 Handle<String> symbol = GetSymbol(ok);
4809 if (!symbol->IsEqualTo(CStrVector(keyword))) {
4811 ReportUnexpectedToken(scanner().current_token());
4816 Literal* Parser::GetLiteralUndefined() {
4817 return factory()->NewLiteral(isolate()->factory()->undefined_value());
4821 Literal* Parser::GetLiteralTheHole() {
4822 return factory()->NewLiteral(isolate()->factory()->the_hole_value());
4826 // Parses an identifier that is valid for the current scope, in particular it
4827 // fails on strict mode future reserved keywords in a strict scope.
4828 Handle<String> Parser::ParseIdentifier(bool* ok) {
4829 if (!top_scope_->is_classic_mode()) {
4830 Expect(Token::IDENTIFIER, ok);
4831 } else if (!Check(Token::IDENTIFIER)) {
4832 Expect(Token::FUTURE_STRICT_RESERVED_WORD, ok);
4834 if (!*ok) return Handle<String>();
4835 return GetSymbol(ok);
4839 // Parses and identifier or a strict mode future reserved word, and indicate
4840 // whether it is strict mode future reserved.
4841 Handle<String> Parser::ParseIdentifierOrStrictReservedWord(
4842 bool* is_strict_reserved, bool* ok) {
4843 *is_strict_reserved = false;
4844 if (!Check(Token::IDENTIFIER)) {
4845 Expect(Token::FUTURE_STRICT_RESERVED_WORD, ok);
4846 *is_strict_reserved = true;
4848 if (!*ok) return Handle<String>();
4849 return GetSymbol(ok);
4853 Handle<String> Parser::ParseIdentifierName(bool* ok) {
4854 Token::Value next = Next();
4855 if (next != Token::IDENTIFIER &&
4856 next != Token::FUTURE_RESERVED_WORD &&
4857 next != Token::FUTURE_STRICT_RESERVED_WORD &&
4858 !Token::IsKeyword(next)) {
4859 ReportUnexpectedToken(next);
4861 return Handle<String>();
4863 return GetSymbol(ok);
4867 void Parser::MarkAsLValue(Expression* expression) {
4868 VariableProxy* proxy = expression != NULL
4869 ? expression->AsVariableProxy()
4872 if (proxy != NULL) proxy->MarkAsLValue();
4876 // Checks LHS expression for assignment and prefix/postfix increment/decrement
4878 void Parser::CheckStrictModeLValue(Expression* expression,
4881 ASSERT(!top_scope_->is_classic_mode());
4882 VariableProxy* lhs = expression != NULL
4883 ? expression->AsVariableProxy()
4886 if (lhs != NULL && !lhs->is_this() && IsEvalOrArguments(lhs->name())) {
4887 ReportMessage(error, Vector<const char*>::empty());
4893 // Checks whether an octal literal was last seen between beg_pos and end_pos.
4894 // If so, reports an error. Only called for strict mode.
4895 void Parser::CheckOctalLiteral(int beg_pos, int end_pos, bool* ok) {
4896 Scanner::Location octal = scanner().octal_position();
4897 if (octal.IsValid() &&
4898 beg_pos <= octal.beg_pos &&
4899 octal.end_pos <= end_pos) {
4900 ReportMessageAt(octal, "strict_octal_literal",
4901 Vector<const char*>::empty());
4902 scanner().clear_octal_position();
4908 void Parser::CheckConflictingVarDeclarations(Scope* scope, bool* ok) {
4909 Declaration* decl = scope->CheckConflictingVarDeclarations();
4911 // In harmony mode we treat conflicting variable bindinds as early
4912 // errors. See ES5 16 for a definition of early errors.
4913 Handle<String> name = decl->proxy()->name();
4914 SmartArrayPointer<char> c_string = name->ToCString(DISALLOW_NULLS);
4915 const char* elms[2] = { "Variable", *c_string };
4916 Vector<const char*> args(elms, 2);
4917 int position = decl->proxy()->position();
4918 Scanner::Location location = position == RelocInfo::kNoPosition
4919 ? Scanner::Location::invalid()
4920 : Scanner::Location(position, position + 1);
4921 ReportMessageAt(location, "redeclaration", args);
4927 // This function reads an identifier name and determines whether or not it
4928 // is 'get' or 'set'.
4929 Handle<String> Parser::ParseIdentifierNameOrGetOrSet(bool* is_get,
4932 Handle<String> result = ParseIdentifierName(ok);
4933 if (!*ok) return Handle<String>();
4934 if (scanner().is_literal_ascii() && scanner().literal_length() == 3) {
4935 const char* token = scanner().literal_ascii_string().start();
4936 *is_get = strncmp(token, "get", 3) == 0;
4937 *is_set = !*is_get && strncmp(token, "set", 3) == 0;
4943 // ----------------------------------------------------------------------------
4947 bool Parser::TargetStackContainsLabel(Handle<String> label) {
4948 for (Target* t = target_stack_; t != NULL; t = t->previous()) {
4949 BreakableStatement* stat = t->node()->AsBreakableStatement();
4950 if (stat != NULL && ContainsLabel(stat->labels(), label))
4957 BreakableStatement* Parser::LookupBreakTarget(Handle<String> label, bool* ok) {
4958 bool anonymous = label.is_null();
4959 for (Target* t = target_stack_; t != NULL; t = t->previous()) {
4960 BreakableStatement* stat = t->node()->AsBreakableStatement();
4961 if (stat == NULL) continue;
4962 if ((anonymous && stat->is_target_for_anonymous()) ||
4963 (!anonymous && ContainsLabel(stat->labels(), label))) {
4964 RegisterTargetUse(stat->break_target(), t->previous());
4972 IterationStatement* Parser::LookupContinueTarget(Handle<String> label,
4974 bool anonymous = label.is_null();
4975 for (Target* t = target_stack_; t != NULL; t = t->previous()) {
4976 IterationStatement* stat = t->node()->AsIterationStatement();
4977 if (stat == NULL) continue;
4979 ASSERT(stat->is_target_for_anonymous());
4980 if (anonymous || ContainsLabel(stat->labels(), label)) {
4981 RegisterTargetUse(stat->continue_target(), t->previous());
4989 void Parser::RegisterTargetUse(Label* target, Target* stop) {
4990 // Register that a break target found at the given stop in the
4991 // target stack has been used from the top of the target stack. Add
4992 // the break target to any TargetCollectors passed on the stack.
4993 for (Target* t = target_stack_; t != stop; t = t->previous()) {
4994 TargetCollector* collector = t->node()->AsTargetCollector();
4995 if (collector != NULL) collector->AddTarget(target);
5000 Expression* Parser::NewThrowReferenceError(Handle<String> type) {
5001 return NewThrowError(isolate()->factory()->MakeReferenceError_symbol(),
5002 type, HandleVector<Object>(NULL, 0));
5006 Expression* Parser::NewThrowSyntaxError(Handle<String> type,
5007 Handle<Object> first) {
5008 int argc = first.is_null() ? 0 : 1;
5009 Vector< Handle<Object> > arguments = HandleVector<Object>(&first, argc);
5010 return NewThrowError(
5011 isolate()->factory()->MakeSyntaxError_symbol(), type, arguments);
5015 Expression* Parser::NewThrowTypeError(Handle<String> type,
5016 Handle<Object> first,
5017 Handle<Object> second) {
5018 ASSERT(!first.is_null() && !second.is_null());
5019 Handle<Object> elements[] = { first, second };
5020 Vector< Handle<Object> > arguments =
5021 HandleVector<Object>(elements, ARRAY_SIZE(elements));
5022 return NewThrowError(
5023 isolate()->factory()->MakeTypeError_symbol(), type, arguments);
5027 Expression* Parser::NewThrowError(Handle<String> constructor,
5028 Handle<String> type,
5029 Vector< Handle<Object> > arguments) {
5030 int argc = arguments.length();
5031 Handle<FixedArray> elements = isolate()->factory()->NewFixedArray(argc,
5033 for (int i = 0; i < argc; i++) {
5034 Handle<Object> element = arguments[i];
5035 if (!element.is_null()) {
5036 elements->set(i, *element);
5039 Handle<JSArray> array = isolate()->factory()->NewJSArrayWithElements(
5040 elements, FAST_ELEMENTS, TENURED);
5042 ZoneList<Expression*>* args = new(zone()) ZoneList<Expression*>(2);
5043 args->Add(factory()->NewLiteral(type));
5044 args->Add(factory()->NewLiteral(array));
5045 CallRuntime* call_constructor =
5046 factory()->NewCallRuntime(constructor, NULL, args);
5047 return factory()->NewThrow(call_constructor, scanner().location().beg_pos);
5050 // ----------------------------------------------------------------------------
5051 // Regular expressions
5054 RegExpParser::RegExpParser(FlatStringReader* in,
5055 Handle<String>* error,
5057 : isolate_(Isolate::Current()),
5061 current_(kEndMarker),
5065 multiline_(multiline),
5067 contains_anchor_(false),
5068 is_scanned_for_captures_(false),
5074 uc32 RegExpParser::Next() {
5076 return in()->Get(next_pos_);
5083 void RegExpParser::Advance() {
5084 if (next_pos_ < in()->length()) {
5085 StackLimitCheck check(isolate());
5086 if (check.HasOverflowed()) {
5087 ReportError(CStrVector(Isolate::kStackOverflowMessage));
5088 } else if (isolate()->zone()->excess_allocation()) {
5089 ReportError(CStrVector("Regular expression too large"));
5091 current_ = in()->Get(next_pos_);
5095 current_ = kEndMarker;
5101 void RegExpParser::Reset(int pos) {
5107 void RegExpParser::Advance(int dist) {
5108 next_pos_ += dist - 1;
5113 bool RegExpParser::simple() {
5117 RegExpTree* RegExpParser::ReportError(Vector<const char> message) {
5119 *error_ = isolate()->factory()->NewStringFromAscii(message, NOT_TENURED);
5120 // Zip to the end to make sure the no more input is read.
5121 current_ = kEndMarker;
5122 next_pos_ = in()->length();
5129 RegExpTree* RegExpParser::ParsePattern() {
5130 RegExpTree* result = ParseDisjunction(CHECK_FAILED);
5131 ASSERT(!has_more());
5132 // If the result of parsing is a literal string atom, and it has the
5133 // same length as the input, then the atom is identical to the input.
5134 if (result->IsAtom() && result->AsAtom()->length() == in()->length()) {
5143 // Alternative | Disjunction
5151 RegExpTree* RegExpParser::ParseDisjunction() {
5152 // Used to store current state while parsing subexpressions.
5153 RegExpParserState initial_state(NULL, INITIAL, 0);
5154 RegExpParserState* stored_state = &initial_state;
5155 // Cache the builder in a local variable for quick access.
5156 RegExpBuilder* builder = initial_state.builder();
5158 switch (current()) {
5160 if (stored_state->IsSubexpression()) {
5161 // Inside a parenthesized group when hitting end of input.
5162 ReportError(CStrVector("Unterminated group") CHECK_FAILED);
5164 ASSERT_EQ(INITIAL, stored_state->group_type());
5165 // Parsing completed successfully.
5166 return builder->ToRegExp();
5168 if (!stored_state->IsSubexpression()) {
5169 ReportError(CStrVector("Unmatched ')'") CHECK_FAILED);
5171 ASSERT_NE(INITIAL, stored_state->group_type());
5174 // End disjunction parsing and convert builder content to new single
5176 RegExpTree* body = builder->ToRegExp();
5178 int end_capture_index = captures_started();
5180 int capture_index = stored_state->capture_index();
5181 SubexpressionType type = stored_state->group_type();
5183 // Restore previous state.
5184 stored_state = stored_state->previous_state();
5185 builder = stored_state->builder();
5187 // Build result of subexpression.
5188 if (type == CAPTURE) {
5189 RegExpCapture* capture = new(zone()) RegExpCapture(body, capture_index);
5190 captures_->at(capture_index - 1) = capture;
5192 } else if (type != GROUPING) {
5193 ASSERT(type == POSITIVE_LOOKAHEAD || type == NEGATIVE_LOOKAHEAD);
5194 bool is_positive = (type == POSITIVE_LOOKAHEAD);
5195 body = new(zone()) RegExpLookahead(body,
5197 end_capture_index - capture_index,
5200 builder->AddAtom(body);
5201 // For compatability with JSC and ES3, we allow quantifiers after
5202 // lookaheads, and break in all cases.
5207 builder->NewAlternative();
5213 return ReportError(CStrVector("Nothing to repeat"));
5217 builder->AddAssertion(
5218 new(zone()) RegExpAssertion(RegExpAssertion::START_OF_LINE));
5220 builder->AddAssertion(
5221 new(zone()) RegExpAssertion(RegExpAssertion::START_OF_INPUT));
5222 set_contains_anchor();
5228 RegExpAssertion::Type type =
5229 multiline_ ? RegExpAssertion::END_OF_LINE :
5230 RegExpAssertion::END_OF_INPUT;
5231 builder->AddAssertion(new(zone()) RegExpAssertion(type));
5236 // everything except \x0a, \x0d, \u2028 and \u2029
5237 ZoneList<CharacterRange>* ranges =
5238 new(zone()) ZoneList<CharacterRange>(2);
5239 CharacterRange::AddClassEscape('.', ranges);
5240 RegExpTree* atom = new(zone()) RegExpCharacterClass(ranges, false);
5241 builder->AddAtom(atom);
5245 SubexpressionType type = CAPTURE;
5247 if (current() == '?') {
5253 type = POSITIVE_LOOKAHEAD;
5256 type = NEGATIVE_LOOKAHEAD;
5259 ReportError(CStrVector("Invalid group") CHECK_FAILED);
5264 if (captures_ == NULL) {
5265 captures_ = new(zone()) ZoneList<RegExpCapture*>(2);
5267 if (captures_started() >= kMaxCaptures) {
5268 ReportError(CStrVector("Too many captures") CHECK_FAILED);
5270 captures_->Add(NULL);
5272 // Store current state and begin new disjunction parsing.
5273 stored_state = new(zone()) RegExpParserState(stored_state,
5275 captures_started());
5276 builder = stored_state->builder();
5280 RegExpTree* atom = ParseCharacterClass(CHECK_FAILED);
5281 builder->AddAtom(atom);
5289 return ReportError(CStrVector("\\ at end of pattern"));
5292 builder->AddAssertion(
5293 new(zone()) RegExpAssertion(RegExpAssertion::BOUNDARY));
5297 builder->AddAssertion(
5298 new(zone()) RegExpAssertion(RegExpAssertion::NON_BOUNDARY));
5301 // CharacterClassEscape
5303 // CharacterClassEscape :: one of
5305 case 'd': case 'D': case 's': case 'S': case 'w': case 'W': {
5308 ZoneList<CharacterRange>* ranges =
5309 new(zone()) ZoneList<CharacterRange>(2);
5310 CharacterRange::AddClassEscape(c, ranges);
5311 RegExpTree* atom = new(zone()) RegExpCharacterClass(ranges, false);
5312 builder->AddAtom(atom);
5315 case '1': case '2': case '3': case '4': case '5': case '6':
5316 case '7': case '8': case '9': {
5318 if (ParseBackReferenceIndex(&index)) {
5319 RegExpCapture* capture = NULL;
5320 if (captures_ != NULL && index <= captures_->length()) {
5321 capture = captures_->at(index - 1);
5323 if (capture == NULL) {
5324 builder->AddEmpty();
5327 RegExpTree* atom = new(zone()) RegExpBackReference(capture);
5328 builder->AddAtom(atom);
5331 uc32 first_digit = Next();
5332 if (first_digit == '8' || first_digit == '9') {
5333 // Treat as identity escape
5334 builder->AddCharacter(first_digit);
5342 uc32 octal = ParseOctalLiteral();
5343 builder->AddCharacter(octal);
5346 // ControlEscape :: one of
5350 builder->AddCharacter('\f');
5354 builder->AddCharacter('\n');
5358 builder->AddCharacter('\r');
5362 builder->AddCharacter('\t');
5366 builder->AddCharacter('\v');
5370 uc32 controlLetter = Next();
5371 // Special case if it is an ASCII letter.
5372 // Convert lower case letters to uppercase.
5373 uc32 letter = controlLetter & ~('a' ^ 'A');
5374 if (letter < 'A' || 'Z' < letter) {
5375 // controlLetter is not in range 'A'-'Z' or 'a'-'z'.
5376 // This is outside the specification. We match JSC in
5377 // reading the backslash as a literal character instead
5378 // of as starting an escape.
5379 builder->AddCharacter('\\');
5382 builder->AddCharacter(controlLetter & 0x1f);
5389 if (ParseHexEscape(2, &value)) {
5390 builder->AddCharacter(value);
5392 builder->AddCharacter('x');
5399 if (ParseHexEscape(4, &value)) {
5400 builder->AddCharacter(value);
5402 builder->AddCharacter('u');
5408 builder->AddCharacter(Next());
5415 if (ParseIntervalQuantifier(&dummy, &dummy)) {
5416 ReportError(CStrVector("Nothing to repeat") CHECK_FAILED);
5421 builder->AddCharacter(current());
5424 } // end switch(current())
5428 switch (current()) {
5429 // QuantifierPrefix ::
5436 max = RegExpTree::kInfinity;
5441 max = RegExpTree::kInfinity;
5450 if (ParseIntervalQuantifier(&min, &max)) {
5452 ReportError(CStrVector("numbers out of order in {} quantifier.")
5462 RegExpQuantifier::Type type = RegExpQuantifier::GREEDY;
5463 if (current() == '?') {
5464 type = RegExpQuantifier::NON_GREEDY;
5466 } else if (FLAG_regexp_possessive_quantifier && current() == '+') {
5467 // FLAG_regexp_possessive_quantifier is a debug-only flag.
5468 type = RegExpQuantifier::POSSESSIVE;
5471 builder->AddQuantifierToAtom(min, max, type);
5477 // Currently only used in an ASSERT.
5478 static bool IsSpecialClassEscape(uc32 c) {
5491 // In order to know whether an escape is a backreference or not we have to scan
5492 // the entire regexp and find the number of capturing parentheses. However we
5493 // don't want to scan the regexp twice unless it is necessary. This mini-parser
5494 // is called when needed. It can see the difference between capturing and
5495 // noncapturing parentheses and can skip character classes and backslash-escaped
5497 void RegExpParser::ScanForCaptures() {
5498 // Start with captures started previous to current position
5499 int capture_count = captures_started();
5500 // Add count of captures after this position.
5502 while ((n = current()) != kEndMarker) {
5510 while ((c = current()) != kEndMarker) {
5515 if (c == ']') break;
5521 if (current() != '?') capture_count++;
5525 capture_count_ = capture_count;
5526 is_scanned_for_captures_ = true;
5530 bool RegExpParser::ParseBackReferenceIndex(int* index_out) {
5531 ASSERT_EQ('\\', current());
5532 ASSERT('1' <= Next() && Next() <= '9');
5533 // Try to parse a decimal literal that is no greater than the total number
5534 // of left capturing parentheses in the input.
5535 int start = position();
5536 int value = Next() - '0';
5540 if (IsDecimalDigit(c)) {
5541 value = 10 * value + (c - '0');
5542 if (value > kMaxCaptures) {
5551 if (value > captures_started()) {
5552 if (!is_scanned_for_captures_) {
5553 int saved_position = position();
5555 Reset(saved_position);
5557 if (value > capture_count_) {
5567 // QuantifierPrefix ::
5568 // { DecimalDigits }
5569 // { DecimalDigits , }
5570 // { DecimalDigits , DecimalDigits }
5572 // Returns true if parsing succeeds, and set the min_out and max_out
5573 // values. Values are truncated to RegExpTree::kInfinity if they overflow.
5574 bool RegExpParser::ParseIntervalQuantifier(int* min_out, int* max_out) {
5575 ASSERT_EQ(current(), '{');
5576 int start = position();
5579 if (!IsDecimalDigit(current())) {
5583 while (IsDecimalDigit(current())) {
5584 int next = current() - '0';
5585 if (min > (RegExpTree::kInfinity - next) / 10) {
5586 // Overflow. Skip past remaining decimal digits and return -1.
5589 } while (IsDecimalDigit(current()));
5590 min = RegExpTree::kInfinity;
5593 min = 10 * min + next;
5597 if (current() == '}') {
5600 } else if (current() == ',') {
5602 if (current() == '}') {
5603 max = RegExpTree::kInfinity;
5606 while (IsDecimalDigit(current())) {
5607 int next = current() - '0';
5608 if (max > (RegExpTree::kInfinity - next) / 10) {
5611 } while (IsDecimalDigit(current()));
5612 max = RegExpTree::kInfinity;
5615 max = 10 * max + next;
5618 if (current() != '}') {
5634 uc32 RegExpParser::ParseOctalLiteral() {
5635 ASSERT('0' <= current() && current() <= '7');
5636 // For compatibility with some other browsers (not all), we parse
5637 // up to three octal digits with a value below 256.
5638 uc32 value = current() - '0';
5640 if ('0' <= current() && current() <= '7') {
5641 value = value * 8 + current() - '0';
5643 if (value < 32 && '0' <= current() && current() <= '7') {
5644 value = value * 8 + current() - '0';
5652 bool RegExpParser::ParseHexEscape(int length, uc32 *value) {
5653 int start = position();
5656 for (int i = 0; !done; i++) {
5658 int d = HexValue(c);
5665 if (i == length - 1) {
5674 uc32 RegExpParser::ParseClassCharacterEscape() {
5675 ASSERT(current() == '\\');
5676 ASSERT(has_next() && !IsSpecialClassEscape(Next()));
5678 switch (current()) {
5682 // ControlEscape :: one of
5700 uc32 controlLetter = Next();
5701 uc32 letter = controlLetter & ~('A' ^ 'a');
5702 // For compatibility with JSC, inside a character class
5703 // we also accept digits and underscore as control characters.
5704 if ((controlLetter >= '0' && controlLetter <= '9') ||
5705 controlLetter == '_' ||
5706 (letter >= 'A' && letter <= 'Z')) {
5708 // Control letters mapped to ASCII control characters in the range
5710 return controlLetter & 0x1f;
5712 // We match JSC in reading the backslash as a literal
5713 // character instead of as starting an escape.
5716 case '0': case '1': case '2': case '3': case '4': case '5':
5718 // For compatibility, we interpret a decimal escape that isn't
5719 // a back reference (and therefore either \0 or not valid according
5720 // to the specification) as a 1..3 digit octal character code.
5721 return ParseOctalLiteral();
5725 if (ParseHexEscape(2, &value)) {
5728 // If \x is not followed by a two-digit hexadecimal, treat it
5729 // as an identity escape.
5735 if (ParseHexEscape(4, &value)) {
5738 // If \u is not followed by a four-digit hexadecimal, treat it
5739 // as an identity escape.
5743 // Extended identity escape. We accept any character that hasn't
5744 // been matched by a more specific case, not just the subset required
5745 // by the ECMAScript specification.
5746 uc32 result = current();
5755 CharacterRange RegExpParser::ParseClassAtom(uc16* char_class) {
5756 ASSERT_EQ(0, *char_class);
5757 uc32 first = current();
5758 if (first == '\\') {
5760 case 'w': case 'W': case 'd': case 'D': case 's': case 'S': {
5761 *char_class = Next();
5763 return CharacterRange::Singleton(0); // Return dummy value.
5766 return ReportError(CStrVector("\\ at end of pattern"));
5768 uc32 c = ParseClassCharacterEscape(CHECK_FAILED);
5769 return CharacterRange::Singleton(c);
5773 return CharacterRange::Singleton(first);
5778 static const uc16 kNoCharClass = 0;
5780 // Adds range or pre-defined character class to character ranges.
5781 // If char_class is not kInvalidClass, it's interpreted as a class
5782 // escape (i.e., 's' means whitespace, from '\s').
5783 static inline void AddRangeOrEscape(ZoneList<CharacterRange>* ranges,
5785 CharacterRange range) {
5786 if (char_class != kNoCharClass) {
5787 CharacterRange::AddClassEscape(char_class, ranges);
5794 RegExpTree* RegExpParser::ParseCharacterClass() {
5795 static const char* kUnterminated = "Unterminated character class";
5796 static const char* kRangeOutOfOrder = "Range out of order in character class";
5798 ASSERT_EQ(current(), '[');
5800 bool is_negated = false;
5801 if (current() == '^') {
5805 ZoneList<CharacterRange>* ranges = new(zone()) ZoneList<CharacterRange>(2);
5806 while (has_more() && current() != ']') {
5807 uc16 char_class = kNoCharClass;
5808 CharacterRange first = ParseClassAtom(&char_class CHECK_FAILED);
5809 if (current() == '-') {
5811 if (current() == kEndMarker) {
5812 // If we reach the end we break out of the loop and let the
5813 // following code report an error.
5815 } else if (current() == ']') {
5816 AddRangeOrEscape(ranges, char_class, first);
5817 ranges->Add(CharacterRange::Singleton('-'));
5820 uc16 char_class_2 = kNoCharClass;
5821 CharacterRange next = ParseClassAtom(&char_class_2 CHECK_FAILED);
5822 if (char_class != kNoCharClass || char_class_2 != kNoCharClass) {
5823 // Either end is an escaped character class. Treat the '-' verbatim.
5824 AddRangeOrEscape(ranges, char_class, first);
5825 ranges->Add(CharacterRange::Singleton('-'));
5826 AddRangeOrEscape(ranges, char_class_2, next);
5829 if (first.from() > next.to()) {
5830 return ReportError(CStrVector(kRangeOutOfOrder) CHECK_FAILED);
5832 ranges->Add(CharacterRange::Range(first.from(), next.to()));
5834 AddRangeOrEscape(ranges, char_class, first);
5838 return ReportError(CStrVector(kUnterminated) CHECK_FAILED);
5841 if (ranges->length() == 0) {
5842 ranges->Add(CharacterRange::Everything());
5843 is_negated = !is_negated;
5845 return new(zone()) RegExpCharacterClass(ranges, is_negated);
5849 // ----------------------------------------------------------------------------
5850 // The Parser interface.
5852 ParserMessage::~ParserMessage() {
5853 for (int i = 0; i < args().length(); i++)
5854 DeleteArray(args()[i]);
5855 DeleteArray(args().start());
5859 ScriptDataImpl::~ScriptDataImpl() {
5860 if (owns_store_) store_.Dispose();
5864 int ScriptDataImpl::Length() {
5865 return store_.length() * sizeof(unsigned);
5869 const char* ScriptDataImpl::Data() {
5870 return reinterpret_cast<const char*>(store_.start());
5874 bool ScriptDataImpl::HasError() {
5879 void ScriptDataImpl::Initialize() {
5880 // Prepares state for use.
5881 if (store_.length() >= PreparseDataConstants::kHeaderSize) {
5882 function_index_ = PreparseDataConstants::kHeaderSize;
5883 int symbol_data_offset = PreparseDataConstants::kHeaderSize
5884 + store_[PreparseDataConstants::kFunctionsSizeOffset];
5885 if (store_.length() > symbol_data_offset) {
5886 symbol_data_ = reinterpret_cast<byte*>(&store_[symbol_data_offset]);
5888 // Partial preparse causes no symbol information.
5889 symbol_data_ = reinterpret_cast<byte*>(&store_[0] + store_.length());
5891 symbol_data_end_ = reinterpret_cast<byte*>(&store_[0] + store_.length());
5896 int ScriptDataImpl::ReadNumber(byte** source) {
5897 // Reads a number from symbol_data_ in base 128. The most significant
5898 // bit marks that there are more digits.
5899 // If the first byte is 0x80 (kNumberTerminator), it would normally
5900 // represent a leading zero. Since that is useless, and therefore won't
5901 // appear as the first digit of any actual value, it is used to
5902 // mark the end of the input stream.
5903 byte* data = *source;
5904 if (data >= symbol_data_end_) return -1;
5906 if (input == PreparseDataConstants::kNumberTerminator) {
5907 // End of stream marker.
5910 int result = input & 0x7f;
5912 while ((input & 0x80u) != 0) {
5913 if (data >= symbol_data_end_) return -1;
5915 result = (result << 7) | (input & 0x7f);
5923 // Create a Scanner for the preparser to use as input, and preparse the source.
5924 static ScriptDataImpl* DoPreParse(Utf16CharacterStream* source,
5926 ParserRecorder* recorder) {
5927 Isolate* isolate = Isolate::Current();
5928 HistogramTimerScope timer(isolate->counters()->pre_parse());
5929 Scanner scanner(isolate->unicode_cache());
5930 scanner.SetHarmonyScoping(FLAG_harmony_scoping);
5931 scanner.Initialize(source);
5932 intptr_t stack_limit = isolate->stack_guard()->real_climit();
5933 preparser::PreParser::PreParseResult result =
5934 preparser::PreParser::PreParseProgram(&scanner,
5938 if (result == preparser::PreParser::kPreParseStackOverflow) {
5939 isolate->StackOverflow();
5943 // Extract the accumulated data from the recorder as a single
5944 // contiguous vector that we are responsible for disposing.
5945 Vector<unsigned> store = recorder->ExtractData();
5946 return new ScriptDataImpl(store);
5950 // Preparse, but only collect data that is immediately useful,
5951 // even if the preparser data is only used once.
5952 ScriptDataImpl* ParserApi::PartialPreParse(Handle<String> source,
5953 v8::Extension* extension,
5955 bool allow_lazy = FLAG_lazy && (extension == NULL);
5957 // Partial preparsing is only about lazily compiled functions.
5958 // If we don't allow lazy compilation, the log data will be empty.
5961 flags |= kAllowLazy;
5962 PartialParserRecorder recorder;
5963 int source_length = source->length();
5964 if (source->IsExternalTwoByteString()) {
5965 ExternalTwoByteStringUtf16CharacterStream stream(
5966 Handle<ExternalTwoByteString>::cast(source), 0, source_length);
5967 return DoPreParse(&stream, flags, &recorder);
5969 GenericStringUtf16CharacterStream stream(source, 0, source_length);
5970 return DoPreParse(&stream, flags, &recorder);
5975 ScriptDataImpl* ParserApi::PreParse(Utf16CharacterStream* source,
5976 v8::Extension* extension,
5978 Handle<Script> no_script;
5979 if (FLAG_lazy && (extension == NULL)) {
5980 flags |= kAllowLazy;
5982 CompleteParserRecorder recorder;
5983 return DoPreParse(source, flags, &recorder);
5987 bool RegExpParser::ParseRegExp(FlatStringReader* input,
5989 RegExpCompileData* result) {
5990 ASSERT(result != NULL);
5991 RegExpParser parser(input, &result->error, multiline);
5992 RegExpTree* tree = parser.ParsePattern();
5993 if (parser.failed()) {
5994 ASSERT(tree == NULL);
5995 ASSERT(!result->error.is_null());
5997 ASSERT(tree != NULL);
5998 ASSERT(result->error.is_null());
5999 result->tree = tree;
6000 int capture_count = parser.captures_started();
6001 result->simple = tree->IsAtom() && parser.simple() && capture_count == 0;
6002 result->contains_anchor = parser.contains_anchor();
6003 result->capture_count = capture_count;
6005 return !parser.failed();
6009 bool ParserApi::Parse(CompilationInfo* info, int parsing_flags) {
6010 ASSERT(info->function() == NULL);
6011 FunctionLiteral* result = NULL;
6012 Handle<Script> script = info->script();
6013 ASSERT((parsing_flags & kLanguageModeMask) == CLASSIC_MODE);
6014 if (!info->is_native() && FLAG_harmony_scoping) {
6015 // Harmony scoping is requested.
6016 parsing_flags |= EXTENDED_MODE;
6018 if (!info->is_native() && FLAG_harmony_modules) {
6019 parsing_flags |= kAllowModules;
6021 if (FLAG_allow_natives_syntax || info->is_native()) {
6022 // We require %identifier(..) syntax.
6023 parsing_flags |= kAllowNativesSyntax;
6025 if (info->is_lazy()) {
6026 ASSERT(!info->is_eval());
6027 Parser parser(script, parsing_flags, NULL, NULL);
6028 if (info->shared_info()->is_function()) {
6029 result = parser.ParseLazy(info);
6031 result = parser.ParseProgram(info);
6034 ScriptDataImpl* pre_data = info->pre_parse_data();
6035 Parser parser(script, parsing_flags, info->extension(), pre_data);
6036 if (pre_data != NULL && pre_data->has_error()) {
6037 Scanner::Location loc = pre_data->MessageLocation();
6038 const char* message = pre_data->BuildMessage();
6039 Vector<const char*> args = pre_data->BuildArgs();
6040 parser.ReportMessageAt(loc, message, args);
6041 DeleteArray(message);
6042 for (int i = 0; i < args.length(); i++) {
6043 DeleteArray(args[i]);
6045 DeleteArray(args.start());
6046 ASSERT(info->isolate()->has_pending_exception());
6048 result = parser.ParseProgram(info);
6051 info->SetFunction(result);
6052 return (result != NULL);
6055 } } // namespace v8::internal