xref: /freebsd/contrib/llvm-project/llvm/include/llvm/Frontend/HLSL/HLSLRootSignature.h (revision 700637cbb5e582861067a11aaca4d053546871d2)
1 //===- HLSLRootSignature.h - HLSL Root Signature helper objects -----------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 ///
9 /// \file This file contains structure definitions of HLSL Root Signature
10 /// objects.
11 ///
12 //===----------------------------------------------------------------------===//
13 
14 #ifndef LLVM_FRONTEND_HLSL_HLSLROOTSIGNATURE_H
15 #define LLVM_FRONTEND_HLSL_HLSLROOTSIGNATURE_H
16 
17 #include "llvm/BinaryFormat/DXContainer.h"
18 #include "llvm/Support/Compiler.h"
19 #include "llvm/Support/DXILABI.h"
20 #include "llvm/Support/raw_ostream.h"
21 #include <limits>
22 #include <variant>
23 
24 namespace llvm {
25 namespace hlsl {
26 namespace rootsig {
27 
28 // Definitions of the in-memory data layout structures
29 
30 // Models the different registers: bReg | tReg | uReg | sReg
31 enum class RegisterType { BReg, TReg, UReg, SReg };
32 struct Register {
33   RegisterType ViewType;
34   uint32_t Number;
35 };
36 
37 // Models the parameter values of root constants
38 struct RootConstants {
39   uint32_t Num32BitConstants;
40   Register Reg;
41   uint32_t Space = 0;
42   dxbc::ShaderVisibility Visibility = dxbc::ShaderVisibility::All;
43 };
44 
45 enum class DescriptorType : uint8_t { SRV = 0, UAV, CBuffer };
46 // Models RootDescriptor : CBV | SRV | UAV, by collecting like parameters
47 struct RootDescriptor {
48   DescriptorType Type;
49   Register Reg;
50   uint32_t Space = 0;
51   dxbc::ShaderVisibility Visibility = dxbc::ShaderVisibility::All;
52   dxbc::RootDescriptorFlags Flags;
53 
setDefaultFlagsRootDescriptor54   void setDefaultFlags(dxbc::RootSignatureVersion Version) {
55     if (Version == dxbc::RootSignatureVersion::V1_0) {
56       Flags = dxbc::RootDescriptorFlags::DataVolatile;
57       return;
58     }
59 
60     assert(Version == llvm::dxbc::RootSignatureVersion::V1_1 &&
61            "Specified an invalid root signature version");
62     switch (Type) {
63     case DescriptorType::CBuffer:
64     case DescriptorType::SRV:
65       Flags = dxbc::RootDescriptorFlags::DataStaticWhileSetAtExecute;
66       break;
67     case DescriptorType::UAV:
68       Flags = dxbc::RootDescriptorFlags::DataVolatile;
69       break;
70     }
71   }
72 };
73 
74 // Models the end of a descriptor table and stores its visibility
75 struct DescriptorTable {
76   dxbc::ShaderVisibility Visibility = dxbc::ShaderVisibility::All;
77   // Denotes that the previous NumClauses in the RootElement array
78   // are the clauses in the table.
79   uint32_t NumClauses = 0;
80 };
81 
82 static const uint32_t NumDescriptorsUnbounded = 0xffffffff;
83 static const uint32_t DescriptorTableOffsetAppend = 0xffffffff;
84 // Models DTClause : CBV | SRV | UAV | Sampler, by collecting like parameters
85 using ClauseType = llvm::dxil::ResourceClass;
86 struct DescriptorTableClause {
87   ClauseType Type;
88   Register Reg;
89   uint32_t NumDescriptors = 1;
90   uint32_t Space = 0;
91   uint32_t Offset = DescriptorTableOffsetAppend;
92   dxbc::DescriptorRangeFlags Flags;
93 
setDefaultFlagsDescriptorTableClause94   void setDefaultFlags(dxbc::RootSignatureVersion Version) {
95     if (Version == dxbc::RootSignatureVersion::V1_0) {
96       Flags = dxbc::DescriptorRangeFlags::DescriptorsVolatile;
97       if (Type != ClauseType::Sampler)
98         Flags |= dxbc::DescriptorRangeFlags::DataVolatile;
99       return;
100     }
101 
102     assert(Version == dxbc::RootSignatureVersion::V1_1 &&
103            "Specified an invalid root signature version");
104     switch (Type) {
105     case ClauseType::CBuffer:
106     case ClauseType::SRV:
107       Flags = dxbc::DescriptorRangeFlags::DataStaticWhileSetAtExecute;
108       break;
109     case ClauseType::UAV:
110       Flags = dxbc::DescriptorRangeFlags::DataVolatile;
111       break;
112     case ClauseType::Sampler:
113       Flags = dxbc::DescriptorRangeFlags::None;
114       break;
115     }
116   }
117 };
118 
119 struct StaticSampler {
120   Register Reg;
121   dxbc::SamplerFilter Filter = dxbc::SamplerFilter::Anisotropic;
122   dxbc::TextureAddressMode AddressU = dxbc::TextureAddressMode::Wrap;
123   dxbc::TextureAddressMode AddressV = dxbc::TextureAddressMode::Wrap;
124   dxbc::TextureAddressMode AddressW = dxbc::TextureAddressMode::Wrap;
125   float MipLODBias = 0.f;
126   uint32_t MaxAnisotropy = 16;
127   dxbc::ComparisonFunc CompFunc = dxbc::ComparisonFunc::LessEqual;
128   dxbc::StaticBorderColor BorderColor = dxbc::StaticBorderColor::OpaqueWhite;
129   float MinLOD = 0.f;
130   float MaxLOD = std::numeric_limits<float>::max();
131   uint32_t Space = 0;
132   dxbc::ShaderVisibility Visibility = dxbc::ShaderVisibility::All;
133 };
134 
135 /// Models RootElement : RootFlags | RootConstants | RootParam
136 ///  | DescriptorTable | DescriptorTableClause | StaticSampler
137 ///
138 /// A Root Signature is modeled in-memory by an array of RootElements. These
139 /// aim to map closely to their DSL grammar reprsentation defined in the spec.
140 ///
141 /// Each optional parameter has its default value defined in the struct, and,
142 /// each mandatory parameter does not have a default initialization.
143 ///
144 /// For the variants RootFlags, RootConstants, RootParam, StaticSampler and
145 /// DescriptorTableClause: each data member maps directly to a parameter in the
146 /// grammar.
147 ///
148 /// The DescriptorTable is modelled by having its Clauses as the previous
149 /// RootElements in the array, and it holds a data member for the Visibility
150 /// parameter.
151 using RootElement =
152     std::variant<dxbc::RootFlags, RootConstants, RootDescriptor,
153                  DescriptorTable, DescriptorTableClause, StaticSampler>;
154 
155 /// The following contains the serialization interface for root elements
156 LLVM_ABI raw_ostream &operator<<(raw_ostream &OS, const dxbc::RootFlags &Flags);
157 LLVM_ABI raw_ostream &operator<<(raw_ostream &OS,
158                                  const RootConstants &Constants);
159 LLVM_ABI raw_ostream &operator<<(raw_ostream &OS,
160                                  const DescriptorTableClause &Clause);
161 LLVM_ABI raw_ostream &operator<<(raw_ostream &OS, const DescriptorTable &Table);
162 LLVM_ABI raw_ostream &operator<<(raw_ostream &OS,
163                                  const RootDescriptor &Descriptor);
164 LLVM_ABI raw_ostream &operator<<(raw_ostream &OS,
165                                  const StaticSampler &StaticSampler);
166 LLVM_ABI raw_ostream &operator<<(raw_ostream &OS, const RootElement &Element);
167 
168 LLVM_ABI void dumpRootElements(raw_ostream &OS, ArrayRef<RootElement> Elements);
169 
170 } // namespace rootsig
171 } // namespace hlsl
172 } // namespace llvm
173 
174 #endif // LLVM_FRONTEND_HLSL_HLSLROOTSIGNATURE_H
175