aboutsummaryrefslogtreecommitdiffstats
path: root/src/qml/compiler/qv4compilerscanfunctions.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/qml/compiler/qv4compilerscanfunctions.cpp')
-rw-r--r--src/qml/compiler/qv4compilerscanfunctions.cpp38
1 files changed, 35 insertions, 3 deletions
diff --git a/src/qml/compiler/qv4compilerscanfunctions.cpp b/src/qml/compiler/qv4compilerscanfunctions.cpp
index b779e37946..0feba7bb61 100644
--- a/src/qml/compiler/qv4compilerscanfunctions.cpp
+++ b/src/qml/compiler/qv4compilerscanfunctions.cpp
@@ -474,13 +474,17 @@ void ScanFunctions::calcEscapingVariables()
while (c) {
Context::MemberMap::const_iterator it = c->members.find(var);
if (it != c->members.end()) {
- if (c != inner)
+ if (c != inner) {
it->canEscape = true;
+ c->requiresExecutionContext = true;
+ }
break;
}
if (c->findArgument(var) != -1) {
- if (c != inner)
+ if (c != inner) {
c->argumentsCanEscape = true;
+ c->requiresExecutionContext = true;
+ }
break;
}
c = c->parent;
@@ -489,16 +493,44 @@ void ScanFunctions::calcEscapingVariables()
Context *c = inner->parent;
while (c) {
c->hasDirectEval |= inner->hasDirectEval;
+ c->hasWith |= inner->hasWith;
c = c->parent;
}
}
+ for (Context *c : qAsConst(m->contextMap)) {
+ bool allVarsEscape = c->hasWith || c->hasTry || c->hasDirectEval || m->debugMode;
+ if (allVarsEscape) {
+ c->requiresExecutionContext = true;
+ c->argumentsCanEscape = true;
+ for (auto &m : c->members) {
+ m.canEscape = true;
+ }
+ }
+ // ### for now until we have lexically scoped vars that'll require it
+ if (c->type == ContextType::Global)
+ c->requiresExecutionContext = false;
+ // ### Shouldn't be required, we could probably rather change the ContextType to FunctionCode for strict eval
+ if (c->type == ContextType::Eval && c->isStrict)
+ c->requiresExecutionContext = true;
+ if (!c->parent || c->usesArgumentsObject == Context::ArgumentsObjectUnknown)
+ c->usesArgumentsObject = Context::ArgumentsObjectNotUsed;
+ if (c->usesArgumentsObject == Context::ArgumentsObjectUsed) {
+ QString arguments = QStringLiteral("arguments");
+ c->addLocalVar(arguments, Context::VariableDeclaration, AST::VariableScope::Var);
+ if (!c->isStrict) {
+ c->argumentsCanEscape = true;
+ c->requiresExecutionContext = true;
+ }
+ }
+ }
static const bool showEscapingVars = qEnvironmentVariableIsSet("QV4_SHOW_ESCAPING_VARS");
if (showEscapingVars) {
qDebug() << "==== escaping variables ====";
for (Context *c : qAsConst(m->contextMap)) {
qDebug() << "Context" << c->name << ":";
- qDebug() << " Arguments escape" << c->argumentsCanEscape;
+ if (c->argumentsCanEscape)
+ qDebug() << " Arguments escape";
for (auto it = c->members.constBegin(); it != c->members.constEnd(); ++it) {
qDebug() << " " << it.key() << it.value().canEscape;
}