10
10
#include " DXILResourceAnalysis.h"
11
11
#include " DirectX.h"
12
12
#include " llvm/ADT/StringRef.h"
13
+ #include " llvm/Analysis/DXILResource.h"
13
14
#include " llvm/IR/PassManager.h"
15
+ #include " llvm/InitializePasses.h"
14
16
#include " llvm/Pass.h"
17
+ #include " llvm/Support/FormatAdapters.h"
15
18
#include " llvm/Support/FormatVariadic.h"
16
19
#include " llvm/Support/raw_ostream.h"
17
20
18
21
using namespace llvm ;
19
22
20
- static void prettyPrintResources (raw_ostream &OS,
23
+ static StringRef getRCName (dxil::ResourceClass RC) {
24
+ switch (RC) {
25
+ case dxil::ResourceClass::SRV:
26
+ return " SRV" ;
27
+ case dxil::ResourceClass::UAV:
28
+ return " UAV" ;
29
+ case dxil::ResourceClass::CBuffer:
30
+ return " cbuffer" ;
31
+ case dxil::ResourceClass::Sampler:
32
+ return " sampler" ;
33
+ }
34
+ llvm_unreachable (" covered switch" );
35
+ }
36
+
37
+ static StringRef getRCPrefix (dxil::ResourceClass RC) {
38
+ switch (RC) {
39
+ case dxil::ResourceClass::SRV:
40
+ return " t" ;
41
+ case dxil::ResourceClass::UAV:
42
+ return " u" ;
43
+ case dxil::ResourceClass::CBuffer:
44
+ return " cb" ;
45
+ case dxil::ResourceClass::Sampler:
46
+ return " s" ;
47
+ }
48
+ }
49
+
50
+ static StringRef getFormatName (const dxil::ResourceInfo &RI) {
51
+ if (RI.isTyped ()) {
52
+ switch (RI.getTyped ().ElementTy ) {
53
+ case dxil::ElementType::I1:
54
+ return " i1" ;
55
+ case dxil::ElementType::I16:
56
+ return " i16" ;
57
+ case dxil::ElementType::U16:
58
+ return " u16" ;
59
+ case dxil::ElementType::I32:
60
+ return " i32" ;
61
+ case dxil::ElementType::U32:
62
+ return " u32" ;
63
+ case dxil::ElementType::I64:
64
+ return " i64" ;
65
+ case dxil::ElementType::U64:
66
+ return " u64" ;
67
+ case dxil::ElementType::F16:
68
+ return " f16" ;
69
+ case dxil::ElementType::F32:
70
+ return " f32" ;
71
+ case dxil::ElementType::F64:
72
+ return " f64" ;
73
+ case dxil::ElementType::SNormF16:
74
+ return " snorm_f16" ;
75
+ case dxil::ElementType::UNormF16:
76
+ return " unorm_f16" ;
77
+ case dxil::ElementType::SNormF32:
78
+ return " snorm_f32" ;
79
+ case dxil::ElementType::UNormF32:
80
+ return " unorm_f32" ;
81
+ case dxil::ElementType::SNormF64:
82
+ return " snorm_f64" ;
83
+ case dxil::ElementType::UNormF64:
84
+ return " unorm_f64" ;
85
+ case dxil::ElementType::PackedS8x32:
86
+ return " p32i8" ;
87
+ case dxil::ElementType::PackedU8x32:
88
+ return " p32u8" ;
89
+ case dxil::ElementType::Invalid:
90
+ llvm_unreachable (" Invalid ElementType" );
91
+ }
92
+ llvm_unreachable (" Unhandled ElementType" );
93
+ } else if (RI.isStruct ())
94
+ return " struct" ;
95
+ else if (RI.isCBuffer () || RI.isSampler ())
96
+ return " NA" ;
97
+ return " byte" ;
98
+ }
99
+
100
+ static StringRef getTextureDimName (dxil::ResourceKind RK) {
101
+ switch (RK) {
102
+ case dxil::ResourceKind::Texture1D:
103
+ return " 1d" ;
104
+ case dxil::ResourceKind::Texture2D:
105
+ return " 2d" ;
106
+ case dxil::ResourceKind::Texture3D:
107
+ return " 3d" ;
108
+ case dxil::ResourceKind::TextureCube:
109
+ return " cube" ;
110
+ case dxil::ResourceKind::Texture1DArray:
111
+ return " 1darray" ;
112
+ case dxil::ResourceKind::Texture2DArray:
113
+ return " 2darray" ;
114
+ case dxil::ResourceKind::TextureCubeArray:
115
+ return " cubearray" ;
116
+ case dxil::ResourceKind::TBuffer:
117
+ return " tbuffer" ;
118
+ case dxil::ResourceKind::FeedbackTexture2D:
119
+ return " fbtex2d" ;
120
+ case dxil::ResourceKind::FeedbackTexture2DArray:
121
+ return " fbtex2darray" ;
122
+ case dxil::ResourceKind::Texture2DMS:
123
+ return " 2dMS" ;
124
+ case dxil::ResourceKind::Texture2DMSArray:
125
+ return " 2darrayMS" ;
126
+ case dxil::ResourceKind::Invalid:
127
+ case dxil::ResourceKind::NumEntries:
128
+ case dxil::ResourceKind::CBuffer:
129
+ case dxil::ResourceKind::RawBuffer:
130
+ case dxil::ResourceKind::Sampler:
131
+ case dxil::ResourceKind::StructuredBuffer:
132
+ case dxil::ResourceKind::TypedBuffer:
133
+ case dxil::ResourceKind::RTAccelerationStructure:
134
+ llvm_unreachable (" Invalid ResourceKind for texture" );
135
+ }
136
+ llvm_unreachable (" Unhandled ResourceKind" );
137
+ }
138
+
139
+ namespace {
140
+ struct FormatResourceDimension
141
+ : public llvm::FormatAdapter<const dxil::ResourceInfo &> {
142
+ explicit FormatResourceDimension (const dxil::ResourceInfo &RI)
143
+ : llvm::FormatAdapter<const dxil::ResourceInfo &>(RI) {}
144
+
145
+ void format (llvm::raw_ostream &OS, StringRef Style ) override {
146
+ dxil::ResourceKind RK = Item.getResourceKind ();
147
+ switch (RK) {
148
+ default : {
149
+ OS << getTextureDimName (RK);
150
+ if (Item.isMultiSample ())
151
+ OS << Item.getMultiSample ().Count ;
152
+ break ;
153
+ }
154
+ case dxil::ResourceKind::RawBuffer:
155
+ case dxil::ResourceKind::StructuredBuffer:
156
+ if (!Item.isUAV ())
157
+ OS << " r/o" ;
158
+ else if (Item.getUAV ().HasCounter )
159
+ OS << " r/w+cnt" ;
160
+ else
161
+ OS << " r/w" ;
162
+ break ;
163
+ case dxil::ResourceKind::TypedBuffer:
164
+ OS << " buf" ;
165
+ break ;
166
+ case dxil::ResourceKind::RTAccelerationStructure:
167
+ // TODO: dxc would print "ras" here. Can/should this happen?
168
+ llvm_unreachable (" RTAccelerationStructure printing is not implemented" );
169
+ }
170
+ }
171
+ };
172
+
173
+ struct FormatBindingID
174
+ : public llvm::FormatAdapter<const dxil::ResourceInfo &> {
175
+ explicit FormatBindingID (const dxil::ResourceInfo &RI)
176
+ : llvm::FormatAdapter<const dxil::ResourceInfo &>(RI) {}
177
+
178
+ void format (llvm::raw_ostream &OS, StringRef Style ) override {
179
+ OS << getRCPrefix (Item.getResourceClass ()).upper ()
180
+ << Item.getBinding ().RecordID ;
181
+ }
182
+ };
183
+
184
+ struct FormatBindingLocation
185
+ : public llvm::FormatAdapter<const dxil::ResourceInfo &> {
186
+ explicit FormatBindingLocation (const dxil::ResourceInfo &RI)
187
+ : llvm::FormatAdapter<const dxil::ResourceInfo &>(RI) {}
188
+
189
+ void format (llvm::raw_ostream &OS, StringRef Style ) override {
190
+ const auto &Binding = Item.getBinding ();
191
+ OS << getRCPrefix (Item.getResourceClass ()) << Binding.LowerBound ;
192
+ if (Binding.Space )
193
+ OS << " ,space" << Binding.Space ;
194
+ }
195
+ };
196
+
197
+ struct FormatBindingSize
198
+ : public llvm::FormatAdapter<const dxil::ResourceInfo &> {
199
+ explicit FormatBindingSize (const dxil::ResourceInfo &RI)
200
+ : llvm::FormatAdapter<const dxil::ResourceInfo &>(RI) {}
201
+
202
+ void format (llvm::raw_ostream &OS, StringRef Style ) override {
203
+ uint32_t Size = Item.getBinding ().Size ;
204
+ if (Size == std::numeric_limits<uint32_t >::max ())
205
+ OS << " unbounded" ;
206
+ else
207
+ OS << Size ;
208
+ }
209
+ };
210
+
211
+ } // namespace
212
+
213
+ static void prettyPrintResources (raw_ostream &OS, const DXILResourceMap &DRM,
21
214
const dxil::Resources &MDResources) {
22
215
// Column widths are arbitrary but match the widths DXC uses.
23
216
OS << " ;\n ; Resource Bindings:\n ;\n " ;
24
- OS << formatv (" ; {0,-30} {1,10} {2,7} {3,11} {4,7} {5,14} {6,16 }\n " , " Name" ,
217
+ OS << formatv (" ; {0,-30} {1,10} {2,7} {3,11} {4,7} {5,14} {6,9 }\n " , " Name" ,
25
218
" Type" , " Format" , " Dim" , " ID" , " HLSL Bind" , " Count" );
26
219
OS << formatv (
27
- " ; {0,-+30} {1,-+10} {2,-+7} {3,-+11} {4,-+7} {5,-+14} {6,-+16}\n " , " " ,
28
- " " , " " , " " , " " , " " , " " );
220
+ " ; {0,-+30} {1,-+10} {2,-+7} {3,-+11} {4,-+7} {5,-+14} {6,-+9}\n " , " " , " " ,
221
+ " " , " " , " " , " " , " " );
222
+
223
+ // TODO: Do we want to sort these by binding or something like that?
224
+ for (const dxil::ResourceInfo &RI : DRM) {
225
+ dxil::ResourceClass RC = RI.getResourceClass ();
226
+ assert ((RC != dxil::ResourceClass::CBuffer || !MDResources.hasCBuffers ()) &&
227
+ " Old and new cbuffer representations can't coexist" );
228
+ assert ((RC != dxil::ResourceClass::UAV || !MDResources.hasUAVs ()) &&
229
+ " Old and new UAV representations can't coexist" );
230
+
231
+ StringRef Name (RI.getName ());
232
+ StringRef Type (getRCName (RC));
233
+ StringRef Format (getFormatName (RI));
234
+ FormatResourceDimension Dim (RI);
235
+ FormatBindingID ID (RI);
236
+ FormatBindingLocation Bind (RI);
237
+ FormatBindingSize Count (RI);
238
+ OS << formatv (" ; {0,-30} {1,10} {2,7} {3,11} {4,7} {5,14} {6,9}\n " , Name,
239
+ Type, Format, Dim, ID, Bind, Count);
240
+ }
29
241
30
242
if (MDResources.hasCBuffers ())
31
243
MDResources.printCBuffers (OS);
@@ -37,8 +249,9 @@ static void prettyPrintResources(raw_ostream &OS,
37
249
38
250
PreservedAnalyses DXILPrettyPrinterPass::run (Module &M,
39
251
ModuleAnalysisManager &MAM) {
252
+ const DXILResourceMap &DRM = MAM.getResult <DXILResourceAnalysis>(M);
40
253
const dxil::Resources &MDResources = MAM.getResult <DXILResourceMDAnalysis>(M);
41
- prettyPrintResources (OS, MDResources);
254
+ prettyPrintResources (OS, DRM, MDResources);
42
255
return PreservedAnalyses::all ();
43
256
}
44
257
@@ -63,6 +276,7 @@ class DXILPrettyPrinterLegacy : public llvm::ModulePass {
63
276
bool runOnModule (Module &M) override ;
64
277
void getAnalysisUsage (AnalysisUsage &AU) const override {
65
278
AU.setPreservesAll ();
279
+ AU.addRequired <DXILResourceWrapperPass>();
66
280
AU.addRequired <DXILResourceMDWrapper>();
67
281
}
68
282
};
@@ -71,13 +285,16 @@ class DXILPrettyPrinterLegacy : public llvm::ModulePass {
71
285
char DXILPrettyPrinterLegacy::ID = 0 ;
72
286
INITIALIZE_PASS_BEGIN (DXILPrettyPrinterLegacy, " dxil-pretty-printer" ,
73
287
" DXIL Metadata Pretty Printer" , true , true )
288
+ INITIALIZE_PASS_DEPENDENCY(DXILResourceWrapperPass)
74
289
INITIALIZE_PASS_DEPENDENCY(DXILResourceMDWrapper)
75
290
INITIALIZE_PASS_END(DXILPrettyPrinterLegacy, " dxil-pretty-printer" ,
76
291
" DXIL Metadata Pretty Printer" , true , true )
77
292
78
293
bool DXILPrettyPrinterLegacy::runOnModule(Module &M) {
294
+ const DXILResourceMap &DRM =
295
+ getAnalysis<DXILResourceWrapperPass>().getResourceMap ();
79
296
dxil::Resources &Res = getAnalysis<DXILResourceMDWrapper>().getDXILResource ();
80
- prettyPrintResources (OS, Res);
297
+ prettyPrintResources (OS, DRM, Res);
81
298
return false ;
82
299
}
83
300
0 commit comments