diff options
author | Simon Hausmann <simon.hausmann@digia.com> | 2014-02-11 11:08:11 +0100 |
---|---|---|
committer | Simon Hausmann <simon.hausmann@digia.com> | 2014-02-11 12:00:31 +0100 |
commit | 7c9497a6d47a02d961baef3993ba4cf4267ec607 (patch) | |
tree | 335fae3e9e3a84d33310efca23f1d6993265805b /src/qml/compiler | |
parent | 67ba88947f57ab2d1859bbeb96c6dcba020561b1 (diff) | |
parent | 6c840c70d61c3ae277b60a024a086215c743e5b3 (diff) |
Merge remote-tracking branch 'origin/stable' into dev
Conflicts:
src/qml/compiler/qv4ssa.cpp
src/qml/jsruntime/qv4arrayobject.cpp
src/qml/jsruntime/qv4context.cpp
Change-Id: Ied5b23bec4dc14abe51127c507aed668f855c1e1
Diffstat (limited to 'src/qml/compiler')
-rw-r--r-- | src/qml/compiler/qv4isel_masm.cpp | 2 | ||||
-rw-r--r-- | src/qml/compiler/qv4isel_masm_p.h | 4 | ||||
-rw-r--r-- | src/qml/compiler/qv4regalloc.cpp | 34 | ||||
-rw-r--r-- | src/qml/compiler/qv4ssa.cpp | 9 |
4 files changed, 38 insertions, 11 deletions
diff --git a/src/qml/compiler/qv4isel_masm.cpp b/src/qml/compiler/qv4isel_masm.cpp index a1145c2f10..c89b108309 100644 --- a/src/qml/compiler/qv4isel_masm.cpp +++ b/src/qml/compiler/qv4isel_masm.cpp @@ -122,7 +122,7 @@ static const Assembler::RegisterID calleeSavedRegisters[] = { #if CPU(X86) static const Assembler::RegisterID calleeSavedRegisters[] = { - // Not used: JSC::X86Registers::ebx, + JSC::X86Registers::ebx, // temporary register JSC::X86Registers::esi, // ContextRegister JSC::X86Registers::edi // LocalsRegister }; diff --git a/src/qml/compiler/qv4isel_masm_p.h b/src/qml/compiler/qv4isel_masm_p.h index b1e981533b..76fe6c6391 100644 --- a/src/qml/compiler/qv4isel_masm_p.h +++ b/src/qml/compiler/qv4isel_masm_p.h @@ -981,6 +981,10 @@ public: prepareRelativeCall(function, this); loadArgumentOnStackOrRegister<0>(arg1); +#if OS(LINUX) && CPU(X86) && (defined(__PIC__) || defined(__PIE__)) + load32(Address(StackFrameRegister, -sizeof(void*)), JSC::X86Registers::ebx); // restore the GOT ptr +#endif + callAbsolute(functionName, function); if (stackSpaceNeeded) diff --git a/src/qml/compiler/qv4regalloc.cpp b/src/qml/compiler/qv4regalloc.cpp index bc88d5849a..cc9ce4fc96 100644 --- a/src/qml/compiler/qv4regalloc.cpp +++ b/src/qml/compiler/qv4regalloc.cpp @@ -114,6 +114,13 @@ public: return false; } + bool isUsedAt(const Temp &t, int position) { + foreach (const Use &use, uses(t)) + if (use.pos == position) + return true; + return false; + } + int def(const Temp &t) const { Q_ASSERT(_defs[t].isValid()); return _defs[t].defStmt; @@ -746,17 +753,17 @@ private: os << "Intervals live at the start of L" << bb->index << ":" << endl; if (_liveAtStart[bb].isEmpty()) os << "\t(none)" << endl; - foreach (const LifeTimeInterval &i, _liveAtStart[bb]) { + foreach (const LifeTimeInterval *i, _liveAtStart[bb]) { os << "\t"; - i.dump(os); + i->dump(os); os << endl; } os << "Intervals live at the end of L" << bb->index << ":" << endl; if (_liveAtEnd[bb].isEmpty()) os << "\t(none)" << endl; - foreach (const LifeTimeInterval &i, _liveAtEnd[bb]) { + foreach (const LifeTimeInterval *i, _liveAtEnd[bb]) { os << "\t"; - i.dump(os); + i->dump(os); os << endl; } #endif @@ -1069,6 +1076,8 @@ RegisterAllocator::RegisterAllocator(const QVector<int> &normalRegisters, const : _normalRegisters(normalRegisters) , _fpRegisters(fpRegisters) { + Q_ASSERT(normalRegisters.size() >= 2); + Q_ASSERT(fpRegisters.size() >= 2); } RegisterAllocator::~RegisterAllocator() @@ -1416,9 +1425,20 @@ void RegisterAllocator::allocateBlockedReg(LifeTimeInterval ¤t, const int #endif // DEBUG_REGALLOC current.setReg(reg); _lastAssignedRegister.insert(current.temp(), reg); - Q_ASSERT(nextUseRangeForReg[reg]); - Q_ASSERT(!nextUseRangeForReg[reg]->isFixedInterval()); - split(*nextUseRangeForReg[reg], position); + LifeTimeInterval *nextUse = nextUseRangeForReg[reg]; + Q_ASSERT(nextUse); + Q_ASSERT(!nextUse->isFixedInterval()); + + if (_info->isUsedAt(nextUse->temp(), position)) { + Q_ASSERT(!_info->isUsedAt(current.temp(), position)); + // the register is used (as an incoming parameter) at the current position, so split + // the interval immediately after the (use at the) current position + split(*nextUse, position + 1); + } else { + // the register was used before the current position + split(*nextUse, position); + } + splitInactiveAtEndOfLifetimeHole(reg, needsFPReg, position); // make sure that current does not intersect with the fixed interval for reg diff --git a/src/qml/compiler/qv4ssa.cpp b/src/qml/compiler/qv4ssa.cpp index 3ffaca5134..8f3e186cc7 100644 --- a/src/qml/compiler/qv4ssa.cpp +++ b/src/qml/compiler/qv4ssa.cpp @@ -3711,9 +3711,12 @@ void LifeTimeInterval::dump(QTextStream &out) const { } bool LifeTimeInterval::lessThan(const LifeTimeInterval &r1, const LifeTimeInterval &r2) { - if (r1._ranges.first().start == r2._ranges.first().start) - return r1._ranges.last().end < r2._ranges.last().end; - else + if (r1._ranges.first().start == r2._ranges.first().start) { + if (r1.isSplitFromInterval() == r2.isSplitFromInterval()) + return r1._ranges.last().end < r2._ranges.last().end; + else + return r1.isSplitFromInterval(); + } else return r1._ranges.first().start < r2._ranges.first().start; } |