dub 0.2.2 → 1.0.0

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 dub might be problematic. Click here for more details.

Files changed (277) hide show
  1. data/History.txt +92 -0
  2. data/LICENSE +20 -0
  3. data/README.rdoc +115 -0
  4. data/Rakefile +59 -0
  5. data/dub.gemspec +197 -0
  6. data/lib/dub/argument.rb +286 -0
  7. data/lib/dub/entities_unescape.rb +9 -0
  8. data/lib/dub/function.rb +177 -0
  9. data/lib/dub/function_group.rb +72 -0
  10. data/lib/dub/generator.rb +15 -0
  11. data/lib/dub/group.rb +20 -0
  12. data/lib/dub/klass.rb +338 -0
  13. data/lib/dub/lua/class.cpp.erb +114 -0
  14. data/lib/dub/lua/class_gen.rb +96 -0
  15. data/lib/dub/lua/function.cpp.erb +15 -0
  16. data/lib/dub/lua/function_gen.rb +329 -0
  17. data/lib/dub/lua/group.cpp.erb +9 -0
  18. data/lib/dub/lua/lua_cpp_helper.cpp +259 -0
  19. data/lib/dub/lua/lua_cpp_helper.h +219 -0
  20. data/lib/dub/lua/lua_object.cpp +158 -0
  21. data/lib/dub/lua/lua_object.h +69 -0
  22. data/lib/dub/lua/namespace.cpp.erb +42 -0
  23. data/lib/dub/lua/namespace_gen.rb +69 -0
  24. data/lib/dub/lua.rb +24 -0
  25. data/lib/dub/member_extraction.rb +128 -0
  26. data/lib/dub/namespace.rb +295 -0
  27. data/lib/dub/opts_parser.rb +30 -0
  28. data/lib/dub/parser.rb +46 -0
  29. data/lib/dub/templates/lua_template.erb +21 -0
  30. data/lib/dub/version.rb +3 -0
  31. data/lib/dub.rb +24 -20
  32. data/test/argument_test.rb +581 -0
  33. data/test/fixtures/app/CMakeLists.txt +54 -0
  34. data/test/fixtures/app/Doxyfile +1600 -0
  35. data/test/fixtures/app/bindings/all_lua.cpp +299 -0
  36. data/test/fixtures/app/include/matrix.h +283 -0
  37. data/test/fixtures/app/make_lua_bindings.rb +13 -0
  38. data/test/fixtures/app/vendor/lua/CMakeLists.txt +25 -0
  39. data/test/fixtures/app/vendor/lua/COPYRIGHT +34 -0
  40. data/test/fixtures/app/vendor/lua/HISTORY +183 -0
  41. data/test/fixtures/app/vendor/lua/INSTALL +99 -0
  42. data/test/fixtures/app/vendor/lua/Makefile +183 -0
  43. data/test/fixtures/app/vendor/lua/README +37 -0
  44. data/test/fixtures/app/vendor/lua/lapi.c +1080 -0
  45. data/test/fixtures/app/vendor/lua/lapi.h +16 -0
  46. data/test/fixtures/app/vendor/lua/lauxlib.c +653 -0
  47. data/test/fixtures/app/vendor/lua/lauxlib.h +174 -0
  48. data/test/fixtures/app/vendor/lua/lbaselib.c +643 -0
  49. data/test/fixtures/app/vendor/lua/lcode.c +839 -0
  50. data/test/fixtures/app/vendor/lua/lcode.h +76 -0
  51. data/test/fixtures/app/vendor/lua/ldblib.c +397 -0
  52. data/test/fixtures/app/vendor/lua/ldebug.c +622 -0
  53. data/test/fixtures/app/vendor/lua/ldebug.h +33 -0
  54. data/test/fixtures/app/vendor/lua/ldo.c +516 -0
  55. data/test/fixtures/app/vendor/lua/ldo.h +57 -0
  56. data/test/fixtures/app/vendor/lua/ldump.c +164 -0
  57. data/test/fixtures/app/vendor/lua/lfunc.c +174 -0
  58. data/test/fixtures/app/vendor/lua/lfunc.h +34 -0
  59. data/test/fixtures/app/vendor/lua/lgc.c +711 -0
  60. data/test/fixtures/app/vendor/lua/lgc.h +110 -0
  61. data/test/fixtures/app/vendor/lua/liblua.a +0 -0
  62. data/test/fixtures/app/vendor/lua/linit.c +38 -0
  63. data/test/fixtures/app/vendor/lua/liolib.c +532 -0
  64. data/test/fixtures/app/vendor/lua/llex.c +461 -0
  65. data/test/fixtures/app/vendor/lua/llex.h +81 -0
  66. data/test/fixtures/app/vendor/lua/llimits.h +128 -0
  67. data/test/fixtures/app/vendor/lua/lmathlib.c +263 -0
  68. data/test/fixtures/app/vendor/lua/lmem.c +86 -0
  69. data/test/fixtures/app/vendor/lua/lmem.h +49 -0
  70. data/test/fixtures/app/vendor/lua/loadlib.c +664 -0
  71. data/test/fixtures/app/vendor/lua/lobject.c +214 -0
  72. data/test/fixtures/app/vendor/lua/lobject.h +381 -0
  73. data/test/fixtures/app/vendor/lua/lopcodes.c +102 -0
  74. data/test/fixtures/app/vendor/lua/lopcodes.h +268 -0
  75. data/test/fixtures/app/vendor/lua/loslib.c +244 -0
  76. data/test/fixtures/app/vendor/lua/lparser.c +1337 -0
  77. data/test/fixtures/app/vendor/lua/lparser.h +82 -0
  78. data/test/fixtures/app/vendor/lua/lstate.c +214 -0
  79. data/test/fixtures/app/vendor/lua/lstate.h +168 -0
  80. data/test/fixtures/app/vendor/lua/lstring.c +111 -0
  81. data/test/fixtures/app/vendor/lua/lstring.h +31 -0
  82. data/test/fixtures/app/vendor/lua/lstrlib.c +868 -0
  83. data/test/fixtures/app/vendor/lua/ltable.c +588 -0
  84. data/test/fixtures/app/vendor/lua/ltable.h +40 -0
  85. data/test/fixtures/app/vendor/lua/ltablib.c +278 -0
  86. data/test/fixtures/app/vendor/lua/ltm.c +75 -0
  87. data/test/fixtures/app/vendor/lua/ltm.h +54 -0
  88. data/test/fixtures/app/vendor/lua/lua.c +695 -0
  89. data/test/fixtures/app/vendor/lua/lua.h +385 -0
  90. data/test/fixtures/app/vendor/lua/lua_dub_helper.h +77 -0
  91. data/test/fixtures/app/vendor/lua/luac +0 -0
  92. data/test/fixtures/app/vendor/lua/luac.c +200 -0
  93. data/test/fixtures/app/vendor/lua/luaconf.h +762 -0
  94. data/test/fixtures/app/vendor/lua/lualib.h +53 -0
  95. data/test/fixtures/app/vendor/lua/lundump.c +223 -0
  96. data/test/fixtures/app/vendor/lua/lundump.h +36 -0
  97. data/test/fixtures/app/vendor/lua/lvm.c +765 -0
  98. data/test/fixtures/app/vendor/lua/lvm.h +36 -0
  99. data/test/fixtures/app/vendor/lua/lzio.c +82 -0
  100. data/test/fixtures/app/vendor/lua/lzio.h +67 -0
  101. data/test/fixtures/app/vendor/lua/matrix.h +102 -0
  102. data/test/fixtures/app/vendor/lua/print.c +227 -0
  103. data/test/fixtures/app/vendor/lua/test/README +26 -0
  104. data/test/fixtures/app/vendor/lua/test/bisect.lua +27 -0
  105. data/test/fixtures/app/vendor/lua/test/cf.lua +16 -0
  106. data/test/fixtures/app/vendor/lua/test/echo.lua +5 -0
  107. data/test/fixtures/app/vendor/lua/test/env.lua +7 -0
  108. data/test/fixtures/app/vendor/lua/test/factorial.lua +32 -0
  109. data/test/fixtures/app/vendor/lua/test/fib.lua +40 -0
  110. data/test/fixtures/app/vendor/lua/test/fibfor.lua +13 -0
  111. data/test/fixtures/app/vendor/lua/test/globals.lua +13 -0
  112. data/test/fixtures/app/vendor/lua/test/hello.lua +3 -0
  113. data/test/fixtures/app/vendor/lua/test/life.lua +111 -0
  114. data/test/fixtures/app/vendor/lua/test/luac.lua +7 -0
  115. data/test/fixtures/app/vendor/lua/test/printf.lua +7 -0
  116. data/test/fixtures/app/vendor/lua/test/readonly.lua +12 -0
  117. data/test/fixtures/app/vendor/lua/test/sieve.lua +29 -0
  118. data/test/fixtures/app/vendor/lua/test/sort.lua +66 -0
  119. data/test/fixtures/app/vendor/lua/test/table.lua +12 -0
  120. data/test/fixtures/app/vendor/lua/test/trace-calls.lua +32 -0
  121. data/test/fixtures/app/vendor/lua/test/trace-globals.lua +38 -0
  122. data/test/fixtures/app/vendor/lua/test/xd.lua +14 -0
  123. data/test/fixtures/app/xml/classdub_1_1_base.xml +85 -0
  124. data/test/fixtures/app/xml/classdub_1_1_custom_destructor.xml +67 -0
  125. data/test/fixtures/app/xml/classdub_1_1_deletable_out_of_lua.xml +43 -0
  126. data/test/fixtures/app/xml/classdub_1_1_matrix.xml +482 -0
  127. data/test/fixtures/app/xml/classdub_1_1_no_destructor.xml +49 -0
  128. data/test/fixtures/app/xml/classdub_1_1_priv_sub_base.xml +89 -0
  129. data/test/fixtures/app/xml/classdub_1_1_private_constr.xml +68 -0
  130. data/test/fixtures/app/xml/classdub_1_1_static_constr.xml +69 -0
  131. data/test/fixtures/app/xml/classdub_1_1_sub_base.xml +89 -0
  132. data/test/fixtures/app/xml/classdub_1_1_t_mat.xml +252 -0
  133. data/test/fixtures/app/xml/combine.xslt +15 -0
  134. data/test/fixtures/app/xml/compound.xsd +814 -0
  135. data/test/fixtures/app/xml/dir_53661a2bdeb1d55e60581a7e15deb763.xml +12 -0
  136. data/test/fixtures/app/xml/index.xml +91 -0
  137. data/test/fixtures/app/xml/index.xsd +66 -0
  138. data/test/fixtures/app/xml/matrix_8h.xml +310 -0
  139. data/test/fixtures/app/xml/namespacedub.xml +48 -0
  140. data/test/fixtures/classcv_1_1_mat.xml +1996 -0
  141. data/test/fixtures/classcv_1_1_point__.xml +341 -0
  142. data/test/fixtures/classcv_1_1_scalar__.xml +269 -0
  143. data/test/fixtures/classcv_1_1_size__.xml +270 -0
  144. data/test/fixtures/dummy_class.cpp.erb +1 -0
  145. data/test/fixtures/dummy_function.cpp.erb +1 -0
  146. data/test/fixtures/group___magic_type.xml +406 -0
  147. data/test/fixtures/namespacecv.xml +12659 -0
  148. data/test/function_group_test.rb +43 -0
  149. data/test/function_test.rb +405 -0
  150. data/test/group_test.rb +241 -0
  151. data/test/helper.rb +34 -0
  152. data/test/klass_test.rb +551 -0
  153. data/test/lua_function_gen_test.rb +242 -0
  154. data/test/namespace_test.rb +220 -0
  155. data/test/parser_test.rb +36 -0
  156. metadata +229 -272
  157. checksums.yaml +0 -7
  158. data/lib/open_api_sdk/analytics.rb +0 -99
  159. data/lib/open_api_sdk/domains.rb +0 -353
  160. data/lib/open_api_sdk/dub.rb +0 -88
  161. data/lib/open_api_sdk/links.rb +0 -766
  162. data/lib/open_api_sdk/metatags.rb +0 -54
  163. data/lib/open_api_sdk/models/operations/bulkcreatelinks_response.rb +0 -60
  164. data/lib/open_api_sdk/models/operations/bulkupdatelinks_requestbody.rb +0 -27
  165. data/lib/open_api_sdk/models/operations/bulkupdatelinks_response.rb +0 -60
  166. data/lib/open_api_sdk/models/operations/color.rb +0 -24
  167. data/lib/open_api_sdk/models/operations/createdomain_requestbody.rb +0 -33
  168. data/lib/open_api_sdk/models/operations/createdomain_response.rb +0 -60
  169. data/lib/open_api_sdk/models/operations/createlink_requestbody.rb +0 -95
  170. data/lib/open_api_sdk/models/operations/createlink_response.rb +0 -60
  171. data/lib/open_api_sdk/models/operations/createtag_requestbody.rb +0 -32
  172. data/lib/open_api_sdk/models/operations/createtag_response.rb +0 -60
  173. data/lib/open_api_sdk/models/operations/data.rb +0 -83
  174. data/lib/open_api_sdk/models/operations/deletedomain_request.rb +0 -24
  175. data/lib/open_api_sdk/models/operations/deletedomain_response.rb +0 -60
  176. data/lib/open_api_sdk/models/operations/deletedomain_responsebody.rb +0 -24
  177. data/lib/open_api_sdk/models/operations/deletelink_request.rb +0 -24
  178. data/lib/open_api_sdk/models/operations/deletelink_response.rb +0 -60
  179. data/lib/open_api_sdk/models/operations/deletelink_responsebody.rb +0 -24
  180. data/lib/open_api_sdk/models/operations/event.rb +0 -21
  181. data/lib/open_api_sdk/models/operations/getlinkinfo_request.rb +0 -33
  182. data/lib/open_api_sdk/models/operations/getlinkinfo_response.rb +0 -60
  183. data/lib/open_api_sdk/models/operations/getlinks_request.rb +0 -51
  184. data/lib/open_api_sdk/models/operations/getlinks_response.rb +0 -60
  185. data/lib/open_api_sdk/models/operations/getlinkscount_request.rb +0 -48
  186. data/lib/open_api_sdk/models/operations/getlinkscount_response.rb +0 -60
  187. data/lib/open_api_sdk/models/operations/getmetatags_request.rb +0 -24
  188. data/lib/open_api_sdk/models/operations/getmetatags_response.rb +0 -33
  189. data/lib/open_api_sdk/models/operations/getmetatags_responsebody.rb +0 -30
  190. data/lib/open_api_sdk/models/operations/getqrcode_request.rb +0 -39
  191. data/lib/open_api_sdk/models/operations/getqrcode_response.rb +0 -60
  192. data/lib/open_api_sdk/models/operations/gettags_response.rb +0 -60
  193. data/lib/open_api_sdk/models/operations/getworkspace_request.rb +0 -24
  194. data/lib/open_api_sdk/models/operations/getworkspace_response.rb +0 -60
  195. data/lib/open_api_sdk/models/operations/groupby.rb +0 -28
  196. data/lib/open_api_sdk/models/operations/interval.rb +0 -25
  197. data/lib/open_api_sdk/models/operations/level.rb +0 -21
  198. data/lib/open_api_sdk/models/operations/listdomains_response.rb +0 -60
  199. data/lib/open_api_sdk/models/operations/paymentprocessor.rb +0 -20
  200. data/lib/open_api_sdk/models/operations/requestbody.rb +0 -95
  201. data/lib/open_api_sdk/models/operations/retrieveanalytics_request.rb +0 -81
  202. data/lib/open_api_sdk/models/operations/retrieveanalytics_response.rb +0 -60
  203. data/lib/open_api_sdk/models/operations/sort.rb +0 -20
  204. data/lib/open_api_sdk/models/operations/trackcustomer_requestbody.rb +0 -33
  205. data/lib/open_api_sdk/models/operations/trackcustomer_response.rb +0 -60
  206. data/lib/open_api_sdk/models/operations/trackcustomer_responsebody.rb +0 -33
  207. data/lib/open_api_sdk/models/operations/tracklead_requestbody.rb +0 -42
  208. data/lib/open_api_sdk/models/operations/tracklead_response.rb +0 -60
  209. data/lib/open_api_sdk/models/operations/tracklead_responsebody.rb +0 -42
  210. data/lib/open_api_sdk/models/operations/tracksale_requestbody.rb +0 -42
  211. data/lib/open_api_sdk/models/operations/tracksale_response.rb +0 -60
  212. data/lib/open_api_sdk/models/operations/tracksale_responsebody.rb +0 -42
  213. data/lib/open_api_sdk/models/operations/updatedomain_request.rb +0 -27
  214. data/lib/open_api_sdk/models/operations/updatedomain_requestbody.rb +0 -33
  215. data/lib/open_api_sdk/models/operations/updatedomain_response.rb +0 -60
  216. data/lib/open_api_sdk/models/operations/updatelink_request.rb +0 -27
  217. data/lib/open_api_sdk/models/operations/updatelink_requestbody.rb +0 -95
  218. data/lib/open_api_sdk/models/operations/updatelink_response.rb +0 -60
  219. data/lib/open_api_sdk/models/operations/updatetag_color.rb +0 -24
  220. data/lib/open_api_sdk/models/operations/updatetag_request.rb +0 -27
  221. data/lib/open_api_sdk/models/operations/updatetag_requestbody.rb +0 -32
  222. data/lib/open_api_sdk/models/operations/updatetag_response.rb +0 -60
  223. data/lib/open_api_sdk/models/operations/updateworkspace_request.rb +0 -27
  224. data/lib/open_api_sdk/models/operations/updateworkspace_requestbody.rb +0 -27
  225. data/lib/open_api_sdk/models/operations/updateworkspace_response.rb +0 -60
  226. data/lib/open_api_sdk/models/operations/upsertlink_requestbody.rb +0 -95
  227. data/lib/open_api_sdk/models/operations/upsertlink_response.rb +0 -60
  228. data/lib/open_api_sdk/models/operations.rb +0 -74
  229. data/lib/open_api_sdk/models/shared/badrequest.rb +0 -24
  230. data/lib/open_api_sdk/models/shared/code.rb +0 -18
  231. data/lib/open_api_sdk/models/shared/color.rb +0 -24
  232. data/lib/open_api_sdk/models/shared/conflict.rb +0 -24
  233. data/lib/open_api_sdk/models/shared/conflict_code.rb +0 -18
  234. data/lib/open_api_sdk/models/shared/conflict_error.rb +0 -30
  235. data/lib/open_api_sdk/models/shared/countrycode.rb +0 -267
  236. data/lib/open_api_sdk/models/shared/domains.rb +0 -27
  237. data/lib/open_api_sdk/models/shared/domainschema.rb +0 -48
  238. data/lib/open_api_sdk/models/shared/error.rb +0 -30
  239. data/lib/open_api_sdk/models/shared/forbidden.rb +0 -24
  240. data/lib/open_api_sdk/models/shared/forbidden_code.rb +0 -18
  241. data/lib/open_api_sdk/models/shared/forbidden_error.rb +0 -30
  242. data/lib/open_api_sdk/models/shared/geo.rb +0 -771
  243. data/lib/open_api_sdk/models/shared/internalservererror.rb +0 -24
  244. data/lib/open_api_sdk/models/shared/internalservererror_code.rb +0 -18
  245. data/lib/open_api_sdk/models/shared/internalservererror_error.rb +0 -30
  246. data/lib/open_api_sdk/models/shared/inviteexpired.rb +0 -24
  247. data/lib/open_api_sdk/models/shared/inviteexpired_code.rb +0 -18
  248. data/lib/open_api_sdk/models/shared/inviteexpired_error.rb +0 -30
  249. data/lib/open_api_sdk/models/shared/linkgeotargeting.rb +0 -771
  250. data/lib/open_api_sdk/models/shared/linkschema.rb +0 -142
  251. data/lib/open_api_sdk/models/shared/notfound.rb +0 -24
  252. data/lib/open_api_sdk/models/shared/notfound_code.rb +0 -18
  253. data/lib/open_api_sdk/models/shared/notfound_error.rb +0 -30
  254. data/lib/open_api_sdk/models/shared/plan.rb +0 -24
  255. data/lib/open_api_sdk/models/shared/ratelimitexceeded.rb +0 -24
  256. data/lib/open_api_sdk/models/shared/ratelimitexceeded_code.rb +0 -18
  257. data/lib/open_api_sdk/models/shared/ratelimitexceeded_error.rb +0 -30
  258. data/lib/open_api_sdk/models/shared/role.rb +0 -19
  259. data/lib/open_api_sdk/models/shared/security.rb +0 -24
  260. data/lib/open_api_sdk/models/shared/tagschema.rb +0 -30
  261. data/lib/open_api_sdk/models/shared/unauthorized.rb +0 -24
  262. data/lib/open_api_sdk/models/shared/unauthorized_code.rb +0 -18
  263. data/lib/open_api_sdk/models/shared/unauthorized_error.rb +0 -30
  264. data/lib/open_api_sdk/models/shared/unprocessableentity.rb +0 -24
  265. data/lib/open_api_sdk/models/shared/unprocessableentity_code.rb +0 -18
  266. data/lib/open_api_sdk/models/shared/unprocessableentity_error.rb +0 -30
  267. data/lib/open_api_sdk/models/shared/users.rb +0 -24
  268. data/lib/open_api_sdk/models/shared/workspaceschema.rb +0 -81
  269. data/lib/open_api_sdk/models/shared.rb +0 -49
  270. data/lib/open_api_sdk/qr_codes.rb +0 -97
  271. data/lib/open_api_sdk/sdkconfiguration.rb +0 -52
  272. data/lib/open_api_sdk/tags.rb +0 -272
  273. data/lib/open_api_sdk/track.rb +0 -276
  274. data/lib/open_api_sdk/utils/metadata_fields.rb +0 -150
  275. data/lib/open_api_sdk/utils/t.rb +0 -59
  276. data/lib/open_api_sdk/utils/utils.rb +0 -772
  277. data/lib/open_api_sdk/workspaces.rb +0 -192
