spirv_target_env.cpp 10 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343
  1. // Copyright (c) 2015-2016 The Khronos Group Inc.
  2. //
  3. // Licensed under the Apache License, Version 2.0 (the "License");
  4. // you may not use this file except in compliance with the License.
  5. // You may obtain a copy of the License at
  6. //
  7. // http://www.apache.org/licenses/LICENSE-2.0
  8. //
  9. // Unless required by applicable law or agreed to in writing, software
  10. // distributed under the License is distributed on an "AS IS" BASIS,
  11. // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12. // See the License for the specific language governing permissions and
  13. // limitations under the License.
  14. #include "source/spirv_target_env.h"
  15. #include <cstring>
  16. #include <string>
  17. #include "source/spirv_constant.h"
  18. #include "spirv-tools/libspirv.h"
  19. const char* spvTargetEnvDescription(spv_target_env env) {
  20. switch (env) {
  21. case SPV_ENV_UNIVERSAL_1_0:
  22. return "SPIR-V 1.0";
  23. case SPV_ENV_VULKAN_1_0:
  24. return "SPIR-V 1.0 (under Vulkan 1.0 semantics)";
  25. case SPV_ENV_UNIVERSAL_1_1:
  26. return "SPIR-V 1.1";
  27. case SPV_ENV_OPENCL_1_2:
  28. return "SPIR-V 1.0 (under OpenCL 1.2 Full Profile semantics)";
  29. case SPV_ENV_OPENCL_EMBEDDED_1_2:
  30. return "SPIR-V 1.0 (under OpenCL 1.2 Embedded Profile semantics)";
  31. case SPV_ENV_OPENCL_2_0:
  32. return "SPIR-V 1.0 (under OpenCL 2.0 Full Profile semantics)";
  33. case SPV_ENV_OPENCL_EMBEDDED_2_0:
  34. return "SPIR-V 1.0 (under OpenCL 2.0 Embedded Profile semantics)";
  35. case SPV_ENV_OPENCL_2_1:
  36. return "SPIR-V 1.0 (under OpenCL 2.1 Full Profile semantics)";
  37. case SPV_ENV_OPENCL_EMBEDDED_2_1:
  38. return "SPIR-V 1.0 (under OpenCL 2.1 Embedded Profile semantics)";
  39. case SPV_ENV_OPENCL_2_2:
  40. return "SPIR-V 1.2 (under OpenCL 2.2 Full Profile semantics)";
  41. case SPV_ENV_OPENCL_EMBEDDED_2_2:
  42. return "SPIR-V 1.2 (under OpenCL 2.2 Embedded Profile semantics)";
  43. case SPV_ENV_OPENGL_4_0:
  44. return "SPIR-V 1.0 (under OpenGL 4.0 semantics)";
  45. case SPV_ENV_OPENGL_4_1:
  46. return "SPIR-V 1.0 (under OpenGL 4.1 semantics)";
  47. case SPV_ENV_OPENGL_4_2:
  48. return "SPIR-V 1.0 (under OpenGL 4.2 semantics)";
  49. case SPV_ENV_OPENGL_4_3:
  50. return "SPIR-V 1.0 (under OpenGL 4.3 semantics)";
  51. case SPV_ENV_OPENGL_4_5:
  52. return "SPIR-V 1.0 (under OpenGL 4.5 semantics)";
  53. case SPV_ENV_UNIVERSAL_1_2:
  54. return "SPIR-V 1.2";
  55. case SPV_ENV_UNIVERSAL_1_3:
  56. return "SPIR-V 1.3";
  57. case SPV_ENV_VULKAN_1_1:
  58. return "SPIR-V 1.3 (under Vulkan 1.1 semantics)";
  59. case SPV_ENV_WEBGPU_0:
  60. return "SPIR-V 1.3 (under WIP WebGPU semantics)";
  61. case SPV_ENV_UNIVERSAL_1_4:
  62. return "SPIR-V 1.4";
  63. case SPV_ENV_VULKAN_1_1_SPIRV_1_4:
  64. return "SPIR-V 1.4 (under Vulkan 1.1 semantics)";
  65. case SPV_ENV_UNIVERSAL_1_5:
  66. return "SPIR-V 1.5";
  67. }
  68. return "";
  69. }
  70. uint32_t spvVersionForTargetEnv(spv_target_env env) {
  71. switch (env) {
  72. case SPV_ENV_UNIVERSAL_1_0:
  73. case SPV_ENV_VULKAN_1_0:
  74. case SPV_ENV_OPENCL_1_2:
  75. case SPV_ENV_OPENCL_EMBEDDED_1_2:
  76. case SPV_ENV_OPENCL_2_0:
  77. case SPV_ENV_OPENCL_EMBEDDED_2_0:
  78. case SPV_ENV_OPENCL_2_1:
  79. case SPV_ENV_OPENCL_EMBEDDED_2_1:
  80. case SPV_ENV_OPENGL_4_0:
  81. case SPV_ENV_OPENGL_4_1:
  82. case SPV_ENV_OPENGL_4_2:
  83. case SPV_ENV_OPENGL_4_3:
  84. case SPV_ENV_OPENGL_4_5:
  85. return SPV_SPIRV_VERSION_WORD(1, 0);
  86. case SPV_ENV_UNIVERSAL_1_1:
  87. return SPV_SPIRV_VERSION_WORD(1, 1);
  88. case SPV_ENV_UNIVERSAL_1_2:
  89. case SPV_ENV_OPENCL_2_2:
  90. case SPV_ENV_OPENCL_EMBEDDED_2_2:
  91. return SPV_SPIRV_VERSION_WORD(1, 2);
  92. case SPV_ENV_UNIVERSAL_1_3:
  93. case SPV_ENV_VULKAN_1_1:
  94. case SPV_ENV_WEBGPU_0:
  95. return SPV_SPIRV_VERSION_WORD(1, 3);
  96. case SPV_ENV_UNIVERSAL_1_4:
  97. case SPV_ENV_VULKAN_1_1_SPIRV_1_4:
  98. return SPV_SPIRV_VERSION_WORD(1, 4);
  99. case SPV_ENV_UNIVERSAL_1_5:
  100. return SPV_SPIRV_VERSION_WORD(1, 5);
  101. }
  102. return SPV_SPIRV_VERSION_WORD(0, 0);
  103. }
  104. static const std::pair<const char*, spv_target_env> spvTargetEnvNameMap[] = {
  105. {"vulkan1.1spv1.4", SPV_ENV_VULKAN_1_1_SPIRV_1_4},
  106. {"vulkan1.0", SPV_ENV_VULKAN_1_0},
  107. {"vulkan1.1", SPV_ENV_VULKAN_1_1},
  108. {"spv1.0", SPV_ENV_UNIVERSAL_1_0},
  109. {"spv1.1", SPV_ENV_UNIVERSAL_1_1},
  110. {"spv1.2", SPV_ENV_UNIVERSAL_1_2},
  111. {"spv1.3", SPV_ENV_UNIVERSAL_1_3},
  112. {"spv1.4", SPV_ENV_UNIVERSAL_1_4},
  113. {"spv1.5", SPV_ENV_UNIVERSAL_1_5},
  114. {"opencl1.2embedded", SPV_ENV_OPENCL_EMBEDDED_1_2},
  115. {"opencl1.2", SPV_ENV_OPENCL_1_2},
  116. {"opencl2.0embedded", SPV_ENV_OPENCL_EMBEDDED_2_0},
  117. {"opencl2.0", SPV_ENV_OPENCL_2_0},
  118. {"opencl2.1embedded", SPV_ENV_OPENCL_EMBEDDED_2_1},
  119. {"opencl2.1", SPV_ENV_OPENCL_2_1},
  120. {"opencl2.2embedded", SPV_ENV_OPENCL_EMBEDDED_2_2},
  121. {"opencl2.2", SPV_ENV_OPENCL_2_2},
  122. {"opengl4.0", SPV_ENV_OPENGL_4_0},
  123. {"opengl4.1", SPV_ENV_OPENGL_4_1},
  124. {"opengl4.2", SPV_ENV_OPENGL_4_2},
  125. {"opengl4.3", SPV_ENV_OPENGL_4_3},
  126. {"opengl4.5", SPV_ENV_OPENGL_4_5},
  127. {"webgpu0", SPV_ENV_WEBGPU_0},
  128. };
  129. bool spvParseTargetEnv(const char* s, spv_target_env* env) {
  130. auto match = [s](const char* b) {
  131. return s && (0 == strncmp(s, b, strlen(b)));
  132. };
  133. for (auto& name_env : spvTargetEnvNameMap) {
  134. if (match(name_env.first)) {
  135. if (env) {
  136. *env = name_env.second;
  137. }
  138. return true;
  139. }
  140. }
  141. if (env) *env = SPV_ENV_UNIVERSAL_1_0;
  142. return false;
  143. }
  144. bool spvIsVulkanEnv(spv_target_env env) {
  145. switch (env) {
  146. case SPV_ENV_UNIVERSAL_1_0:
  147. case SPV_ENV_OPENCL_1_2:
  148. case SPV_ENV_OPENCL_EMBEDDED_1_2:
  149. case SPV_ENV_OPENCL_2_0:
  150. case SPV_ENV_OPENCL_EMBEDDED_2_0:
  151. case SPV_ENV_OPENCL_2_1:
  152. case SPV_ENV_OPENCL_EMBEDDED_2_1:
  153. case SPV_ENV_OPENGL_4_0:
  154. case SPV_ENV_OPENGL_4_1:
  155. case SPV_ENV_OPENGL_4_2:
  156. case SPV_ENV_OPENGL_4_3:
  157. case SPV_ENV_OPENGL_4_5:
  158. case SPV_ENV_UNIVERSAL_1_1:
  159. case SPV_ENV_UNIVERSAL_1_2:
  160. case SPV_ENV_OPENCL_2_2:
  161. case SPV_ENV_OPENCL_EMBEDDED_2_2:
  162. case SPV_ENV_UNIVERSAL_1_3:
  163. case SPV_ENV_WEBGPU_0:
  164. case SPV_ENV_UNIVERSAL_1_4:
  165. case SPV_ENV_UNIVERSAL_1_5:
  166. return false;
  167. case SPV_ENV_VULKAN_1_0:
  168. case SPV_ENV_VULKAN_1_1:
  169. case SPV_ENV_VULKAN_1_1_SPIRV_1_4:
  170. return true;
  171. }
  172. return false;
  173. }
  174. bool spvIsOpenCLEnv(spv_target_env env) {
  175. switch (env) {
  176. case SPV_ENV_UNIVERSAL_1_0:
  177. case SPV_ENV_VULKAN_1_0:
  178. case SPV_ENV_UNIVERSAL_1_1:
  179. case SPV_ENV_OPENGL_4_0:
  180. case SPV_ENV_OPENGL_4_1:
  181. case SPV_ENV_OPENGL_4_2:
  182. case SPV_ENV_OPENGL_4_3:
  183. case SPV_ENV_OPENGL_4_5:
  184. case SPV_ENV_UNIVERSAL_1_2:
  185. case SPV_ENV_UNIVERSAL_1_3:
  186. case SPV_ENV_VULKAN_1_1:
  187. case SPV_ENV_WEBGPU_0:
  188. case SPV_ENV_UNIVERSAL_1_4:
  189. case SPV_ENV_VULKAN_1_1_SPIRV_1_4:
  190. case SPV_ENV_UNIVERSAL_1_5:
  191. return false;
  192. case SPV_ENV_OPENCL_1_2:
  193. case SPV_ENV_OPENCL_EMBEDDED_1_2:
  194. case SPV_ENV_OPENCL_2_0:
  195. case SPV_ENV_OPENCL_EMBEDDED_2_0:
  196. case SPV_ENV_OPENCL_EMBEDDED_2_1:
  197. case SPV_ENV_OPENCL_EMBEDDED_2_2:
  198. case SPV_ENV_OPENCL_2_1:
  199. case SPV_ENV_OPENCL_2_2:
  200. return true;
  201. }
  202. return false;
  203. }
  204. bool spvIsWebGPUEnv(spv_target_env env) {
  205. switch (env) {
  206. case SPV_ENV_UNIVERSAL_1_0:
  207. case SPV_ENV_VULKAN_1_0:
  208. case SPV_ENV_UNIVERSAL_1_1:
  209. case SPV_ENV_OPENGL_4_0:
  210. case SPV_ENV_OPENGL_4_1:
  211. case SPV_ENV_OPENGL_4_2:
  212. case SPV_ENV_OPENGL_4_3:
  213. case SPV_ENV_OPENGL_4_5:
  214. case SPV_ENV_UNIVERSAL_1_2:
  215. case SPV_ENV_UNIVERSAL_1_3:
  216. case SPV_ENV_VULKAN_1_1:
  217. case SPV_ENV_OPENCL_1_2:
  218. case SPV_ENV_OPENCL_EMBEDDED_1_2:
  219. case SPV_ENV_OPENCL_2_0:
  220. case SPV_ENV_OPENCL_EMBEDDED_2_0:
  221. case SPV_ENV_OPENCL_EMBEDDED_2_1:
  222. case SPV_ENV_OPENCL_EMBEDDED_2_2:
  223. case SPV_ENV_OPENCL_2_1:
  224. case SPV_ENV_OPENCL_2_2:
  225. case SPV_ENV_UNIVERSAL_1_4:
  226. case SPV_ENV_VULKAN_1_1_SPIRV_1_4:
  227. case SPV_ENV_UNIVERSAL_1_5:
  228. return false;
  229. case SPV_ENV_WEBGPU_0:
  230. return true;
  231. }
  232. return false;
  233. }
  234. bool spvIsOpenGLEnv(spv_target_env env) {
  235. switch (env) {
  236. case SPV_ENV_UNIVERSAL_1_0:
  237. case SPV_ENV_VULKAN_1_0:
  238. case SPV_ENV_UNIVERSAL_1_1:
  239. case SPV_ENV_UNIVERSAL_1_2:
  240. case SPV_ENV_UNIVERSAL_1_3:
  241. case SPV_ENV_VULKAN_1_1:
  242. case SPV_ENV_OPENCL_1_2:
  243. case SPV_ENV_OPENCL_EMBEDDED_1_2:
  244. case SPV_ENV_OPENCL_2_0:
  245. case SPV_ENV_OPENCL_EMBEDDED_2_0:
  246. case SPV_ENV_OPENCL_EMBEDDED_2_1:
  247. case SPV_ENV_OPENCL_EMBEDDED_2_2:
  248. case SPV_ENV_OPENCL_2_1:
  249. case SPV_ENV_OPENCL_2_2:
  250. case SPV_ENV_WEBGPU_0:
  251. case SPV_ENV_UNIVERSAL_1_4:
  252. case SPV_ENV_VULKAN_1_1_SPIRV_1_4:
  253. case SPV_ENV_UNIVERSAL_1_5:
  254. return false;
  255. case SPV_ENV_OPENGL_4_0:
  256. case SPV_ENV_OPENGL_4_1:
  257. case SPV_ENV_OPENGL_4_2:
  258. case SPV_ENV_OPENGL_4_3:
  259. case SPV_ENV_OPENGL_4_5:
  260. return true;
  261. }
  262. return false;
  263. }
  264. bool spvIsVulkanOrWebGPUEnv(spv_target_env env) {
  265. return spvIsVulkanEnv(env) || spvIsWebGPUEnv(env);
  266. }
  267. std::string spvLogStringForEnv(spv_target_env env) {
  268. switch (env) {
  269. case SPV_ENV_OPENCL_1_2:
  270. case SPV_ENV_OPENCL_2_0:
  271. case SPV_ENV_OPENCL_2_1:
  272. case SPV_ENV_OPENCL_2_2:
  273. case SPV_ENV_OPENCL_EMBEDDED_1_2:
  274. case SPV_ENV_OPENCL_EMBEDDED_2_0:
  275. case SPV_ENV_OPENCL_EMBEDDED_2_1:
  276. case SPV_ENV_OPENCL_EMBEDDED_2_2: {
  277. return "OpenCL";
  278. }
  279. case SPV_ENV_OPENGL_4_0:
  280. case SPV_ENV_OPENGL_4_1:
  281. case SPV_ENV_OPENGL_4_2:
  282. case SPV_ENV_OPENGL_4_3:
  283. case SPV_ENV_OPENGL_4_5: {
  284. return "OpenGL";
  285. }
  286. case SPV_ENV_VULKAN_1_0:
  287. case SPV_ENV_VULKAN_1_1:
  288. case SPV_ENV_VULKAN_1_1_SPIRV_1_4: {
  289. return "Vulkan";
  290. }
  291. case SPV_ENV_WEBGPU_0: {
  292. return "WebGPU";
  293. }
  294. case SPV_ENV_UNIVERSAL_1_0:
  295. case SPV_ENV_UNIVERSAL_1_1:
  296. case SPV_ENV_UNIVERSAL_1_2:
  297. case SPV_ENV_UNIVERSAL_1_3:
  298. case SPV_ENV_UNIVERSAL_1_4:
  299. case SPV_ENV_UNIVERSAL_1_5: {
  300. return "Universal";
  301. }
  302. }
  303. return "Unknown";
  304. }
  305. std::string spvTargetEnvList(const int pad, const int wrap) {
  306. std::string ret;
  307. size_t max_line_len = wrap - pad; // The first line isn't padded
  308. std::string line;
  309. std::string sep = "";
  310. for (auto& name_env : spvTargetEnvNameMap) {
  311. std::string word = sep + name_env.first;
  312. if (line.length() + word.length() > max_line_len) {
  313. // Adding one word wouldn't fit, commit the line in progress and
  314. // start a new one.
  315. ret += line + "\n";
  316. line.assign(pad, ' ');
  317. // The first line is done. The max length now comprises the
  318. // padding.
  319. max_line_len = wrap;
  320. }
  321. line += word;
  322. sep = "|";
  323. }
  324. ret += line;
  325. return ret;
  326. }