Index: src/scopes.cc |
diff --git a/src/scopes.cc b/src/scopes.cc |
index 7d9bce5c40da0d442d5084ebe4ee7a0b6dfa5e27..33f8c83bd852131bcb94da938a31b68da3a27e75 100644 |
--- a/src/scopes.cc |
+++ b/src/scopes.cc |
@@ -1,4 +1,4 @@ |
-// Copyright 2010 the V8 project authors. All rights reserved. |
+// Copyright 2011 the V8 project authors. All rights reserved. |
// Redistribution and use in source and binary forms, with or without |
// modification, are permitted provided that the following conditions are |
// met: |
@@ -199,6 +199,7 @@ void Scope::SetDefaults(Type type, |
// Inherit the strict mode from the parent scope. |
strict_mode_ = (outer_scope != NULL) && outer_scope->strict_mode_; |
outer_scope_calls_eval_ = false; |
+ outer_scope_calls_non_strict_eval_ = false; |
inner_scope_calls_eval_ = false; |
outer_scope_is_eval_scope_ = false; |
force_eager_compilation_ = false; |
@@ -483,8 +484,17 @@ void Scope::AllocateVariables(Handle<Context> context) { |
// and assume they may invoke eval themselves. Eventually we could capture |
// this information in the ScopeInfo and then use it here (by traversing |
// the call chain stack, at compile time). |
+ |
bool eval_scope = is_eval_scope(); |
- PropagateScopeInfo(eval_scope, eval_scope); |
+ bool outer_scope_calls_eval = false; |
+ bool outer_scope_calls_non_strict_eval = false; |
+ if (!is_global_scope()) { |
+ context->ComputeEvalScopeInfo(&outer_scope_calls_eval, |
+ &outer_scope_calls_non_strict_eval); |
+ } |
+ PropagateScopeInfo(outer_scope_calls_eval, |
+ outer_scope_calls_non_strict_eval, |
+ eval_scope); |
// 2) Resolve variables. |
Scope* global_scope = NULL; |
@@ -616,10 +626,14 @@ void Scope::Print(int n) { |
if (HasTrivialOuterContext()) { |
Indent(n1, "// scope has trivial outer context\n"); |
} |
+ if (is_strict_mode()) Indent(n1, "// strict mode scope\n"); |
if (scope_inside_with_) Indent(n1, "// scope inside 'with'\n"); |
if (scope_contains_with_) Indent(n1, "// scope contains 'with'\n"); |
if (scope_calls_eval_) Indent(n1, "// scope calls 'eval'\n"); |
if (outer_scope_calls_eval_) Indent(n1, "// outer scope calls 'eval'\n"); |
+ if (outer_scope_calls_non_strict_eval_) { |
+ Indent(n1, "// outer scope calls 'eval' in non-strict context\n"); |
+ } |
if (inner_scope_calls_eval_) Indent(n1, "// inner scope calls 'eval'\n"); |
if (outer_scope_is_eval_scope_) { |
Indent(n1, "// outer scope is 'eval' scope\n"); |
@@ -846,20 +860,29 @@ void Scope::ResolveVariablesRecursively(Scope* global_scope, |
bool Scope::PropagateScopeInfo(bool outer_scope_calls_eval, |
+ bool outer_scope_calls_non_strict_eval, |
bool outer_scope_is_eval_scope) { |
if (outer_scope_calls_eval) { |
outer_scope_calls_eval_ = true; |
} |
+ if (outer_scope_calls_non_strict_eval) { |
+ outer_scope_calls_non_strict_eval_ = true; |
+ } |
+ |
if (outer_scope_is_eval_scope) { |
outer_scope_is_eval_scope_ = true; |
} |
bool calls_eval = scope_calls_eval_ || outer_scope_calls_eval_; |
bool is_eval = is_eval_scope() || outer_scope_is_eval_scope_; |
+ bool calls_non_strict_eval = |
+ (scope_calls_eval_ && !is_strict_mode()) || outer_scope_calls_non_strict_eval_; |
fschneider
2011/05/11 10:35:11
Long line.
Mads Ager (chromium)
2011/05/11 11:24:11
Done.
|
for (int i = 0; i < inner_scopes_.length(); i++) { |
Scope* inner_scope = inner_scopes_[i]; |
- if (inner_scope->PropagateScopeInfo(calls_eval, is_eval)) { |
+ if (inner_scope->PropagateScopeInfo(calls_eval, |
+ calls_non_strict_eval, |
+ is_eval)) { |
inner_scope_calls_eval_ = true; |
} |
if (inner_scope->force_eager_compilation_) { |