From 4e17c59cc2723c2f453c42e4efa9cb406b25e9d8 Mon Sep 17 00:00:00 2001 From: "Unknown W. Brackets" Date: Tue, 25 Jul 2023 19:11:27 -0700 Subject: [PATCH] riscv: Implement simple vec4 ops via floats. --- Core/MIPS/RiscV/RiscVCompLoadStore.cpp | 4 +-- Core/MIPS/RiscV/RiscVCompVec.cpp | 37 +++++++++++++++++++++++++- Core/MIPS/RiscV/RiscVRegCacheFPU.cpp | 26 ++++++++++++++++++ Core/MIPS/RiscV/RiscVRegCacheFPU.h | 3 +++ 4 files changed, 67 insertions(+), 3 deletions(-) diff --git a/Core/MIPS/RiscV/RiscVCompLoadStore.cpp b/Core/MIPS/RiscV/RiscVCompLoadStore.cpp index a1e0ae08c4..a543236610 100644 --- a/Core/MIPS/RiscV/RiscVCompLoadStore.cpp +++ b/Core/MIPS/RiscV/RiscVCompLoadStore.cpp @@ -125,7 +125,7 @@ void RiscVJit::CompIR_LoadShift(IRInst inst) { case IROp::Load32Left: case IROp::Load32Right: // Should not happen if the pass to split is active. - CompIR_Generic(inst); + DISABLE; break; default: @@ -256,7 +256,7 @@ void RiscVJit::CompIR_StoreShift(IRInst inst) { case IROp::Store32Left: case IROp::Store32Right: // Should not happen if the pass to split is active. - CompIR_Generic(inst); + DISABLE; break; default: diff --git a/Core/MIPS/RiscV/RiscVCompVec.cpp b/Core/MIPS/RiscV/RiscVCompVec.cpp index ac54192dd9..35dcd06b4e 100644 --- a/Core/MIPS/RiscV/RiscVCompVec.cpp +++ b/Core/MIPS/RiscV/RiscVCompVec.cpp @@ -55,13 +55,48 @@ void RiscVJit::CompIR_VecArith(IRInst inst) { switch (inst.op) { case IROp::Vec4Add: + fpr.Map4DirtyInIn(inst.dest, inst.src1, inst.src2); + for (int i = 0; i < 4; ++i) + FADD(32, fpr.R(inst.dest + i), fpr.R(inst.src1 + i), fpr.R(inst.src2 + i)); + break; + case IROp::Vec4Sub: + fpr.Map4DirtyInIn(inst.dest, inst.src1, inst.src2); + for (int i = 0; i < 4; ++i) + FSUB(32, fpr.R(inst.dest + i), fpr.R(inst.src1 + i), fpr.R(inst.src2 + i)); + break; + case IROp::Vec4Mul: + fpr.Map4DirtyInIn(inst.dest, inst.src1, inst.src2); + for (int i = 0; i < 4; ++i) + FMUL(32, fpr.R(inst.dest + i), fpr.R(inst.src1 + i), fpr.R(inst.src2 + i)); + break; + case IROp::Vec4Div: + fpr.Map4DirtyInIn(inst.dest, inst.src1, inst.src2); + for (int i = 0; i < 4; ++i) + FDIV(32, fpr.R(inst.dest + i), fpr.R(inst.src1 + i), fpr.R(inst.src2 + i)); + break; + case IROp::Vec4Scale: + fpr.SpillLock(inst.src2); + fpr.MapReg(inst.src2); + fpr.Map4DirtyIn(inst.dest, inst.src1); + fpr.ReleaseSpillLock(inst.src2); + for (int i = 0; i < 4; ++i) + FMUL(32, fpr.R(inst.dest + i), fpr.R(inst.src1 + i), fpr.R(inst.src2)); + break; + case IROp::Vec4Neg: + fpr.Map4DirtyIn(inst.dest, inst.src1); + for (int i = 0; i < 4; ++i) + FNEG(32, fpr.R(inst.dest + i), fpr.R(inst.src1 + i)); + break; + case IROp::Vec4Abs: - CompIR_Generic(inst); + fpr.Map4DirtyIn(inst.dest, inst.src1); + for (int i = 0; i < 4; ++i) + FABS(32, fpr.R(inst.dest + i), fpr.R(inst.src1 + i)); break; default: diff --git a/Core/MIPS/RiscV/RiscVRegCacheFPU.cpp b/Core/MIPS/RiscV/RiscVRegCacheFPU.cpp index f4ddba03ad..3277bcda89 100644 --- a/Core/MIPS/RiscV/RiscVRegCacheFPU.cpp +++ b/Core/MIPS/RiscV/RiscVRegCacheFPU.cpp @@ -211,6 +211,32 @@ void RiscVRegCacheFPU::MapDirtyInIn(IRRegIndex rd, IRRegIndex rs, IRRegIndex rt, ReleaseSpillLock(rt); } +void RiscVRegCacheFPU::Map4DirtyIn(IRRegIndex rdbase, IRRegIndex rsbase, bool avoidLoad) { + for (int i = 0; i < 4; ++i) + SpillLock(rdbase + i, rsbase + i); + bool load = !avoidLoad || (rdbase < rsbase + 4 && rdbase + 4 > rsbase); + for (int i = 0; i < 4; ++i) + MapReg(rdbase + i, load ? MIPSMap::DIRTY : MIPSMap::NOINIT); + for (int i = 0; i < 4; ++i) + MapReg(rsbase + i); + for (int i = 0; i < 4; ++i) + ReleaseSpillLock(rdbase + i, rsbase + i); +} + +void RiscVRegCacheFPU::Map4DirtyInIn(IRRegIndex rdbase, IRRegIndex rsbase, IRRegIndex rtbase, bool avoidLoad) { + for (int i = 0; i < 4; ++i) + SpillLock(rdbase + i, rsbase + i, rtbase + i); + bool load = !avoidLoad || (rdbase < rsbase + 4 && rdbase + 4 > rsbase) || (rdbase < rtbase + 4 && rdbase + 4 > rtbase); + for (int i = 0; i < 4; ++i) + MapReg(rdbase + i, load ? MIPSMap::DIRTY : MIPSMap::NOINIT); + for (int i = 0; i < 4; ++i) + MapReg(rsbase + i); + for (int i = 0; i < 4; ++i) + MapReg(rtbase + i); + for (int i = 0; i < 4; ++i) + ReleaseSpillLock(rdbase + i, rsbase + i, rtbase + i); +} + void RiscVRegCacheFPU::FlushRiscVReg(RiscVReg r) { _dbg_assert_(r >= F0 && r <= F31); int reg = r - F0; diff --git a/Core/MIPS/RiscV/RiscVRegCacheFPU.h b/Core/MIPS/RiscV/RiscVRegCacheFPU.h index c861c6599b..934e312ca7 100644 --- a/Core/MIPS/RiscV/RiscVRegCacheFPU.h +++ b/Core/MIPS/RiscV/RiscVRegCacheFPU.h @@ -64,6 +64,9 @@ public: void MapInIn(IRRegIndex rd, IRRegIndex rs); void MapDirtyIn(IRRegIndex rd, IRRegIndex rs, bool avoidLoad = true); void MapDirtyInIn(IRRegIndex rd, IRRegIndex rs, IRRegIndex rt, bool avoidLoad = true); + void Map4Dirty(IRRegIndex rdbase, bool avoidLoad = true); + void Map4DirtyIn(IRRegIndex rdbase, IRRegIndex rsbase, bool avoidLoad = true); + void Map4DirtyInIn(IRRegIndex rdbase, IRRegIndex rsbase, IRRegIndex rtbase, bool avoidLoad = true); void FlushAll(); void FlushR(IRRegIndex r); void DiscardR(IRRegIndex r);