diff options
author | Simon Hausmann <simon.hausmann@qt.io> | 2017-02-07 13:22:32 +0100 |
---|---|---|
committer | Simon Hausmann <simon.hausmann@qt.io> | 2017-02-08 12:16:40 +0000 |
commit | be92f31b7eb2a689c8a12fc0e193878a84c4532e (patch) | |
tree | a93ab442ac5d199d0a4d82e7f29d923e3ababddc /src/qml/jit | |
parent | aa76e89b4d66e80c66999680e6a3db00c8a00b33 (diff) |
Enable cross-compiling binops from 32-bit host 64-bit target
Move the #if CPU(X86) specific bits into a template specialization, so
that we won't try to call 32-bit specific methods on the assembler when
targeting a 64-bit architecture.
Change-Id: I3b7e6c2c77d8a34ef50913cbfd34dad2c3199923
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: Lars Knoll <lars.knoll@qt.io>
Diffstat (limited to 'src/qml/jit')
-rw-r--r-- | src/qml/jit/qv4binop.cpp | 193 |
1 files changed, 135 insertions, 58 deletions
diff --git a/src/qml/jit/qv4binop.cpp b/src/qml/jit/qv4binop.cpp index a09f3f8449..988425d73f 100644 --- a/src/qml/jit/qv4binop.cpp +++ b/src/qml/jit/qv4binop.cpp @@ -41,8 +41,128 @@ #if ENABLE(ASSEMBLER) -using namespace QV4; -using namespace JIT; +QT_BEGIN_NAMESPACE + +namespace QV4 { +namespace JIT { + +template <typename JITAssembler> +struct ArchitectureSpecificBinaryOperation +{ + using FPRegisterID = typename JITAssembler::FPRegisterID; + + static bool doubleAdd(JITAssembler *as, IR::Expr *lhs, IR::Expr *rhs, FPRegisterID targetReg) + { + Q_UNUSED(as); + Q_UNUSED(lhs); + Q_UNUSED(rhs); + Q_UNUSED(targetReg); + return false; + } + static bool doubleMul(JITAssembler *as, IR::Expr *lhs, IR::Expr *rhs, FPRegisterID targetReg) + { + Q_UNUSED(as); + Q_UNUSED(lhs); + Q_UNUSED(rhs); + Q_UNUSED(targetReg); + return false; + } + static bool doubleSub(JITAssembler *as, IR::Expr *lhs, IR::Expr *rhs, FPRegisterID targetReg) + { + Q_UNUSED(as); + Q_UNUSED(lhs); + Q_UNUSED(rhs); + Q_UNUSED(targetReg); + return false; + } + static bool doubleDiv(JITAssembler *as, IR::Expr *lhs, IR::Expr *rhs, FPRegisterID targetReg) + { + Q_UNUSED(as); + Q_UNUSED(lhs); + Q_UNUSED(rhs); + Q_UNUSED(targetReg); + return false; + } +}; + +#if CPU(X86) +template <> +struct ArchitectureSpecificBinaryOperation<Assembler<AssemblerTargetConfiguration<JSC::MacroAssemblerX86, NoOperatingSystemSpecialization>>> +{ + using JITAssembler = Assembler<AssemblerTargetConfiguration<JSC::MacroAssemblerX86, NoOperatingSystemSpecialization>>; + using FPRegisterID = JITAssembler::FPRegisterID; + using Address = JITAssembler::Address; + + static bool doubleAdd(JITAssembler *as, IR::Expr *lhs, IR::Expr *rhs, FPRegisterID targetReg) + { + if (IR::Const *c = rhs->asConst()) { // Y = X + constant -> Y = X; Y += [constant-address] + as->moveDouble(as->toDoubleRegister(lhs, targetReg), targetReg); + Address addr = as->loadConstant(c, JITAssembler::ScratchRegister); + as->addDouble(addr, targetReg); + return true; + } + if (IR::Temp *t = rhs->asTemp()) { // Y = X + [temp-memory-address] -> Y = X; Y += [temp-memory-address] + if (t->kind != IR::Temp::PhysicalRegister) { + as->moveDouble(as->toDoubleRegister(lhs, targetReg), targetReg); + as->addDouble(as->loadTempAddress(t), targetReg); + return true; + } + } + return false; + } + static bool doubleMul(JITAssembler *as, IR::Expr *lhs, IR::Expr *rhs, FPRegisterID targetReg) + { + if (IR::Const *c = rhs->asConst()) { // Y = X * constant -> Y = X; Y *= [constant-address] + as->moveDouble(as->toDoubleRegister(lhs, targetReg), targetReg); + Address addr = as->loadConstant(c, JITAssembler::ScratchRegister); + as->mulDouble(addr, targetReg); + return true; + } + if (IR::Temp *t = rhs->asTemp()) { // Y = X * [temp-memory-address] -> Y = X; Y *= [temp-memory-address] + if (t->kind != IR::Temp::PhysicalRegister) { + as->moveDouble(as->toDoubleRegister(lhs, targetReg), targetReg); + as->mulDouble(as->loadTempAddress(t), targetReg); + return true; + } + } + return false; + } + static bool doubleSub(JITAssembler *as, IR::Expr *lhs, IR::Expr *rhs, FPRegisterID targetReg) + { + if (IR::Const *c = rhs->asConst()) { // Y = X - constant -> Y = X; Y -= [constant-address] + as->moveDouble(as->toDoubleRegister(lhs, targetReg), targetReg); + Address addr = as->loadConstant(c, JITAssembler::ScratchRegister); + as->subDouble(addr, targetReg); + return true; + } + if (IR::Temp *t = rhs->asTemp()) { // Y = X - [temp-memory-address] -> Y = X; Y -= [temp-memory-address] + if (t->kind != IR::Temp::PhysicalRegister) { + as->moveDouble(as->toDoubleRegister(lhs, targetReg), targetReg); + as->subDouble(as->loadTempAddress(t), targetReg); + return true; + } + } + return false; + } + static bool doubleDiv(JITAssembler *as, IR::Expr *lhs, IR::Expr *rhs, FPRegisterID targetReg) + { + if (IR::Const *c = rhs->asConst()) { // Y = X / constant -> Y = X; Y /= [constant-address] + as->moveDouble(as->toDoubleRegister(lhs, targetReg), targetReg); + Address addr = as->loadConstant(c, JITAssembler::ScratchRegister); + as->divDouble(addr, targetReg); + return true; + } + if (IR::Temp *t = rhs->asTemp()) { // Y = X / [temp-memory-address] -> Y = X; Y /= [temp-memory-address] + if (t->kind != IR::Temp::PhysicalRegister) { + as->moveDouble(as->toDoubleRegister(lhs, targetReg), targetReg); + as->divDouble(as->loadTempAddress(t), targetReg); + return true; + } + } + return false; + } +}; +#endif #define OP(op) \ { "Runtime::" isel_stringIfy(op), offsetof(QV4::Runtime, op), INT_MIN, 0, 0, QV4::Runtime::Method_##op##_NeedsExceptionCheck } @@ -162,21 +282,9 @@ void Binop<JITAssembler>::doubleBinop(IR::Expr *lhs, IR::Expr *rhs, IR::Expr *ta if (lhs->asConst()) std::swap(lhs, rhs); // Y = constant + X -> Y = X + constant -#if CPU(X86) - if (IR::Const *c = rhs->asConst()) { // Y = X + constant -> Y = X; Y += [constant-address] - as->moveDouble(as->toDoubleRegister(lhs, targetReg), targetReg); - Address addr = as->loadConstant(c, JITAssembler::ScratchRegister); - as->addDouble(addr, targetReg); + if (ArchitectureSpecificBinaryOperation<JITAssembler>::doubleAdd(as, lhs, rhs, targetReg)) break; - } - if (IR::Temp *t = rhs->asTemp()) { // Y = X + [temp-memory-address] -> Y = X; Y += [temp-memory-address] - if (t->kind != IR::Temp::PhysicalRegister) { - as->moveDouble(as->toDoubleRegister(lhs, targetReg), targetReg); - as->addDouble(as->loadTempAddress(t), targetReg); - break; - } - } -#endif + as->addDouble(as->toDoubleRegister(lhs, JITAssembler::FPGpr0), as->toDoubleRegister(rhs, JITAssembler::FPGpr1), targetReg); break; @@ -184,40 +292,16 @@ void Binop<JITAssembler>::doubleBinop(IR::Expr *lhs, IR::Expr *rhs, IR::Expr *ta if (lhs->asConst()) std::swap(lhs, rhs); // Y = constant * X -> Y = X * constant -#if CPU(X86) - if (IR::Const *c = rhs->asConst()) { // Y = X * constant -> Y = X; Y *= [constant-address] - as->moveDouble(as->toDoubleRegister(lhs, targetReg), targetReg); - Address addr = as->loadConstant(c, JITAssembler::ScratchRegister); - as->mulDouble(addr, targetReg); + if (ArchitectureSpecificBinaryOperation<JITAssembler>::doubleMul(as, lhs, rhs, targetReg)) break; - } - if (IR::Temp *t = rhs->asTemp()) { // Y = X * [temp-memory-address] -> Y = X; Y *= [temp-memory-address] - if (t->kind != IR::Temp::PhysicalRegister) { - as->moveDouble(as->toDoubleRegister(lhs, targetReg), targetReg); - as->mulDouble(as->loadTempAddress(t), targetReg); - break; - } - } -#endif + as->mulDouble(as->toDoubleRegister(lhs, JITAssembler::FPGpr0), as->toDoubleRegister(rhs, JITAssembler::FPGpr1), targetReg); break; case IR::OpSub: -#if CPU(X86) - if (IR::Const *c = rhs->asConst()) { // Y = X - constant -> Y = X; Y -= [constant-address] - as->moveDouble(as->toDoubleRegister(lhs, targetReg), targetReg); - Address addr = as->loadConstant(c, JITAssembler::ScratchRegister); - as->subDouble(addr, targetReg); + if (ArchitectureSpecificBinaryOperation<JITAssembler>::doubleSub(as, lhs, rhs, targetReg)) break; - } - if (IR::Temp *t = rhs->asTemp()) { // Y = X - [temp-memory-address] -> Y = X; Y -= [temp-memory-address] - if (t->kind != IR::Temp::PhysicalRegister) { - as->moveDouble(as->toDoubleRegister(lhs, targetReg), targetReg); - as->subDouble(as->loadTempAddress(t), targetReg); - break; - } - } -#endif + if (rhs->asTemp() && rhs->asTemp()->kind == IR::Temp::PhysicalRegister && targetTemp && targetTemp->kind == IR::Temp::PhysicalRegister @@ -231,21 +315,8 @@ void Binop<JITAssembler>::doubleBinop(IR::Expr *lhs, IR::Expr *rhs, IR::Expr *ta break; case IR::OpDiv: -#if CPU(X86) - if (IR::Const *c = rhs->asConst()) { // Y = X / constant -> Y = X; Y /= [constant-address] - as->moveDouble(as->toDoubleRegister(lhs, targetReg), targetReg); - Address addr = as->loadConstant(c, JITAssembler::ScratchRegister); - as->divDouble(addr, targetReg); + if (ArchitectureSpecificBinaryOperation<JITAssembler>::doubleDiv(as, lhs, rhs, targetReg)) break; - } - if (IR::Temp *t = rhs->asTemp()) { // Y = X / [temp-memory-address] -> Y = X; Y /= [temp-memory-address] - if (t->kind != IR::Temp::PhysicalRegister) { - as->moveDouble(as->toDoubleRegister(lhs, targetReg), targetReg); - as->divDouble(as->loadTempAddress(t), targetReg); - break; - } - } -#endif if (rhs->asTemp() && rhs->asTemp()->kind == IR::Temp::PhysicalRegister && targetTemp @@ -581,4 +652,10 @@ template struct QV4::JIT::Binop<QV4::JIT::Assembler<DefaultAssemblerTargetConfig template struct QV4::JIT::Binop<QV4::JIT::Assembler<AssemblerTargetConfiguration<JSC::MacroAssemblerARMv7, NoOperatingSystemSpecialization>>>; #endif +} // end of namespace JIT +} // end of namespace QV4 + +QT_END_NAMESPACE + + #endif |