shader_spirv.cpp 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732
  1. /*
  2. * Copyright 2011-2015 Branimir Karadzic. All rights reserved.
  3. * License: http://www.opensource.org/licenses/BSD-2-Clause
  4. */
  5. #include "bgfx_p.h"
  6. #include "shader_spirv.h"
  7. namespace bgfx
  8. {
  9. struct SpirvOpcodeInfo
  10. {
  11. uint8_t numOperands;
  12. uint8_t numValues;
  13. bool hasVariable;
  14. };
  15. static const SpirvOpcodeInfo s_sprivOpcodeInfo[] =
  16. {
  17. { 0, 0, false }, // Nop,
  18. { 0, 0, true }, // Source
  19. { 0, 0, true }, // SourceExtension
  20. { 0, 0, false }, // Extension
  21. { 0, 1, true }, // ExtInstImport
  22. { 0, 2, false }, // MemoryModel
  23. { 0, 2, false }, // EntryPoint
  24. { 0, 0, false }, // ExecutionMode
  25. { 0, 1, false }, // TypeVoid
  26. { 0, 1, false }, // TypeBool
  27. { 0, 3, false }, // TypeInt
  28. { 0, 2, false }, // TypeFloat
  29. { 0, 3, false }, // TypeVector
  30. { 0, 3, false }, // TypeMatrix
  31. { 1, 7, false }, // TypeSampler
  32. { 0, 0, false }, // TypeFilter
  33. { 0, 0, false }, // TypeArray
  34. { 0, 0, false }, // TypeRuntimeArray
  35. { 0, 0, false }, // TypeStruct
  36. { 0, 0, false }, // TypeOpaque
  37. { 0, 3, false }, // TypePointer
  38. { 0, 2, true }, // TypeFunction
  39. { 0, 0, false }, // TypeEvent
  40. { 0, 0, false }, // TypeDeviceEvent
  41. { 0, 0, false }, // TypeReserveId
  42. { 0, 0, false }, // TypeQueue
  43. { 0, 0, false }, // TypePipe
  44. { 0, 0, false }, // ConstantTrue
  45. { 0, 0, false }, // ConstantFalse
  46. { 0, 2, true }, // Constant
  47. { 0, 2, true }, // ConstantComposite
  48. { 0, 0, false }, // ConstantSampler
  49. { 0, 0, false }, // ConstantNullPointer
  50. { 0, 0, false }, // ConstantNullObject
  51. { 0, 0, false }, // SpecConstantTrue
  52. { 0, 0, false }, // SpecConstantFalse
  53. { 0, 0, false }, // SpecConstant
  54. { 0, 0, false }, // SpecConstantComposite
  55. { 0, 3, true }, // Variable
  56. { 0, 0, false }, // VariableArray
  57. { 0, 4, false }, // Function
  58. { 0, 0, false }, // FunctionParameter
  59. { 0, 0, false }, // FunctionEnd
  60. { 0, 0, false }, // FunctionCall
  61. { 0, 0, false }, // ExtInst
  62. { 0, 0, false }, // Undef
  63. { 0, 0, false }, // Load
  64. { 0, 2, true }, // Store
  65. { 0, 0, false }, // Phi
  66. { 0, 0, false }, // DecorationGroup
  67. { 0, 2, true }, // Decorate
  68. { 0, 0, false }, // MemberDecorate
  69. { 0, 0, false }, // GroupDecorate
  70. { 0, 0, false }, // GroupMemberDecorate
  71. { 0, 1, true }, // Name
  72. { 0, 1, true }, // MemberName
  73. { 0, 0, false }, // String
  74. { 0, 0, false }, // Line
  75. { 0, 0, false }, // VectorExtractDynamic
  76. { 0, 0, false }, // VectorInsertDynamic
  77. { 0, 0, false }, // VectorShuffle
  78. { 0, 0, false }, // CompositeConstruct
  79. { 0, 0, false }, // CompositeExtract
  80. { 0, 0, false }, // CompositeInsert
  81. { 0, 0, false }, // CopyObject
  82. { 0, 0, false }, // CopyMemory
  83. { 0, 0, false }, // CopyMemorySized
  84. { 0, 0, false }, // Sampler
  85. { 0, 0, false }, // TextureSample
  86. { 0, 0, false }, // TextureSampleDref
  87. { 0, 0, false }, // TextureSampleLod
  88. { 0, 0, false }, // TextureSampleProj
  89. { 0, 0, false }, // TextureSampleGrad
  90. { 0, 0, false }, // TextureSampleOffset
  91. { 0, 0, false }, // TextureSampleProjLod
  92. { 0, 0, false }, // TextureSampleProjGrad
  93. { 0, 0, false }, // TextureSampleLodOffset
  94. { 0, 0, false }, // TextureSampleProjOffset
  95. { 0, 0, false }, // TextureSampleGradOffset
  96. { 0, 0, false }, // TextureSampleProjLodOffset
  97. { 0, 0, false }, // TextureSampleProjGradOffset
  98. { 0, 0, false }, // TextureFetchTexelLod
  99. { 0, 0, false }, // TextureFetchTexelOffset
  100. { 0, 0, false }, // TextureFetchSample
  101. { 0, 0, false }, // TextureFetchTexel
  102. { 0, 0, false }, // TextureGather
  103. { 0, 0, false }, // TextureGatherOffset
  104. { 0, 0, false }, // TextureGatherOffsets
  105. { 0, 0, false }, // TextureQuerySizeLod
  106. { 0, 0, false }, // TextureQuerySize
  107. { 0, 0, false }, // TextureQueryLod
  108. { 0, 0, false }, // TextureQueryLevels
  109. { 0, 0, false }, // TextureQuerySamples
  110. { 0, 0, false }, // AccessChain
  111. { 0, 0, false }, // InBoundsAccessChain
  112. { 0, 0, false }, // SNegate
  113. { 0, 0, false }, // FNegate
  114. { 0, 0, false }, // Not
  115. { 0, 0, false }, // Any
  116. { 0, 0, false }, // All
  117. { 0, 0, false }, // ConvertFToU
  118. { 0, 0, false }, // ConvertFToS
  119. { 0, 0, false }, // ConvertSToF
  120. { 0, 0, false }, // ConvertUToF
  121. { 0, 0, false }, // UConvert
  122. { 0, 0, false }, // SConvert
  123. { 0, 0, false }, // FConvert
  124. { 0, 0, false }, // ConvertPtrToU
  125. { 0, 0, false }, // ConvertUToPtr
  126. { 0, 0, false }, // PtrCastToGeneric
  127. { 0, 0, false }, // GenericCastToPtr
  128. { 0, 0, false }, // Bitcast
  129. { 0, 0, false }, // Transpose
  130. { 0, 0, false }, // IsNan
  131. { 0, 0, false }, // IsInf
  132. { 0, 0, false }, // IsFinite
  133. { 0, 0, false }, // IsNormal
  134. { 0, 0, false }, // SignBitSet
  135. { 0, 0, false }, // LessOrGreater
  136. { 0, 0, false }, // Ordered
  137. { 0, 0, false }, // Unordered
  138. { 0, 0, false }, // ArrayLength
  139. { 0, 0, false }, // IAdd
  140. { 0, 0, false }, // FAdd
  141. { 0, 0, false }, // ISub
  142. { 0, 0, false }, // FSub
  143. { 0, 0, false }, // IMul
  144. { 0, 0, false }, // FMul
  145. { 0, 0, false }, // UDiv
  146. { 0, 0, false }, // SDiv
  147. { 0, 0, false }, // FDiv
  148. { 0, 0, false }, // UMod
  149. { 0, 0, false }, // SRem
  150. { 0, 0, false }, // SMod
  151. { 0, 0, false }, // FRem
  152. { 0, 0, false }, // FMod
  153. { 0, 0, false }, // VectorTimesScalar
  154. { 0, 0, false }, // MatrixTimesScalar
  155. { 0, 0, false }, // VectorTimesMatrix
  156. { 0, 0, false }, // MatrixTimesVector
  157. { 0, 0, false }, // MatrixTimesMatrix
  158. { 0, 0, false }, // OuterProduct
  159. { 0, 0, false }, // Dot
  160. { 0, 0, false }, // ShiftRightLogical
  161. { 0, 0, false }, // ShiftRightArithmetic
  162. { 0, 0, false }, // ShiftLeftLogical
  163. { 0, 0, false }, // LogicalOr
  164. { 0, 0, false }, // LogicalXor
  165. { 0, 0, false }, // LogicalAnd
  166. { 0, 0, false }, // BitwiseOr
  167. { 0, 0, false }, // BitwiseXor
  168. { 0, 0, false }, // BitwiseAnd
  169. { 0, 0, false }, // Select
  170. { 0, 0, false }, // IEqual
  171. { 0, 0, false }, // FOrdEqual
  172. { 0, 0, false }, // FUnordEqual
  173. { 0, 0, false }, // INotEqual
  174. { 0, 0, false }, // FOrdNotEqual
  175. { 0, 0, false }, // FUnordNotEqual
  176. { 0, 0, false }, // ULessThan
  177. { 0, 0, false }, // SLessThan
  178. { 0, 0, false }, // FOrdLessThan
  179. { 0, 0, false }, // FUnordLessThan
  180. { 0, 0, false }, // UGreaterThan
  181. { 0, 0, false }, // SGreaterThan
  182. { 0, 0, false }, // FOrdGreaterThan
  183. { 0, 0, false }, // FUnordGreaterThan
  184. { 0, 0, false }, // ULessThanEqual
  185. { 0, 0, false }, // SLessThanEqual
  186. { 0, 0, false }, // FOrdLessThanEqual
  187. { 0, 0, false }, // FUnordLessThanEqual
  188. { 0, 0, false }, // UGreaterThanEqual
  189. { 0, 0, false }, // SGreaterThanEqual
  190. { 0, 0, false }, // FOrdGreaterThanEqual
  191. { 0, 0, false }, // FUnordGreaterThanEqual
  192. { 0, 0, false }, // DPdx
  193. { 0, 0, false }, // DPdy
  194. { 0, 0, false }, // Fwidth
  195. { 0, 0, false }, // DPdxFine
  196. { 0, 0, false }, // DPdyFine
  197. { 0, 0, false }, // FwidthFine
  198. { 0, 0, false }, // DPdxCoarse
  199. { 0, 0, false }, // DPdyCoarse
  200. { 0, 0, false }, // FwidthCoarse
  201. { 0, 0, false }, // EmitVertex
  202. { 0, 0, false }, // EndPrimitive
  203. { 0, 0, false }, // EmitStreamVertex
  204. { 0, 0, false }, // EndStreamPrimitive
  205. { 0, 0, false }, // ControlBarrier
  206. { 0, 0, false }, // MemoryBarrier
  207. { 0, 0, false }, // ImagePointer
  208. { 0, 0, false }, // AtomicInit
  209. { 0, 0, false }, // AtomicLoad
  210. { 0, 0, false }, // AtomicStore
  211. { 0, 0, false }, // AtomicExchange
  212. { 0, 0, false }, // AtomicCompareExchange
  213. { 0, 0, false }, // AtomicCompareExchangeWeak
  214. { 0, 0, false }, // AtomicIIncrement
  215. { 0, 0, false }, // AtomicIDecrement
  216. { 0, 0, false }, // AtomicIAdd
  217. { 0, 0, false }, // AtomicISub
  218. { 0, 0, false }, // AtomicUMin
  219. { 0, 0, false }, // AtomicUMax
  220. { 0, 0, false }, // AtomicAnd
  221. { 0, 0, false }, // AtomicOr
  222. { 0, 0, false }, // AtomicXor
  223. { 0, 0, false }, // LoopMerge
  224. { 0, 0, false }, // SelectionMerge
  225. { 0, 1, false }, // Label
  226. { 0, 1, false }, // Branch
  227. { 0, 0, false }, // BranchConditional
  228. { 0, 0, false }, // Switch
  229. { 0, 0, false }, // Kill
  230. { 0, 0, false }, // Return
  231. { 0, 0, false }, // ReturnValue
  232. { 0, 0, false }, // Unreachable
  233. { 0, 0, false }, // LifetimeStart
  234. { 0, 0, false }, // LifetimeStop
  235. { 0, 0, false }, // CompileFlag
  236. { 0, 0, false }, // AsyncGroupCopy
  237. { 0, 0, false }, // WaitGroupEvents
  238. { 0, 0, false }, // GroupAll
  239. { 0, 0, false }, // GroupAny
  240. { 0, 0, false }, // GroupBroadcast
  241. { 0, 0, false }, // GroupIAdd
  242. { 0, 0, false }, // GroupFAdd
  243. { 0, 0, false }, // GroupFMin
  244. { 0, 0, false }, // GroupUMin
  245. { 0, 0, false }, // GroupSMin
  246. { 0, 0, false }, // GroupFMax
  247. { 0, 0, false }, // GroupUMax
  248. { 0, 0, false }, // GroupSMax
  249. { 0, 0, false }, // GenericCastToPtrExplicit
  250. { 0, 0, false }, // GenericPtrMemSemantics
  251. { 0, 0, false }, // ReadPipe
  252. { 0, 0, false }, // WritePipe
  253. { 0, 0, false }, // ReservedReadPipe
  254. { 0, 0, false }, // ReservedWritePipe
  255. { 0, 0, false }, // ReserveReadPipePackets
  256. { 0, 0, false }, // ReserveWritePipePackets
  257. { 0, 0, false }, // CommitReadPipe
  258. { 0, 0, false }, // CommitWritePipe
  259. { 0, 0, false }, // IsValidReserveId
  260. { 0, 0, false }, // GetNumPipePackets
  261. { 0, 0, false }, // GetMaxPipePackets
  262. { 0, 0, false }, // GroupReserveReadPipePackets
  263. { 0, 0, false }, // GroupReserveWritePipePackets
  264. { 0, 0, false }, // GroupCommitReadPipe
  265. { 0, 0, false }, // GroupCommitWritePipe
  266. { 0, 0, false }, // EnqueueMarker
  267. { 0, 0, false }, // EnqueueKernel
  268. { 0, 0, false }, // GetKernelNDrangeSubGroupCount
  269. { 0, 0, false }, // GetKernelNDrangeMaxSubGroupSize
  270. { 0, 0, false }, // GetKernelWorkGroupSize
  271. { 0, 0, false }, // GetKernelPreferredWorkGroupSizeMultiple
  272. { 0, 0, false }, // RetainEvent
  273. { 0, 0, false }, // ReleaseEvent
  274. { 0, 0, false }, // CreateUserEvent
  275. { 0, 0, false }, // IsValidEvent
  276. { 0, 0, false }, // SetUserEventStatus
  277. { 0, 0, false }, // CaptureEventProfilingInfo
  278. { 0, 0, false }, // GetDefaultQueue
  279. { 0, 0, false }, // BuildNDRange
  280. { 0, 0, false }, // SatConvertSToU
  281. { 0, 0, false }, // SatConvertUToS
  282. { 0, 0, false }, // AtomicIMin
  283. { 0, 0, false }, // AtomicIMax
  284. };
  285. BX_STATIC_ASSERT(BX_COUNTOF(s_sprivOpcodeInfo) == SpirvOpcode::Count);
  286. const char* s_spirvOpcode[] =
  287. {
  288. "Nop",
  289. "Source",
  290. "SourceExtension",
  291. "Extension",
  292. "ExtInstImport",
  293. "MemoryModel",
  294. "EntryPoint",
  295. "ExecutionMode",
  296. "TypeVoid",
  297. "TypeBool",
  298. "TypeInt",
  299. "TypeFloat",
  300. "TypeVector",
  301. "TypeMatrix",
  302. "TypeSampler",
  303. "TypeFilter",
  304. "TypeArray",
  305. "TypeRuntimeArray",
  306. "TypeStruct",
  307. "TypeOpaque",
  308. "TypePointer",
  309. "TypeFunction",
  310. "TypeEvent",
  311. "TypeDeviceEvent",
  312. "TypeReserveId",
  313. "TypeQueue",
  314. "TypePipe",
  315. "ConstantTrue",
  316. "ConstantFalse",
  317. "Constant",
  318. "ConstantComposite",
  319. "ConstantSampler",
  320. "ConstantNullPointer",
  321. "ConstantNullObject",
  322. "SpecConstantTrue",
  323. "SpecConstantFalse",
  324. "SpecConstant",
  325. "SpecConstantComposite",
  326. "Variable",
  327. "VariableArray",
  328. "Function",
  329. "FunctionParameter",
  330. "FunctionEnd",
  331. "FunctionCall",
  332. "ExtInst",
  333. "Undef",
  334. "Load",
  335. "Store",
  336. "Phi",
  337. "DecorationGroup",
  338. "Decorate",
  339. "MemberDecorate",
  340. "GroupDecorate",
  341. "GroupMemberDecorate",
  342. "Name",
  343. "MemberName",
  344. "String",
  345. "Line",
  346. "VectorExtractDynamic",
  347. "VectorInsertDynamic",
  348. "VectorShuffle",
  349. "CompositeConstruct",
  350. "CompositeExtract",
  351. "CompositeInsert",
  352. "CopyObject",
  353. "CopyMemory",
  354. "CopyMemorySized",
  355. "Sampler",
  356. "TextureSample",
  357. "TextureSampleDref",
  358. "TextureSampleLod",
  359. "TextureSampleProj",
  360. "TextureSampleGrad",
  361. "TextureSampleOffset",
  362. "TextureSampleProjLod",
  363. "TextureSampleProjGrad",
  364. "TextureSampleLodOffset",
  365. "TextureSampleProjOffset",
  366. "TextureSampleGradOffset",
  367. "TextureSampleProjLodOffset",
  368. "TextureSampleProjGradOffset",
  369. "TextureFetchTexelLod",
  370. "TextureFetchTexelOffset",
  371. "TextureFetchSample",
  372. "TextureFetchTexel",
  373. "TextureGather",
  374. "TextureGatherOffset",
  375. "TextureGatherOffsets",
  376. "TextureQuerySizeLod",
  377. "TextureQuerySize",
  378. "TextureQueryLod",
  379. "TextureQueryLevels",
  380. "TextureQuerySamples",
  381. "AccessChain",
  382. "InBoundsAccessChain",
  383. "SNegate",
  384. "FNegate",
  385. "Not",
  386. "Any",
  387. "All",
  388. "ConvertFToU",
  389. "ConvertFToS",
  390. "ConvertSToF",
  391. "ConvertUToF",
  392. "UConvert",
  393. "SConvert",
  394. "FConvert",
  395. "ConvertPtrToU",
  396. "ConvertUToPtr",
  397. "PtrCastToGeneric",
  398. "GenericCastToPtr",
  399. "Bitcast",
  400. "Transpose",
  401. "IsNan",
  402. "IsInf",
  403. "IsFinite",
  404. "IsNormal",
  405. "SignBitSet",
  406. "LessOrGreater",
  407. "Ordered",
  408. "Unordered",
  409. "ArrayLength",
  410. "IAdd",
  411. "FAdd",
  412. "ISub",
  413. "FSub",
  414. "IMul",
  415. "FMul",
  416. "UDiv",
  417. "SDiv",
  418. "FDiv",
  419. "UMod",
  420. "SRem",
  421. "SMod",
  422. "FRem",
  423. "FMod",
  424. "VectorTimesScalar",
  425. "MatrixTimesScalar",
  426. "VectorTimesMatrix",
  427. "MatrixTimesVector",
  428. "MatrixTimesMatrix",
  429. "OuterProduct",
  430. "Dot",
  431. "ShiftRightLogical",
  432. "ShiftRightArithmetic",
  433. "ShiftLeftLogical",
  434. "LogicalOr",
  435. "LogicalXor",
  436. "LogicalAnd",
  437. "BitwiseOr",
  438. "BitwiseXor",
  439. "BitwiseAnd",
  440. "Select",
  441. "IEqual",
  442. "FOrdEqual",
  443. "FUnordEqual",
  444. "INotEqual",
  445. "FOrdNotEqual",
  446. "FUnordNotEqual",
  447. "ULessThan",
  448. "SLessThan",
  449. "FOrdLessThan",
  450. "FUnordLessThan",
  451. "UGreaterThan",
  452. "SGreaterThan",
  453. "FOrdGreaterThan",
  454. "FUnordGreaterThan",
  455. "ULessThanEqual",
  456. "SLessThanEqual",
  457. "FOrdLessThanEqual",
  458. "FUnordLessThanEqual",
  459. "UGreaterThanEqual",
  460. "SGreaterThanEqual",
  461. "FOrdGreaterThanEqual",
  462. "FUnordGreaterThanEqual",
  463. "DPdx",
  464. "DPdy",
  465. "Fwidth",
  466. "DPdxFine",
  467. "DPdyFine",
  468. "FwidthFine",
  469. "DPdxCoarse",
  470. "DPdyCoarse",
  471. "FwidthCoarse",
  472. "EmitVertex",
  473. "EndPrimitive",
  474. "EmitStreamVertex",
  475. "EndStreamPrimitive",
  476. "ControlBarrier",
  477. "MemoryBarrier",
  478. "ImagePointer",
  479. "AtomicInit",
  480. "AtomicLoad",
  481. "AtomicStore",
  482. "AtomicExchange",
  483. "AtomicCompareExchange",
  484. "AtomicCompareExchangeWeak",
  485. "AtomicIIncrement",
  486. "AtomicIDecrement",
  487. "AtomicIAdd",
  488. "AtomicISub",
  489. "AtomicUMin",
  490. "AtomicUMax",
  491. "AtomicAnd",
  492. "AtomicOr",
  493. "AtomicXor",
  494. "LoopMerge",
  495. "SelectionMerge",
  496. "Label",
  497. "Branch",
  498. "BranchConditional",
  499. "Switch",
  500. "Kill",
  501. "Return",
  502. "ReturnValue",
  503. "Unreachable",
  504. "LifetimeStart",
  505. "LifetimeStop",
  506. "CompileFlag",
  507. "AsyncGroupCopy",
  508. "WaitGroupEvents",
  509. "GroupAll",
  510. "GroupAny",
  511. "GroupBroadcast",
  512. "GroupIAdd",
  513. "GroupFAdd",
  514. "GroupFMin",
  515. "GroupUMin",
  516. "GroupSMin",
  517. "GroupFMax",
  518. "GroupUMax",
  519. "GroupSMax",
  520. "GenericCastToPtrExplicit",
  521. "GenericPtrMemSemantics",
  522. "ReadPipe",
  523. "WritePipe",
  524. "ReservedReadPipe",
  525. "ReservedWritePipe",
  526. "ReserveReadPipePackets",
  527. "ReserveWritePipePackets",
  528. "CommitReadPipe",
  529. "CommitWritePipe",
  530. "IsValidReserveId",
  531. "GetNumPipePackets",
  532. "GetMaxPipePackets",
  533. "GroupReserveReadPipePackets",
  534. "GroupReserveWritePipePackets",
  535. "GroupCommitReadPipe",
  536. "GroupCommitWritePipe",
  537. "EnqueueMarker",
  538. "EnqueueKernel",
  539. "GetKernelNDrangeSubGroupCount",
  540. "GetKernelNDrangeMaxSubGroupSize",
  541. "GetKernelWorkGroupSize",
  542. "GetKernelPreferredWorkGroupSizeMultiple",
  543. "RetainEvent",
  544. "ReleaseEvent",
  545. "CreateUserEvent",
  546. "IsValidEvent",
  547. "SetUserEventStatus",
  548. "CaptureEventProfilingInfo",
  549. "GetDefaultQueue",
  550. "BuildNDRange",
  551. "SatConvertSToU",
  552. "SatConvertUToS",
  553. "AtomicIMin",
  554. "AtomicIMax",
  555. };
  556. BX_STATIC_ASSERT(BX_COUNTOF(s_spirvOpcode) == SpirvOpcode::Count);
  557. const char* getName(SpirvOpcode::Enum _opcode)
  558. {
  559. BX_CHECK(_opcode < SpirvOpcode::Count, "Unknown opcode id %d.", _opcode);
  560. return s_spirvOpcode[_opcode];
  561. }
  562. int32_t read(bx::ReaderI* _reader, SpirvOperand& _operand)
  563. {
  564. int32_t size = 0;
  565. BX_UNUSED(_operand);
  566. uint32_t token;
  567. size += bx::read(_reader, token);
  568. return size;
  569. }
  570. int32_t read(bx::ReaderI* _reader, SpirvInstruction& _instruction)
  571. {
  572. int32_t size = 0;
  573. uint32_t token;
  574. size += bx::read(_reader, token);
  575. _instruction.opcode = SpirvOpcode::Enum( (token & UINT32_C(0x0000ffff) ) );
  576. _instruction.length = uint16_t( (token & UINT32_C(0xffff0000) ) >> 16);
  577. uint32_t currOp = 0;
  578. const SpirvOpcodeInfo& info = s_sprivOpcodeInfo[_instruction.opcode];
  579. if (0 < info.numValues)
  580. {
  581. size += read(_reader, _instruction.un.value, info.numValues*sizeof(uint32_t) );
  582. }
  583. if (info.hasVariable)
  584. {
  585. while (size/4 != _instruction.length)
  586. {
  587. uint32_t tmp;
  588. size += bx::read(_reader, tmp);
  589. }
  590. }
  591. else
  592. {
  593. _instruction.numOperands = info.numOperands;
  594. switch (info.numOperands)
  595. {
  596. case 6: size += read(_reader, _instruction.operand[currOp++]);
  597. case 5: size += read(_reader, _instruction.operand[currOp++]);
  598. case 4: size += read(_reader, _instruction.operand[currOp++]);
  599. case 3: size += read(_reader, _instruction.operand[currOp++]);
  600. case 2: size += read(_reader, _instruction.operand[currOp++]);
  601. case 1: size += read(_reader, _instruction.operand[currOp++]);
  602. case 0:
  603. break;
  604. default:
  605. BX_WARN(false, "Instruction %s with invalid number of operands %d (numValues %d)."
  606. , getName(_instruction.opcode)
  607. , info.numOperands
  608. , info.numValues
  609. );
  610. break;
  611. }
  612. BX_WARN(size/4 == _instruction.length, "read %d, expected %d, %s"
  613. , size/4
  614. , _instruction.length
  615. , getName(_instruction.opcode)
  616. );
  617. while (size/4 != _instruction.length)
  618. {
  619. uint32_t tmp;
  620. size += bx::read(_reader, tmp);
  621. }
  622. }
  623. return size;
  624. }
  625. int32_t write(bx::WriterI* _writer, const SpirvInstruction& _instruction)
  626. {
  627. int32_t size = 0;
  628. BX_UNUSED(_writer, _instruction);
  629. return size;
  630. }
  631. int32_t toString(char* _out, int32_t _size, const SpirvInstruction& _instruction)
  632. {
  633. int32_t size = 0;
  634. size += bx::snprintf(&_out[size], bx::uint32_imax(0, _size-size)
  635. , "%s %d (%d, %d)"
  636. , getName(_instruction.opcode)
  637. , _instruction.numOperands
  638. , _instruction.un.value[0]
  639. , _instruction.un.value[1]
  640. );
  641. return size;
  642. }
  643. int32_t read(bx::ReaderSeekerI* _reader, SpirvShader& _shader)
  644. {
  645. int32_t size = 0;
  646. uint32_t len = uint32_t(bx::getSize(_reader) - bx::seek(_reader) );
  647. _shader.byteCode.resize(len);
  648. size += bx::read(_reader, _shader.byteCode.data(), len);
  649. return size;
  650. }
  651. int32_t write(bx::WriterI* _writer, const SpirvShader& _shader)
  652. {
  653. int32_t size = 0;
  654. BX_UNUSED(_writer, _shader);
  655. return size;
  656. }
  657. #define SPIRV_MAGIC 0x07230203
  658. int32_t read(bx::ReaderSeekerI* _reader, Spirv& _spirv)
  659. {
  660. int32_t size = 0;
  661. size += bx::read(_reader, _spirv.header);
  662. if (size != sizeof(Spirv::Header)
  663. || _spirv.header.magic != SPIRV_MAGIC
  664. )
  665. {
  666. // error
  667. return -size;
  668. }
  669. size += read(_reader, _spirv.shader);
  670. return size;
  671. }
  672. int32_t write(bx::WriterSeekerI* _writer, const Spirv& _spirv)
  673. {
  674. int32_t size = 0;
  675. BX_UNUSED(_writer, _spirv);
  676. return size;
  677. }
  678. void parse(const SpirvShader& _src, SpirvParseFn _fn, void* _userData)
  679. {
  680. bx::MemoryReader reader(_src.byteCode.data(), uint32_t(_src.byteCode.size() ) );
  681. for (uint32_t token = 0, numTokens = uint32_t(_src.byteCode.size() / sizeof(uint32_t) ); token < numTokens;)
  682. {
  683. SpirvInstruction instruction;
  684. uint32_t size = read(&reader, instruction);
  685. BX_CHECK(size/4 == instruction.length, "read %d, expected %d, %s"
  686. , size/4
  687. , instruction.length
  688. , getName(instruction.opcode)
  689. );
  690. BX_UNUSED(size);
  691. _fn(token * sizeof(uint32_t), instruction, _userData);
  692. token += instruction.length;
  693. }
  694. }
  695. } // namespace bgfx