Chromium Code Reviews| 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 #include "src/v8.h" | 5 #include "src/v8.h" |
| 6 | 6 |
| 7 #include "src/scopes.h" | 7 #include "src/scopes.h" |
| 8 | 8 |
| 9 #include "src/accessors.h" | 9 #include "src/accessors.h" |
| 10 #include "src/bootstrapper.h" | 10 #include "src/bootstrapper.h" |
| (...skipping 138 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 149 new_target_ = nullptr; | 149 new_target_ = nullptr; |
| 150 function_ = NULL; | 150 function_ = NULL; |
| 151 arguments_ = NULL; | 151 arguments_ = NULL; |
| 152 illegal_redecl_ = NULL; | 152 illegal_redecl_ = NULL; |
| 153 scope_inside_with_ = false; | 153 scope_inside_with_ = false; |
| 154 scope_contains_with_ = false; | 154 scope_contains_with_ = false; |
| 155 scope_calls_eval_ = false; | 155 scope_calls_eval_ = false; |
| 156 scope_uses_arguments_ = false; | 156 scope_uses_arguments_ = false; |
| 157 scope_uses_super_property_ = false; | 157 scope_uses_super_property_ = false; |
| 158 scope_uses_this_ = false; | 158 scope_uses_this_ = false; |
| 159 scope_uses_new_target_ = false; | |
| 159 asm_module_ = false; | 160 asm_module_ = false; |
| 160 asm_function_ = outer_scope != NULL && outer_scope->asm_module_; | 161 asm_function_ = outer_scope != NULL && outer_scope->asm_module_; |
| 161 // Inherit the language mode from the parent scope. | 162 // Inherit the language mode from the parent scope. |
| 162 language_mode_ = outer_scope != NULL ? outer_scope->language_mode_ : SLOPPY; | 163 language_mode_ = outer_scope != NULL ? outer_scope->language_mode_ : SLOPPY; |
| 163 outer_scope_calls_sloppy_eval_ = false; | 164 outer_scope_calls_sloppy_eval_ = false; |
| 164 inner_scope_calls_eval_ = false; | 165 inner_scope_calls_eval_ = false; |
| 165 inner_scope_uses_arguments_ = false; | 166 inner_scope_uses_arguments_ = false; |
| 166 inner_scope_uses_this_ = false; | 167 inner_scope_uses_this_ = false; |
| 168 inner_scope_uses_new_target_ = false; | |
| 167 inner_scope_uses_super_property_ = false; | 169 inner_scope_uses_super_property_ = false; |
| 168 force_eager_compilation_ = false; | 170 force_eager_compilation_ = false; |
| 169 force_context_allocation_ = (outer_scope != NULL && !is_function_scope()) | 171 force_context_allocation_ = (outer_scope != NULL && !is_function_scope()) |
| 170 ? outer_scope->has_forced_context_allocation() : false; | 172 ? outer_scope->has_forced_context_allocation() : false; |
| 171 num_var_or_const_ = 0; | 173 num_var_or_const_ = 0; |
| 172 num_stack_slots_ = 0; | 174 num_stack_slots_ = 0; |
| 173 num_heap_slots_ = 0; | 175 num_heap_slots_ = 0; |
| 174 num_modules_ = 0; | 176 num_modules_ = 0; |
| 175 module_var_ = NULL, | 177 module_var_ = NULL, |
| 176 rest_parameter_ = NULL; | 178 rest_parameter_ = NULL; |
| (...skipping 111 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 288 scope_inside_with_ = outer_scope_->scope_inside_with_ || is_with_scope(); | 290 scope_inside_with_ = outer_scope_->scope_inside_with_ || is_with_scope(); |
| 289 } else { | 291 } else { |
| 290 scope_inside_with_ = is_with_scope(); | 292 scope_inside_with_ = is_with_scope(); |
| 291 } | 293 } |
| 292 | 294 |
| 293 // Declare convenience variables. | 295 // Declare convenience variables. |
| 294 // Declare and allocate receiver (even for the script scope, and even | 296 // Declare and allocate receiver (even for the script scope, and even |
| 295 // if naccesses_ == 0). | 297 // if naccesses_ == 0). |
| 296 // NOTE: When loading parameters in the script scope, we must take | 298 // NOTE: When loading parameters in the script scope, we must take |
| 297 // care not to access them as properties of the global object, but | 299 // care not to access them as properties of the global object, but |
| 298 // instead load them directly from the stack. Currently, the only | 300 // instead load them directly from the stack. Currently, the only two |
| 299 // such parameter is 'this' which is passed on the stack when | 301 // such parameter are 'this' and 'new.target' which are passed on the stack |
| 300 // invoking scripts | 302 // when invoking scripts |
| 301 if (is_declaration_scope()) { | 303 if (is_declaration_scope()) { |
| 302 DCHECK(!subclass_constructor || is_function_scope()); | 304 DCHECK(!subclass_constructor || is_function_scope()); |
| 303 Variable* var = variables_.Declare( | 305 Variable* var = variables_.Declare( |
| 304 this, ast_value_factory_->this_string(), | 306 this, ast_value_factory_->this_string(), |
| 305 subclass_constructor ? CONST : VAR, false, Variable::THIS, | 307 subclass_constructor ? CONST : VAR, false, Variable::THIS, |
| 306 subclass_constructor ? kNeedsInitialization : kCreatedInitialized); | 308 subclass_constructor ? kNeedsInitialization : kCreatedInitialized); |
| 307 var->AllocateTo(Variable::PARAMETER, -1); | 309 var->AllocateTo(Variable::PARAMETER, -1); |
| 308 receiver_ = var; | 310 receiver_ = var; |
| 309 | 311 |
| 310 if (subclass_constructor) { | 312 // TODO(arv): Can the construct call check if new target is needed? |
| 311 new_target_ = variables_.Declare( | 313 // TODO(arv): Make `new.target` generate `%_IsConstruct() ? new.target : |
| 312 this, ast_value_factory_->new_target_string(), CONST, false, | 314 // undefined |
| 313 Variable::NEW_TARGET, kCreatedInitialized); | 315 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
| |
| 314 new_target_->AllocateTo(Variable::PARAMETER, -2); | 316 variables_.Declare(this, ast_value_factory_->new_target_string(), CONST, |
| 317 false, Variable::NEW_TARGET, kCreatedInitialized); | |
| 318 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
| |
| 319 if (subclass_constructor || scope_uses_new_target_) { | |
| 315 new_target_->set_is_used(); | 320 new_target_->set_is_used(); |
| 316 } | 321 } |
| 317 } else { | 322 } else { |
| 318 DCHECK(outer_scope() != NULL); | 323 DCHECK(outer_scope() != NULL); |
| 319 receiver_ = outer_scope()->receiver(); | 324 receiver_ = outer_scope()->receiver(); |
| 320 } | 325 } |
| 321 | 326 |
| 322 if (is_function_scope()) { | 327 if (is_function_scope()) { |
| 323 // Declare 'arguments' variable which exists in all functions. | 328 // Declare 'arguments' variable which exists in all functions. |
| 324 // Note that it might never be accessed, in which case it won't be | 329 // Note that it might never be accessed, in which case it won't be |
| (...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 356 | 361 |
| 357 // Move unresolved variables | 362 // Move unresolved variables |
| 358 for (int i = 0; i < unresolved_.length(); i++) { | 363 for (int i = 0; i < unresolved_.length(); i++) { |
| 359 outer_scope()->unresolved_.Add(unresolved_[i], zone()); | 364 outer_scope()->unresolved_.Add(unresolved_[i], zone()); |
| 360 } | 365 } |
| 361 | 366 |
| 362 // Propagate usage flags to outer scope. | 367 // Propagate usage flags to outer scope. |
| 363 if (uses_arguments()) outer_scope_->RecordArgumentsUsage(); | 368 if (uses_arguments()) outer_scope_->RecordArgumentsUsage(); |
| 364 if (uses_super_property()) outer_scope_->RecordSuperPropertyUsage(); | 369 if (uses_super_property()) outer_scope_->RecordSuperPropertyUsage(); |
| 365 if (uses_this()) outer_scope_->RecordThisUsage(); | 370 if (uses_this()) outer_scope_->RecordThisUsage(); |
| 371 if (uses_new_target()) outer_scope_->RecordNewTargetUsage(); | |
| 366 | 372 |
| 367 return NULL; | 373 return NULL; |
| 368 } | 374 } |
| 369 | 375 |
| 370 | 376 |
| 371 Variable* Scope::LookupLocal(const AstRawString* name) { | 377 Variable* Scope::LookupLocal(const AstRawString* name) { |
| 372 Variable* result = variables_.Lookup(name); | 378 Variable* result = variables_.Lookup(name); |
| 373 if (result != NULL || scope_info_.is_null()) { | 379 if (result != NULL || scope_info_.is_null()) { |
| 374 return result; | 380 return result; |
| 375 } | 381 } |
| (...skipping 508 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 884 } else if (is_strict(language_mode())) { | 890 } else if (is_strict(language_mode())) { |
| 885 Indent(n1, "// strict mode scope\n"); | 891 Indent(n1, "// strict mode scope\n"); |
| 886 } | 892 } |
| 887 if (scope_inside_with_) Indent(n1, "// scope inside 'with'\n"); | 893 if (scope_inside_with_) Indent(n1, "// scope inside 'with'\n"); |
| 888 if (scope_contains_with_) Indent(n1, "// scope contains 'with'\n"); | 894 if (scope_contains_with_) Indent(n1, "// scope contains 'with'\n"); |
| 889 if (scope_calls_eval_) Indent(n1, "// scope calls 'eval'\n"); | 895 if (scope_calls_eval_) Indent(n1, "// scope calls 'eval'\n"); |
| 890 if (scope_uses_arguments_) Indent(n1, "// scope uses 'arguments'\n"); | 896 if (scope_uses_arguments_) Indent(n1, "// scope uses 'arguments'\n"); |
| 891 if (scope_uses_super_property_) | 897 if (scope_uses_super_property_) |
| 892 Indent(n1, "// scope uses 'super' property\n"); | 898 Indent(n1, "// scope uses 'super' property\n"); |
| 893 if (scope_uses_this_) Indent(n1, "// scope uses 'this'\n"); | 899 if (scope_uses_this_) Indent(n1, "// scope uses 'this'\n"); |
| 900 if (scope_uses_new_target_) Indent(n1, "// scope uses 'new.target'\n"); | |
| 894 if (inner_scope_uses_arguments_) { | 901 if (inner_scope_uses_arguments_) { |
| 895 Indent(n1, "// inner scope uses 'arguments'\n"); | 902 Indent(n1, "// inner scope uses 'arguments'\n"); |
| 896 } | 903 } |
| 897 if (inner_scope_uses_super_property_) | 904 if (inner_scope_uses_super_property_) |
| 898 Indent(n1, "// inner scope uses 'super' property\n"); | 905 Indent(n1, "// inner scope uses 'super' property\n"); |
| 899 if (inner_scope_uses_this_) Indent(n1, "// inner scope uses 'this'\n"); | 906 if (inner_scope_uses_this_) Indent(n1, "// inner scope uses 'this'\n"); |
| 907 if (inner_scope_uses_new_target_) { | |
| 908 Indent(n1, "// inner scope uses 'new.target'\n"); | |
| 909 } | |
| 900 if (outer_scope_calls_sloppy_eval_) { | 910 if (outer_scope_calls_sloppy_eval_) { |
| 901 Indent(n1, "// outer scope calls 'eval' in sloppy context\n"); | 911 Indent(n1, "// outer scope calls 'eval' in sloppy context\n"); |
| 902 } | 912 } |
| 903 if (inner_scope_calls_eval_) Indent(n1, "// inner scope calls 'eval'\n"); | 913 if (inner_scope_calls_eval_) Indent(n1, "// inner scope calls 'eval'\n"); |
| 904 if (num_stack_slots_ > 0) { Indent(n1, "// "); | 914 if (num_stack_slots_ > 0) { Indent(n1, "// "); |
| 905 PrintF("%d stack slots\n", num_stack_slots_); } | 915 PrintF("%d stack slots\n", num_stack_slots_); } |
| 906 if (num_heap_slots_ > 0) { Indent(n1, "// "); | 916 if (num_heap_slots_ > 0) { Indent(n1, "// "); |
| 907 PrintF("%d heap slots\n", num_heap_slots_); } | 917 PrintF("%d heap slots\n", num_heap_slots_); } |
| 908 | 918 |
| 909 // Print locals. | 919 // Print locals. |
| (...skipping 222 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1132 if (inner->scope_uses_arguments_ || inner->inner_scope_uses_arguments_) { | 1142 if (inner->scope_uses_arguments_ || inner->inner_scope_uses_arguments_) { |
| 1133 inner_scope_uses_arguments_ = true; | 1143 inner_scope_uses_arguments_ = true; |
| 1134 } | 1144 } |
| 1135 if (inner->scope_uses_super_property_ || | 1145 if (inner->scope_uses_super_property_ || |
| 1136 inner->inner_scope_uses_super_property_) { | 1146 inner->inner_scope_uses_super_property_) { |
| 1137 inner_scope_uses_super_property_ = true; | 1147 inner_scope_uses_super_property_ = true; |
| 1138 } | 1148 } |
| 1139 if (inner->scope_uses_this_ || inner->inner_scope_uses_this_) { | 1149 if (inner->scope_uses_this_ || inner->inner_scope_uses_this_) { |
| 1140 inner_scope_uses_this_ = true; | 1150 inner_scope_uses_this_ = true; |
| 1141 } | 1151 } |
| 1152 if (inner->scope_uses_new_target_ || | |
| 1153 inner->inner_scope_uses_new_target_) { | |
| 1154 inner_scope_uses_new_target_ = true; | |
| 1155 } | |
| 1142 } | 1156 } |
| 1143 if (inner->force_eager_compilation_) { | 1157 if (inner->force_eager_compilation_) { |
| 1144 force_eager_compilation_ = true; | 1158 force_eager_compilation_ = true; |
| 1145 } | 1159 } |
| 1146 if (asm_module_ && inner->scope_type() == FUNCTION_SCOPE) { | 1160 if (asm_module_ && inner->scope_type() == FUNCTION_SCOPE) { |
| 1147 inner->asm_function_ = true; | 1161 inner->asm_function_ = true; |
| 1148 } | 1162 } |
| 1149 } | 1163 } |
| 1150 } | 1164 } |
| 1151 | 1165 |
| (...skipping 229 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1381 } | 1395 } |
| 1382 | 1396 |
| 1383 | 1397 |
| 1384 int Scope::ContextLocalCount() const { | 1398 int Scope::ContextLocalCount() const { |
| 1385 if (num_heap_slots() == 0) return 0; | 1399 if (num_heap_slots() == 0) return 0; |
| 1386 return num_heap_slots() - Context::MIN_CONTEXT_SLOTS - | 1400 return num_heap_slots() - Context::MIN_CONTEXT_SLOTS - |
| 1387 (function_ != NULL && function_->proxy()->var()->IsContextSlot() ? 1 : 0); | 1401 (function_ != NULL && function_->proxy()->var()->IsContextSlot() ? 1 : 0); |
| 1388 } | 1402 } |
| 1389 | 1403 |
| 1390 } } // namespace v8::internal | 1404 } } // namespace v8::internal |
| OLD | NEW |