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/ast/scopes.h" | 5 #include "src/ast/scopes.h" |
| 6 | 6 |
| 7 #include <set> | 7 #include <set> |
| 8 | 8 |
| 9 #include "src/accessors.h" | 9 #include "src/accessors.h" |
| 10 #include "src/bootstrapper.h" | 10 #include "src/bootstrapper.h" |
| (...skipping 656 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 667 MaybeAssignedFlag maybe_assigned_flag) { | 667 MaybeAssignedFlag maybe_assigned_flag) { |
| 668 DCHECK(!already_resolved()); | 668 DCHECK(!already_resolved()); |
| 669 // This function handles VAR, LET, and CONST modes. DYNAMIC variables are | 669 // This function handles VAR, LET, and CONST modes. DYNAMIC variables are |
| 670 // introduced during variable allocation, and TEMPORARY variables are | 670 // introduced during variable allocation, and TEMPORARY variables are |
| 671 // allocated via NewTemporary(). | 671 // allocated via NewTemporary(). |
| 672 DCHECK(IsDeclaredVariableMode(mode)); | 672 DCHECK(IsDeclaredVariableMode(mode)); |
| 673 return variables_.Declare(zone(), this, name, mode, kind, init_flag, | 673 return variables_.Declare(zone(), this, name, mode, kind, init_flag, |
| 674 maybe_assigned_flag); | 674 maybe_assigned_flag); |
| 675 } | 675 } |
| 676 | 676 |
| 677 Variable* DeclarationScope::DeclareDynamicGlobal(const AstRawString* name) { | 677 Variable* DeclarationScope::DeclareDynamicGlobal(const AstRawString* name, |
| 678 Variable::Kind kind) { | |
| 678 DCHECK(is_script_scope()); | 679 DCHECK(is_script_scope()); |
| 679 return variables_.Declare(zone(), this, name, DYNAMIC_GLOBAL, | 680 return variables_.Declare(zone(), this, name, DYNAMIC_GLOBAL, kind, |
| 680 Variable::NORMAL, kCreatedInitialized); | 681 kCreatedInitialized); |
| 681 } | 682 } |
| 682 | 683 |
| 683 | 684 |
| 684 bool Scope::RemoveUnresolved(VariableProxy* var) { | 685 bool Scope::RemoveUnresolved(VariableProxy* var) { |
| 685 if (unresolved_ == var) { | 686 if (unresolved_ == var) { |
| 686 unresolved_ = var->next_unresolved(); | 687 unresolved_ = var->next_unresolved(); |
| 687 var->set_next_unresolved(nullptr); | 688 var->set_next_unresolved(nullptr); |
| 688 return true; | 689 return true; |
| 689 } | 690 } |
| 690 VariableProxy* current = unresolved_; | 691 VariableProxy* current = unresolved_; |
| (...skipping 553 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1244 } | 1245 } |
| 1245 } | 1246 } |
| 1246 | 1247 |
| 1247 void Scope::CheckZones() { | 1248 void Scope::CheckZones() { |
| 1248 for (Scope* scope = inner_scope_; scope != nullptr; scope = scope->sibling_) { | 1249 for (Scope* scope = inner_scope_; scope != nullptr; scope = scope->sibling_) { |
| 1249 CHECK_EQ(scope->zone(), zone()); | 1250 CHECK_EQ(scope->zone(), zone()); |
| 1250 } | 1251 } |
| 1251 } | 1252 } |
| 1252 #endif // DEBUG | 1253 #endif // DEBUG |
| 1253 | 1254 |
| 1254 | 1255 Variable* Scope::NonLocal(const AstRawString* name, VariableMode mode, |
| 1255 Variable* Scope::NonLocal(const AstRawString* name, VariableMode mode) { | 1256 Variable::Kind kind) { |
| 1256 if (dynamics_ == NULL) dynamics_ = new (zone()) DynamicScopePart(zone()); | 1257 if (dynamics_ == NULL) dynamics_ = new (zone()) DynamicScopePart(zone()); |
| 1257 VariableMap* map = dynamics_->GetMap(mode); | 1258 VariableMap* map = dynamics_->GetMap(mode); |
| 1258 Variable* var = map->Lookup(name); | 1259 Variable* var = map->Lookup(name); |
| 1259 if (var == NULL) { | 1260 if (var == NULL) { |
| 1260 // Declare a new non-local. | 1261 // Declare a new non-local. |
| 1261 InitializationFlag init_flag = (mode == VAR) | 1262 InitializationFlag init_flag = (mode == VAR) |
| 1262 ? kCreatedInitialized : kNeedsInitialization; | 1263 ? kCreatedInitialized : kNeedsInitialization; |
| 1263 var = map->Declare(zone(), NULL, name, mode, Variable::NORMAL, init_flag); | 1264 var = map->Declare(zone(), NULL, name, mode, kind, init_flag); |
| 1264 // Allocate it by giving it a dynamic lookup. | 1265 // Allocate it by giving it a dynamic lookup. |
| 1265 var->AllocateTo(VariableLocation::LOOKUP, -1); | 1266 var->AllocateTo(VariableLocation::LOOKUP, -1); |
| 1266 } | 1267 } |
| 1267 return var; | 1268 return var; |
| 1268 } | 1269 } |
| 1269 | 1270 |
| 1270 Variable* Scope::LookupRecursive(VariableProxy* proxy, | 1271 Variable* Scope::LookupRecursive(VariableProxy* proxy, |
| 1271 BindingKind* binding_kind, | 1272 BindingKind* binding_kind, |
| 1272 AstNodeFactory* factory, | 1273 AstNodeFactory* factory, |
| 1273 Scope* max_outer_scope) { | 1274 Scope* max_outer_scope) { |
| (...skipping 80 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1354 // (functions and consts may be resolved by the parser). | 1355 // (functions and consts may be resolved by the parser). |
| 1355 if (proxy->is_resolved()) return; | 1356 if (proxy->is_resolved()) return; |
| 1356 | 1357 |
| 1357 // Otherwise, try to resolve the variable. | 1358 // Otherwise, try to resolve the variable. |
| 1358 BindingKind binding_kind; | 1359 BindingKind binding_kind; |
| 1359 Variable* var = LookupRecursive(proxy, &binding_kind, factory); | 1360 Variable* var = LookupRecursive(proxy, &binding_kind, factory); |
| 1360 | 1361 |
| 1361 ResolveTo(info, binding_kind, proxy, var); | 1362 ResolveTo(info, binding_kind, proxy, var); |
| 1362 } | 1363 } |
| 1363 | 1364 |
| 1364 void Scope::ResolveTo(ParseInfo* info, BindingKind binding_kind, | 1365 void Scope::ResolveTo(ParseInfo* info, BindingKind binding_kind, |
|
adamk
2016/08/10 17:57:39
It looks like this is the only code that calls Var
Toon Verwaest
2016/08/11 08:46:25
Done.
| |
| 1365 VariableProxy* proxy, Variable* var) { | 1366 VariableProxy* proxy, Variable* var) { |
| 1366 #ifdef DEBUG | 1367 #ifdef DEBUG |
| 1367 if (info->script_is_native()) { | 1368 if (info->script_is_native()) { |
| 1368 // To avoid polluting the global object in native scripts | 1369 // To avoid polluting the global object in native scripts |
| 1369 // - Variables must not be allocated to the global scope. | 1370 // - Variables must not be allocated to the global scope. |
| 1370 CHECK_NOT_NULL(outer_scope()); | 1371 CHECK_NOT_NULL(outer_scope()); |
| 1371 // - Variables must be bound locally or unallocated. | 1372 // - Variables must be bound locally or unallocated. |
| 1372 if (BOUND != binding_kind) { | 1373 if (BOUND != binding_kind) { |
| 1373 // The following variable name may be minified. If so, disable | 1374 // The following variable name may be minified. If so, disable |
| 1374 // minification in js2c.py for better output. | 1375 // minification in js2c.py for better output. |
| (...skipping 12 matching lines...) Expand all Loading... | |
| 1387 switch (binding_kind) { | 1388 switch (binding_kind) { |
| 1388 case BOUND: | 1389 case BOUND: |
| 1389 break; | 1390 break; |
| 1390 | 1391 |
| 1391 case BOUND_EVAL_SHADOWED: | 1392 case BOUND_EVAL_SHADOWED: |
| 1392 // We either found a variable binding that might be shadowed by eval or | 1393 // We either found a variable binding that might be shadowed by eval or |
| 1393 // gave up on it (e.g. by encountering a local with the same in the outer | 1394 // gave up on it (e.g. by encountering a local with the same in the outer |
| 1394 // scope which was not promoted to a context, this can happen if we use | 1395 // scope which was not promoted to a context, this can happen if we use |
| 1395 // debugger to evaluate arbitrary expressions at a break point). | 1396 // debugger to evaluate arbitrary expressions at a break point). |
| 1396 if (var->IsGlobalObjectProperty()) { | 1397 if (var->IsGlobalObjectProperty()) { |
| 1397 var = NonLocal(proxy->raw_name(), DYNAMIC_GLOBAL); | 1398 var = NonLocal(proxy->raw_name(), DYNAMIC_GLOBAL, proxy->var_kind()); |
| 1398 } else if (var->is_dynamic()) { | 1399 } else if (var->is_dynamic()) { |
| 1399 var = NonLocal(proxy->raw_name(), DYNAMIC); | 1400 var = NonLocal(proxy->raw_name(), DYNAMIC, proxy->var_kind()); |
| 1400 } else { | 1401 } else { |
| 1401 Variable* invalidated = var; | 1402 Variable* invalidated = var; |
| 1402 var = NonLocal(proxy->raw_name(), DYNAMIC_LOCAL); | 1403 var = NonLocal(proxy->raw_name(), DYNAMIC_LOCAL, proxy->var_kind()); |
| 1403 var->set_local_if_not_shadowed(invalidated); | 1404 var->set_local_if_not_shadowed(invalidated); |
| 1404 } | 1405 } |
| 1405 break; | 1406 break; |
| 1406 | 1407 |
| 1407 case UNBOUND: | 1408 case UNBOUND: |
| 1408 // No binding has been found. Declare a variable on the global object. | 1409 // No binding has been found. Declare a variable on the global object. |
| 1409 var = info->script_scope()->DeclareDynamicGlobal(proxy->raw_name()); | 1410 var = info->script_scope()->DeclareDynamicGlobal(proxy->raw_name(), |
| 1411 proxy->var_kind()); | |
| 1410 break; | 1412 break; |
| 1411 | 1413 |
| 1412 case UNBOUND_EVAL_SHADOWED: | 1414 case UNBOUND_EVAL_SHADOWED: |
| 1413 // No binding has been found. But some scope makes a sloppy 'eval' call. | 1415 // No binding has been found. But some scope makes a sloppy 'eval' call. |
| 1414 var = NonLocal(proxy->raw_name(), DYNAMIC_GLOBAL); | 1416 var = NonLocal(proxy->raw_name(), DYNAMIC_GLOBAL, proxy->var_kind()); |
| 1415 break; | 1417 break; |
| 1416 | 1418 |
| 1417 case DYNAMIC_LOOKUP: | 1419 case DYNAMIC_LOOKUP: |
| 1418 // The variable could not be resolved statically. | 1420 // The variable could not be resolved statically. |
| 1419 var = NonLocal(proxy->raw_name(), DYNAMIC); | 1421 var = NonLocal(proxy->raw_name(), DYNAMIC, proxy->var_kind()); |
| 1420 break; | 1422 break; |
| 1421 } | 1423 } |
| 1422 | 1424 |
| 1423 DCHECK(var != NULL); | 1425 DCHECK(var != NULL); |
| 1424 if (proxy->is_assigned()) var->set_maybe_assigned(); | 1426 if (proxy->is_assigned()) var->set_maybe_assigned(); |
| 1425 | 1427 |
| 1426 proxy->BindTo(var); | 1428 proxy->BindTo(var); |
| 1427 } | 1429 } |
| 1428 | 1430 |
| 1429 void Scope::ResolveVariablesRecursively(ParseInfo* info, | 1431 void Scope::ResolveVariablesRecursively(ParseInfo* info, |
| (...skipping 361 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1791 function != NULL && function->proxy()->var()->IsContextSlot(); | 1793 function != NULL && function->proxy()->var()->IsContextSlot(); |
| 1792 return num_heap_slots() - Context::MIN_CONTEXT_SLOTS - num_global_slots() - | 1794 return num_heap_slots() - Context::MIN_CONTEXT_SLOTS - num_global_slots() - |
| 1793 (is_function_var_in_context ? 1 : 0); | 1795 (is_function_var_in_context ? 1 : 0); |
| 1794 } | 1796 } |
| 1795 | 1797 |
| 1796 | 1798 |
| 1797 int Scope::ContextGlobalCount() const { return num_global_slots(); } | 1799 int Scope::ContextGlobalCount() const { return num_global_slots(); } |
| 1798 | 1800 |
| 1799 } // namespace internal | 1801 } // namespace internal |
| 1800 } // namespace v8 | 1802 } // namespace v8 |
| OLD | NEW |