OLD | NEW |
---|---|
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #ifndef V8_AST_SCOPES_H_ | 5 #ifndef V8_AST_SCOPES_H_ |
6 #define V8_AST_SCOPES_H_ | 6 #define V8_AST_SCOPES_H_ |
7 | 7 |
8 #include "src/ast/ast.h" | 8 #include "src/ast/ast.h" |
9 #include "src/base/hashmap.h" | 9 #include "src/base/hashmap.h" |
10 #include "src/globals.h" | 10 #include "src/globals.h" |
(...skipping 181 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
192 // Create a new unresolved variable. | 192 // Create a new unresolved variable. |
193 VariableProxy* NewUnresolved(AstNodeFactory* factory, | 193 VariableProxy* NewUnresolved(AstNodeFactory* factory, |
194 const AstRawString* name, | 194 const AstRawString* name, |
195 Variable::Kind kind = Variable::NORMAL, | 195 Variable::Kind kind = Variable::NORMAL, |
196 int start_position = kNoSourcePosition, | 196 int start_position = kNoSourcePosition, |
197 int end_position = kNoSourcePosition) { | 197 int end_position = kNoSourcePosition) { |
198 // Note that we must not share the unresolved variables with | 198 // Note that we must not share the unresolved variables with |
199 // the same name because they may be removed selectively via | 199 // the same name because they may be removed selectively via |
200 // RemoveUnresolved(). | 200 // RemoveUnresolved(). |
201 DCHECK(!already_resolved()); | 201 DCHECK(!already_resolved()); |
202 DCHECK_EQ(factory->zone(), zone()); | |
202 VariableProxy* proxy = | 203 VariableProxy* proxy = |
203 factory->NewVariableProxy(name, kind, start_position, end_position); | 204 factory->NewVariableProxy(name, kind, start_position, end_position); |
204 proxy->set_next_unresolved(unresolved_); | 205 proxy->set_next_unresolved(unresolved_); |
205 unresolved_ = proxy; | 206 unresolved_ = proxy; |
206 return proxy; | 207 return proxy; |
207 } | 208 } |
208 | 209 |
209 void AddUnresolved(VariableProxy* proxy) { | 210 void AddUnresolved(VariableProxy* proxy) { |
210 DCHECK(!already_resolved()); | 211 DCHECK(!already_resolved()); |
211 DCHECK(!proxy->is_resolved()); | 212 DCHECK(!proxy->is_resolved()); |
(...skipping 367 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
579 Scope* ClosureScope(); | 580 Scope* ClosureScope(); |
580 | 581 |
581 // Find the first (non-arrow) function or script scope. This is where | 582 // Find the first (non-arrow) function or script scope. This is where |
582 // 'this' is bound, and what determines the function kind. | 583 // 'this' is bound, and what determines the function kind. |
583 Scope* ReceiverScope(); | 584 Scope* ReceiverScope(); |
584 | 585 |
585 Handle<ScopeInfo> GetScopeInfo(Isolate* isolate); | 586 Handle<ScopeInfo> GetScopeInfo(Isolate* isolate); |
586 | 587 |
587 Handle<StringSet> CollectNonLocals(Handle<StringSet> non_locals); | 588 Handle<StringSet> CollectNonLocals(Handle<StringSet> non_locals); |
588 | 589 |
590 // Tries to resolve local variables inside max_outer_scope; collects those | |
591 // which cannot be resolved. | |
592 void CollectUnresolvableLocals(VariableProxy** still_unresolved, | |
titzer
2016/08/01 17:58:43
Since this is a public method, is it possible to w
marja
2016/08/02 07:42:37
Oops, this was public by accident, making it priva
| |
593 Scope* max_outer_scope); | |
594 | |
589 // --------------------------------------------------------------------------- | 595 // --------------------------------------------------------------------------- |
590 // Strict mode support. | 596 // Strict mode support. |
591 bool IsDeclared(const AstRawString* name) { | 597 bool IsDeclared(const AstRawString* name) { |
592 // During formal parameter list parsing the scope only contains | 598 // During formal parameter list parsing the scope only contains |
593 // two variables inserted at initialization: "this" and "arguments". | 599 // two variables inserted at initialization: "this" and "arguments". |
594 // "this" is an invalid parameter name and "arguments" is invalid parameter | 600 // "this" is an invalid parameter name and "arguments" is invalid parameter |
595 // name in strict mode. Therefore looking up with the map which includes | 601 // name in strict mode. Therefore looking up with the map which includes |
596 // "this" and "arguments" in addition to all formal parameters is safe. | 602 // "this" and "arguments" in addition to all formal parameters is safe. |
597 return variables_.Lookup(name) != NULL; | 603 return variables_.Lookup(name) != NULL; |
598 } | 604 } |
599 | 605 |
600 bool IsDeclaredParameter(const AstRawString* name) { | 606 bool IsDeclaredParameter(const AstRawString* name) { |
601 // If IsSimpleParameterList is false, duplicate parameters are not allowed, | 607 // If IsSimpleParameterList is false, duplicate parameters are not allowed, |
602 // however `arguments` may be allowed if function is not strict code. Thus, | 608 // however `arguments` may be allowed if function is not strict code. Thus, |
603 // the assumptions explained above do not hold. | 609 // the assumptions explained above do not hold. |
604 return params_.Contains(variables_.Lookup(name)); | 610 return params_.Contains(variables_.Lookup(name)); |
605 } | 611 } |
606 | 612 |
607 SloppyBlockFunctionMap* sloppy_block_function_map() { | 613 SloppyBlockFunctionMap* sloppy_block_function_map() { |
608 return &sloppy_block_function_map_; | 614 return &sloppy_block_function_map_; |
609 } | 615 } |
610 | 616 |
617 // To be called during parsing. Do just enough scope analysis that we can | |
618 // discard the Scope for lazily compiled functions. In particular, this | |
619 // records variables which cannot be resolved inside the Scope (we don't yet | |
620 // know what they will resolve to since the outer Scopes are incomplete) and | |
621 // migrates them into migrate_to. | |
622 void AnalyzePartially(Scope* migrate_to, AstNodeFactory* ast_node_factory); | |
titzer
2016/08/01 17:58:43
Same here. Is it possible to write a unittest that
marja
2016/08/02 07:42:37
I'll look into that after this CL to see how much
| |
623 | |
611 // --------------------------------------------------------------------------- | 624 // --------------------------------------------------------------------------- |
612 // Debugging. | 625 // Debugging. |
613 | 626 |
614 #ifdef DEBUG | 627 #ifdef DEBUG |
615 void Print(int n = 0); // n = indentation; n < 0 => don't print recursively | 628 void Print(int n = 0); // n = indentation; n < 0 => don't print recursively |
616 | 629 |
617 // Check that the scope has positions assigned. | 630 // Check that the scope has positions assigned. |
618 void CheckScopePositions(); | 631 void CheckScopePositions(); |
632 | |
633 // Check that all Scopes in the scope tree use the same Zone. | |
634 void CheckZones(); | |
619 #endif | 635 #endif |
620 | 636 |
621 // --------------------------------------------------------------------------- | 637 // --------------------------------------------------------------------------- |
622 // Implementation. | 638 // Implementation. |
623 private: | 639 private: |
624 // Scope tree. | 640 // Scope tree. |
625 Scope* outer_scope_; // the immediately enclosing outer scope, or NULL | 641 Scope* outer_scope_; // the immediately enclosing outer scope, or NULL |
626 Scope* inner_scope_; // an inner scope of this scope | 642 Scope* inner_scope_; // an inner scope of this scope |
627 Scope* sibling_; // a sibling inner scope of the outer scope of this scope. | 643 Scope* sibling_; // a sibling inner scope of the outer scope of this scope. |
628 | 644 |
(...skipping 139 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
768 // * A 'with' statement has been encountered and there is no variable | 784 // * A 'with' statement has been encountered and there is no variable |
769 // binding for the name between the variable reference and the 'with'. | 785 // binding for the name between the variable reference and the 'with'. |
770 // The variable potentially references a property of the 'with' object. | 786 // The variable potentially references a property of the 'with' object. |
771 // * The code is being executed as part of a call to 'eval' and the calling | 787 // * The code is being executed as part of a call to 'eval' and the calling |
772 // context chain contains either a variable binding for the name or it | 788 // context chain contains either a variable binding for the name or it |
773 // contains a 'with' context. | 789 // contains a 'with' context. |
774 DYNAMIC_LOOKUP | 790 DYNAMIC_LOOKUP |
775 }; | 791 }; |
776 | 792 |
777 // Lookup a variable reference given by name recursively starting with this | 793 // Lookup a variable reference given by name recursively starting with this |
778 // scope. If the code is executed because of a call to 'eval', the context | 794 // scope, but only until max_outer_scope (if not nullptr). If the code is |
779 // parameter should be set to the calling context of 'eval'. | 795 // executed because of a call to 'eval', the context parameter should be set |
796 // to the calling context of 'eval'. | |
780 Variable* LookupRecursive(VariableProxy* proxy, BindingKind* binding_kind, | 797 Variable* LookupRecursive(VariableProxy* proxy, BindingKind* binding_kind, |
781 AstNodeFactory* factory); | 798 AstNodeFactory* factory, |
799 Scope* max_outer_scope = nullptr); | |
782 MUST_USE_RESULT | 800 MUST_USE_RESULT |
783 bool ResolveVariable(ParseInfo* info, VariableProxy* proxy, | 801 bool ResolveVariable(ParseInfo* info, VariableProxy* proxy, |
784 AstNodeFactory* factory); | 802 AstNodeFactory* factory); |
785 MUST_USE_RESULT | 803 MUST_USE_RESULT |
786 bool ResolveVariablesRecursively(ParseInfo* info, AstNodeFactory* factory); | 804 bool ResolveVariablesRecursively(ParseInfo* info, AstNodeFactory* factory); |
787 | 805 |
788 // Scope analysis. | 806 // Scope analysis. |
789 void PropagateScopeInfo(bool outer_scope_calls_sloppy_eval); | 807 void PropagateScopeInfo(bool outer_scope_calls_sloppy_eval); |
790 bool HasTrivialContext() const; | 808 bool HasTrivialContext() const; |
791 | 809 |
(...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
851 | 869 |
852 void SetDefaults(); | 870 void SetDefaults(); |
853 | 871 |
854 PendingCompilationErrorHandler pending_error_handler_; | 872 PendingCompilationErrorHandler pending_error_handler_; |
855 }; | 873 }; |
856 | 874 |
857 } // namespace internal | 875 } // namespace internal |
858 } // namespace v8 | 876 } // namespace v8 |
859 | 877 |
860 #endif // V8_AST_SCOPES_H_ | 878 #endif // V8_AST_SCOPES_H_ |
OLD | NEW |