numba-cuda 0.22.0__cp312-cp312-manylinux_2_24_aarch64.manylinux_2_28_aarch64.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of numba-cuda might be problematic. Click here for more details.

Files changed (487) hide show
  1. _numba_cuda_redirector.pth +4 -0
  2. _numba_cuda_redirector.py +89 -0
  3. numba_cuda/VERSION +1 -0
  4. numba_cuda/__init__.py +6 -0
  5. numba_cuda/_version.py +11 -0
  6. numba_cuda/numba/cuda/__init__.py +70 -0
  7. numba_cuda/numba/cuda/_internal/cuda_bf16.py +16394 -0
  8. numba_cuda/numba/cuda/_internal/cuda_fp16.py +8112 -0
  9. numba_cuda/numba/cuda/api.py +580 -0
  10. numba_cuda/numba/cuda/api_util.py +76 -0
  11. numba_cuda/numba/cuda/args.py +72 -0
  12. numba_cuda/numba/cuda/bf16.py +397 -0
  13. numba_cuda/numba/cuda/cache_hints.py +287 -0
  14. numba_cuda/numba/cuda/cext/__init__.py +2 -0
  15. numba_cuda/numba/cuda/cext/_devicearray.cpp +159 -0
  16. numba_cuda/numba/cuda/cext/_devicearray.cpython-312-aarch64-linux-gnu.so +0 -0
  17. numba_cuda/numba/cuda/cext/_devicearray.h +29 -0
  18. numba_cuda/numba/cuda/cext/_dispatcher.cpp +1098 -0
  19. numba_cuda/numba/cuda/cext/_dispatcher.cpython-312-aarch64-linux-gnu.so +0 -0
  20. numba_cuda/numba/cuda/cext/_hashtable.cpp +532 -0
  21. numba_cuda/numba/cuda/cext/_hashtable.h +135 -0
  22. numba_cuda/numba/cuda/cext/_helperlib.c +71 -0
  23. numba_cuda/numba/cuda/cext/_helperlib.cpython-312-aarch64-linux-gnu.so +0 -0
  24. numba_cuda/numba/cuda/cext/_helpermod.c +82 -0
  25. numba_cuda/numba/cuda/cext/_pymodule.h +38 -0
  26. numba_cuda/numba/cuda/cext/_typeconv.cpp +206 -0
  27. numba_cuda/numba/cuda/cext/_typeconv.cpython-312-aarch64-linux-gnu.so +0 -0
  28. numba_cuda/numba/cuda/cext/_typeof.cpp +1159 -0
  29. numba_cuda/numba/cuda/cext/_typeof.h +19 -0
  30. numba_cuda/numba/cuda/cext/capsulethunk.h +111 -0
  31. numba_cuda/numba/cuda/cext/mviewbuf.c +385 -0
  32. numba_cuda/numba/cuda/cext/mviewbuf.cpython-312-aarch64-linux-gnu.so +0 -0
  33. numba_cuda/numba/cuda/cext/typeconv.cpp +212 -0
  34. numba_cuda/numba/cuda/cext/typeconv.hpp +101 -0
  35. numba_cuda/numba/cuda/cg.py +67 -0
  36. numba_cuda/numba/cuda/cgutils.py +1294 -0
  37. numba_cuda/numba/cuda/cloudpickle/__init__.py +21 -0
  38. numba_cuda/numba/cuda/cloudpickle/cloudpickle.py +1598 -0
  39. numba_cuda/numba/cuda/cloudpickle/cloudpickle_fast.py +17 -0
  40. numba_cuda/numba/cuda/codegen.py +541 -0
  41. numba_cuda/numba/cuda/compiler.py +1396 -0
  42. numba_cuda/numba/cuda/core/analysis.py +758 -0
  43. numba_cuda/numba/cuda/core/annotations/__init__.py +0 -0
  44. numba_cuda/numba/cuda/core/annotations/pretty_annotate.py +288 -0
  45. numba_cuda/numba/cuda/core/annotations/type_annotations.py +305 -0
  46. numba_cuda/numba/cuda/core/base.py +1332 -0
  47. numba_cuda/numba/cuda/core/boxing.py +1411 -0
  48. numba_cuda/numba/cuda/core/bytecode.py +728 -0
  49. numba_cuda/numba/cuda/core/byteflow.py +2346 -0
  50. numba_cuda/numba/cuda/core/caching.py +744 -0
  51. numba_cuda/numba/cuda/core/callconv.py +392 -0
  52. numba_cuda/numba/cuda/core/codegen.py +171 -0
  53. numba_cuda/numba/cuda/core/compiler.py +199 -0
  54. numba_cuda/numba/cuda/core/compiler_lock.py +85 -0
  55. numba_cuda/numba/cuda/core/compiler_machinery.py +497 -0
  56. numba_cuda/numba/cuda/core/config.py +650 -0
  57. numba_cuda/numba/cuda/core/consts.py +124 -0
  58. numba_cuda/numba/cuda/core/controlflow.py +989 -0
  59. numba_cuda/numba/cuda/core/entrypoints.py +57 -0
  60. numba_cuda/numba/cuda/core/environment.py +66 -0
  61. numba_cuda/numba/cuda/core/errors.py +917 -0
  62. numba_cuda/numba/cuda/core/event.py +511 -0
  63. numba_cuda/numba/cuda/core/funcdesc.py +330 -0
  64. numba_cuda/numba/cuda/core/generators.py +387 -0
  65. numba_cuda/numba/cuda/core/imputils.py +509 -0
  66. numba_cuda/numba/cuda/core/inline_closurecall.py +1787 -0
  67. numba_cuda/numba/cuda/core/interpreter.py +3617 -0
  68. numba_cuda/numba/cuda/core/ir.py +1812 -0
  69. numba_cuda/numba/cuda/core/ir_utils.py +2638 -0
  70. numba_cuda/numba/cuda/core/optional.py +129 -0
  71. numba_cuda/numba/cuda/core/options.py +262 -0
  72. numba_cuda/numba/cuda/core/postproc.py +249 -0
  73. numba_cuda/numba/cuda/core/pythonapi.py +1859 -0
  74. numba_cuda/numba/cuda/core/registry.py +46 -0
  75. numba_cuda/numba/cuda/core/removerefctpass.py +123 -0
  76. numba_cuda/numba/cuda/core/rewrites/__init__.py +26 -0
  77. numba_cuda/numba/cuda/core/rewrites/ir_print.py +91 -0
  78. numba_cuda/numba/cuda/core/rewrites/registry.py +104 -0
  79. numba_cuda/numba/cuda/core/rewrites/static_binop.py +41 -0
  80. numba_cuda/numba/cuda/core/rewrites/static_getitem.py +189 -0
  81. numba_cuda/numba/cuda/core/rewrites/static_raise.py +100 -0
  82. numba_cuda/numba/cuda/core/sigutils.py +68 -0
  83. numba_cuda/numba/cuda/core/ssa.py +498 -0
  84. numba_cuda/numba/cuda/core/targetconfig.py +330 -0
  85. numba_cuda/numba/cuda/core/tracing.py +231 -0
  86. numba_cuda/numba/cuda/core/transforms.py +956 -0
  87. numba_cuda/numba/cuda/core/typed_passes.py +867 -0
  88. numba_cuda/numba/cuda/core/typeinfer.py +1950 -0
  89. numba_cuda/numba/cuda/core/unsafe/__init__.py +0 -0
  90. numba_cuda/numba/cuda/core/unsafe/bytes.py +67 -0
  91. numba_cuda/numba/cuda/core/unsafe/eh.py +67 -0
  92. numba_cuda/numba/cuda/core/unsafe/refcount.py +98 -0
  93. numba_cuda/numba/cuda/core/untyped_passes.py +1979 -0
  94. numba_cuda/numba/cuda/cpython/builtins.py +1153 -0
  95. numba_cuda/numba/cuda/cpython/charseq.py +1218 -0
  96. numba_cuda/numba/cuda/cpython/cmathimpl.py +560 -0
  97. numba_cuda/numba/cuda/cpython/enumimpl.py +103 -0
  98. numba_cuda/numba/cuda/cpython/iterators.py +167 -0
  99. numba_cuda/numba/cuda/cpython/listobj.py +1326 -0
  100. numba_cuda/numba/cuda/cpython/mathimpl.py +499 -0
  101. numba_cuda/numba/cuda/cpython/numbers.py +1475 -0
  102. numba_cuda/numba/cuda/cpython/rangeobj.py +289 -0
  103. numba_cuda/numba/cuda/cpython/slicing.py +322 -0
  104. numba_cuda/numba/cuda/cpython/tupleobj.py +456 -0
  105. numba_cuda/numba/cuda/cpython/unicode.py +2865 -0
  106. numba_cuda/numba/cuda/cpython/unicode_support.py +1597 -0
  107. numba_cuda/numba/cuda/cpython/unsafe/__init__.py +0 -0
  108. numba_cuda/numba/cuda/cpython/unsafe/numbers.py +64 -0
  109. numba_cuda/numba/cuda/cpython/unsafe/tuple.py +92 -0
  110. numba_cuda/numba/cuda/cuda_paths.py +691 -0
  111. numba_cuda/numba/cuda/cudadecl.py +543 -0
  112. numba_cuda/numba/cuda/cudadrv/__init__.py +14 -0
  113. numba_cuda/numba/cuda/cudadrv/devicearray.py +954 -0
  114. numba_cuda/numba/cuda/cudadrv/devices.py +249 -0
  115. numba_cuda/numba/cuda/cudadrv/driver.py +3238 -0
  116. numba_cuda/numba/cuda/cudadrv/drvapi.py +435 -0
  117. numba_cuda/numba/cuda/cudadrv/dummyarray.py +562 -0
  118. numba_cuda/numba/cuda/cudadrv/enums.py +613 -0
  119. numba_cuda/numba/cuda/cudadrv/error.py +48 -0
  120. numba_cuda/numba/cuda/cudadrv/libs.py +220 -0
  121. numba_cuda/numba/cuda/cudadrv/linkable_code.py +184 -0
  122. numba_cuda/numba/cuda/cudadrv/mappings.py +14 -0
  123. numba_cuda/numba/cuda/cudadrv/ndarray.py +26 -0
  124. numba_cuda/numba/cuda/cudadrv/nvrtc.py +193 -0
  125. numba_cuda/numba/cuda/cudadrv/nvvm.py +756 -0
  126. numba_cuda/numba/cuda/cudadrv/rtapi.py +13 -0
  127. numba_cuda/numba/cuda/cudadrv/runtime.py +34 -0
  128. numba_cuda/numba/cuda/cudaimpl.py +983 -0
  129. numba_cuda/numba/cuda/cudamath.py +149 -0
  130. numba_cuda/numba/cuda/datamodel/__init__.py +7 -0
  131. numba_cuda/numba/cuda/datamodel/cuda_manager.py +66 -0
  132. numba_cuda/numba/cuda/datamodel/cuda_models.py +1446 -0
  133. numba_cuda/numba/cuda/datamodel/cuda_packer.py +224 -0
  134. numba_cuda/numba/cuda/datamodel/cuda_registry.py +22 -0
  135. numba_cuda/numba/cuda/datamodel/cuda_testing.py +153 -0
  136. numba_cuda/numba/cuda/datamodel/manager.py +11 -0
  137. numba_cuda/numba/cuda/datamodel/models.py +9 -0
  138. numba_cuda/numba/cuda/datamodel/packer.py +9 -0
  139. numba_cuda/numba/cuda/datamodel/registry.py +11 -0
  140. numba_cuda/numba/cuda/datamodel/testing.py +11 -0
  141. numba_cuda/numba/cuda/debuginfo.py +997 -0
  142. numba_cuda/numba/cuda/decorators.py +294 -0
  143. numba_cuda/numba/cuda/descriptor.py +35 -0
  144. numba_cuda/numba/cuda/device_init.py +155 -0
  145. numba_cuda/numba/cuda/deviceufunc.py +1021 -0
  146. numba_cuda/numba/cuda/dispatcher.py +2463 -0
  147. numba_cuda/numba/cuda/errors.py +72 -0
  148. numba_cuda/numba/cuda/extending.py +697 -0
  149. numba_cuda/numba/cuda/flags.py +178 -0
  150. numba_cuda/numba/cuda/fp16.py +357 -0
  151. numba_cuda/numba/cuda/include/12/cuda_bf16.h +5118 -0
  152. numba_cuda/numba/cuda/include/12/cuda_bf16.hpp +3865 -0
  153. numba_cuda/numba/cuda/include/12/cuda_fp16.h +5363 -0
  154. numba_cuda/numba/cuda/include/12/cuda_fp16.hpp +3483 -0
  155. numba_cuda/numba/cuda/include/13/cuda_bf16.h +5118 -0
  156. numba_cuda/numba/cuda/include/13/cuda_bf16.hpp +3865 -0
  157. numba_cuda/numba/cuda/include/13/cuda_fp16.h +5363 -0
  158. numba_cuda/numba/cuda/include/13/cuda_fp16.hpp +3483 -0
  159. numba_cuda/numba/cuda/initialize.py +24 -0
  160. numba_cuda/numba/cuda/intrinsics.py +531 -0
  161. numba_cuda/numba/cuda/itanium_mangler.py +214 -0
  162. numba_cuda/numba/cuda/kernels/__init__.py +2 -0
  163. numba_cuda/numba/cuda/kernels/reduction.py +265 -0
  164. numba_cuda/numba/cuda/kernels/transpose.py +65 -0
  165. numba_cuda/numba/cuda/libdevice.py +3386 -0
  166. numba_cuda/numba/cuda/libdevicedecl.py +20 -0
  167. numba_cuda/numba/cuda/libdevicefuncs.py +1060 -0
  168. numba_cuda/numba/cuda/libdeviceimpl.py +88 -0
  169. numba_cuda/numba/cuda/locks.py +19 -0
  170. numba_cuda/numba/cuda/lowering.py +1980 -0
  171. numba_cuda/numba/cuda/mathimpl.py +374 -0
  172. numba_cuda/numba/cuda/memory_management/__init__.py +4 -0
  173. numba_cuda/numba/cuda/memory_management/memsys.cu +99 -0
  174. numba_cuda/numba/cuda/memory_management/memsys.cuh +22 -0
  175. numba_cuda/numba/cuda/memory_management/nrt.cu +212 -0
  176. numba_cuda/numba/cuda/memory_management/nrt.cuh +48 -0
  177. numba_cuda/numba/cuda/memory_management/nrt.py +390 -0
  178. numba_cuda/numba/cuda/memory_management/nrt_context.py +438 -0
  179. numba_cuda/numba/cuda/misc/appdirs.py +594 -0
  180. numba_cuda/numba/cuda/misc/cffiimpl.py +24 -0
  181. numba_cuda/numba/cuda/misc/coverage_support.py +43 -0
  182. numba_cuda/numba/cuda/misc/dump_style.py +41 -0
  183. numba_cuda/numba/cuda/misc/findlib.py +75 -0
  184. numba_cuda/numba/cuda/misc/firstlinefinder.py +96 -0
  185. numba_cuda/numba/cuda/misc/gdb_hook.py +240 -0
  186. numba_cuda/numba/cuda/misc/literal.py +28 -0
  187. numba_cuda/numba/cuda/misc/llvm_pass_timings.py +412 -0
  188. numba_cuda/numba/cuda/misc/special.py +94 -0
  189. numba_cuda/numba/cuda/models.py +56 -0
  190. numba_cuda/numba/cuda/np/arraymath.py +5130 -0
  191. numba_cuda/numba/cuda/np/arrayobj.py +7635 -0
  192. numba_cuda/numba/cuda/np/extensions.py +11 -0
  193. numba_cuda/numba/cuda/np/linalg.py +3087 -0
  194. numba_cuda/numba/cuda/np/math/__init__.py +0 -0
  195. numba_cuda/numba/cuda/np/math/cmathimpl.py +558 -0
  196. numba_cuda/numba/cuda/np/math/mathimpl.py +487 -0
  197. numba_cuda/numba/cuda/np/math/numbers.py +1461 -0
  198. numba_cuda/numba/cuda/np/npdatetime.py +969 -0
  199. numba_cuda/numba/cuda/np/npdatetime_helpers.py +217 -0
  200. numba_cuda/numba/cuda/np/npyfuncs.py +1808 -0
  201. numba_cuda/numba/cuda/np/npyimpl.py +1027 -0
  202. numba_cuda/numba/cuda/np/numpy_support.py +798 -0
  203. numba_cuda/numba/cuda/np/polynomial/__init__.py +4 -0
  204. numba_cuda/numba/cuda/np/polynomial/polynomial_core.py +242 -0
  205. numba_cuda/numba/cuda/np/polynomial/polynomial_functions.py +380 -0
  206. numba_cuda/numba/cuda/np/ufunc/__init__.py +4 -0
  207. numba_cuda/numba/cuda/np/ufunc/decorators.py +203 -0
  208. numba_cuda/numba/cuda/np/ufunc/sigparse.py +68 -0
  209. numba_cuda/numba/cuda/np/ufunc/ufuncbuilder.py +65 -0
  210. numba_cuda/numba/cuda/np/ufunc_db.py +1282 -0
  211. numba_cuda/numba/cuda/np/unsafe/__init__.py +0 -0
  212. numba_cuda/numba/cuda/np/unsafe/ndarray.py +84 -0
  213. numba_cuda/numba/cuda/nvvmutils.py +254 -0
  214. numba_cuda/numba/cuda/printimpl.py +126 -0
  215. numba_cuda/numba/cuda/random.py +308 -0
  216. numba_cuda/numba/cuda/reshape_funcs.cu +156 -0
  217. numba_cuda/numba/cuda/serialize.py +267 -0
  218. numba_cuda/numba/cuda/simulator/__init__.py +63 -0
  219. numba_cuda/numba/cuda/simulator/_internal/__init__.py +4 -0
  220. numba_cuda/numba/cuda/simulator/_internal/cuda_bf16.py +2 -0
  221. numba_cuda/numba/cuda/simulator/api.py +179 -0
  222. numba_cuda/numba/cuda/simulator/bf16.py +4 -0
  223. numba_cuda/numba/cuda/simulator/compiler.py +38 -0
  224. numba_cuda/numba/cuda/simulator/cudadrv/__init__.py +11 -0
  225. numba_cuda/numba/cuda/simulator/cudadrv/devicearray.py +462 -0
  226. numba_cuda/numba/cuda/simulator/cudadrv/devices.py +122 -0
  227. numba_cuda/numba/cuda/simulator/cudadrv/driver.py +66 -0
  228. numba_cuda/numba/cuda/simulator/cudadrv/drvapi.py +7 -0
  229. numba_cuda/numba/cuda/simulator/cudadrv/dummyarray.py +7 -0
  230. numba_cuda/numba/cuda/simulator/cudadrv/error.py +10 -0
  231. numba_cuda/numba/cuda/simulator/cudadrv/libs.py +10 -0
  232. numba_cuda/numba/cuda/simulator/cudadrv/linkable_code.py +61 -0
  233. numba_cuda/numba/cuda/simulator/cudadrv/nvrtc.py +11 -0
  234. numba_cuda/numba/cuda/simulator/cudadrv/nvvm.py +32 -0
  235. numba_cuda/numba/cuda/simulator/cudadrv/runtime.py +22 -0
  236. numba_cuda/numba/cuda/simulator/dispatcher.py +11 -0
  237. numba_cuda/numba/cuda/simulator/kernel.py +320 -0
  238. numba_cuda/numba/cuda/simulator/kernelapi.py +509 -0
  239. numba_cuda/numba/cuda/simulator/memory_management/__init__.py +4 -0
  240. numba_cuda/numba/cuda/simulator/memory_management/nrt.py +21 -0
  241. numba_cuda/numba/cuda/simulator/reduction.py +19 -0
  242. numba_cuda/numba/cuda/simulator/tests/support.py +4 -0
  243. numba_cuda/numba/cuda/simulator/vector_types.py +65 -0
  244. numba_cuda/numba/cuda/simulator_init.py +18 -0
  245. numba_cuda/numba/cuda/stubs.py +624 -0
  246. numba_cuda/numba/cuda/target.py +505 -0
  247. numba_cuda/numba/cuda/testing.py +347 -0
  248. numba_cuda/numba/cuda/tests/__init__.py +62 -0
  249. numba_cuda/numba/cuda/tests/benchmarks/__init__.py +0 -0
  250. numba_cuda/numba/cuda/tests/benchmarks/test_kernel_launch.py +119 -0
  251. numba_cuda/numba/cuda/tests/cloudpickle_main_class.py +9 -0
  252. numba_cuda/numba/cuda/tests/core/serialize_usecases.py +113 -0
  253. numba_cuda/numba/cuda/tests/core/test_itanium_mangler.py +83 -0
  254. numba_cuda/numba/cuda/tests/core/test_serialize.py +371 -0
  255. numba_cuda/numba/cuda/tests/cudadrv/__init__.py +9 -0
  256. numba_cuda/numba/cuda/tests/cudadrv/test_array_attr.py +147 -0
  257. numba_cuda/numba/cuda/tests/cudadrv/test_context_stack.py +161 -0
  258. numba_cuda/numba/cuda/tests/cudadrv/test_cuda_array_slicing.py +397 -0
  259. numba_cuda/numba/cuda/tests/cudadrv/test_cuda_auto_context.py +24 -0
  260. numba_cuda/numba/cuda/tests/cudadrv/test_cuda_devicerecord.py +180 -0
  261. numba_cuda/numba/cuda/tests/cudadrv/test_cuda_driver.py +313 -0
  262. numba_cuda/numba/cuda/tests/cudadrv/test_cuda_memory.py +191 -0
  263. numba_cuda/numba/cuda/tests/cudadrv/test_cuda_ndarray.py +621 -0
  264. numba_cuda/numba/cuda/tests/cudadrv/test_deallocations.py +247 -0
  265. numba_cuda/numba/cuda/tests/cudadrv/test_detect.py +100 -0
  266. numba_cuda/numba/cuda/tests/cudadrv/test_emm_plugins.py +200 -0
  267. numba_cuda/numba/cuda/tests/cudadrv/test_events.py +53 -0
  268. numba_cuda/numba/cuda/tests/cudadrv/test_host_alloc.py +72 -0
  269. numba_cuda/numba/cuda/tests/cudadrv/test_init.py +138 -0
  270. numba_cuda/numba/cuda/tests/cudadrv/test_inline_ptx.py +43 -0
  271. numba_cuda/numba/cuda/tests/cudadrv/test_is_fp16.py +15 -0
  272. numba_cuda/numba/cuda/tests/cudadrv/test_linkable_code.py +58 -0
  273. numba_cuda/numba/cuda/tests/cudadrv/test_linker.py +348 -0
  274. numba_cuda/numba/cuda/tests/cudadrv/test_managed_alloc.py +128 -0
  275. numba_cuda/numba/cuda/tests/cudadrv/test_module_callbacks.py +301 -0
  276. numba_cuda/numba/cuda/tests/cudadrv/test_nvjitlink.py +174 -0
  277. numba_cuda/numba/cuda/tests/cudadrv/test_nvrtc.py +28 -0
  278. numba_cuda/numba/cuda/tests/cudadrv/test_nvvm_driver.py +185 -0
  279. numba_cuda/numba/cuda/tests/cudadrv/test_pinned.py +39 -0
  280. numba_cuda/numba/cuda/tests/cudadrv/test_profiler.py +23 -0
  281. numba_cuda/numba/cuda/tests/cudadrv/test_reset_device.py +38 -0
  282. numba_cuda/numba/cuda/tests/cudadrv/test_runtime.py +48 -0
  283. numba_cuda/numba/cuda/tests/cudadrv/test_select_device.py +44 -0
  284. numba_cuda/numba/cuda/tests/cudadrv/test_streams.py +127 -0
  285. numba_cuda/numba/cuda/tests/cudapy/__init__.py +9 -0
  286. numba_cuda/numba/cuda/tests/cudapy/cache_usecases.py +231 -0
  287. numba_cuda/numba/cuda/tests/cudapy/cache_with_cpu_usecases.py +50 -0
  288. numba_cuda/numba/cuda/tests/cudapy/cg_cache_usecases.py +36 -0
  289. numba_cuda/numba/cuda/tests/cudapy/complex_usecases.py +116 -0
  290. numba_cuda/numba/cuda/tests/cudapy/enum_usecases.py +59 -0
  291. numba_cuda/numba/cuda/tests/cudapy/extensions_usecases.py +62 -0
  292. numba_cuda/numba/cuda/tests/cudapy/jitlink.ptx +28 -0
  293. numba_cuda/numba/cuda/tests/cudapy/overload_usecases.py +33 -0
  294. numba_cuda/numba/cuda/tests/cudapy/recursion_usecases.py +104 -0
  295. numba_cuda/numba/cuda/tests/cudapy/test_alignment.py +47 -0
  296. numba_cuda/numba/cuda/tests/cudapy/test_analysis.py +1122 -0
  297. numba_cuda/numba/cuda/tests/cudapy/test_array.py +344 -0
  298. numba_cuda/numba/cuda/tests/cudapy/test_array_alignment.py +268 -0
  299. numba_cuda/numba/cuda/tests/cudapy/test_array_args.py +203 -0
  300. numba_cuda/numba/cuda/tests/cudapy/test_array_methods.py +63 -0
  301. numba_cuda/numba/cuda/tests/cudapy/test_array_reductions.py +360 -0
  302. numba_cuda/numba/cuda/tests/cudapy/test_atomics.py +1815 -0
  303. numba_cuda/numba/cuda/tests/cudapy/test_bfloat16.py +599 -0
  304. numba_cuda/numba/cuda/tests/cudapy/test_bfloat16_bindings.py +377 -0
  305. numba_cuda/numba/cuda/tests/cudapy/test_blackscholes.py +160 -0
  306. numba_cuda/numba/cuda/tests/cudapy/test_boolean.py +27 -0
  307. numba_cuda/numba/cuda/tests/cudapy/test_byteflow.py +98 -0
  308. numba_cuda/numba/cuda/tests/cudapy/test_cache_hints.py +210 -0
  309. numba_cuda/numba/cuda/tests/cudapy/test_caching.py +683 -0
  310. numba_cuda/numba/cuda/tests/cudapy/test_casting.py +265 -0
  311. numba_cuda/numba/cuda/tests/cudapy/test_cffi.py +42 -0
  312. numba_cuda/numba/cuda/tests/cudapy/test_compiler.py +718 -0
  313. numba_cuda/numba/cuda/tests/cudapy/test_complex.py +370 -0
  314. numba_cuda/numba/cuda/tests/cudapy/test_complex_kernel.py +23 -0
  315. numba_cuda/numba/cuda/tests/cudapy/test_const_string.py +142 -0
  316. numba_cuda/numba/cuda/tests/cudapy/test_constmem.py +178 -0
  317. numba_cuda/numba/cuda/tests/cudapy/test_cooperative_groups.py +193 -0
  318. numba_cuda/numba/cuda/tests/cudapy/test_copy_propagate.py +131 -0
  319. numba_cuda/numba/cuda/tests/cudapy/test_cuda_array_interface.py +438 -0
  320. numba_cuda/numba/cuda/tests/cudapy/test_cuda_jit_no_types.py +94 -0
  321. numba_cuda/numba/cuda/tests/cudapy/test_datetime.py +101 -0
  322. numba_cuda/numba/cuda/tests/cudapy/test_debug.py +105 -0
  323. numba_cuda/numba/cuda/tests/cudapy/test_debuginfo.py +978 -0
  324. numba_cuda/numba/cuda/tests/cudapy/test_debuginfo_types.py +476 -0
  325. numba_cuda/numba/cuda/tests/cudapy/test_device_func.py +500 -0
  326. numba_cuda/numba/cuda/tests/cudapy/test_dispatcher.py +820 -0
  327. numba_cuda/numba/cuda/tests/cudapy/test_enums.py +152 -0
  328. numba_cuda/numba/cuda/tests/cudapy/test_errors.py +111 -0
  329. numba_cuda/numba/cuda/tests/cudapy/test_exception.py +170 -0
  330. numba_cuda/numba/cuda/tests/cudapy/test_extending.py +1088 -0
  331. numba_cuda/numba/cuda/tests/cudapy/test_extending_types.py +71 -0
  332. numba_cuda/numba/cuda/tests/cudapy/test_fastmath.py +265 -0
  333. numba_cuda/numba/cuda/tests/cudapy/test_flow_control.py +1433 -0
  334. numba_cuda/numba/cuda/tests/cudapy/test_forall.py +57 -0
  335. numba_cuda/numba/cuda/tests/cudapy/test_freevar.py +34 -0
  336. numba_cuda/numba/cuda/tests/cudapy/test_frexp_ldexp.py +69 -0
  337. numba_cuda/numba/cuda/tests/cudapy/test_globals.py +62 -0
  338. numba_cuda/numba/cuda/tests/cudapy/test_gufunc.py +474 -0
  339. numba_cuda/numba/cuda/tests/cudapy/test_gufunc_scalar.py +167 -0
  340. numba_cuda/numba/cuda/tests/cudapy/test_gufunc_scheduling.py +92 -0
  341. numba_cuda/numba/cuda/tests/cudapy/test_idiv.py +39 -0
  342. numba_cuda/numba/cuda/tests/cudapy/test_inline.py +170 -0
  343. numba_cuda/numba/cuda/tests/cudapy/test_inspect.py +255 -0
  344. numba_cuda/numba/cuda/tests/cudapy/test_intrinsics.py +1219 -0
  345. numba_cuda/numba/cuda/tests/cudapy/test_ipc.py +263 -0
  346. numba_cuda/numba/cuda/tests/cudapy/test_ir.py +598 -0
  347. numba_cuda/numba/cuda/tests/cudapy/test_ir_utils.py +276 -0
  348. numba_cuda/numba/cuda/tests/cudapy/test_iterators.py +101 -0
  349. numba_cuda/numba/cuda/tests/cudapy/test_lang.py +68 -0
  350. numba_cuda/numba/cuda/tests/cudapy/test_laplace.py +123 -0
  351. numba_cuda/numba/cuda/tests/cudapy/test_libdevice.py +194 -0
  352. numba_cuda/numba/cuda/tests/cudapy/test_lineinfo.py +220 -0
  353. numba_cuda/numba/cuda/tests/cudapy/test_localmem.py +173 -0
  354. numba_cuda/numba/cuda/tests/cudapy/test_make_function_to_jit_function.py +364 -0
  355. numba_cuda/numba/cuda/tests/cudapy/test_mandel.py +47 -0
  356. numba_cuda/numba/cuda/tests/cudapy/test_math.py +842 -0
  357. numba_cuda/numba/cuda/tests/cudapy/test_matmul.py +76 -0
  358. numba_cuda/numba/cuda/tests/cudapy/test_minmax.py +78 -0
  359. numba_cuda/numba/cuda/tests/cudapy/test_montecarlo.py +25 -0
  360. numba_cuda/numba/cuda/tests/cudapy/test_multigpu.py +145 -0
  361. numba_cuda/numba/cuda/tests/cudapy/test_multiprocessing.py +39 -0
  362. numba_cuda/numba/cuda/tests/cudapy/test_multithreads.py +82 -0
  363. numba_cuda/numba/cuda/tests/cudapy/test_nondet.py +53 -0
  364. numba_cuda/numba/cuda/tests/cudapy/test_operator.py +504 -0
  365. numba_cuda/numba/cuda/tests/cudapy/test_optimization.py +93 -0
  366. numba_cuda/numba/cuda/tests/cudapy/test_overload.py +402 -0
  367. numba_cuda/numba/cuda/tests/cudapy/test_powi.py +128 -0
  368. numba_cuda/numba/cuda/tests/cudapy/test_print.py +193 -0
  369. numba_cuda/numba/cuda/tests/cudapy/test_py2_div_issue.py +37 -0
  370. numba_cuda/numba/cuda/tests/cudapy/test_random.py +117 -0
  371. numba_cuda/numba/cuda/tests/cudapy/test_record_dtype.py +614 -0
  372. numba_cuda/numba/cuda/tests/cudapy/test_recursion.py +130 -0
  373. numba_cuda/numba/cuda/tests/cudapy/test_reduction.py +94 -0
  374. numba_cuda/numba/cuda/tests/cudapy/test_retrieve_autoconverted_arrays.py +83 -0
  375. numba_cuda/numba/cuda/tests/cudapy/test_serialize.py +86 -0
  376. numba_cuda/numba/cuda/tests/cudapy/test_slicing.py +40 -0
  377. numba_cuda/numba/cuda/tests/cudapy/test_sm.py +457 -0
  378. numba_cuda/numba/cuda/tests/cudapy/test_sm_creation.py +233 -0
  379. numba_cuda/numba/cuda/tests/cudapy/test_ssa.py +454 -0
  380. numba_cuda/numba/cuda/tests/cudapy/test_stream_api.py +56 -0
  381. numba_cuda/numba/cuda/tests/cudapy/test_sync.py +277 -0
  382. numba_cuda/numba/cuda/tests/cudapy/test_tracing.py +200 -0
  383. numba_cuda/numba/cuda/tests/cudapy/test_transpose.py +90 -0
  384. numba_cuda/numba/cuda/tests/cudapy/test_typeconv.py +333 -0
  385. numba_cuda/numba/cuda/tests/cudapy/test_typeinfer.py +538 -0
  386. numba_cuda/numba/cuda/tests/cudapy/test_ufuncs.py +585 -0
  387. numba_cuda/numba/cuda/tests/cudapy/test_userexc.py +42 -0
  388. numba_cuda/numba/cuda/tests/cudapy/test_vector_type.py +485 -0
  389. numba_cuda/numba/cuda/tests/cudapy/test_vectorize.py +312 -0
  390. numba_cuda/numba/cuda/tests/cudapy/test_vectorize_complex.py +23 -0
  391. numba_cuda/numba/cuda/tests/cudapy/test_vectorize_decor.py +183 -0
  392. numba_cuda/numba/cuda/tests/cudapy/test_vectorize_device.py +40 -0
  393. numba_cuda/numba/cuda/tests/cudapy/test_vectorize_scalar_arg.py +40 -0
  394. numba_cuda/numba/cuda/tests/cudapy/test_warning.py +206 -0
  395. numba_cuda/numba/cuda/tests/cudapy/test_warp_ops.py +446 -0
  396. numba_cuda/numba/cuda/tests/cudasim/__init__.py +9 -0
  397. numba_cuda/numba/cuda/tests/cudasim/support.py +9 -0
  398. numba_cuda/numba/cuda/tests/cudasim/test_cudasim_issues.py +111 -0
  399. numba_cuda/numba/cuda/tests/data/__init__.py +2 -0
  400. numba_cuda/numba/cuda/tests/data/cta_barrier.cu +28 -0
  401. numba_cuda/numba/cuda/tests/data/cuda_include.cu +10 -0
  402. numba_cuda/numba/cuda/tests/data/error.cu +12 -0
  403. numba_cuda/numba/cuda/tests/data/include/add.cuh +8 -0
  404. numba_cuda/numba/cuda/tests/data/jitlink.cu +28 -0
  405. numba_cuda/numba/cuda/tests/data/jitlink.ptx +49 -0
  406. numba_cuda/numba/cuda/tests/data/warn.cu +12 -0
  407. numba_cuda/numba/cuda/tests/doc_examples/__init__.py +9 -0
  408. numba_cuda/numba/cuda/tests/doc_examples/ffi/__init__.py +2 -0
  409. numba_cuda/numba/cuda/tests/doc_examples/ffi/functions.cu +54 -0
  410. numba_cuda/numba/cuda/tests/doc_examples/ffi/include/mul.cuh +8 -0
  411. numba_cuda/numba/cuda/tests/doc_examples/ffi/saxpy.cu +14 -0
  412. numba_cuda/numba/cuda/tests/doc_examples/test_cg.py +86 -0
  413. numba_cuda/numba/cuda/tests/doc_examples/test_cpointer.py +68 -0
  414. numba_cuda/numba/cuda/tests/doc_examples/test_cpu_gpu_compat.py +81 -0
  415. numba_cuda/numba/cuda/tests/doc_examples/test_ffi.py +141 -0
  416. numba_cuda/numba/cuda/tests/doc_examples/test_laplace.py +160 -0
  417. numba_cuda/numba/cuda/tests/doc_examples/test_matmul.py +180 -0
  418. numba_cuda/numba/cuda/tests/doc_examples/test_montecarlo.py +119 -0
  419. numba_cuda/numba/cuda/tests/doc_examples/test_random.py +66 -0
  420. numba_cuda/numba/cuda/tests/doc_examples/test_reduction.py +80 -0
  421. numba_cuda/numba/cuda/tests/doc_examples/test_sessionize.py +206 -0
  422. numba_cuda/numba/cuda/tests/doc_examples/test_ufunc.py +53 -0
  423. numba_cuda/numba/cuda/tests/doc_examples/test_vecadd.py +76 -0
  424. numba_cuda/numba/cuda/tests/nocuda/__init__.py +9 -0
  425. numba_cuda/numba/cuda/tests/nocuda/test_dummyarray.py +452 -0
  426. numba_cuda/numba/cuda/tests/nocuda/test_function_resolution.py +48 -0
  427. numba_cuda/numba/cuda/tests/nocuda/test_import.py +63 -0
  428. numba_cuda/numba/cuda/tests/nocuda/test_library_lookup.py +252 -0
  429. numba_cuda/numba/cuda/tests/nocuda/test_nvvm.py +59 -0
  430. numba_cuda/numba/cuda/tests/nrt/__init__.py +9 -0
  431. numba_cuda/numba/cuda/tests/nrt/test_nrt.py +387 -0
  432. numba_cuda/numba/cuda/tests/nrt/test_nrt_refct.py +124 -0
  433. numba_cuda/numba/cuda/tests/support.py +900 -0
  434. numba_cuda/numba/cuda/typeconv/__init__.py +4 -0
  435. numba_cuda/numba/cuda/typeconv/castgraph.py +137 -0
  436. numba_cuda/numba/cuda/typeconv/rules.py +63 -0
  437. numba_cuda/numba/cuda/typeconv/typeconv.py +121 -0
  438. numba_cuda/numba/cuda/types/__init__.py +233 -0
  439. numba_cuda/numba/cuda/types/__init__.pyi +167 -0
  440. numba_cuda/numba/cuda/types/abstract.py +9 -0
  441. numba_cuda/numba/cuda/types/common.py +9 -0
  442. numba_cuda/numba/cuda/types/containers.py +9 -0
  443. numba_cuda/numba/cuda/types/cuda_abstract.py +533 -0
  444. numba_cuda/numba/cuda/types/cuda_common.py +110 -0
  445. numba_cuda/numba/cuda/types/cuda_containers.py +971 -0
  446. numba_cuda/numba/cuda/types/cuda_function_type.py +230 -0
  447. numba_cuda/numba/cuda/types/cuda_functions.py +798 -0
  448. numba_cuda/numba/cuda/types/cuda_iterators.py +120 -0
  449. numba_cuda/numba/cuda/types/cuda_misc.py +569 -0
  450. numba_cuda/numba/cuda/types/cuda_npytypes.py +690 -0
  451. numba_cuda/numba/cuda/types/cuda_scalars.py +280 -0
  452. numba_cuda/numba/cuda/types/ext_types.py +101 -0
  453. numba_cuda/numba/cuda/types/function_type.py +11 -0
  454. numba_cuda/numba/cuda/types/functions.py +9 -0
  455. numba_cuda/numba/cuda/types/iterators.py +9 -0
  456. numba_cuda/numba/cuda/types/misc.py +9 -0
  457. numba_cuda/numba/cuda/types/npytypes.py +9 -0
  458. numba_cuda/numba/cuda/types/scalars.py +9 -0
  459. numba_cuda/numba/cuda/typing/__init__.py +19 -0
  460. numba_cuda/numba/cuda/typing/arraydecl.py +939 -0
  461. numba_cuda/numba/cuda/typing/asnumbatype.py +130 -0
  462. numba_cuda/numba/cuda/typing/bufproto.py +70 -0
  463. numba_cuda/numba/cuda/typing/builtins.py +1209 -0
  464. numba_cuda/numba/cuda/typing/cffi_utils.py +219 -0
  465. numba_cuda/numba/cuda/typing/cmathdecl.py +47 -0
  466. numba_cuda/numba/cuda/typing/collections.py +138 -0
  467. numba_cuda/numba/cuda/typing/context.py +782 -0
  468. numba_cuda/numba/cuda/typing/ctypes_utils.py +125 -0
  469. numba_cuda/numba/cuda/typing/dictdecl.py +63 -0
  470. numba_cuda/numba/cuda/typing/enumdecl.py +74 -0
  471. numba_cuda/numba/cuda/typing/listdecl.py +147 -0
  472. numba_cuda/numba/cuda/typing/mathdecl.py +158 -0
  473. numba_cuda/numba/cuda/typing/npdatetime.py +322 -0
  474. numba_cuda/numba/cuda/typing/npydecl.py +749 -0
  475. numba_cuda/numba/cuda/typing/setdecl.py +115 -0
  476. numba_cuda/numba/cuda/typing/templates.py +1446 -0
  477. numba_cuda/numba/cuda/typing/typeof.py +301 -0
  478. numba_cuda/numba/cuda/ufuncs.py +746 -0
  479. numba_cuda/numba/cuda/utils.py +724 -0
  480. numba_cuda/numba/cuda/vector_types.py +214 -0
  481. numba_cuda/numba/cuda/vectorizers.py +260 -0
  482. numba_cuda-0.22.0.dist-info/METADATA +109 -0
  483. numba_cuda-0.22.0.dist-info/RECORD +487 -0
  484. numba_cuda-0.22.0.dist-info/WHEEL +6 -0
  485. numba_cuda-0.22.0.dist-info/licenses/LICENSE +26 -0
  486. numba_cuda-0.22.0.dist-info/licenses/LICENSE.numba +24 -0
  487. numba_cuda-0.22.0.dist-info/top_level.txt +1 -0
