OLD | NEW |
---|---|
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 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 523 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
534 | 534 |
535 // ---------------------------------------------------------------------------- | 535 // ---------------------------------------------------------------------------- |
536 // Implementation of Parser | 536 // Implementation of Parser |
537 | 537 |
538 Parser::Parser(CompilationInfo* info) | 538 Parser::Parser(CompilationInfo* info) |
539 : isolate_(info->isolate()), | 539 : isolate_(info->isolate()), |
540 symbol_cache_(0, info->zone()), | 540 symbol_cache_(0, info->zone()), |
541 script_(info->script()), | 541 script_(info->script()), |
542 scanner_(isolate_->unicode_cache()), | 542 scanner_(isolate_->unicode_cache()), |
543 reusable_preparser_(NULL), | 543 reusable_preparser_(NULL), |
544 top_scope_(NULL), | 544 top_scope_(NULL), |
Michael Starzinger
2013/08/23 08:56:30
Missing initialization of original_scope_(NULL) he
rossberg
2013/08/23 09:09:21
Done.
| |
545 current_function_state_(NULL), | 545 current_function_state_(NULL), |
546 target_stack_(NULL), | 546 target_stack_(NULL), |
547 extension_(info->extension()), | 547 extension_(info->extension()), |
548 pre_parse_data_(NULL), | 548 pre_parse_data_(NULL), |
549 fni_(NULL), | 549 fni_(NULL), |
550 allow_natives_syntax_(false), | 550 allow_natives_syntax_(false), |
551 allow_lazy_(false), | 551 allow_lazy_(false), |
552 allow_generators_(false), | 552 allow_generators_(false), |
553 allow_for_of_(false), | 553 allow_for_of_(false), |
554 stack_overflow_(false), | 554 stack_overflow_(false), |
(...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
615 if (pre_parse_data_ != NULL) pre_parse_data_->Initialize(); | 615 if (pre_parse_data_ != NULL) pre_parse_data_->Initialize(); |
616 | 616 |
617 Handle<String> no_name = isolate()->factory()->empty_string(); | 617 Handle<String> no_name = isolate()->factory()->empty_string(); |
618 | 618 |
619 FunctionLiteral* result = NULL; | 619 FunctionLiteral* result = NULL; |
620 { Scope* scope = NewScope(top_scope_, GLOBAL_SCOPE); | 620 { Scope* scope = NewScope(top_scope_, GLOBAL_SCOPE); |
621 info->SetGlobalScope(scope); | 621 info->SetGlobalScope(scope); |
622 if (!info->context().is_null()) { | 622 if (!info->context().is_null()) { |
623 scope = Scope::DeserializeScopeChain(*info->context(), scope, zone()); | 623 scope = Scope::DeserializeScopeChain(*info->context(), scope, zone()); |
624 } | 624 } |
625 original_scope_ = scope; | |
625 if (info->is_eval()) { | 626 if (info->is_eval()) { |
626 if (!scope->is_global_scope() || info->language_mode() != CLASSIC_MODE) { | 627 if (!scope->is_global_scope() || info->language_mode() != CLASSIC_MODE) { |
627 scope = NewScope(scope, EVAL_SCOPE); | 628 scope = NewScope(scope, EVAL_SCOPE); |
628 } | 629 } |
629 } else if (info->is_global()) { | 630 } else if (info->is_global()) { |
630 scope = NewScope(scope, GLOBAL_SCOPE); | 631 scope = NewScope(scope, GLOBAL_SCOPE); |
631 } | 632 } |
632 scope->set_start_position(0); | 633 scope->set_start_position(0); |
633 scope->set_end_position(source->length()); | 634 scope->set_end_position(source->length()); |
634 | 635 |
(...skipping 107 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
742 FunctionLiteral* result = NULL; | 743 FunctionLiteral* result = NULL; |
743 | 744 |
744 { | 745 { |
745 // Parse the function literal. | 746 // Parse the function literal. |
746 Scope* scope = NewScope(top_scope_, GLOBAL_SCOPE); | 747 Scope* scope = NewScope(top_scope_, GLOBAL_SCOPE); |
747 info()->SetGlobalScope(scope); | 748 info()->SetGlobalScope(scope); |
748 if (!info()->closure().is_null()) { | 749 if (!info()->closure().is_null()) { |
749 scope = Scope::DeserializeScopeChain(info()->closure()->context(), scope, | 750 scope = Scope::DeserializeScopeChain(info()->closure()->context(), scope, |
750 zone()); | 751 zone()); |
751 } | 752 } |
753 original_scope_ = scope; | |
752 FunctionState function_state(this, scope, isolate()); | 754 FunctionState function_state(this, scope, isolate()); |
753 ASSERT(scope->language_mode() != STRICT_MODE || !info()->is_classic_mode()); | 755 ASSERT(scope->language_mode() != STRICT_MODE || !info()->is_classic_mode()); |
754 ASSERT(scope->language_mode() != EXTENDED_MODE || | 756 ASSERT(scope->language_mode() != EXTENDED_MODE || |
755 info()->is_extended_mode()); | 757 info()->is_extended_mode()); |
756 ASSERT(info()->language_mode() == shared_info->language_mode()); | 758 ASSERT(info()->language_mode() == shared_info->language_mode()); |
757 scope->SetLanguageMode(shared_info->language_mode()); | 759 scope->SetLanguageMode(shared_info->language_mode()); |
758 FunctionLiteral::FunctionType function_type = shared_info->is_expression() | 760 FunctionLiteral::FunctionType function_type = shared_info->is_expression() |
759 ? (shared_info->is_anonymous() | 761 ? (shared_info->is_anonymous() |
760 ? FunctionLiteral::ANONYMOUS_EXPRESSION | 762 ? FunctionLiteral::ANONYMOUS_EXPRESSION |
761 : FunctionLiteral::NAMED_EXPRESSION) | 763 : FunctionLiteral::NAMED_EXPRESSION) |
(...skipping 3510 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
4272 | 4274 |
4273 // We want a non-null handle as the function name. | 4275 // We want a non-null handle as the function name. |
4274 if (should_infer_name) { | 4276 if (should_infer_name) { |
4275 function_name = isolate()->factory()->empty_string(); | 4277 function_name = isolate()->factory()->empty_string(); |
4276 } | 4278 } |
4277 | 4279 |
4278 int num_parameters = 0; | 4280 int num_parameters = 0; |
4279 // Function declarations are function scoped in normal mode, so they are | 4281 // Function declarations are function scoped in normal mode, so they are |
4280 // hoisted. In harmony block scoping mode they are block scoped, so they | 4282 // hoisted. In harmony block scoping mode they are block scoped, so they |
4281 // are not hoisted. | 4283 // are not hoisted. |
4284 // | |
4285 // One tricky case are function declarations in a local sloppy-mode eval: | |
4286 // their declaration is hoisted, but they still see the local scope. E.g., | |
4287 // | |
4288 // function() { | |
4289 // var x=0 | |
4290 // try {throw 1} catch (x) { eval("function g() { return x }") } | |
Michael Starzinger
2013/08/23 08:56:30
nit: A few white spaces missing here and in the li
rossberg
2013/08/23 09:09:21
Done.
| |
4291 // return g() | |
4292 // } | |
4293 // | |
4294 // needs to return 1. To distinguish such cases, we need to detect | |
4295 // (1) whether a function stems from a sloppy eval, and | |
4296 // (2) whether it actually hoists across the eval. | |
4297 // Unfortunately, we do not represent sloppy eval scopes, so we do not have | |
4298 // either information available directly, especially not when lazily compiling | |
4299 // a function like 'g'. We hence rely on the following invariants: | |
4300 // - (1) is the case iff the innermost scope of the deserialized scope chain | |
4301 // under which we compile is _not_ a declaration scope. This holds because | |
4302 // in all normal cases, function declarations are fully hoisted to a | |
4303 // declaration scope and compiled relative to that. | |
4304 // - (2) is the case iff the current declaration scope is still the original | |
4305 // one relative to the deserialized scope chain. Otherwise we must be | |
4306 // compiling a function in an inner declaration scope in the eval, e.g. a | |
4307 // nested function, and hoisting works normally relative to that. | |
4308 Scope* declaration_scope = top_scope_->DeclarationScope(); | |
4309 Scope* original_declaration_scope = original_scope_->DeclarationScope(); | |
4282 Scope* scope = | 4310 Scope* scope = |
4283 (function_type == FunctionLiteral::DECLARATION && !is_extended_mode()) | 4311 function_type == FunctionLiteral::DECLARATION && !is_extended_mode() && |
4284 ? NewScope(top_scope_->DeclarationScope(), FUNCTION_SCOPE) | 4312 (original_scope_ == original_declaration_scope || |
4285 : NewScope(top_scope_, FUNCTION_SCOPE); | 4313 declaration_scope != original_declaration_scope) |
4314 ? NewScope(declaration_scope, FUNCTION_SCOPE) | |
4315 : NewScope(top_scope_, FUNCTION_SCOPE); | |
4286 ZoneList<Statement*>* body = NULL; | 4316 ZoneList<Statement*>* body = NULL; |
4287 int materialized_literal_count = -1; | 4317 int materialized_literal_count = -1; |
4288 int expected_property_count = -1; | 4318 int expected_property_count = -1; |
4289 int handler_count = 0; | 4319 int handler_count = 0; |
4290 FunctionLiteral::ParameterFlag duplicate_parameters = | 4320 FunctionLiteral::ParameterFlag duplicate_parameters = |
4291 FunctionLiteral::kNoDuplicateParameters; | 4321 FunctionLiteral::kNoDuplicateParameters; |
4292 FunctionLiteral::IsParenthesizedFlag parenthesized = parenthesized_function_ | 4322 FunctionLiteral::IsParenthesizedFlag parenthesized = parenthesized_function_ |
4293 ? FunctionLiteral::kIsParenthesized | 4323 ? FunctionLiteral::kIsParenthesized |
4294 : FunctionLiteral::kNotParenthesized; | 4324 : FunctionLiteral::kNotParenthesized; |
4295 FunctionLiteral::IsGeneratorFlag generator = is_generator | 4325 FunctionLiteral::IsGeneratorFlag generator = is_generator |
(...skipping 1637 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
5933 ASSERT(info()->isolate()->has_pending_exception()); | 5963 ASSERT(info()->isolate()->has_pending_exception()); |
5934 } else { | 5964 } else { |
5935 result = ParseProgram(); | 5965 result = ParseProgram(); |
5936 } | 5966 } |
5937 } | 5967 } |
5938 info()->SetFunction(result); | 5968 info()->SetFunction(result); |
5939 return (result != NULL); | 5969 return (result != NULL); |
5940 } | 5970 } |
5941 | 5971 |
5942 } } // namespace v8::internal | 5972 } } // namespace v8::internal |
OLD | NEW |