@@ -0,0 +1,329 @@
1
+ require 'dub/generator'
2
+ require 'erb'
3
+
4
+ module Dub
5
+ module Lua
6
+ SELF = "self"
7
+ class FunctionGen < Dub::Generator
8
+ # klass is used when parsing members from the superclasses.
9
+ attr_accessor :template_path, :klass
10
+
11
+ NUMBER_TYPES = [
12
+ 'float',
13
+ 'double',
14
+ 'time_t',
15
+ ]
16
+
17
+ INT_TYPES = [
18
+ 'int',
19
+ 'size_t',
20
+ 'unsigned int',
21
+ 'uint',
22
+ 'uchar',
23
+ 'char',
24
+ ]
25
+
26
+ BOOL_TYPES = [
27
+ 'bool',
28
+ ]
29
+
30
+ DEFAULT_CUSTOM_TYPES = [
31
+ [/lua_State /, Proc.new do |type_def, arg, stack_pos|
32
+ if type_def =~ /lua_State\s*\*\s*L/
33
+ ""
34
+ else
35
+ "#{type_def} = L;"
36
+ end
37
+ end]
38
+ ]
39
+
40
+ def initialize
41
+ load_erb
42
+ @custom_types = DEFAULT_CUSTOM_TYPES.dup
43
+ end
44
+
45
+ def template_path=(template_path)
46
+ @template_path = template_path
47
+ load_erb
48
+ end
49
+
50
+ def custom_type(regexp, &block)
51
+ @custom_types << [regexp, block]
52
+ end
53
+
54
+ # Produce bindings for a group of overloaded functions
55
+ def group(group)
56
+ @group = group
57
+ if @group.members
58
+ @group_template.result(binding)
59
+ else
60
+ ''
61
+ end
62
+ end
63
+
64
+ def function(function)
65
+ @function = function
66
+ @function_template.result(binding)
67
+ end
68
+
69
+ def function_generator
70
+ self
71
+ end
72
+
73
+ def namespace_generator
74
+ Dub::Lua.namespace_generator
75
+ end
76
+
77
+ def chooser_body(group = @group)
78
+ if group.first.member_method? && !group.first.constructor?
79
+ delta_depth = 1
80
+ else
81
+ delta_depth = 0
82
+ end
83
+ decision_tree = Argument.decision_tree(group.members)
84
+ res = []
85
+ res << "int type__ = lua_type(L, #{1 + delta_depth});"
86
+ if flatten_hash(decision_tree).include?(nil)
87
+ res << "int top__ = lua_gettop(L);"
88
+ end
89
+ res << switch(decision_tree, delta_depth + 1, true)
90
+ res.join("\n")
91
+ end
92
+
93
+ # Create a switch to choose the correct method from argument types (overloaded functions)
94
+ def switch(hash_or_function, depth = 1, start = false)
95
+ if hash_or_function.kind_of?(Function)
96
+ method_call(hash_or_function)
97
+ else
98
+ res = []
99
+ res << "type__ = lua_type(L, #{depth});" unless start
100
+ else_prefix = ''
101
+ default_sub_group = nil
102
+ hash_or_function.each do |type, sub_group|
103
+ default_sub_group = sub_group
104
+ case type
105
+ when :number
106
+ res << "#{else_prefix}if (type__ == LUA_TNUMBER) {"
107
+ when :string
108
+ res << "#{else_prefix}if (type__ == LUA_TSTRING) {"
109
+ when nil
110
+ res << "#{else_prefix}if (top__ < #{depth}) {"
111
+ else
112
+ res << "#{else_prefix}if (type__ == LUA_TUSERDATA && is_userdata(L, #{depth}, \"#{type}\")) {"
113
+ end
114
+
115
+ res << indent(switch(sub_group, depth + 1), 2)
116
+
117
+ else_prefix = '} else '
118
+ end
119
+
120
+ last = default_sub_group.kind_of?(Hash) ? flatten_hash(default_sub_group).last : default_sub_group
121
+
122
+ res << "} else {"
123
+ res << " // use any to raise errors"
124
+ res << indent(method_call(last), 2)
125
+ res << "}"
126
+ res.join("\n")
127
+ end
128
+ end
129
+
130
+ def signature(func, overloaded_index = nil)
131
+ "static int #{method_name(func, overloaded_index)}(lua_State *L)"
132
+ end
133
+
134
+ # The check_prefix parameter chooses between dubL_check and luaL_check depending
135
+ # on exceptions that can be thrown.
136
+ def body(func, check_prefix)
137
+ res = []
138
+ delta_top = 0
139
+ if func.member_method? && !func.constructor? && !func.static?
140
+ # Force @klass when serializing members from superclass.
141
+ klass = @klass || func.parent
142
+ res << "#{klass.name} *#{SELF} = *((#{klass.name}**)#{check_prefix}L_checksdata(L, 1, #{klass.id_name.inspect}));"
143
+ if func.member_method? && func.klass.custom_destructor?
144
+ # protect calls
145
+ if check_prefix == 'dub'
146
+ # we cannot use luaL_error
147
+ res << "if (!#{SELF}) throw dub::Exception(\"Using deleted #{klass.id_name} in #{func.name}\");"
148
+ else
149
+ res << "if (!#{SELF}) return luaL_error(L, \"Using deleted #{klass.id_name} in #{func.name}\");"
150
+ end
151
+ end
152
+ delta_top = 1
153
+ end
154
+
155
+ custom_body = func.custom_body('lua')
156
+
157
+ if_indent = 0
158
+ if custom_body && func.has_default_arguments?
159
+ # we do not prepare arguments
160
+ else
161
+ if func.has_default_arguments?
162
+ res << "int top__ = lua_gettop(L);"
163
+ if return_value = func.return_value
164
+ res << "#{return_value.create_type} retval__;"
165
+ end
166
+ end
167
+ func.arguments.each_with_index do |arg, i|
168
+ if arg.has_default?
169
+ res << indent("if (top__ < #{i+1+delta_top}) {", if_indent)
170
+ res << indent(" #{call_string(func, i)}", if_indent)
171
+ res << indent("} else {", if_indent)
172
+ if_indent += 2
173
+ end
174
+ res << indent(get_arg(arg, i + 1 + delta_top, check_prefix), if_indent)
175
+ end
176
+ end
177
+ if custom_body
178
+ res << indent(custom_body, if_indent)
179
+ else
180
+ res << indent(call_string(func, func.arguments.count), if_indent)
181
+ end
182
+ while if_indent > 0
183
+ if_indent -= 2
184
+ res << indent("}", if_indent)
185
+ end
186
+
187
+ unless custom_body
188
+ res << return_value(func)
189
+ end
190
+ res.join("\n")
191
+ end
192
+
193
+ def method_name(func, overloaded_index = nil)
194
+ overloaded_index ||= func.overloaded_index
195
+ overloaded_index = '' if overloaded_index == 0
196
+ "#{func.prefix}_#{func.name}#{overloaded_index}"
197
+ end
198
+
199
+ def method_call(func)
200
+ "return #{method_name(func)}(L);"
201
+ end
202
+
203
+ def call_string(func, upto_arg = nil)
204
+ upto_arg ||= func.arguments.count
205
+ if upto_arg == 0
206
+ call_string = "#{func.call_name}();"
207
+ else
208
+ call_string = "#{func.call_name}(#{func.arguments[0..(upto_arg-1)].map{|arg| arg.in_call_type}.join(', ')});"
209
+ end
210
+
211
+ if func.constructor?
212
+ call_string = "new #{call_string}"
213
+ elsif func.member_method? && !func.static?
214
+ call_string = "#{SELF}->#{call_string}"
215
+ end
216
+
217
+
218
+ if return_value = func.return_value
219
+ if func.has_default_arguments?
220
+ "retval__ = #{call_string}"
221
+ else
222
+ "#{return_value.create_type} retval__ = #{call_string}"
223
+ end
224
+ else
225
+ call_string
226
+ end
227
+ end
228
+
229
+ def return_value(func)
230
+ res = []
231
+ if return_value = func.return_value
232
+ if return_value.create_type == 'LuaStackSize '
233
+ return "return retval__;"
234
+ end
235
+ case Argument.type_group(return_value)
236
+ when :number
237
+ res << "lua_pushnumber(L, retval__);"
238
+ when :boolean
239
+ res << "lua_pushboolean(L, retval__);"
240
+ when :string
241
+ res << "lua_pushstring(L, retval__);"
242
+ else
243
+ pushclass = 'lua_pushclass'
244
+ if func.constructor?
245
+ if ctor_with_lua_init?(func)
246
+ res << "// The class inherits from 'LuaCallback', use lua_init instead of pushclass."
247
+ res << "return retval__->luaInit(L, retval__, \"#{return_value.id_name}\");"
248
+ return res.join("\n")
249
+ elsif func.klass.custom_destructor?
250
+ # Use special pushclass to set userdata
251
+ pushclass = 'lua_pushclass2'
252
+ end
253
+ prefix = func.klass.prefix
254
+ else
255
+ prefix = func.prefix
256
+ end
257
+ res << "#{pushclass}<#{return_value.type}>(L, retval__, \"#{return_value.id_name}\");"
258
+ end
259
+ res << "return 1;"
260
+ else
261
+ res << "return 0;"
262
+ end
263
+ res.join("\n")
264
+ end
265
+
266
+ # Get argument and verify type
267
+ # // luaL_argcheck could be better to report errors like "expected Mat"
268
+ # the check_prefix chooses between 'luaL_check...' and 'dubL_check' methods
269
+ # depending on C++ exceptions raised by the function.
270
+ def get_arg(arg, stack_pos, check_prefix)
271
+ type_def = "#{arg.create_type}#{arg.name}#{arg.array_suffix}"
272
+ if custom_type = @custom_types.detect {|reg,proc| type_def =~ reg}
273
+ custom_type[1].call(type_def, arg, stack_pos)
274
+ elsif arg.is_native?
275
+ if arg.is_pointer?
276
+ if arg.type == 'char'
277
+ type_def = "const #{type_def}" unless arg.is_const?
278
+ "#{type_def} = #{check_prefix}L_checkstring(L, #{stack_pos});"
279
+ else
280
+ # retrieve by using a table accessor
281
+ # TODO: we should have a hint on required sizes !
282
+ "\nDubArgPointer<#{arg.type}> ptr_#{arg.name};\n" +
283
+ "#{type_def} = ptr_#{arg.name}(L, #{stack_pos});"
284
+ end
285
+ else
286
+ if NUMBER_TYPES.include?(arg.type)
287
+ "#{type_def} = #{check_prefix}L_checknumber(L, #{stack_pos});"
288
+ elsif BOOL_TYPES.include?(arg.type)
289
+ "#{type_def} = lua_toboolean(L, #{stack_pos});"
290
+ elsif INT_TYPES.include?(arg.type)
291
+ "#{type_def} = #{check_prefix}L_checkint(L, #{stack_pos});"
292
+ else
293
+ raise "Unsuported type: #{arg.type}"
294
+ end
295
+ end
296
+ else
297
+ "#{type_def} = *((#{arg.create_type}*)#{check_prefix}L_checksdata(L, #{stack_pos}, #{arg.id_name.inspect}));"
298
+ end
299
+ end
300
+
301
+ def flatten_hash(hash)
302
+ list = []
303
+ hash.each do |k, v|
304
+ if v.kind_of?(Hash)
305
+ list << [k, flatten_hash(v)]
306
+ else
307
+ list << [k, v]
308
+ end
309
+ end
310
+ list.flatten
311
+ end
312
+
313
+ def load_erb
314
+ @function_template = ::ERB.new(File.read(@template_path ||File.join(File.dirname(__FILE__), 'function.cpp.erb')), nil, '%<>-')
315
+ @group_template = ::ERB.new(File.read(File.join(File.dirname(__FILE__), 'group.cpp.erb')))
316
+ end
317
+
318
+ def ctor_with_lua_init?(func)
319
+ # If the class inherits from LuaObject, we need to use
320
+ # s->lua_init(L); instead of pushclass.
321
+ if func.constructor?
322
+ func.klass.ancestors.detect{|a| a =~ /LuaObject/}
323
+ else
324
+ false
325
+ end
326
+ end
327
+ end # FunctionGen
328
+ end # Lua
329
+ end # Dub
@@ -0,0 +1,9 @@
1
+ <% @group.members.each do |f| %>
2
+ <%= function(f) %>
3
+
4
+ <% end %>
5
+
6
+ /** Overloaded function chooser for <%= @group.name %>(...) */
7
+ <%= signature(@group.first, 0) %> {
8
+ <%= indent(chooser_body, 2) %>
9
+ }
@@ -0,0 +1,259 @@
1
+ /*
2
+ Copyright (c) 2011 by Gaspard Bucher (http://teti.ch).
3
+
4
+ Permission is hereby granted, free of charge, to any person obtaining
5
+ a copy of this software and associated documentation files (the
6
+ "Software"), to deal in the Software without restriction, including
7
+ without limitation the rights to use, copy, modify, merge, publish,
8
+ distribute, sublicense, and/or sell copies of the Software, and to
9
+ permit persons to whom the Software is furnished to do so, subject to
10
+ the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be
13
+ included in all copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
16
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
17
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
18
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
19
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
20
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
21
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
22
+ */
23
+
24
+ #include "lua_cpp_helper.h"
25
+
26
+ #define DUB_EXCEPTION_BUFFER_SIZE 256
27
+ #define TYPE_EXCEPTION_MSG "%s expected, got %s"
28
+ #define TYPE_EXCEPTION_SMSG "%s expected, got %s (using super)"
29
+ using namespace dub;
30
+
31
+ Exception::Exception(const char *format, ...) {
32
+ char buffer[DUB_EXCEPTION_BUFFER_SIZE];
33
+ va_list args;
34
+ va_start(args, format);
35
+ vsnprintf(buffer, DUB_EXCEPTION_BUFFER_SIZE, format, args);
36
+ va_end(args);
37
+ message_ = buffer;
38
+ }
39
+
40
+ Exception::~Exception() throw() {}
41
+
42
+ const char* Exception::what() const throw() {
43
+ return message_.c_str();
44
+ }
45
+
46
+
47
+ TypeException::TypeException(lua_State *L, int narg, const char *type, bool is_super) :
48
+ Exception(is_super ? TYPE_EXCEPTION_SMSG : TYPE_EXCEPTION_MSG, type, luaL_typename(L, narg)) {}
49
+
50
+ // ================================================== LuaL_check... try/catch safe
51
+ // These methods (dubL_...) are slight adaptations from luaxlib.c
52
+ // Copyright (C) 1994-2008 Lua.org, PUC-Rio.
53
+
54
+ lua_Number dubL_checknumber(lua_State *L, int narg) throw(TypeException) {
55
+ lua_Number d = lua_tonumber(L, narg);
56
+ if (d == 0 && !lua_isnumber(L, narg)) /* avoid extra test when d is not 0 */
57
+ throw TypeException(L, narg, lua_typename(L, LUA_TNUMBER));
58
+ return d;
59
+ }
60
+
61
+ lua_Integer dubL_checkinteger(lua_State *L, int narg) throw(TypeException) {
62
+ lua_Integer d = lua_tointeger(L, narg);
63
+ if (d == 0 && !lua_isnumber(L, narg)) /* avoid extra test when d is not 0 */
64
+ throw TypeException(L, narg, lua_typename(L, LUA_TNUMBER));
65
+ return d;
66
+ }
67
+
68
+ const char *dubL_checklstring(lua_State *L, int narg, size_t *len) throw(TypeException) {
69
+ const char *s = lua_tolstring(L, narg, len);
70
+ if (!s) throw TypeException(L, narg, lua_typename(L, LUA_TSTRING));
71
+ return s;
72
+ }
73
+
74
+ void *dubL_checkudata(lua_State *L, int ud, const char *tname) throw(TypeException) {
75
+ void *p = lua_touserdata(L, ud);
76
+ if (p != NULL) { /* value is a userdata? */
77
+ if (lua_getmetatable(L, ud)) { /* does it have a metatable? */
78
+ lua_getfield(L, LUA_REGISTRYINDEX, tname); /* get correct metatable */
79
+ if (lua_rawequal(L, -1, -2)) { /* does it have the correct mt? */
80
+ lua_pop(L, 2); /* remove both metatables */
81
+ return p;
82
+ }
83
+ }
84
+ }
85
+ throw TypeException(L, ud, tname); /* else error */
86
+ return NULL; /* to avoid warnings */
87
+ }
88
+
89
+ // throws exceptions
90
+ void *dubL_checksdata(lua_State *L, int ud, const char *tname) throw(dub::TypeException) {
91
+ void *p = lua_touserdata(L, ud);
92
+ if (p != NULL) { /* value is a userdata? */
93
+ if (lua_getmetatable(L, ud)) { /* does it have a metatable? */
94
+ lua_getfield(L, LUA_REGISTRYINDEX, tname); /* get correct metatable */
95
+ if (lua_rawequal(L, -1, -2)) { /* does it have the correct mt? */
96
+ lua_pop(L, 2); /* remove both metatables */
97
+ return p;
98
+ }
99
+ }
100
+ } else if (lua_istable(L, ud)) {
101
+ if (ud < 0) {
102
+ ud = lua_gettop(L) + 1 + ud;
103
+ }
104
+ // get p from super
105
+ // ... <ud> ...
106
+ // TODO: optimize by storing key in registry ?
107
+ lua_pushlstring(L, "super", 5);
108
+ // ... <ud> ... <'super'>
109
+ lua_rawget(L, ud);
110
+ // ... <ud> ... <ud?>
111
+ p = lua_touserdata(L, -1);
112
+ if (p != NULL) {
113
+ if (lua_getmetatable(L, -1)) { /* does it have a metatable? */
114
+ lua_getfield(L, LUA_REGISTRYINDEX, tname); /* get correct metatable */
115
+ if (lua_rawequal(L, -1, -2)) { /* does it have the correct mt? */
116
+ lua_pop(L, 3); /* remove both metatables and super */
117
+ return p;
118
+ }
119
+ // remove both metatables
120
+ lua_pop(L, 2);
121
+ }
122
+ throw dub::TypeException(L, -1, tname, true);
123
+ }
124
+ }
125
+ throw dub::TypeException(L, ud, tname);
126
+ return NULL;
127
+ }
128
+
129
+ // does not throw exceptions
130
+ void *dubL_checksdata_n(lua_State *L, int ud, const char *tname) throw() {
131
+ void *p = lua_touserdata(L, ud);
132
+ if (p != NULL) { /* value is a userdata? */
133
+ if (lua_getmetatable(L, ud)) { /* does it have a metatable? */
134
+ lua_getfield(L, LUA_REGISTRYINDEX, tname); /* get correct metatable */
135
+ if (lua_rawequal(L, -1, -2)) { /* does it have the correct mt? */
136
+ lua_pop(L, 2); /* remove both metatables */
137
+ return p;
138
+ }
139
+ }
140
+ } else if (lua_istable(L, ud)) {
141
+ if (ud < 0) {
142
+ ud = lua_gettop(L) + 1 + ud;
143
+ }
144
+ // get p from super
145
+ // ... <ud> ...
146
+ // TODO: optimize by storing key in registry ?
147
+ lua_pushlstring(L, "super", 5);
148
+ // ... <ud> ... <'super'>
149
+ lua_rawget(L, ud);
150
+ // ... <ud> ... <ud?>
151
+ p = lua_touserdata(L, -1);
152
+ if (p != NULL) {
153
+ if (lua_getmetatable(L, -1)) { /* does it have a metatable? */
154
+ lua_getfield(L, LUA_REGISTRYINDEX, tname); /* get correct metatable */
155
+ if (lua_rawequal(L, -1, -2)) { /* does it have the correct mt? */
156
+ lua_pop(L, 3); /* remove both metatables and super */
157
+ return p;
158
+ }
159
+ // remove both metatables
160
+ lua_pop(L, 2);
161
+ }
162
+ luaL_error(L, "%s expected, got %s (using super)", tname, luaL_typename(L, -1));
163
+ }
164
+ }
165
+ luaL_error(L, "%s expected, got %s", tname, luaL_typename(L, ud));
166
+ return NULL;
167
+ }
168
+
169
+ // ==================================================
170
+
171
+ DeletableOutOfLua::DeletableOutOfLua() :
172
+ userdata_ptr_(NULL) {}
173
+
174
+ DeletableOutOfLua::~DeletableOutOfLua() {
175
+ if (userdata_ptr_) {
176
+ *userdata_ptr_ = NULL;
177
+ userdata_ptr_ = NULL;
178
+ }
179
+ }
180
+
181
+ void DeletableOutOfLua::dub_destroy() {
182
+ dub_cleanup();
183
+ delete this;
184
+ }
185
+
186
+ void DeletableOutOfLua::set_userdata_ptr(void **ptr) {
187
+ userdata_ptr_ = ptr;
188
+ }
189
+
190
+ void DeletableOutOfLua::dub_cleanup() {
191
+ // so that it is not changed in ~DeletableOutOfLua
192
+ userdata_ptr_ = NULL;
193
+ }
194
+
195
+ /** ======================================== is_userdata */
196
+
197
+ bool is_userdata(lua_State *L, int index, const char *tname) {
198
+ void *p = lua_touserdata(L, index);
199
+ if (p != NULL) { /* value is a userdata? */
200
+ if (lua_getmetatable(L, index)) { /* does it have a metatable? */
201
+ lua_getfield(L, LUA_REGISTRYINDEX, tname); /* get correct metatable */
202
+ if (lua_rawequal(L, -1, -2)) { /* does it have the correct mt? */
203
+ lua_pop(L, 2); /* remove both metatables */
204
+ // type match
205
+ return true;
206
+ }
207
+ }
208
+ }
209
+ // type does not match
210
+ return false;
211
+ }
212
+
213
+ int libsize (const lua_constants_Reg *l) {
214
+ int size = 0;
215
+ for (; l->name; l++) size++;
216
+ return size;
217
+ }
218
+
219
+ void register_constants(lua_State *L, const char *name_space, const lua_constants_Reg *l) {
220
+ if (name_space) {
221
+ /* compute size hint for new table. */
222
+ int size = libsize(l);
223
+
224
+ /* try global variable (and create one if it does not exist) */
225
+ if (luaL_findtable(L, LUA_GLOBALSINDEX, name_space, size) != NULL)
226
+ luaL_error(L, "name conflict for module " LUA_QS, name_space);
227
+
228
+ /* found name_space in global index ==> stack -1 */
229
+ }
230
+ for (; l->name; l++) {
231
+ /* push each constant into the name_space (stack position = -1)*/
232
+ lua_pushnumber(L, l->constant);
233
+ lua_setfield(L, -2, l->name);
234
+ }
235
+ /* pop name_space */
236
+ lua_pop(L, 1);
237
+ }
238
+
239
+ // The metatable lives in libname.ClassName_
240
+ void register_mt(lua_State *L, const char *libname, const char *class_name) {
241
+ size_t len = strlen(class_name) + 2;
242
+ char *buffer = (char*)malloc(sizeof(char) * len);
243
+ snprintf(buffer, len, "%s_", class_name);
244
+
245
+ // meta-table should be on top
246
+ // <mt>
247
+ lua_getglobal(L, libname);
248
+ // <mt> <lib>
249
+ lua_pushstring(L, buffer);
250
+ // <mt> <lib> "Foobar_"
251
+ lua_pushvalue(L, -3);
252
+ // <mt> <lib> "Foobar" <mt>
253
+ lua_settable(L, -3);
254
+ // <mt> <lib>
255
+ lua_pop(L, 1);
256
+ // <mt>
257
+ }
258
+
259
+