Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2006-2008 the V8 project authors. All rights reserved. | 1 // Copyright 2006-2008 the V8 project authors. All rights reserved. |
| 2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
| 3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
| 4 // met: | 4 // met: |
| 5 // | 5 // |
| 6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
| 7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
| 8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
| 9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
| 10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
| (...skipping 24 matching lines...) Expand all Loading... | |
| 35 #include "runtime.h" | 35 #include "runtime.h" |
| 36 #include "parser.h" | 36 #include "parser.h" |
| 37 #include "scopes.h" | 37 #include "scopes.h" |
| 38 #include "string-stream.h" | 38 #include "string-stream.h" |
| 39 | 39 |
| 40 namespace v8 { namespace internal { | 40 namespace v8 { namespace internal { |
| 41 | 41 |
| 42 class ParserFactory; | 42 class ParserFactory; |
| 43 class ParserLog; | 43 class ParserLog; |
| 44 class TemporaryScope; | 44 class TemporaryScope; |
| 45 class Target; | |
| 46 | |
| 45 template <typename T> class ZoneListWrapper; | 47 template <typename T> class ZoneListWrapper; |
| 46 | 48 |
| 47 | 49 |
| 50 // PositionStack is used for on-stack allocation of token positions for | |
| 51 // new expressions. Please look at ParseNewExpression. | |
| 52 | |
| 53 class PositionStack { | |
| 54 public: | |
| 55 PositionStack() : top_(NULL) {} | |
| 56 ~PositionStack() { } | |
| 57 | |
| 58 class Element { | |
|
Kasper Lund
2009/05/15 13:37:11
Couldn't the entire Element class be private?
| |
| 59 public: | |
| 60 Element(PositionStack* stack, int value) { | |
| 61 previous_ = stack->top(); | |
| 62 value_ = value; | |
| 63 stack->set_top(this); | |
| 64 } | |
| 65 protected: | |
|
Kasper Lund
2009/05/15 13:37:11
How about a newline before protected: and private:
Kasper Lund
2009/05/15 13:37:11
Why do you have both private and protected? Do you
| |
| 66 Element* previous() { return previous_; } | |
| 67 int value() { return value_; } | |
| 68 friend class PositionStack; | |
| 69 private: | |
| 70 Element* previous_; | |
| 71 int value_; | |
| 72 }; | |
| 73 | |
| 74 bool is_empty() { return top_ == NULL; } | |
| 75 int pop() { | |
| 76 ASSERT(!is_empty()); | |
| 77 int result = top_->value(); | |
| 78 top_ = top_->previous(); | |
| 79 return result; | |
| 80 } | |
| 81 protected: | |
| 82 Element* top() { return top_; } | |
| 83 void set_top(Element* value) { top_ = value; } | |
| 84 private: | |
| 85 Element* top_; | |
| 86 }; | |
| 87 | |
| 88 | |
| 48 class Parser { | 89 class Parser { |
| 49 public: | 90 public: |
| 50 Parser(Handle<Script> script, bool allow_natives_syntax, | 91 Parser(Handle<Script> script, bool allow_natives_syntax, |
| 51 v8::Extension* extension, bool is_pre_parsing, | 92 v8::Extension* extension, bool is_pre_parsing, |
| 52 ParserFactory* factory, ParserLog* log, ScriptDataImpl* pre_data); | 93 ParserFactory* factory, ParserLog* log, ScriptDataImpl* pre_data); |
| 53 virtual ~Parser() { } | 94 virtual ~Parser() { } |
| 54 | 95 |
| 55 // Pre-parse the program from the character stream; returns true on | 96 // Pre-parse the program from the character stream; returns true on |
| 56 // success, false if a stack-overflow happened during parsing. | 97 // success, false if a stack-overflow happened during parsing. |
| 57 bool PreParseProgram(unibrow::CharacterStream* stream); | 98 bool PreParseProgram(unibrow::CharacterStream* stream); |
| (...skipping 28 matching lines...) Expand all Loading... | |
| 86 void ReportUnexpectedToken(Token::Value token); | 127 void ReportUnexpectedToken(Token::Value token); |
| 87 | 128 |
| 88 Handle<Script> script_; | 129 Handle<Script> script_; |
| 89 Scanner scanner_; | 130 Scanner scanner_; |
| 90 | 131 |
| 91 Scope* top_scope_; | 132 Scope* top_scope_; |
| 92 int with_nesting_level_; | 133 int with_nesting_level_; |
| 93 | 134 |
| 94 TemporaryScope* temp_scope_; | 135 TemporaryScope* temp_scope_; |
| 95 Mode mode_; | 136 Mode mode_; |
| 96 List<Node*>* target_stack_; // for break, continue statements | 137 |
| 138 Target* target_stack_; // for break, continue statements | |
| 97 bool allow_natives_syntax_; | 139 bool allow_natives_syntax_; |
| 98 v8::Extension* extension_; | 140 v8::Extension* extension_; |
| 99 ParserFactory* factory_; | 141 ParserFactory* factory_; |
| 100 ParserLog* log_; | 142 ParserLog* log_; |
| 101 bool is_pre_parsing_; | 143 bool is_pre_parsing_; |
| 102 ScriptDataImpl* pre_data_; | 144 ScriptDataImpl* pre_data_; |
| 103 | 145 |
| 104 bool inside_with() const { return with_nesting_level_ > 0; } | 146 bool inside_with() const { return with_nesting_level_ > 0; } |
| 105 ParserFactory* factory() const { return factory_; } | 147 ParserFactory* factory() const { return factory_; } |
| 106 ParserLog* log() const { return log_; } | 148 ParserLog* log() const { return log_; } |
| (...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 143 | 185 |
| 144 Expression* ParseExpression(bool accept_IN, bool* ok); | 186 Expression* ParseExpression(bool accept_IN, bool* ok); |
| 145 Expression* ParseAssignmentExpression(bool accept_IN, bool* ok); | 187 Expression* ParseAssignmentExpression(bool accept_IN, bool* ok); |
| 146 Expression* ParseConditionalExpression(bool accept_IN, bool* ok); | 188 Expression* ParseConditionalExpression(bool accept_IN, bool* ok); |
| 147 Expression* ParseBinaryExpression(int prec, bool accept_IN, bool* ok); | 189 Expression* ParseBinaryExpression(int prec, bool accept_IN, bool* ok); |
| 148 Expression* ParseUnaryExpression(bool* ok); | 190 Expression* ParseUnaryExpression(bool* ok); |
| 149 Expression* ParsePostfixExpression(bool* ok); | 191 Expression* ParsePostfixExpression(bool* ok); |
| 150 Expression* ParseLeftHandSideExpression(bool* ok); | 192 Expression* ParseLeftHandSideExpression(bool* ok); |
| 151 Expression* ParseNewExpression(bool* ok); | 193 Expression* ParseNewExpression(bool* ok); |
| 152 Expression* ParseMemberExpression(bool* ok); | 194 Expression* ParseMemberExpression(bool* ok); |
| 153 Expression* ParseMemberWithNewPrefixesExpression(List<int>* new_prefixes, | 195 Expression* ParseNewPrefix(PositionStack* stack, bool* ok); |
| 196 Expression* ParseMemberWithNewPrefixesExpression(PositionStack* stack, | |
| 154 bool* ok); | 197 bool* ok); |
| 155 Expression* ParsePrimaryExpression(bool* ok); | 198 Expression* ParsePrimaryExpression(bool* ok); |
| 156 Expression* ParseArrayLiteral(bool* ok); | 199 Expression* ParseArrayLiteral(bool* ok); |
| 157 Expression* ParseObjectLiteral(bool* ok); | 200 Expression* ParseObjectLiteral(bool* ok); |
| 158 Expression* ParseRegExpLiteral(bool seen_equal, bool* ok); | 201 Expression* ParseRegExpLiteral(bool seen_equal, bool* ok); |
| 159 | 202 |
| 160 // Decide if a property should be the object boilerplate. | 203 // Decide if a property should be the object boilerplate. |
| 161 bool IsBoilerplateProperty(ObjectLiteral::Property* property); | 204 bool IsBoilerplateProperty(ObjectLiteral::Property* property); |
| 162 // If the expression is a literal, return the literal value; | 205 // If the expression is a literal, return the literal value; |
| 163 // if the expression is a materialized literal and is simple return a | 206 // if the expression is a materialized literal and is simple return a |
| (...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 201 // Parser support | 244 // Parser support |
| 202 virtual VariableProxy* Declare(Handle<String> name, Variable::Mode mode, | 245 virtual VariableProxy* Declare(Handle<String> name, Variable::Mode mode, |
| 203 FunctionLiteral* fun, | 246 FunctionLiteral* fun, |
| 204 bool resolve, | 247 bool resolve, |
| 205 bool* ok) = 0; | 248 bool* ok) = 0; |
| 206 | 249 |
| 207 bool TargetStackContainsLabel(Handle<String> label); | 250 bool TargetStackContainsLabel(Handle<String> label); |
| 208 BreakableStatement* LookupBreakTarget(Handle<String> label, bool* ok); | 251 BreakableStatement* LookupBreakTarget(Handle<String> label, bool* ok); |
| 209 IterationStatement* LookupContinueTarget(Handle<String> label, bool* ok); | 252 IterationStatement* LookupContinueTarget(Handle<String> label, bool* ok); |
| 210 | 253 |
| 211 void RegisterTargetUse(BreakTarget* target, int index); | 254 void RegisterTargetUse(BreakTarget* target, Target* stop); |
| 212 | 255 |
| 213 // Create a number literal. | 256 // Create a number literal. |
| 214 Literal* NewNumberLiteral(double value); | 257 Literal* NewNumberLiteral(double value); |
| 215 | 258 |
| 216 // Generate AST node that throw a ReferenceError with the given type. | 259 // Generate AST node that throw a ReferenceError with the given type. |
| 217 Expression* NewThrowReferenceError(Handle<String> type); | 260 Expression* NewThrowReferenceError(Handle<String> type); |
| 218 | 261 |
| 219 // Generate AST node that throw a SyntaxError with the given | 262 // Generate AST node that throw a SyntaxError with the given |
| 220 // type. The first argument may be null (in the handle sense) in | 263 // type. The first argument may be null (in the handle sense) in |
| 221 // which case no arguments are passed to the constructor. | 264 // which case no arguments are passed to the constructor. |
| (...skipping 742 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 964 | 1007 |
| 965 | 1008 |
| 966 // ---------------------------------------------------------------------------- | 1009 // ---------------------------------------------------------------------------- |
| 967 // Target is a support class to facilitate manipulation of the | 1010 // Target is a support class to facilitate manipulation of the |
| 968 // Parser's target_stack_ (the stack of potential 'break' and | 1011 // Parser's target_stack_ (the stack of potential 'break' and |
| 969 // 'continue' statement targets). Upon construction, a new target is | 1012 // 'continue' statement targets). Upon construction, a new target is |
| 970 // added; it is removed upon destruction. | 1013 // added; it is removed upon destruction. |
| 971 | 1014 |
| 972 class Target BASE_EMBEDDED { | 1015 class Target BASE_EMBEDDED { |
| 973 public: | 1016 public: |
| 974 Target(Parser* parser, Node* node) : parser_(parser) { | 1017 Target(Parser* parser, Node* node) |
| 975 parser_->target_stack_->Add(node); | 1018 : parser_(parser), node_(node), previous_(parser_->target_stack_) { |
| 1019 parser_->target_stack_ = this; | |
| 976 } | 1020 } |
| 977 | 1021 |
| 978 ~Target() { | 1022 ~Target() { |
| 979 parser_->target_stack_->RemoveLast(); | 1023 parser_->target_stack_ = previous_; |
| 980 } | 1024 } |
| 981 | 1025 |
| 1026 Target* previous() { return previous_; } | |
| 1027 Node* node() { return node_; } | |
| 1028 | |
| 982 private: | 1029 private: |
| 983 Parser* parser_; | 1030 Parser* parser_; |
| 1031 Node* node_; | |
| 1032 Target* previous_; | |
| 984 }; | 1033 }; |
| 985 | 1034 |
| 986 | 1035 |
| 987 class TargetScope BASE_EMBEDDED { | 1036 class TargetScope BASE_EMBEDDED { |
| 988 public: | 1037 public: |
| 989 explicit TargetScope(Parser* parser) | 1038 explicit TargetScope(Parser* parser) |
| 990 : parser_(parser), previous_(parser->target_stack_), stack_(0) { | 1039 : parser_(parser), previous_(parser->target_stack_) { |
| 991 parser_->target_stack_ = &stack_; | 1040 parser->target_stack_ = NULL; |
| 992 } | 1041 } |
| 993 | 1042 |
| 994 ~TargetScope() { | 1043 ~TargetScope() { |
| 995 ASSERT(stack_.is_empty()); | |
| 996 parser_->target_stack_ = previous_; | 1044 parser_->target_stack_ = previous_; |
| 997 } | 1045 } |
| 998 | 1046 |
| 999 private: | 1047 private: |
| 1000 Parser* parser_; | 1048 Parser* parser_; |
| 1001 List<Node*>* previous_; | 1049 Target* previous_; |
| 1002 List<Node*> stack_; | |
| 1003 }; | 1050 }; |
| 1004 | 1051 |
| 1005 | 1052 |
| 1006 // ---------------------------------------------------------------------------- | 1053 // ---------------------------------------------------------------------------- |
| 1007 // LexicalScope is a support class to facilitate manipulation of the | 1054 // LexicalScope is a support class to facilitate manipulation of the |
| 1008 // Parser's scope stack. The constructor sets the parser's top scope | 1055 // Parser's scope stack. The constructor sets the parser's top scope |
| 1009 // to the incoming scope, and the destructor resets it. | 1056 // to the incoming scope, and the destructor resets it. |
| 1010 | 1057 |
| 1011 class LexicalScope BASE_EMBEDDED { | 1058 class LexicalScope BASE_EMBEDDED { |
| 1012 public: | 1059 public: |
| (...skipping 1772 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 2785 break; | 2832 break; |
| 2786 } | 2833 } |
| 2787 | 2834 |
| 2788 default: | 2835 default: |
| 2789 return result; | 2836 return result; |
| 2790 } | 2837 } |
| 2791 } | 2838 } |
| 2792 } | 2839 } |
| 2793 | 2840 |
| 2794 | 2841 |
| 2795 Expression* Parser::ParseNewExpression(bool* ok) { | 2842 |
| 2843 Expression* Parser::ParseNewPrefix(PositionStack* stack, bool* ok) { | |
| 2796 // NewExpression :: | 2844 // NewExpression :: |
| 2797 // ('new')+ MemberExpression | 2845 // ('new')+ MemberExpression |
| 2798 | 2846 |
| 2799 // The grammar for new expressions is pretty warped. The keyword | 2847 // The grammar for new expressions is pretty warped. The keyword |
| 2800 // 'new' can either be a part of the new expression (where it isn't | 2848 // 'new' can either be a part of the new expression (where it isn't |
| 2801 // followed by an argument list) or a part of the member expression, | 2849 // followed by an argument list) or a part of the member expression, |
| 2802 // where it must be followed by an argument list. To accommodate | 2850 // where it must be followed by an argument list. To accommodate |
| 2803 // this, we parse the 'new' keywords greedily and keep track of how | 2851 // this, we parse the 'new' keywords greedily and keep track of how |
| 2804 // many we have parsed. This information is then passed on to the | 2852 // many we have parsed. This information is then passed on to the |
| 2805 // member expression parser, which is only allowed to match argument | 2853 // member expression parser, which is only allowed to match argument |
| 2806 // lists as long as it has 'new' prefixes left | 2854 // lists as long as it has 'new' prefixes left |
| 2807 List<int> new_positions(4); | 2855 Expect(Token::NEW, CHECK_OK); |
| 2808 while (peek() == Token::NEW) { | 2856 PositionStack::Element pos(stack, scanner().location().beg_pos); |
| 2809 Consume(Token::NEW); | 2857 |
| 2810 new_positions.Add(scanner().location().beg_pos); | 2858 Expression* result; |
| 2859 if (peek() == Token::NEW) { | |
| 2860 result = ParseNewPrefix(stack, CHECK_OK); | |
| 2861 } else { | |
| 2862 result = ParseMemberWithNewPrefixesExpression(stack, CHECK_OK); | |
| 2811 } | 2863 } |
| 2812 ASSERT(new_positions.length() > 0); | |
| 2813 | 2864 |
| 2814 Expression* result = | 2865 if (!stack->is_empty()) { |
| 2815 ParseMemberWithNewPrefixesExpression(&new_positions, CHECK_OK); | 2866 result = NEW(CallNew(result, new ZoneList<Expression*>(0), stack->pop())); |
| 2816 while (!new_positions.is_empty()) { | |
| 2817 int last = new_positions.RemoveLast(); | |
| 2818 result = NEW(CallNew(result, new ZoneList<Expression*>(0), last)); | |
| 2819 } | 2867 } |
| 2820 return result; | 2868 return result; |
| 2821 } | 2869 } |
| 2822 | 2870 |
| 2823 | 2871 |
| 2824 Expression* Parser::ParseMemberExpression(bool* ok) { | 2872 Expression* Parser::ParseNewExpression(bool* ok) { |
| 2825 static List<int> new_positions(0); | 2873 PositionStack stack; |
| 2826 return ParseMemberWithNewPrefixesExpression(&new_positions, ok); | 2874 return ParseNewPrefix(&stack, ok); |
| 2827 } | 2875 } |
| 2828 | 2876 |
| 2829 | 2877 |
| 2830 Expression* Parser::ParseMemberWithNewPrefixesExpression( | 2878 Expression* Parser::ParseMemberExpression(bool* ok) { |
| 2831 List<int>* new_positions, | 2879 return ParseMemberWithNewPrefixesExpression(NULL, ok); |
| 2832 bool* ok) { | 2880 } |
| 2881 | |
| 2882 | |
| 2883 Expression* Parser::ParseMemberWithNewPrefixesExpression(PositionStack* stack, | |
| 2884 bool* ok) { | |
| 2833 // MemberExpression :: | 2885 // MemberExpression :: |
| 2834 // (PrimaryExpression | FunctionLiteral) | 2886 // (PrimaryExpression | FunctionLiteral) |
| 2835 // ('[' Expression ']' | '.' Identifier | Arguments)* | 2887 // ('[' Expression ']' | '.' Identifier | Arguments)* |
| 2836 | 2888 |
| 2837 // Parse the initial primary or function expression. | 2889 // Parse the initial primary or function expression. |
| 2838 Expression* result = NULL; | 2890 Expression* result = NULL; |
| 2839 if (peek() == Token::FUNCTION) { | 2891 if (peek() == Token::FUNCTION) { |
| 2840 Expect(Token::FUNCTION, CHECK_OK); | 2892 Expect(Token::FUNCTION, CHECK_OK); |
| 2841 int function_token_position = scanner().location().beg_pos; | 2893 int function_token_position = scanner().location().beg_pos; |
| 2842 Handle<String> name; | 2894 Handle<String> name; |
| (...skipping 15 matching lines...) Expand all Loading... | |
| 2858 break; | 2910 break; |
| 2859 } | 2911 } |
| 2860 case Token::PERIOD: { | 2912 case Token::PERIOD: { |
| 2861 Consume(Token::PERIOD); | 2913 Consume(Token::PERIOD); |
| 2862 int pos = scanner().location().beg_pos; | 2914 int pos = scanner().location().beg_pos; |
| 2863 Handle<String> name = ParseIdentifier(CHECK_OK); | 2915 Handle<String> name = ParseIdentifier(CHECK_OK); |
| 2864 result = factory()->NewProperty(result, NEW(Literal(name)), pos); | 2916 result = factory()->NewProperty(result, NEW(Literal(name)), pos); |
| 2865 break; | 2917 break; |
| 2866 } | 2918 } |
| 2867 case Token::LPAREN: { | 2919 case Token::LPAREN: { |
| 2868 if (new_positions->is_empty()) return result; | 2920 if ((stack == NULL) || stack->is_empty()) return result; |
| 2869 // Consume one of the new prefixes (already parsed). | 2921 // Consume one of the new prefixes (already parsed). |
| 2870 ZoneList<Expression*>* args = ParseArguments(CHECK_OK); | 2922 ZoneList<Expression*>* args = ParseArguments(CHECK_OK); |
| 2871 int last = new_positions->RemoveLast(); | 2923 result = NEW(CallNew(result, args, stack->pop())); |
| 2872 result = NEW(CallNew(result, args, last)); | |
| 2873 break; | 2924 break; |
| 2874 } | 2925 } |
| 2875 default: | 2926 default: |
| 2876 return result; | 2927 return result; |
| 2877 } | 2928 } |
| 2878 } | 2929 } |
| 2879 } | 2930 } |
| 2880 | 2931 |
| 2881 | 2932 |
| 2882 DebuggerStatement* Parser::ParseDebuggerStatement(bool* ok) { | 2933 DebuggerStatement* Parser::ParseDebuggerStatement(bool* ok) { |
| (...skipping 658 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 3541 return factory()->LookupSymbol(scanner_.literal_string(), | 3592 return factory()->LookupSymbol(scanner_.literal_string(), |
| 3542 scanner_.literal_length()); | 3593 scanner_.literal_length()); |
| 3543 } | 3594 } |
| 3544 | 3595 |
| 3545 | 3596 |
| 3546 // ---------------------------------------------------------------------------- | 3597 // ---------------------------------------------------------------------------- |
| 3547 // Parser support | 3598 // Parser support |
| 3548 | 3599 |
| 3549 | 3600 |
| 3550 bool Parser::TargetStackContainsLabel(Handle<String> label) { | 3601 bool Parser::TargetStackContainsLabel(Handle<String> label) { |
| 3551 for (int i = target_stack_->length(); i-- > 0;) { | 3602 for (Target* t = target_stack_; t != NULL; t = t->previous()) { |
| 3552 BreakableStatement* stat = target_stack_->at(i)->AsBreakableStatement(); | 3603 BreakableStatement* stat = t->node()->AsBreakableStatement(); |
| 3553 if (stat != NULL && ContainsLabel(stat->labels(), label)) | 3604 if (stat != NULL && ContainsLabel(stat->labels(), label)) |
| 3554 return true; | 3605 return true; |
| 3555 } | 3606 } |
| 3556 return false; | 3607 return false; |
| 3557 } | 3608 } |
| 3558 | 3609 |
| 3559 | 3610 |
| 3560 BreakableStatement* Parser::LookupBreakTarget(Handle<String> label, bool* ok) { | 3611 BreakableStatement* Parser::LookupBreakTarget(Handle<String> label, bool* ok) { |
| 3561 bool anonymous = label.is_null(); | 3612 bool anonymous = label.is_null(); |
| 3562 for (int i = target_stack_->length(); i-- > 0;) { | 3613 for (Target* t = target_stack_; t != NULL; t = t->previous()) { |
| 3563 BreakableStatement* stat = target_stack_->at(i)->AsBreakableStatement(); | 3614 BreakableStatement* stat = t->node()->AsBreakableStatement(); |
| 3564 if (stat == NULL) continue; | 3615 if (stat == NULL) continue; |
| 3565 | |
| 3566 if ((anonymous && stat->is_target_for_anonymous()) || | 3616 if ((anonymous && stat->is_target_for_anonymous()) || |
| 3567 (!anonymous && ContainsLabel(stat->labels(), label))) { | 3617 (!anonymous && ContainsLabel(stat->labels(), label))) { |
| 3568 RegisterTargetUse(stat->break_target(), i); | 3618 RegisterTargetUse(stat->break_target(), t->previous()); |
| 3569 return stat; | 3619 return stat; |
| 3570 } | 3620 } |
| 3571 } | 3621 } |
| 3572 return NULL; | 3622 return NULL; |
| 3573 } | 3623 } |
| 3574 | 3624 |
| 3575 | 3625 |
| 3576 IterationStatement* Parser::LookupContinueTarget(Handle<String> label, | 3626 IterationStatement* Parser::LookupContinueTarget(Handle<String> label, |
| 3577 bool* ok) { | 3627 bool* ok) { |
| 3578 bool anonymous = label.is_null(); | 3628 bool anonymous = label.is_null(); |
| 3579 for (int i = target_stack_->length(); i-- > 0;) { | 3629 for (Target* t = target_stack_; t != NULL; t = t->previous()) { |
| 3580 IterationStatement* stat = target_stack_->at(i)->AsIterationStatement(); | 3630 IterationStatement* stat = t->node()->AsIterationStatement(); |
| 3581 if (stat == NULL) continue; | 3631 if (stat == NULL) continue; |
| 3582 | 3632 |
| 3583 ASSERT(stat->is_target_for_anonymous()); | 3633 ASSERT(stat->is_target_for_anonymous()); |
| 3584 if (anonymous || ContainsLabel(stat->labels(), label)) { | 3634 if (anonymous || ContainsLabel(stat->labels(), label)) { |
| 3585 RegisterTargetUse(stat->continue_target(), i); | 3635 RegisterTargetUse(stat->continue_target(), t->previous()); |
| 3586 return stat; | 3636 return stat; |
| 3587 } | 3637 } |
| 3588 } | 3638 } |
| 3589 return NULL; | 3639 return NULL; |
| 3590 } | 3640 } |
| 3591 | 3641 |
| 3592 | 3642 |
| 3593 void Parser::RegisterTargetUse(BreakTarget* target, int index) { | 3643 void Parser::RegisterTargetUse(BreakTarget* target, Target* stop) { |
| 3594 // Register that a break target found at the given index in the | 3644 // Register that a break target found at the given stop in the |
| 3595 // target stack has been used from the top of the target stack. Add | 3645 // target stack has been used from the top of the target stack. Add |
| 3596 // the break target to any TargetCollectors passed on the stack. | 3646 // the break target to any TargetCollectors passed on the stack. |
| 3597 for (int i = target_stack_->length(); i-- > index;) { | 3647 for (Target* t = target_stack_; t != stop; t = t->previous()) { |
| 3598 TargetCollector* collector = target_stack_->at(i)->AsTargetCollector(); | 3648 TargetCollector* collector = t->node()->AsTargetCollector(); |
| 3599 if (collector != NULL) collector->AddTarget(target); | 3649 if (collector != NULL) collector->AddTarget(target); |
| 3600 } | 3650 } |
| 3601 } | 3651 } |
| 3602 | 3652 |
| 3603 | 3653 |
| 3604 Literal* Parser::NewNumberLiteral(double number) { | 3654 Literal* Parser::NewNumberLiteral(double number) { |
| 3605 return NEW(Literal(Factory::NewNumber(number, TENURED))); | 3655 return NEW(Literal(Factory::NewNumber(number, TENURED))); |
| 3606 } | 3656 } |
| 3607 | 3657 |
| 3608 | 3658 |
| (...skipping 962 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 4571 start_position, | 4621 start_position, |
| 4572 is_expression); | 4622 is_expression); |
| 4573 return result; | 4623 return result; |
| 4574 } | 4624 } |
| 4575 | 4625 |
| 4576 | 4626 |
| 4577 #undef NEW | 4627 #undef NEW |
| 4578 | 4628 |
| 4579 | 4629 |
| 4580 } } // namespace v8::internal | 4630 } } // namespace v8::internal |
| OLD | NEW |