diff options
Diffstat (limited to 'src/qml/compiler/qv4compilerscanfunctions.cpp')
| -rw-r--r-- | src/qml/compiler/qv4compilerscanfunctions.cpp | 38 |
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; } |
