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 1286 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1297 *binding_kind = UNBOUND; | 1297 *binding_kind = UNBOUND; |
1298 var = | 1298 var = |
1299 is_function_scope() | 1299 is_function_scope() |
1300 ? AsDeclarationScope()->LookupFunctionVar(proxy->raw_name(), factory) | 1300 ? AsDeclarationScope()->LookupFunctionVar(proxy->raw_name(), factory) |
1301 : nullptr; | 1301 : nullptr; |
1302 if (var != NULL) { | 1302 if (var != NULL) { |
1303 *binding_kind = BOUND; | 1303 *binding_kind = BOUND; |
1304 } else if (outer_scope_ != nullptr && this != max_outer_scope) { | 1304 } else if (outer_scope_ != nullptr && this != max_outer_scope) { |
1305 var = outer_scope_->LookupRecursive(proxy, binding_kind, factory, | 1305 var = outer_scope_->LookupRecursive(proxy, binding_kind, factory, |
1306 max_outer_scope); | 1306 max_outer_scope); |
1307 if (*binding_kind == BOUND && (is_function_scope() || is_with_scope())) { | 1307 if (*binding_kind == BOUND && is_function_scope()) { |
1308 var->ForceContextAllocation(); | 1308 var->ForceContextAllocation(); |
1309 } | 1309 } |
1310 } else { | 1310 } else { |
1311 DCHECK(is_script_scope() || this == max_outer_scope); | 1311 DCHECK(is_script_scope() || this == max_outer_scope); |
1312 } | 1312 } |
1313 | 1313 |
1314 // "this" can't be shadowed by "eval"-introduced bindings or by "with" scopes. | 1314 // "this" can't be shadowed by "eval"-introduced bindings or by "with" scopes. |
1315 // TODO(wingo): There are other variables in this category; add them. | 1315 // TODO(wingo): There are other variables in this category; add them. |
1316 bool name_can_be_shadowed = var == nullptr || !var->is_this(); | 1316 bool name_can_be_shadowed = var == nullptr || !var->is_this(); |
1317 | 1317 |
1318 if (is_with_scope() && name_can_be_shadowed) { | 1318 if (is_with_scope() && name_can_be_shadowed) { |
1319 DCHECK(!already_resolved()); | 1319 DCHECK(!already_resolved()); |
1320 // The current scope is a with scope, so the variable binding can not be | 1320 // The current scope is a with scope, so the variable binding can not be |
1321 // statically resolved. However, note that it was necessary to do a lookup | 1321 // statically resolved. However, note that it was necessary to do a lookup |
1322 // in the outer scope anyway, because if a binding exists in an outer scope, | 1322 // in the outer scope anyway, because if a binding exists in an outer scope, |
1323 // the associated variable has to be marked as potentially being accessed | 1323 // the associated variable has to be marked as potentially being accessed |
1324 // from inside of an inner with scope (the property may not be in the 'with' | 1324 // from inside of an inner with scope (the property may not be in the 'with' |
1325 // object). | 1325 // object). |
1326 if (var != NULL && proxy->is_assigned()) var->set_maybe_assigned(); | 1326 if (var != NULL) { |
1327 var->set_is_used(); | |
1328 var->ForceContextAllocation(); | |
1329 if (proxy->is_assigned()) var->set_maybe_assigned(); | |
1330 } | |
1327 *binding_kind = DYNAMIC_LOOKUP; | 1331 *binding_kind = DYNAMIC_LOOKUP; |
1328 return NULL; | 1332 return NULL; |
1329 } else if (calls_sloppy_eval() && is_declaration_scope() && | 1333 } else if (calls_sloppy_eval() && is_declaration_scope() && |
1330 !is_script_scope() && name_can_be_shadowed) { | 1334 !is_script_scope() && name_can_be_shadowed) { |
1331 // A variable binding may have been found in an outer scope, but the current | 1335 // A variable binding may have been found in an outer scope, but the current |
1332 // scope makes a sloppy 'eval' call, so the found variable may not be | 1336 // scope makes a sloppy 'eval' call, so the found variable may not be |
1333 // the correct one (the 'eval' may introduce a binding with the same name). | 1337 // the correct one (the 'eval' may introduce a binding with the same name). |
1334 // In that case, change the lookup result to reflect this situation. | 1338 // In that case, change the lookup result to reflect this situation. |
1335 // Only scopes that can host var bindings (declaration scopes) need be | 1339 // Only scopes that can host var bindings (declaration scopes) need be |
1336 // considered here (this excludes block and catch scopes), and variable | 1340 // considered here (this excludes block and catch scopes), and variable |
(...skipping 145 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1482 } | 1486 } |
1483 } | 1487 } |
1484 | 1488 |
1485 | 1489 |
1486 bool Scope::MustAllocate(Variable* var) { | 1490 bool Scope::MustAllocate(Variable* var) { |
1487 DCHECK(var->location() != VariableLocation::MODULE); | 1491 DCHECK(var->location() != VariableLocation::MODULE); |
1488 // Give var a read/write use if there is a chance it might be accessed | 1492 // Give var a read/write use if there is a chance it might be accessed |
1489 // via an eval() call. This is only possible if the variable has a | 1493 // via an eval() call. This is only possible if the variable has a |
1490 // visible name. | 1494 // visible name. |
1491 if ((var->is_this() || !var->raw_name()->IsEmpty()) && | 1495 if ((var->is_this() || !var->raw_name()->IsEmpty()) && |
1492 (var->has_forced_context_allocation() || scope_calls_eval_ || | 1496 (scope_calls_eval_ || inner_scope_calls_eval_ || is_catch_scope() || |
1493 inner_scope_calls_eval_ || is_catch_scope() || is_block_scope() || | |
1494 is_script_scope())) { | 1497 is_script_scope())) { |
1495 var->set_is_used(); | 1498 var->set_is_used(); |
1496 if (scope_calls_eval_ || inner_scope_calls_eval_) var->set_maybe_assigned(); | 1499 if (scope_calls_eval_ || inner_scope_calls_eval_) var->set_maybe_assigned(); |
1497 } | 1500 } |
1498 // Global variables do not need to be allocated. | 1501 // Global variables do not need to be allocated. |
1499 return !var->IsGlobalObjectProperty() && var->is_used(); | 1502 return !var->IsGlobalObjectProperty() && var->is_used(); |
neis
2016/08/09 07:27:15
Can you add DCHECK(!var->has_forced_context_alloca
adamk
2016/08/09 16:25:18
Done.
| |
1500 } | 1503 } |
1501 | 1504 |
1502 | 1505 |
1503 bool Scope::MustAllocateInContext(Variable* var) { | 1506 bool Scope::MustAllocateInContext(Variable* var) { |
1504 // If var is accessed from an inner scope, or if there is a possibility | 1507 // If var is accessed from an inner scope, or if there is a possibility |
1505 // that it might be accessed from the current or an inner scope (through | 1508 // that it might be accessed from the current or an inner scope (through |
1506 // an eval() call or a runtime with lookup), it must be allocated in the | 1509 // an eval() call or a runtime with lookup), it must be allocated in the |
1507 // context. | 1510 // context. |
1508 // | 1511 // |
1509 // Exceptions: If the scope as a whole has forced context allocation, all | 1512 // Exceptions: If the scope as a whole has forced context allocation, all |
(...skipping 272 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1782 function != NULL && function->proxy()->var()->IsContextSlot(); | 1785 function != NULL && function->proxy()->var()->IsContextSlot(); |
1783 return num_heap_slots() - Context::MIN_CONTEXT_SLOTS - num_global_slots() - | 1786 return num_heap_slots() - Context::MIN_CONTEXT_SLOTS - num_global_slots() - |
1784 (is_function_var_in_context ? 1 : 0); | 1787 (is_function_var_in_context ? 1 : 0); |
1785 } | 1788 } |
1786 | 1789 |
1787 | 1790 |
1788 int Scope::ContextGlobalCount() const { return num_global_slots(); } | 1791 int Scope::ContextGlobalCount() const { return num_global_slots(); } |
1789 | 1792 |
1790 } // namespace internal | 1793 } // namespace internal |
1791 } // namespace v8 | 1794 } // namespace v8 |
OLD | NEW |