Chromium Code Reviews| Index: src/scopes.cc |
| diff --git a/src/scopes.cc b/src/scopes.cc |
| index 35449643cec2dce0742737c35b33e9b559b9ab0f..2ece77ee83083c4c442c8a8e7fc7e32b2cafb0c0 100644 |
| --- a/src/scopes.cc |
| +++ b/src/scopes.cc |
| @@ -156,6 +156,7 @@ void Scope::SetDefaults(ScopeType scope_type, |
| scope_uses_arguments_ = false; |
| scope_uses_super_property_ = false; |
| scope_uses_this_ = false; |
| + scope_uses_new_target_ = false; |
| asm_module_ = false; |
| asm_function_ = outer_scope != NULL && outer_scope->asm_module_; |
| // Inherit the language mode from the parent scope. |
| @@ -164,6 +165,7 @@ void Scope::SetDefaults(ScopeType scope_type, |
| inner_scope_calls_eval_ = false; |
| inner_scope_uses_arguments_ = false; |
| inner_scope_uses_this_ = false; |
| + inner_scope_uses_new_target_ = false; |
| inner_scope_uses_super_property_ = false; |
| force_eager_compilation_ = false; |
| force_context_allocation_ = (outer_scope != NULL && !is_function_scope()) |
| @@ -295,9 +297,9 @@ void Scope::Initialize(bool subclass_constructor) { |
| // if naccesses_ == 0). |
| // NOTE: When loading parameters in the script scope, we must take |
| // care not to access them as properties of the global object, but |
| - // instead load them directly from the stack. Currently, the only |
| - // such parameter is 'this' which is passed on the stack when |
| - // invoking scripts |
| + // instead load them directly from the stack. Currently, the only two |
| + // such parameter are 'this' and 'new.target' which are passed on the stack |
| + // when invoking scripts |
| if (is_declaration_scope()) { |
| DCHECK(!subclass_constructor || is_function_scope()); |
| Variable* var = variables_.Declare( |
| @@ -307,11 +309,14 @@ void Scope::Initialize(bool subclass_constructor) { |
| var->AllocateTo(Variable::PARAMETER, -1); |
| receiver_ = var; |
| - if (subclass_constructor) { |
| - new_target_ = variables_.Declare( |
| - this, ast_value_factory_->new_target_string(), CONST, false, |
| - Variable::NEW_TARGET, kCreatedInitialized); |
| - new_target_->AllocateTo(Variable::PARAMETER, -2); |
| + // TODO(arv): Can the construct call check if new target is needed? |
| + // TODO(arv): Make `new.target` generate `%_IsConstruct() ? new.target : |
| + // undefined |
| + new_target_ = |
|
Dmitry Lomov (no reviews)
2015/02/25 11:28:40
I'd prefer not declaring new.target if it is not n
arv (Not doing code reviews)
2015/02/25 14:47:25
This is where I was when I got pulled into other w
|
| + variables_.Declare(this, ast_value_factory_->new_target_string(), CONST, |
| + false, Variable::NEW_TARGET, kCreatedInitialized); |
| + new_target_->AllocateTo(Variable::PARAMETER, -2); |
|
arv (Not doing code reviews)
2015/02/25 14:47:24
Do you think this is OK for cases like?
function
Dmitry Lomov (no reviews)
2015/02/26 14:15:05
Depends on the codegen we will have for such funct
|
| + if (subclass_constructor || scope_uses_new_target_) { |
| new_target_->set_is_used(); |
| } |
| } else { |
| @@ -363,6 +368,7 @@ Scope* Scope::FinalizeBlockScope() { |
| if (uses_arguments()) outer_scope_->RecordArgumentsUsage(); |
| if (uses_super_property()) outer_scope_->RecordSuperPropertyUsage(); |
| if (uses_this()) outer_scope_->RecordThisUsage(); |
| + if (uses_new_target()) outer_scope_->RecordNewTargetUsage(); |
| return NULL; |
| } |
| @@ -891,12 +897,16 @@ void Scope::Print(int n) { |
| if (scope_uses_super_property_) |
| Indent(n1, "// scope uses 'super' property\n"); |
| if (scope_uses_this_) Indent(n1, "// scope uses 'this'\n"); |
| + if (scope_uses_new_target_) Indent(n1, "// scope uses 'new.target'\n"); |
| if (inner_scope_uses_arguments_) { |
| Indent(n1, "// inner scope uses 'arguments'\n"); |
| } |
| if (inner_scope_uses_super_property_) |
| Indent(n1, "// inner scope uses 'super' property\n"); |
| if (inner_scope_uses_this_) Indent(n1, "// inner scope uses 'this'\n"); |
| + if (inner_scope_uses_new_target_) { |
| + Indent(n1, "// inner scope uses 'new.target'\n"); |
| + } |
| if (outer_scope_calls_sloppy_eval_) { |
| Indent(n1, "// outer scope calls 'eval' in sloppy context\n"); |
| } |
| @@ -1139,6 +1149,10 @@ void Scope::PropagateScopeInfo(bool outer_scope_calls_sloppy_eval ) { |
| if (inner->scope_uses_this_ || inner->inner_scope_uses_this_) { |
| inner_scope_uses_this_ = true; |
| } |
| + if (inner->scope_uses_new_target_ || |
| + inner->inner_scope_uses_new_target_) { |
| + inner_scope_uses_new_target_ = true; |
| + } |
| } |
| if (inner->force_eager_compilation_) { |
| force_eager_compilation_ = true; |