DxbcUtil.cpp 46 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053
  1. ///////////////////////////////////////////////////////////////////////////////
  2. // //
  3. // DxbcUtil.cpp //
  4. // Copyright (C) Microsoft Corporation. All rights reserved. //
  5. // This file is distributed under the University of Illinois Open Source //
  6. // License. See LICENSE.TXT for details. //
  7. // //
  8. // Utilities to convert from DXBC to DXIL. //
  9. // //
  10. ///////////////////////////////////////////////////////////////////////////////
  11. #include "dxc/Support/Global.h"
  12. #include "dxc/DXIL/DxilSampler.h"
  13. #include "dxc/DXIL/DxilResource.h"
  14. #include "llvm/Support/Casting.h"
  15. #include "llvm/IR/LLVMContext.h"
  16. #include "llvm/IR/Type.h"
  17. #include "llvm/IR/Instructions.h"
  18. #include "Support/DXIncludes.h"
  19. #include "DxbcUtil.h"
  20. using namespace llvm;
  21. namespace hlsl {
  22. //------------------------------------------------------------------------------
  23. //
  24. // CMask methods.
  25. //
  26. CMask::CMask() : m_Mask(0) {
  27. }
  28. CMask::CMask(BYTE Mask) : m_Mask(Mask) {
  29. DXASSERT(Mask <= DXBC::kAllCompMask, "otherwise the caller did not check");
  30. }
  31. CMask::CMask(BYTE c0, BYTE c1, BYTE c2, BYTE c3) {
  32. DXASSERT(c0<=1 && c1<=1 && c2<=1 && c3<=1, "otherwise the caller did not check");
  33. m_Mask = c0 | (c1<<1) | (c2<<2) | (c3<<3);
  34. }
  35. CMask::CMask(BYTE StartComp, BYTE NumComp) {
  36. DXASSERT(StartComp<DXBC::kAllCompMask && NumComp<=DXBC::kAllCompMask && (StartComp+NumComp-1)<DXBC::kAllCompMask, "otherwise the caller did not check");
  37. m_Mask = 0;
  38. for (BYTE c = StartComp; c < StartComp+NumComp; c++) {
  39. m_Mask |= (1<<c);
  40. }
  41. }
  42. BYTE CMask::ToByte() const {
  43. DXASSERT(m_Mask <= DXBC::kAllCompMask, "otherwise the caller did not check");
  44. return m_Mask;
  45. }
  46. static bool IsSet(BYTE Mask, BYTE c) {
  47. return CMask(Mask).IsSet(c);
  48. }
  49. bool CMask::IsSet(BYTE c) const {
  50. DXASSERT(c < DXBC::kWidth, "otherwise the caller did not check");
  51. return (m_Mask & (1<<c)) != 0;
  52. }
  53. void CMask::Set(BYTE c) {
  54. DXASSERT(c < DXBC::kWidth, "otherwise the caller did not check");
  55. m_Mask = m_Mask | (1<<c);
  56. }
  57. CMask CMask::operator|(const CMask &o) {
  58. return CMask(m_Mask | o.m_Mask);
  59. }
  60. BYTE CMask::GetNumActiveComps() const {
  61. DXASSERT(m_Mask <= DXBC::kAllCompMask, "otherwise the caller did not check");
  62. BYTE n = 0;
  63. for (BYTE c = 0; c < DXBC::kWidth; c++) {
  64. n += (m_Mask >> c) & 1;
  65. }
  66. return n;
  67. }
  68. BYTE CMask::GetNumActiveRangeComps() const {
  69. DXASSERT(m_Mask <= DXBC::kAllCompMask, "otherwise the caller did not check");
  70. if ((m_Mask & DXBC::kAllCompMask) == 0)
  71. return 0;
  72. BYTE FirstComp = 0;
  73. for (BYTE c = 0; c < DXBC::kWidth; c++) {
  74. if (m_Mask & (1 << c)) {
  75. FirstComp = c;
  76. break;
  77. }
  78. }
  79. BYTE LastComp = 0;
  80. for (BYTE c1 = 0; c1 < DXBC::kWidth; c1++) {
  81. BYTE c = DXBC::kWidth - 1 - c1;
  82. if (m_Mask & (1 << c)) {
  83. LastComp = c;
  84. break;
  85. }
  86. }
  87. return LastComp - FirstComp + 1;
  88. }
  89. BYTE CMask::MakeMask(BYTE c0, BYTE c1, BYTE c2, BYTE c3) {
  90. return CMask(c0,c1,c2,c3).ToByte();
  91. }
  92. CMask CMask::MakeXYZWMask() {
  93. return CMask(DXBC::kAllCompMask);
  94. }
  95. CMask CMask::MakeFirstNCompMask(BYTE n) {
  96. switch(n) {
  97. case 0: return CMask(0,0,0,0);
  98. case 1: return CMask(1,0,0,0);
  99. case 2: return CMask(1,1,0,0);
  100. case 3: return CMask(1,1,1,0);
  101. default: DXASSERT(n == 4, "otherwise the caller did not pass the right number of components");
  102. return CMask(1,1,1,1);
  103. }
  104. }
  105. CMask CMask::MakeCompMask(BYTE Component) {
  106. DXASSERT(Component < DXBC::kWidth, "otherwise the caller should have checked that the mask is non-zero");
  107. return CMask((BYTE)(1 << Component));
  108. }
  109. CMask CMask::MakeXMask() {
  110. return MakeCompMask(0);
  111. }
  112. bool CMask::IsValidDoubleMask(const CMask &Mask) {
  113. BYTE b = Mask.ToByte();
  114. return b == 0xF || b == 0xC || b == 0x3;
  115. }
  116. CMask CMask::GetMaskForDoubleOperation(const CMask &Mask) {
  117. switch (Mask.GetNumActiveComps()) {
  118. case 0: return CMask(0,0,0,0);
  119. case 1: return CMask(1,1,0,0);
  120. case 2: return CMask(1,1,1,1);
  121. }
  122. DXASSERT(false, "otherwise missed a case");
  123. return CMask();
  124. }
  125. BYTE CMask::GetFirstActiveComp() const {
  126. DXASSERT(m_Mask > 0, "otherwise the caller should have checked that the mask is non-zero");
  127. for (BYTE c = 0; c < DXBC::kWidth; c++) {
  128. if ((m_Mask >> c) & 1)
  129. return c;
  130. }
  131. return _UI8_MAX;
  132. }
  133. CMask CMask::FromDXBC(const unsigned DxbcMask) {
  134. return CMask(DxbcMask >> D3D10_SB_OPERAND_4_COMPONENT_MASK_SHIFT);
  135. }
  136. //------------------------------------------------------------------------------
  137. //
  138. // OperandValue methods.
  139. //
  140. OperandValue::OperandValue() {
  141. m_pVal[0] = m_pVal[1] = m_pVal[2] = m_pVal[3] = nullptr;
  142. }
  143. OperandValue::PValue &OperandValue::operator[](BYTE c) {
  144. DXASSERT_NOMSG(c < DXBC::kWidth);
  145. return m_pVal[c];
  146. }
  147. const OperandValue::PValue &OperandValue::operator[](BYTE c) const {
  148. DXASSERT_NOMSG(c < DXBC::kWidth);
  149. DXASSERT(m_pVal[c] != nullptr, "otherwise required component value has not been set");
  150. return m_pVal[c];
  151. }
  152. //------------------------------------------------------------------------------
  153. //
  154. // OperandValue methods.
  155. //
  156. OperandValueHelper::OperandValueHelper()
  157. : m_pOpValue(nullptr)
  158. , m_Index(DXBC::kWidth) {
  159. m_Components[0] = m_Components[1] = m_Components[2] = m_Components[3] = kBadComp;
  160. }
  161. OperandValueHelper::OperandValueHelper(OperandValue &OpValue, const CMask &Mask, const D3D10ShaderBinary::COperandBase &O)
  162. : m_pOpValue(&OpValue) {
  163. switch (O.m_ComponentSelection) {
  164. case D3D10_SB_OPERAND_4_COMPONENT_SWIZZLE_MODE:
  165. Initialize(Mask, O.m_Swizzle);
  166. break;
  167. case D3D10_SB_OPERAND_4_COMPONENT_SELECT_1_MODE: {
  168. BYTE Swizzle[DXBC::kWidth] = { (BYTE)O.m_ComponentName, (BYTE)O.m_ComponentName,
  169. (BYTE)O.m_ComponentName, (BYTE)O.m_ComponentName };
  170. Initialize(Mask, Swizzle);
  171. break;
  172. }
  173. case D3D10_SB_OPERAND_4_COMPONENT_MASK_MODE: {
  174. BYTE Swizzle[DXBC::kWidth] = { (BYTE)D3D10_SB_4_COMPONENT_X, (BYTE)D3D10_SB_4_COMPONENT_Y,
  175. (BYTE)D3D10_SB_4_COMPONENT_Z, (BYTE)D3D10_SB_4_COMPONENT_W };
  176. Initialize(Mask, Swizzle);
  177. break;
  178. }
  179. default:
  180. DXASSERT_DXBC(false);
  181. }
  182. }
  183. void OperandValueHelper::Initialize(const CMask &Mask, const BYTE CompSwizzle[DXBC::kWidth]) {
  184. DXASSERT(Mask.GetNumActiveComps() > 0, "otherwise the caller passed incorrect mask");
  185. for (BYTE c = 0; c < DXBC::kWidth; c++) {
  186. DXASSERT(m_pOpValue->m_pVal[c] == nullptr, "otherwise the caller passed a stale/corrupt OpValue");
  187. if (Mask.IsSet(c))
  188. m_Components[c] = CompSwizzle[c];
  189. else
  190. m_Components[c] = kBadComp;
  191. }
  192. for (m_Index = 0; m_Index < DXBC::kWidth; m_Index++)
  193. if (m_Components[m_Index] != kBadComp)
  194. break;
  195. DXASSERT_NOMSG(m_Index < DXBC::kWidth);
  196. }
  197. BYTE OperandValueHelper::GetComp() const {
  198. return (m_Index < DXBC::kWidth) ? m_Components[m_Index] : kBadComp;
  199. }
  200. bool OperandValueHelper::IsDone() const {
  201. return m_Index == DXBC::kWidth;
  202. }
  203. void OperandValueHelper::Advance() {
  204. if (IsDone()) {
  205. DXASSERT(false, "otherwise Advance got called past the last active component, which is not the intended use");
  206. return;
  207. }
  208. // 1. Look for the next component that needs a value.
  209. // 2. Disable m_Components[c] that are equal to Comp to iterate only through unique components.
  210. BYTE Comp = m_Components[m_Index];
  211. DXASSERT_NOMSG(Comp < DXBC::kWidth);
  212. m_Components[m_Index] = kBadComp;
  213. BYTE StartComp = m_Index + 1;
  214. m_Index = DXBC::kWidth;
  215. for (BYTE c = StartComp; c < DXBC::kWidth; c++) {
  216. if (m_Components[c] == Comp) {
  217. m_Components[c] = kBadComp;
  218. } else if (m_Components[c] != kBadComp) {
  219. if (m_Index == DXBC::kWidth)
  220. m_Index = c;
  221. }
  222. }
  223. }
  224. void OperandValueHelper::SetValue(llvm::Value *pValue) {
  225. DXASSERT(m_Index < DXBC::kWidth, "otherwise the client uses the instance after all unique components have been set");
  226. DXASSERT(m_pOpValue->m_pVal[m_Index] == nullptr, "otherwise the client tried to redefine a value, which is not the intended use");
  227. BYTE Comp = m_Components[m_Index];
  228. DXASSERT_NOMSG(Comp < DXBC::kWidth);
  229. for (BYTE c = m_Index; c < DXBC::kWidth; c++) {
  230. if (m_Components[c] == Comp) {
  231. DXASSERT_NOMSG(m_pOpValue->m_pVal[c] == nullptr);
  232. m_pOpValue->m_pVal[c] = pValue;
  233. }
  234. }
  235. }
  236. //------------------------------------------------------------------------------
  237. //
  238. // DXBC namespace functions.
  239. //
  240. namespace DXBC {
  241. ShaderModel::Kind GetShaderModelKind(D3D10_SB_TOKENIZED_PROGRAM_TYPE Type) {
  242. switch (Type) {
  243. case D3D10_SB_PIXEL_SHADER: return ShaderModel::Kind::Pixel;
  244. case D3D10_SB_VERTEX_SHADER: return ShaderModel::Kind::Vertex;
  245. case D3D10_SB_GEOMETRY_SHADER: return ShaderModel::Kind::Geometry;
  246. case D3D11_SB_HULL_SHADER: return ShaderModel::Kind::Hull;
  247. case D3D11_SB_DOMAIN_SHADER: return ShaderModel::Kind::Domain;
  248. case D3D11_SB_COMPUTE_SHADER: return ShaderModel::Kind::Compute;
  249. default: return ShaderModel::Kind::Invalid;
  250. }
  251. }
  252. bool IsFlagDisableOptimizations (unsigned Flags) { return (Flags & D3D11_1_SB_GLOBAL_FLAG_SKIP_OPTIMIZATION) != 0; }
  253. bool IsFlagDisableMathRefactoring (unsigned Flags) { return (Flags & D3D10_SB_GLOBAL_FLAG_REFACTORING_ALLOWED) == 0; }
  254. bool IsFlagEnableDoublePrecision (unsigned Flags) { return (Flags & D3D11_SB_GLOBAL_FLAG_ENABLE_DOUBLE_PRECISION_FLOAT_OPS) != 0; }
  255. bool IsFlagForceEarlyDepthStencil (unsigned Flags) { return (Flags & D3D11_SB_GLOBAL_FLAG_FORCE_EARLY_DEPTH_STENCIL) != 0; }
  256. bool IsFlagEnableRawAndStructuredBuffers(unsigned Flags) { return (Flags & D3D11_SB_GLOBAL_FLAG_ENABLE_RAW_AND_STRUCTURED_BUFFERS) != 0; }
  257. bool IsFlagEnableMinPrecision (unsigned Flags) { return (Flags & D3D11_1_SB_GLOBAL_FLAG_ENABLE_MINIMUM_PRECISION) != 0; }
  258. bool IsFlagEnableDoubleExtensions (unsigned Flags) { return (Flags & D3D11_1_SB_GLOBAL_FLAG_ENABLE_DOUBLE_EXTENSIONS) != 0; }
  259. bool IsFlagEnableMSAD (unsigned Flags) { return (Flags & D3D11_1_SB_GLOBAL_FLAG_ENABLE_SHADER_EXTENSIONS) != 0; }
  260. bool IsFlagAllResourcesBound (unsigned Flags) { return (Flags & D3D12_SB_GLOBAL_FLAG_ALL_RESOURCES_BOUND) != 0; }
  261. InterpolationMode::Kind GetInterpolationModeKind(D3D_INTERPOLATION_MODE Mode) {
  262. switch (Mode) {
  263. case D3D_INTERPOLATION_UNDEFINED: return InterpolationMode::Kind::Undefined;
  264. case D3D_INTERPOLATION_CONSTANT: return InterpolationMode::Kind::Constant;
  265. case D3D_INTERPOLATION_LINEAR: return InterpolationMode::Kind::Linear;
  266. case D3D_INTERPOLATION_LINEAR_CENTROID: return InterpolationMode::Kind::LinearCentroid;
  267. case D3D_INTERPOLATION_LINEAR_NOPERSPECTIVE: return InterpolationMode::Kind::LinearNoperspective;
  268. case D3D_INTERPOLATION_LINEAR_NOPERSPECTIVE_CENTROID: return InterpolationMode::Kind::LinearNoperspectiveCentroid;
  269. case D3D_INTERPOLATION_LINEAR_SAMPLE: return InterpolationMode::Kind::LinearSample;
  270. case D3D_INTERPOLATION_LINEAR_NOPERSPECTIVE_SAMPLE: return InterpolationMode::Kind::LinearNoperspectiveSample;
  271. }
  272. DXASSERT(false, "otherwise the caller did not check the range");
  273. return InterpolationMode::Kind::Invalid;
  274. }
  275. D3D10_SB_OPERAND_TYPE GetOperandRegType(Semantic::Kind Kind, bool IsOutput) {
  276. switch (Kind) {
  277. case Semantic::Kind::Coverage:
  278. if (IsOutput) return D3D10_SB_OPERAND_TYPE_OUTPUT_COVERAGE_MASK;
  279. else return D3D11_SB_OPERAND_TYPE_INPUT_COVERAGE_MASK;
  280. case Semantic::Kind::InnerCoverage: return D3D11_SB_OPERAND_TYPE_INNER_COVERAGE;
  281. case Semantic::Kind::PrimitiveID: return D3D10_SB_OPERAND_TYPE_INPUT_PRIMITIVEID;
  282. case Semantic::Kind::Depth: return D3D10_SB_OPERAND_TYPE_OUTPUT_DEPTH;
  283. case Semantic::Kind::DepthLessEqual: return D3D11_SB_OPERAND_TYPE_OUTPUT_DEPTH_LESS_EQUAL;
  284. case Semantic::Kind::DepthGreaterEqual: return D3D11_SB_OPERAND_TYPE_OUTPUT_DEPTH_GREATER_EQUAL;
  285. case Semantic::Kind::StencilRef: return D3D11_SB_OPERAND_TYPE_OUTPUT_STENCIL_REF;
  286. }
  287. DXASSERT(false, "otherwise the caller passed wrong semantic type");
  288. return D3D10_SB_OPERAND_TYPE_TEMP;
  289. }
  290. DxilResource::Kind GetResourceKind(D3D10_SB_RESOURCE_DIMENSION ResType) {
  291. switch (ResType) {
  292. case D3D10_SB_RESOURCE_DIMENSION_UNKNOWN: return DxilResource::Kind::Invalid;
  293. case D3D10_SB_RESOURCE_DIMENSION_BUFFER: return DxilResource::Kind::TypedBuffer;
  294. case D3D10_SB_RESOURCE_DIMENSION_TEXTURE1D: return DxilResource::Kind::Texture1D;
  295. case D3D10_SB_RESOURCE_DIMENSION_TEXTURE2D: return DxilResource::Kind::Texture2D;
  296. case D3D10_SB_RESOURCE_DIMENSION_TEXTURE2DMS: return DxilResource::Kind::Texture2DMS;
  297. case D3D10_SB_RESOURCE_DIMENSION_TEXTURE3D: return DxilResource::Kind::Texture3D;
  298. case D3D10_SB_RESOURCE_DIMENSION_TEXTURECUBE: return DxilResource::Kind::TextureCube;
  299. case D3D10_SB_RESOURCE_DIMENSION_TEXTURE1DARRAY: return DxilResource::Kind::Texture1DArray;
  300. case D3D10_SB_RESOURCE_DIMENSION_TEXTURE2DARRAY: return DxilResource::Kind::Texture2DArray;
  301. case D3D10_SB_RESOURCE_DIMENSION_TEXTURE2DMSARRAY: return DxilResource::Kind::Texture2DMSArray;
  302. case D3D10_SB_RESOURCE_DIMENSION_TEXTURECUBEARRAY: return DxilResource::Kind::TextureCubeArray;
  303. case D3D11_SB_RESOURCE_DIMENSION_RAW_BUFFER: return DxilResource::Kind::RawBuffer;
  304. case D3D11_SB_RESOURCE_DIMENSION_STRUCTURED_BUFFER: return DxilResource::Kind::RawBuffer;
  305. }
  306. DXASSERT(false, "otherwise the caller did not check the range");
  307. return DxilResource::Kind::Invalid;
  308. }
  309. BYTE GetNumResCoords(DxilResource::Kind ResKind) {
  310. switch (ResKind) {
  311. case DxilResource::Kind::Texture1D: return 1;
  312. case DxilResource::Kind::Texture2D: return 2;
  313. case DxilResource::Kind::Texture2DMS: return 2;
  314. case DxilResource::Kind::Texture3D: return 3;
  315. case DxilResource::Kind::TextureCube: return 3;
  316. case DxilResource::Kind::Texture1DArray: return 2;
  317. case DxilResource::Kind::Texture2DArray: return 3;
  318. case DxilResource::Kind::Texture2DMSArray: return 3;
  319. case DxilResource::Kind::TextureCubeArray: return 4;
  320. case DxilResource::Kind::TypedBuffer: return 1;
  321. case DxilResource::Kind::RawBuffer: return 1;
  322. }
  323. DXASSERT(false, "otherwise the caller did not pass correct resource kind");
  324. return 0;
  325. }
  326. BYTE GetNumResOffsets(DxilResource::Kind ResKind) {
  327. switch (ResKind) {
  328. case DxilResource::Kind::Texture1D: return 1;
  329. case DxilResource::Kind::Texture2D: return 2;
  330. case DxilResource::Kind::Texture2DMS: return 2;
  331. case DxilResource::Kind::Texture3D: return 3;
  332. case DxilResource::Kind::TextureCube: return 3;
  333. case DxilResource::Kind::Texture1DArray: return 1;
  334. case DxilResource::Kind::Texture2DArray: return 2;
  335. case DxilResource::Kind::Texture2DMSArray: return 2;
  336. case DxilResource::Kind::TextureCubeArray: return 3;
  337. case DxilResource::Kind::TypedBuffer: return 0;
  338. case DxilResource::Kind::RawBuffer: return 0;
  339. }
  340. DXASSERT(false, "otherwise the caller did not pass correct resource kind");
  341. return 0;
  342. }
  343. CompType GetCompType(D3D_REGISTER_COMPONENT_TYPE CompTy) {
  344. switch (CompTy) {
  345. case D3D_REGISTER_COMPONENT_FLOAT32: return CompType::getF32();
  346. case D3D_REGISTER_COMPONENT_SINT32: return CompType::getI32();
  347. case D3D_REGISTER_COMPONENT_UINT32: return CompType::getU32();
  348. }
  349. DXASSERT(false, "incorrect component type value");
  350. return CompType();
  351. }
  352. CompType GetCompTypeWithMinPrec(D3D_REGISTER_COMPONENT_TYPE BaseCompTy,
  353. D3D11_SB_OPERAND_MIN_PRECISION MinPrec) {
  354. switch (BaseCompTy) {
  355. case D3D_REGISTER_COMPONENT_FLOAT32:
  356. switch (MinPrec) {
  357. case D3D11_SB_OPERAND_MIN_PRECISION_DEFAULT: return CompType::getF32();
  358. case D3D11_SB_OPERAND_MIN_PRECISION_FLOAT_16: __fallthrough;
  359. case D3D11_SB_OPERAND_MIN_PRECISION_FLOAT_2_8: return CompType::getF16();
  360. }
  361. break;
  362. case D3D_REGISTER_COMPONENT_SINT32:
  363. switch (MinPrec) {
  364. case D3D11_SB_OPERAND_MIN_PRECISION_DEFAULT: return CompType::getI32();
  365. case D3D11_SB_OPERAND_MIN_PRECISION_SINT_16: return CompType::getI16();
  366. case D3D11_SB_OPERAND_MIN_PRECISION_UINT_16: return CompType::getU16();
  367. }
  368. break;
  369. case D3D_REGISTER_COMPONENT_UINT32:
  370. switch (MinPrec) {
  371. case D3D11_SB_OPERAND_MIN_PRECISION_DEFAULT: return CompType::getU32();
  372. case D3D11_SB_OPERAND_MIN_PRECISION_SINT_16: return CompType::getI16();
  373. case D3D11_SB_OPERAND_MIN_PRECISION_UINT_16: return CompType::getU16();
  374. }
  375. break;
  376. }
  377. DXASSERT(false, "otherwise incorrect combination of type and min-precision");
  378. return CompType();
  379. }
  380. CompType GetCompTypeWithMinPrec(CompType BaseCompTy,
  381. D3D11_SB_OPERAND_MIN_PRECISION MinPrec) {
  382. switch (BaseCompTy.GetKind()) {
  383. case CompType::Kind::F32:
  384. switch (MinPrec) {
  385. case D3D11_SB_OPERAND_MIN_PRECISION_DEFAULT: return CompType::getF32();
  386. case D3D11_SB_OPERAND_MIN_PRECISION_FLOAT_16: __fallthrough;
  387. case D3D11_SB_OPERAND_MIN_PRECISION_FLOAT_2_8: return CompType::getF16();
  388. }
  389. break;
  390. case CompType::Kind::I32:
  391. switch (MinPrec) {
  392. case D3D11_SB_OPERAND_MIN_PRECISION_DEFAULT: return CompType::getI32();
  393. case D3D11_SB_OPERAND_MIN_PRECISION_SINT_16: return CompType::getI16();
  394. case D3D11_SB_OPERAND_MIN_PRECISION_UINT_16: return CompType::getU16();
  395. }
  396. break;
  397. case CompType::Kind::U32:
  398. switch (MinPrec) {
  399. case D3D11_SB_OPERAND_MIN_PRECISION_DEFAULT: return CompType::getU32();
  400. case D3D11_SB_OPERAND_MIN_PRECISION_SINT_16: return CompType::getI16();
  401. case D3D11_SB_OPERAND_MIN_PRECISION_UINT_16: return CompType::getU16();
  402. }
  403. break;
  404. case CompType::Kind::F64:
  405. return CompType::getF64();
  406. }
  407. DXASSERT(false, "otherwise incorrect combination of type and min-precision");
  408. return CompType();
  409. }
  410. static CompType GetFullPrecCompType(CompType CompTy) {
  411. switch (CompTy.GetKind()) {
  412. case CompType::Kind::F16: return CompType::getF32();
  413. case CompType::Kind::I16: return CompType::getI32();
  414. case CompType::Kind::U16: return CompType::getU32();
  415. default: return CompTy;
  416. }
  417. }
  418. CompType GetCompTypeFromMinPrec(D3D11_SB_OPERAND_MIN_PRECISION MinPrec,
  419. CompType DefaultPrecCompType) {
  420. switch (MinPrec) {
  421. case D3D11_SB_OPERAND_MIN_PRECISION_DEFAULT: return GetFullPrecCompType(DefaultPrecCompType);
  422. case D3D11_SB_OPERAND_MIN_PRECISION_FLOAT_16: __fallthrough;
  423. case D3D11_SB_OPERAND_MIN_PRECISION_FLOAT_2_8: return CompType::getF16();
  424. case D3D11_SB_OPERAND_MIN_PRECISION_SINT_16: return CompType::getI16();
  425. case D3D11_SB_OPERAND_MIN_PRECISION_UINT_16: return CompType::getU16();
  426. default: DXASSERT_DXBC(false); return GetFullPrecCompType(DefaultPrecCompType);
  427. }
  428. }
  429. CompType GetResCompType(D3D10_SB_RESOURCE_RETURN_TYPE CompTy) {
  430. switch(CompTy) {
  431. case D3D10_SB_RETURN_TYPE_UNORM: return CompType::getF32();
  432. case D3D10_SB_RETURN_TYPE_SNORM: return CompType::getF32();
  433. case D3D10_SB_RETURN_TYPE_SINT: return CompType::getI32();
  434. case D3D10_SB_RETURN_TYPE_UINT: return CompType::getU32();
  435. case D3D10_SB_RETURN_TYPE_FLOAT: return CompType::getF32();
  436. case D3D10_SB_RETURN_TYPE_MIXED: return CompType::getInvalid();
  437. case D3D11_SB_RETURN_TYPE_DOUBLE: return CompType::getF64();
  438. case D3D11_SB_RETURN_TYPE_CONTINUED: return CompType::getInvalid();
  439. case D3D11_SB_RETURN_TYPE_UNUSED: return CompType::getInvalid();
  440. default: DXASSERT(false, "invalid comp type"); return CompType::getInvalid();
  441. }
  442. }
  443. CompType GetDeclResCompType(D3D10_SB_RESOURCE_RETURN_TYPE CompTy) {
  444. switch(CompTy) {
  445. case D3D10_SB_RETURN_TYPE_UNORM: return CompType::getUNormF32();
  446. case D3D10_SB_RETURN_TYPE_SNORM: return CompType::getSNormF32();
  447. case D3D10_SB_RETURN_TYPE_SINT: return CompType::getI32();
  448. case D3D10_SB_RETURN_TYPE_UINT: return CompType::getU32();
  449. case D3D10_SB_RETURN_TYPE_FLOAT: return CompType::getF32();
  450. case D3D10_SB_RETURN_TYPE_MIXED: return CompType::getInvalid();
  451. case D3D11_SB_RETURN_TYPE_DOUBLE: return CompType::getF64();
  452. case D3D11_SB_RETURN_TYPE_CONTINUED: return CompType::getInvalid();
  453. case D3D11_SB_RETURN_TYPE_UNUSED: return CompType::getInvalid();
  454. default: DXASSERT(false, "invalid comp type"); return CompType::getInvalid();
  455. }
  456. }
  457. static const char s_ComponentName[kWidth] = { 'x', 'y', 'z', 'w' };
  458. char GetCompName(BYTE c) {
  459. DXASSERT(c < kWidth, "otherwise the caller did not pass the right component value");
  460. return s_ComponentName[c];
  461. }
  462. DxilSampler::SamplerKind GetSamplerKind(D3D10_SB_SAMPLER_MODE Mode) {
  463. switch(Mode) {
  464. case D3D10_SB_SAMPLER_MODE_DEFAULT: return DxilSampler::SamplerKind::Default;
  465. case D3D10_SB_SAMPLER_MODE_COMPARISON: return DxilSampler::SamplerKind::Comparison;
  466. case D3D10_SB_SAMPLER_MODE_MONO: return DxilSampler::SamplerKind::Mono;
  467. }
  468. DXASSERT(false, "otherwise the caller did not pass the right Mode");
  469. return DxilSampler::SamplerKind::Invalid;
  470. }
  471. unsigned GetRegIndex(unsigned Reg, unsigned Comp) {
  472. return Reg * 4 + Comp;
  473. }
  474. DXIL::AtomicBinOpCode GetAtomicBinOp(D3D10_SB_OPCODE_TYPE DxbcOpCode) {
  475. switch (DxbcOpCode) {
  476. case D3D11_SB_OPCODE_ATOMIC_IADD: return DXIL::AtomicBinOpCode::Add;
  477. case D3D11_SB_OPCODE_ATOMIC_AND: return DXIL::AtomicBinOpCode::And;
  478. case D3D11_SB_OPCODE_ATOMIC_OR: return DXIL::AtomicBinOpCode::Or;
  479. case D3D11_SB_OPCODE_ATOMIC_XOR: return DXIL::AtomicBinOpCode::Xor;
  480. case D3D11_SB_OPCODE_ATOMIC_IMAX: return DXIL::AtomicBinOpCode::IMax;
  481. case D3D11_SB_OPCODE_ATOMIC_IMIN: return DXIL::AtomicBinOpCode::IMin;
  482. case D3D11_SB_OPCODE_ATOMIC_UMAX: return DXIL::AtomicBinOpCode::UMax;
  483. case D3D11_SB_OPCODE_ATOMIC_UMIN: return DXIL::AtomicBinOpCode::UMin;
  484. case D3D11_SB_OPCODE_IMM_ATOMIC_EXCH: return DXIL::AtomicBinOpCode::Exchange;
  485. case D3D11_SB_OPCODE_IMM_ATOMIC_IADD: return DXIL::AtomicBinOpCode::Add;
  486. case D3D11_SB_OPCODE_IMM_ATOMIC_AND: return DXIL::AtomicBinOpCode::And;
  487. case D3D11_SB_OPCODE_IMM_ATOMIC_OR: return DXIL::AtomicBinOpCode::Or;
  488. case D3D11_SB_OPCODE_IMM_ATOMIC_XOR: return DXIL::AtomicBinOpCode::Xor;
  489. case D3D11_SB_OPCODE_IMM_ATOMIC_IMAX: return DXIL::AtomicBinOpCode::IMax;
  490. case D3D11_SB_OPCODE_IMM_ATOMIC_IMIN: return DXIL::AtomicBinOpCode::IMin;
  491. case D3D11_SB_OPCODE_IMM_ATOMIC_UMAX: return DXIL::AtomicBinOpCode::UMax;
  492. case D3D11_SB_OPCODE_IMM_ATOMIC_UMIN: return DXIL::AtomicBinOpCode::UMin;
  493. case D3D11_SB_OPCODE_ATOMIC_CMP_STORE:
  494. case D3D11_SB_OPCODE_IMM_ATOMIC_CMP_EXCH:
  495. default: DXASSERT(false, "otherwise the caller did not pass the right OpCode");
  496. }
  497. return DXIL::AtomicBinOpCode::Invalid;
  498. }
  499. llvm::AtomicRMWInst::BinOp GetLlvmAtomicBinOp(D3D10_SB_OPCODE_TYPE DxbcOpCode) {
  500. switch (DxbcOpCode) {
  501. case D3D11_SB_OPCODE_ATOMIC_IADD: return llvm::AtomicRMWInst::Add;
  502. case D3D11_SB_OPCODE_ATOMIC_AND: return llvm::AtomicRMWInst::And;
  503. case D3D11_SB_OPCODE_ATOMIC_OR: return llvm::AtomicRMWInst::Or;
  504. case D3D11_SB_OPCODE_ATOMIC_XOR: return llvm::AtomicRMWInst::Xor;
  505. case D3D11_SB_OPCODE_ATOMIC_IMAX: return llvm::AtomicRMWInst::Max;
  506. case D3D11_SB_OPCODE_ATOMIC_IMIN: return llvm::AtomicRMWInst::Min;
  507. case D3D11_SB_OPCODE_ATOMIC_UMAX: return llvm::AtomicRMWInst::UMax;
  508. case D3D11_SB_OPCODE_ATOMIC_UMIN: return llvm::AtomicRMWInst::UMin;
  509. case D3D11_SB_OPCODE_IMM_ATOMIC_EXCH: return llvm::AtomicRMWInst::Xchg;
  510. case D3D11_SB_OPCODE_IMM_ATOMIC_IADD: return llvm::AtomicRMWInst::Add;
  511. case D3D11_SB_OPCODE_IMM_ATOMIC_AND: return llvm::AtomicRMWInst::And;
  512. case D3D11_SB_OPCODE_IMM_ATOMIC_OR: return llvm::AtomicRMWInst::Or;
  513. case D3D11_SB_OPCODE_IMM_ATOMIC_XOR: return llvm::AtomicRMWInst::Xor;
  514. case D3D11_SB_OPCODE_IMM_ATOMIC_IMAX: return llvm::AtomicRMWInst::Max;
  515. case D3D11_SB_OPCODE_IMM_ATOMIC_IMIN: return llvm::AtomicRMWInst::Min;
  516. case D3D11_SB_OPCODE_IMM_ATOMIC_UMAX: return llvm::AtomicRMWInst::UMax;
  517. case D3D11_SB_OPCODE_IMM_ATOMIC_UMIN: return llvm::AtomicRMWInst::UMin;
  518. case D3D11_SB_OPCODE_ATOMIC_CMP_STORE:
  519. case D3D11_SB_OPCODE_IMM_ATOMIC_CMP_EXCH:
  520. default:
  521. DXASSERT(false, "otherwise the caller did not pass the right OpCode");
  522. }
  523. return llvm::AtomicRMWInst::BAD_BINOP;
  524. }
  525. bool AtomicBinOpHasReturn(D3D10_SB_OPCODE_TYPE DxbcOpCode) {
  526. switch (DxbcOpCode)
  527. {
  528. case D3D11_SB_OPCODE_ATOMIC_AND:
  529. case D3D11_SB_OPCODE_ATOMIC_OR:
  530. case D3D11_SB_OPCODE_ATOMIC_XOR:
  531. case D3D11_SB_OPCODE_ATOMIC_IADD:
  532. case D3D11_SB_OPCODE_ATOMIC_IMAX:
  533. case D3D11_SB_OPCODE_ATOMIC_IMIN:
  534. case D3D11_SB_OPCODE_ATOMIC_UMAX:
  535. case D3D11_SB_OPCODE_ATOMIC_UMIN:
  536. case D3D11_SB_OPCODE_ATOMIC_CMP_STORE:
  537. return false;
  538. case D3D11_SB_OPCODE_IMM_ATOMIC_IADD:
  539. case D3D11_SB_OPCODE_IMM_ATOMIC_AND:
  540. case D3D11_SB_OPCODE_IMM_ATOMIC_OR:
  541. case D3D11_SB_OPCODE_IMM_ATOMIC_XOR:
  542. case D3D11_SB_OPCODE_IMM_ATOMIC_EXCH:
  543. case D3D11_SB_OPCODE_IMM_ATOMIC_IMAX:
  544. case D3D11_SB_OPCODE_IMM_ATOMIC_IMIN:
  545. case D3D11_SB_OPCODE_IMM_ATOMIC_UMAX:
  546. case D3D11_SB_OPCODE_IMM_ATOMIC_UMIN:
  547. case D3D11_SB_OPCODE_IMM_ATOMIC_CMP_EXCH:
  548. return true;
  549. }
  550. DXASSERT(false, "otherwise the caller did not pass the right OpCode");
  551. return false;
  552. }
  553. bool IsCompareExchAtomicBinOp(D3D10_SB_OPCODE_TYPE DxbcOpCode) {
  554. switch (DxbcOpCode)
  555. {
  556. case D3D11_SB_OPCODE_ATOMIC_CMP_STORE:
  557. case D3D11_SB_OPCODE_IMM_ATOMIC_CMP_EXCH:
  558. return true;
  559. case D3D11_SB_OPCODE_ATOMIC_AND:
  560. case D3D11_SB_OPCODE_ATOMIC_OR:
  561. case D3D11_SB_OPCODE_ATOMIC_XOR:
  562. case D3D11_SB_OPCODE_ATOMIC_IADD:
  563. case D3D11_SB_OPCODE_ATOMIC_IMAX:
  564. case D3D11_SB_OPCODE_ATOMIC_IMIN:
  565. case D3D11_SB_OPCODE_ATOMIC_UMAX:
  566. case D3D11_SB_OPCODE_ATOMIC_UMIN:
  567. case D3D11_SB_OPCODE_IMM_ATOMIC_IADD:
  568. case D3D11_SB_OPCODE_IMM_ATOMIC_AND:
  569. case D3D11_SB_OPCODE_IMM_ATOMIC_OR:
  570. case D3D11_SB_OPCODE_IMM_ATOMIC_XOR:
  571. case D3D11_SB_OPCODE_IMM_ATOMIC_EXCH:
  572. case D3D11_SB_OPCODE_IMM_ATOMIC_IMAX:
  573. case D3D11_SB_OPCODE_IMM_ATOMIC_IMIN:
  574. case D3D11_SB_OPCODE_IMM_ATOMIC_UMAX:
  575. case D3D11_SB_OPCODE_IMM_ATOMIC_UMIN:
  576. return false;
  577. }
  578. DXASSERT(false, "otherwise the caller did not pass the right OpCode");
  579. return false;
  580. }
  581. bool HasFeedback(D3D10_SB_OPCODE_TYPE OpCode) {
  582. switch (OpCode) {
  583. case D3DWDDM1_3_SB_OPCODE_GATHER4_FEEDBACK:
  584. case D3DWDDM1_3_SB_OPCODE_GATHER4_C_FEEDBACK:
  585. case D3DWDDM1_3_SB_OPCODE_GATHER4_PO_FEEDBACK:
  586. case D3DWDDM1_3_SB_OPCODE_GATHER4_PO_C_FEEDBACK:
  587. case D3DWDDM1_3_SB_OPCODE_LD_FEEDBACK:
  588. case D3DWDDM1_3_SB_OPCODE_LD_MS_FEEDBACK:
  589. case D3DWDDM1_3_SB_OPCODE_LD_UAV_TYPED_FEEDBACK:
  590. case D3DWDDM1_3_SB_OPCODE_LD_RAW_FEEDBACK:
  591. case D3DWDDM1_3_SB_OPCODE_LD_STRUCTURED_FEEDBACK:
  592. case D3DWDDM1_3_SB_OPCODE_SAMPLE_L_FEEDBACK:
  593. case D3DWDDM1_3_SB_OPCODE_SAMPLE_C_LZ_FEEDBACK:
  594. case D3DWDDM1_3_SB_OPCODE_SAMPLE_CLAMP_FEEDBACK:
  595. case D3DWDDM1_3_SB_OPCODE_SAMPLE_B_CLAMP_FEEDBACK:
  596. case D3DWDDM1_3_SB_OPCODE_SAMPLE_D_CLAMP_FEEDBACK:
  597. case D3DWDDM1_3_SB_OPCODE_SAMPLE_C_CLAMP_FEEDBACK:
  598. return true;
  599. }
  600. return false;
  601. }
  602. unsigned GetResourceSlot(D3D10_SB_OPCODE_TYPE OpCode) {
  603. switch (OpCode)
  604. {
  605. case D3D11_SB_OPCODE_STORE_UAV_TYPED:
  606. case D3D11_SB_OPCODE_STORE_RAW:
  607. case D3D11_SB_OPCODE_STORE_STRUCTURED:
  608. case D3D11_SB_OPCODE_ATOMIC_AND:
  609. case D3D11_SB_OPCODE_ATOMIC_OR:
  610. case D3D11_SB_OPCODE_ATOMIC_XOR:
  611. case D3D11_SB_OPCODE_ATOMIC_IADD:
  612. case D3D11_SB_OPCODE_ATOMIC_IMAX:
  613. case D3D11_SB_OPCODE_ATOMIC_IMIN:
  614. case D3D11_SB_OPCODE_ATOMIC_UMAX:
  615. case D3D11_SB_OPCODE_ATOMIC_UMIN:
  616. case D3D11_SB_OPCODE_ATOMIC_CMP_STORE:
  617. return 0;
  618. case D3D11_SB_OPCODE_IMM_ATOMIC_IADD:
  619. case D3D11_SB_OPCODE_IMM_ATOMIC_AND:
  620. case D3D11_SB_OPCODE_IMM_ATOMIC_OR:
  621. case D3D11_SB_OPCODE_IMM_ATOMIC_XOR:
  622. case D3D11_SB_OPCODE_IMM_ATOMIC_EXCH:
  623. case D3D11_SB_OPCODE_IMM_ATOMIC_IMAX:
  624. case D3D11_SB_OPCODE_IMM_ATOMIC_IMIN:
  625. case D3D11_SB_OPCODE_IMM_ATOMIC_UMAX:
  626. case D3D11_SB_OPCODE_IMM_ATOMIC_UMIN:
  627. case D3D11_SB_OPCODE_IMM_ATOMIC_CMP_EXCH:
  628. case D3D10_1_SB_OPCODE_SAMPLE_INFO:
  629. case D3D10_1_SB_OPCODE_SAMPLE_POS:
  630. return 1;
  631. case D3D10_SB_OPCODE_SAMPLE:
  632. case D3D10_SB_OPCODE_SAMPLE_B:
  633. case D3D10_SB_OPCODE_SAMPLE_L:
  634. case D3D10_SB_OPCODE_SAMPLE_D:
  635. case D3D10_SB_OPCODE_SAMPLE_C:
  636. case D3D10_SB_OPCODE_SAMPLE_C_LZ:
  637. case D3D10_SB_OPCODE_LD:
  638. case D3D10_SB_OPCODE_LD_MS:
  639. case D3D11_SB_OPCODE_LD_UAV_TYPED:
  640. case D3D11_SB_OPCODE_LD_RAW:
  641. case D3D10_SB_OPCODE_RESINFO:
  642. case D3D10_1_SB_OPCODE_LOD:
  643. case D3D10_1_SB_OPCODE_GATHER4:
  644. case D3D11_SB_OPCODE_GATHER4_C:
  645. return 2;
  646. case D3DWDDM1_3_SB_OPCODE_SAMPLE_CLAMP_FEEDBACK:
  647. case D3DWDDM1_3_SB_OPCODE_SAMPLE_B_CLAMP_FEEDBACK:
  648. case D3DWDDM1_3_SB_OPCODE_SAMPLE_L_FEEDBACK:
  649. case D3DWDDM1_3_SB_OPCODE_SAMPLE_D_CLAMP_FEEDBACK:
  650. case D3DWDDM1_3_SB_OPCODE_SAMPLE_C_CLAMP_FEEDBACK:
  651. case D3DWDDM1_3_SB_OPCODE_SAMPLE_C_LZ_FEEDBACK:
  652. case D3DWDDM1_3_SB_OPCODE_LD_FEEDBACK:
  653. case D3DWDDM1_3_SB_OPCODE_LD_MS_FEEDBACK:
  654. case D3DWDDM1_3_SB_OPCODE_LD_UAV_TYPED_FEEDBACK:
  655. case D3DWDDM1_3_SB_OPCODE_LD_RAW_FEEDBACK:
  656. case D3D11_SB_OPCODE_LD_STRUCTURED:
  657. case D3DWDDM1_3_SB_OPCODE_GATHER4_FEEDBACK:
  658. case D3DWDDM1_3_SB_OPCODE_GATHER4_C_FEEDBACK:
  659. case D3D11_SB_OPCODE_GATHER4_PO:
  660. case D3D11_SB_OPCODE_GATHER4_PO_C:
  661. return 3;
  662. case D3DWDDM1_3_SB_OPCODE_LD_STRUCTURED_FEEDBACK:
  663. case D3DWDDM1_3_SB_OPCODE_GATHER4_PO_FEEDBACK:
  664. case D3DWDDM1_3_SB_OPCODE_GATHER4_PO_C_FEEDBACK:
  665. return 4;
  666. }
  667. DXASSERT_NOMSG(false);
  668. return 0;
  669. }
  670. DXIL::BarrierMode GetBarrierMode(bool bSyncThreadGroup,
  671. bool bUAVFenceGlobal,
  672. bool bUAVFenceThreadGroup,
  673. bool bTGSMFence) {
  674. unsigned M = 0;
  675. if (bSyncThreadGroup)
  676. M |= (unsigned)DXIL::BarrierMode::SyncThreadGroup;
  677. if (bUAVFenceGlobal)
  678. M |= (unsigned)DXIL::BarrierMode::UAVFenceGlobal;
  679. if (bUAVFenceThreadGroup)
  680. M |= (unsigned)DXIL::BarrierMode::UAVFenceThreadGroup;
  681. if (bTGSMFence)
  682. M |= (unsigned)DXIL::BarrierMode::TGSMFence;
  683. return (DXIL::BarrierMode)M;
  684. }
  685. DXIL::InputPrimitive GetInputPrimitive(D3D10_SB_PRIMITIVE Primitive) {
  686. switch (Primitive) {
  687. case D3D10_SB_PRIMITIVE_UNDEFINED: return DXIL::InputPrimitive::Undefined;
  688. case D3D10_SB_PRIMITIVE_POINT: return DXIL::InputPrimitive::Point;
  689. case D3D10_SB_PRIMITIVE_LINE: return DXIL::InputPrimitive::Line;
  690. case D3D10_SB_PRIMITIVE_TRIANGLE: return DXIL::InputPrimitive::Triangle;
  691. case D3D10_SB_PRIMITIVE_LINE_ADJ: return DXIL::InputPrimitive::LineWithAdjacency;
  692. case D3D10_SB_PRIMITIVE_TRIANGLE_ADJ: return DXIL::InputPrimitive::TriangleWithAdjacency;
  693. case D3D11_SB_PRIMITIVE_1_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch1;
  694. case D3D11_SB_PRIMITIVE_2_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch2;
  695. case D3D11_SB_PRIMITIVE_3_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch3;
  696. case D3D11_SB_PRIMITIVE_4_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch4;
  697. case D3D11_SB_PRIMITIVE_5_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch5;
  698. case D3D11_SB_PRIMITIVE_6_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch6;
  699. case D3D11_SB_PRIMITIVE_7_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch7;
  700. case D3D11_SB_PRIMITIVE_8_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch8;
  701. case D3D11_SB_PRIMITIVE_9_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch9;
  702. case D3D11_SB_PRIMITIVE_10_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch10;
  703. case D3D11_SB_PRIMITIVE_11_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch11;
  704. case D3D11_SB_PRIMITIVE_12_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch12;
  705. case D3D11_SB_PRIMITIVE_13_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch13;
  706. case D3D11_SB_PRIMITIVE_14_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch14;
  707. case D3D11_SB_PRIMITIVE_15_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch15;
  708. case D3D11_SB_PRIMITIVE_16_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch16;
  709. case D3D11_SB_PRIMITIVE_17_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch17;
  710. case D3D11_SB_PRIMITIVE_18_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch18;
  711. case D3D11_SB_PRIMITIVE_19_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch19;
  712. case D3D11_SB_PRIMITIVE_20_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch20;
  713. case D3D11_SB_PRIMITIVE_21_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch21;
  714. case D3D11_SB_PRIMITIVE_22_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch22;
  715. case D3D11_SB_PRIMITIVE_23_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch23;
  716. case D3D11_SB_PRIMITIVE_24_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch24;
  717. case D3D11_SB_PRIMITIVE_25_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch25;
  718. case D3D11_SB_PRIMITIVE_26_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch26;
  719. case D3D11_SB_PRIMITIVE_27_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch27;
  720. case D3D11_SB_PRIMITIVE_28_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch28;
  721. case D3D11_SB_PRIMITIVE_29_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch29;
  722. case D3D11_SB_PRIMITIVE_30_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch30;
  723. case D3D11_SB_PRIMITIVE_31_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch31;
  724. case D3D11_SB_PRIMITIVE_32_CONTROL_POINT_PATCH: return DXIL::InputPrimitive::ControlPointPatch32;
  725. }
  726. DXASSERT_NOMSG(false);
  727. return DXIL::InputPrimitive::Undefined;
  728. }
  729. DXIL::PrimitiveTopology GetPrimitiveTopology(D3D10_SB_PRIMITIVE_TOPOLOGY Topology) {
  730. switch(Topology) {
  731. case D3D10_SB_PRIMITIVE_TOPOLOGY_UNDEFINED: return DXIL::PrimitiveTopology::Undefined;
  732. case D3D10_SB_PRIMITIVE_TOPOLOGY_POINTLIST: return DXIL::PrimitiveTopology::PointList;
  733. case D3D10_SB_PRIMITIVE_TOPOLOGY_LINELIST: return DXIL::PrimitiveTopology::LineList;
  734. case D3D10_SB_PRIMITIVE_TOPOLOGY_LINESTRIP: return DXIL::PrimitiveTopology::LineStrip;
  735. case D3D10_SB_PRIMITIVE_TOPOLOGY_TRIANGLELIST: return DXIL::PrimitiveTopology::TriangleList;
  736. case D3D10_SB_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP: return DXIL::PrimitiveTopology::TriangleStrip;
  737. case D3D10_SB_PRIMITIVE_TOPOLOGY_LINELIST_ADJ: __fallthrough; // The ADJ versions are redundant in DXBC and are ot used, probably put there by mistake.
  738. case D3D10_SB_PRIMITIVE_TOPOLOGY_LINESTRIP_ADJ: __fallthrough;
  739. case D3D10_SB_PRIMITIVE_TOPOLOGY_TRIANGLELIST_ADJ: __fallthrough;
  740. case D3D10_SB_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP_ADJ: __fallthrough;
  741. }
  742. IFTBOOL(false, DXC_E_INCORRECT_DXBC);
  743. return DXIL::PrimitiveTopology::Undefined;
  744. }
  745. const char *GetD3D10SBName(D3D10_SB_NAME D3DName) {
  746. switch (D3DName) {
  747. case D3D10_SB_NAME_UNDEFINED: return "undefined";
  748. case D3D10_SB_NAME_POSITION: return "SV_Position";
  749. case D3D10_SB_NAME_CLIP_DISTANCE: return "SV_ClipDistance";
  750. case D3D10_SB_NAME_CULL_DISTANCE: return "SV_CullDistance";
  751. case D3D10_SB_NAME_RENDER_TARGET_ARRAY_INDEX: return "SV_RenderTargetArrayIndex";
  752. case D3D10_SB_NAME_VIEWPORT_ARRAY_INDEX: return "SV_ViewportArrayIndex";
  753. case D3D10_SB_NAME_VERTEX_ID: return "SV_VertexID";
  754. case D3D10_SB_NAME_PRIMITIVE_ID: return "SV_PrimitiveID";
  755. case D3D10_SB_NAME_INSTANCE_ID: return "SV_InstanceID";
  756. case D3D10_SB_NAME_IS_FRONT_FACE: return "SV_IsFrontFace";
  757. case D3D10_SB_NAME_SAMPLE_INDEX: return "SV_SampleIndex";
  758. case D3D11_SB_NAME_FINAL_QUAD_U_EQ_0_EDGE_TESSFACTOR:
  759. case D3D11_SB_NAME_FINAL_QUAD_V_EQ_0_EDGE_TESSFACTOR:
  760. case D3D11_SB_NAME_FINAL_QUAD_U_EQ_1_EDGE_TESSFACTOR:
  761. case D3D11_SB_NAME_FINAL_QUAD_V_EQ_1_EDGE_TESSFACTOR:
  762. case D3D11_SB_NAME_FINAL_TRI_U_EQ_0_EDGE_TESSFACTOR:
  763. case D3D11_SB_NAME_FINAL_TRI_V_EQ_0_EDGE_TESSFACTOR:
  764. case D3D11_SB_NAME_FINAL_TRI_W_EQ_0_EDGE_TESSFACTOR:
  765. case D3D11_SB_NAME_FINAL_LINE_DETAIL_TESSFACTOR:
  766. case D3D11_SB_NAME_FINAL_LINE_DENSITY_TESSFACTOR: return "SV_TessFactor";
  767. case D3D11_SB_NAME_FINAL_QUAD_U_INSIDE_TESSFACTOR:
  768. case D3D11_SB_NAME_FINAL_QUAD_V_INSIDE_TESSFACTOR:
  769. case D3D11_SB_NAME_FINAL_TRI_INSIDE_TESSFACTOR: return "SV_InsideTessFactor";
  770. default:
  771. IFT(DXC_E_INCORRECT_DXBC);
  772. return "unknown";
  773. }
  774. }
  775. unsigned GetD3D10SBSemanticIndex(D3D10_SB_NAME D3DName) {
  776. switch (D3DName) {
  777. case D3D10_SB_NAME_UNDEFINED:
  778. case D3D10_SB_NAME_POSITION:
  779. case D3D10_SB_NAME_CLIP_DISTANCE:
  780. case D3D10_SB_NAME_CULL_DISTANCE:
  781. case D3D10_SB_NAME_RENDER_TARGET_ARRAY_INDEX:
  782. case D3D10_SB_NAME_VIEWPORT_ARRAY_INDEX:
  783. case D3D10_SB_NAME_VERTEX_ID:
  784. case D3D10_SB_NAME_PRIMITIVE_ID:
  785. case D3D10_SB_NAME_INSTANCE_ID:
  786. case D3D10_SB_NAME_IS_FRONT_FACE:
  787. case D3D10_SB_NAME_SAMPLE_INDEX: return 0;
  788. case D3D11_SB_NAME_FINAL_QUAD_U_EQ_0_EDGE_TESSFACTOR: return 0;
  789. case D3D11_SB_NAME_FINAL_QUAD_V_EQ_0_EDGE_TESSFACTOR: return 1;
  790. case D3D11_SB_NAME_FINAL_QUAD_U_EQ_1_EDGE_TESSFACTOR: return 2;
  791. case D3D11_SB_NAME_FINAL_QUAD_V_EQ_1_EDGE_TESSFACTOR: return 3;
  792. case D3D11_SB_NAME_FINAL_QUAD_U_INSIDE_TESSFACTOR: return 0;
  793. case D3D11_SB_NAME_FINAL_QUAD_V_INSIDE_TESSFACTOR: return 1;
  794. case D3D11_SB_NAME_FINAL_TRI_U_EQ_0_EDGE_TESSFACTOR: return 0;
  795. case D3D11_SB_NAME_FINAL_TRI_V_EQ_0_EDGE_TESSFACTOR: return 1;
  796. case D3D11_SB_NAME_FINAL_TRI_W_EQ_0_EDGE_TESSFACTOR: return 2;
  797. case D3D11_SB_NAME_FINAL_TRI_INSIDE_TESSFACTOR: return 0;
  798. case D3D11_SB_NAME_FINAL_LINE_DETAIL_TESSFACTOR: return 0;
  799. case D3D11_SB_NAME_FINAL_LINE_DENSITY_TESSFACTOR: return 1;
  800. default: return 0;
  801. }
  802. }
  803. D3D_REGISTER_COMPONENT_TYPE GetD3DRegCompType(D3D10_SB_NAME D3DName) {
  804. switch (D3DName) {
  805. case D3D10_SB_NAME_POSITION:
  806. case D3D10_SB_NAME_CLIP_DISTANCE:
  807. case D3D10_SB_NAME_CULL_DISTANCE: return D3D_REGISTER_COMPONENT_FLOAT32;
  808. case D3D10_SB_NAME_RENDER_TARGET_ARRAY_INDEX:
  809. case D3D10_SB_NAME_VIEWPORT_ARRAY_INDEX:
  810. case D3D10_SB_NAME_VERTEX_ID:
  811. case D3D10_SB_NAME_PRIMITIVE_ID:
  812. case D3D10_SB_NAME_INSTANCE_ID:
  813. case D3D10_SB_NAME_IS_FRONT_FACE:
  814. case D3D10_SB_NAME_SAMPLE_INDEX: return D3D_REGISTER_COMPONENT_UINT32;
  815. case D3D10_SB_NAME_UNDEFINED: // this shpild not be called for an undefined name.
  816. case D3D11_SB_NAME_FINAL_QUAD_U_EQ_0_EDGE_TESSFACTOR:
  817. case D3D11_SB_NAME_FINAL_QUAD_V_EQ_0_EDGE_TESSFACTOR:
  818. case D3D11_SB_NAME_FINAL_QUAD_U_EQ_1_EDGE_TESSFACTOR:
  819. case D3D11_SB_NAME_FINAL_QUAD_V_EQ_1_EDGE_TESSFACTOR:
  820. case D3D11_SB_NAME_FINAL_QUAD_U_INSIDE_TESSFACTOR:
  821. case D3D11_SB_NAME_FINAL_QUAD_V_INSIDE_TESSFACTOR:
  822. case D3D11_SB_NAME_FINAL_TRI_U_EQ_0_EDGE_TESSFACTOR:
  823. case D3D11_SB_NAME_FINAL_TRI_V_EQ_0_EDGE_TESSFACTOR:
  824. case D3D11_SB_NAME_FINAL_TRI_W_EQ_0_EDGE_TESSFACTOR:
  825. case D3D11_SB_NAME_FINAL_TRI_INSIDE_TESSFACTOR:
  826. case D3D11_SB_NAME_FINAL_LINE_DETAIL_TESSFACTOR:
  827. case D3D11_SB_NAME_FINAL_LINE_DENSITY_TESSFACTOR:
  828. default:
  829. IFT(DXC_E_INCORRECT_DXBC);
  830. return D3D_REGISTER_COMPONENT_UNKNOWN;
  831. }
  832. }
  833. const char *GetSemanticNameFromD3DName(D3D_NAME D3DName) {
  834. switch (D3DName) {
  835. case D3D_NAME_UNDEFINED: return "undefined";
  836. case D3D_NAME_POSITION: return "SV_Position";
  837. case D3D_NAME_CLIP_DISTANCE: return "SV_ClipDistance";
  838. case D3D_NAME_CULL_DISTANCE: return "SV_CullDistance";
  839. case D3D_NAME_RENDER_TARGET_ARRAY_INDEX: return "SV_RenderTargetArrayIndex";
  840. case D3D_NAME_VIEWPORT_ARRAY_INDEX: return "SV_ViewportArrayIndex";
  841. case D3D_NAME_VERTEX_ID: return "SV_VertexID";
  842. case D3D_NAME_PRIMITIVE_ID: return "SV_PrimitiveID";
  843. case D3D_NAME_INSTANCE_ID: return "SV_InstanceID";
  844. case D3D_NAME_IS_FRONT_FACE: return "SV_IsFrontFace";
  845. case D3D_NAME_SAMPLE_INDEX: return "SV_SampleIndex";
  846. case D3D_NAME_FINAL_QUAD_EDGE_TESSFACTOR: return "SV_TessFactor";
  847. case D3D_NAME_FINAL_QUAD_INSIDE_TESSFACTOR: return "SV_InsideTessFactor";
  848. case D3D_NAME_FINAL_TRI_EDGE_TESSFACTOR: return "SV_TessFactor";
  849. case D3D_NAME_FINAL_TRI_INSIDE_TESSFACTOR: return "SV_InsideTessFactor";
  850. case D3D_NAME_FINAL_LINE_DETAIL_TESSFACTOR: return "SV_TessFactor";
  851. case D3D_NAME_FINAL_LINE_DENSITY_TESSFACTOR: return "SV_TessFactor";
  852. case D3D_NAME_TARGET: return "SV_Target";
  853. case D3D_NAME_DEPTH: return "SV_Depth";
  854. case D3D_NAME_COVERAGE: return "SV_Coverage";
  855. case D3D_NAME_DEPTH_GREATER_EQUAL: return "SV_DepthGreaterEqual";
  856. case D3D_NAME_DEPTH_LESS_EQUAL: return "SV_DepthLessEqual";
  857. case D3D_NAME_STENCIL_REF: return "SV_StencilRef";
  858. case D3D_NAME_INNER_COVERAGE: return "SV_InnerCoverage";
  859. default: DXASSERT_NOMSG(false); return "undefined";
  860. }
  861. }
  862. unsigned GetSemanticIndexFromD3DName(D3D_NAME D3DName) {
  863. switch (D3DName) {
  864. case D3D_NAME_UNDEFINED:
  865. case D3D_NAME_POSITION:
  866. case D3D_NAME_CLIP_DISTANCE:
  867. case D3D_NAME_CULL_DISTANCE:
  868. case D3D_NAME_RENDER_TARGET_ARRAY_INDEX:
  869. case D3D_NAME_VIEWPORT_ARRAY_INDEX:
  870. case D3D_NAME_VERTEX_ID:
  871. case D3D_NAME_PRIMITIVE_ID:
  872. case D3D_NAME_INSTANCE_ID:
  873. case D3D_NAME_IS_FRONT_FACE:
  874. case D3D_NAME_SAMPLE_INDEX:
  875. case D3D_NAME_FINAL_QUAD_EDGE_TESSFACTOR:
  876. case D3D_NAME_FINAL_QUAD_INSIDE_TESSFACTOR:
  877. case D3D_NAME_FINAL_TRI_EDGE_TESSFACTOR:
  878. case D3D_NAME_FINAL_TRI_INSIDE_TESSFACTOR:
  879. case D3D_NAME_TARGET:
  880. case D3D_NAME_DEPTH:
  881. case D3D_NAME_COVERAGE:
  882. case D3D_NAME_DEPTH_GREATER_EQUAL:
  883. case D3D_NAME_DEPTH_LESS_EQUAL:
  884. case D3D_NAME_STENCIL_REF:
  885. case D3D_NAME_INNER_COVERAGE: return UINT_MAX;
  886. case D3D_NAME_FINAL_LINE_DETAIL_TESSFACTOR: return 0;
  887. case D3D_NAME_FINAL_LINE_DENSITY_TESSFACTOR: return 1;
  888. default: DXASSERT_NOMSG(false); return UINT_MAX;
  889. }
  890. }
  891. DXIL::TessellatorDomain GetTessellatorDomain(D3D11_SB_TESSELLATOR_DOMAIN TessDomain) {
  892. switch (TessDomain) {
  893. case D3D11_SB_TESSELLATOR_DOMAIN_UNDEFINED: return DXIL::TessellatorDomain::Undefined;
  894. case D3D11_SB_TESSELLATOR_DOMAIN_ISOLINE: return DXIL::TessellatorDomain::IsoLine;
  895. case D3D11_SB_TESSELLATOR_DOMAIN_TRI: return DXIL::TessellatorDomain::Tri;
  896. case D3D11_SB_TESSELLATOR_DOMAIN_QUAD: return DXIL::TessellatorDomain::Quad;
  897. }
  898. IFTBOOL(false, DXC_E_INCORRECT_DXBC);
  899. return DXIL::TessellatorDomain::Undefined;
  900. }
  901. DXIL::TessellatorPartitioning GetTessellatorPartitioning(D3D11_SB_TESSELLATOR_PARTITIONING TessPartitioning) {
  902. switch (TessPartitioning) {
  903. case D3D11_SB_TESSELLATOR_PARTITIONING_UNDEFINED: return DXIL::TessellatorPartitioning::Undefined;
  904. case D3D11_SB_TESSELLATOR_PARTITIONING_INTEGER: return DXIL::TessellatorPartitioning::Integer;
  905. case D3D11_SB_TESSELLATOR_PARTITIONING_POW2: return DXIL::TessellatorPartitioning::Pow2;
  906. case D3D11_SB_TESSELLATOR_PARTITIONING_FRACTIONAL_ODD: return DXIL::TessellatorPartitioning::FractionalOdd;
  907. case D3D11_SB_TESSELLATOR_PARTITIONING_FRACTIONAL_EVEN: return DXIL::TessellatorPartitioning::FractionalEven;
  908. }
  909. IFTBOOL(false, DXC_E_INCORRECT_DXBC);
  910. return DXIL::TessellatorPartitioning::Undefined;
  911. }
  912. DXIL::TessellatorOutputPrimitive GetTessellatorOutputPrimitive(D3D11_SB_TESSELLATOR_OUTPUT_PRIMITIVE TessOutputPrimitive) {
  913. switch (TessOutputPrimitive) {
  914. case D3D11_SB_TESSELLATOR_OUTPUT_UNDEFINED: return DXIL::TessellatorOutputPrimitive::Undefined;
  915. case D3D11_SB_TESSELLATOR_OUTPUT_POINT: return DXIL::TessellatorOutputPrimitive::Point;
  916. case D3D11_SB_TESSELLATOR_OUTPUT_LINE: return DXIL::TessellatorOutputPrimitive::Line;
  917. case D3D11_SB_TESSELLATOR_OUTPUT_TRIANGLE_CW: return DXIL::TessellatorOutputPrimitive::TriangleCW;
  918. case D3D11_SB_TESSELLATOR_OUTPUT_TRIANGLE_CCW: return DXIL::TessellatorOutputPrimitive::TriangleCCW;
  919. }
  920. IFTBOOL(false, DXC_E_INCORRECT_DXBC);
  921. return DXIL::TessellatorOutputPrimitive::Undefined;
  922. }
  923. } // namespace DXBC
  924. //------------------------------------------------------------------------------
  925. //
  926. // Asserts to match DXBC and DXIL constant values.
  927. //
  928. using namespace DXIL;
  929. #define MSG "Constant value mismatch between DXBC and DXIL"
  930. static_assert(kMaxTempRegCount == D3D11_COMMONSHADER_TEMP_REGISTER_COUNT, MSG);
  931. static_assert(kMaxCBufferSize == D3D10_REQ_CONSTANT_BUFFER_ELEMENT_COUNT, MSG);
  932. static_assert((int)DxilSampler::SamplerKind::Default == D3D10_SB_SAMPLER_MODE_DEFAULT, MSG);
  933. static_assert((int)DxilSampler::SamplerKind::Comparison == D3D10_SB_SAMPLER_MODE_COMPARISON, MSG);
  934. static_assert((int)DxilSampler::SamplerKind::Mono == D3D10_SB_SAMPLER_MODE_MONO, MSG);
  935. static_assert(D3D10_SB_4_COMPONENT_X == 0, MSG);
  936. static_assert(D3D10_SB_4_COMPONENT_Y == 1, MSG);
  937. static_assert(D3D10_SB_4_COMPONENT_Z == 2, MSG);
  938. static_assert(D3D10_SB_4_COMPONENT_W == 3, MSG);
  939. static_assert(D3D_MIN_PRECISION_DEFAULT == D3D11_SB_OPERAND_MIN_PRECISION_DEFAULT, MSG);
  940. static_assert(D3D_MIN_PRECISION_FLOAT_16 == D3D11_SB_OPERAND_MIN_PRECISION_FLOAT_16, MSG);
  941. static_assert(D3D_MIN_PRECISION_FLOAT_2_8 == D3D11_SB_OPERAND_MIN_PRECISION_FLOAT_2_8, MSG);
  942. static_assert(D3D_MIN_PRECISION_SINT_16 == D3D11_SB_OPERAND_MIN_PRECISION_SINT_16, MSG);
  943. static_assert(D3D_MIN_PRECISION_UINT_16 == D3D11_SB_OPERAND_MIN_PRECISION_UINT_16, MSG);
  944. } // namespace hlsl