Path: blob/21.2-virgl/src/gallium/drivers/nouveau/codegen/nv50_ir_emit_gv100.h
4574 views
/*1* Copyright 2020 Red Hat Inc.2*3* Permission is hereby granted, free of charge, to any person obtaining a4* copy of this software and associated documentation files (the "Software"),5* to deal in the Software without restriction, including without limitation6* the rights to use, copy, modify, merge, publish, distribute, sublicense,7* and/or sell copies of the Software, and to permit persons to whom the8* Software is furnished to do so, subject to the following conditions:9*10* The above copyright notice and this permission notice shall be included in11* all copies or substantial portions of the Software.12*13* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR14* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,15* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL16* THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR17* OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,18* ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR19* OTHER DEALINGS IN THE SOFTWARE.20*/21#ifndef __NV50_IR_EMIT_GV100_H__22#define __NV50_IR_EMIT_GV100_H__23#include "codegen/nv50_ir_target_gv100.h"2425namespace nv50_ir {2627class CodeEmitterGV100 : public CodeEmitter {28public:29CodeEmitterGV100(TargetGV100 *target);3031virtual bool emitInstruction(Instruction *);32virtual uint32_t getMinEncodingSize(const Instruction *) const { return 16; }3334private:35const Program *prog;36const TargetGV100 *targ;37const Instruction *insn;3839virtual void prepareEmission(Program *);40virtual void prepareEmission(Function *);41virtual void prepareEmission(BasicBlock *);4243inline void emitInsn(uint32_t op) {44code[0] = op;45code[1] = 0;46code[2] = 0;47code[3] = 0;48if (insn->predSrc >= 0) {49emitField(12, 3, insn->getSrc(insn->predSrc)->rep()->reg.data.id);50emitField(15, 1, insn->cc == CC_NOT_P);51} else {52emitField(12, 3, 7);53}54};5556inline void emitField(int b, int s, uint64_t v) {57if (b >= 0) {58uint64_t m = ~0ULL >> (64 - s);59uint64_t d = v & m;60assert(!(v & ~m) || (v & ~m) == ~m);61if (b < 64 && b + s > 64) {62*(uint64_t *)&code[0] |= d << b;63*(uint64_t *)&code[2] |= d >> (64 - b);64} else {65*(uint64_t *)&code[(b/64*2)] |= d << (b & 0x3f);66}67}68};6970inline void emitABS(int pos, int src, bool supported)71{72if (insn->src(src).mod.abs()) {73assert(supported);74emitField(pos, 1, 1);75}76}7778inline void emitABS(int pos, int src)79{80emitABS(pos, src, true);81}8283inline void emitNEG(int pos, int src, bool supported) {84if (insn->src(src).mod.neg()) {85assert(supported);86emitField(pos, 1, 1);87}88}8990inline void emitNEG(int pos, int src) {91emitNEG(pos, src, true);92}9394inline void emitNOT(int pos) {95emitField(pos, 1, 0);96};9798inline void emitNOT(int pos, const ValueRef &ref) {99emitField(pos, 1, !!(ref.mod & Modifier(NV50_IR_MOD_NOT)));100}101102inline void emitSAT(int pos) {103emitField(pos, 1, insn->saturate);104}105106inline void emitRND(int rmp, RoundMode rnd, int rip) {107int rm = 0, ri = 0;108switch (rnd) {109case ROUND_NI: ri = 1;110case ROUND_N : rm = 0; break;111case ROUND_MI: ri = 1;112case ROUND_M : rm = 1; break;113case ROUND_PI: ri = 1;114case ROUND_P : rm = 2; break;115case ROUND_ZI: ri = 1;116case ROUND_Z : rm = 3; break;117default:118assert(!"invalid round mode");119break;120}121emitField(rip, 1, ri);122emitField(rmp, 2, rm);123}124125inline void emitRND(int pos) {126emitRND(pos, insn->rnd, -1);127}128129inline void emitFMZ(int pos, int len) {130emitField(pos, len, insn->dnz << 1 | insn->ftz);131}132133inline void emitPDIV(int pos) {134emitField(pos, 3, insn->postFactor + 4);135}136137inline void emitO(int pos) {138emitField(pos, 1, insn->getSrc(0)->reg.file == FILE_SHADER_OUTPUT);139}140141inline void emitP(int pos) {142emitField(pos, 1, insn->perPatch);143}144145inline void emitCond3(int pos, CondCode code) {146int data = 0;147148switch (code) {149case CC_FL : data = 0x00; break;150case CC_LTU:151case CC_LT : data = 0x01; break;152case CC_EQU:153case CC_EQ : data = 0x02; break;154case CC_LEU:155case CC_LE : data = 0x03; break;156case CC_GTU:157case CC_GT : data = 0x04; break;158case CC_NEU:159case CC_NE : data = 0x05; break;160case CC_GEU:161case CC_GE : data = 0x06; break;162case CC_TR : data = 0x07; break;163default:164assert(!"invalid cond3");165break;166}167168emitField(pos, 3, data);169}170171inline void emitCond4(int pos, CondCode code) {172int data = 0;173174switch (code) {175case CC_FL: data = 0x00; break;176case CC_LT: data = 0x01; break;177case CC_EQ: data = 0x02; break;178case CC_LE: data = 0x03; break;179case CC_GT: data = 0x04; break;180case CC_NE: data = 0x05; break;181case CC_GE: data = 0x06; break;182// case CC_NUM: data = 0x07; break;183// case CC_NAN: data = 0x08; break;184case CC_LTU: data = 0x09; break;185case CC_EQU: data = 0x0a; break;186case CC_LEU: data = 0x0b; break;187case CC_GTU: data = 0x0c; break;188case CC_NEU: data = 0x0d; break;189case CC_GEU: data = 0x0e; break;190case CC_TR: data = 0x0f; break;191default:192assert(!"invalid cond4");193break;194}195196emitField(pos, 4, data);197}198199inline void emitSYS(int pos, const Value *val) {200int id = val ? val->reg.data.id : -1;201202switch (id) {203case SV_LANEID : id = 0x00; break;204case SV_VERTEX_COUNT : id = 0x10; break;205case SV_INVOCATION_ID : id = 0x11; break;206case SV_THREAD_KILL : id = 0x13; break;207case SV_INVOCATION_INFO: id = 0x1d; break;208case SV_COMBINED_TID : id = 0x20; break;209case SV_TID : id = 0x21 + val->reg.data.sv.index; break;210case SV_CTAID : id = 0x25 + val->reg.data.sv.index; break;211case SV_LANEMASK_EQ : id = 0x38; break;212case SV_LANEMASK_LT : id = 0x39; break;213case SV_LANEMASK_LE : id = 0x3a; break;214case SV_LANEMASK_GT : id = 0x3b; break;215case SV_LANEMASK_GE : id = 0x3c; break;216case SV_CLOCK : id = 0x50 + val->reg.data.sv.index; break;217default:218assert(!"invalid system value");219id = 0;220break;221}222223emitField(pos, 8, id);224}225226inline void emitSYS(int pos, const ValueRef &ref) {227emitSYS(pos, ref.get() ? ref.rep() : (const Value *)NULL);228}229230inline void emitBTS(int pos, const Value *val) {231if (val->inFile(FILE_THREAD_STATE)) {232TSSemantic ts = val->reg.data.ts == TS_PQUAD_MACTIVE ? TS_MACTIVE : val->reg.data.ts;233emitField(pos, 5, ts | 0x10);234} else {235emitField(pos, 5, val->reg.data.id);236}237}238239inline void emitBTS(int pos, const ValueRef &ref) {240emitBTS(pos, ref.get() ? ref.rep() : (const Value *)NULL);241}242243inline void emitBTS(int pos, const ValueDef &def) {244emitBTS(pos, def.get() ? def.rep() : (const Value *)NULL);245}246247inline void emitGPR(int pos, const Value *val, int off) {248emitField(pos, 8, val && !val->inFile(FILE_FLAGS) ?249val->reg.data.id + off: 255);250}251252inline void emitGPR(int pos, const Value *v) {253emitGPR(pos, v, 0);254}255256inline void emitGPR(int pos) {257emitGPR(pos, (const Value *)NULL);258}259260inline void emitGPR(int pos, const ValueRef &ref) {261emitGPR(pos, ref.get() ? ref.rep() : (const Value *)NULL);262}263264inline void emitGPR(int pos, const ValueRef *ref) {265emitGPR(pos, ref ? ref->rep() : (const Value *)NULL);266}267268inline void emitGPR(int pos, const ValueDef &def) {269emitGPR(pos, def.get() ? def.rep() : (const Value *)NULL);270}271272inline void emitGPR(int pos, const ValueDef &def, int off) {273emitGPR(pos, def.get() ? def.rep() : (const Value *)NULL, off);274}275276inline void emitPRED(int pos, const Value *val) {277emitField(pos, 3, val ? val->reg.data.id : 7);278};279280inline void emitPRED(int pos) {281emitPRED(pos, (const Value *)NULL);282}283284inline void emitPRED(int pos, const ValueRef &ref) {285emitPRED(pos, ref.get() ? ref.rep() : (const Value *)NULL);286}287288inline void emitPRED(int pos, const ValueDef &def) {289emitPRED(pos, def.get() ? def.rep() : (const Value *)NULL);290}291292inline void emitCBUF(int buf, int gpr, int off, int len, int align,293const ValueRef &ref) {294const Value *v = ref.get();295const Symbol *s = v->asSym();296297assert(!(s->reg.data.offset & ((1 << align) - 1)));298299emitField(buf, 5, v->reg.fileIndex);300if (gpr >= 0)301emitGPR(gpr, ref.getIndirect(0));302emitField(off, 16, s->reg.data.offset);303}304305inline void emitIMMD(int pos, int len, const ValueRef &ref) {306const ImmediateValue *imm = ref.get()->asImm();307uint32_t val = imm->reg.data.u32;308309if (insn->sType == TYPE_F64) {310assert(!(imm->reg.data.u64 & 0x00000000ffffffffULL));311val = imm->reg.data.u64 >> 32;312}313314emitField(pos, len, val);315}316317inline void emitADDR(int gpr, int off, int len, int shr,318const ValueRef &ref) {319const Value *v = ref.get();320assert(!(v->reg.data.offset & ((1 << shr) - 1)));321if (gpr >= 0)322emitGPR(gpr, ref.getIndirect(0));323emitField(off, len, v->reg.data.offset >> shr);324}325326inline void emitFormA(uint16_t op, uint8_t forms, int src0, int src1, int src2);327inline void emitFormA_RRR(uint16_t op, int src1, int src2);328inline void emitFormA_RRI(uint16_t op, int src1, int src2);329inline void emitFormA_RRC(uint16_t op, int src1, int src2);330inline void emitFormA_I32(int src);331332void emitBRA();333void emitEXIT();334void emitKILL();335void emitNOP();336void emitWARPSYNC();337338void emitCS2R();339void emitF2F();340void emitF2I();341void emitFRND();342void emitI2F();343void emitMOV();344void emitPRMT();345void emitS2R();346void emitSEL();347void emitSHFL();348349void emitFADD();350void emitFFMA();351void emitFMNMX();352void emitFMUL();353void emitFSET_BF();354void emitFSETP();355void emitFSWZADD();356void emitMUFU();357358void emitDADD();359void emitDFMA();360void emitDMUL();361void emitDSETP();362363void emitBMSK();364void emitBREV();365void emitFLO();366void emitIABS();367void emitIADD3();368void emitIMAD();369void emitIMAD_WIDE();370void emitISETP();371void emitLEA();372void emitLOP3_LUT();373void emitPOPC();374void emitSGXT();375void emitSHF();376377void emitALD();378void emitAST();379void emitATOM();380void emitATOMS();381void emitIPA();382void emitISBERD();383void emitLDSTc(int, int);384void emitLDSTs(int, DataType);385void emitLD();386void emitLDC();387void emitLDL();388void emitLDS();389void emitOUT();390void emitRED();391void emitST();392void emitSTL();393void emitSTS();394395void emitTEXs(int);396void emitTEX();397void emitTLD();398void emitTLD4();399void emitTMML();400void emitTXD();401void emitTXQ();402403void emitSUHandle(const int);404void emitSUTarget();405void emitSUATOM();406void emitSULD();407void emitSUST();408409void emitAL2P();410void emitBAR();411void emitCCTL();412void emitMEMBAR();413void emitPIXLD();414void emitPLOP3_LUT();415void emitVOTE();416};417418};419#endif420421422