immunio 0.15.4 → 0.16.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.
Files changed (454) hide show
  1. checksums.yaml +4 -4
  2. data/LICENSE +0 -27
  3. data/ext/immunio/Rakefile +9 -0
  4. data/lib/immunio/plugins/active_record.rb +1 -1
  5. data/lib/immunio/plugins/active_record_relation.rb +1 -1
  6. data/lib/immunio/plugins/environment_reporter.rb +20 -0
  7. data/lib/immunio/rufus_lua_ext/ref.rb +1 -3
  8. data/lib/immunio/version.rb +1 -1
  9. data/lib/immunio/vm.rb +1 -2
  10. data/lua-hooks/Makefile +97 -0
  11. data/lua-hooks/ext/all.c +41 -52
  12. data/lua-hooks/ext/all.o +0 -0
  13. data/lua-hooks/ext/libinjection/libinjection_html5.o +0 -0
  14. data/lua-hooks/ext/libinjection/libinjection_sqli.o +0 -0
  15. data/lua-hooks/ext/libinjection/libinjection_xss.o +0 -0
  16. data/lua-hooks/ext/libinjection/lualib.c +2 -2
  17. data/lua-hooks/ext/lpeg/lpcap.c +2 -2
  18. data/lua-hooks/ext/lpeg/lpcap.o +0 -0
  19. data/lua-hooks/ext/lpeg/lpcode.c +2 -2
  20. data/lua-hooks/ext/lpeg/lpcode.h +1 -1
  21. data/lua-hooks/ext/lpeg/lpcode.o +0 -0
  22. data/lua-hooks/ext/lpeg/lpprint.o +0 -0
  23. data/lua-hooks/ext/lpeg/lptree.c +2 -2
  24. data/lua-hooks/ext/lpeg/lptypes.h +1 -1
  25. data/lua-hooks/ext/lpeg/lpvm.c +2 -2
  26. data/lua-hooks/ext/lpeg/lpvm.o +0 -0
  27. data/lua-hooks/ext/lua-cmsgpack/lua_cmsgpack.c +16 -3
  28. data/lua-hooks/ext/lua-snapshot/snapshot.c +14 -7
  29. data/lua-hooks/ext/luajit/COPYRIGHT +56 -0
  30. data/lua-hooks/ext/luajit/Makefile +159 -0
  31. data/lua-hooks/ext/luajit/README +16 -0
  32. data/lua-hooks/ext/luajit/doc/bluequad-print.css +166 -0
  33. data/lua-hooks/ext/luajit/doc/bluequad.css +325 -0
  34. data/lua-hooks/ext/luajit/doc/changes.html +804 -0
  35. data/lua-hooks/ext/luajit/doc/contact.html +104 -0
  36. data/lua-hooks/ext/luajit/doc/ext_c_api.html +189 -0
  37. data/lua-hooks/ext/luajit/doc/ext_ffi.html +332 -0
  38. data/lua-hooks/ext/luajit/doc/ext_ffi_api.html +570 -0
  39. data/lua-hooks/ext/luajit/doc/ext_ffi_semantics.html +1261 -0
  40. data/lua-hooks/ext/luajit/doc/ext_ffi_tutorial.html +603 -0
  41. data/lua-hooks/ext/luajit/doc/ext_jit.html +201 -0
  42. data/lua-hooks/ext/luajit/doc/ext_profiler.html +365 -0
  43. data/lua-hooks/ext/luajit/doc/extensions.html +448 -0
  44. data/lua-hooks/ext/luajit/doc/faq.html +186 -0
  45. data/lua-hooks/ext/luajit/doc/img/contact.png +0 -0
  46. data/lua-hooks/ext/luajit/doc/install.html +659 -0
  47. data/lua-hooks/ext/luajit/doc/luajit.html +236 -0
  48. data/lua-hooks/ext/luajit/doc/running.html +309 -0
  49. data/lua-hooks/ext/luajit/doc/status.html +118 -0
  50. data/lua-hooks/ext/luajit/dynasm/dasm_arm.h +456 -0
  51. data/lua-hooks/ext/luajit/dynasm/dasm_arm.lua +1125 -0
  52. data/lua-hooks/ext/luajit/dynasm/dasm_arm64.h +518 -0
  53. data/lua-hooks/ext/luajit/dynasm/dasm_arm64.lua +1166 -0
  54. data/lua-hooks/ext/luajit/dynasm/dasm_mips.h +416 -0
  55. data/lua-hooks/ext/luajit/dynasm/dasm_mips.lua +953 -0
  56. data/lua-hooks/ext/luajit/dynasm/dasm_ppc.h +419 -0
  57. data/lua-hooks/ext/luajit/dynasm/dasm_ppc.lua +1919 -0
  58. data/lua-hooks/ext/luajit/dynasm/dasm_proto.h +83 -0
  59. data/lua-hooks/ext/luajit/dynasm/dasm_x64.lua +12 -0
  60. data/lua-hooks/ext/luajit/dynasm/dasm_x86.h +471 -0
  61. data/lua-hooks/ext/luajit/dynasm/dasm_x86.lua +1945 -0
  62. data/lua-hooks/ext/luajit/dynasm/dynasm.lua +1094 -0
  63. data/lua-hooks/ext/luajit/etc/luajit.1 +88 -0
  64. data/lua-hooks/ext/luajit/etc/luajit.pc +25 -0
  65. data/lua-hooks/ext/luajit/src/Makefile +697 -0
  66. data/lua-hooks/ext/luajit/src/Makefile.dep +244 -0
  67. data/lua-hooks/ext/luajit/src/host/README +4 -0
  68. data/lua-hooks/ext/luajit/src/host/buildvm +0 -0
  69. data/lua-hooks/ext/luajit/src/host/buildvm.c +518 -0
  70. data/lua-hooks/ext/luajit/src/host/buildvm.h +105 -0
  71. data/lua-hooks/ext/luajit/src/host/buildvm.o +0 -0
  72. data/lua-hooks/ext/luajit/src/host/buildvm_arch.h +7449 -0
  73. data/lua-hooks/ext/luajit/src/host/buildvm_asm.c +345 -0
  74. data/lua-hooks/ext/luajit/src/host/buildvm_asm.o +0 -0
  75. data/lua-hooks/ext/luajit/src/host/buildvm_fold.c +229 -0
  76. data/lua-hooks/ext/luajit/src/host/buildvm_fold.o +0 -0
  77. data/lua-hooks/ext/luajit/src/host/buildvm_lib.c +457 -0
  78. data/lua-hooks/ext/luajit/src/host/buildvm_lib.o +0 -0
  79. data/lua-hooks/ext/luajit/src/host/buildvm_libbc.h +45 -0
  80. data/lua-hooks/ext/luajit/src/host/buildvm_peobj.c +368 -0
  81. data/lua-hooks/ext/luajit/src/host/buildvm_peobj.o +0 -0
  82. data/lua-hooks/ext/luajit/src/host/genlibbc.lua +197 -0
  83. data/lua-hooks/ext/luajit/src/host/genminilua.lua +428 -0
  84. data/lua-hooks/ext/luajit/src/host/minilua +0 -0
  85. data/lua-hooks/ext/luajit/src/host/minilua.c +7770 -0
  86. data/lua-hooks/ext/luajit/src/host/minilua.o +0 -0
  87. data/lua-hooks/ext/luajit/src/jit/bc.lua +190 -0
  88. data/lua-hooks/ext/luajit/src/jit/bcsave.lua +661 -0
  89. data/lua-hooks/ext/luajit/src/jit/dis_arm.lua +689 -0
  90. data/lua-hooks/ext/luajit/src/jit/dis_mips.lua +428 -0
  91. data/lua-hooks/ext/luajit/src/jit/dis_mipsel.lua +17 -0
  92. data/lua-hooks/ext/luajit/src/jit/dis_ppc.lua +591 -0
  93. data/lua-hooks/ext/luajit/src/jit/dis_x64.lua +17 -0
  94. data/lua-hooks/ext/luajit/src/jit/dis_x86.lua +838 -0
  95. data/lua-hooks/ext/luajit/src/jit/dump.lua +706 -0
  96. data/lua-hooks/ext/luajit/src/jit/p.lua +310 -0
  97. data/lua-hooks/ext/luajit/src/jit/v.lua +170 -0
  98. data/lua-hooks/ext/luajit/src/jit/vmdef.lua +362 -0
  99. data/lua-hooks/ext/luajit/src/jit/zone.lua +45 -0
  100. data/lua-hooks/ext/{lua → luajit/src}/lauxlib.h +10 -17
  101. data/lua-hooks/ext/luajit/src/lib_aux.c +356 -0
  102. data/lua-hooks/ext/luajit/src/lib_aux.o +0 -0
  103. data/lua-hooks/ext/luajit/src/lib_aux_dyn.o +0 -0
  104. data/lua-hooks/ext/luajit/src/lib_base.c +664 -0
  105. data/lua-hooks/ext/luajit/src/lib_base.o +0 -0
  106. data/lua-hooks/ext/luajit/src/lib_base_dyn.o +0 -0
  107. data/lua-hooks/ext/luajit/src/lib_bit.c +180 -0
  108. data/lua-hooks/ext/luajit/src/lib_bit.o +0 -0
  109. data/lua-hooks/ext/luajit/src/lib_bit_dyn.o +0 -0
  110. data/lua-hooks/ext/luajit/src/lib_debug.c +405 -0
  111. data/lua-hooks/ext/luajit/src/lib_debug.o +0 -0
  112. data/lua-hooks/ext/luajit/src/lib_debug_dyn.o +0 -0
  113. data/lua-hooks/ext/luajit/src/lib_ffi.c +872 -0
  114. data/lua-hooks/ext/luajit/src/lib_ffi.o +0 -0
  115. data/lua-hooks/ext/luajit/src/lib_ffi_dyn.o +0 -0
  116. data/lua-hooks/ext/luajit/src/lib_init.c +55 -0
  117. data/lua-hooks/ext/luajit/src/lib_init.o +0 -0
  118. data/lua-hooks/ext/luajit/src/lib_init_dyn.o +0 -0
  119. data/lua-hooks/ext/luajit/src/lib_io.c +541 -0
  120. data/lua-hooks/ext/luajit/src/lib_io.o +0 -0
  121. data/lua-hooks/ext/luajit/src/lib_io_dyn.o +0 -0
  122. data/lua-hooks/ext/luajit/src/lib_jit.c +767 -0
  123. data/lua-hooks/ext/luajit/src/lib_jit.o +0 -0
  124. data/lua-hooks/ext/luajit/src/lib_jit_dyn.o +0 -0
  125. data/lua-hooks/ext/luajit/src/lib_math.c +230 -0
  126. data/lua-hooks/ext/luajit/src/lib_math.o +0 -0
  127. data/lua-hooks/ext/luajit/src/lib_math_dyn.o +0 -0
  128. data/lua-hooks/ext/luajit/src/lib_os.c +292 -0
  129. data/lua-hooks/ext/luajit/src/lib_os.o +0 -0
  130. data/lua-hooks/ext/luajit/src/lib_os_dyn.o +0 -0
  131. data/lua-hooks/ext/luajit/src/lib_package.c +610 -0
  132. data/lua-hooks/ext/luajit/src/lib_package.o +0 -0
  133. data/lua-hooks/ext/luajit/src/lib_package_dyn.o +0 -0
  134. data/lua-hooks/ext/luajit/src/lib_string.c +752 -0
  135. data/lua-hooks/ext/luajit/src/lib_string.o +0 -0
  136. data/lua-hooks/ext/luajit/src/lib_string_dyn.o +0 -0
  137. data/lua-hooks/ext/luajit/src/lib_table.c +307 -0
  138. data/lua-hooks/ext/luajit/src/lib_table.o +0 -0
  139. data/lua-hooks/ext/luajit/src/lib_table_dyn.o +0 -0
  140. data/lua-hooks/ext/luajit/src/libluajit.a +0 -0
  141. data/lua-hooks/ext/luajit/src/libluajit.so +0 -0
  142. data/lua-hooks/ext/luajit/src/lj.supp +26 -0
  143. data/lua-hooks/ext/luajit/src/lj_alloc.c +1398 -0
  144. data/lua-hooks/ext/luajit/src/lj_alloc.h +17 -0
  145. data/lua-hooks/ext/luajit/src/lj_alloc.o +0 -0
  146. data/lua-hooks/ext/luajit/src/lj_alloc_dyn.o +0 -0
  147. data/lua-hooks/ext/luajit/src/lj_api.c +1210 -0
  148. data/lua-hooks/ext/luajit/src/lj_api.o +0 -0
  149. data/lua-hooks/ext/luajit/src/lj_api_dyn.o +0 -0
  150. data/lua-hooks/ext/luajit/src/lj_arch.h +509 -0
  151. data/lua-hooks/ext/luajit/src/lj_asm.c +2278 -0
  152. data/lua-hooks/ext/luajit/src/lj_asm.h +17 -0
  153. data/lua-hooks/ext/luajit/src/lj_asm.o +0 -0
  154. data/lua-hooks/ext/luajit/src/lj_asm_arm.h +2217 -0
  155. data/lua-hooks/ext/luajit/src/lj_asm_dyn.o +0 -0
  156. data/lua-hooks/ext/luajit/src/lj_asm_mips.h +1833 -0
  157. data/lua-hooks/ext/luajit/src/lj_asm_ppc.h +2015 -0
  158. data/lua-hooks/ext/luajit/src/lj_asm_x86.h +2634 -0
  159. data/lua-hooks/ext/luajit/src/lj_bc.c +14 -0
  160. data/lua-hooks/ext/luajit/src/lj_bc.h +265 -0
  161. data/lua-hooks/ext/luajit/src/lj_bc.o +0 -0
  162. data/lua-hooks/ext/luajit/src/lj_bc_dyn.o +0 -0
  163. data/lua-hooks/ext/luajit/src/lj_bcdef.h +220 -0
  164. data/lua-hooks/ext/luajit/src/lj_bcdump.h +68 -0
  165. data/lua-hooks/ext/luajit/src/lj_bcread.c +457 -0
  166. data/lua-hooks/ext/luajit/src/lj_bcread.o +0 -0
  167. data/lua-hooks/ext/luajit/src/lj_bcread_dyn.o +0 -0
  168. data/lua-hooks/ext/luajit/src/lj_bcwrite.c +361 -0
  169. data/lua-hooks/ext/luajit/src/lj_bcwrite.o +0 -0
  170. data/lua-hooks/ext/luajit/src/lj_bcwrite_dyn.o +0 -0
  171. data/lua-hooks/ext/luajit/src/lj_buf.c +234 -0
  172. data/lua-hooks/ext/luajit/src/lj_buf.h +105 -0
  173. data/lua-hooks/ext/luajit/src/lj_buf.o +0 -0
  174. data/lua-hooks/ext/luajit/src/lj_buf_dyn.o +0 -0
  175. data/lua-hooks/ext/luajit/src/lj_carith.c +429 -0
  176. data/lua-hooks/ext/luajit/src/lj_carith.h +37 -0
  177. data/lua-hooks/ext/luajit/src/lj_carith.o +0 -0
  178. data/lua-hooks/ext/luajit/src/lj_carith_dyn.o +0 -0
  179. data/lua-hooks/ext/luajit/src/lj_ccall.c +984 -0
  180. data/lua-hooks/ext/luajit/src/lj_ccall.h +178 -0
  181. data/lua-hooks/ext/luajit/src/lj_ccall.o +0 -0
  182. data/lua-hooks/ext/luajit/src/lj_ccall_dyn.o +0 -0
  183. data/lua-hooks/ext/luajit/src/lj_ccallback.c +712 -0
  184. data/lua-hooks/ext/luajit/src/lj_ccallback.h +25 -0
  185. data/lua-hooks/ext/luajit/src/lj_ccallback.o +0 -0
  186. data/lua-hooks/ext/luajit/src/lj_ccallback_dyn.o +0 -0
  187. data/lua-hooks/ext/luajit/src/lj_cconv.c +752 -0
  188. data/lua-hooks/ext/luajit/src/lj_cconv.h +70 -0
  189. data/lua-hooks/ext/luajit/src/lj_cconv.o +0 -0
  190. data/lua-hooks/ext/luajit/src/lj_cconv_dyn.o +0 -0
  191. data/lua-hooks/ext/luajit/src/lj_cdata.c +288 -0
  192. data/lua-hooks/ext/luajit/src/lj_cdata.h +76 -0
  193. data/lua-hooks/ext/luajit/src/lj_cdata.o +0 -0
  194. data/lua-hooks/ext/luajit/src/lj_cdata_dyn.o +0 -0
  195. data/lua-hooks/ext/luajit/src/lj_char.c +43 -0
  196. data/lua-hooks/ext/luajit/src/lj_char.h +42 -0
  197. data/lua-hooks/ext/luajit/src/lj_char.o +0 -0
  198. data/lua-hooks/ext/luajit/src/lj_char_dyn.o +0 -0
  199. data/lua-hooks/ext/luajit/src/lj_clib.c +418 -0
  200. data/lua-hooks/ext/luajit/src/lj_clib.h +29 -0
  201. data/lua-hooks/ext/luajit/src/lj_clib.o +0 -0
  202. data/lua-hooks/ext/luajit/src/lj_clib_dyn.o +0 -0
  203. data/lua-hooks/ext/luajit/src/lj_cparse.c +1862 -0
  204. data/lua-hooks/ext/luajit/src/lj_cparse.h +65 -0
  205. data/lua-hooks/ext/luajit/src/lj_cparse.o +0 -0
  206. data/lua-hooks/ext/luajit/src/lj_cparse_dyn.o +0 -0
  207. data/lua-hooks/ext/luajit/src/lj_crecord.c +1834 -0
  208. data/lua-hooks/ext/luajit/src/lj_crecord.h +38 -0
  209. data/lua-hooks/ext/luajit/src/lj_crecord.o +0 -0
  210. data/lua-hooks/ext/luajit/src/lj_crecord_dyn.o +0 -0
  211. data/lua-hooks/ext/luajit/src/lj_ctype.c +635 -0
  212. data/lua-hooks/ext/luajit/src/lj_ctype.h +461 -0
  213. data/lua-hooks/ext/luajit/src/lj_ctype.o +0 -0
  214. data/lua-hooks/ext/luajit/src/lj_ctype_dyn.o +0 -0
  215. data/lua-hooks/ext/luajit/src/lj_debug.c +699 -0
  216. data/lua-hooks/ext/luajit/src/lj_debug.h +65 -0
  217. data/lua-hooks/ext/luajit/src/lj_debug.o +0 -0
  218. data/lua-hooks/ext/luajit/src/lj_debug_dyn.o +0 -0
  219. data/lua-hooks/ext/luajit/src/lj_def.h +365 -0
  220. data/lua-hooks/ext/luajit/src/lj_dispatch.c +557 -0
  221. data/lua-hooks/ext/luajit/src/lj_dispatch.h +138 -0
  222. data/lua-hooks/ext/luajit/src/lj_dispatch.o +0 -0
  223. data/lua-hooks/ext/luajit/src/lj_dispatch_dyn.o +0 -0
  224. data/lua-hooks/ext/luajit/src/lj_emit_arm.h +356 -0
  225. data/lua-hooks/ext/luajit/src/lj_emit_mips.h +211 -0
  226. data/lua-hooks/ext/luajit/src/lj_emit_ppc.h +238 -0
  227. data/lua-hooks/ext/luajit/src/lj_emit_x86.h +462 -0
  228. data/lua-hooks/ext/luajit/src/lj_err.c +794 -0
  229. data/lua-hooks/ext/luajit/src/lj_err.h +41 -0
  230. data/lua-hooks/ext/luajit/src/lj_err.o +0 -0
  231. data/lua-hooks/ext/luajit/src/lj_err_dyn.o +0 -0
  232. data/lua-hooks/ext/luajit/src/lj_errmsg.h +190 -0
  233. data/lua-hooks/ext/luajit/src/lj_ff.h +18 -0
  234. data/lua-hooks/ext/luajit/src/lj_ffdef.h +209 -0
  235. data/lua-hooks/ext/luajit/src/lj_ffrecord.c +1247 -0
  236. data/lua-hooks/ext/luajit/src/lj_ffrecord.h +24 -0
  237. data/lua-hooks/ext/luajit/src/lj_ffrecord.o +0 -0
  238. data/lua-hooks/ext/luajit/src/lj_ffrecord_dyn.o +0 -0
  239. data/lua-hooks/ext/luajit/src/lj_folddef.h +1138 -0
  240. data/lua-hooks/ext/luajit/src/lj_frame.h +259 -0
  241. data/lua-hooks/ext/luajit/src/lj_func.c +185 -0
  242. data/lua-hooks/ext/luajit/src/lj_func.h +24 -0
  243. data/lua-hooks/ext/luajit/src/lj_func.o +0 -0
  244. data/lua-hooks/ext/luajit/src/lj_func_dyn.o +0 -0
  245. data/lua-hooks/ext/luajit/src/lj_gc.c +845 -0
  246. data/lua-hooks/ext/luajit/src/lj_gc.h +134 -0
  247. data/lua-hooks/ext/luajit/src/lj_gc.o +0 -0
  248. data/lua-hooks/ext/luajit/src/lj_gc_dyn.o +0 -0
  249. data/lua-hooks/ext/luajit/src/lj_gdbjit.c +787 -0
  250. data/lua-hooks/ext/luajit/src/lj_gdbjit.h +22 -0
  251. data/lua-hooks/ext/luajit/src/lj_gdbjit.o +0 -0
  252. data/lua-hooks/ext/luajit/src/lj_gdbjit_dyn.o +0 -0
  253. data/lua-hooks/ext/luajit/src/lj_ir.c +505 -0
  254. data/lua-hooks/ext/luajit/src/lj_ir.h +577 -0
  255. data/lua-hooks/ext/luajit/src/lj_ir.o +0 -0
  256. data/lua-hooks/ext/luajit/src/lj_ir_dyn.o +0 -0
  257. data/lua-hooks/ext/luajit/src/lj_ircall.h +321 -0
  258. data/lua-hooks/ext/luajit/src/lj_iropt.h +161 -0
  259. data/lua-hooks/ext/luajit/src/lj_jit.h +440 -0
  260. data/lua-hooks/ext/luajit/src/lj_lex.c +482 -0
  261. data/lua-hooks/ext/luajit/src/lj_lex.h +86 -0
  262. data/lua-hooks/ext/luajit/src/lj_lex.o +0 -0
  263. data/lua-hooks/ext/luajit/src/lj_lex_dyn.o +0 -0
  264. data/lua-hooks/ext/luajit/src/lj_lib.c +303 -0
  265. data/lua-hooks/ext/luajit/src/lj_lib.h +115 -0
  266. data/lua-hooks/ext/luajit/src/lj_lib.o +0 -0
  267. data/lua-hooks/ext/luajit/src/lj_lib_dyn.o +0 -0
  268. data/lua-hooks/ext/luajit/src/lj_libdef.h +414 -0
  269. data/lua-hooks/ext/luajit/src/lj_load.c +168 -0
  270. data/lua-hooks/ext/luajit/src/lj_load.o +0 -0
  271. data/lua-hooks/ext/luajit/src/lj_load_dyn.o +0 -0
  272. data/lua-hooks/ext/luajit/src/lj_mcode.c +386 -0
  273. data/lua-hooks/ext/luajit/src/lj_mcode.h +30 -0
  274. data/lua-hooks/ext/luajit/src/lj_mcode.o +0 -0
  275. data/lua-hooks/ext/luajit/src/lj_mcode_dyn.o +0 -0
  276. data/lua-hooks/ext/luajit/src/lj_meta.c +477 -0
  277. data/lua-hooks/ext/luajit/src/lj_meta.h +38 -0
  278. data/lua-hooks/ext/luajit/src/lj_meta.o +0 -0
  279. data/lua-hooks/ext/luajit/src/lj_meta_dyn.o +0 -0
  280. data/lua-hooks/ext/luajit/src/lj_obj.c +50 -0
  281. data/lua-hooks/ext/luajit/src/lj_obj.h +976 -0
  282. data/lua-hooks/ext/luajit/src/lj_obj.o +0 -0
  283. data/lua-hooks/ext/luajit/src/lj_obj_dyn.o +0 -0
  284. data/lua-hooks/ext/luajit/src/lj_opt_dce.c +78 -0
  285. data/lua-hooks/ext/luajit/src/lj_opt_dce.o +0 -0
  286. data/lua-hooks/ext/luajit/src/lj_opt_dce_dyn.o +0 -0
  287. data/lua-hooks/ext/luajit/src/lj_opt_fold.c +2488 -0
  288. data/lua-hooks/ext/luajit/src/lj_opt_fold.o +0 -0
  289. data/lua-hooks/ext/luajit/src/lj_opt_fold_dyn.o +0 -0
  290. data/lua-hooks/ext/luajit/src/lj_opt_loop.c +449 -0
  291. data/lua-hooks/ext/luajit/src/lj_opt_loop.o +0 -0
  292. data/lua-hooks/ext/luajit/src/lj_opt_loop_dyn.o +0 -0
  293. data/lua-hooks/ext/luajit/src/lj_opt_mem.c +935 -0
  294. data/lua-hooks/ext/luajit/src/lj_opt_mem.o +0 -0
  295. data/lua-hooks/ext/luajit/src/lj_opt_mem_dyn.o +0 -0
  296. data/lua-hooks/ext/luajit/src/lj_opt_narrow.c +652 -0
  297. data/lua-hooks/ext/luajit/src/lj_opt_narrow.o +0 -0
  298. data/lua-hooks/ext/luajit/src/lj_opt_narrow_dyn.o +0 -0
  299. data/lua-hooks/ext/luajit/src/lj_opt_sink.c +245 -0
  300. data/lua-hooks/ext/luajit/src/lj_opt_sink.o +0 -0
  301. data/lua-hooks/ext/luajit/src/lj_opt_sink_dyn.o +0 -0
  302. data/lua-hooks/ext/luajit/src/lj_opt_split.c +856 -0
  303. data/lua-hooks/ext/luajit/src/lj_opt_split.o +0 -0
  304. data/lua-hooks/ext/luajit/src/lj_opt_split_dyn.o +0 -0
  305. data/lua-hooks/ext/luajit/src/lj_parse.c +2725 -0
  306. data/lua-hooks/ext/luajit/src/lj_parse.h +18 -0
  307. data/lua-hooks/ext/luajit/src/lj_parse.o +0 -0
  308. data/lua-hooks/ext/luajit/src/lj_parse_dyn.o +0 -0
  309. data/lua-hooks/ext/luajit/src/lj_profile.c +368 -0
  310. data/lua-hooks/ext/luajit/src/lj_profile.h +21 -0
  311. data/lua-hooks/ext/luajit/src/lj_profile.o +0 -0
  312. data/lua-hooks/ext/luajit/src/lj_profile_dyn.o +0 -0
  313. data/lua-hooks/ext/luajit/src/lj_recdef.h +270 -0
  314. data/lua-hooks/ext/luajit/src/lj_record.c +2554 -0
  315. data/lua-hooks/ext/luajit/src/lj_record.h +45 -0
  316. data/lua-hooks/ext/luajit/src/lj_record.o +0 -0
  317. data/lua-hooks/ext/luajit/src/lj_record_dyn.o +0 -0
  318. data/lua-hooks/ext/luajit/src/lj_snap.c +870 -0
  319. data/lua-hooks/ext/luajit/src/lj_snap.h +34 -0
  320. data/lua-hooks/ext/luajit/src/lj_snap.o +0 -0
  321. data/lua-hooks/ext/luajit/src/lj_snap_dyn.o +0 -0
  322. data/lua-hooks/ext/luajit/src/lj_state.c +300 -0
  323. data/lua-hooks/ext/luajit/src/lj_state.h +35 -0
  324. data/lua-hooks/ext/luajit/src/lj_state.o +0 -0
  325. data/lua-hooks/ext/luajit/src/lj_state_dyn.o +0 -0
  326. data/lua-hooks/ext/luajit/src/lj_str.c +197 -0
  327. data/lua-hooks/ext/luajit/src/lj_str.h +27 -0
  328. data/lua-hooks/ext/luajit/src/lj_str.o +0 -0
  329. data/lua-hooks/ext/luajit/src/lj_str_dyn.o +0 -0
  330. data/lua-hooks/ext/luajit/src/lj_strfmt.c +554 -0
  331. data/lua-hooks/ext/luajit/src/lj_strfmt.h +125 -0
  332. data/lua-hooks/ext/luajit/src/lj_strfmt.o +0 -0
  333. data/lua-hooks/ext/luajit/src/lj_strfmt_dyn.o +0 -0
  334. data/lua-hooks/ext/luajit/src/lj_strscan.c +547 -0
  335. data/lua-hooks/ext/luajit/src/lj_strscan.h +39 -0
  336. data/lua-hooks/ext/luajit/src/lj_strscan.o +0 -0
  337. data/lua-hooks/ext/luajit/src/lj_strscan_dyn.o +0 -0
  338. data/lua-hooks/ext/luajit/src/lj_tab.c +666 -0
  339. data/lua-hooks/ext/luajit/src/lj_tab.h +73 -0
  340. data/lua-hooks/ext/luajit/src/lj_tab.o +0 -0
  341. data/lua-hooks/ext/luajit/src/lj_tab_dyn.o +0 -0
  342. data/lua-hooks/ext/luajit/src/lj_target.h +164 -0
  343. data/lua-hooks/ext/luajit/src/lj_target_arm.h +270 -0
  344. data/lua-hooks/ext/luajit/src/lj_target_arm64.h +97 -0
  345. data/lua-hooks/ext/luajit/src/lj_target_mips.h +260 -0
  346. data/lua-hooks/ext/luajit/src/lj_target_ppc.h +280 -0
  347. data/lua-hooks/ext/luajit/src/lj_target_x86.h +345 -0
  348. data/lua-hooks/ext/luajit/src/lj_trace.c +859 -0
  349. data/lua-hooks/ext/luajit/src/lj_trace.h +54 -0
  350. data/lua-hooks/ext/luajit/src/lj_trace.o +0 -0
  351. data/lua-hooks/ext/luajit/src/lj_trace_dyn.o +0 -0
  352. data/lua-hooks/ext/luajit/src/lj_traceerr.h +63 -0
  353. data/lua-hooks/ext/luajit/src/lj_udata.c +34 -0
  354. data/lua-hooks/ext/luajit/src/lj_udata.h +14 -0
  355. data/lua-hooks/ext/luajit/src/lj_udata.o +0 -0
  356. data/lua-hooks/ext/luajit/src/lj_udata_dyn.o +0 -0
  357. data/lua-hooks/ext/luajit/src/lj_vm.S +2730 -0
  358. data/lua-hooks/ext/luajit/src/lj_vm.h +114 -0
  359. data/lua-hooks/ext/luajit/src/lj_vm.o +0 -0
  360. data/lua-hooks/ext/luajit/src/lj_vm_dyn.o +0 -0
  361. data/lua-hooks/ext/luajit/src/lj_vmevent.c +58 -0
  362. data/lua-hooks/ext/luajit/src/lj_vmevent.h +59 -0
  363. data/lua-hooks/ext/luajit/src/lj_vmevent.o +0 -0
  364. data/lua-hooks/ext/luajit/src/lj_vmevent_dyn.o +0 -0
  365. data/lua-hooks/ext/luajit/src/lj_vmmath.c +152 -0
  366. data/lua-hooks/ext/luajit/src/lj_vmmath.o +0 -0
  367. data/lua-hooks/ext/luajit/src/lj_vmmath_dyn.o +0 -0
  368. data/lua-hooks/ext/luajit/src/ljamalg.c +96 -0
  369. data/lua-hooks/ext/{lua → luajit/src}/lua.h +12 -7
  370. data/lua-hooks/ext/luajit/src/lua.hpp +9 -0
  371. data/lua-hooks/ext/luajit/src/luaconf.h +156 -0
  372. data/lua-hooks/ext/luajit/src/luajit +0 -0
  373. data/lua-hooks/ext/luajit/src/luajit.c +570 -0
  374. data/lua-hooks/ext/luajit/src/luajit.h +79 -0
  375. data/lua-hooks/ext/luajit/src/luajit.o +0 -0
  376. data/lua-hooks/ext/luajit/src/lualib.h +43 -0
  377. data/lua-hooks/ext/luajit/src/msvcbuild.bat +114 -0
  378. data/lua-hooks/ext/luajit/src/ps4build.bat +103 -0
  379. data/lua-hooks/ext/luajit/src/psvitabuild.bat +93 -0
  380. data/lua-hooks/ext/luajit/src/vm_arm.dasc +4585 -0
  381. data/lua-hooks/ext/luajit/src/vm_arm64.dasc +3764 -0
  382. data/lua-hooks/ext/luajit/src/vm_mips.dasc +4355 -0
  383. data/lua-hooks/ext/luajit/src/vm_ppc.dasc +5252 -0
  384. data/lua-hooks/ext/luajit/src/vm_x64.dasc +4902 -0
  385. data/lua-hooks/ext/luajit/src/vm_x86.dasc +5710 -0
  386. data/lua-hooks/ext/luajit/src/xb1build.bat +101 -0
  387. data/lua-hooks/ext/luajit/src/xedkbuild.bat +92 -0
  388. data/lua-hooks/ext/luautf8/lutf8lib.c +3 -3
  389. data/lua-hooks/lib/boot.lua +37 -2
  390. metadata +372 -69
  391. data/lua-hooks/ext/bitop/README +0 -22
  392. data/lua-hooks/ext/bitop/bit.c +0 -189
  393. data/lua-hooks/ext/extconf.rb +0 -38
  394. data/lua-hooks/ext/lua/COPYRIGHT +0 -34
  395. data/lua-hooks/ext/lua/lapi.c +0 -1087
  396. data/lua-hooks/ext/lua/lapi.h +0 -16
  397. data/lua-hooks/ext/lua/lauxlib.c +0 -652
  398. data/lua-hooks/ext/lua/lbaselib.c +0 -659
  399. data/lua-hooks/ext/lua/lcode.c +0 -831
  400. data/lua-hooks/ext/lua/lcode.h +0 -76
  401. data/lua-hooks/ext/lua/ldblib.c +0 -398
  402. data/lua-hooks/ext/lua/ldebug.c +0 -638
  403. data/lua-hooks/ext/lua/ldebug.h +0 -33
  404. data/lua-hooks/ext/lua/ldo.c +0 -519
  405. data/lua-hooks/ext/lua/ldo.h +0 -57
  406. data/lua-hooks/ext/lua/ldump.c +0 -164
  407. data/lua-hooks/ext/lua/lfunc.c +0 -174
  408. data/lua-hooks/ext/lua/lfunc.h +0 -34
  409. data/lua-hooks/ext/lua/lgc.c +0 -710
  410. data/lua-hooks/ext/lua/lgc.h +0 -110
  411. data/lua-hooks/ext/lua/linit.c +0 -38
  412. data/lua-hooks/ext/lua/liolib.c +0 -556
  413. data/lua-hooks/ext/lua/llex.c +0 -463
  414. data/lua-hooks/ext/lua/llex.h +0 -81
  415. data/lua-hooks/ext/lua/llimits.h +0 -128
  416. data/lua-hooks/ext/lua/lmathlib.c +0 -263
  417. data/lua-hooks/ext/lua/lmem.c +0 -86
  418. data/lua-hooks/ext/lua/lmem.h +0 -49
  419. data/lua-hooks/ext/lua/loadlib.c +0 -705
  420. data/lua-hooks/ext/lua/loadlib_rel.c +0 -760
  421. data/lua-hooks/ext/lua/lobject.c +0 -214
  422. data/lua-hooks/ext/lua/lobject.h +0 -381
  423. data/lua-hooks/ext/lua/lopcodes.c +0 -102
  424. data/lua-hooks/ext/lua/lopcodes.h +0 -268
  425. data/lua-hooks/ext/lua/loslib.c +0 -243
  426. data/lua-hooks/ext/lua/lparser.c +0 -1339
  427. data/lua-hooks/ext/lua/lparser.h +0 -82
  428. data/lua-hooks/ext/lua/lstate.c +0 -214
  429. data/lua-hooks/ext/lua/lstate.h +0 -169
  430. data/lua-hooks/ext/lua/lstring.c +0 -111
  431. data/lua-hooks/ext/lua/lstring.h +0 -31
  432. data/lua-hooks/ext/lua/lstrlib.c +0 -871
  433. data/lua-hooks/ext/lua/ltable.c +0 -588
  434. data/lua-hooks/ext/lua/ltable.h +0 -40
  435. data/lua-hooks/ext/lua/ltablib.c +0 -287
  436. data/lua-hooks/ext/lua/ltm.c +0 -75
  437. data/lua-hooks/ext/lua/ltm.h +0 -54
  438. data/lua-hooks/ext/lua/lua.c +0 -392
  439. data/lua-hooks/ext/lua/lua.def +0 -131
  440. data/lua-hooks/ext/lua/lua.rc +0 -28
  441. data/lua-hooks/ext/lua/lua_dll.rc +0 -26
  442. data/lua-hooks/ext/lua/luac.c +0 -200
  443. data/lua-hooks/ext/lua/luac.rc +0 -1
  444. data/lua-hooks/ext/lua/luaconf.h +0 -763
  445. data/lua-hooks/ext/lua/luaconf.h.in +0 -724
  446. data/lua-hooks/ext/lua/luaconf.h.orig +0 -763
  447. data/lua-hooks/ext/lua/lualib.h +0 -53
  448. data/lua-hooks/ext/lua/lundump.c +0 -227
  449. data/lua-hooks/ext/lua/lundump.h +0 -36
  450. data/lua-hooks/ext/lua/lvm.c +0 -767
  451. data/lua-hooks/ext/lua/lvm.h +0 -36
  452. data/lua-hooks/ext/lua/lzio.c +0 -82
  453. data/lua-hooks/ext/lua/lzio.h +0 -67
  454. data/lua-hooks/ext/lua/print.c +0 -227
