aboutsummaryrefslogtreecommitdiffstats
path: root/src/qml/compiler/qv4compilercontext.cpp
diff options
context:
space:
mode:
authorLars Knoll <lars.knoll@qt.io>2018-04-03 21:15:18 +0200
committerLars Knoll <lars.knoll@qt.io>2018-05-02 14:17:25 +0000
commit9934514db7ec46f1c57d82e54e61c02b35bfd357 (patch)
tree422d1db77b9c65b52e559a38a4cf3e84adc9613c /src/qml/compiler/qv4compilercontext.cpp
parent851c28d140c398990513640047a20aab36ccc655 (diff)
Split out the generation of indices for locals and registers
Change-Id: I0e98ccba9ae3026cd8bfdc4cae100f280b5aa22c Reviewed-by: Simon Hausmann <simon.hausmann@qt.io>
Diffstat (limited to 'src/qml/compiler/qv4compilercontext.cpp')
-rw-r--r--src/qml/compiler/qv4compilercontext.cpp55
1 files changed, 34 insertions, 21 deletions
diff --git a/src/qml/compiler/qv4compilercontext.cpp b/src/qml/compiler/qv4compilercontext.cpp
index 1c583b5cf2..e2e978be7c 100644
--- a/src/qml/compiler/qv4compilercontext.cpp
+++ b/src/qml/compiler/qv4compilercontext.cpp
@@ -163,10 +163,12 @@ Context::ResolvedName Context::resolveName(const QString &name)
void Context::emitHeaderBytecode(Codegen *codegen)
{
+
using Instruction = Moth::Instruction;
Moth::BytecodeGenerator *bytecodeGenerator = codegen->generator();
- bool allVarsEscape = hasWith || hasTry || hasDirectEval;
+ setupFunctionIndices(bytecodeGenerator);
+
if (requiresExecutionContext ||
type == ContextType::Binding) { // we don't really need this for bindings, but we do for signal handlers, and we don't know if the code is a signal handler or not.
Instruction::CreateCallContext createContext;
@@ -181,26 +183,14 @@ void Context::emitHeaderBytecode(Codegen *codegen)
// variables in global code are properties of the global context object, not locals as with other functions.
if (type == ContextType::Function || type == ContextType::Binding) {
for (Context::MemberMap::iterator it = members.begin(), end = members.end(); it != end; ++it) {
- const QString &local = it.key();
- if (allVarsEscape)
- it->canEscape = true;
- if (it->canEscape) {
- it->index = locals.size();
- locals.append(local);
- if (it->type == Context::ThisFunctionName) {
- // move the name from the stack to the call context
- Instruction::LoadReg load;
- load.reg = CallData::Function;
- bytecodeGenerator->addInstruction(load);
- Instruction::StoreLocal store;
- store.index = it->index;
- bytecodeGenerator->addInstruction(store);
- }
- } else {
- if (it->type == Context::ThisFunctionName)
- it->index = CallData::Function;
- else
- it->index = bytecodeGenerator->newRegister();
+ if (it->canEscape && it->type == Context::ThisFunctionName) {
+ // move the function from the stack to the call context
+ Instruction::LoadReg load;
+ load.reg = CallData::Function;
+ bytecodeGenerator->addInstruction(load);
+ Instruction::StoreLocal store;
+ store.index = it->index;
+ bytecodeGenerator->addInstruction(store);
}
}
} else {
@@ -226,4 +216,27 @@ void Context::emitHeaderBytecode(Codegen *codegen)
}
}
+void Context::setupFunctionIndices(Moth::BytecodeGenerator *bytecodeGenerator)
+{
+ Q_ASSERT(locals.size() == 0);
+ Q_ASSERT(nRegisters == 0);
+ registerOffset = bytecodeGenerator->registerCount();
+
+ if (type == ContextType::Function || type == ContextType::Binding) {
+ for (Context::MemberMap::iterator it = members.begin(), end = members.end(); it != end; ++it) {
+ const QString &local = it.key();
+ if (it->canEscape) {
+ it->index = locals.size();
+ locals.append(local);
+ } else {
+ if (it->type == Context::ThisFunctionName)
+ it->index = CallData::Function;
+ else
+ it->index = bytecodeGenerator->newRegister();
+ }
+ }
+ }
+ nRegisters = bytecodeGenerator->registerCount() - registerOffset;
+}
+
QT_END_NAMESPACE