diff --git a/llvm/lib/Target/SPIRV/SPIRVInstrInfo.cpp b/llvm/lib/Target/SPIRV/SPIRVInstrInfo.cpp --- a/llvm/lib/Target/SPIRV/SPIRVInstrInfo.cpp +++ b/llvm/lib/Target/SPIRV/SPIRVInstrInfo.cpp @@ -245,9 +245,8 @@ } bool SPIRVInstrInfo::expandPostRAPseudo(MachineInstr &MI) const { - if (MI.getOpcode() == SPIRV::GET_ID || MI.getOpcode() == SPIRV::GET_fID || - MI.getOpcode() == SPIRV::GET_pID || MI.getOpcode() == SPIRV::GET_vfID || - MI.getOpcode() == SPIRV::GET_vID) { + if (MI.getOpcode() == SPIRV::GET_ID || MI.getOpcode() == SPIRV::GET_SID || + MI.getOpcode() == SPIRV::GET_VID) { auto &MRI = MI.getMF()->getRegInfo(); MRI.replaceRegWith(MI.getOperand(0).getReg(), MI.getOperand(1).getReg()); MI.eraseFromParent(); diff --git a/llvm/lib/Target/SPIRV/SPIRVInstrInfo.td b/llvm/lib/Target/SPIRV/SPIRVInstrInfo.td --- a/llvm/lib/Target/SPIRV/SPIRVInstrInfo.td +++ b/llvm/lib/Target/SPIRV/SPIRVInstrInfo.td @@ -15,13 +15,10 @@ // Codegen only metadata instructions let isCodeGenOnly=1 in { - def ASSIGN_TYPE: Pseudo<(outs ANYID:$dst_id), (ins ANYID:$src_id, TYPE:$src_ty)>; - def DECL_TYPE: Pseudo<(outs ANYID:$dst_id), (ins ANYID:$src_id, TYPE:$src_ty)>; + def ASSIGN_TYPE: Pseudo<(outs ANYID:$dst_id), (ins unknown:$src_id, TYPE:$src_ty)>; def GET_ID: Pseudo<(outs ID:$dst_id), (ins ANYID:$src)>; - def GET_fID: Pseudo<(outs fID:$dst_id), (ins ANYID:$src)>; - def GET_pID: Pseudo<(outs pID:$dst_id), (ins ANYID:$src)>; - def GET_vID: Pseudo<(outs vID:$dst_id), (ins ANYID:$src)>; - def GET_vfID: Pseudo<(outs vfID:$dst_id), (ins ANYID:$src)>; + def GET_SID: Pseudo<(outs SID:$dst_id), (ins ANYID:$src)>; + def GET_VID: Pseudo<(outs VID:$dst_id), (ins ANYID:$src)>; } def SPVTypeBin : SDTypeProfile<1, 2, []>; @@ -38,17 +35,10 @@ : Op; -multiclass BinOpTypedGen opCode, SDNode node, bit genF = 0, bit genV = 0> { - if genF then - def S: BinOpTyped; - else - def S: BinOpTyped; - if genV then { - if genF then - def V: BinOpTyped; - else - def V: BinOpTyped; - } +multiclass BinOpTypedGen opCode, SDNode node, bit genV = 0> { + def S: BinOpTyped; + if genV then + def V: BinOpTyped; } class UnOp opCode, list pattern=[]> @@ -74,7 +64,7 @@ "OpSource $lang $version">; def OpSourceExtension: Op<4, (outs), (ins StringImm:$extension, variable_ops), "OpSourceExtension $extension">; -def OpName: Op<5, (outs), (ins ANY:$tar, StringImm:$name, variable_ops), "OpName $tar $name">; +def OpName: Op<5, (outs), (ins ANYID:$tar, StringImm:$name, variable_ops), "OpName $tar $name">; def OpMemberName: Op<6, (outs), (ins TYPE:$ty, i32imm:$mem, StringImm:$name, variable_ops), "OpMemberName $ty $mem $name">; def OpString: Op<7, (outs ID:$r), (ins StringImm:$s, variable_ops), "$r = OpString $s">; @@ -85,7 +75,7 @@ // 3.42.3 Annotation Instructions -def OpDecorate: Op<71, (outs), (ins ANY:$target, Decoration:$dec, variable_ops), +def OpDecorate: Op<71, (outs), (ins ANYID:$target, Decoration:$dec, variable_ops), "OpDecorate $target $dec">; def OpMemberDecorate: Op<72, (outs), (ins TYPE:$t, i32imm:$m, Decoration:$d, variable_ops), "OpMemberDecorate $t $m $d">; @@ -93,9 +83,9 @@ // TODO Currently some deprecated opcodes are missing: OpDecorationGroup, // OpGroupDecorate and OpGroupMemberDecorate -def OpDecorateId: Op<332, (outs), (ins ANY:$target, Decoration:$dec, variable_ops), +def OpDecorateId: Op<332, (outs), (ins ANYID:$target, Decoration:$dec, variable_ops), "OpDecorateId $target $dec">; -def OpDecorateString: Op<5632, (outs), (ins ANY:$t, Decoration:$d, StringImm:$s, variable_ops), +def OpDecorateString: Op<5632, (outs), (ins ANYID:$t, Decoration:$d, StringImm:$s, variable_ops), "OpDecorateString $t $d $s">; def OpMemberDecorateString: Op<5633, (outs), (ins TYPE:$ty, i32imm:$mem, Decoration:$dec, StringImm:$str, variable_ops), @@ -106,7 +96,7 @@ def OpExtension: Op<10, (outs), (ins StringImm:$name, variable_ops), "OpExtension $name">; def OpExtInstImport: Op<11, (outs ID:$res), (ins StringImm:$extInstsName, variable_ops), "$res = OpExtInstImport $extInstsName">; -def OpExtInst: Op<12, (outs ID:$res), (ins TYPE:$ty, ID:$set, Extension:$inst, variable_ops), +def OpExtInst: Op<12, (outs ID:$res), (ins TYPE:$ty, i32imm:$set, Extension:$inst, variable_ops), "$res = OpExtInst $ty $set $inst">; // 3.42.5 Mode-Setting Instructions @@ -173,9 +163,9 @@ N->getValueAP().bitcastToAPInt().getZExtValue(), SDLoc(N), MVT::i32); }]>; -def fimm_to_i32 : SDNodeXFormgetTargetConstant( - N->getValueAPF().bitcastToAPInt().getZExtValue(), SDLoc(N), MVT::i32); + N->getValueAPF().bitcastToAPInt().getZExtValue(), SDLoc(N), MVT::f32); }]>; def gi_bitcast_fimm_to_i32 : GICustomOperandRenderer<"renderFImm32">, @@ -185,7 +175,8 @@ GISDNodeXFormEquiv; def PseudoConstI: IntImmLeaf; -def PseudoConstF: FPImmLeaf; +def PseudoConstF: FPImmLeaf; + def ConstPseudoTrue: IntImmLeaf; def ConstPseudoFalse: IntImmLeaf; def ConstPseudoNull: IntImmLeaf; @@ -193,7 +184,7 @@ multiclass IntFPImm opCode, string name> { def I: Op; - def F: Op; } @@ -403,9 +394,8 @@ // 3.42.12 Composite Instructions -def OpVectorExtractDynamic: Op<77, (outs ID:$res), (ins TYPE:$type, vID:$vec, ID:$idx), - "$res = OpVectorExtractDynamic $type $vec $idx", [(set ID:$res, (assigntype (extractelt vID:$vec, ID:$idx), TYPE:$type))]>; - +def OpVectorExtractDynamic: Op<77, (outs ID:$res), (ins TYPE:$ty, ID:$vec, ID:$idx), + "$res = OpVectorExtractDynamic $ty $vec $idx">; def OpVectorInsertDynamic: Op<78, (outs ID:$res), (ins TYPE:$ty, ID:$vec, ID:$comp, ID:$idx), "$res = OpVectorInsertDynamic $ty $vec $comp $idx">; def OpVectorShuffle: Op<79, (outs ID:$res), (ins TYPE:$ty, ID:$v1, ID:$v2, variable_ops), @@ -423,27 +413,27 @@ // 3.42.13 Arithmetic Instructions def OpSNegate: UnOp<"OpSNegate", 126>; -def OpFNegate: UnOpTyped<"OpFNegate", 127, fID, fneg>; -def OpFNegateV: UnOpTyped<"OpFNegate", 127, vfID, fneg>; -defm OpIAdd: BinOpTypedGen<"OpIAdd", 128, add, 0, 1>; -defm OpFAdd: BinOpTypedGen<"OpFAdd", 129, fadd, 1, 1>; +def OpFNegate: UnOpTyped<"OpFNegate", 127, SID, fneg>; +def OpFNegateV: UnOpTyped<"OpFNegate", 127, VID, fneg>; +defm OpIAdd: BinOpTypedGen<"OpIAdd", 128, add, 1>; +defm OpFAdd: BinOpTypedGen<"OpFAdd", 129, fadd, 1>; -defm OpISub: BinOpTypedGen<"OpISub", 130, sub, 0, 1>; -defm OpFSub: BinOpTypedGen<"OpFSub", 131, fsub, 1, 1>; +defm OpISub: BinOpTypedGen<"OpISub", 130, sub, 1>; +defm OpFSub: BinOpTypedGen<"OpFSub", 131, fsub, 1>; -defm OpIMul: BinOpTypedGen<"OpIMul", 132, mul, 0, 1>; -defm OpFMul: BinOpTypedGen<"OpFMul", 133, fmul, 1, 1>; +defm OpIMul: BinOpTypedGen<"OpIMul", 132, mul, 1>; +defm OpFMul: BinOpTypedGen<"OpFMul", 133, fmul, 1>; -defm OpUDiv: BinOpTypedGen<"OpUDiv", 134, udiv, 0, 1>; -defm OpSDiv: BinOpTypedGen<"OpSDiv", 135, sdiv, 0, 1>; -defm OpFDiv: BinOpTypedGen<"OpFDiv", 136, fdiv, 1, 1>; +defm OpUDiv: BinOpTypedGen<"OpUDiv", 134, udiv, 1>; +defm OpSDiv: BinOpTypedGen<"OpSDiv", 135, sdiv, 1>; +defm OpFDiv: BinOpTypedGen<"OpFDiv", 136, fdiv, 1>; -defm OpUMod: BinOpTypedGen<"OpUMod", 137, urem, 0, 1>; -defm OpSRem: BinOpTypedGen<"OpSRem", 138, srem, 0, 1>; +defm OpUMod: BinOpTypedGen<"OpUMod", 137, urem, 1>; +defm OpSRem: BinOpTypedGen<"OpSRem", 138, srem, 1>; def OpSMod: BinOp<"OpSMod", 139>; -defm OpFRem: BinOpTypedGen<"OpFRem", 140, frem, 1, 1>; +defm OpFRem: BinOpTypedGen<"OpFRem", 140, frem, 1>; def OpFMod: BinOp<"OpFMod", 141>; def OpVectorTimesScalar: BinOp<"OpVectorTimesScalar", 142>; @@ -462,13 +452,13 @@ // 3.42.14 Bit Instructions -defm OpShiftRightLogical: BinOpTypedGen<"OpShiftRightLogical", 194, srl, 0, 1>; -defm OpShiftRightArithmetic: BinOpTypedGen<"OpShiftRightArithmetic", 195, sra, 0, 1>; -defm OpShiftLeftLogical: BinOpTypedGen<"OpShiftLeftLogical", 196, shl, 0, 1>; +defm OpShiftRightLogical: BinOpTypedGen<"OpShiftRightLogical", 194, srl, 1>; +defm OpShiftRightArithmetic: BinOpTypedGen<"OpShiftRightArithmetic", 195, sra, 1>; +defm OpShiftLeftLogical: BinOpTypedGen<"OpShiftLeftLogical", 196, shl, 1>; -defm OpBitwiseOr: BinOpTypedGen<"OpBitwiseOr", 197, or, 0, 1>; -defm OpBitwiseXor: BinOpTypedGen<"OpBitwiseXor", 198, xor, 0, 1>; -defm OpBitwiseAnd: BinOpTypedGen<"OpBitwiseAnd", 199, and, 0, 1>; +defm OpBitwiseOr: BinOpTypedGen<"OpBitwiseOr", 197, or, 1>; +defm OpBitwiseXor: BinOpTypedGen<"OpBitwiseXor", 198, xor, 1>; +defm OpBitwiseAnd: BinOpTypedGen<"OpBitwiseAnd", 199, and, 1>; def OpNot: UnOp<"OpNot", 200>; def OpBitFieldInsert: Op<201, (outs ID:$res), diff --git a/llvm/lib/Target/SPIRV/SPIRVPreLegalizer.cpp b/llvm/lib/Target/SPIRV/SPIRVPreLegalizer.cpp --- a/llvm/lib/Target/SPIRV/SPIRVPreLegalizer.cpp +++ b/llvm/lib/Target/SPIRV/SPIRVPreLegalizer.cpp @@ -301,21 +301,10 @@ createNewIdReg(Register ValReg, unsigned Opcode, MachineRegisterInfo &MRI, const SPIRVGlobalRegistry &GR) { LLT NewT = LLT::scalar(32); - SPIRVType *SpvType = GR.getSPIRVTypeForVReg(ValReg); - assert(SpvType && "VReg is expected to have SPIRV type"); - bool IsFloat = SpvType->getOpcode() == SPIRV::OpTypeFloat; - bool IsVectorFloat = - SpvType->getOpcode() == SPIRV::OpTypeVector && - GR.getSPIRVTypeForVReg(SpvType->getOperand(1).getReg())->getOpcode() == - SPIRV::OpTypeFloat; - IsFloat |= IsVectorFloat; - auto GetIdOp = IsFloat ? SPIRV::GET_fID : SPIRV::GET_ID; - if (MRI.getType(ValReg).isPointer()) { - NewT = LLT::pointer(0, 32); - GetIdOp = SPIRV::GET_pID; - } else if (MRI.getType(ValReg).isVector()) { + auto GetIdOp = SPIRV::GET_SID; + if (MRI.getType(ValReg).isVector()) { NewT = LLT::fixed_vector(2, NewT); - GetIdOp = IsFloat ? SPIRV::GET_vfID : SPIRV::GET_vID; + GetIdOp = SPIRV::GET_VID; } Register IdReg = MRI.createGenericVirtualRegister(NewT); return {IdReg, GetIdOp}; diff --git a/llvm/lib/Target/SPIRV/SPIRVRegisterBankInfo.cpp b/llvm/lib/Target/SPIRV/SPIRVRegisterBankInfo.cpp --- a/llvm/lib/Target/SPIRV/SPIRVRegisterBankInfo.cpp +++ b/llvm/lib/Target/SPIRV/SPIRVRegisterBankInfo.cpp @@ -27,21 +27,5 @@ const RegisterBank & SPIRVRegisterBankInfo::getRegBankFromRegClass(const TargetRegisterClass &RC, LLT Ty) const { - switch (RC.getID()) { - case SPIRV::TYPERegClassID: - return SPIRV::TYPERegBank; - case SPIRV::pIDRegClassID: - case SPIRV::IDRegClassID: - return SPIRV::IDRegBank; - case SPIRV::fIDRegClassID: - return SPIRV::fIDRegBank; - case SPIRV::vIDRegClassID: - return SPIRV::vIDRegBank; - case SPIRV::vfIDRegClassID: - return SPIRV::vfIDRegBank; - case SPIRV::ANYIDRegClassID: - case SPIRV::ANYRegClassID: - return SPIRV::IDRegBank; - } - llvm_unreachable("Unknown register class"); + return SPIRV::IDRegBank; } diff --git a/llvm/lib/Target/SPIRV/SPIRVRegisterBanks.td b/llvm/lib/Target/SPIRV/SPIRVRegisterBanks.td --- a/llvm/lib/Target/SPIRV/SPIRVRegisterBanks.td +++ b/llvm/lib/Target/SPIRV/SPIRVRegisterBanks.td @@ -6,10 +6,6 @@ // //===----------------------------------------------------------------------===// -// Although RegisterBankSelection is disabled we need to distinct the banks -// as InstructionSelector RegClass checking code relies on them -def IDRegBank : RegisterBank<"IDBank", [ID]>; -def fIDRegBank : RegisterBank<"fIDBank", [fID]>; -def vIDRegBank : RegisterBank<"vIDBank", [vID]>; -def vfIDRegBank : RegisterBank<"vfIDBank", [vfID]>; -def TYPERegBank : RegisterBank<"TYPEBank", [TYPE]>; +// Although RegBankSelect is disabled, we need to have +// at least one regbank to support instruction selector +def IDRegBank : RegisterBank<"IDBank", [ID]>; \ No newline at end of file diff --git a/llvm/lib/Target/SPIRV/SPIRVRegisterInfo.td b/llvm/lib/Target/SPIRV/SPIRVRegisterInfo.td --- a/llvm/lib/Target/SPIRV/SPIRVRegisterInfo.td +++ b/llvm/lib/Target/SPIRV/SPIRVRegisterInfo.td @@ -12,7 +12,6 @@ let Namespace = "SPIRV" in { def p0 : PtrValueType ; - // All registers are for 32-bit identifiers, so have a single dummy register // Class for registers that are the result of OpTypeXXX instructions def TYPE0 : Register<"TYPE0">; @@ -21,19 +20,16 @@ // Class for every other non-type ID def ID0 : Register<"ID0">; def ID : RegisterClass<"SPIRV", [i32], 32, (add ID0)>; - def fID0 : Register<"FID0">; - def fID : RegisterClass<"SPIRV", [f32], 32, (add fID0)>; - def pID0 : Register<"pID0">; - def pID : RegisterClass<"SPIRV", [p0], 32, (add pID0)>; - def vID0 : Register<"pID0">; - def vID : RegisterClass<"SPIRV", [v2i32], 32, (add vID0)>; - def vfID0 : Register<"pID0">; - def vfID : RegisterClass<"SPIRV", [v2f32], 32, (add vfID0)>; + def VID0 : Register<"VID0">; - def ANYID : RegisterClass<"SPIRV", [i32, f32, p0, v2i32, v2f32], 32, (add ID, fID, pID, vID, vfID)>; + // TODO: FID register class is only needed for constants selection, + // consider redesigning the pattern to get rid of this + def FID0 : Register<"FID0">; + def FID : RegisterClass<"SPIRV", [f32], 32, (add FID0)>; - // A few instructions like OpName can take ids from both type and non-type - // instructions, so we need a super-class to allow for both to count as valid - // arguments for these instructions. - def ANY : RegisterClass<"SPIRV", [i32], 32, (add TYPE, ID)>; + // Scalar ID + def SID : RegisterClass<"SPIRV", [i32, f32, p0], 32, (add ID0)>; + // Vector ID + def VID : RegisterClass<"SPIRV", [v2i32, v2f32], 32, (add VID0)>; + def ANYID : RegisterClass<"SPIRV", [i32, f32, p0, v2i32, v2f32], 32, (add SID, VID)>; }