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

Side by Side Diff: src/parser.cc

Issue 3141034: Move the function name inferrer code from the AstOptimizer to... (Closed) Base URL: http://v8.googlecode.com/svn/branches/bleeding_edge/
Patch Set: '' Created 10 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « src/func-name-inferrer.cc ('k') | src/rewriter.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2010 the V8 project authors. All rights reserved. 1 // Copyright 2010 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 14 matching lines...) Expand all
25 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 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. 26 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 27
28 #include "v8.h" 28 #include "v8.h"
29 29
30 #include "api.h" 30 #include "api.h"
31 #include "ast.h" 31 #include "ast.h"
32 #include "bootstrapper.h" 32 #include "bootstrapper.h"
33 #include "codegen.h" 33 #include "codegen.h"
34 #include "compiler.h" 34 #include "compiler.h"
35 #include "func-name-inferrer.h"
35 #include "messages.h" 36 #include "messages.h"
36 #include "parser.h" 37 #include "parser.h"
37 #include "platform.h" 38 #include "platform.h"
38 #include "runtime.h" 39 #include "runtime.h"
39 #include "scopeinfo.h" 40 #include "scopeinfo.h"
40 #include "scopes.h" 41 #include "scopes.h"
41 #include "string-stream.h" 42 #include "string-stream.h"
42 43
43 #include "ast-inl.h" 44 #include "ast-inl.h"
44 #include "jump-target-inl.h" 45 #include "jump-target-inl.h"
(...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after
147 Mode mode_; 148 Mode mode_;
148 149
149 Target* target_stack_; // for break, continue statements 150 Target* target_stack_; // for break, continue statements
150 bool allow_natives_syntax_; 151 bool allow_natives_syntax_;
151 v8::Extension* extension_; 152 v8::Extension* extension_;
152 ParserFactory* factory_; 153 ParserFactory* factory_;
153 ParserLog* log_; 154 ParserLog* log_;
154 bool is_pre_parsing_; 155 bool is_pre_parsing_;
155 ScriptDataImpl* pre_data_; 156 ScriptDataImpl* pre_data_;
156 bool seen_loop_stmt_; // Used for inner loop detection. 157 bool seen_loop_stmt_; // Used for inner loop detection.
158 FuncNameInferrer* fni_;
157 159
158 bool inside_with() const { return with_nesting_level_ > 0; } 160 bool inside_with() const { return with_nesting_level_ > 0; }
159 ParserFactory* factory() const { return factory_; } 161 ParserFactory* factory() const { return factory_; }
160 ParserLog* log() const { return log_; } 162 ParserLog* log() const { return log_; }
161 Scanner& scanner() { return scanner_; } 163 Scanner& scanner() { return scanner_; }
162 Mode mode() const { return mode_; } 164 Mode mode() const { return mode_; }
163 ScriptDataImpl* pre_data() const { return pre_data_; } 165 ScriptDataImpl* pre_data() const { return pre_data_; }
164 166
165 // All ParseXXX functions take as the last argument an *ok parameter 167 // All ParseXXX functions take as the last argument an *ok parameter
166 // which is set to false if parsing failed; it is unchanged otherwise. 168 // which is set to false if parsing failed; it is unchanged otherwise.
(...skipping 1040 matching lines...) Expand 10 before | Expand all | Expand 10 after
1207 top_scope_(NULL), 1209 top_scope_(NULL),
1208 with_nesting_level_(0), 1210 with_nesting_level_(0),
1209 temp_scope_(NULL), 1211 temp_scope_(NULL),
1210 target_stack_(NULL), 1212 target_stack_(NULL),
1211 allow_natives_syntax_(allow_natives_syntax), 1213 allow_natives_syntax_(allow_natives_syntax),
1212 extension_(extension), 1214 extension_(extension),
1213 factory_(factory), 1215 factory_(factory),
1214 log_(log), 1216 log_(log),
1215 is_pre_parsing_(is_pre_parsing == PREPARSE), 1217 is_pre_parsing_(is_pre_parsing == PREPARSE),
1216 pre_data_(pre_data), 1218 pre_data_(pre_data),
1217 seen_loop_stmt_(false) { 1219 seen_loop_stmt_(false),
1220 fni_(NULL) {
1218 } 1221 }
1219 1222
1220 1223
1221 bool Parser::PreParseProgram(Handle<String> source, 1224 bool Parser::PreParseProgram(Handle<String> source,
1222 unibrow::CharacterStream* stream) { 1225 unibrow::CharacterStream* stream) {
1223 HistogramTimerScope timer(&Counters::pre_parse); 1226 HistogramTimerScope timer(&Counters::pre_parse);
1224 AssertNoZoneAllocation assert_no_zone_allocation; 1227 AssertNoZoneAllocation assert_no_zone_allocation;
1225 AssertNoAllocation assert_no_allocation; 1228 AssertNoAllocation assert_no_allocation;
1226 NoHandleAllocation no_handle_allocation; 1229 NoHandleAllocation no_handle_allocation;
1227 scanner_.Initialize(source, stream, JAVASCRIPT); 1230 scanner_.Initialize(source, stream, JAVASCRIPT);
1228 ASSERT(target_stack_ == NULL); 1231 ASSERT(target_stack_ == NULL);
1229 mode_ = PARSE_EAGERLY; 1232 mode_ = PARSE_EAGERLY;
1230 DummyScope top_scope; 1233 DummyScope top_scope;
1231 LexicalScope scope(this, &top_scope); 1234 LexicalScope scope(this, &top_scope);
1232 TemporaryScope temp_scope(this); 1235 TemporaryScope temp_scope(this);
1233 ZoneListWrapper<Statement> processor; 1236 ZoneListWrapper<Statement> processor;
1234 bool ok = true; 1237 bool ok = true;
1235 ParseSourceElements(&processor, Token::EOS, &ok); 1238 ParseSourceElements(&processor, Token::EOS, &ok);
1236 return !scanner().stack_overflow(); 1239 return !scanner().stack_overflow();
1237 } 1240 }
1238 1241
1239 1242
1240 FunctionLiteral* Parser::ParseProgram(Handle<String> source, 1243 FunctionLiteral* Parser::ParseProgram(Handle<String> source,
1241 bool in_global_context) { 1244 bool in_global_context) {
1242 CompilationZoneScope zone_scope(DONT_DELETE_ON_EXIT); 1245 CompilationZoneScope zone_scope(DONT_DELETE_ON_EXIT);
1243 1246
1244 HistogramTimerScope timer(&Counters::parse); 1247 HistogramTimerScope timer(&Counters::parse);
1245 Counters::total_parse_size.Increment(source->length()); 1248 Counters::total_parse_size.Increment(source->length());
1249 fni_ = new FuncNameInferrer();
1246 1250
1247 // Initialize parser state. 1251 // Initialize parser state.
1248 source->TryFlatten(); 1252 source->TryFlatten();
1249 scanner_.Initialize(source, JAVASCRIPT); 1253 scanner_.Initialize(source, JAVASCRIPT);
1250 ASSERT(target_stack_ == NULL); 1254 ASSERT(target_stack_ == NULL);
1251 1255
1252 // Compute the parsing mode. 1256 // Compute the parsing mode.
1253 mode_ = FLAG_lazy ? PARSE_LAZILY : PARSE_EAGERLY; 1257 mode_ = FLAG_lazy ? PARSE_LAZILY : PARSE_EAGERLY;
1254 if (allow_natives_syntax_ || extension_ != NULL) mode_ = PARSE_EAGERLY; 1258 if (allow_natives_syntax_ || extension_ != NULL) mode_ = PARSE_EAGERLY;
1255 1259
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after
1296 1300
1297 FunctionLiteral* Parser::ParseLazy(Handle<String> source, 1301 FunctionLiteral* Parser::ParseLazy(Handle<String> source,
1298 Handle<String> name, 1302 Handle<String> name,
1299 int start_position, 1303 int start_position,
1300 int end_position, 1304 int end_position,
1301 bool is_expression) { 1305 bool is_expression) {
1302 CompilationZoneScope zone_scope(DONT_DELETE_ON_EXIT); 1306 CompilationZoneScope zone_scope(DONT_DELETE_ON_EXIT);
1303 HistogramTimerScope timer(&Counters::parse_lazy); 1307 HistogramTimerScope timer(&Counters::parse_lazy);
1304 Counters::total_parse_size.Increment(source->length()); 1308 Counters::total_parse_size.Increment(source->length());
1305 1309
1310 fni_ = new FuncNameInferrer();
1311 fni_->PushEnclosingName(name);
1312
1306 // Initialize parser state. 1313 // Initialize parser state.
1307 source->TryFlatten(); 1314 source->TryFlatten();
1308 scanner_.Initialize(source, start_position, end_position, JAVASCRIPT); 1315 scanner_.Initialize(source, start_position, end_position, JAVASCRIPT);
1309 ASSERT(target_stack_ == NULL); 1316 ASSERT(target_stack_ == NULL);
1310 mode_ = PARSE_EAGERLY; 1317 mode_ = PARSE_EAGERLY;
1311 1318
1312 // Place holder for the result. 1319 // Place holder for the result.
1313 FunctionLiteral* result = NULL; 1320 FunctionLiteral* result = NULL;
1314 1321
1315 { 1322 {
(...skipping 757 matching lines...) Expand 10 before | Expand all | Expand 10 after
2073 // rewriter to add a '.result' assignment to such a block (to get compliant 2080 // rewriter to add a '.result' assignment to such a block (to get compliant
2074 // behavior for code such as print(eval('var x = 7')), and for cosmetic 2081 // behavior for code such as print(eval('var x = 7')), and for cosmetic
2075 // reasons when pretty-printing. Also, unless an assignment (initialization) 2082 // reasons when pretty-printing. Also, unless an assignment (initialization)
2076 // is inside an initializer block, it is ignored. 2083 // is inside an initializer block, it is ignored.
2077 // 2084 //
2078 // Create new block with one expected declaration. 2085 // Create new block with one expected declaration.
2079 Block* block = NEW(Block(NULL, 1, true)); 2086 Block* block = NEW(Block(NULL, 1, true));
2080 VariableProxy* last_var = NULL; // the last variable declared 2087 VariableProxy* last_var = NULL; // the last variable declared
2081 int nvars = 0; // the number of variables declared 2088 int nvars = 0; // the number of variables declared
2082 do { 2089 do {
2090 if (fni_ != NULL) fni_->Enter();
2091
2083 // Parse variable name. 2092 // Parse variable name.
2084 if (nvars > 0) Consume(Token::COMMA); 2093 if (nvars > 0) Consume(Token::COMMA);
2085 Handle<String> name = ParseIdentifier(CHECK_OK); 2094 Handle<String> name = ParseIdentifier(CHECK_OK);
2095 if (fni_ != NULL) fni_->PushVariableName(name);
2086 2096
2087 // Declare variable. 2097 // Declare variable.
2088 // Note that we *always* must treat the initial value via a separate init 2098 // Note that we *always* must treat the initial value via a separate init
2089 // assignment for variables and constants because the value must be assigned 2099 // assignment for variables and constants because the value must be assigned
2090 // when the variable is encountered in the source. But the variable/constant 2100 // when the variable is encountered in the source. But the variable/constant
2091 // is declared (and set to 'undefined') upon entering the function within 2101 // is declared (and set to 'undefined') upon entering the function within
2092 // which the variable or constant is declared. Only function variables have 2102 // which the variable or constant is declared. Only function variables have
2093 // an initial value in the declaration (because they are initialized upon 2103 // an initial value in the declaration (because they are initialized upon
2094 // entering the function). 2104 // entering the function).
2095 // 2105 //
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after
2127 // The "variable" c initialized to x is the same as the declared 2137 // The "variable" c initialized to x is the same as the declared
2128 // one - there is no re-lookup (see the last parameter of the 2138 // one - there is no re-lookup (see the last parameter of the
2129 // Declare() call above). 2139 // Declare() call above).
2130 2140
2131 Expression* value = NULL; 2141 Expression* value = NULL;
2132 int position = -1; 2142 int position = -1;
2133 if (peek() == Token::ASSIGN) { 2143 if (peek() == Token::ASSIGN) {
2134 Expect(Token::ASSIGN, CHECK_OK); 2144 Expect(Token::ASSIGN, CHECK_OK);
2135 position = scanner().location().beg_pos; 2145 position = scanner().location().beg_pos;
2136 value = ParseAssignmentExpression(accept_IN, CHECK_OK); 2146 value = ParseAssignmentExpression(accept_IN, CHECK_OK);
2147 // Don't infer if it is "a = function(){...}();"-like expression.
2148 if (fni_ != NULL && value->AsCall() == NULL) fni_->Infer();
2137 } 2149 }
2138 2150
2139 // Make sure that 'const c' actually initializes 'c' to undefined 2151 // Make sure that 'const c' actually initializes 'c' to undefined
2140 // even though it seems like a stupid thing to do. 2152 // even though it seems like a stupid thing to do.
2141 if (value == NULL && is_const) { 2153 if (value == NULL && is_const) {
2142 value = GetLiteralUndefined(); 2154 value = GetLiteralUndefined();
2143 } 2155 }
2144 2156
2145 // Global variable declarations must be compiled in a specific 2157 // Global variable declarations must be compiled in a specific
2146 // way. When the script containing the global variable declaration 2158 // way. When the script containing the global variable declaration
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after
2203 // initializations always assign to the declared constant which is 2215 // initializations always assign to the declared constant which is
2204 // always at the function scope level. This is only relevant for 2216 // always at the function scope level. This is only relevant for
2205 // dynamically looked-up variables and constants (the start context 2217 // dynamically looked-up variables and constants (the start context
2206 // for constant lookups is always the function context, while it is 2218 // for constant lookups is always the function context, while it is
2207 // the top context for variables). Sigh... 2219 // the top context for variables). Sigh...
2208 if (value != NULL) { 2220 if (value != NULL) {
2209 Token::Value op = (is_const ? Token::INIT_CONST : Token::INIT_VAR); 2221 Token::Value op = (is_const ? Token::INIT_CONST : Token::INIT_VAR);
2210 Assignment* assignment = NEW(Assignment(op, last_var, value, position)); 2222 Assignment* assignment = NEW(Assignment(op, last_var, value, position));
2211 if (block) block->AddStatement(NEW(ExpressionStatement(assignment))); 2223 if (block) block->AddStatement(NEW(ExpressionStatement(assignment)));
2212 } 2224 }
2225
2226 if (fni_ != NULL) fni_->Leave();
2213 } while (peek() == Token::COMMA); 2227 } while (peek() == Token::COMMA);
2214 2228
2215 if (!is_const && nvars == 1) { 2229 if (!is_const && nvars == 1) {
2216 // We have a single, non-const variable. 2230 // We have a single, non-const variable.
2217 if (is_pre_parsing_) { 2231 if (is_pre_parsing_) {
2218 // If we're preparsing then we need to set the var to something 2232 // If we're preparsing then we need to set the var to something
2219 // in order for for-in loops to parse correctly. 2233 // in order for for-in loops to parse correctly.
2220 *var = ValidLeftHandSideSentinel::instance(); 2234 *var = ValidLeftHandSideSentinel::instance();
2221 } else { 2235 } else {
2222 ASSERT(last_var != NULL); 2236 ASSERT(last_var != NULL);
(...skipping 592 matching lines...) Expand 10 before | Expand all | Expand 10 after
2815 return result; 2829 return result;
2816 } 2830 }
2817 2831
2818 2832
2819 // Precedence = 2 2833 // Precedence = 2
2820 Expression* Parser::ParseAssignmentExpression(bool accept_IN, bool* ok) { 2834 Expression* Parser::ParseAssignmentExpression(bool accept_IN, bool* ok) {
2821 // AssignmentExpression :: 2835 // AssignmentExpression ::
2822 // ConditionalExpression 2836 // ConditionalExpression
2823 // LeftHandSideExpression AssignmentOperator AssignmentExpression 2837 // LeftHandSideExpression AssignmentOperator AssignmentExpression
2824 2838
2839 if (fni_ != NULL) fni_->Enter();
2825 Expression* expression = ParseConditionalExpression(accept_IN, CHECK_OK); 2840 Expression* expression = ParseConditionalExpression(accept_IN, CHECK_OK);
2826 2841
2827 if (!Token::IsAssignmentOp(peek())) { 2842 if (!Token::IsAssignmentOp(peek())) {
2843 if (fni_ != NULL) fni_->Leave();
2828 // Parsed conditional expression only (no assignment). 2844 // Parsed conditional expression only (no assignment).
2829 return expression; 2845 return expression;
2830 } 2846 }
2831 2847
2832 // Signal a reference error if the expression is an invalid left-hand 2848 // Signal a reference error if the expression is an invalid left-hand
2833 // side expression. We could report this as a syntax error here but 2849 // side expression. We could report this as a syntax error here but
2834 // for compatibility with JSC we choose to report the error at 2850 // for compatibility with JSC we choose to report the error at
2835 // runtime. 2851 // runtime.
2836 if (expression == NULL || !expression->IsValidLeftHandSide()) { 2852 if (expression == NULL || !expression->IsValidLeftHandSide()) {
2837 Handle<String> type = Factory::invalid_lhs_in_assignment_symbol(); 2853 Handle<String> type = Factory::invalid_lhs_in_assignment_symbol();
(...skipping 10 matching lines...) Expand all
2848 // properties if we haven't seen them before. Otherwise we'll 2864 // properties if we haven't seen them before. Otherwise we'll
2849 // probably overestimate the number of properties. 2865 // probably overestimate the number of properties.
2850 Property* property = expression ? expression->AsProperty() : NULL; 2866 Property* property = expression ? expression->AsProperty() : NULL;
2851 if (op == Token::ASSIGN && 2867 if (op == Token::ASSIGN &&
2852 property != NULL && 2868 property != NULL &&
2853 property->obj()->AsVariableProxy() != NULL && 2869 property->obj()->AsVariableProxy() != NULL &&
2854 property->obj()->AsVariableProxy()->is_this()) { 2870 property->obj()->AsVariableProxy()->is_this()) {
2855 temp_scope_->AddProperty(); 2871 temp_scope_->AddProperty();
2856 } 2872 }
2857 2873
2874 if (fni_ != NULL) {
2875 // Check if the right hand side is a call to avoid inferring a
2876 // name if we're dealing with "a = function(){...}();"-like
2877 // expression.
2878 if ((op == Token::INIT_VAR
2879 || op == Token::INIT_CONST
2880 || op == Token::ASSIGN)
2881 && (right->AsCall() == NULL)) {
2882 fni_->Infer();
2883 }
2884 fni_->Leave();
2885 }
2886
2858 return NEW(Assignment(op, expression, right, pos)); 2887 return NEW(Assignment(op, expression, right, pos));
2859 } 2888 }
2860 2889
2861 2890
2862 // Precedence = 3 2891 // Precedence = 3
2863 Expression* Parser::ParseConditionalExpression(bool accept_IN, bool* ok) { 2892 Expression* Parser::ParseConditionalExpression(bool accept_IN, bool* ok) {
2864 // ConditionalExpression :: 2893 // ConditionalExpression ::
2865 // LogicalOrExpression 2894 // LogicalOrExpression
2866 // LogicalOrExpression '?' AssignmentExpression ':' AssignmentExpression 2895 // LogicalOrExpression '?' AssignmentExpression ':' AssignmentExpression
2867 2896
(...skipping 250 matching lines...) Expand 10 before | Expand all | Expand 10 after
3118 } 3147 }
3119 result = factory()->NewCall(result, args, pos); 3148 result = factory()->NewCall(result, args, pos);
3120 break; 3149 break;
3121 } 3150 }
3122 3151
3123 case Token::PERIOD: { 3152 case Token::PERIOD: {
3124 Consume(Token::PERIOD); 3153 Consume(Token::PERIOD);
3125 int pos = scanner().location().beg_pos; 3154 int pos = scanner().location().beg_pos;
3126 Handle<String> name = ParseIdentifierName(CHECK_OK); 3155 Handle<String> name = ParseIdentifierName(CHECK_OK);
3127 result = factory()->NewProperty(result, NEW(Literal(name)), pos); 3156 result = factory()->NewProperty(result, NEW(Literal(name)), pos);
3157 if (fni_ != NULL) fni_->PushLiteralName(name);
3128 break; 3158 break;
3129 } 3159 }
3130 3160
3131 default: 3161 default:
3132 return result; 3162 return result;
3133 } 3163 }
3134 } 3164 }
3135 } 3165 }
3136 3166
3137 3167
(...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after
3204 Expression* index = ParseExpression(true, CHECK_OK); 3234 Expression* index = ParseExpression(true, CHECK_OK);
3205 result = factory()->NewProperty(result, index, pos); 3235 result = factory()->NewProperty(result, index, pos);
3206 Expect(Token::RBRACK, CHECK_OK); 3236 Expect(Token::RBRACK, CHECK_OK);
3207 break; 3237 break;
3208 } 3238 }
3209 case Token::PERIOD: { 3239 case Token::PERIOD: {
3210 Consume(Token::PERIOD); 3240 Consume(Token::PERIOD);
3211 int pos = scanner().location().beg_pos; 3241 int pos = scanner().location().beg_pos;
3212 Handle<String> name = ParseIdentifierName(CHECK_OK); 3242 Handle<String> name = ParseIdentifierName(CHECK_OK);
3213 result = factory()->NewProperty(result, NEW(Literal(name)), pos); 3243 result = factory()->NewProperty(result, NEW(Literal(name)), pos);
3244 if (fni_ != NULL) fni_->PushLiteralName(name);
3214 break; 3245 break;
3215 } 3246 }
3216 case Token::LPAREN: { 3247 case Token::LPAREN: {
3217 if ((stack == NULL) || stack->is_empty()) return result; 3248 if ((stack == NULL) || stack->is_empty()) return result;
3218 // Consume one of the new prefixes (already parsed). 3249 // Consume one of the new prefixes (already parsed).
3219 ZoneList<Expression*>* args = ParseArguments(CHECK_OK); 3250 ZoneList<Expression*>* args = ParseArguments(CHECK_OK);
3220 int last = stack->pop(); 3251 int last = stack->pop();
3221 result = NEW(CallNew(result, args, last)); 3252 result = NEW(CallNew(result, args, last));
3222 break; 3253 break;
3223 } 3254 }
(...skipping 90 matching lines...) Expand 10 before | Expand all | Expand 10 after
3314 result = NEW(Literal(Factory::true_value())); 3345 result = NEW(Literal(Factory::true_value()));
3315 break; 3346 break;
3316 3347
3317 case Token::FALSE_LITERAL: 3348 case Token::FALSE_LITERAL:
3318 Consume(Token::FALSE_LITERAL); 3349 Consume(Token::FALSE_LITERAL);
3319 result = NEW(Literal(Factory::false_value())); 3350 result = NEW(Literal(Factory::false_value()));
3320 break; 3351 break;
3321 3352
3322 case Token::IDENTIFIER: { 3353 case Token::IDENTIFIER: {
3323 Handle<String> name = ParseIdentifier(CHECK_OK); 3354 Handle<String> name = ParseIdentifier(CHECK_OK);
3355 if (fni_ != NULL) fni_->PushVariableName(name);
3324 if (is_pre_parsing_) { 3356 if (is_pre_parsing_) {
3325 result = VariableProxySentinel::identifier_proxy(); 3357 result = VariableProxySentinel::identifier_proxy();
3326 } else { 3358 } else {
3327 result = top_scope_->NewUnresolved(name, inside_with()); 3359 result = top_scope_->NewUnresolved(name, inside_with());
3328 } 3360 }
3329 break; 3361 break;
3330 } 3362 }
3331 3363
3332 case Token::NUMBER: { 3364 case Token::NUMBER: {
3333 Consume(Token::NUMBER); 3365 Consume(Token::NUMBER);
3334 double value = 3366 double value =
3335 StringToDouble(scanner_.literal_string(), ALLOW_HEX | ALLOW_OCTALS); 3367 StringToDouble(scanner_.literal_string(), ALLOW_HEX | ALLOW_OCTALS);
3336 result = NewNumberLiteral(value); 3368 result = NewNumberLiteral(value);
3337 break; 3369 break;
3338 } 3370 }
3339 3371
3340 case Token::STRING: { 3372 case Token::STRING: {
3341 Consume(Token::STRING); 3373 Consume(Token::STRING);
3342 Handle<String> symbol = 3374 Handle<String> symbol =
3343 factory()->LookupSymbol(scanner_.literal_string(), 3375 factory()->LookupSymbol(scanner_.literal_string(),
3344 scanner_.literal_length()); 3376 scanner_.literal_length());
3345 result = NEW(Literal(symbol)); 3377 result = NEW(Literal(symbol));
3378 if (fni_ != NULL) fni_->PushLiteralName(symbol);
3346 break; 3379 break;
3347 } 3380 }
3348 3381
3349 case Token::ASSIGN_DIV: 3382 case Token::ASSIGN_DIV:
3350 result = ParseRegExpLiteral(true, CHECK_OK); 3383 result = ParseRegExpLiteral(true, CHECK_OK);
3351 break; 3384 break;
3352 3385
3353 case Token::DIV: 3386 case Token::DIV:
3354 result = ParseRegExpLiteral(false, CHECK_OK); 3387 result = ParseRegExpLiteral(false, CHECK_OK);
3355 break; 3388 break;
(...skipping 277 matching lines...) Expand 10 before | Expand all | Expand 10 after
3633 // ((IdentifierName | String | Number) ':' AssignmentExpression) 3666 // ((IdentifierName | String | Number) ':' AssignmentExpression)
3634 // | (('get' | 'set') (IdentifierName | String | Number) FunctionLiteral) 3667 // | (('get' | 'set') (IdentifierName | String | Number) FunctionLiteral)
3635 // )*[','] '}' 3668 // )*[','] '}'
3636 3669
3637 ZoneListWrapper<ObjectLiteral::Property> properties = 3670 ZoneListWrapper<ObjectLiteral::Property> properties =
3638 factory()->NewList<ObjectLiteral::Property>(4); 3671 factory()->NewList<ObjectLiteral::Property>(4);
3639 int number_of_boilerplate_properties = 0; 3672 int number_of_boilerplate_properties = 0;
3640 3673
3641 Expect(Token::LBRACE, CHECK_OK); 3674 Expect(Token::LBRACE, CHECK_OK);
3642 while (peek() != Token::RBRACE) { 3675 while (peek() != Token::RBRACE) {
3676 if (fni_ != NULL) fni_->Enter();
3677
3643 Literal* key = NULL; 3678 Literal* key = NULL;
3644 Token::Value next = peek(); 3679 Token::Value next = peek();
3645 switch (next) { 3680 switch (next) {
3646 case Token::IDENTIFIER: { 3681 case Token::IDENTIFIER: {
3647 bool is_getter = false; 3682 bool is_getter = false;
3648 bool is_setter = false; 3683 bool is_setter = false;
3649 Handle<String> id = 3684 Handle<String> id =
3650 ParseIdentifierOrGetOrSet(&is_getter, &is_setter, CHECK_OK); 3685 ParseIdentifierOrGetOrSet(&is_getter, &is_setter, CHECK_OK);
3686 if (fni_ != NULL) fni_->PushLiteralName(id);
3687
3651 if ((is_getter || is_setter) && peek() != Token::COLON) { 3688 if ((is_getter || is_setter) && peek() != Token::COLON) {
3652 ObjectLiteral::Property* property = 3689 ObjectLiteral::Property* property =
3653 ParseObjectLiteralGetSet(is_getter, CHECK_OK); 3690 ParseObjectLiteralGetSet(is_getter, CHECK_OK);
3654 if (IsBoilerplateProperty(property)) { 3691 if (IsBoilerplateProperty(property)) {
3655 number_of_boilerplate_properties++; 3692 number_of_boilerplate_properties++;
3656 } 3693 }
3657 properties.Add(property); 3694 properties.Add(property);
3658 if (peek() != Token::RBRACE) Expect(Token::COMMA, CHECK_OK); 3695 if (peek() != Token::RBRACE) Expect(Token::COMMA, CHECK_OK);
3696
3697 if (fni_ != NULL) {
3698 fni_->Infer();
3699 fni_->Leave();
3700 }
3659 continue; // restart the while 3701 continue; // restart the while
3660 } 3702 }
3661 // Failed to parse as get/set property, so it's just a property 3703 // Failed to parse as get/set property, so it's just a property
3662 // called "get" or "set". 3704 // called "get" or "set".
3663 key = NEW(Literal(id)); 3705 key = NEW(Literal(id));
3664 break; 3706 break;
3665 } 3707 }
3666 case Token::STRING: { 3708 case Token::STRING: {
3667 Consume(Token::STRING); 3709 Consume(Token::STRING);
3668 Handle<String> string = 3710 Handle<String> string =
3669 factory()->LookupSymbol(scanner_.literal_string(), 3711 factory()->LookupSymbol(scanner_.literal_string(),
3670 scanner_.literal_length()); 3712 scanner_.literal_length());
3713 if (fni_ != NULL) fni_->PushLiteralName(string);
3671 uint32_t index; 3714 uint32_t index;
3672 if (!string.is_null() && string->AsArrayIndex(&index)) { 3715 if (!string.is_null() && string->AsArrayIndex(&index)) {
3673 key = NewNumberLiteral(index); 3716 key = NewNumberLiteral(index);
3674 break; 3717 break;
3675 } 3718 }
3676 key = NEW(Literal(string)); 3719 key = NEW(Literal(string));
3677 break; 3720 break;
3678 } 3721 }
3679 case Token::NUMBER: { 3722 case Token::NUMBER: {
3680 Consume(Token::NUMBER); 3723 Consume(Token::NUMBER);
(...skipping 23 matching lines...) Expand all
3704 3747
3705 ObjectLiteral::Property* property = 3748 ObjectLiteral::Property* property =
3706 NEW(ObjectLiteral::Property(key, value)); 3749 NEW(ObjectLiteral::Property(key, value));
3707 3750
3708 // Count CONSTANT or COMPUTED properties to maintain the enumeration order. 3751 // Count CONSTANT or COMPUTED properties to maintain the enumeration order.
3709 if (IsBoilerplateProperty(property)) number_of_boilerplate_properties++; 3752 if (IsBoilerplateProperty(property)) number_of_boilerplate_properties++;
3710 properties.Add(property); 3753 properties.Add(property);
3711 3754
3712 // TODO(1240767): Consider allowing trailing comma. 3755 // TODO(1240767): Consider allowing trailing comma.
3713 if (peek() != Token::RBRACE) Expect(Token::COMMA, CHECK_OK); 3756 if (peek() != Token::RBRACE) Expect(Token::COMMA, CHECK_OK);
3757
3758 if (fni_ != NULL) {
3759 fni_->Infer();
3760 fni_->Leave();
3761 }
3714 } 3762 }
3715 Expect(Token::RBRACE, CHECK_OK); 3763 Expect(Token::RBRACE, CHECK_OK);
3716 // Computation of literal_index must happen before pre parse bailout. 3764 // Computation of literal_index must happen before pre parse bailout.
3717 int literal_index = temp_scope_->NextMaterializedLiteralIndex(); 3765 int literal_index = temp_scope_->NextMaterializedLiteralIndex();
3718 if (is_pre_parsing_) return NULL; 3766 if (is_pre_parsing_) return NULL;
3719 3767
3720 Handle<FixedArray> constant_properties = 3768 Handle<FixedArray> constant_properties =
3721 Factory::NewFixedArray(number_of_boilerplate_properties * 2, TENURED); 3769 Factory::NewFixedArray(number_of_boilerplate_properties * 2, TENURED);
3722 3770
3723 bool is_simple = true; 3771 bool is_simple = true;
(...skipping 191 matching lines...) Expand 10 before | Expand all | Expand 10 after
3915 function_name->length() > 0)); 3963 function_name->length() > 0));
3916 if (!is_pre_parsing_) { 3964 if (!is_pre_parsing_) {
3917 function_literal->set_function_token_position(function_token_position); 3965 function_literal->set_function_token_position(function_token_position);
3918 } 3966 }
3919 3967
3920 // Set flag for inner loop detection. We treat loops that contain a function 3968 // Set flag for inner loop detection. We treat loops that contain a function
3921 // literal not as inner loops because we avoid duplicating function literals 3969 // literal not as inner loops because we avoid duplicating function literals
3922 // when peeling or unrolling such a loop. 3970 // when peeling or unrolling such a loop.
3923 seen_loop_stmt_ = true; 3971 seen_loop_stmt_ = true;
3924 3972
3973 if (fni_ != NULL && !is_named) fni_->AddFunction(function_literal);
3925 return function_literal; 3974 return function_literal;
3926 } 3975 }
3927 } 3976 }
3928 3977
3929 3978
3930 Expression* Parser::ParseV8Intrinsic(bool* ok) { 3979 Expression* Parser::ParseV8Intrinsic(bool* ok) {
3931 // CallRuntime :: 3980 // CallRuntime ::
3932 // '%' Identifier Arguments 3981 // '%' Identifier Arguments
3933 3982
3934 Expect(Token::MOD, CHECK_OK); 3983 Expect(Token::MOD, CHECK_OK);
(...skipping 1322 matching lines...) Expand 10 before | Expand all | Expand 10 after
5257 parser.ParseLazy(script_source, name, 5306 parser.ParseLazy(script_source, name,
5258 start_position, end_position, is_expression); 5307 start_position, end_position, is_expression);
5259 return result; 5308 return result;
5260 } 5309 }
5261 5310
5262 5311
5263 #undef NEW 5312 #undef NEW
5264 5313
5265 5314
5266 } } // namespace v8::internal 5315 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « src/func-name-inferrer.cc ('k') | src/rewriter.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698