@@ -341,6 +341,9 @@ class SPIRVInstructionSelector : public InstructionSelector {
341
341
bool loadVec3BuiltinInputID (SPIRV::BuiltIn::BuiltIn BuiltInValue,
342
342
Register ResVReg, const SPIRVType *ResType,
343
343
MachineInstr &I) const ;
344
+ bool loadBuiltinInputID (SPIRV::BuiltIn::BuiltIn BuiltInValue,
345
+ Register ResVReg, const SPIRVType *ResType,
346
+ MachineInstr &I) const ;
344
347
bool loadHandleBeforePosition (Register &HandleReg, const SPIRVType *ResType,
345
348
GIntrinsic &HandleDef, MachineInstr &Pos) const ;
346
349
};
@@ -3059,6 +3062,15 @@ bool SPIRVInstructionSelector::selectIntrinsic(Register ResVReg,
3059
3062
// builtin variable
3060
3063
return loadVec3BuiltinInputID (SPIRV::BuiltIn::WorkgroupId, ResVReg, ResType,
3061
3064
I);
3065
+ case Intrinsic::spv_flattened_thread_id_in_group:
3066
+ // The HLSL SV_GroupIndex semantic is lowered to
3067
+ // llvm.spv.flattened.thread.id.in.group() intrinsic in LLVM IR for SPIR-V
3068
+ // backend.
3069
+ //
3070
+ // In SPIR-V backend, llvm.spv.flattened.thread.id.in.group is translated to
3071
+ // a `LocalInvocationIndex` builtin variable
3072
+ return loadBuiltinInputID (SPIRV::BuiltIn::LocalInvocationIndex, ResVReg,
3073
+ ResType, I);
3062
3074
case Intrinsic::spv_fdot:
3063
3075
return selectFloatDot (ResVReg, ResType, I);
3064
3076
case Intrinsic::spv_udot:
@@ -4005,6 +4017,38 @@ bool SPIRVInstructionSelector::loadVec3BuiltinInputID(
4005
4017
return Result && MIB.constrainAllUses (TII, TRI, RBI);
4006
4018
}
4007
4019
4020
+ // Generate the instructions to load 32-bit integer builtin input IDs/Indices.
4021
+ // Like LocalInvocationIndex
4022
+ bool SPIRVInstructionSelector::loadBuiltinInputID (
4023
+ SPIRV::BuiltIn::BuiltIn BuiltInValue, Register ResVReg,
4024
+ const SPIRVType *ResType, MachineInstr &I) const {
4025
+ MachineIRBuilder MIRBuilder (I);
4026
+ const SPIRVType *U32Type = GR.getOrCreateSPIRVIntegerType (32 , MIRBuilder);
4027
+ const SPIRVType *PtrType = GR.getOrCreateSPIRVPointerType (
4028
+ U32Type, MIRBuilder, SPIRV::StorageClass::Input);
4029
+
4030
+ // Create new register for the input ID builtin variable.
4031
+ Register NewRegister =
4032
+ MIRBuilder.getMRI ()->createVirtualRegister (&SPIRV::iIDRegClass);
4033
+ MIRBuilder.getMRI ()->setType (NewRegister, LLT::pointer (0 , 64 ));
4034
+ GR.assignSPIRVTypeToVReg (PtrType, NewRegister, MIRBuilder.getMF ());
4035
+
4036
+ // Build global variable with the necessary decorations for the input ID
4037
+ // builtin variable.
4038
+ Register Variable = GR.buildGlobalVariable (
4039
+ NewRegister, PtrType, getLinkStringForBuiltIn (BuiltInValue), nullptr ,
4040
+ SPIRV::StorageClass::Input, nullptr , true , true ,
4041
+ SPIRV::LinkageType::Import, MIRBuilder, false );
4042
+
4043
+ // Load uint value from the global variable.
4044
+ auto MIB = BuildMI (*I.getParent (), I, I.getDebugLoc (), TII.get (SPIRV::OpLoad))
4045
+ .addDef (ResVReg)
4046
+ .addUse (GR.getSPIRVTypeID (U32Type))
4047
+ .addUse (Variable);
4048
+
4049
+ return MIB.constrainAllUses (TII, TRI, RBI);
4050
+ }
4051
+
4008
4052
SPIRVType *SPIRVInstructionSelector::widenTypeToVec4 (const SPIRVType *Type,
4009
4053
MachineInstr &I) const {
4010
4054
MachineIRBuilder MIRBuilder (I);
0 commit comments