@@ -0,0 +1,603 @@
1
+ <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd">
2
+ <html>
3
+ <head>
4
+ <title>FFI Tutorial</title>
5
+ <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
6
+ <meta name="Author" content="Mike Pall">
7
+ <meta name="Copyright" content="Copyright (C) 2005-2015, Mike Pall">
8
+ <meta name="Language" content="en">
9
+ <link rel="stylesheet" type="text/css" href="bluequad.css" media="screen">
10
+ <link rel="stylesheet" type="text/css" href="bluequad-print.css" media="print">
11
+ <style type="text/css">
12
+ table.idiomtable { font-size: 90%; line-height: 1.2; }
13
+ table.idiomtable tt { font-size: 100%; }
14
+ table.idiomtable td { vertical-align: top; }
15
+ tr.idiomhead td { font-weight: bold; }
16
+ td.idiomlua b { font-weight: normal; color: #2142bf; }
17
+ </style>
18
+ </head>
19
+ <body>
20
+ <div id="site">
21
+ <a href="http://luajit.org"><span>Lua<span id="logo">JIT</span></span></a>
22
+ </div>
23
+ <div id="head">
24
+ <h1>FFI Tutorial</h1>
25
+ </div>
26
+ <div id="nav">
27
+ <ul><li>
28
+ <a href="luajit.html">LuaJIT</a>
29
+ <ul><li>
30
+ <a href="http://luajit.org/download.html">Download <span class="ext">&raquo;</span></a>
31
+ </li><li>
32
+ <a href="install.html">Installation</a>
33
+ </li><li>
34
+ <a href="running.html">Running</a>
35
+ </li></ul>
36
+ </li><li>
37
+ <a href="extensions.html">Extensions</a>
38
+ <ul><li>
39
+ <a href="ext_ffi.html">FFI Library</a>
40
+ <ul><li>
41
+ <a class="current" href="ext_ffi_tutorial.html">FFI Tutorial</a>
42
+ </li><li>
43
+ <a href="ext_ffi_api.html">ffi.* API</a>
44
+ </li><li>
45
+ <a href="ext_ffi_semantics.html">FFI Semantics</a>
46
+ </li></ul>
47
+ </li><li>
48
+ <a href="ext_jit.html">jit.* Library</a>
49
+ </li><li>
50
+ <a href="ext_c_api.html">Lua/C API</a>
51
+ </li><li>
52
+ <a href="ext_profiler.html">Profiler</a>
53
+ </li></ul>
54
+ </li><li>
55
+ <a href="status.html">Status</a>
56
+ <ul><li>
57
+ <a href="changes.html">Changes</a>
58
+ </li></ul>
59
+ </li><li>
60
+ <a href="faq.html">FAQ</a>
61
+ </li><li>
62
+ <a href="http://luajit.org/performance.html">Performance <span class="ext">&raquo;</span></a>
63
+ </li><li>
64
+ <a href="http://wiki.luajit.org/">Wiki <span class="ext">&raquo;</span></a>
65
+ </li><li>
66
+ <a href="http://luajit.org/list.html">Mailing List <span class="ext">&raquo;</span></a>
67
+ </li></ul>
68
+ </div>
69
+ <div id="main">
70
+ <p>
71
+ This page is intended to give you an overview of the features of the FFI
72
+ library by presenting a few use cases and guidelines.
73
+ </p>
74
+ <p>
75
+ This page makes no attempt to explain all of the FFI library, though.
76
+ You'll want to have a look at the <a href="ext_ffi_api.html">ffi.* API
77
+ function reference</a> and the <a href="ext_ffi_semantics.html">FFI
78
+ semantics</a> to learn more.
79
+ </p>
80
+
81
+ <h2 id="load">Loading the FFI Library</h2>
82
+ <p>
83
+ The FFI library is built into LuaJIT by default, but it's not loaded
84
+ and initialized by default. The suggested way to use the FFI library
85
+ is to add the following to the start of every Lua file that needs one
86
+ of its functions:
87
+ </p>
88
+ <pre class="code">
89
+ local ffi = require("ffi")
90
+ </pre>
91
+ <p>
92
+ Please note this doesn't define an <tt>ffi</tt> variable in the table
93
+ of globals &mdash; you really need to use the local variable. The
94
+ <tt>require</tt> function ensures the library is only loaded once.
95
+ </p>
96
+ <p style="font-size: 8pt;">
97
+ Note: If you want to experiment with the FFI from the interactive prompt
98
+ of the command line executable, omit the <tt>local</tt>, as it doesn't
99
+ preserve local variables across lines.
100
+ </p>
101
+
102
+ <h2 id="sleep">Accessing Standard System Functions</h2>
103
+ <p>
104
+ The following code explains how to access standard system functions.
105
+ We slowly print two lines of dots by sleeping for 10&nbsp;milliseconds
106
+ after each dot:
107
+ </p>
108
+ <pre class="code mark">
109
+ <span class="codemark">&nbsp;
110
+ &#9312;
111
+
112
+
113
+
114
+
115
+
116
+ &#9313;
117
+ &#9314;
118
+ &#9315;
119
+
120
+
121
+
122
+ &#9316;
123
+
124
+
125
+
126
+
127
+
128
+ &#9317;</span>local ffi = require("ffi")
129
+ ffi.cdef[[
130
+ <span style="color:#00a000;">void Sleep(int ms);
131
+ int poll(struct pollfd *fds, unsigned long nfds, int timeout);</span>
132
+ ]]
133
+
134
+ local sleep
135
+ if ffi.os == "Windows" then
136
+ function sleep(s)
137
+ ffi.C.Sleep(s*1000)
138
+ end
139
+ else
140
+ function sleep(s)
141
+ ffi.C.poll(nil, 0, s*1000)
142
+ end
143
+ end
144
+
145
+ for i=1,160 do
146
+ io.write("."); io.flush()
147
+ sleep(0.01)
148
+ end
149
+ io.write("\n")
150
+ </pre>
151
+ <p>
152
+ Here's the step-by-step explanation:
153
+ </p>
154
+ <p>
155
+ <span class="mark">&#9312;</span> This defines the
156
+ C&nbsp;library functions we're going to use. The part inside the
157
+ double-brackets (in green) is just standard C&nbsp;syntax. You can
158
+ usually get this info from the C&nbsp;header files or the
159
+ documentation provided by each C&nbsp;library or C&nbsp;compiler.
160
+ </p>
161
+ <p>
162
+ <span class="mark">&#9313;</span> The difficulty we're
163
+ facing here, is that there are different standards to choose from.
164
+ Windows has a simple <tt>Sleep()</tt> function. On other systems there
165
+ are a variety of functions available to achieve sub-second sleeps, but
166
+ with no clear consensus. Thankfully <tt>poll()</tt> can be used for
167
+ this task, too, and it's present on most non-Windows systems. The
168
+ check for <tt>ffi.os</tt> makes sure we use the Windows-specific
169
+ function only on Windows systems.
170
+ </p>
171
+ <p>
172
+ <span class="mark">&#9314;</span> Here we're wrapping the
173
+ call to the C&nbsp;function in a Lua function. This isn't strictly
174
+ necessary, but it's helpful to deal with system-specific issues only
175
+ in one part of the code. The way we're wrapping it ensures the check
176
+ for the OS is only done during initialization and not for every call.
177
+ </p>
178
+ <p>
179
+ <span class="mark">&#9315;</span> A more subtle point is
180
+ that we defined our <tt>sleep()</tt> function (for the sake of this
181
+ example) as taking the number of seconds, but accepting fractional
182
+ seconds. Multiplying this by 1000 gets us milliseconds, but that still
183
+ leaves it a Lua number, which is a floating-point value. Alas, the
184
+ <tt>Sleep()</tt> function only accepts an integer value. Luckily for
185
+ us, the FFI library automatically performs the conversion when calling
186
+ the function (truncating the FP value towards zero, like in C).
187
+ </p>
188
+ <p style="font-size: 8pt;">
189
+ Some readers will notice that <tt>Sleep()</tt> is part of
190
+ <tt>KERNEL32.DLL</tt> and is also a <tt>stdcall</tt> function. So how
191
+ can this possibly work? The FFI library provides the <tt>ffi.C</tt>
192
+ default C&nbsp;library namespace, which allows calling functions from
193
+ the default set of libraries, like a C&nbsp;compiler would. Also, the
194
+ FFI library automatically detects <tt>stdcall</tt> functions, so you
195
+ don't need to declare them as such.
196
+ </p>
197
+ <p>
198
+ <span class="mark">&#9316;</span> The <tt>poll()</tt>
199
+ function takes a couple more arguments we're not going to use. You can
200
+ simply use <tt>nil</tt> to pass a <tt>NULL</tt> pointer and <tt>0</tt>
201
+ for the <tt>nfds</tt> parameter. Please note that the
202
+ number&nbsp;<tt>0</tt> <em>does not convert to a pointer value</em>,
203
+ unlike in C++. You really have to pass pointers to pointer arguments
204
+ and numbers to number arguments.
205
+ </p>
206
+ <p style="font-size: 8pt;">
207
+ The page on <a href="ext_ffi_semantics.html">FFI semantics</a> has all
208
+ of the gory details about
209
+ <a href="ext_ffi_semantics.html#convert">conversions between Lua
210
+ objects and C&nbsp;types</a>. For the most part you don't have to deal
211
+ with this, as it's performed automatically and it's carefully designed
212
+ to bridge the semantic differences between Lua and C.
213
+ </p>
214
+ <p>
215
+ <span class="mark">&#9317;</span> Now that we have defined
216
+ our own <tt>sleep()</tt> function, we can just call it from plain Lua
217
+ code. That wasn't so bad, huh? Turning these boring animated dots into
218
+ a fascinating best-selling game is left as an exercise for the reader.
219
+ :-)
220
+ </p>
221
+
222
+ <h2 id="zlib">Accessing the zlib Compression Library</h2>
223
+ <p>
224
+ The following code shows how to access the <a
225
+ href="http://zlib.net/">zlib</a> compression library from Lua code.
226
+ We'll define two convenience wrapper functions that take a string and
227
+ compress or uncompress it to another string:
228
+ </p>
229
+ <pre class="code mark">
230
+ <span class="codemark">&nbsp;
231
+ &#9312;
232
+
233
+
234
+
235
+
236
+
237
+
238
+ &#9313;
239
+
240
+
241
+ &#9314;
242
+
243
+ &#9315;
244
+
245
+
246
+ &#9316;
247
+
248
+
249
+ &#9317;
250
+
251
+
252
+
253
+
254
+
255
+
256
+
257
+ &#9318;</span>local ffi = require("ffi")
258
+ ffi.cdef[[
259
+ <span style="color:#00a000;">unsigned long compressBound(unsigned long sourceLen);
260
+ int compress2(uint8_t *dest, unsigned long *destLen,
261
+ const uint8_t *source, unsigned long sourceLen, int level);
262
+ int uncompress(uint8_t *dest, unsigned long *destLen,
263
+ const uint8_t *source, unsigned long sourceLen);</span>
264
+ ]]
265
+ local zlib = ffi.load(ffi.os == "Windows" and "zlib1" or "z")
266
+
267
+ local function compress(txt)
268
+ local n = zlib.compressBound(#txt)
269
+ local buf = ffi.new("uint8_t[?]", n)
270
+ local buflen = ffi.new("unsigned long[1]", n)
271
+ local res = zlib.compress2(buf, buflen, txt, #txt, 9)
272
+ assert(res == 0)
273
+ return ffi.string(buf, buflen[0])
274
+ end
275
+
276
+ local function uncompress(comp, n)
277
+ local buf = ffi.new("uint8_t[?]", n)
278
+ local buflen = ffi.new("unsigned long[1]", n)
279
+ local res = zlib.uncompress(buf, buflen, comp, #comp)
280
+ assert(res == 0)
281
+ return ffi.string(buf, buflen[0])
282
+ end
283
+
284
+ -- Simple test code.
285
+ local txt = string.rep("abcd", 1000)
286
+ print("Uncompressed size: ", #txt)
287
+ local c = compress(txt)
288
+ print("Compressed size: ", #c)
289
+ local txt2 = uncompress(c, #txt)
290
+ assert(txt2 == txt)
291
+ </pre>
292
+ <p>
293
+ Here's the step-by-step explanation:
294
+ </p>
295
+ <p>
296
+ <span class="mark">&#9312;</span> This defines some of the
297
+ C&nbsp;functions provided by zlib. For the sake of this example, some
298
+ type indirections have been reduced and it uses the pre-defined
299
+ fixed-size integer types, while still adhering to the zlib API/ABI.
300
+ </p>
301
+ <p>
302
+ <span class="mark">&#9313;</span> This loads the zlib shared
303
+ library. On POSIX systems it's named <tt>libz.so</tt> and usually
304
+ comes pre-installed. Since <tt>ffi.load()</tt> automatically adds any
305
+ missing standard prefixes/suffixes, we can simply load the
306
+ <tt>"z"</tt> library. On Windows it's named <tt>zlib1.dll</tt> and
307
+ you'll have to download it first from the
308
+ <a href="http://zlib.net/"><span class="ext">&raquo;</span>&nbsp;zlib site</a>. The check for
309
+ <tt>ffi.os</tt> makes sure we pass the right name to
310
+ <tt>ffi.load()</tt>.
311
+ </p>
312
+ <p>
313
+ <span class="mark">&#9314;</span> First, the maximum size of
314
+ the compression buffer is obtained by calling the
315
+ <tt>zlib.compressBound</tt> function with the length of the
316
+ uncompressed string. The next line allocates a byte buffer of this
317
+ size. The <tt>[?]</tt> in the type specification indicates a
318
+ variable-length array (VLA). The actual number of elements of this
319
+ array is given as the 2nd argument to <tt>ffi.new()</tt>.
320
+ </p>
321
+ <p>
322
+ <span class="mark">&#9315;</span> This may look strange at
323
+ first, but have a look at the declaration of the <tt>compress2</tt>
324
+ function from zlib: the destination length is defined as a pointer!
325
+ This is because you pass in the maximum buffer size and get back the
326
+ actual length that was used.
327
+ </p>
328
+ <p>
329
+ In C you'd pass in the address of a local variable
330
+ (<tt>&amp;buflen</tt>). But since there's no address-of operator in
331
+ Lua, we'll just pass in a one-element array. Conveniently it can be
332
+ initialized with the maximum buffer size in one step. Calling the
333
+ actual <tt>zlib.compress2</tt> function is then straightforward.
334
+ </p>
335
+ <p>
336
+ <span class="mark">&#9316;</span> We want to return the
337
+ compressed data as a Lua string, so we'll use <tt>ffi.string()</tt>.
338
+ It needs a pointer to the start of the data and the actual length. The
339
+ length has been returned in the <tt>buflen</tt> array, so we'll just
340
+ get it from there.
341
+ </p>
342
+ <p style="font-size: 8pt;">
343
+ Note that since the function returns now, the <tt>buf</tt> and
344
+ <tt>buflen</tt> variables will eventually be garbage collected. This
345
+ is fine, because <tt>ffi.string()</tt> has copied the contents to a
346
+ newly created (interned) Lua string. If you plan to call this function
347
+ lots of times, consider reusing the buffers and/or handing back the
348
+ results in buffers instead of strings. This will reduce the overhead
349
+ for garbage collection and string interning.
350
+ </p>
351
+ <p>
352
+ <span class="mark">&#9317;</span> The <tt>uncompress</tt>
353
+ functions does the exact opposite of the <tt>compress</tt> function.
354
+ The compressed data doesn't include the size of the original string,
355
+ so this needs to be passed in. Otherwise no surprises here.
356
+ </p>
357
+ <p>
358
+ <span class="mark">&#9318;</span> The code, that makes use
359
+ of the functions we just defined, is just plain Lua code. It doesn't
360
+ need to know anything about the LuaJIT FFI &mdash; the convenience
361
+ wrapper functions completely hide it.
362
+ </p>
363
+ <p>
364
+ One major advantage of the LuaJIT FFI is that you are now able to
365
+ write those wrappers <em>in Lua</em>. And at a fraction of the time it
366
+ would cost you to create an extra C&nbsp;module using the Lua/C API.
367
+ Many of the simpler C&nbsp;functions can probably be used directly
368
+ from your Lua code, without any wrappers.
369
+ </p>
370
+ <p style="font-size: 8pt;">
371
+ Side note: the zlib API uses the <tt>long</tt> type for passing
372
+ lengths and sizes around. But all those zlib functions actually only
373
+ deal with 32&nbsp;bit values. This is an unfortunate choice for a
374
+ public API, but may be explained by zlib's history &mdash; we'll just
375
+ have to deal with it.
376
+ </p>
377
+ <p style="font-size: 8pt;">
378
+ First, you should know that a <tt>long</tt> is a 64&nbsp;bit type e.g.
379
+ on POSIX/x64 systems, but a 32&nbsp;bit type on Windows/x64 and on
380
+ 32&nbsp;bit systems. Thus a <tt>long</tt> result can be either a plain
381
+ Lua number or a boxed 64&nbsp;bit integer cdata object, depending on
382
+ the target system.
383
+ </p>
384
+ <p style="font-size: 8pt;">
385
+ Ok, so the <tt>ffi.*</tt> functions generally accept cdata objects
386
+ wherever you'd want to use a number. That's why we get a away with
387
+ passing <tt>n</tt> to <tt>ffi.string()</tt> above. But other Lua
388
+ library functions or modules don't know how to deal with this. So for
389
+ maximum portability one needs to use <tt>tonumber()</tt> on returned
390
+ <tt>long</tt> results before passing them on. Otherwise the
391
+ application might work on some systems, but would fail in a POSIX/x64
392
+ environment.
393
+ </p>
394
+
395
+ <h2 id="metatype">Defining Metamethods for a C&nbsp;Type</h2>
396
+ <p>
397
+ The following code explains how to define metamethods for a C type.
398
+ We define a simple point type and add some operations to it:
399
+ </p>
400
+ <pre class="code mark">
401
+ <span class="codemark">&nbsp;
402
+ &#9312;
403
+
404
+
405
+
406
+ &#9313;
407
+
408
+ &#9314;
409
+
410
+ &#9315;
411
+
412
+
413
+
414
+ &#9316;
415
+
416
+ &#9317;</span>local ffi = require("ffi")
417
+ ffi.cdef[[
418
+ <span style="color:#00a000;">typedef struct { double x, y; } point_t;</span>
419
+ ]]
420
+
421
+ local point
422
+ local mt = {
423
+ __add = function(a, b) return point(a.x+b.x, a.y+b.y) end,
424
+ __len = function(a) return math.sqrt(a.x*a.x + a.y*a.y) end,
425
+ __index = {
426
+ area = function(a) return a.x*a.x + a.y*a.y end,
427
+ },
428
+ }
429
+ point = ffi.metatype("point_t", mt)
430
+
431
+ local a = point(3, 4)
432
+ print(a.x, a.y) --> 3 4
433
+ print(#a) --> 5
434
+ print(a:area()) --> 25
435
+ local b = a + point(0.5, 8)
436
+ print(#b) --> 12.5
437
+ </pre>
438
+ <p>
439
+ Here's the step-by-step explanation:
440
+ </p>
441
+ <p>
442
+ <span class="mark">&#9312;</span> This defines the C&nbsp;type for a
443
+ two-dimensional point object.
444
+ </p>
445
+ <p>
446
+ <span class="mark">&#9313;</span> We have to declare the variable
447
+ holding the point constructor first, because it's used inside of a
448
+ metamethod.
449
+ </p>
450
+ <p>
451
+ <span class="mark">&#9314;</span> Let's define an <tt>__add</tt>
452
+ metamethod which adds the coordinates of two points and creates a new
453
+ point object. For simplicity, this function assumes that both arguments
454
+ are points. But it could be any mix of objects, if at least one operand
455
+ is of the required type (e.g. adding a point plus a number or vice
456
+ versa). Our <tt>__len</tt> metamethod returns the distance of a point to
457
+ the origin.
458
+ </p>
459
+ <p>
460
+ <span class="mark">&#9315;</span> If we run out of operators, we can
461
+ define named methods, too. Here the <tt>__index</tt> table defines an
462
+ <tt>area</tt> function. For custom indexing needs, one might want to
463
+ define <tt>__index</tt> and <tt>__newindex</tt> <em>functions</em> instead.
464
+ </p>
465
+ <p>
466
+ <span class="mark">&#9316;</span> This associates the metamethods with
467
+ our C&nbsp;type. This only needs to be done once. For convenience, a
468
+ constructor is returned by
469
+ <a href="ext_ffi_api.html#ffi_metatype"><tt>ffi.metatype()</tt></a>.
470
+ We're not required to use it, though. The original C&nbsp;type can still
471
+ be used e.g. to create an array of points. The metamethods automatically
472
+ apply to any and all uses of this type.
473
+ </p>
474
+ <p>
475
+ Please note that the association with a metatable is permanent and
476
+ <b>the metatable must not be modified afterwards!</b> Ditto for the
477
+ <tt>__index</tt> table.
478
+ </p>
479
+ <p>
480
+ <span class="mark">&#9317;</span> Here are some simple usage examples
481
+ for the point type and their expected results. The pre-defined
482
+ operations (such as <tt>a.x</tt>) can be freely mixed with the newly
483
+ defined metamethods. Note that <tt>area</tt> is a method and must be
484
+ called with the Lua syntax for methods: <tt>a:area()</tt>, not
485
+ <tt>a.area()</tt>.
486
+ </p>
487
+ <p>
488
+ The C&nbsp;type metamethod mechanism is most useful when used in
489
+ conjunction with C&nbsp;libraries that are written in an object-oriented
490
+ style. Creators return a pointer to a new instance and methods take an
491
+ instance pointer as the first argument. Sometimes you can just point
492
+ <tt>__index</tt> to the library namespace and <tt>__gc</tt> to the
493
+ destructor and you're done. But often enough you'll want to add
494
+ convenience wrappers, e.g. to return actual Lua strings or when
495
+ returning multiple values.
496
+ </p>
497
+ <p>
498
+ Some C libraries only declare instance pointers as an opaque
499
+ <tt>void&nbsp;*</tt> type. In this case you can use a fake type for all
500
+ declarations, e.g. a pointer to a named (incomplete) struct will do:
501
+ <tt>typedef struct foo_type *foo_handle</tt>. The C&nbsp;side doesn't
502
+ know what you declare with the LuaJIT FFI, but as long as the underlying
503
+ types are compatible, everything still works.
504
+ </p>
505
+
506
+ <h2 id="idioms">Translating C&nbsp;Idioms</h2>
507
+ <p>
508
+ Here's a list of common C&nbsp;idioms and their translation to the
509
+ LuaJIT FFI:
510
+ </p>
511
+ <table class="idiomtable">
512
+ <tr class="idiomhead">
513
+ <td class="idiomdesc">Idiom</td>
514
+ <td class="idiomc">C&nbsp;code</td>
515
+ <td class="idiomlua">Lua code</td>
516
+ </tr>
517
+ <tr class="odd separate">
518
+ <td class="idiomdesc">Pointer dereference<br><tt>int *p;</tt></td><td class="idiomc"><tt>x = *p;<br>*p = y;</tt></td><td class="idiomlua"><tt>x = <b>p[0]</b><br><b>p[0]</b> = y</tt></td></tr>
519
+ <tr class="even">
520
+ <td class="idiomdesc">Pointer indexing<br><tt>int i, *p;</tt></td><td class="idiomc"><tt>x = p[i];<br>p[i+1] = y;</tt></td><td class="idiomlua"><tt>x = p[i]<br>p[i+1] = y</tt></td></tr>
521
+ <tr class="odd">
522
+ <td class="idiomdesc">Array indexing<br><tt>int i, a[];</tt></td><td class="idiomc"><tt>x = a[i];<br>a[i+1] = y;</tt></td><td class="idiomlua"><tt>x = a[i]<br>a[i+1] = y</tt></td></tr>
523
+ <tr class="even separate">
524
+ <td class="idiomdesc"><tt>struct</tt>/<tt>union</tt> dereference<br><tt>struct foo s;</tt></td><td class="idiomc"><tt>x = s.field;<br>s.field = y;</tt></td><td class="idiomlua"><tt>x = s.field<br>s.field = y</tt></td></tr>
525
+ <tr class="odd">
526
+ <td class="idiomdesc"><tt>struct</tt>/<tt>union</tt> pointer deref.<br><tt>struct foo *sp;</tt></td><td class="idiomc"><tt>x = sp->field;<br>sp->field = y;</tt></td><td class="idiomlua"><tt>x = <b>s.field</b><br><b>s.field</b> = y</tt></td></tr>
527
+ <tr class="even separate">
528
+ <td class="idiomdesc">Pointer arithmetic<br><tt>int i, *p;</tt></td><td class="idiomc"><tt>x = p + i;<br>y = p - i;</tt></td><td class="idiomlua"><tt>x = p + i<br>y = p - i</tt></td></tr>
529
+ <tr class="odd">
530
+ <td class="idiomdesc">Pointer difference<br><tt>int *p1, *p2;</tt></td><td class="idiomc"><tt>x = p1 - p2;</tt></td><td class="idiomlua"><tt>x = p1 - p2</tt></td></tr>
531
+ <tr class="even">
532
+ <td class="idiomdesc">Array element pointer<br><tt>int i, a[];</tt></td><td class="idiomc"><tt>x = &amp;a[i];</tt></td><td class="idiomlua"><tt>x = <b>a+i</b></tt></td></tr>
533
+ <tr class="odd">
534
+ <td class="idiomdesc">Cast pointer to address<br><tt>int *p;</tt></td><td class="idiomc"><tt>x = (intptr_t)p;</tt></td><td class="idiomlua"><tt>x = <b>tonumber(<br>&nbsp;ffi.cast("intptr_t",<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;p))</b></tt></td></tr>
535
+ <tr class="even separate">
536
+ <td class="idiomdesc">Functions with outargs<br><tt>void foo(int *inoutlen);</tt></td><td class="idiomc"><tt>int len = x;<br>foo(&amp;len);<br>y = len;</tt></td><td class="idiomlua"><tt><b>local len =<br>&nbsp;&nbsp;ffi.new("int[1]", x)<br>foo(len)<br>y = len[0]</b></tt></td></tr>
537
+ <tr class="odd">
538
+ <td class="idiomdesc"><a href="ext_ffi_semantics.html#convert_vararg">Vararg conversions</a><br><tt>int printf(char *fmt, ...);</tt></td><td class="idiomc"><tt>printf("%g", 1.0);<br>printf("%d", 1);<br>&nbsp;</tt></td><td class="idiomlua"><tt>printf("%g", 1);<br>printf("%d",<br>&nbsp;&nbsp;<b>ffi.new("int", 1)</b>)</tt></td></tr>
539
+ </table>
540
+
541
+ <h2 id="cache">To Cache or Not to Cache</h2>
542
+ <p>
543
+ It's a common Lua idiom to cache library functions in local variables
544
+ or upvalues, e.g.:
545
+ </p>
546
+ <pre class="code">
547
+ local byte, char = string.byte, string.char
548
+ local function foo(x)
549
+ return char(byte(x)+1)
550
+ end
551
+ </pre>
552
+ <p>
553
+ This replaces several hash-table lookups with a (faster) direct use of
554
+ a local or an upvalue. This is less important with LuaJIT, since the
555
+ JIT compiler optimizes hash-table lookups a lot and is even able to
556
+ hoist most of them out of the inner loops. It can't eliminate
557
+ <em>all</em> of them, though, and it saves some typing for often-used
558
+ functions. So there's still a place for this, even with LuaJIT.
559
+ </p>
560
+ <p>
561
+ The situation is a bit different with C&nbsp;function calls via the
562
+ FFI library. The JIT compiler has special logic to eliminate <em>all
563
+ of the lookup overhead</em> for functions resolved from a
564
+ <a href="ext_ffi_semantics.html#clib">C&nbsp;library namespace</a>!
565
+ Thus it's not helpful and actually counter-productive to cache
566
+ individual C&nbsp;functions like this:
567
+ </p>
568
+ <pre class="code">
569
+ local <b>funca</b>, <b>funcb</b> = ffi.C.funca, ffi.C.funcb -- <span style="color:#c00000;">Not helpful!</span>
570
+ local function foo(x, n)
571
+ for i=1,n do <b>funcb</b>(<b>funca</b>(x, i), 1) end
572
+ end
573
+ </pre>
574
+ <p>
575
+ This turns them into indirect calls and generates bigger and slower
576
+ machine code. Instead you'll want to cache the namespace itself and
577
+ rely on the JIT compiler to eliminate the lookups:
578
+ </p>
579
+ <pre class="code">
580
+ local <b>C</b> = ffi.C -- <span style="color:#00a000;">Instead use this!</span>
581
+ local function foo(x, n)
582
+ for i=1,n do <b>C.funcb</b>(<b>C.funca</b>(x, i), 1) end
583
+ end
584
+ </pre>
585
+ <p>
586
+ This generates both shorter and faster code. So <b>don't cache
587
+ C&nbsp;functions</b>, but <b>do</b> cache namespaces! Most often the
588
+ namespace is already in a local variable at an outer scope, e.g. from
589
+ <tt>local&nbsp;lib&nbsp;=&nbsp;ffi.load(...)</tt>. Note that copying
590
+ it to a local variable in the function scope is unnecessary.
591
+ </p>
592
+ <br class="flush">
593
+ </div>
594
+ <div id="foot">
595
+ <hr class="hide">
596
+ Copyright &copy; 2005-2015 Mike Pall
597
+ <span class="noprint">
598
+ &middot;
599
+ <a href="contact.html">Contact</a>
600
+ </span>
601
+ </div>
602
+ </body>
603
+ </html>