[Mesa-dev] [PATCH 4/5] nv50/ir: use suld.p on GM107+
Rhys Perry
pendingchaos02 at gmail.com
Fri Jun 15 20:24:53 UTC 2018
Signed-off-by: Rhys Perry <pendingchaos02 at gmail.com>
---
src/gallium/drivers/nouveau/codegen/nv50_ir.h | 4 +++
.../drivers/nouveau/codegen/nv50_ir_emit_gm107.cpp | 34 ++++++++++++++--------
.../nouveau/codegen/nv50_ir_lowering_nvc0.cpp | 3 --
.../drivers/nouveau/codegen/nv50_ir_peephole.cpp | 27 +++++++++++++++++
.../drivers/nouveau/codegen/nv50_ir_print.cpp | 17 +++++++++++
5 files changed, 70 insertions(+), 15 deletions(-)
diff --git a/src/gallium/drivers/nouveau/codegen/nv50_ir.h b/src/gallium/drivers/nouveau/codegen/nv50_ir.h
index f4f3c70888..a13bc6a6bb 100644
--- a/src/gallium/drivers/nouveau/codegen/nv50_ir.h
+++ b/src/gallium/drivers/nouveau/codegen/nv50_ir.h
@@ -221,6 +221,10 @@ enum operation
#define NV50_IR_SUBOP_SULD_ZERO 0
#define NV50_IR_SUBOP_SULD_TRAP 1
#define NV50_IR_SUBOP_SULD_SDCL 3
+// These three are only for GM107+.
+#define NV50_IR_SUBOP_SULDP_RGBA (0 << 2)
+#define NV50_IR_SUBOP_SULDP_RG (1 << 2)
+#define NV50_IR_SUBOP_SULDP_R (2 << 2)
#define NV50_IR_SUBOP_SUBFM_3D 1
#define NV50_IR_SUBOP_SUCLAMP_2D 0x10
#define NV50_IR_SUBOP_SUCLAMP_SD(r, d) (( 0 + (r)) | ((d == 2) ? 0x10 : 0))
diff --git a/src/gallium/drivers/nouveau/codegen/nv50_ir_emit_gm107.cpp b/src/gallium/drivers/nouveau/codegen/nv50_ir_emit_gm107.cpp
index 26826d6360..f1db0674b1 100644
--- a/src/gallium/drivers/nouveau/codegen/nv50_ir_emit_gm107.cpp
+++ b/src/gallium/drivers/nouveau/codegen/nv50_ir_emit_gm107.cpp
@@ -3042,26 +3042,36 @@ void
CodeEmitterGM107::emitSULDx()
{
const TexInstruction *insn = this->insn->asTex();
- int type = 0;
emitInsn(0xeb000000);
if (insn->op == OP_SULDB)
emitField(0x34, 1, 1);
emitSUTarget();
- switch (insn->dType) {
- case TYPE_S8: type = 1; break;
- case TYPE_U16: type = 2; break;
- case TYPE_S16: type = 3; break;
- case TYPE_U32: type = 4; break;
- case TYPE_U64: type = 5; break;
- case TYPE_B128: type = 6; break;
- default:
- assert(insn->dType == TYPE_U8);
- break;
+ if (insn->op == OP_SULDB) {
+ int type = 0;
+ switch (insn->dType) {
+ case TYPE_S8: type = 1; break;
+ case TYPE_U16: type = 2; break;
+ case TYPE_S16: type = 3; break;
+ case TYPE_U32: type = 4; break;
+ case TYPE_U64: type = 5; break;
+ case TYPE_B128: type = 6; break;
+ default:
+ assert(insn->dType == TYPE_U8);
+ break;
+ }
+ emitField(0x14, 3, type);
+ } else {
+ int type = 0;
+ switch (insn->subOp & 0xc) {
+ case NV50_IR_SUBOP_SULDP_R: type = 0x1; break;
+ case NV50_IR_SUBOP_SULDP_RG: type = 0x3; break;
+ case NV50_IR_SUBOP_SULDP_RGBA: type = 0xf; break;
+ }
+ emitField(0x14, 4, type);
}
emitLDSTc(0x18);
- emitField(0x14, 3, type);
emitGPR (0x00, insn->def(0));
emitGPR (0x08, insn->src(0));
diff --git a/src/gallium/drivers/nouveau/codegen/nv50_ir_lowering_nvc0.cpp b/src/gallium/drivers/nouveau/codegen/nv50_ir_lowering_nvc0.cpp
index 29f674b451..f7ffa5627c 100644
--- a/src/gallium/drivers/nouveau/codegen/nv50_ir_lowering_nvc0.cpp
+++ b/src/gallium/drivers/nouveau/codegen/nv50_ir_lowering_nvc0.cpp
@@ -2397,9 +2397,6 @@ NVC0LoweringPass::handleSurfaceOpGM107(TexInstruction *su)
{
processSurfaceCoordsGM107(su);
- if (su->op == OP_SULDP)
- convertSurfaceFormat(su);
-
if (su->op == OP_SUREDP) {
Value *def = su->getDef(0);
diff --git a/src/gallium/drivers/nouveau/codegen/nv50_ir_peephole.cpp b/src/gallium/drivers/nouveau/codegen/nv50_ir_peephole.cpp
index 39177bd044..65db2acfa2 100644
--- a/src/gallium/drivers/nouveau/codegen/nv50_ir_peephole.cpp
+++ b/src/gallium/drivers/nouveau/codegen/nv50_ir_peephole.cpp
@@ -1671,6 +1671,7 @@ private:
void handleCVT_EXTBF(Instruction *);
void handleSUCLAMP(Instruction *);
void handleNEG(Instruction *);
+ void handleSULDP(Instruction *);
BuildUtil bld;
};
@@ -2175,6 +2176,29 @@ AlgebraicOpt::handleNEG(Instruction *i) {
}
}
+void
+AlgebraicOpt::handleSULDP(Instruction *i) {
+ if (prog->getTarget()->getChipset() < NVISA_GM107_CHIPSET)
+ return;
+
+ int max = 0;
+ for (int d = 0; i->defExists(d); d++) {
+ if (i->getDef(d)->uses.size() > 0)
+ max = MAX2(max, d);
+ }
+
+ if (max == 0) {
+ i->subOp |= NV50_IR_SUBOP_SULDP_R;
+ i->setDef(1, NULL);
+ i->setDef(2, NULL);
+ i->setDef(3, NULL);
+ } else if (max == 1) {
+ i->subOp |= NV50_IR_SUBOP_SULDP_RG;
+ i->setDef(2, NULL);
+ i->setDef(3, NULL);
+ }
+}
+
bool
AlgebraicOpt::visit(BasicBlock *bb)
{
@@ -2215,6 +2239,9 @@ AlgebraicOpt::visit(BasicBlock *bb)
case OP_NEG:
handleNEG(i);
break;
+ case OP_SULDP:
+ handleSULDP(i);
+ break;
default:
break;
}
diff --git a/src/gallium/drivers/nouveau/codegen/nv50_ir_print.cpp b/src/gallium/drivers/nouveau/codegen/nv50_ir_print.cpp
index cbb21f5f72..8a9e0af4fd 100644
--- a/src/gallium/drivers/nouveau/codegen/nv50_ir_print.cpp
+++ b/src/gallium/drivers/nouveau/codegen/nv50_ir_print.cpp
@@ -240,6 +240,16 @@ static const char *barOpStr[] =
"sync", "arrive", "red and", "red or", "red popc"
};
+static const char *suldOpStr[] =
+{
+ "zero", "trap", "sdcl"
+};
+
+static const char *suldSwizzleOpStr[] =
+{
+ "rgba", "rg", "r"
+};
+
static const char *DataTypeStr[] =
{
"-",
@@ -624,6 +634,13 @@ void Instruction::print() const
if (subOp < ARRAY_SIZE(barOpStr))
PRINT("%s ", barOpStr[subOp]);
break;
+ case OP_SULDB:
+ case OP_SULDP:
+ if ((subOp & 0x3) < ARRAY_SIZE(suldOpStr))
+ PRINT("%s ", suldOpStr[subOp & 0x3]);
+ if (op == OP_SULDP && subOp >> 2 < (int)ARRAY_SIZE(suldSwizzleOpStr))
+ PRINT("%s ", suldSwizzleOpStr[subOp >> 2]);
+ break;
default:
if (subOp)
PRINT("(SUBOP:%u) ", subOp);
--
2.14.4
More information about the mesa-dev
mailing list