@@ -0,0 +1,1446 @@
1
+ # SPDX-FileCopyrightText: Copyright (c) 2025 NVIDIA CORPORATION & AFFILIATES. All rights reserved.
2
+ # SPDX-License-Identifier: BSD-2-Clause
3
+
4
+ """
5
+ Define typing templates
6
+ """
7
+
8
+ from abc import ABC, abstractmethod
9
+ import functools
10
+ import sys
11
+ import inspect
12
+ import os.path
13
+ from collections import namedtuple
14
+ from collections.abc import Sequence
15
+ from types import MethodType, FunctionType, MappingProxyType
16
+
17
+ import numba
18
+ from numba.cuda import types
19
+ from numba.cuda.core.errors import (
20
+ TypingError,
21
+ InternalError,
22
+ )
23
+ from numba.cuda.core.options import InlineOptions
24
+
25
+ from numba.cuda import utils
26
+ from numba.cuda.core import targetconfig
27
+
28
+ from numba.cuda import HAS_NUMBA
29
+
30
+ if HAS_NUMBA:
31
+ from numba.core.typing import Signature as CoreSignature
32
+
33
+ # info store for inliner callback functions e.g. cost model
34
+ _inline_info = namedtuple("inline_info", "func_ir typemap calltypes signature")
35
+
36
+
37
+ class Signature(object):
38
+ """
39
+ The signature of a function call or operation, i.e. its argument types
40
+ and return type.
41
+ """
42
+
43
+ # XXX Perhaps the signature should be a BoundArguments, instead
44
+ # of separate args and pysig...
45
+ __slots__ = "_return_type", "_args", "_recvr", "_pysig"
46
+
47
+ def __init__(self, return_type, args, recvr, pysig=None):
48
+ if isinstance(args, list):
49
+ args = tuple(args)
50
+ self._return_type = return_type
51
+ self._args = args
52
+ self._recvr = recvr
53
+ self._pysig = pysig
54
+
55
+ @property
56
+ def return_type(self):
57
+ return self._return_type
58
+
59
+ @property
60
+ def args(self):
61
+ return self._args
62
+
63
+ @property
64
+ def recvr(self):
65
+ return self._recvr
66
+
67
+ @property
68
+ def pysig(self):
69
+ return self._pysig
70
+
71
+ def replace(self, **kwargs):
72
+ """Copy and replace the given attributes provided as keyword arguments.
73
+ Returns an updated copy.
74
+ """
75
+ curstate = dict(
76
+ return_type=self.return_type,
77
+ args=self.args,
78
+ recvr=self.recvr,
79
+ pysig=self.pysig,
80
+ )
81
+ curstate.update(kwargs)
82
+ return Signature(**curstate)
83
+
84
+ def __getstate__(self):
85
+ """
86
+ Needed because of __slots__.
87
+ """
88
+ return self._return_type, self._args, self._recvr, self._pysig
89
+
90
+ def __setstate__(self, state):
91
+ """
92
+ Needed because of __slots__.
93
+ """
94
+ self._return_type, self._args, self._recvr, self._pysig = state
95
+
96
+ def __hash__(self):
97
+ return hash((self.args, self.return_type))
98
+
99
+ def __eq__(self, other):
100
+ sig_types = (Signature,)
101
+ if HAS_NUMBA:
102
+ sig_types = (Signature, CoreSignature)
103
+ if isinstance(other, sig_types):
104
+ return (
105
+ self.args == other.args
106
+ and self.return_type == other.return_type
107
+ and self.recvr == other.recvr
108
+ and self.pysig == other.pysig
109
+ )
110
+
111
+ def __ne__(self, other):
112
+ return not (self == other)
113
+
114
+ def __repr__(self):
115
+ return "%s -> %s" % (self.args, self.return_type)
116
+
117
+ @property
118
+ def is_method(self):
119
+ """
120
+ Whether this signature represents a bound method or a regular
121
+ function.
122
+ """
123
+ return self.recvr is not None
124
+
125
+ def as_method(self):
126
+ """
127
+ Convert this signature to a bound method signature.
128
+ """
129
+ if self.recvr is not None:
130
+ return self
131
+ sig = signature(self.return_type, *self.args[1:], recvr=self.args[0])
132
+
133
+ # Adjust the python signature
134
+ params = list(self.pysig.parameters.values())[1:]
135
+ sig = sig.replace(
136
+ pysig=utils.pySignature(
137
+ parameters=params,
138
+ return_annotation=self.pysig.return_annotation,
139
+ ),
140
+ )
141
+ return sig
142
+
143
+ def as_function(self):
144
+ """
145
+ Convert this signature to a regular function signature.
146
+ """
147
+ if self.recvr is None:
148
+ return self
149
+ sig = signature(self.return_type, *((self.recvr,) + self.args))
150
+ return sig
151
+
152
+ def as_type(self):
153
+ """
154
+ Convert this signature to a first-class function type.
155
+ """
156
+ return types.FunctionType(self)
157
+
158
+ def __unliteral__(self):
159
+ return signature(
160
+ types.unliteral(self.return_type), *map(types.unliteral, self.args)
161
+ )
162
+
163
+ def dump(self, tab=""):
164
+ c = self.as_type()._code
165
+ print(f"{tab}DUMP {type(self).__name__} [type code: {c}]")
166
+ print(f"{tab} Argument types:")
167
+ for a in self.args:
168
+ a.dump(tab=tab + " | ")
169
+ print(f"{tab} Return type:")
170
+ self.return_type.dump(tab=tab + " | ")
171
+ print(f"{tab}END DUMP")
172
+
173
+ def is_precise(self):
174
+ for atype in self.args:
175
+ if not atype.is_precise():
176
+ return False
177
+ return self.return_type.is_precise()
178
+
179
+
180
+ def make_concrete_template(name, key, signatures):
181
+ baseclasses = (ConcreteTemplate,)
182
+ gvars = dict(key=key, cases=list(signatures))
183
+ return type(name, baseclasses, gvars)
184
+
185
+
186
+ def make_callable_template(key, typer, recvr=None):
187
+ """
188
+ Create a callable template with the given key and typer function.
189
+ """
190
+
191
+ def generic(self):
192
+ return typer
193
+
194
+ name = "%s_CallableTemplate" % (key,)
195
+ bases = (CallableTemplate,)
196
+ class_dict = dict(key=key, generic=generic, recvr=recvr)
197
+ return type(name, bases, class_dict)
198
+
199
+
200
+ def signature(return_type, *args, **kws):
201
+ recvr = kws.pop("recvr", None)
202
+ assert not kws
203
+ if HAS_NUMBA:
204
+ signature_class = CoreSignature
205
+ else:
206
+ signature_class = Signature
207
+ return signature_class(return_type, args, recvr=recvr)
208
+
209
+
210
+ def fold_arguments(
211
+ pysig, args, kws, normal_handler, default_handler, stararg_handler
212
+ ):
213
+ """
214
+ Given the signature *pysig*, explicit *args* and *kws*, resolve
215
+ omitted arguments and keyword arguments. A tuple of positional
216
+ arguments is returned.
217
+ Various handlers allow to process arguments:
218
+ - normal_handler(index, param, value) is called for normal arguments
219
+ - default_handler(index, param, default) is called for omitted arguments
220
+ - stararg_handler(index, param, values) is called for a "*args" argument
221
+ """
222
+ if isinstance(kws, Sequence):
223
+ # Normalize dict kws
224
+ kws = dict(kws)
225
+
226
+ # deal with kwonly args
227
+ params = pysig.parameters
228
+ kwonly = []
229
+ for name, p in params.items():
230
+ if p.kind == p.KEYWORD_ONLY:
231
+ kwonly.append(name)
232
+
233
+ if kwonly:
234
+ bind_args = args[: -len(kwonly)]
235
+ else:
236
+ bind_args = args
237
+ bind_kws = kws.copy()
238
+ if kwonly:
239
+ for idx, n in enumerate(kwonly):
240
+ bind_kws[n] = args[len(kwonly) + idx]
241
+
242
+ # now bind
243
+ try:
244
+ ba = pysig.bind(*bind_args, **bind_kws)
245
+ except TypeError as e:
246
+ # The binding attempt can raise if the args don't match up, this needs
247
+ # to be converted to a TypingError so that e.g. partial type inference
248
+ # doesn't just halt.
249
+ msg = (
250
+ f"Cannot bind 'args={bind_args} kws={bind_kws}' to "
251
+ f"signature '{pysig}' due to \"{type(e).__name__}: {e}\"."
252
+ )
253
+ raise TypingError(msg)
254
+ for i, param in enumerate(pysig.parameters.values()):
255
+ name = param.name
256
+ default = param.default
257
+ if param.kind == param.VAR_POSITIONAL:
258
+ # stararg may be omitted, in which case its "default" value
259
+ # is simply the empty tuple
260
+ if name in ba.arguments:
261
+ argval = ba.arguments[name]
262
+ # NOTE: avoid wrapping the tuple type for stararg in another
263
+ # tuple.
264
+ if len(argval) == 1 and isinstance(
265
+ argval[0], (types.StarArgTuple, types.StarArgUniTuple)
266
+ ):
267
+ argval = tuple(argval[0])
268
+ else:
269
+ argval = ()
270
+ out = stararg_handler(i, param, argval)
271
+
272
+ ba.arguments[name] = out
273
+ elif name in ba.arguments:
274
+ # Non-stararg, present
275
+ ba.arguments[name] = normal_handler(i, param, ba.arguments[name])
276
+ else:
277
+ # Non-stararg, omitted
278
+ assert default is not param.empty
279
+ ba.arguments[name] = default_handler(i, param, default)
280
+ # Collect args in the right order
281
+ args = tuple(
282
+ ba.arguments[param.name] for param in pysig.parameters.values()
283
+ )
284
+ return args
285
+
286
+
287
+ class FunctionTemplate(ABC):
288
+ # Set to true to disable unsafe cast.
289
+ # subclass overide-able
290
+ unsafe_casting = True
291
+ # Set to true to require exact match without casting.
292
+ # subclass overide-able
293
+ exact_match_required = False
294
+ # Set to true to prefer literal arguments.
295
+ # Useful for definitions that specialize on literal but also support
296
+ # non-literals.
297
+ # subclass overide-able
298
+ prefer_literal = False
299
+ # metadata
300
+ metadata = {}
301
+
302
+ def __init__(self, context):
303
+ self.context = context
304
+
305
+ def _select(self, cases, args, kws):
306
+ options = {
307
+ "unsafe_casting": self.unsafe_casting,
308
+ "exact_match_required": self.exact_match_required,
309
+ }
310
+ selected = self.context.resolve_overload(
311
+ self.key, cases, args, kws, **options
312
+ )
313
+ return selected
314
+
315
+ def get_impl_key(self, sig):
316
+ """
317
+ Return the key for looking up the implementation for the given
318
+ signature on the target context.
319
+ """
320
+ # Lookup the key on the class, to avoid binding it with `self`.
321
+ key = type(self).key
322
+ # On Python 2, we must also take care about unbound methods
323
+ if isinstance(key, MethodType):
324
+ assert key.im_self is None
325
+ key = key.im_func
326
+ return key
327
+
328
+ @classmethod
329
+ def get_source_code_info(cls, impl):
330
+ """
331
+ Gets the source information about function impl.
332
+ Returns:
333
+
334
+ code - str: source code as a string
335
+ firstlineno - int: the first line number of the function impl
336
+ path - str: the path to file containing impl
337
+
338
+ if any of the above are not available something generic is returned
339
+ """
340
+ try:
341
+ code, firstlineno = inspect.getsourcelines(impl)
342
+ except OSError: # missing source, probably a string
343
+ code = "None available (built from string?)"
344
+ firstlineno = 0
345
+ path = inspect.getsourcefile(impl)
346
+ if path is None:
347
+ path = "<unknown> (built from string?)"
348
+ return code, firstlineno, path
349
+
350
+ @abstractmethod
351
+ def get_template_info(self):
352
+ """
353
+ Returns a dictionary with information specific to the template that will
354
+ govern how error messages are displayed to users. The dictionary must
355
+ be of the form:
356
+ info = {
357
+ 'kind': "unknown", # str: The kind of template, e.g. "Overload"
358
+ 'name': "unknown", # str: The name of the source function
359
+ 'sig': "unknown", # str: The signature(s) of the source function
360
+ 'filename': "unknown", # str: The filename of the source function
361
+ 'lines': ("start", "end"), # tuple(int, int): The start and
362
+ end line of the source function.
363
+ 'docstring': "unknown" # str: The docstring of the source function
364
+ }
365
+ """
366
+ pass
367
+
368
+ def __str__(self):
369
+ info = self.get_template_info()
370
+ srcinfo = f"{info['filename']}:{info['lines'][0]}"
371
+ return f"<{self.__class__.__name__} {srcinfo}>"
372
+
373
+ __repr__ = __str__
374
+
375
+
376
+ class AbstractTemplate(FunctionTemplate):
377
+ """
378
+ Defines method ``generic(self, args, kws)`` which compute a possible
379
+ signature base on input types. The signature does not have to match the
380
+ input types. It is compared against the input types afterwards.
381
+ """
382
+
383
+ def apply(self, args, kws):
384
+ generic = getattr(self, "generic")
385
+ sig = generic(args, kws)
386
+ # Enforce that *generic()* must return None or Signature
387
+ if sig is not None:
388
+ sig_types = (Signature,)
389
+ if HAS_NUMBA:
390
+ sig_types = (Signature, CoreSignature)
391
+ if not isinstance(sig, sig_types):
392
+ raise AssertionError(
393
+ "generic() must return a Signature or None. "
394
+ "{} returned {}".format(generic, type(sig)),
395
+ )
396
+
397
+ # Unpack optional type if no matching signature
398
+ if not sig and any(isinstance(x, types.Optional) for x in args):
399
+
400
+ def unpack_opt(x):
401
+ if isinstance(x, types.Optional):
402
+ return x.type
403
+ else:
404
+ return x
405
+
406
+ args = list(map(unpack_opt, args))
407
+ assert not kws # Not supported yet
408
+ sig = generic(args, kws)
409
+
410
+ return sig
411
+
412
+ def get_template_info(self):
413
+ impl = getattr(self, "generic")
414
+ basepath = os.path.dirname(
415
+ os.path.dirname(os.path.dirname(numba.cuda.__file__))
416
+ )
417
+
418
+ code, firstlineno, path = self.get_source_code_info(impl)
419
+ sig = str(utils.pysignature(impl))
420
+ info = {
421
+ "kind": "overload",
422
+ "name": getattr(impl, "__qualname__", impl.__name__),
423
+ "sig": sig,
424
+ "filename": utils.safe_relpath(path, start=basepath),
425
+ "lines": (firstlineno, firstlineno + len(code) - 1),
426
+ "docstring": impl.__doc__,
427
+ }
428
+ return info
429
+
430
+
431
+ class CallableTemplate(FunctionTemplate):
432
+ """
433
+ Base class for a template defining a ``generic(self)`` method
434
+ returning a callable to be called with the actual ``*args`` and
435
+ ``**kwargs`` representing the call signature. The callable has
436
+ to return a return type, a full signature, or None. The signature
437
+ does not have to match the input types. It is compared against the
438
+ input types afterwards.
439
+ """
440
+
441
+ recvr = None
442
+
443
+ def apply(self, args, kws):
444
+ generic = getattr(self, "generic")
445
+ typer = generic()
446
+ match_sig = inspect.signature(typer)
447
+ try:
448
+ match_sig.bind(*args, **kws)
449
+ except TypeError as e:
450
+ # bind failed, raise, if there's a
451
+ # ValueError then there's likely unrecoverable
452
+ # problems
453
+ raise TypingError(str(e)) from e
454
+
455
+ sig = typer(*args, **kws)
456
+
457
+ # Unpack optional type if no matching signature
458
+ if sig is None:
459
+ if any(isinstance(x, types.Optional) for x in args):
460
+
461
+ def unpack_opt(x):
462
+ if isinstance(x, types.Optional):
463
+ return x.type
464
+ else:
465
+ return x
466
+
467
+ args = list(map(unpack_opt, args))
468
+ sig = typer(*args, **kws)
469
+ if sig is None:
470
+ return
471
+
472
+ # Get the pysig
473
+ try:
474
+ pysig = typer.pysig
475
+ except AttributeError:
476
+ pysig = utils.pysignature(typer)
477
+
478
+ # Fold any keyword arguments
479
+ bound = pysig.bind(*args, **kws)
480
+ if bound.kwargs:
481
+ raise TypingError("unsupported call signature")
482
+ if not isinstance(sig, Signature):
483
+ # If not a signature, `sig` is assumed to be the return type
484
+ if not isinstance(sig, types.Type):
485
+ raise TypeError(
486
+ "invalid return type for callable template: got %r" % (sig,)
487
+ )
488
+ sig = signature(sig, *bound.args)
489
+ if self.recvr is not None:
490
+ sig = sig.replace(recvr=self.recvr)
491
+ # Hack any omitted parameters out of the typer's pysig,
492
+ # as lowering expects an exact match between formal signature
493
+ # and actual args.
494
+ if len(bound.args) < len(pysig.parameters):
495
+ parameters = list(pysig.parameters.values())[: len(bound.args)]
496
+ pysig = pysig.replace(parameters=parameters)
497
+ sig = sig.replace(pysig=pysig)
498
+ cases = [sig]
499
+ return self._select(cases, bound.args, bound.kwargs)
500
+
501
+ def get_template_info(self):
502
+ impl = getattr(self, "generic")
503
+ basepath = os.path.dirname(
504
+ os.path.dirname(os.path.dirname(numba.cuda.__file__))
505
+ )
506
+ code, firstlineno, path = self.get_source_code_info(impl)
507
+ sig = str(utils.pysignature(impl))
508
+ info = {
509
+ "kind": "overload",
510
+ "name": getattr(
511
+ self.key,
512
+ "__name__",
513
+ getattr(impl, "__qualname__", impl.__name__),
514
+ ),
515
+ "sig": sig,
516
+ "filename": utils.safe_relpath(path, start=basepath),
517
+ "lines": (firstlineno, firstlineno + len(code) - 1),
518
+ "docstring": impl.__doc__,
519
+ }
520
+ return info
521
+
522
+
523
+ class ConcreteTemplate(FunctionTemplate):
524
+ """
525
+ Defines attributes "cases" as a list of signature to match against the
526
+ given input types.
527
+ """
528
+
529
+ def apply(self, args, kws):
530
+ cases = getattr(self, "cases")
531
+ return self._select(cases, args, kws)
532
+
533
+ def get_template_info(self):
534
+ import operator
535
+
536
+ name = getattr(self.key, "__name__", "unknown")
537
+ op_func = getattr(operator, name, None)
538
+
539
+ kind = "Type restricted function"
540
+ if op_func is not None:
541
+ if self.key is op_func:
542
+ kind = "operator overload"
543
+ info = {
544
+ "kind": kind,
545
+ "name": name,
546
+ "sig": "unknown",
547
+ "filename": "unknown",
548
+ "lines": ("unknown", "unknown"),
549
+ "docstring": "unknown",
550
+ }
551
+ return info
552
+
553
+
554
+ class _EmptyImplementationEntry(InternalError):
555
+ def __init__(self, reason):
556
+ super(_EmptyImplementationEntry, self).__init__(
557
+ "_EmptyImplementationEntry({!r})".format(reason),
558
+ )
559
+
560
+
561
+ class _OverloadFunctionTemplate(AbstractTemplate):
562
+ """
563
+ A base class of templates for overload functions.
564
+ """
565
+
566
+ def _validate_sigs(self, typing_func, impl_func):
567
+ # check that the impl func and the typing func have the same signature!
568
+ typing_sig = utils.pysignature(typing_func)
569
+ impl_sig = utils.pysignature(impl_func)
570
+ # the typing signature is considered golden and must be adhered to by
571
+ # the implementation...
572
+ # Things that are valid:
573
+ # 1. args match exactly
574
+ # 2. kwargs match exactly in name and default value
575
+ # 3. Use of *args in the same location by the same name in both typing
576
+ # and implementation signature
577
+ # 4. Use of *args in the implementation signature to consume any number
578
+ # of arguments in the typing signature.
579
+ # Things that are invalid:
580
+ # 5. Use of *args in the typing signature that is not replicated
581
+ # in the implementing signature
582
+ # 6. Use of **kwargs
583
+
584
+ def get_args_kwargs(sig):
585
+ kws = []
586
+ args = []
587
+ pos_arg = None
588
+ for x in sig.parameters.values():
589
+ if x.default == utils.pyParameter.empty:
590
+ args.append(x)
591
+ if x.kind == utils.pyParameter.VAR_POSITIONAL:
592
+ pos_arg = x
593
+ elif x.kind == utils.pyParameter.VAR_KEYWORD:
594
+ msg = (
595
+ "The use of VAR_KEYWORD (e.g. **kwargs) is "
596
+ "unsupported. (offending argument name is '%s')"
597
+ )
598
+ raise InternalError(msg % x)
599
+ else:
600
+ kws.append(x)
601
+ return args, kws, pos_arg
602
+
603
+ ty_args, ty_kws, ty_pos = get_args_kwargs(typing_sig)
604
+ im_args, im_kws, im_pos = get_args_kwargs(impl_sig)
605
+
606
+ sig_fmt = "Typing signature: %s\nImplementation signature: %s"
607
+ sig_str = sig_fmt % (typing_sig, impl_sig)
608
+
609
+ err_prefix = "Typing and implementation arguments differ in "
610
+
611
+ a = ty_args
612
+ b = im_args
613
+ if ty_pos:
614
+ if not im_pos:
615
+ # case 5. described above
616
+ msg = (
617
+ "VAR_POSITIONAL (e.g. *args) argument kind (offending "
618
+ "argument name is '%s') found in the typing function "
619
+ "signature, but is not in the implementing function "
620
+ "signature.\n%s"
621
+ ) % (ty_pos, sig_str)
622
+ raise InternalError(msg)
623
+ else:
624
+ if im_pos:
625
+ # no *args in typing but there's a *args in the implementation
626
+ # this is case 4. described above
627
+ b = im_args[: im_args.index(im_pos)]
628
+ try:
629
+ a = ty_args[: ty_args.index(b[-1]) + 1]
630
+ except ValueError:
631
+ # there's no b[-1] arg name in the ty_args, something is
632
+ # very wrong, we can't work out a diff (*args consumes
633
+ # unknown quantity of args) so just report first error
634
+ specialized = "argument names.\n%s\nFirst difference: '%s'"
635
+ msg = err_prefix + specialized % (sig_str, b[-1])
636
+ raise InternalError(msg)
637
+
638
+ def gen_diff(typing, implementing):
639
+ diff = set(typing) ^ set(implementing)
640
+ return "Difference: %s" % diff
641
+
642
+ if a != b:
643
+ specialized = "argument names.\n%s\n%s" % (sig_str, gen_diff(a, b))
644
+ raise InternalError(err_prefix + specialized)
645
+
646
+ # ensure kwargs are the same
647
+ ty = [x.name for x in ty_kws]
648
+ im = [x.name for x in im_kws]
649
+ if ty != im:
650
+ specialized = "keyword argument names.\n%s\n%s"
651
+ msg = err_prefix + specialized % (sig_str, gen_diff(ty_kws, im_kws))
652
+ raise InternalError(msg)
653
+ same = [x.default for x in ty_kws] == [x.default for x in im_kws]
654
+ if not same:
655
+ specialized = "keyword argument default values.\n%s\n%s"
656
+ msg = err_prefix + specialized % (sig_str, gen_diff(ty_kws, im_kws))
657
+ raise InternalError(msg)
658
+
659
+ def generic(self, args, kws):
660
+ """
661
+ Type the overloaded function by compiling the appropriate
662
+ implementation for the given args.
663
+ """
664
+ from numba.cuda.core.typed_passes import PreLowerStripPhis
665
+
666
+ disp, new_args = self._get_impl(args, kws)
667
+ if disp is None:
668
+ return
669
+ # Compile and type it for the given types
670
+ disp_type = types.Dispatcher(disp)
671
+ # Store the compiled overload for use in the lowering phase if there's
672
+ # no inlining required (else functions are being compiled which will
673
+ # never be used as they are inlined)
674
+ if not self._inline.is_never_inline:
675
+ # need to run the compiler front end up to type inference to compute
676
+ # a signature
677
+ from numba.cuda.core import typed_passes
678
+ from numba.cuda.flags import Flags
679
+ from numba.cuda.core.inline_closurecall import InlineWorker
680
+
681
+ fcomp = disp._compiler
682
+ flags = Flags()
683
+
684
+ # Updating these causes problems?!
685
+ # fcomp.targetdescr.options.parse_as_flags(flags,
686
+ # fcomp.targetoptions)
687
+ # flags = fcomp._customize_flags(flags)
688
+
689
+ # spoof a compiler pipline like the one that will be in use
690
+ tyctx = fcomp.targetdescr.typing_context
691
+ tgctx = fcomp.targetdescr.target_context
692
+ compiler_inst = fcomp.pipeline_class(
693
+ tyctx,
694
+ tgctx,
695
+ None,
696
+ None,
697
+ None,
698
+ flags,
699
+ None,
700
+ )
701
+ inline_worker = InlineWorker(
702
+ tyctx,
703
+ tgctx,
704
+ fcomp.locals,
705
+ compiler_inst,
706
+ flags,
707
+ None,
708
+ )
709
+
710
+ # If the inlinee contains something to trigger literal arg dispatch
711
+ # then the pipeline call will unconditionally fail due to a raised
712
+ # ForceLiteralArg exception. Therefore `resolve` is run first, as
713
+ # type resolution must occur at some point, this will hit any
714
+ # `literally` calls and because it's going via the dispatcher will
715
+ # handle them correctly i.e. ForceLiteralArg propagates. This having
716
+ # the desired effect of ensuring the pipeline call is only made in
717
+ # situations that will succeed. For context see #5887.
718
+ resolve = disp_type.dispatcher.get_call_template
719
+ template, pysig, folded_args, kws = resolve(new_args, kws)
720
+ ir = inline_worker.run_untyped_passes(
721
+ disp_type.dispatcher.py_func, enable_ssa=True
722
+ )
723
+
724
+ (typemap, return_type, calltypes, _) = (
725
+ typed_passes.type_inference_stage(
726
+ self.context, tgctx, ir, folded_args, None
727
+ )
728
+ )
729
+ ir = PreLowerStripPhis()._strip_phi_nodes(ir)
730
+ ir._definitions = numba.cuda.core.ir_utils.build_definitions(
731
+ ir.blocks
732
+ )
733
+
734
+ sig = Signature(return_type, folded_args, None)
735
+ # this stores a load of info for the cost model function if supplied
736
+ # it by default is None
737
+ self._inline_overloads[sig.args] = {"folded_args": folded_args}
738
+ # this stores the compiled overloads, if there's no compiled
739
+ # overload available i.e. function is always inlined, the key still
740
+ # needs to exist for type resolution
741
+
742
+ # NOTE: If lowering is failing on a `_EmptyImplementationEntry`,
743
+ # the inliner has failed to inline this entry correctly.
744
+ impl_init = _EmptyImplementationEntry("always inlined")
745
+ self._compiled_overloads[sig.args] = impl_init
746
+ if not self._inline.is_always_inline:
747
+ # this branch is here because a user has supplied a function to
748
+ # determine whether to inline or not. As a result both compiled
749
+ # function and inliner info needed, delaying the computation of
750
+ # this leads to an internal state mess at present. TODO: Fix!
751
+ sig = disp_type.get_call_type(self.context, new_args, kws)
752
+ self._compiled_overloads[sig.args] = disp_type.get_overload(sig)
753
+ # store the inliner information, it's used later in the cost
754
+ # model function call
755
+ iinfo = _inline_info(ir, typemap, calltypes, sig)
756
+ self._inline_overloads[sig.args] = {
757
+ "folded_args": folded_args,
758
+ "iinfo": iinfo,
759
+ }
760
+ else:
761
+ sig = disp_type.get_call_type(self.context, new_args, kws)
762
+ if sig is None: # can't resolve for this target
763
+ return None
764
+ self._compiled_overloads[sig.args] = disp_type.get_overload(sig)
765
+ return sig
766
+
767
+ def _get_impl(self, args, kws):
768
+ """Get implementation given the argument types.
769
+
770
+ Returning a Dispatcher object. The Dispatcher object is cached
771
+ internally in `self._impl_cache`.
772
+ """
773
+ flags = targetconfig.ConfigStack.top_or_none()
774
+ cache_key = self.context, tuple(args), tuple(kws.items()), flags
775
+ try:
776
+ impl, args = self._impl_cache[cache_key]
777
+ return impl, args
778
+ except KeyError:
779
+ # pass and try outside the scope so as to not have KeyError with a
780
+ # nested addition error in the case the _build_impl fails
781
+ pass
782
+ impl, args = self._build_impl(cache_key, args, kws)
783
+ return impl, args
784
+
785
+ def _get_jit_decorator(self):
786
+ """Gets a jit decorator suitable for the current target"""
787
+ from numba.cuda.decorators import jit
788
+
789
+ return jit
790
+
791
+ def _build_impl(self, cache_key, args, kws):
792
+ """Build and cache the implementation.
793
+
794
+ Given the positional (`args`) and keyword arguments (`kws`), obtains
795
+ the `overload` implementation and wrap it in a Dispatcher object.
796
+ The expected argument types are returned for use by type-inference.
797
+ The expected argument types are only different from the given argument
798
+ types if there is an imprecise type in the given argument types.
799
+
800
+ Parameters
801
+ ----------
802
+ cache_key : hashable
803
+ The key used for caching the implementation.
804
+ args : Tuple[Type]
805
+ Types of positional argument.
806
+ kws : Dict[Type]
807
+ Types of keyword argument.
808
+
809
+ Returns
810
+ -------
811
+ disp, args :
812
+ On success, returns `(Dispatcher, Tuple[Type])`.
813
+ On failure, returns `(None, None)`.
814
+
815
+ """
816
+ jitter = self._get_jit_decorator()
817
+
818
+ # Get the overload implementation for the given types
819
+ ov_sig = inspect.signature(self._overload_func)
820
+ try:
821
+ ov_sig.bind(*args, **kws)
822
+ except TypeError as e:
823
+ # bind failed, raise, if there's a
824
+ # ValueError then there's likely unrecoverable
825
+ # problems
826
+ raise TypingError(str(e)) from e
827
+ else:
828
+ ovf_result = self._overload_func(*args, **kws)
829
+
830
+ if ovf_result is None:
831
+ # No implementation => fail typing
832
+ self._impl_cache[cache_key] = None, None
833
+ return None, None
834
+ elif isinstance(ovf_result, tuple):
835
+ # The implementation returned a signature that the type-inferencer
836
+ # should be using.
837
+ sig, pyfunc = ovf_result
838
+ args = sig.args
839
+ kws = {}
840
+ cache_key = None # don't cache
841
+ else:
842
+ # Regular case
843
+ pyfunc = ovf_result
844
+
845
+ # Check type of pyfunc
846
+ if not isinstance(pyfunc, FunctionType):
847
+ msg = (
848
+ "Implementation function returned by `@overload` "
849
+ "has an unexpected type. Got {}"
850
+ )
851
+ raise AssertionError(msg.format(pyfunc))
852
+
853
+ # check that the typing and impl sigs match up
854
+ if self._strict:
855
+ self._validate_sigs(self._overload_func, pyfunc)
856
+ # Make dispatcher
857
+ jitdecor = jitter(**self._jit_options)
858
+ disp = jitdecor(pyfunc)
859
+ # Make sure that the implementation can be fully compiled
860
+ disp_type = types.Dispatcher(disp)
861
+ disp_type.get_call_type(self.context, args, kws)
862
+ if cache_key is not None:
863
+ self._impl_cache[cache_key] = disp, args
864
+ return disp, args
865
+
866
+ def get_impl_key(self, sig):
867
+ """
868
+ Return the key for looking up the implementation for the given
869
+ signature on the target context.
870
+ """
871
+ return self._compiled_overloads[sig.args]
872
+
873
+ @classmethod
874
+ def get_source_info(cls):
875
+ """Return a dictionary with information about the source code of the
876
+ implementation.
877
+
878
+ Returns
879
+ -------
880
+ info : dict
881
+ - "kind" : str
882
+ The implementation kind.
883
+ - "name" : str
884
+ The name of the function that provided the definition.
885
+ - "sig" : str
886
+ The formatted signature of the function.
887
+ - "filename" : str
888
+ The name of the source file.
889
+ - "lines": tuple (int, int)
890
+ First and list line number.
891
+ - "docstring": str
892
+ The docstring of the definition.
893
+ """
894
+ basepath = os.path.dirname(
895
+ os.path.dirname(os.path.dirname(numba.cuda.__file__))
896
+ )
897
+ impl = cls._overload_func
898
+ code, firstlineno, path = cls.get_source_code_info(impl)
899
+ sig = str(utils.pysignature(impl))
900
+ info = {
901
+ "kind": "overload",
902
+ "name": getattr(impl, "__qualname__", impl.__name__),
903
+ "sig": sig,
904
+ "filename": utils.safe_relpath(path, start=basepath),
905
+ "lines": (firstlineno, firstlineno + len(code) - 1),
906
+ "docstring": impl.__doc__,
907
+ }
908
+ return info
909
+
910
+ def get_template_info(self):
911
+ basepath = os.path.dirname(
912
+ os.path.dirname(os.path.dirname(numba.cuda.__file__))
913
+ )
914
+ impl = self._overload_func
915
+ code, firstlineno, path = self.get_source_code_info(impl)
916
+ sig = str(utils.pysignature(impl))
917
+ info = {
918
+ "kind": "overload",
919
+ "name": getattr(impl, "__qualname__", impl.__name__),
920
+ "sig": sig,
921
+ "filename": utils.safe_relpath(path, start=basepath),
922
+ "lines": (firstlineno, firstlineno + len(code) - 1),
923
+ "docstring": impl.__doc__,
924
+ }
925
+ return info
926
+
927
+
928
+ def make_overload_template(
929
+ func,
930
+ overload_func,
931
+ jit_options,
932
+ strict,
933
+ inline,
934
+ prefer_literal=False,
935
+ **kwargs,
936
+ ):
937
+ """
938
+ Make a template class for function *func* overloaded by *overload_func*.
939
+ Compiler options are passed as a dictionary to *jit_options*.
940
+ """
941
+ func_name = getattr(func, "__name__", str(func))
942
+ name = "OverloadTemplate_%s" % (func_name,)
943
+ base = _OverloadFunctionTemplate
944
+ dct = dict(
945
+ key=func,
946
+ _overload_func=staticmethod(overload_func),
947
+ _impl_cache={},
948
+ _compiled_overloads={},
949
+ _jit_options=jit_options,
950
+ _strict=strict,
951
+ _inline=staticmethod(InlineOptions(inline)),
952
+ _inline_overloads={},
953
+ prefer_literal=prefer_literal,
954
+ metadata=kwargs,
955
+ )
956
+ return type(base)(name, (base,), dct)
957
+
958
+
959
+ class _TemplateTargetHelperMixin(object):
960
+ """Mixin for helper methods that assist with target/registry resolution"""
961
+
962
+ def _get_target_registry(self, reason):
963
+ """Returns the registry for the current target.
964
+
965
+ Parameters
966
+ ----------
967
+ reason: str
968
+ Reason for the resolution. Expects a noun.
969
+ Returns
970
+ -------
971
+ reg : a registry suitable for the current target.
972
+ """
973
+ from numba.cuda.descriptor import cuda_target
974
+
975
+ tgtctx = cuda_target.target_context
976
+
977
+ # ---------------------------------------------------------------------
978
+ # XXX: In upstream Numba, this function would prefer the builtin
979
+ # registry if it was installed in the target (as it is for the CUDA
980
+ # target). The builtin registry has been removed from this file (it was
981
+ # initialized as `builtin_registry = Registry()`) as it would duplicate
982
+ # the builtin registry in upstream Numba, which would be likely to lead
983
+ # to confusion / mixing things up between two builtin registries. The
984
+ # comment that accompanied this behaviour is left here, even though the
985
+ # code that would pick the builtin registry has been removed, for the
986
+ # benefit of future understanding.
987
+ #
988
+ # ---------------------------------------------------------------------
989
+ #
990
+ # Comment left in from upstream:
991
+ #
992
+ # This is all workarounds...
993
+ # The issue is that whilst targets shouldn't care about which registry
994
+ # in which to register lowering implementations, the CUDA target
995
+ # "borrows" implementations from the CPU from specific registries. This
996
+ # means that if some impl is defined via @intrinsic, e.g. numba.*unsafe
997
+ # modules, _AND_ CUDA also makes use of the same impl, then it's
998
+ # required that the registry in use is one that CUDA borrows from. This
999
+ # leads to the following expression where by the CPU builtin_registry is
1000
+ # used if it is in the target context as a known registry (i.e. the
1001
+ # target installed it) and if it is not then it is assumed that the
1002
+ # registries for the target are unbound to any other target and so it's
1003
+ # fine to use any of them as a place to put lowering impls.
1004
+ #
1005
+ # NOTE: This will need subsequently fixing again when targets use solely
1006
+ # the extension APIs to describe their implementation. The issue will be
1007
+ # that the builtin_registry should contain _just_ the stack allocated
1008
+ # implementations and low level target invariant things and should not
1009
+ # be modified further. It should be acceptable to remove the `then`
1010
+ # branch and just keep the `else`.
1011
+ # =====================================================================
1012
+
1013
+ # =====================================================================
1014
+ # XXX: This ought not to be necessary in the long term, but is left in
1015
+ # for now. When there are fewer registries (or just one) for a target,
1016
+ # it may be safe to remove this. Or, it may always require a refresh in
1017
+ # case there are pending registrations - this remains to be seen
1018
+ # ---------------------------------------------------------------------
1019
+ #
1020
+ # Comment / code left in from upstream:
1021
+ #
1022
+ # In case the target has swapped, e.g. cuda borrowing cpu, refresh to
1023
+ # populate.
1024
+ tgtctx.refresh()
1025
+ # =====================================================================
1026
+
1027
+ # Pick a registry in which to install intrinsics
1028
+ registries = iter(tgtctx._registries)
1029
+ reg = next(registries)
1030
+ return reg
1031
+
1032
+
1033
+ class _IntrinsicTemplate(_TemplateTargetHelperMixin, AbstractTemplate):
1034
+ """
1035
+ A base class of templates for intrinsic definition
1036
+ """
1037
+
1038
+ def generic(self, args, kws):
1039
+ """
1040
+ Type the intrinsic by the arguments.
1041
+ """
1042
+ lower_builtin = self._get_target_registry("intrinsic").lower
1043
+ cache_key = self.context, args, tuple(kws.items())
1044
+ try:
1045
+ return self._impl_cache[cache_key]
1046
+ except KeyError:
1047
+ pass
1048
+ result = self._definition_func(self.context, *args, **kws)
1049
+ if result is None:
1050
+ return
1051
+ [sig, imp] = result
1052
+ pysig = utils.pysignature(self._definition_func)
1053
+ # omit context argument from user function
1054
+ parameters = list(pysig.parameters.values())[1:]
1055
+ sig = sig.replace(pysig=pysig.replace(parameters=parameters))
1056
+ self._impl_cache[cache_key] = sig
1057
+ self._overload_cache[sig.args] = imp
1058
+ # register the lowering
1059
+ lower_builtin(imp, *sig.args)(imp)
1060
+ return sig
1061
+
1062
+ def get_impl_key(self, sig):
1063
+ """
1064
+ Return the key for looking up the implementation for the given
1065
+ signature on the target context.
1066
+ """
1067
+ return self._overload_cache[sig.args]
1068
+
1069
+ def get_template_info(self):
1070
+ basepath = os.path.dirname(
1071
+ os.path.dirname(os.path.dirname(numba.cuda.__file__))
1072
+ )
1073
+ impl = self._definition_func
1074
+ code, firstlineno, path = self.get_source_code_info(impl)
1075
+ sig = str(utils.pysignature(impl))
1076
+ info = {
1077
+ "kind": "intrinsic",
1078
+ "name": getattr(impl, "__qualname__", impl.__name__),
1079
+ "sig": sig,
1080
+ "filename": utils.safe_relpath(path, start=basepath),
1081
+ "lines": (firstlineno, firstlineno + len(code) - 1),
1082
+ "docstring": impl.__doc__,
1083
+ }
1084
+ return info
1085
+
1086
+
1087
+ def make_intrinsic_template(
1088
+ handle, defn, name, *, prefer_literal=False, kwargs=None
1089
+ ):
1090
+ """
1091
+ Make a template class for a intrinsic handle *handle* defined by the
1092
+ function *defn*. The *name* is used for naming the new template class.
1093
+ """
1094
+ kwargs = MappingProxyType({} if kwargs is None else kwargs)
1095
+ base = _IntrinsicTemplate
1096
+ name = "_IntrinsicTemplate_%s" % (name)
1097
+ dct = dict(
1098
+ key=handle,
1099
+ _definition_func=staticmethod(defn),
1100
+ _impl_cache={},
1101
+ _overload_cache={},
1102
+ prefer_literal=prefer_literal,
1103
+ metadata=kwargs,
1104
+ )
1105
+ return type(base)(name, (base,), dct)
1106
+
1107
+
1108
+ class AttributeTemplate(object):
1109
+ def __init__(self, context):
1110
+ self.context = context
1111
+
1112
+ def resolve(self, value, attr):
1113
+ return self._resolve(value, attr)
1114
+
1115
+ def _resolve(self, value, attr):
1116
+ fn = getattr(self, "resolve_%s" % attr, None)
1117
+ if fn is None:
1118
+ fn = self.generic_resolve
1119
+ if fn is NotImplemented:
1120
+ if isinstance(value, types.Module):
1121
+ return self.context.resolve_module_constants(value, attr)
1122
+ else:
1123
+ return None
1124
+ else:
1125
+ return fn(value, attr)
1126
+ else:
1127
+ return fn(value)
1128
+
1129
+ generic_resolve = NotImplemented
1130
+
1131
+
1132
+ class _OverloadAttributeTemplate(_TemplateTargetHelperMixin, AttributeTemplate):
1133
+ """
1134
+ A base class of templates for @overload_attribute functions.
1135
+ """
1136
+
1137
+ is_method = False
1138
+
1139
+ def __init__(self, context):
1140
+ super(_OverloadAttributeTemplate, self).__init__(context)
1141
+ self.context = context
1142
+ self._init_once()
1143
+
1144
+ def _init_once(self):
1145
+ cls = type(self)
1146
+ attr = cls._attr
1147
+
1148
+ lower_getattr = self._get_target_registry("attribute").lower_getattr
1149
+
1150
+ @lower_getattr(cls.key, attr)
1151
+ def getattr_impl(context, builder, typ, value):
1152
+ typingctx = context.typing_context
1153
+ fnty = cls._get_function_type(typingctx, typ)
1154
+ sig = cls._get_signature(typingctx, fnty, (typ,), {})
1155
+ call = context.get_function(fnty, sig)
1156
+ return call(builder, (value,))
1157
+
1158
+ def _resolve(self, typ, attr):
1159
+ if self._attr != attr:
1160
+ return None
1161
+ fnty = self._get_function_type(self.context, typ)
1162
+ sig = self._get_signature(self.context, fnty, (typ,), {})
1163
+ # There should only be one template
1164
+ for template in fnty.templates:
1165
+ self._inline_overloads.update(template._inline_overloads)
1166
+ return sig.return_type
1167
+
1168
+ @classmethod
1169
+ def _get_signature(cls, typingctx, fnty, args, kws):
1170
+ sig = fnty.get_call_type(typingctx, args, kws)
1171
+ sig = sig.replace(pysig=utils.pysignature(cls._overload_func))
1172
+ return sig
1173
+
1174
+ @classmethod
1175
+ def _get_function_type(cls, typingctx, typ):
1176
+ return typingctx.resolve_value_type(cls._overload_func)
1177
+
1178
+
1179
+ class _OverloadMethodTemplate(_OverloadAttributeTemplate):
1180
+ """
1181
+ A base class of templates for @overload_method functions.
1182
+ """
1183
+
1184
+ is_method = True
1185
+
1186
+ def _init_once(self):
1187
+ """
1188
+ Overriding parent definition
1189
+ """
1190
+ attr = self._attr
1191
+
1192
+ registry = self._get_target_registry("method")
1193
+
1194
+ @registry.lower((self.key, attr), self.key, types.VarArg(types.Any))
1195
+ def method_impl(context, builder, sig, args):
1196
+ typ = sig.args[0]
1197
+ typing_context = context.typing_context
1198
+ fnty = self._get_function_type(typing_context, typ)
1199
+ sig = self._get_signature(typing_context, fnty, sig.args, {})
1200
+ call = context.get_function(fnty, sig)
1201
+ # Link dependent library
1202
+ context.add_linking_libs(getattr(call, "libs", ()))
1203
+ return call(builder, args)
1204
+
1205
+ def _resolve(self, typ, attr):
1206
+ if self._attr != attr:
1207
+ return None
1208
+
1209
+ if isinstance(typ, types.TypeRef):
1210
+ assert typ == self.key
1211
+ elif isinstance(typ, types.Callable):
1212
+ assert typ == self.key
1213
+ else:
1214
+ assert isinstance(typ, self.key)
1215
+
1216
+ class MethodTemplate(AbstractTemplate):
1217
+ key = (self.key, attr)
1218
+ _inline = self._inline
1219
+ _overload_func = staticmethod(self._overload_func)
1220
+ _inline_overloads = self._inline_overloads
1221
+ prefer_literal = self.prefer_literal
1222
+
1223
+ def generic(_, args, kws):
1224
+ args = (typ,) + tuple(args)
1225
+ fnty = self._get_function_type(self.context, typ)
1226
+ sig = self._get_signature(self.context, fnty, args, kws)
1227
+ sig = sig.replace(pysig=utils.pysignature(self._overload_func))
1228
+ for template in fnty.templates:
1229
+ self._inline_overloads.update(template._inline_overloads)
1230
+ if sig is not None:
1231
+ return sig.as_method()
1232
+
1233
+ def get_template_info(self):
1234
+ basepath = os.path.dirname(
1235
+ os.path.dirname(os.path.dirname(numba.cuda.__file__))
1236
+ )
1237
+ impl = self._overload_func
1238
+ code, firstlineno, path = self.get_source_code_info(impl)
1239
+ sig = str(utils.pysignature(impl))
1240
+ info = {
1241
+ "kind": "overload_method",
1242
+ "name": getattr(impl, "__qualname__", impl.__name__),
1243
+ "sig": sig,
1244
+ "filename": utils.safe_relpath(path, start=basepath),
1245
+ "lines": (firstlineno, firstlineno + len(code) - 1),
1246
+ "docstring": impl.__doc__,
1247
+ }
1248
+
1249
+ return info
1250
+
1251
+ return types.BoundFunction(MethodTemplate, typ)
1252
+
1253
+
1254
+ def make_overload_attribute_template(
1255
+ typ,
1256
+ attr,
1257
+ overload_func,
1258
+ inline="never",
1259
+ prefer_literal=False,
1260
+ base=_OverloadAttributeTemplate,
1261
+ **kwargs,
1262
+ ):
1263
+ """
1264
+ Make a template class for attribute *attr* of *typ* overloaded by
1265
+ *overload_func*.
1266
+ """
1267
+ assert isinstance(typ, types.Type) or issubclass(typ, types.Type)
1268
+ name = "OverloadAttributeTemplate_%s_%s" % (typ, attr)
1269
+ # Note the implementation cache is subclass-specific
1270
+ dct = dict(
1271
+ key=typ,
1272
+ _attr=attr,
1273
+ _impl_cache={},
1274
+ _inline=staticmethod(InlineOptions(inline)),
1275
+ _inline_overloads={},
1276
+ _overload_func=staticmethod(overload_func),
1277
+ prefer_literal=prefer_literal,
1278
+ metadata=kwargs,
1279
+ )
1280
+ obj = type(base)(name, (base,), dct)
1281
+ return obj
1282
+
1283
+
1284
+ def make_overload_method_template(
1285
+ typ, attr, overload_func, inline, prefer_literal=False, **kwargs
1286
+ ):
1287
+ """
1288
+ Make a template class for method *attr* of *typ* overloaded by
1289
+ *overload_func*.
1290
+ """
1291
+ return make_overload_attribute_template(
1292
+ typ,
1293
+ attr,
1294
+ overload_func,
1295
+ inline=inline,
1296
+ base=_OverloadMethodTemplate,
1297
+ prefer_literal=prefer_literal,
1298
+ **kwargs,
1299
+ )
1300
+
1301
+
1302
+ def bound_function(template_key):
1303
+ """
1304
+ Wrap an AttributeTemplate resolve_* method to allow it to
1305
+ resolve an instance method's signature rather than a instance attribute.
1306
+ The wrapped method must return the resolved method's signature
1307
+ according to the given self type, args, and keywords.
1308
+
1309
+ It is used thusly:
1310
+
1311
+ class ComplexAttributes(AttributeTemplate):
1312
+ @bound_function("complex.conjugate")
1313
+ def resolve_conjugate(self, ty, args, kwds):
1314
+ return ty
1315
+
1316
+ *template_key* (e.g. "complex.conjugate" above) will be used by the
1317
+ target to look up the method's implementation, as a regular function.
1318
+ """
1319
+
1320
+ def wrapper(method_resolver):
1321
+ @functools.wraps(method_resolver)
1322
+ def attribute_resolver(self, ty):
1323
+ class MethodTemplate(AbstractTemplate):
1324
+ key = template_key
1325
+
1326
+ def generic(_, args, kws):
1327
+ sig = method_resolver(self, ty, args, kws)
1328
+ if sig is not None and sig.recvr is None:
1329
+ sig = sig.replace(recvr=ty)
1330
+ return sig
1331
+
1332
+ return types.BoundFunction(MethodTemplate, ty)
1333
+
1334
+ return attribute_resolver
1335
+
1336
+ return wrapper
1337
+
1338
+
1339
+ # -----------------------------
1340
+
1341
+
1342
+ class Registry(object):
1343
+ """
1344
+ A registry of typing declarations. The registry stores such declarations
1345
+ for functions, attributes and globals.
1346
+ """
1347
+
1348
+ def __init__(self):
1349
+ self.functions = []
1350
+ self.attributes = []
1351
+ self.globals = []
1352
+
1353
+ def register(self, item):
1354
+ self.functions.append(item)
1355
+ return item
1356
+
1357
+ def register_attr(self, item):
1358
+ self.attributes.append(item)
1359
+ return item
1360
+
1361
+ def register_global(self, val=None, typ=None, **kwargs):
1362
+ """
1363
+ Register the typing of a global value.
1364
+ Functional usage with a Numba type::
1365
+ register_global(value, typ)
1366
+
1367
+ Decorator usage with a template class::
1368
+ @register_global(value, typing_key=None)
1369
+ class Template: ...
1370
+ """
1371
+ if typ is not None:
1372
+ # register_global(val, typ)
1373
+ assert val is not None
1374
+ assert not kwargs
1375
+ self.globals.append((val, typ))
1376
+ else:
1377
+
1378
+ def decorate(cls, typing_key):
1379
+ class Template(cls):
1380
+ key = typing_key
1381
+
1382
+ if callable(val):
1383
+ typ = types.Function(Template)
1384
+ else:
1385
+ raise TypeError("cannot infer type for global value %r")
1386
+ self.globals.append((val, typ))
1387
+ return cls
1388
+
1389
+ # register_global(val, typing_key=None)(<template class>)
1390
+ assert val is not None
1391
+ typing_key = kwargs.pop("typing_key", val)
1392
+ assert not kwargs
1393
+ if typing_key is val:
1394
+ # Check the value is globally reachable, as it is going
1395
+ # to be used as the key.
1396
+ mod = sys.modules[val.__module__]
1397
+ if getattr(mod, val.__name__) is not val:
1398
+ raise ValueError(
1399
+ "%r is not globally reachable as '%s.%s'"
1400
+ % (mod, val.__module__, val.__name__)
1401
+ )
1402
+
1403
+ def decorator(cls):
1404
+ return decorate(cls, typing_key)
1405
+
1406
+ return decorator
1407
+
1408
+
1409
+ class BaseRegistryLoader(object):
1410
+ """
1411
+ An incremental loader for a registry. Each new call to
1412
+ new_registrations() will iterate over the not yet seen registrations.
1413
+
1414
+ The reason for this object is multiple:
1415
+ - there can be several contexts
1416
+ - each context wants to install all registrations
1417
+ - registrations can be added after the first installation, so contexts
1418
+ must be able to get the "new" installations
1419
+
1420
+ Therefore each context maintains its own loaders for each existing
1421
+ registry, without duplicating the registries themselves.
1422
+ """
1423
+
1424
+ def __init__(self, registry):
1425
+ self._registrations = dict(
1426
+ (name, utils.stream_list(getattr(registry, name)))
1427
+ for name in self.registry_items
1428
+ )
1429
+
1430
+ def new_registrations(self, name):
1431
+ for item in next(self._registrations[name]):
1432
+ yield item
1433
+
1434
+
1435
+ class RegistryLoader(BaseRegistryLoader):
1436
+ """
1437
+ An incremental loader for a typing registry.
1438
+ """
1439
+
1440
+ registry_items = ("functions", "attributes", "globals")
1441
+
1442
+
1443
+ builtin_registry = Registry()
1444
+ infer = builtin_registry.register
1445
+ infer_getattr = builtin_registry.register_attr
1446
+ infer_global = builtin_registry.register_global