xref: /freebsd-src/contrib/llvm-project/llvm/lib/Target/DirectX/DXILShaderFlags.h (revision 0fca6ea1d4eea4c934cfff25ac9ee8ad6fe95583)
1bdd1243dSDimitry Andric //===- DXILShaderFlags.h - DXIL Shader Flags helper objects ---------------===//
2bdd1243dSDimitry Andric //
3bdd1243dSDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4bdd1243dSDimitry Andric // See https://llvm.org/LICENSE.txt for license information.
5bdd1243dSDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6bdd1243dSDimitry Andric //
7bdd1243dSDimitry Andric //===----------------------------------------------------------------------===//
8bdd1243dSDimitry Andric ///
9bdd1243dSDimitry Andric /// \file This file contains helper objects and APIs for working with DXIL
10bdd1243dSDimitry Andric ///       Shader Flags.
11bdd1243dSDimitry Andric ///
12bdd1243dSDimitry Andric //===----------------------------------------------------------------------===//
13bdd1243dSDimitry Andric 
14bdd1243dSDimitry Andric #ifndef LLVM_TARGET_DIRECTX_DXILSHADERFLAGS_H
15bdd1243dSDimitry Andric #define LLVM_TARGET_DIRECTX_DXILSHADERFLAGS_H
16bdd1243dSDimitry Andric 
17bdd1243dSDimitry Andric #include "llvm/IR/PassManager.h"
18bdd1243dSDimitry Andric #include "llvm/Pass.h"
19bdd1243dSDimitry Andric #include "llvm/Support/Compiler.h"
20bdd1243dSDimitry Andric #include "llvm/Support/Debug.h"
21bdd1243dSDimitry Andric #include "llvm/Support/raw_ostream.h"
22bdd1243dSDimitry Andric #include <cstdint>
23bdd1243dSDimitry Andric 
24bdd1243dSDimitry Andric namespace llvm {
25bdd1243dSDimitry Andric class Module;
26bdd1243dSDimitry Andric class GlobalVariable;
27bdd1243dSDimitry Andric 
28bdd1243dSDimitry Andric namespace dxil {
29bdd1243dSDimitry Andric 
30bdd1243dSDimitry Andric struct ComputedShaderFlags {
31*0fca6ea1SDimitry Andric #define SHADER_FEATURE_FLAG(FeatureBit, DxilModuleBit, FlagName, Str)          \
32*0fca6ea1SDimitry Andric   bool FlagName : 1;
33*0fca6ea1SDimitry Andric #define DXIL_MODULE_FLAG(DxilModuleBit, FlagName, Str) bool FlagName : 1;
34bdd1243dSDimitry Andric #include "llvm/BinaryFormat/DXContainerConstants.def"
35bdd1243dSDimitry Andric 
36*0fca6ea1SDimitry Andric #define SHADER_FEATURE_FLAG(FeatureBit, DxilModuleBit, FlagName, Str)          \
37*0fca6ea1SDimitry Andric   FlagName = false;
38*0fca6ea1SDimitry Andric #define DXIL_MODULE_FLAG(DxilModuleBit, FlagName, Str) FlagName = false;
39bdd1243dSDimitry Andric   ComputedShaderFlags() {
40bdd1243dSDimitry Andric #include "llvm/BinaryFormat/DXContainerConstants.def"
41bdd1243dSDimitry Andric   }
42bdd1243dSDimitry Andric 
43*0fca6ea1SDimitry Andric   constexpr uint64_t getMask(int Bit) const {
44*0fca6ea1SDimitry Andric     return Bit != -1 ? 1ull << Bit : 0;
45*0fca6ea1SDimitry Andric   }
46bdd1243dSDimitry Andric   operator uint64_t() const {
47bdd1243dSDimitry Andric     uint64_t FlagValue = 0;
48*0fca6ea1SDimitry Andric #define SHADER_FEATURE_FLAG(FeatureBit, DxilModuleBit, FlagName, Str)          \
49*0fca6ea1SDimitry Andric   FlagValue |= FlagName ? getMask(DxilModuleBit) : 0ull;
50*0fca6ea1SDimitry Andric #define DXIL_MODULE_FLAG(DxilModuleBit, FlagName, Str)                         \
51*0fca6ea1SDimitry Andric   FlagValue |= FlagName ? getMask(DxilModuleBit) : 0ull;
52bdd1243dSDimitry Andric #include "llvm/BinaryFormat/DXContainerConstants.def"
53bdd1243dSDimitry Andric     return FlagValue;
54bdd1243dSDimitry Andric   }
55*0fca6ea1SDimitry Andric   uint64_t getFeatureFlags() const {
56*0fca6ea1SDimitry Andric     uint64_t FeatureFlags = 0;
57*0fca6ea1SDimitry Andric #define SHADER_FEATURE_FLAG(FeatureBit, DxilModuleBit, FlagName, Str)          \
58*0fca6ea1SDimitry Andric   FeatureFlags |= FlagName ? getMask(FeatureBit) : 0ull;
59*0fca6ea1SDimitry Andric #include "llvm/BinaryFormat/DXContainerConstants.def"
60*0fca6ea1SDimitry Andric     return FeatureFlags;
61*0fca6ea1SDimitry Andric   }
62bdd1243dSDimitry Andric 
63bdd1243dSDimitry Andric   static ComputedShaderFlags computeFlags(Module &M);
64bdd1243dSDimitry Andric   void print(raw_ostream &OS = dbgs()) const;
65bdd1243dSDimitry Andric   LLVM_DUMP_METHOD void dump() const { print(); }
66bdd1243dSDimitry Andric };
67bdd1243dSDimitry Andric 
68bdd1243dSDimitry Andric class ShaderFlagsAnalysis : public AnalysisInfoMixin<ShaderFlagsAnalysis> {
69bdd1243dSDimitry Andric   friend AnalysisInfoMixin<ShaderFlagsAnalysis>;
70bdd1243dSDimitry Andric   static AnalysisKey Key;
71bdd1243dSDimitry Andric 
72bdd1243dSDimitry Andric public:
73bdd1243dSDimitry Andric   ShaderFlagsAnalysis() = default;
74bdd1243dSDimitry Andric 
75bdd1243dSDimitry Andric   using Result = ComputedShaderFlags;
76bdd1243dSDimitry Andric 
77bdd1243dSDimitry Andric   ComputedShaderFlags run(Module &M, ModuleAnalysisManager &AM);
78bdd1243dSDimitry Andric };
79bdd1243dSDimitry Andric 
80bdd1243dSDimitry Andric /// Printer pass for ShaderFlagsAnalysis results.
81bdd1243dSDimitry Andric class ShaderFlagsAnalysisPrinter
82bdd1243dSDimitry Andric     : public PassInfoMixin<ShaderFlagsAnalysisPrinter> {
83bdd1243dSDimitry Andric   raw_ostream &OS;
84bdd1243dSDimitry Andric 
85bdd1243dSDimitry Andric public:
86bdd1243dSDimitry Andric   explicit ShaderFlagsAnalysisPrinter(raw_ostream &OS) : OS(OS) {}
87bdd1243dSDimitry Andric   PreservedAnalyses run(Module &M, ModuleAnalysisManager &AM);
88bdd1243dSDimitry Andric };
89bdd1243dSDimitry Andric 
90bdd1243dSDimitry Andric /// Wrapper pass for the legacy pass manager.
91bdd1243dSDimitry Andric ///
92bdd1243dSDimitry Andric /// This is required because the passes that will depend on this are codegen
93bdd1243dSDimitry Andric /// passes which run through the legacy pass manager.
94bdd1243dSDimitry Andric class ShaderFlagsAnalysisWrapper : public ModulePass {
95bdd1243dSDimitry Andric   ComputedShaderFlags Flags;
96bdd1243dSDimitry Andric 
97bdd1243dSDimitry Andric public:
98bdd1243dSDimitry Andric   static char ID;
99bdd1243dSDimitry Andric 
100bdd1243dSDimitry Andric   ShaderFlagsAnalysisWrapper() : ModulePass(ID) {}
101bdd1243dSDimitry Andric 
102bdd1243dSDimitry Andric   const ComputedShaderFlags &getShaderFlags() { return Flags; }
103bdd1243dSDimitry Andric 
104bdd1243dSDimitry Andric   bool runOnModule(Module &M) override {
105bdd1243dSDimitry Andric     Flags = ComputedShaderFlags::computeFlags(M);
106bdd1243dSDimitry Andric     return false;
107bdd1243dSDimitry Andric   }
108bdd1243dSDimitry Andric 
109bdd1243dSDimitry Andric   void getAnalysisUsage(AnalysisUsage &AU) const override {
110bdd1243dSDimitry Andric     AU.setPreservesAll();
111bdd1243dSDimitry Andric   }
112bdd1243dSDimitry Andric };
113bdd1243dSDimitry Andric 
114bdd1243dSDimitry Andric } // namespace dxil
115bdd1243dSDimitry Andric } // namespace llvm
116bdd1243dSDimitry Andric 
117bdd1243dSDimitry Andric #endif // LLVM_TARGET_DIRECTX_DXILSHADERFLAGS_H
118