[llvm] [DXIL] Add constraint specification and backend implementation of DXIL Ops (PR #97593)
Damyan Pepper via llvm-commits
llvm-commits at lists.llvm.org
Fri Jul 12 14:19:19 PDT 2024
================
@@ -469,28 +561,138 @@ static void emitDXILOperationTable(std::vector<DXILOperationDesc> &Ops,
OS << "}\n ";
}
+static void emitDXILOperationTableDataStructs(RecordKeeper &Records,
+ raw_ostream &OS) {
+ // Get Shader stage records
+ std::vector<Record *> ShaderKindRecs =
+ Records.getAllDerivedDefinitions("ShaderStage");
+ // Sort records by name
+ llvm::sort(ShaderKindRecs,
+ [](Record *A, Record *B) { return A->getName() < B->getName(); });
+
+ OS << "// Valid shader kinds\n\n";
+ // Choose the type of enum ShaderKind based on the number of stages declared
+ // plus one for allKinds
+ // This gives the flexibility to just add add new stage records in DXIL.td, if
+ // needed, with no need to change this backend code.
+ uint64_t ShaderKindCount = PowerOf2Ceil(ShaderKindRecs.size() + 1);
+ OS << "enum ShaderKind : uint" << ShaderKindCount << "_t {\n";
+ const std::string allKinds("allKinds");
+ // set unknown kind to 0
+ OS << " Unknown = 0,\n";
+ int shiftVal = 1;
+ for (auto R : ShaderKindRecs) {
+ auto Name = R->getName();
+ if (Name.compare(allKinds)) {
+ OS << " " << Name << " = 1 << " << std::to_string(shiftVal++) << ",\n";
+ }
+ }
+ // allkinds is set to (1 << ShaderKindCount) - 1, with all bits set denoting
+ // support for all stages
+ OS << " " << allKinds << " = 0x"
+ << utohexstr(((1 << shiftVal) - 1), false, 0) << "\n";
+ OS << "}; // enum ShaderKind\n\n";
+
+ // Emit definitions of various data types used to define DXIL Operation table
+ // entries.
+
+ // Emit enum OverloadKind with valid overload types.
+ const SmallVector<std::string> OverloadKindList = {
+ "VOID", "HALF", "FLOAT", "DOUBLE", "I1", "I8",
+ "I16", "I32", "I64", "UserDefinedType", "ObjectType"};
+ // Choose the type of enum OverloadKind based on the number of valid types in
+ // OverloadKindList. This gives the flexibility to just add new supported
+ // types to the list above, if needed, with no need to change this backend
+ // code.
+ unsigned OverloadKindCount = PowerOf2Ceil(OverloadKindList.size());
+ OS << "enum OverloadKind : uint" << OverloadKindCount << "_t {\n";
+ OS << " UNDEFINED = 0,\n";
+ shiftVal = 1;
+ for (auto TyStr : OverloadKindList) {
+ OS << " " << TyStr << " = 1 << " << shiftVal++ << ",\n";
+ }
+ OS << " }; \n";
+
+ // Emit a convenience struct Version to encode Shader Model version specified
+ // in constraints
+ OS << "struct Version { \n \
+ unsigned Major = 0; \n \
+ unsigned Minor = 0; \n \
+ };\n\n";
+
+ // Emit struct Constraints that encapsulate overload and shader kind
+ // constraints predicated on shader model version, if any.
+ OS << "struct OpConstraints { \n \
+ Version ShaderModelVer; \n";
+ OS << " uint" << OverloadKindCount << "_t ValidTys; \n";
+ OS << " uint" << ShaderKindCount << "_t ValidShaderKinds; \n \
+ };\n\n";
+
+ // Emit struct OpCodeProperty record that encapsulates DXIL Op information.
+ OS << "struct OpCodeProperty { \n \
+ dxil::OpCode OpCode; \n \
+ // Offset in DXILOpCodeNameTable. \n \
+ unsigned OpCodeNameOffset; \n \
+ dxil::OpCodeClass OpCodeClass; \n \
+ // Offset in DXILOpCodeClassNameTable. \n \
+ unsigned OpCodeClassNameOffset; \n \
+ std::vector<OpConstraints> Constraints; \n \
+ llvm::Attribute::AttrKind FuncAttr; \n \
+ int OverloadParamIndex; // parameter index which control the overload. \n \
+ // When < 0, should be only 1 overload type. \n \
+ unsigned NumOfParameters; // Number of parameters include return value. \n \
+ unsigned ParameterTableOffset; // Offset in ParameterTable. \n \
+ };\n\n";
+
+ // Emit access function getOverloadTypeName()
+ OS << "static const char *getOverloadTypeName(OverloadKind Kind) { \n \
----------------
damyanp wrote:
Any reason not to use raw string literals here so there's less escaping?
https://github.com/llvm/llvm-project/pull/97593
More information about the llvm-commits
mailing list