heroku-tokyotyrant 0.4

Sign up to get free protection for your applications and to get access to all the features.
Files changed (340) hide show
  1. data/COPYING +504 -0
  2. data/README.rdoc +231 -0
  3. data/Rakefile +72 -0
  4. data/benchmarks/balancer.rb +101 -0
  5. data/benchmarks/bulk_db.rb +74 -0
  6. data/benchmarks/bulk_table.rb +87 -0
  7. data/benchmarks/db.rb +114 -0
  8. data/benchmarks/table.rb +161 -0
  9. data/ext/extconf.rb +43 -0
  10. data/ext/tokyo/bin/tcamgr +0 -0
  11. data/ext/tokyo/bin/tcamttest +0 -0
  12. data/ext/tokyo/bin/tcatest +0 -0
  13. data/ext/tokyo/bin/tcbmgr +0 -0
  14. data/ext/tokyo/bin/tcbmttest +0 -0
  15. data/ext/tokyo/bin/tcbtest +0 -0
  16. data/ext/tokyo/bin/tcfmgr +0 -0
  17. data/ext/tokyo/bin/tcfmttest +0 -0
  18. data/ext/tokyo/bin/tcftest +0 -0
  19. data/ext/tokyo/bin/tchmgr +0 -0
  20. data/ext/tokyo/bin/tchmttest +0 -0
  21. data/ext/tokyo/bin/tchtest +0 -0
  22. data/ext/tokyo/bin/tcrmgr +0 -0
  23. data/ext/tokyo/bin/tcrmttest +0 -0
  24. data/ext/tokyo/bin/tcrtest +0 -0
  25. data/ext/tokyo/bin/tctmgr +0 -0
  26. data/ext/tokyo/bin/tctmttest +0 -0
  27. data/ext/tokyo/bin/tcttest +0 -0
  28. data/ext/tokyo/bin/tcucodec +0 -0
  29. data/ext/tokyo/bin/tcumttest +0 -0
  30. data/ext/tokyo/bin/tcutest +0 -0
  31. data/ext/tokyo/bin/ttserver +0 -0
  32. data/ext/tokyo/bin/ttulmgr +0 -0
  33. data/ext/tokyo/bin/ttultest +0 -0
  34. data/ext/tokyo/include/tcadb.h +548 -0
  35. data/ext/tokyo/include/tcbdb.h +1101 -0
  36. data/ext/tokyo/include/tcfdb.h +858 -0
  37. data/ext/tokyo/include/tchdb.h +871 -0
  38. data/ext/tokyo/include/tcrdb.h +801 -0
  39. data/ext/tokyo/include/tctdb.h +1086 -0
  40. data/ext/tokyo/include/tculog.h +392 -0
  41. data/ext/tokyo/include/tcutil.h +4184 -0
  42. data/ext/tokyo/include/ttutil.h +494 -0
  43. data/ext/tokyo/lib/libtokyocabinet.9.4.0.dylib +0 -0
  44. data/ext/tokyo/lib/libtokyocabinet.9.dylib +0 -0
  45. data/ext/tokyo/lib/libtokyocabinet.a +0 -0
  46. data/ext/tokyo/lib/libtokyocabinet.dylib +0 -0
  47. data/ext/tokyo/lib/libtokyotyrant.3.22.0.dylib +0 -0
  48. data/ext/tokyo/lib/libtokyotyrant.3.dylib +0 -0
  49. data/ext/tokyo/lib/libtokyotyrant.a +0 -0
  50. data/ext/tokyo/lib/libtokyotyrant.dylib +0 -0
  51. data/ext/tokyo/lib/pkgconfig/tokyocabinet.pc +14 -0
  52. data/ext/tokyo/lib/pkgconfig/tokyotyrant.pc +14 -0
  53. data/ext/tokyo/lib/ttskeldir.bundle +0 -0
  54. data/ext/tokyo/lib/ttskelmock.bundle +0 -0
  55. data/ext/tokyo/lib/ttskelnull.bundle +0 -0
  56. data/ext/tokyo/lib/ttskelproxy.bundle +0 -0
  57. data/ext/tokyo/libexec/tcawmgr.cgi +0 -0
  58. data/ext/tokyo/sbin/ttservctl +163 -0
  59. data/ext/tokyo/share/man/man1/tcamgr.1 +97 -0
  60. data/ext/tokyo/share/man/man1/tcamttest.1 +35 -0
  61. data/ext/tokyo/share/man/man1/tcatest.1 +55 -0
  62. data/ext/tokyo/share/man/man1/tcbmgr.1 +125 -0
  63. data/ext/tokyo/share/man/man1/tcbmttest.1 +81 -0
  64. data/ext/tokyo/share/man/man1/tcbtest.1 +107 -0
  65. data/ext/tokyo/share/man/man1/tcfmgr.1 +98 -0
  66. data/ext/tokyo/share/man/man1/tcfmttest.1 +62 -0
  67. data/ext/tokyo/share/man/man1/tcftest.1 +73 -0
  68. data/ext/tokyo/share/man/man1/tchmgr.1 +110 -0
  69. data/ext/tokyo/share/man/man1/tchmttest.1 +85 -0
  70. data/ext/tokyo/share/man/man1/tchtest.1 +95 -0
  71. data/ext/tokyo/share/man/man1/tcrmgr.1 +164 -0
  72. data/ext/tokyo/share/man/man1/tcrmttest.1 +55 -0
  73. data/ext/tokyo/share/man/man1/tcrtest.1 +89 -0
  74. data/ext/tokyo/share/man/man1/tctmgr.1 +140 -0
  75. data/ext/tokyo/share/man/man1/tctmttest.1 +92 -0
  76. data/ext/tokyo/share/man/man1/tcttest.1 +105 -0
  77. data/ext/tokyo/share/man/man1/tcucodec.1 +162 -0
  78. data/ext/tokyo/share/man/man1/tcumttest.1 +41 -0
  79. data/ext/tokyo/share/man/man1/tcutest.1 +81 -0
  80. data/ext/tokyo/share/man/man1/ttserver.1 +84 -0
  81. data/ext/tokyo/share/man/man1/ttulmgr.1 +40 -0
  82. data/ext/tokyo/share/man/man1/ttultest.1 +16 -0
  83. data/ext/tokyo/share/man/man3/tcadb.3 +676 -0
  84. data/ext/tokyo/share/man/man3/tcbdb.3 +1355 -0
  85. data/ext/tokyo/share/man/man3/tcfdb.3 +975 -0
  86. data/ext/tokyo/share/man/man3/tchdb.3 +898 -0
  87. data/ext/tokyo/share/man/man3/tclist.3 +1 -0
  88. data/ext/tokyo/share/man/man3/tcmap.3 +1 -0
  89. data/ext/tokyo/share/man/man3/tcmdb.3 +1 -0
  90. data/ext/tokyo/share/man/man3/tcmpool.3 +1 -0
  91. data/ext/tokyo/share/man/man3/tcrdb.3 +1309 -0
  92. data/ext/tokyo/share/man/man3/tctdb.3 +1110 -0
  93. data/ext/tokyo/share/man/man3/tctree.3 +1 -0
  94. data/ext/tokyo/share/man/man3/tculog.3 +15 -0
  95. data/ext/tokyo/share/man/man3/tcutil.3 +4518 -0
  96. data/ext/tokyo/share/man/man3/tcxstr.3 +1 -0
  97. data/ext/tokyo/share/man/man3/tokyocabinet.3 +132 -0
  98. data/ext/tokyo/share/man/man3/ttutil.3 +14 -0
  99. data/ext/tokyo/share/man/man8/ttservctl.8 +37 -0
  100. data/ext/tokyo/share/tokyocabinet/COPYING +504 -0
  101. data/ext/tokyo/share/tokyocabinet/ChangeLog +1252 -0
  102. data/ext/tokyo/share/tokyocabinet/THANKS +12 -0
  103. data/ext/tokyo/share/tokyocabinet/doc/benchmark.pdf +0 -0
  104. data/ext/tokyo/share/tokyocabinet/doc/common.css +211 -0
  105. data/ext/tokyo/share/tokyocabinet/doc/icon16.png +0 -0
  106. data/ext/tokyo/share/tokyocabinet/doc/index.html +156 -0
  107. data/ext/tokyo/share/tokyocabinet/doc/index.ja.html +197 -0
  108. data/ext/tokyo/share/tokyocabinet/doc/logo-ja.png +0 -0
  109. data/ext/tokyo/share/tokyocabinet/doc/logo.png +0 -0
  110. data/ext/tokyo/share/tokyocabinet/doc/spex-en.html +7145 -0
  111. data/ext/tokyo/share/tokyocabinet/doc/spex-ja.html +7476 -0
  112. data/ext/tokyo/share/tokyocabinet/doc/tokyoproducts.pdf +0 -0
  113. data/ext/tokyo/share/tokyocabinet/doc/tokyoproducts.ppt +0 -0
  114. data/ext/tokyo/share/tokyotyrant/COPYING +504 -0
  115. data/ext/tokyo/share/tokyotyrant/ChangeLog +578 -0
  116. data/ext/tokyo/share/tokyotyrant/THANKS +15 -0
  117. data/ext/tokyo/share/tokyotyrant/doc/common.css +211 -0
  118. data/ext/tokyo/share/tokyotyrant/doc/index.html +79 -0
  119. data/ext/tokyo/share/tokyotyrant/doc/spex.html +2264 -0
  120. data/ext/tokyo/share/tokyotyrant/ext/mapreduce.lua +57 -0
  121. data/ext/tokyo/share/tokyotyrant/ext/queue.lua +55 -0
  122. data/ext/tokyo/share/tokyotyrant/ext/senatus.lua +532 -0
  123. data/ext/tokyo/share/tokyotyrant/ext/usherette.lua +438 -0
  124. data/ext/tokyo_tyrant.c +147 -0
  125. data/ext/tokyo_tyrant.h +48 -0
  126. data/ext/tokyo_tyrant_db.c +227 -0
  127. data/ext/tokyo_tyrant_db.h +8 -0
  128. data/ext/tokyo_tyrant_module.c +453 -0
  129. data/ext/tokyo_tyrant_module.h +10 -0
  130. data/ext/tokyo_tyrant_query.c +226 -0
  131. data/ext/tokyo_tyrant_query.h +9 -0
  132. data/ext/tokyo_tyrant_table.c +319 -0
  133. data/ext/tokyo_tyrant_table.h +8 -0
  134. data/ext/tokyocabinet-1.4.41/COPYING +504 -0
  135. data/ext/tokyocabinet-1.4.41/ChangeLog +1252 -0
  136. data/ext/tokyocabinet-1.4.41/Makefile.in +825 -0
  137. data/ext/tokyocabinet-1.4.41/README +38 -0
  138. data/ext/tokyocabinet-1.4.41/THANKS +12 -0
  139. data/ext/tokyocabinet-1.4.41/bros/Makefile +133 -0
  140. data/ext/tokyocabinet-1.4.41/bros/bdbtest.c +438 -0
  141. data/ext/tokyocabinet-1.4.41/bros/cdbtest.c +219 -0
  142. data/ext/tokyocabinet-1.4.41/bros/cmpsqltctest.c +186 -0
  143. data/ext/tokyocabinet-1.4.41/bros/gdbmtest.c +216 -0
  144. data/ext/tokyocabinet-1.4.41/bros/mapreporter +72 -0
  145. data/ext/tokyocabinet-1.4.41/bros/maptest.cc +677 -0
  146. data/ext/tokyocabinet-1.4.41/bros/ndbmtest.c +204 -0
  147. data/ext/tokyocabinet-1.4.41/bros/qdbmtest.c +375 -0
  148. data/ext/tokyocabinet-1.4.41/bros/reporter +141 -0
  149. data/ext/tokyocabinet-1.4.41/bros/result.xls +0 -0
  150. data/ext/tokyocabinet-1.4.41/bros/sdbmtest.c +204 -0
  151. data/ext/tokyocabinet-1.4.41/bros/sqltest.c +404 -0
  152. data/ext/tokyocabinet-1.4.41/bros/tctest.c +748 -0
  153. data/ext/tokyocabinet-1.4.41/bros/tdbtest.c +205 -0
  154. data/ext/tokyocabinet-1.4.41/configure +7402 -0
  155. data/ext/tokyocabinet-1.4.41/configure.in +362 -0
  156. data/ext/tokyocabinet-1.4.41/doc/benchmark.pdf +0 -0
  157. data/ext/tokyocabinet-1.4.41/doc/common.css +211 -0
  158. data/ext/tokyocabinet-1.4.41/doc/icon16.png +0 -0
  159. data/ext/tokyocabinet-1.4.41/doc/index.html +156 -0
  160. data/ext/tokyocabinet-1.4.41/doc/index.ja.html +197 -0
  161. data/ext/tokyocabinet-1.4.41/doc/logo-ja.png +0 -0
  162. data/ext/tokyocabinet-1.4.41/doc/logo.png +0 -0
  163. data/ext/tokyocabinet-1.4.41/doc/spex-en.html +7145 -0
  164. data/ext/tokyocabinet-1.4.41/doc/spex-ja.html +7476 -0
  165. data/ext/tokyocabinet-1.4.41/doc/tokyoproducts.pdf +0 -0
  166. data/ext/tokyocabinet-1.4.41/doc/tokyoproducts.ppt +0 -0
  167. data/ext/tokyocabinet-1.4.41/example/Makefile +113 -0
  168. data/ext/tokyocabinet-1.4.41/example/tcadbex.c +55 -0
  169. data/ext/tokyocabinet-1.4.41/example/tcbdbex.c +64 -0
  170. data/ext/tokyocabinet-1.4.41/example/tcfdbex.c +60 -0
  171. data/ext/tokyocabinet-1.4.41/example/tchdbex.c +60 -0
  172. data/ext/tokyocabinet-1.4.41/example/tctchat.c +97 -0
  173. data/ext/tokyocabinet-1.4.41/example/tctchat.tmpl +141 -0
  174. data/ext/tokyocabinet-1.4.41/example/tctdbex.c +85 -0
  175. data/ext/tokyocabinet-1.4.41/example/tctsearch.c +95 -0
  176. data/ext/tokyocabinet-1.4.41/example/tctsearch.tmpl +122 -0
  177. data/ext/tokyocabinet-1.4.41/example/tcutilex.c +77 -0
  178. data/ext/tokyocabinet-1.4.41/f.tsv +2 -0
  179. data/ext/tokyocabinet-1.4.41/lab/calccomp +118 -0
  180. data/ext/tokyocabinet-1.4.41/lab/datechange +56 -0
  181. data/ext/tokyocabinet-1.4.41/lab/diffcheck +45 -0
  182. data/ext/tokyocabinet-1.4.41/lab/htmltotsv +102 -0
  183. data/ext/tokyocabinet-1.4.41/lab/magic +19 -0
  184. data/ext/tokyocabinet-1.4.41/lab/printenv.cgi +27 -0
  185. data/ext/tokyocabinet-1.4.41/lab/stepcount +26 -0
  186. data/ext/tokyocabinet-1.4.41/lab/stopwatch +61 -0
  187. data/ext/tokyocabinet-1.4.41/lab/tabcheck +43 -0
  188. data/ext/tokyocabinet-1.4.41/lab/wgettsv +239 -0
  189. data/ext/tokyocabinet-1.4.41/lab/widthcheck +57 -0
  190. data/ext/tokyocabinet-1.4.41/man/htmltoman +104 -0
  191. data/ext/tokyocabinet-1.4.41/man/tcadb.3 +676 -0
  192. data/ext/tokyocabinet-1.4.41/man/tcamgr.1 +97 -0
  193. data/ext/tokyocabinet-1.4.41/man/tcamttest.1 +35 -0
  194. data/ext/tokyocabinet-1.4.41/man/tcatest.1 +55 -0
  195. data/ext/tokyocabinet-1.4.41/man/tcbdb.3 +1355 -0
  196. data/ext/tokyocabinet-1.4.41/man/tcbmgr.1 +125 -0
  197. data/ext/tokyocabinet-1.4.41/man/tcbmttest.1 +81 -0
  198. data/ext/tokyocabinet-1.4.41/man/tcbtest.1 +107 -0
  199. data/ext/tokyocabinet-1.4.41/man/tcfdb.3 +975 -0
  200. data/ext/tokyocabinet-1.4.41/man/tcfmgr.1 +98 -0
  201. data/ext/tokyocabinet-1.4.41/man/tcfmttest.1 +62 -0
  202. data/ext/tokyocabinet-1.4.41/man/tcftest.1 +73 -0
  203. data/ext/tokyocabinet-1.4.41/man/tchdb.3 +898 -0
  204. data/ext/tokyocabinet-1.4.41/man/tchmgr.1 +110 -0
  205. data/ext/tokyocabinet-1.4.41/man/tchmttest.1 +85 -0
  206. data/ext/tokyocabinet-1.4.41/man/tchtest.1 +95 -0
  207. data/ext/tokyocabinet-1.4.41/man/tclist.3 +1 -0
  208. data/ext/tokyocabinet-1.4.41/man/tcmap.3 +1 -0
  209. data/ext/tokyocabinet-1.4.41/man/tcmdb.3 +1 -0
  210. data/ext/tokyocabinet-1.4.41/man/tcmpool.3 +1 -0
  211. data/ext/tokyocabinet-1.4.41/man/tctdb.3 +1110 -0
  212. data/ext/tokyocabinet-1.4.41/man/tctmgr.1 +140 -0
  213. data/ext/tokyocabinet-1.4.41/man/tctmttest.1 +92 -0
  214. data/ext/tokyocabinet-1.4.41/man/tctree.3 +1 -0
  215. data/ext/tokyocabinet-1.4.41/man/tcttest.1 +105 -0
  216. data/ext/tokyocabinet-1.4.41/man/tcucodec.1 +162 -0
  217. data/ext/tokyocabinet-1.4.41/man/tcumttest.1 +41 -0
  218. data/ext/tokyocabinet-1.4.41/man/tcutest.1 +81 -0
  219. data/ext/tokyocabinet-1.4.41/man/tcutil.3 +4518 -0
  220. data/ext/tokyocabinet-1.4.41/man/tcxstr.3 +1 -0
  221. data/ext/tokyocabinet-1.4.41/man/tokyocabinet.3 +132 -0
  222. data/ext/tokyocabinet-1.4.41/md5.c +381 -0
  223. data/ext/tokyocabinet-1.4.41/md5.h +101 -0
  224. data/ext/tokyocabinet-1.4.41/myconf.c +493 -0
  225. data/ext/tokyocabinet-1.4.41/myconf.h +549 -0
  226. data/ext/tokyocabinet-1.4.41/tcadb.c +4339 -0
  227. data/ext/tokyocabinet-1.4.41/tcadb.h +548 -0
  228. data/ext/tokyocabinet-1.4.41/tcamgr.c +1019 -0
  229. data/ext/tokyocabinet-1.4.41/tcamttest.c +542 -0
  230. data/ext/tokyocabinet-1.4.41/tcatest.c +1845 -0
  231. data/ext/tokyocabinet-1.4.41/tcawmgr.c +482 -0
  232. data/ext/tokyocabinet-1.4.41/tcbdb.c +4180 -0
  233. data/ext/tokyocabinet-1.4.41/tcbdb.h +1101 -0
  234. data/ext/tokyocabinet-1.4.41/tcbmgr.c +1012 -0
  235. data/ext/tokyocabinet-1.4.41/tcbmttest.c +1810 -0
  236. data/ext/tokyocabinet-1.4.41/tcbtest.c +2586 -0
  237. data/ext/tokyocabinet-1.4.41/tcfdb.c +2746 -0
  238. data/ext/tokyocabinet-1.4.41/tcfdb.h +858 -0
  239. data/ext/tokyocabinet-1.4.41/tcfmgr.c +786 -0
  240. data/ext/tokyocabinet-1.4.41/tcfmttest.c +1220 -0
  241. data/ext/tokyocabinet-1.4.41/tcftest.c +1695 -0
  242. data/ext/tokyocabinet-1.4.41/tchdb.c +5153 -0
  243. data/ext/tokyocabinet-1.4.41/tchdb.h +871 -0
  244. data/ext/tokyocabinet-1.4.41/tchmgr.c +842 -0
  245. data/ext/tokyocabinet-1.4.41/tchmttest.c +1757 -0
  246. data/ext/tokyocabinet-1.4.41/tchtest.c +2129 -0
  247. data/ext/tokyocabinet-1.4.41/tctdb.c +6199 -0
  248. data/ext/tokyocabinet-1.4.41/tctdb.h +1086 -0
  249. data/ext/tokyocabinet-1.4.41/tctmgr.c +1241 -0
  250. data/ext/tokyocabinet-1.4.41/tctmttest.c +1563 -0
  251. data/ext/tokyocabinet-1.4.41/tcttest.c +2062 -0
  252. data/ext/tokyocabinet-1.4.41/tcucodec.c +1357 -0
  253. data/ext/tokyocabinet-1.4.41/tcumttest.c +578 -0
  254. data/ext/tokyocabinet-1.4.41/tcutest.c +1875 -0
  255. data/ext/tokyocabinet-1.4.41/tcutil.c +10528 -0
  256. data/ext/tokyocabinet-1.4.41/tcutil.h +4184 -0
  257. data/ext/tokyocabinet-1.4.41/tokyocabinet.idl +336 -0
  258. data/ext/tokyocabinet-1.4.41/tokyocabinet.pc.in +14 -0
  259. data/ext/tokyotyrant-1.1.39/COPYING +504 -0
  260. data/ext/tokyotyrant-1.1.39/ChangeLog +578 -0
  261. data/ext/tokyotyrant-1.1.39/Makefile.in +365 -0
  262. data/ext/tokyotyrant-1.1.39/README +38 -0
  263. data/ext/tokyotyrant-1.1.39/THANKS +15 -0
  264. data/ext/tokyotyrant-1.1.39/configure +6979 -0
  265. data/ext/tokyotyrant-1.1.39/configure.in +300 -0
  266. data/ext/tokyotyrant-1.1.39/doc/common.css +211 -0
  267. data/ext/tokyotyrant-1.1.39/doc/index.html +79 -0
  268. data/ext/tokyotyrant-1.1.39/doc/spex.html +2264 -0
  269. data/ext/tokyotyrant-1.1.39/example/Makefile +68 -0
  270. data/ext/tokyotyrant-1.1.39/example/httptest.pl +88 -0
  271. data/ext/tokyotyrant-1.1.39/example/mcftest.pl +39 -0
  272. data/ext/tokyotyrant-1.1.39/example/mctest.pl +43 -0
  273. data/ext/tokyotyrant-1.1.39/example/tcrdbex +0 -0
  274. data/ext/tokyotyrant-1.1.39/example/tcrdbex.c +49 -0
  275. data/ext/tokyotyrant-1.1.39/example/tcrdbex.o +0 -0
  276. data/ext/tokyotyrant-1.1.39/example/tcrdbtblex +0 -0
  277. data/ext/tokyotyrant-1.1.39/example/tcrdbtblex.c +79 -0
  278. data/ext/tokyotyrant-1.1.39/example/tcrdbtblex.o +0 -0
  279. data/ext/tokyotyrant-1.1.39/ext/mapreduce.lua +57 -0
  280. data/ext/tokyotyrant-1.1.39/ext/queue.lua +55 -0
  281. data/ext/tokyotyrant-1.1.39/ext/senatus.lua +532 -0
  282. data/ext/tokyotyrant-1.1.39/ext/usherette.lua +438 -0
  283. data/ext/tokyotyrant-1.1.39/lab/datechange +56 -0
  284. data/ext/tokyotyrant-1.1.39/lab/diffcheck +45 -0
  285. data/ext/tokyotyrant-1.1.39/lab/fibonacci.lua +20 -0
  286. data/ext/tokyotyrant-1.1.39/lab/footprint.lua +67 -0
  287. data/ext/tokyotyrant-1.1.39/lab/highlow.lua +88 -0
  288. data/ext/tokyotyrant-1.1.39/lab/killdualmaster +12 -0
  289. data/ext/tokyotyrant-1.1.39/lab/rundualmaster +38 -0
  290. data/ext/tokyotyrant-1.1.39/lab/stepcount +26 -0
  291. data/ext/tokyotyrant-1.1.39/lab/tabcheck +43 -0
  292. data/ext/tokyotyrant-1.1.39/lab/ushrtregister.pl +55 -0
  293. data/ext/tokyotyrant-1.1.39/lab/widthcheck +57 -0
  294. data/ext/tokyotyrant-1.1.39/man/htmltoman +100 -0
  295. data/ext/tokyotyrant-1.1.39/man/tcrdb.3 +1309 -0
  296. data/ext/tokyotyrant-1.1.39/man/tcrmgr.1 +164 -0
  297. data/ext/tokyotyrant-1.1.39/man/tcrmttest.1 +55 -0
  298. data/ext/tokyotyrant-1.1.39/man/tcrtest.1 +89 -0
  299. data/ext/tokyotyrant-1.1.39/man/tculog.3 +15 -0
  300. data/ext/tokyotyrant-1.1.39/man/ttservctl.8 +37 -0
  301. data/ext/tokyotyrant-1.1.39/man/ttserver.1 +84 -0
  302. data/ext/tokyotyrant-1.1.39/man/ttulmgr.1 +40 -0
  303. data/ext/tokyotyrant-1.1.39/man/ttultest.1 +16 -0
  304. data/ext/tokyotyrant-1.1.39/man/ttutil.3 +14 -0
  305. data/ext/tokyotyrant-1.1.39/myconf.c +169 -0
  306. data/ext/tokyotyrant-1.1.39/myconf.h +408 -0
  307. data/ext/tokyotyrant-1.1.39/scrext.c +2394 -0
  308. data/ext/tokyotyrant-1.1.39/scrext.h +96 -0
  309. data/ext/tokyotyrant-1.1.39/tcrdb.c +2637 -0
  310. data/ext/tokyotyrant-1.1.39/tcrdb.h +801 -0
  311. data/ext/tokyotyrant-1.1.39/tcrmgr.c +1559 -0
  312. data/ext/tokyotyrant-1.1.39/tcrmttest.c +915 -0
  313. data/ext/tokyotyrant-1.1.39/tcrtest.c +1542 -0
  314. data/ext/tokyotyrant-1.1.39/tculog.c +1211 -0
  315. data/ext/tokyotyrant-1.1.39/tculog.h +392 -0
  316. data/ext/tokyotyrant-1.1.39/tokyotyrant.idl +143 -0
  317. data/ext/tokyotyrant-1.1.39/tokyotyrant.pc.in +14 -0
  318. data/ext/tokyotyrant-1.1.39/ttservctl +163 -0
  319. data/ext/tokyotyrant-1.1.39/ttserver.c +3583 -0
  320. data/ext/tokyotyrant-1.1.39/ttskeldir.c +141 -0
  321. data/ext/tokyotyrant-1.1.39/ttskelmock.c +64 -0
  322. data/ext/tokyotyrant-1.1.39/ttskelnull.c +79 -0
  323. data/ext/tokyotyrant-1.1.39/ttskelproxy.c +74 -0
  324. data/ext/tokyotyrant-1.1.39/ttulmgr.c +266 -0
  325. data/ext/tokyotyrant-1.1.39/ttultest.c +371 -0
  326. data/ext/tokyotyrant-1.1.39/ttutil.c +1510 -0
  327. data/ext/tokyotyrant-1.1.39/ttutil.h +494 -0
  328. data/lib/tokyo_tyrant/balancer.rb +189 -0
  329. data/spec/ext.lua +4 -0
  330. data/spec/plu_db.rb +538 -0
  331. data/spec/spec.rb +1 -0
  332. data/spec/spec_base.rb +17 -0
  333. data/spec/start_tyrants.sh +36 -0
  334. data/spec/stop_tyrants.sh +9 -0
  335. data/spec/tokyo_tyrant_balancer_db_spec.rb +160 -0
  336. data/spec/tokyo_tyrant_balancer_table_spec.rb +177 -0
  337. data/spec/tokyo_tyrant_query_spec.rb +159 -0
  338. data/spec/tokyo_tyrant_spec.rb +254 -0
  339. data/spec/tokyo_tyrant_table_spec.rb +301 -0
  340. metadata +402 -0
@@ -0,0 +1,2394 @@
1
+ /*************************************************************************************************
2
+ * Scripting language extension of Tokyo Tyrant
3
+ * Copyright (C) 2006-2009 Mikio Hirabayashi
4
+ * This file is part of Tokyo Tyrant.
5
+ * Tokyo Tyrant is free software; you can redistribute it and/or modify it under the terms of
6
+ * the GNU Lesser General Public License as published by the Free Software Foundation; either
7
+ * version 2.1 of the License or any later version. Tokyo Tyrant is distributed in the hope
8
+ * that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
9
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
10
+ * License for more details.
11
+ * You should have received a copy of the GNU Lesser General Public License along with Tokyo
12
+ * Tyrant; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330,
13
+ * Boston, MA 02111-1307 USA.
14
+ *************************************************************************************************/
15
+
16
+
17
+ #include "scrext.h"
18
+
19
+
20
+
21
+ /*************************************************************************************************
22
+ * by default
23
+ *************************************************************************************************/
24
+
25
+
26
+ #if defined(TTNOEXT)
27
+
28
+
29
+ typedef struct _SCREXT { // type of structure of the script extension
30
+ struct _SCREXT **screxts; // script extension objects
31
+ int thnum; // number of native threads
32
+ int thid; // thread ID
33
+ char *path; // path of the initializing script
34
+ TCADB *adb; // abstract database object
35
+ TCULOG *ulog; // update log object
36
+ uint32_t sid; // server ID
37
+ TCMDB *stash; // global stash object
38
+ TCMDB *lock; // global lock object
39
+ void (*logger)(int, const char *, void *); // logging function
40
+ void *logopq; // opaque pointer for the logging function
41
+ bool term; // terminate flag
42
+ } SCREXT;
43
+
44
+
45
+ /* Initialize the global scripting language extension. */
46
+ void *scrextnew(void **screxts, int thnum, int thid, const char *path,
47
+ TCADB *adb, TCULOG *ulog, uint32_t sid, TCMDB *stash, TCMDB *lock,
48
+ void (*logger)(int, const char *, void *), void *logopq){
49
+ SCREXT *scr = tcmalloc(sizeof(*scr));
50
+ scr->screxts = (SCREXT **)screxts;
51
+ scr->thnum = thnum;
52
+ scr->thid = thid;
53
+ scr->path = tcstrdup(path);
54
+ scr->adb = adb;
55
+ scr->ulog = ulog;
56
+ scr->sid = sid;
57
+ scr->stash = stash;
58
+ scr->lock = lock;
59
+ scr->logger = logger;
60
+ scr->logopq = logopq;
61
+ scr->term = false;
62
+ return scr;
63
+ }
64
+
65
+
66
+ /* Destroy the global scripting language extension. */
67
+ bool scrextdel(void *scr){
68
+ SCREXT *myscr = scr;
69
+ tcfree(myscr->path);
70
+ tcfree(myscr);
71
+ return true;
72
+ }
73
+
74
+
75
+ /* Call a method of the scripting language extension. */
76
+ char *scrextcallmethod(void *scr, const char *name,
77
+ const void *kbuf, int ksiz, const void *vbuf, int vsiz, int *sp){
78
+ SCREXT *myscr = scr;
79
+ if(!strcmp(name, "put")){
80
+ if(!tculogadbput(myscr->ulog, myscr->sid, 0, myscr->adb, kbuf, ksiz, vbuf, vsiz))
81
+ return NULL;
82
+ char *msg = tcstrdup("ok");
83
+ *sp = strlen(msg);
84
+ return msg;
85
+ } else if(!strcmp(name, "putkeep")){
86
+ if(!tculogadbputkeep(myscr->ulog, myscr->sid, 0, myscr->adb, kbuf, ksiz, vbuf, vsiz))
87
+ return NULL;
88
+ char *msg = tcstrdup("ok");
89
+ *sp = strlen(msg);
90
+ return msg;
91
+ } else if(!strcmp(name, "putcat")){
92
+ if(!tculogadbputcat(myscr->ulog, myscr->sid, 0, myscr->adb, kbuf, ksiz, vbuf, vsiz))
93
+ return NULL;
94
+ char *msg = tcstrdup("ok");
95
+ *sp = strlen(msg);
96
+ return msg;
97
+ } else if(!strcmp(name, "out")){
98
+ if(!tculogadbout(myscr->ulog, myscr->sid, 0, myscr->adb, kbuf, ksiz)) return NULL;
99
+ char *msg = tcstrdup("ok");
100
+ *sp = strlen(msg);
101
+ return msg;
102
+ } else if(!strcmp(name, "get")){
103
+ return tcadbget(myscr->adb, kbuf, ksiz, sp);
104
+ } else if(!strcmp(name, "log")){
105
+ char *msg = tcmemdup(kbuf, ksiz);
106
+ myscr->logger(TTLOGINFO, msg, myscr->logopq);
107
+ tcfree(msg);
108
+ msg = tcstrdup("ok");
109
+ *sp = strlen(msg);
110
+ return msg;
111
+ }
112
+ int psiz = strlen(myscr->path);
113
+ int nsiz = strlen(name);
114
+ char *msg = tcmalloc(psiz + nsiz + ksiz + vsiz + 4);
115
+ char *wp = msg;
116
+ memcpy(wp, myscr->path, psiz);
117
+ wp += psiz;
118
+ *(wp++) = ':';
119
+ memcpy(wp, name, nsiz);
120
+ wp += nsiz;
121
+ *(wp++) = ':';
122
+ memcpy(wp, kbuf, ksiz);
123
+ wp += ksiz;
124
+ *(wp++) = ':';
125
+ memcpy(wp, vbuf, vsiz);
126
+ wp += vsiz;
127
+ *sp = wp - msg;
128
+ return msg;
129
+ }
130
+
131
+
132
+ /* Send the terminate signal to the scripting language extension */
133
+ bool scrextkill(void *scr){
134
+ SCREXT *myscr = scr;
135
+ myscr->term = true;
136
+ return true;
137
+ }
138
+
139
+
140
+ #endif
141
+
142
+
143
+
144
+ /*************************************************************************************************
145
+ * for Lua
146
+ *************************************************************************************************/
147
+
148
+
149
+ #if defined(TTLUAEXT)
150
+
151
+
152
+ #include "lua.h"
153
+ #include "lualib.h"
154
+ #include "lauxlib.h"
155
+
156
+ #define SERVVAR "_serv_" // global variable name for server resources
157
+ #define ITERVAR "_iter_" // global variable name for iterator
158
+ #define MRMAPVAR "_mrmap_" // global variable name for mapreduce mapper
159
+ #define MRREDVAR "_mrred_" // global variable name for mapreduce reducer
160
+ #define MRPOOLVAR "_mrpool_" // global variable name for mapreduce pool
161
+
162
+ typedef struct { // type of structure of the script extension
163
+ lua_State *lua; // Lua environment
164
+ int thnum; // number of native threads
165
+ int thid; // thread ID
166
+ } SCREXT;
167
+
168
+ typedef struct { // type of structure of the server data
169
+ SCREXT **screxts; // script extension objects
170
+ int thnum; // number of native threads
171
+ int thid; // thread ID
172
+ TCADB *adb; // abstract database object
173
+ TCULOG *ulog; // update log object
174
+ uint32_t sid; // server ID
175
+ TCMDB *stash; // global stash object
176
+ TCMDB *lock; // global lock object
177
+ pthread_mutex_t *lcks; // mutex for user locks
178
+ int lcknum; // number of user locks
179
+ void (*logger)(int, const char *, void *); // logging function
180
+ void *logopq; // opaque pointer for the logging function
181
+ bool term; // terminate flag
182
+ } SERV;
183
+
184
+
185
+ /* private function prototypes */
186
+ static void reporterror(lua_State *lua);
187
+ static bool iterrec(const void *kbuf, int ksiz, const void *vbuf, int vsiz, lua_State *lua);
188
+ static int serv_eval(lua_State *lua);
189
+ static int serv_log(lua_State *lua);
190
+ static int serv_put(lua_State *lua);
191
+ static int serv_putkeep(lua_State *lua);
192
+ static int serv_putcat(lua_State *lua);
193
+ static int serv_out(lua_State *lua);
194
+ static int serv_get(lua_State *lua);
195
+ static int serv_vsiz(lua_State *lua);
196
+ static int serv_iterinit(lua_State *lua);
197
+ static int serv_iternext(lua_State *lua);
198
+ static int serv_fwmkeys(lua_State *lua);
199
+ static int serv_addint(lua_State *lua);
200
+ static int serv_adddouble(lua_State *lua);
201
+ static int serv_vanish(lua_State *lua);
202
+ static int serv_rnum(lua_State *lua);
203
+ static int serv_size(lua_State *lua);
204
+ static int serv_misc(lua_State *lua);
205
+ static int serv_foreach(lua_State *lua);
206
+ static int serv_mapreduce(lua_State *lua);
207
+ static int serv_mapreducemapemit(lua_State *lua);
208
+ static int serv_stashput(lua_State *lua);
209
+ static int serv_stashputkeep(lua_State *lua);
210
+ static int serv_stashputcat(lua_State *lua);
211
+ static int serv_stashout(lua_State *lua);
212
+ static int serv_stashget(lua_State *lua);
213
+ static int serv_stashvanish(lua_State *lua);
214
+ static int serv_stashforeach(lua_State *lua);
215
+ static int serv_lock(lua_State *lua);
216
+ static int serv_unlock(lua_State *lua);
217
+ static int serv_pack(lua_State *lua);
218
+ static int serv_unpack(lua_State *lua);
219
+ static int serv_split(lua_State *lua);
220
+ static int serv_codec(lua_State *lua);
221
+ static int serv_hash(lua_State *lua);
222
+ static int serv_bit(lua_State *lua);
223
+ static int serv_strstr(lua_State *lua);
224
+ static int serv_regex(lua_State *lua);
225
+ static int serv_ucs(lua_State *lua);
226
+ static int serv_dist(lua_State *lua);
227
+ static int serv_isect(lua_State *lua);
228
+ static int serv_union(lua_State *lua);
229
+ static int serv_time(lua_State *lua);
230
+ static int serv_sleep(lua_State *lua);
231
+ static int serv_stat(lua_State *lua);
232
+ static int serv_glob(lua_State *lua);
233
+ static int serv_remove(lua_State *lua);
234
+ static int serv_mkdir(lua_State *lua);
235
+
236
+
237
+ /* Initialize the global scripting language extension. */
238
+ void *scrextnew(void **screxts, int thnum, int thid, const char *path,
239
+ TCADB *adb, TCULOG *ulog, uint32_t sid, TCMDB *stash, TCMDB *lock,
240
+ void (*logger)(int, const char *, void *), void *logopq){
241
+ char *ibuf;
242
+ int isiz;
243
+ if(*path == '@'){
244
+ ibuf = tcstrdup(path + 1);
245
+ isiz = strlen(ibuf);
246
+ } else if(*path != '\0'){
247
+ ibuf = tcreadfile(path, 0, &isiz);
248
+ } else {
249
+ ibuf = tcmemdup("", 0);
250
+ isiz = 0;
251
+ }
252
+ if(!ibuf) return NULL;
253
+ lua_State *lua = luaL_newstate();
254
+ if(!lua){
255
+ tcfree(ibuf);
256
+ return NULL;
257
+ }
258
+ luaL_openlibs(lua);
259
+ lua_settop(lua, 0);
260
+ SERV *serv = lua_newuserdata(lua, sizeof(*serv));
261
+ serv->screxts = (SCREXT **)screxts;
262
+ serv->thnum = thnum;
263
+ serv->thid = thid;
264
+ serv->adb = adb;
265
+ serv->ulog = ulog;
266
+ serv->sid = sid;
267
+ serv->stash = stash;
268
+ serv->lock = lock;
269
+ serv->logger = logger;
270
+ serv->logopq = logopq;
271
+ serv->term = false;
272
+ lua_setglobal(lua, SERVVAR);
273
+ lua_register(lua, "_eval", serv_eval);
274
+ lua_register(lua, "_log", serv_log);
275
+ lua_register(lua, "_put", serv_put);
276
+ lua_register(lua, "_putkeep", serv_putkeep);
277
+ lua_register(lua, "_putcat", serv_putcat);
278
+ lua_register(lua, "_out", serv_out);
279
+ lua_register(lua, "_get", serv_get);
280
+ lua_register(lua, "_vsiz", serv_vsiz);
281
+ lua_register(lua, "_iterinit", serv_iterinit);
282
+ lua_register(lua, "_iternext", serv_iternext);
283
+ lua_register(lua, "_fwmkeys", serv_fwmkeys);
284
+ lua_register(lua, "_addint", serv_addint);
285
+ lua_register(lua, "_adddouble", serv_adddouble);
286
+ lua_register(lua, "_vanish", serv_vanish);
287
+ lua_register(lua, "_rnum", serv_rnum);
288
+ lua_register(lua, "_size", serv_size);
289
+ lua_register(lua, "_misc", serv_misc);
290
+ lua_register(lua, "_foreach", serv_foreach);
291
+ lua_register(lua, "_mapreduce", serv_mapreduce);
292
+ lua_register(lua, "_stashput", serv_stashput);
293
+ lua_register(lua, "_stashputkeep", serv_stashputkeep);
294
+ lua_register(lua, "_stashputcat", serv_stashputcat);
295
+ lua_register(lua, "_stashout", serv_stashout);
296
+ lua_register(lua, "_stashget", serv_stashget);
297
+ lua_register(lua, "_stashvanish", serv_stashvanish);
298
+ lua_register(lua, "_stashforeach", serv_stashforeach);
299
+ lua_register(lua, "_lock", serv_lock);
300
+ lua_register(lua, "_unlock", serv_unlock);
301
+ lua_register(lua, "_pack", serv_pack);
302
+ lua_register(lua, "_unpack", serv_unpack);
303
+ lua_register(lua, "_split", serv_split);
304
+ lua_register(lua, "_codec", serv_codec);
305
+ lua_register(lua, "_hash", serv_hash);
306
+ lua_register(lua, "_bit", serv_bit);
307
+ lua_register(lua, "_strstr", serv_strstr);
308
+ lua_register(lua, "_regex", serv_regex);
309
+ lua_register(lua, "_ucs", serv_ucs);
310
+ lua_register(lua, "_dist", serv_dist);
311
+ lua_register(lua, "_isect", serv_isect);
312
+ lua_register(lua, "_union", serv_union);
313
+ lua_register(lua, "_time", serv_time);
314
+ lua_register(lua, "_sleep", serv_sleep);
315
+ lua_register(lua, "_stat", serv_stat);
316
+ lua_register(lua, "_glob", serv_glob);
317
+ lua_register(lua, "_remove", serv_remove);
318
+ lua_register(lua, "_mkdir", serv_mkdir);
319
+ lua_pushstring(lua, ttversion);
320
+ lua_setglobal(lua, "_version");
321
+ lua_pushinteger(lua, getpid());
322
+ lua_setglobal(lua, "_pid");
323
+ lua_pushinteger(lua, sid);
324
+ lua_setglobal(lua, "_sid");
325
+ lua_pushinteger(lua, thnum);
326
+ lua_setglobal(lua, "_thnum");
327
+ lua_pushinteger(lua, thid + 1);
328
+ lua_setglobal(lua, "_thid");
329
+ lua_settop(lua, 0);
330
+ if(luaL_loadstring(lua, ibuf) != 0 || lua_pcall(lua, 0, 0, 0) != 0) reporterror(lua);
331
+ tcfree(ibuf);
332
+ if(thid == 0){
333
+ lua_getglobal(lua, "_begin");
334
+ if(lua_isfunction(lua, -1) && lua_pcall(lua, 0, 0, 0) != 0) reporterror(lua);
335
+ }
336
+ lua_settop(lua, 0);
337
+ SCREXT *scr = tcmalloc(sizeof(*scr));
338
+ scr->lua = lua;
339
+ scr->thnum = thnum;
340
+ scr->thid = thid;
341
+ return scr;
342
+ }
343
+
344
+
345
+ /* Destroy the global scripting language extension. */
346
+ bool scrextdel(void *scr){
347
+ SCREXT *myscr = scr;
348
+ lua_State *lua = myscr->lua;
349
+ if(myscr->thid == 0){
350
+ lua_getglobal(lua, "_end");
351
+ if(lua_isfunction(lua, -1) && lua_pcall(lua, 0, 0, 0) != 0) reporterror(lua);
352
+ }
353
+ lua_close(lua);
354
+ tcfree(scr);
355
+ return true;
356
+ }
357
+
358
+
359
+ /* Call a method of the scripting language extension. */
360
+ char *scrextcallmethod(void *scr, const char *name,
361
+ const void *kbuf, int ksiz, const void *vbuf, int vsiz, int *sp){
362
+ SCREXT *myscr = scr;
363
+ lua_State *lua = myscr->lua;
364
+ if(*name == '_') return NULL;
365
+ lua_getglobal(lua, name);
366
+ if(lua_gettop(lua) != 1 || !lua_isfunction(lua, 1)){
367
+ lua_settop(lua, 0);
368
+ return NULL;
369
+ }
370
+ lua_pushlstring(lua, kbuf, ksiz);
371
+ lua_pushlstring(lua, vbuf, vsiz);
372
+ if(lua_pcall(lua, 2, 1, 0) != 0){
373
+ reporterror(lua);
374
+ lua_settop(lua, 0);
375
+ return NULL;
376
+ }
377
+ if(lua_gettop(lua) < 1) return NULL;
378
+ const char *rbuf = NULL;
379
+ size_t rsiz;
380
+ switch(lua_type(lua, 1)){
381
+ case LUA_TNUMBER:
382
+ case LUA_TSTRING:
383
+ rbuf = lua_tolstring(lua, 1, &rsiz);
384
+ break;
385
+ case LUA_TBOOLEAN:
386
+ if(lua_toboolean(lua, 1)){
387
+ rbuf = "true";
388
+ rsiz = strlen(rbuf);
389
+ }
390
+ break;
391
+ case LUA_TTABLE:
392
+ if(lua_objlen(lua, 1) > 0){
393
+ lua_rawgeti(lua, 1, 1);
394
+ switch(lua_type(lua, -1)){
395
+ case LUA_TNUMBER:
396
+ case LUA_TSTRING:
397
+ rbuf = lua_tolstring(lua, -1, &rsiz);
398
+ break;
399
+ case LUA_TBOOLEAN:
400
+ if(lua_toboolean(lua, -1)){
401
+ rbuf = "true";
402
+ rsiz = strlen(rbuf);
403
+ }
404
+ break;
405
+ }
406
+ lua_pop(lua, 1);
407
+ }
408
+ break;
409
+ }
410
+ if(!rbuf){
411
+ lua_settop(lua, 0);
412
+ return NULL;
413
+ }
414
+ char *rv = tcmemdup(rbuf, rsiz);
415
+ *sp = rsiz;
416
+ lua_settop(lua, 0);
417
+ return rv;
418
+ }
419
+
420
+
421
+ /* Send the terminate signal to the scripting language extension */
422
+ bool scrextkill(void *scr){
423
+ SCREXT *myscr = scr;
424
+ lua_State *lua = myscr->lua;
425
+ lua_getglobal(lua, SERVVAR);
426
+ SERV *serv = lua_touserdata(lua, -1);
427
+ serv->term = true;
428
+ return true;
429
+ }
430
+
431
+
432
+ /* report an error of Lua program */
433
+ static void reporterror(lua_State *lua){
434
+ int argc = lua_gettop(lua);
435
+ char *msg = tcsprintf("Lua error: %s", argc > 0 ? lua_tostring(lua, argc) : "unknown");
436
+ lua_getglobal(lua, SERVVAR);
437
+ SERV *serv = lua_touserdata(lua, -1);
438
+ serv->logger(TTLOGERROR, msg, serv->logopq);
439
+ tcfree(msg);
440
+ }
441
+
442
+
443
+ /* call function for each record */
444
+ static bool iterrec(const void *kbuf, int ksiz, const void *vbuf, int vsiz, lua_State *lua){
445
+ int top = lua_gettop(lua);
446
+ lua_getglobal(lua, ITERVAR);
447
+ lua_pushlstring(lua, kbuf, ksiz);
448
+ lua_pushlstring(lua, vbuf, vsiz);
449
+ bool err = false;
450
+ if(lua_pcall(lua, 2, 1, 0) == 0){
451
+ if(lua_gettop(lua) <= top || !lua_toboolean(lua, -1)) err = true;
452
+ } else {
453
+ reporterror(lua);
454
+ err = true;
455
+ }
456
+ lua_settop(lua, top);
457
+ return !err;
458
+ }
459
+
460
+
461
+ /* call function to map records for mapreduce */
462
+ static bool maprec(void *map, const void *kbuf, int ksiz, const void *vbuf, int vsiz,
463
+ lua_State *lua){
464
+ lua_pushlightuserdata(lua, map);
465
+ lua_setglobal(lua, MRPOOLVAR);
466
+ int top = lua_gettop(lua);
467
+ lua_getglobal(lua, MRMAPVAR);
468
+ lua_pushlstring(lua, kbuf, ksiz);
469
+ lua_pushlstring(lua, vbuf, vsiz);
470
+ lua_pushcfunction(lua, serv_mapreducemapemit);
471
+ bool err = false;
472
+ if(lua_pcall(lua, 3, 1, 0) == 0){
473
+ if(lua_gettop(lua) < 1 && !lua_toboolean(lua, 1)) err = true;
474
+ } else {
475
+ reporterror(lua);
476
+ err = true;
477
+ }
478
+ lua_settop(lua, top);
479
+ return !err;
480
+ }
481
+
482
+
483
+ /* for _eval function */
484
+ static int serv_eval(lua_State *lua){
485
+ int argc = lua_gettop(lua);
486
+ if(argc != 1){
487
+ lua_pushstring(lua, "_eval: invalid arguments");
488
+ lua_error(lua);
489
+ }
490
+ const char *expr = lua_tostring(lua, 1);
491
+ if(!expr){
492
+ lua_pushstring(lua, "_eval: invalid arguments");
493
+ lua_error(lua);
494
+ }
495
+ lua_getglobal(lua, SERVVAR);
496
+ SERV *serv = lua_touserdata(lua, -1);
497
+ SCREXT **screxts = serv->screxts;
498
+ int thnum = serv->thnum;
499
+ bool err = false;
500
+ for(int i = 0; i < thnum; i++){
501
+ if(!screxts[i]){
502
+ lua_pushstring(lua, "_eval: not ready");
503
+ lua_error(lua);
504
+ }
505
+ }
506
+ for(int i = 0; i < thnum; i++){
507
+ lua_State *elua = screxts[i]->lua;
508
+ if(luaL_loadstring(elua, expr) != 0 || lua_pcall(elua, 0, 0, 0) != 0) reporterror(elua);
509
+ }
510
+ lua_settop(lua, 0);
511
+ lua_pushboolean(lua, !err);
512
+ return 1;
513
+ }
514
+
515
+
516
+ /* for _log function */
517
+ static int serv_log(lua_State *lua){
518
+ int argc = lua_gettop(lua);
519
+ if(argc < 1){
520
+ lua_pushstring(lua, "_log: invalid arguments");
521
+ lua_error(lua);
522
+ }
523
+ const char *msg = lua_tostring(lua, 1);
524
+ if(!msg){
525
+ lua_pushstring(lua, "_log: invalid arguments");
526
+ lua_error(lua);
527
+ }
528
+ int level = TTLOGINFO;
529
+ if(argc > 1) level = lua_tointeger(lua, 2);
530
+ lua_getglobal(lua, SERVVAR);
531
+ SERV *serv = lua_touserdata(lua, -1);
532
+ serv->logger(level, msg, serv->logopq);
533
+ lua_settop(lua, 0);
534
+ return 0;
535
+ }
536
+
537
+
538
+ /* for _put function */
539
+ static int serv_put(lua_State *lua){
540
+ int argc = lua_gettop(lua);
541
+ if(argc != 2){
542
+ lua_pushstring(lua, "_put: invalid arguments");
543
+ lua_error(lua);
544
+ }
545
+ size_t ksiz;
546
+ const char *kbuf = lua_tolstring(lua, 1, &ksiz);
547
+ size_t vsiz;
548
+ const char *vbuf = lua_tolstring(lua, 2, &vsiz);
549
+ if(!kbuf || !vbuf){
550
+ lua_pushstring(lua, "_put: invalid arguments");
551
+ lua_error(lua);
552
+ }
553
+ lua_getglobal(lua, SERVVAR);
554
+ SERV *serv = lua_touserdata(lua, -1);
555
+ bool rv = tculogadbput(serv->ulog, serv->sid, 0, serv->adb, kbuf, ksiz, vbuf, vsiz);
556
+ lua_settop(lua, 0);
557
+ lua_pushboolean(lua, rv);
558
+ return 1;
559
+ }
560
+
561
+
562
+ /* for _putkeep function */
563
+ static int serv_putkeep(lua_State *lua){
564
+ int argc = lua_gettop(lua);
565
+ if(argc != 2){
566
+ lua_pushstring(lua, "_putkeep: invalid arguments");
567
+ lua_error(lua);
568
+ }
569
+ size_t ksiz;
570
+ const char *kbuf = lua_tolstring(lua, 1, &ksiz);
571
+ size_t vsiz;
572
+ const char *vbuf = lua_tolstring(lua, 2, &vsiz);
573
+ if(!kbuf || !vbuf){
574
+ lua_pushstring(lua, "_putkeep: invalid arguments");
575
+ lua_error(lua);
576
+ }
577
+ lua_getglobal(lua, SERVVAR);
578
+ SERV *serv = lua_touserdata(lua, -1);
579
+ bool rv = tculogadbputkeep(serv->ulog, serv->sid, 0, serv->adb, kbuf, ksiz, vbuf, vsiz);
580
+ lua_settop(lua, 0);
581
+ lua_pushboolean(lua, rv);
582
+ return 1;
583
+ }
584
+
585
+
586
+ /* for _putcat function */
587
+ static int serv_putcat(lua_State *lua){
588
+ int argc = lua_gettop(lua);
589
+ if(argc != 2){
590
+ lua_pushstring(lua, "_putcat: invalid arguments");
591
+ lua_error(lua);
592
+ }
593
+ size_t ksiz;
594
+ const char *kbuf = lua_tolstring(lua, 1, &ksiz);
595
+ size_t vsiz;
596
+ const char *vbuf = lua_tolstring(lua, 2, &vsiz);
597
+ if(!kbuf || !vbuf){
598
+ lua_pushstring(lua, "_putcat: invalid arguments");
599
+ lua_error(lua);
600
+ }
601
+ lua_getglobal(lua, SERVVAR);
602
+ SERV *serv = lua_touserdata(lua, -1);
603
+ bool rv = tculogadbputcat(serv->ulog, serv->sid, 0, serv->adb, kbuf, ksiz, vbuf, vsiz);
604
+ lua_settop(lua, 0);
605
+ lua_pushboolean(lua, rv);
606
+ return 1;
607
+ }
608
+
609
+
610
+ /* for _putout function */
611
+ static int serv_out(lua_State *lua){
612
+ int argc = lua_gettop(lua);
613
+ if(argc != 1){
614
+ lua_pushstring(lua, "_out: invalid arguments");
615
+ lua_error(lua);
616
+ }
617
+ size_t ksiz;
618
+ const char *kbuf = lua_tolstring(lua, 1, &ksiz);
619
+ if(!kbuf){
620
+ lua_pushstring(lua, "_out: invalid arguments");
621
+ lua_error(lua);
622
+ }
623
+ lua_getglobal(lua, SERVVAR);
624
+ SERV *serv = lua_touserdata(lua, -1);
625
+ bool rv = tculogadbout(serv->ulog, serv->sid, 0, serv->adb, kbuf, ksiz);
626
+ lua_settop(lua, 0);
627
+ lua_pushboolean(lua, rv);
628
+ return 1;
629
+ }
630
+
631
+
632
+ /* for _get function */
633
+ static int serv_get(lua_State *lua){
634
+ int argc = lua_gettop(lua);
635
+ if(argc != 1){
636
+ lua_pushstring(lua, "_get: invalid arguments");
637
+ lua_error(lua);
638
+ }
639
+ size_t ksiz;
640
+ const char *kbuf = lua_tolstring(lua, 1, &ksiz);
641
+ if(!kbuf){
642
+ lua_pushstring(lua, "_get: invalid arguments");
643
+ lua_error(lua);
644
+ }
645
+ lua_getglobal(lua, SERVVAR);
646
+ SERV *serv = lua_touserdata(lua, -1);
647
+ int vsiz;
648
+ char *vbuf = tcadbget(serv->adb, kbuf, ksiz, &vsiz);
649
+ lua_settop(lua, 0);
650
+ if(vbuf){
651
+ lua_pushlstring(lua, vbuf, vsiz);
652
+ tcfree(vbuf);
653
+ } else {
654
+ lua_pushnil(lua);
655
+ }
656
+ return 1;
657
+ }
658
+
659
+
660
+ /* for _vsiz function */
661
+ static int serv_vsiz(lua_State *lua){
662
+ int argc = lua_gettop(lua);
663
+ if(argc != 1){
664
+ lua_pushstring(lua, "_vsiz: invalid arguments");
665
+ lua_error(lua);
666
+ }
667
+ size_t ksiz;
668
+ const char *kbuf = lua_tolstring(lua, 1, &ksiz);
669
+ if(!kbuf){
670
+ lua_pushstring(lua, "_vsiz: invalid arguments");
671
+ lua_error(lua);
672
+ }
673
+ lua_getglobal(lua, SERVVAR);
674
+ SERV *serv = lua_touserdata(lua, -1);
675
+ int vsiz = tcadbvsiz(serv->adb, kbuf, ksiz);
676
+ lua_settop(lua, 0);
677
+ lua_pushnumber(lua, vsiz);
678
+ return 1;
679
+ }
680
+
681
+
682
+ /* for _iterinit function */
683
+ static int serv_iterinit(lua_State *lua){
684
+ int argc = lua_gettop(lua);
685
+ if(argc != 0){
686
+ lua_pushstring(lua, "_iterinit: invalid arguments");
687
+ lua_error(lua);
688
+ }
689
+ lua_getglobal(lua, SERVVAR);
690
+ SERV *serv = lua_touserdata(lua, -1);
691
+ bool rv = tcadbiterinit(serv->adb);
692
+ lua_settop(lua, 0);
693
+ lua_pushboolean(lua, rv);
694
+ return 1;
695
+ }
696
+
697
+
698
+ /* for _iternext function */
699
+ static int serv_iternext(lua_State *lua){
700
+ int argc = lua_gettop(lua);
701
+ if(argc != 0){
702
+ lua_pushstring(lua, "_iternext: invalid arguments");
703
+ lua_error(lua);
704
+ }
705
+ lua_getglobal(lua, SERVVAR);
706
+ SERV *serv = lua_touserdata(lua, -1);
707
+ int vsiz;
708
+ char *vbuf = tcadbiternext(serv->adb, &vsiz);
709
+ lua_settop(lua, 0);
710
+ if(vbuf){
711
+ lua_pushlstring(lua, vbuf, vsiz);
712
+ tcfree(vbuf);
713
+ } else {
714
+ lua_pushnil(lua);
715
+ }
716
+ return 1;
717
+ }
718
+
719
+
720
+ /* for _fwmkeys function */
721
+ static int serv_fwmkeys(lua_State *lua){
722
+ int argc = lua_gettop(lua);
723
+ if(argc < 1){
724
+ lua_pushstring(lua, "_fwmkeys: invalid arguments");
725
+ lua_error(lua);
726
+ }
727
+ size_t psiz;
728
+ const char *pbuf = lua_tolstring(lua, 1, &psiz);
729
+ if(!pbuf){
730
+ lua_pushstring(lua, "_fwmkeys: invalid arguments");
731
+ lua_error(lua);
732
+ }
733
+ int max = argc > 1 && lua_isnumber(lua, 2) ? lua_tonumber(lua, 2) : -1;
734
+ lua_getglobal(lua, SERVVAR);
735
+ SERV *serv = lua_touserdata(lua, -1);
736
+ TCLIST *keys = tcadbfwmkeys(serv->adb, pbuf, psiz, max);
737
+ lua_settop(lua, 0);
738
+ int knum = tclistnum(keys);
739
+ lua_createtable(lua, knum, 0);
740
+ for(int i = 0; i < knum; i++){
741
+ int ksiz;
742
+ const char *kbuf = tclistval(keys, i, &ksiz);
743
+ lua_pushlstring(lua, kbuf, ksiz);
744
+ lua_rawseti(lua, 1, i + 1);
745
+ }
746
+ tclistdel(keys);
747
+ return 1;
748
+ }
749
+
750
+
751
+ /* for _addint function */
752
+ static int serv_addint(lua_State *lua){
753
+ int argc = lua_gettop(lua);
754
+ if(argc != 2){
755
+ lua_pushstring(lua, "_addint: invalid arguments");
756
+ lua_error(lua);
757
+ }
758
+ size_t ksiz;
759
+ const char *kbuf = lua_tolstring(lua, 1, &ksiz);
760
+ int num = lua_tonumber(lua, 2);
761
+ if(!kbuf || !lua_isnumber(lua, 2)){
762
+ lua_pushstring(lua, "_addint: invalid arguments");
763
+ lua_error(lua);
764
+ }
765
+ lua_getglobal(lua, SERVVAR);
766
+ SERV *serv = lua_touserdata(lua, -1);
767
+ int rv = tculogadbaddint(serv->ulog, serv->sid, 0, serv->adb, kbuf, ksiz, num);
768
+ lua_settop(lua, 0);
769
+ if(rv == INT_MIN){
770
+ lua_pushnil(lua);
771
+ } else {
772
+ lua_pushnumber(lua, rv);
773
+ }
774
+ return 1;
775
+ }
776
+
777
+
778
+ /* for _adddouble function */
779
+ static int serv_adddouble(lua_State *lua){
780
+ int argc = lua_gettop(lua);
781
+ if(argc != 2){
782
+ lua_pushstring(lua, "_adddouble: invalid arguments");
783
+ lua_error(lua);
784
+ }
785
+ size_t ksiz;
786
+ const char *kbuf = lua_tolstring(lua, 1, &ksiz);
787
+ double num = lua_tonumber(lua, 2);
788
+ if(!kbuf || !lua_isnumber(lua, 2)){
789
+ lua_pushstring(lua, "_adddouble: invalid arguments");
790
+ lua_error(lua);
791
+ }
792
+ lua_getglobal(lua, SERVVAR);
793
+ SERV *serv = lua_touserdata(lua, -1);
794
+ double rv = tculogadbadddouble(serv->ulog, serv->sid, 0, serv->adb, kbuf, ksiz, num);
795
+ lua_settop(lua, 0);
796
+ if(isnan(rv)){
797
+ lua_pushnil(lua);
798
+ } else {
799
+ lua_pushnumber(lua, rv);
800
+ }
801
+ return 1;
802
+ }
803
+
804
+
805
+ /* for _vanish function */
806
+ static int serv_vanish(lua_State *lua){
807
+ int argc = lua_gettop(lua);
808
+ if(argc != 0){
809
+ lua_pushstring(lua, "_vanish: invalid arguments");
810
+ lua_error(lua);
811
+ }
812
+ lua_getglobal(lua, SERVVAR);
813
+ SERV *serv = lua_touserdata(lua, -1);
814
+ bool rv = tculogadbvanish(serv->ulog, serv->sid, 0, serv->adb);
815
+ lua_settop(lua, 0);
816
+ lua_pushboolean(lua, rv);
817
+ return 1;
818
+ }
819
+
820
+
821
+ /* for _rnum function */
822
+ static int serv_rnum(lua_State *lua){
823
+ int argc = lua_gettop(lua);
824
+ if(argc != 0){
825
+ lua_pushstring(lua, "_rnum: invalid arguments");
826
+ lua_error(lua);
827
+ }
828
+ lua_getglobal(lua, SERVVAR);
829
+ SERV *serv = lua_touserdata(lua, -1);
830
+ uint64_t rnum = tcadbrnum(serv->adb);
831
+ lua_settop(lua, 0);
832
+ lua_pushnumber(lua, rnum);
833
+ return 1;
834
+ }
835
+
836
+
837
+ /* for _size function */
838
+ static int serv_size(lua_State *lua){
839
+ int argc = lua_gettop(lua);
840
+ if(argc != 0){
841
+ lua_pushstring(lua, "_size: invalid arguments");
842
+ lua_error(lua);
843
+ }
844
+ lua_getglobal(lua, SERVVAR);
845
+ SERV *serv = lua_touserdata(lua, -1);
846
+ uint64_t size = tcadbsize(serv->adb);
847
+ lua_settop(lua, 0);
848
+ lua_pushnumber(lua, size);
849
+ return 1;
850
+ }
851
+
852
+
853
+ /* for _misc function */
854
+ static int serv_misc(lua_State *lua){
855
+ int argc = lua_gettop(lua);
856
+ if(argc < 1){
857
+ lua_pushstring(lua, "_misc: invalid arguments");
858
+ lua_error(lua);
859
+ }
860
+ const char *name = lua_tostring(lua, 1);
861
+ if(!name){
862
+ lua_pushstring(lua, "_misc: invalid arguments");
863
+ lua_error(lua);
864
+ }
865
+ bool ulog = true;
866
+ if(*name == '$'){
867
+ name++;
868
+ ulog = false;
869
+ }
870
+ TCLIST *args = tclistnew();
871
+ for(int i = 2; i <= argc; i++){
872
+ const char *aptr;
873
+ size_t asiz;
874
+ int len;
875
+ switch(lua_type(lua, i)){
876
+ case LUA_TNUMBER:
877
+ case LUA_TSTRING:
878
+ aptr = lua_tolstring(lua, i, &asiz);
879
+ tclistpush(args, aptr, asiz);
880
+ break;
881
+ case LUA_TTABLE:
882
+ len = lua_objlen(lua, i);
883
+ for(int j = 1; j <= len; j++){
884
+ lua_rawgeti(lua, i, j);
885
+ switch(lua_type(lua, -1)){
886
+ case LUA_TNUMBER:
887
+ case LUA_TSTRING:
888
+ aptr = lua_tolstring(lua, -1, &asiz);
889
+ tclistpush(args, aptr, asiz);
890
+ break;
891
+ }
892
+ lua_pop(lua, 1);
893
+ }
894
+ break;
895
+ }
896
+ }
897
+ lua_getglobal(lua, SERVVAR);
898
+ SERV *serv = lua_touserdata(lua, -1);
899
+ TCLIST *res = ulog ? tculogadbmisc(serv->ulog, serv->sid, 0, serv->adb, name, args) :
900
+ tcadbmisc(serv->adb, name, args);
901
+ lua_settop(lua, 0);
902
+ if(res){
903
+ int rnum = tclistnum(res);
904
+ lua_createtable(lua, rnum, 0);
905
+ for(int i = 0; i < rnum; i++){
906
+ int rsiz;
907
+ const char *rbuf = tclistval(res, i, &rsiz);
908
+ lua_pushlstring(lua, rbuf, rsiz);
909
+ lua_rawseti(lua, 1, i + 1);
910
+ }
911
+ tclistdel(res);
912
+ } else {
913
+ lua_pushnil(lua);
914
+ }
915
+ tclistdel(args);
916
+ return 1;
917
+ }
918
+
919
+
920
+ /* for _foreach function */
921
+ static int serv_foreach(lua_State *lua){
922
+ int argc = lua_gettop(lua);
923
+ if(argc != 1){
924
+ lua_pushstring(lua, "_foreach: invalid arguments");
925
+ lua_error(lua);
926
+ }
927
+ if(!lua_isfunction(lua, 1)){
928
+ lua_pushstring(lua, "_foreach: invalid arguments");
929
+ lua_error(lua);
930
+ }
931
+ lua_getglobal(lua, SERVVAR);
932
+ SERV *serv = lua_touserdata(lua, -1);
933
+ lua_pushvalue(lua, 1);
934
+ lua_setglobal(lua, ITERVAR);
935
+ bool err = false;
936
+ if(!tcadbforeach(serv->adb, (TCITER)iterrec, lua)) err = true;
937
+ lua_pushnil(lua);
938
+ lua_setglobal(lua, ITERVAR);
939
+ lua_settop(lua, 0);
940
+ lua_pushboolean(lua, !err);
941
+ return 1;
942
+ }
943
+
944
+
945
+ /* for _mapreduce function */
946
+ static int serv_mapreduce(lua_State *lua){
947
+ int argc = lua_gettop(lua);
948
+ if(argc < 2){
949
+ lua_pushstring(lua, "_mapreduce: invalid arguments");
950
+ lua_error(lua);
951
+ }
952
+ if(!lua_isfunction(lua, 1) || !lua_isfunction(lua, 2)){
953
+ lua_pushstring(lua, "_mapreduce: invalid arguments");
954
+ lua_error(lua);
955
+ }
956
+ lua_pushvalue(lua, 1);
957
+ lua_setglobal(lua, MRMAPVAR);
958
+ lua_pushvalue(lua, 2);
959
+ lua_setglobal(lua, MRREDVAR);
960
+ TCLIST *keys = NULL;
961
+ if(argc > 2){
962
+ const char *kbuf;
963
+ size_t ksiz;
964
+ int len;
965
+ switch(lua_type(lua, 3)){
966
+ case LUA_TNUMBER:
967
+ case LUA_TSTRING:
968
+ keys = tclistnew2(1);
969
+ kbuf = lua_tolstring(lua, 3, &ksiz);
970
+ tclistpush(keys, kbuf, ksiz);
971
+ break;
972
+ case LUA_TTABLE:
973
+ len = lua_objlen(lua, 3);
974
+ keys = tclistnew2(len);
975
+ for(int i = 1; i <= len; i++){
976
+ lua_rawgeti(lua, 3, i);
977
+ switch(lua_type(lua, -1)){
978
+ case LUA_TNUMBER:
979
+ case LUA_TSTRING:
980
+ kbuf = lua_tolstring(lua, -1, &ksiz);
981
+ tclistpush(keys, kbuf, ksiz);
982
+ break;
983
+ }
984
+ lua_pop(lua, 1);
985
+ }
986
+ break;
987
+ }
988
+ }
989
+ lua_getglobal(lua, SERVVAR);
990
+ SERV *serv = lua_touserdata(lua, -1);
991
+ bool err = false;
992
+ TCBDB *bdb = tcbdbnew();
993
+ lua_getglobal(lua, "_tmpdir_");
994
+ const char *tmpdir = lua_tostring(lua, -1);
995
+ if(!tmpdir) tmpdir = "/tmp";
996
+ char *path = tcsprintf("%s%c%s-%d-%u",
997
+ tmpdir, MYPATHCHR, "mapbdb", getpid(), (unsigned int)(tctime() * 1000));
998
+ unlink(path);
999
+ if(!tcbdbopen(bdb, path, BDBOWRITER | BDBOCREAT | BDBOTRUNC)) err = true;
1000
+ unlink(path);
1001
+ tcfree(path);
1002
+ if(!tcadbmapbdb(serv->adb, keys, bdb, (ADBMAPPROC)maprec, lua, -1)) err = true;
1003
+ if(!err){
1004
+ BDBCUR *cur = tcbdbcurnew(bdb);
1005
+ tcbdbcurfirst(cur);
1006
+ const char *lbuf = NULL;
1007
+ int lsiz = 0;
1008
+ int lnum = 0;
1009
+ const char *kbuf;
1010
+ int ksiz;
1011
+ while(!err && (kbuf = tcbdbcurkey3(cur, &ksiz)) != NULL){
1012
+ int vsiz;
1013
+ const char *vbuf = tcbdbcurval3(cur, &vsiz);
1014
+ if(lbuf && lsiz == ksiz && !memcmp(lbuf, kbuf, lsiz)){
1015
+ lua_pushlstring(lua, vbuf, vsiz);
1016
+ lua_rawseti(lua, -2, ++lnum);
1017
+ } else {
1018
+ if(lbuf){
1019
+ if(lua_pcall(lua, 2, 1, 0) != 0){
1020
+ reporterror(lua);
1021
+ err = true;
1022
+ } else if(lua_gettop(lua) < 1 || !lua_toboolean(lua, 1)){
1023
+ err = true;
1024
+ }
1025
+ }
1026
+ lua_settop(lua, 0);
1027
+ lua_getglobal(lua, MRREDVAR);
1028
+ lua_pushlstring(lua, kbuf, ksiz);
1029
+ lua_newtable(lua);
1030
+ lnum = 1;
1031
+ lua_pushlstring(lua, vbuf, vsiz);
1032
+ lua_rawseti(lua, -2, lnum);
1033
+ }
1034
+ lbuf = kbuf;
1035
+ lsiz = ksiz;
1036
+ tcbdbcurnext(cur);
1037
+ }
1038
+ if(lbuf){
1039
+ if(lua_pcall(lua, 2, 1, 0) != 0){
1040
+ reporterror(lua);
1041
+ err = true;
1042
+ } else if(lua_gettop(lua) < 1 || !lua_toboolean(lua, 1)){
1043
+ err = true;
1044
+ }
1045
+ lua_settop(lua, 0);
1046
+ }
1047
+ tcbdbcurdel(cur);
1048
+ }
1049
+ if(!tcbdbclose(bdb)) err = true;
1050
+ tcbdbdel(bdb);
1051
+ if(keys) tclistdel(keys);
1052
+ lua_pushnil(lua);
1053
+ lua_setglobal(lua, MRREDVAR);
1054
+ lua_pushnil(lua);
1055
+ lua_setglobal(lua, MRMAPVAR);
1056
+ lua_settop(lua, 0);
1057
+ lua_pushboolean(lua, !err);
1058
+ return 1;
1059
+ }
1060
+
1061
+
1062
+ /* for _mapreduce function */
1063
+ static int serv_mapreducemapemit(lua_State *lua){
1064
+ int argc = lua_gettop(lua);
1065
+ if(argc != 2){
1066
+ lua_pushstring(lua, "_mapreducemapemit: invalid arguments");
1067
+ lua_error(lua);
1068
+ }
1069
+ size_t ksiz;
1070
+ const char *kbuf = lua_tolstring(lua, 1, &ksiz);
1071
+ size_t vsiz;
1072
+ const char *vbuf = lua_tolstring(lua, 2, &vsiz);
1073
+ if(!kbuf || !vbuf){
1074
+ lua_pushstring(lua, "_mapreducemapemit: invalid arguments");
1075
+ lua_error(lua);
1076
+ }
1077
+ lua_getglobal(lua, MRPOOLVAR);
1078
+ void *map = lua_touserdata(lua, -1);
1079
+ bool rv = tcadbmapbdbemit(map, kbuf, ksiz, vbuf, vsiz);
1080
+ lua_settop(lua, 0);
1081
+ lua_pushboolean(lua, rv);
1082
+ return 1;
1083
+ }
1084
+
1085
+
1086
+ /* for _stashput function */
1087
+ static int serv_stashput(lua_State *lua){
1088
+ int argc = lua_gettop(lua);
1089
+ if(argc != 2){
1090
+ lua_pushstring(lua, "_stashput: invalid arguments");
1091
+ lua_error(lua);
1092
+ }
1093
+ size_t ksiz;
1094
+ const char *kbuf = lua_tolstring(lua, 1, &ksiz);
1095
+ size_t vsiz;
1096
+ const char *vbuf = lua_tolstring(lua, 2, &vsiz);
1097
+ if(!kbuf || !vbuf){
1098
+ lua_pushstring(lua, "_stashput: invalid arguments");
1099
+ lua_error(lua);
1100
+ }
1101
+ lua_getglobal(lua, SERVVAR);
1102
+ SERV *serv = lua_touserdata(lua, -1);
1103
+ tcmdbput(serv->stash, kbuf, ksiz, vbuf, vsiz);
1104
+ lua_pushboolean(lua, true);
1105
+ return 1;
1106
+ }
1107
+
1108
+
1109
+ /* for _stashputkeep function */
1110
+ static int serv_stashputkeep(lua_State *lua){
1111
+ int argc = lua_gettop(lua);
1112
+ if(argc != 2){
1113
+ lua_pushstring(lua, "_stashputkeep: invalid arguments");
1114
+ lua_error(lua);
1115
+ }
1116
+ size_t ksiz;
1117
+ const char *kbuf = lua_tolstring(lua, 1, &ksiz);
1118
+ size_t vsiz;
1119
+ const char *vbuf = lua_tolstring(lua, 2, &vsiz);
1120
+ if(!kbuf || !vbuf){
1121
+ lua_pushstring(lua, "_stashputkeep: invalid arguments");
1122
+ lua_error(lua);
1123
+ }
1124
+ lua_getglobal(lua, SERVVAR);
1125
+ SERV *serv = lua_touserdata(lua, -1);
1126
+ tcmdbputkeep(serv->stash, kbuf, ksiz, vbuf, vsiz);
1127
+ lua_pushboolean(lua, true);
1128
+ return 1;
1129
+ }
1130
+
1131
+
1132
+ /* for _stashputcat function */
1133
+ static int serv_stashputcat(lua_State *lua){
1134
+ int argc = lua_gettop(lua);
1135
+ if(argc != 2){
1136
+ lua_pushstring(lua, "_stashputcat: invalid arguments");
1137
+ lua_error(lua);
1138
+ }
1139
+ size_t ksiz;
1140
+ const char *kbuf = lua_tolstring(lua, 1, &ksiz);
1141
+ size_t vsiz;
1142
+ const char *vbuf = lua_tolstring(lua, 2, &vsiz);
1143
+ if(!kbuf || !vbuf){
1144
+ lua_pushstring(lua, "_stashputcat: invalid arguments");
1145
+ lua_error(lua);
1146
+ }
1147
+ lua_getglobal(lua, SERVVAR);
1148
+ SERV *serv = lua_touserdata(lua, -1);
1149
+ tcmdbputcat(serv->stash, kbuf, ksiz, vbuf, vsiz);
1150
+ lua_pushboolean(lua, true);
1151
+ return 1;
1152
+ }
1153
+
1154
+
1155
+ /* for _stashout function */
1156
+ static int serv_stashout(lua_State *lua){
1157
+ int argc = lua_gettop(lua);
1158
+ if(argc != 1){
1159
+ lua_pushstring(lua, "_stashout: invalid arguments");
1160
+ lua_error(lua);
1161
+ }
1162
+ size_t ksiz;
1163
+ const char *kbuf = lua_tolstring(lua, 1, &ksiz);
1164
+ if(!kbuf){
1165
+ lua_pushstring(lua, "_stashout: invalid arguments");
1166
+ lua_error(lua);
1167
+ }
1168
+ lua_getglobal(lua, SERVVAR);
1169
+ SERV *serv = lua_touserdata(lua, -1);
1170
+ bool rv = tcmdbout(serv->stash, kbuf, ksiz);
1171
+ lua_pushboolean(lua, rv);
1172
+ return 1;
1173
+ }
1174
+
1175
+
1176
+ /* for _stashget function */
1177
+ static int serv_stashget(lua_State *lua){
1178
+ int argc = lua_gettop(lua);
1179
+ if(argc != 1){
1180
+ lua_pushstring(lua, "_stashget: invalid arguments");
1181
+ lua_error(lua);
1182
+ }
1183
+ size_t ksiz;
1184
+ const char *kbuf = lua_tolstring(lua, 1, &ksiz);
1185
+ if(!kbuf){
1186
+ lua_pushstring(lua, "_stashget: invalid arguments");
1187
+ lua_error(lua);
1188
+ }
1189
+ lua_getglobal(lua, SERVVAR);
1190
+ SERV *serv = lua_touserdata(lua, -1);
1191
+ int vsiz;
1192
+ char *vbuf = tcmdbget(serv->stash, kbuf, ksiz, &vsiz);
1193
+ if(vbuf){
1194
+ lua_pushlstring(lua, vbuf, vsiz);
1195
+ tcfree(vbuf);
1196
+ } else {
1197
+ lua_pushnil(lua);
1198
+ }
1199
+ return 1;
1200
+ }
1201
+
1202
+
1203
+ /* for _stashvanish function */
1204
+ static int serv_stashvanish(lua_State *lua){
1205
+ int argc = lua_gettop(lua);
1206
+ if(argc != 0){
1207
+ lua_pushstring(lua, "_stashvanish: invalid arguments");
1208
+ lua_error(lua);
1209
+ }
1210
+ lua_getglobal(lua, SERVVAR);
1211
+ SERV *serv = lua_touserdata(lua, -1);
1212
+ tcmdbvanish(serv->stash);
1213
+ return 0;
1214
+ }
1215
+
1216
+
1217
+ /* for _stashforeach function */
1218
+ static int serv_stashforeach(lua_State *lua){
1219
+ int argc = lua_gettop(lua);
1220
+ if(argc != 1){
1221
+ lua_pushstring(lua, "_stashforeach: invalid arguments");
1222
+ lua_error(lua);
1223
+ }
1224
+ if(!lua_isfunction(lua, 1)){
1225
+ lua_pushstring(lua, "_stashforeach: invalid arguments");
1226
+ lua_error(lua);
1227
+ }
1228
+ lua_getglobal(lua, SERVVAR);
1229
+ SERV *serv = lua_touserdata(lua, -1);
1230
+ lua_pushvalue(lua, 1);
1231
+ lua_setglobal(lua, ITERVAR);
1232
+ tcmdbforeach(serv->stash, (TCITER)iterrec, lua);
1233
+ lua_pushnil(lua);
1234
+ lua_setglobal(lua, ITERVAR);
1235
+ return 0;
1236
+ }
1237
+
1238
+
1239
+ /* for _lock function */
1240
+ static int serv_lock(lua_State *lua){
1241
+ int argc = lua_gettop(lua);
1242
+ if(argc != 1){
1243
+ lua_pushstring(lua, "_lock: invalid arguments");
1244
+ lua_error(lua);
1245
+ }
1246
+ size_t ksiz;
1247
+ const char *kbuf = lua_tolstring(lua, 1, &ksiz);
1248
+ if(!kbuf){
1249
+ lua_pushstring(lua, "_lock: invalid arguments");
1250
+ lua_error(lua);
1251
+ }
1252
+ lua_getglobal(lua, SERVVAR);
1253
+ SERV *serv = lua_touserdata(lua, -1);
1254
+ bool rv = true;
1255
+ while(!tcmdbputkeep(serv->lock, kbuf, ksiz, "", 0)){
1256
+ tcsleep(0.1);
1257
+ if(serv->term){
1258
+ rv = false;
1259
+ break;
1260
+ }
1261
+ }
1262
+ lua_settop(lua, 0);
1263
+ lua_pushboolean(lua, rv);
1264
+ return 1;
1265
+ }
1266
+
1267
+
1268
+ /* for _unlock function */
1269
+ static int serv_unlock(lua_State *lua){
1270
+ int argc = lua_gettop(lua);
1271
+ if(argc != 1){
1272
+ lua_pushstring(lua, "_unlock: invalid arguments");
1273
+ lua_error(lua);
1274
+ }
1275
+ size_t ksiz;
1276
+ const char *kbuf = lua_tolstring(lua, 1, &ksiz);
1277
+ if(!kbuf){
1278
+ lua_pushstring(lua, "_unlock: invalid arguments");
1279
+ lua_error(lua);
1280
+ }
1281
+ lua_getglobal(lua, SERVVAR);
1282
+ SERV *serv = lua_touserdata(lua, -1);
1283
+ bool rv = tcmdbout(serv->lock, kbuf, ksiz);
1284
+ lua_settop(lua, 0);
1285
+ lua_pushboolean(lua, rv);
1286
+ return 1;
1287
+ }
1288
+
1289
+
1290
+ /* for _pack function */
1291
+ static int serv_pack(lua_State *lua){
1292
+ int argc = lua_gettop(lua);
1293
+ if(argc < 1){
1294
+ lua_pushstring(lua, "_pack: invalid arguments");
1295
+ lua_error(lua);
1296
+ }
1297
+ const char *format = lua_tostring(lua, 1);
1298
+ if(!format){
1299
+ lua_pushstring(lua, "_pack: invalid arguments");
1300
+ lua_error(lua);
1301
+ }
1302
+ lua_newtable(lua);
1303
+ int aidx = argc + 1;
1304
+ int eidx = 1;
1305
+ for(int i = 2; i <= argc; i++){
1306
+ int len;
1307
+ switch(lua_type(lua, i)){
1308
+ case LUA_TNUMBER:
1309
+ case LUA_TSTRING:
1310
+ lua_pushvalue(lua, i);
1311
+ lua_rawseti(lua, aidx, eidx++);
1312
+ break;
1313
+ case LUA_TTABLE:
1314
+ len = lua_objlen(lua, i);
1315
+ for(int j = 1; j <= len; j++){
1316
+ lua_rawgeti(lua, i, j);
1317
+ lua_rawseti(lua, aidx, eidx++);
1318
+ }
1319
+ break;
1320
+ default:
1321
+ lua_pushnumber(lua, 0);
1322
+ lua_rawseti(lua, aidx, eidx++);
1323
+ break;
1324
+ }
1325
+ }
1326
+ lua_replace(lua, 2);
1327
+ lua_settop(lua, 2);
1328
+ TCXSTR *xstr = tcxstrnew();
1329
+ int emax = eidx - 1;
1330
+ eidx = 1;
1331
+ while(*format != '\0'){
1332
+ int c = *format;
1333
+ int loop = 1;
1334
+ if(format[1] == '*'){
1335
+ loop = INT_MAX;
1336
+ format++;
1337
+ } else if(format[1] >= '0' && format[1] <= '9'){
1338
+ format++;
1339
+ loop = 0;
1340
+ while(*format >= '0' && *format <= '9'){
1341
+ loop = loop * 10 + *format - '0';
1342
+ format++;
1343
+ }
1344
+ format--;
1345
+ }
1346
+ loop = tclmin(loop, emax);
1347
+ int end = tclmin(eidx + loop - 1, emax);
1348
+ while(eidx <= end){
1349
+ lua_rawgeti(lua, 2, eidx);
1350
+ double num = lua_tonumber(lua, 3);
1351
+ lua_pop(lua, 1);
1352
+ uint8_t cnum;
1353
+ uint16_t snum;
1354
+ uint32_t inum;
1355
+ uint64_t lnum;
1356
+ double dnum;
1357
+ float fnum;
1358
+ uint64_t wnum;
1359
+ char wbuf[TTNUMBUFSIZ], *wp;
1360
+ switch(c){
1361
+ case 'c':
1362
+ case 'C':
1363
+ cnum = num;
1364
+ tcxstrcat(xstr, &cnum, sizeof(cnum));
1365
+ break;
1366
+ case 's':
1367
+ case 'S':
1368
+ snum = num;
1369
+ tcxstrcat(xstr, &snum, sizeof(snum));
1370
+ break;
1371
+ case 'i':
1372
+ case 'I':
1373
+ inum = num;
1374
+ tcxstrcat(xstr, &inum, sizeof(inum));
1375
+ break;
1376
+ case 'l':
1377
+ case 'L':
1378
+ lnum = num;
1379
+ tcxstrcat(xstr, &lnum, sizeof(lnum));
1380
+ break;
1381
+ case 'f':
1382
+ case 'F':
1383
+ fnum = num;
1384
+ tcxstrcat(xstr, &fnum, sizeof(fnum));
1385
+ break;
1386
+ case 'd':
1387
+ case 'D':
1388
+ dnum = num;
1389
+ tcxstrcat(xstr, &dnum, sizeof(dnum));
1390
+ break;
1391
+ case 'n':
1392
+ snum = num;
1393
+ snum = TTHTONS(snum);
1394
+ tcxstrcat(xstr, &snum, sizeof(snum));
1395
+ break;
1396
+ case 'N':
1397
+ inum = num;
1398
+ inum = TTHTONL(inum);
1399
+ tcxstrcat(xstr, &inum, sizeof(inum));
1400
+ break;
1401
+ case 'M':
1402
+ lnum = num;
1403
+ lnum = TTHTONLL(lnum);
1404
+ tcxstrcat(xstr, &lnum, sizeof(lnum));
1405
+ break;
1406
+ case 'w':
1407
+ case 'W':
1408
+ wnum = num;
1409
+ wp = wbuf;
1410
+ if(wnum < (1ULL << 7)){
1411
+ *(wp++) = wnum;
1412
+ } else if(wnum < (1ULL << 14)){
1413
+ *(wp++) = (wnum >> 7) | 0x80;
1414
+ *(wp++) = wnum & 0x7f;
1415
+ } else if(wnum < (1ULL << 21)){
1416
+ *(wp++) = (wnum >> 14) | 0x80;
1417
+ *(wp++) = ((wnum >> 7) & 0x7f) | 0x80;
1418
+ *(wp++) = wnum & 0x7f;
1419
+ } else if(wnum < (1ULL << 28)){
1420
+ *(wp++) = (wnum >> 21) | 0x80;
1421
+ *(wp++) = ((wnum >> 14) & 0x7f) | 0x80;
1422
+ *(wp++) = ((wnum >> 7) & 0x7f) | 0x80;
1423
+ *(wp++) = wnum & 0x7f;
1424
+ } else if(wnum < (1ULL << 35)){
1425
+ *(wp++) = (wnum >> 28) | 0x80;
1426
+ *(wp++) = ((wnum >> 21) & 0x7f) | 0x80;
1427
+ *(wp++) = ((wnum >> 14) & 0x7f) | 0x80;
1428
+ *(wp++) = ((wnum >> 7) & 0x7f) | 0x80;
1429
+ *(wp++) = wnum & 0x7f;
1430
+ } else if(wnum < (1ULL << 42)){
1431
+ *(wp++) = (wnum >> 35) | 0x80;
1432
+ *(wp++) = ((wnum >> 28) & 0x7f) | 0x80;
1433
+ *(wp++) = ((wnum >> 21) & 0x7f) | 0x80;
1434
+ *(wp++) = ((wnum >> 14) & 0x7f) | 0x80;
1435
+ *(wp++) = ((wnum >> 7) & 0x7f) | 0x80;
1436
+ *(wp++) = wnum & 0x7f;
1437
+ } else if(wnum < (1ULL << 49)){
1438
+ *(wp++) = (wnum >> 42) | 0x80;
1439
+ *(wp++) = ((wnum >> 35) & 0x7f) | 0x80;
1440
+ *(wp++) = ((wnum >> 28) & 0x7f) | 0x80;
1441
+ *(wp++) = ((wnum >> 21) & 0x7f) | 0x80;
1442
+ *(wp++) = ((wnum >> 14) & 0x7f) | 0x80;
1443
+ *(wp++) = ((wnum >> 7) & 0x7f) | 0x80;
1444
+ *(wp++) = wnum & 0x7f;
1445
+ } else if(wnum < (1ULL << 56)){
1446
+ *(wp++) = (wnum >> 49) | 0x80;
1447
+ *(wp++) = ((wnum >> 42) & 0x7f) | 0x80;
1448
+ *(wp++) = ((wnum >> 35) & 0x7f) | 0x80;
1449
+ *(wp++) = ((wnum >> 28) & 0x7f) | 0x80;
1450
+ *(wp++) = ((wnum >> 21) & 0x7f) | 0x80;
1451
+ *(wp++) = ((wnum >> 14) & 0x7f) | 0x80;
1452
+ *(wp++) = ((wnum >> 7) & 0x7f) | 0x80;
1453
+ *(wp++) = wnum & 0x7f;
1454
+ } else {
1455
+ *(wp++) = (wnum >> 63) | 0x80;
1456
+ *(wp++) = ((wnum >> 49) & 0x7f) | 0x80;
1457
+ *(wp++) = ((wnum >> 42) & 0x7f) | 0x80;
1458
+ *(wp++) = ((wnum >> 35) & 0x7f) | 0x80;
1459
+ *(wp++) = ((wnum >> 28) & 0x7f) | 0x80;
1460
+ *(wp++) = ((wnum >> 21) & 0x7f) | 0x80;
1461
+ *(wp++) = ((wnum >> 14) & 0x7f) | 0x80;
1462
+ *(wp++) = ((wnum >> 7) & 0x7f) | 0x80;
1463
+ *(wp++) = wnum & 0x7f;
1464
+ }
1465
+ tcxstrcat(xstr, wbuf, wp - wbuf);
1466
+ break;
1467
+ }
1468
+ eidx++;
1469
+ }
1470
+ format++;
1471
+ if(eidx > emax) break;
1472
+ }
1473
+ lua_settop(lua, 0);
1474
+ lua_pushlstring(lua, tcxstrptr(xstr), tcxstrsize(xstr));
1475
+ tcxstrdel(xstr);
1476
+ return 1;
1477
+ }
1478
+
1479
+
1480
+ /* for _unpack function */
1481
+ static int serv_unpack(lua_State *lua){
1482
+ int argc = lua_gettop(lua);
1483
+ if(argc != 2){
1484
+ lua_pushstring(lua, "_unpack: invalid arguments");
1485
+ lua_error(lua);
1486
+ }
1487
+ const char *format = lua_tostring(lua, 1);
1488
+ size_t size;
1489
+ const char *buf = lua_tolstring(lua, 2, &size);
1490
+ if(!format){
1491
+ lua_pushstring(lua, "_unpack: invalid arguments");
1492
+ lua_error(lua);
1493
+ }
1494
+ if(!buf){
1495
+ buf = "";
1496
+ size = 0;
1497
+ }
1498
+ lua_newtable(lua);
1499
+ const char *rp = buf;
1500
+ int eidx = 1;
1501
+ while(*format != '\0'){
1502
+ int c = *format;
1503
+ int loop = 1;
1504
+ if(format[1] == '*'){
1505
+ loop = INT_MAX;
1506
+ format++;
1507
+ } else if(format[1] >= '0' && format[1] <= '9'){
1508
+ format++;
1509
+ loop = 0;
1510
+ while(*format >= '0' && *format <= '9'){
1511
+ loop = loop * 10 + *format - '0';
1512
+ format++;
1513
+ }
1514
+ format--;
1515
+ }
1516
+ loop = tclmin(loop, size);
1517
+ for(int i = 0; i < loop && size > 0; i++){
1518
+ uint8_t cnum;
1519
+ uint16_t snum;
1520
+ uint32_t inum;
1521
+ uint64_t lnum;
1522
+ float fnum;
1523
+ double dnum;
1524
+ uint64_t wnum;
1525
+ switch(c){
1526
+ case 'c':
1527
+ if(size >= sizeof(cnum)){
1528
+ memcpy(&cnum, rp, sizeof(cnum));
1529
+ lua_pushnumber(lua, (int8_t)cnum);
1530
+ lua_rawseti(lua, 3, eidx++);
1531
+ rp += sizeof(cnum);
1532
+ size -= sizeof(cnum);
1533
+ } else {
1534
+ size = 0;
1535
+ }
1536
+ break;
1537
+ case 'C':
1538
+ if(size >= sizeof(cnum)){
1539
+ memcpy(&cnum, rp, sizeof(cnum));
1540
+ lua_pushnumber(lua, (uint8_t)cnum);
1541
+ lua_rawseti(lua, 3, eidx++);
1542
+ rp += sizeof(cnum);
1543
+ size -= sizeof(cnum);
1544
+ } else {
1545
+ size = 0;
1546
+ }
1547
+ break;
1548
+ case 's':
1549
+ if(size >= sizeof(snum)){
1550
+ memcpy(&snum, rp, sizeof(snum));
1551
+ lua_pushnumber(lua, (int16_t)snum);
1552
+ lua_rawseti(lua, 3, eidx++);
1553
+ rp += sizeof(snum);
1554
+ size -= sizeof(snum);
1555
+ } else {
1556
+ size = 0;
1557
+ }
1558
+ break;
1559
+ case 'S':
1560
+ if(size >= sizeof(snum)){
1561
+ memcpy(&snum, rp, sizeof(snum));
1562
+ lua_pushnumber(lua, (uint16_t)snum);
1563
+ lua_rawseti(lua, 3, eidx++);
1564
+ rp += sizeof(snum);
1565
+ size -= sizeof(snum);
1566
+ } else {
1567
+ size = 0;
1568
+ }
1569
+ break;
1570
+ case 'i':
1571
+ if(size >= sizeof(inum)){
1572
+ memcpy(&inum, rp, sizeof(inum));
1573
+ lua_pushnumber(lua, (int32_t)inum);
1574
+ lua_rawseti(lua, 3, eidx++);
1575
+ rp += sizeof(inum);
1576
+ size -= sizeof(inum);
1577
+ } else {
1578
+ size = 0;
1579
+ }
1580
+ break;
1581
+ case 'I':
1582
+ if(size >= sizeof(inum)){
1583
+ memcpy(&inum, rp, sizeof(inum));
1584
+ lua_pushnumber(lua, (uint32_t)inum);
1585
+ lua_rawseti(lua, 3, eidx++);
1586
+ rp += sizeof(inum);
1587
+ size -= sizeof(inum);
1588
+ } else {
1589
+ size = 0;
1590
+ }
1591
+ break;
1592
+ case 'l':
1593
+ if(size >= sizeof(lnum)){
1594
+ memcpy(&lnum, rp, sizeof(lnum));
1595
+ lua_pushnumber(lua, (int64_t)lnum);
1596
+ lua_rawseti(lua, 3, eidx++);
1597
+ rp += sizeof(lnum);
1598
+ size -= sizeof(lnum);
1599
+ } else {
1600
+ size = 0;
1601
+ }
1602
+ break;
1603
+ case 'L':
1604
+ if(size >= sizeof(lnum)){
1605
+ memcpy(&lnum, rp, sizeof(lnum));
1606
+ lua_pushnumber(lua, (uint64_t)lnum);
1607
+ lua_rawseti(lua, 3, eidx++);
1608
+ rp += sizeof(lnum);
1609
+ size -= sizeof(lnum);
1610
+ } else {
1611
+ size = 0;
1612
+ }
1613
+ break;
1614
+ case 'f':
1615
+ case 'F':
1616
+ if(size >= sizeof(fnum)){
1617
+ memcpy(&fnum, rp, sizeof(fnum));
1618
+ lua_pushnumber(lua, (float)fnum);
1619
+ lua_rawseti(lua, 3, eidx++);
1620
+ rp += sizeof(fnum);
1621
+ size -= sizeof(fnum);
1622
+ } else {
1623
+ size = 0;
1624
+ }
1625
+ break;
1626
+ case 'd':
1627
+ case 'D':
1628
+ if(size >= sizeof(dnum)){
1629
+ memcpy(&dnum, rp, sizeof(dnum));
1630
+ lua_pushnumber(lua, (double)dnum);
1631
+ lua_rawseti(lua, 3, eidx++);
1632
+ rp += sizeof(dnum);
1633
+ size -= sizeof(dnum);
1634
+ } else {
1635
+ size = 0;
1636
+ }
1637
+ break;
1638
+ case 'n':
1639
+ if(size >= sizeof(snum)){
1640
+ memcpy(&snum, rp, sizeof(snum));
1641
+ snum = TTNTOHS(snum);
1642
+ lua_pushnumber(lua, (uint16_t)snum);
1643
+ lua_rawseti(lua, 3, eidx++);
1644
+ rp += sizeof(snum);
1645
+ size -= sizeof(snum);
1646
+ } else {
1647
+ size = 0;
1648
+ }
1649
+ break;
1650
+ case 'N':
1651
+ if(size >= sizeof(inum)){
1652
+ memcpy(&inum, rp, sizeof(inum));
1653
+ inum = TTNTOHL(inum);
1654
+ lua_pushnumber(lua, (uint32_t)inum);
1655
+ lua_rawseti(lua, 3, eidx++);
1656
+ rp += sizeof(inum);
1657
+ size -= sizeof(inum);
1658
+ } else {
1659
+ size = 0;
1660
+ }
1661
+ break;
1662
+ case 'M':
1663
+ if(size >= sizeof(lnum)){
1664
+ memcpy(&lnum, rp, sizeof(lnum));
1665
+ lnum = TTNTOHLL(lnum);
1666
+ lua_pushnumber(lua, (uint64_t)lnum);
1667
+ lua_rawseti(lua, 3, eidx++);
1668
+ rp += sizeof(lnum);
1669
+ size -= sizeof(lnum);
1670
+ } else {
1671
+ size = 0;
1672
+ }
1673
+ break;
1674
+ case 'w':
1675
+ case 'W':
1676
+ wnum = 0;
1677
+ do {
1678
+ inum = *(unsigned char *)rp;
1679
+ wnum = wnum * 0x80 + (inum & 0x7f);
1680
+ rp++;
1681
+ size--;
1682
+ } while(inum >= 0x80 && size > 0);
1683
+ lua_pushnumber(lua, wnum);
1684
+ lua_rawseti(lua, 3, eidx++);
1685
+ break;
1686
+ }
1687
+ }
1688
+ format++;
1689
+ if(size < 1) break;
1690
+ }
1691
+ lua_replace(lua, 1);
1692
+ lua_settop(lua, 1);
1693
+ return 1;
1694
+ }
1695
+
1696
+
1697
+ /* for _split function */
1698
+ static int serv_split(lua_State *lua){
1699
+ int argc = lua_gettop(lua);
1700
+ if(argc < 1){
1701
+ lua_pushstring(lua, "_split: invalid arguments");
1702
+ lua_error(lua);
1703
+ }
1704
+ size_t isiz;
1705
+ const char *ibuf = lua_tolstring(lua, 1, &isiz);
1706
+ if(!ibuf){
1707
+ lua_pushstring(lua, "_split: invalid arguments");
1708
+ lua_error(lua);
1709
+ }
1710
+ const char *delims = argc > 1 ? lua_tostring(lua, 2) : NULL;
1711
+ lua_newtable(lua);
1712
+ int lnum = 1;
1713
+ if(delims){
1714
+ const char *str = ibuf;
1715
+ while(true){
1716
+ const char *sp = str;
1717
+ while(*str != '\0' && !strchr(delims, *str)){
1718
+ str++;
1719
+ }
1720
+ lua_pushlstring(lua, sp, str - sp);
1721
+ lua_rawseti(lua, -2, lnum++);
1722
+ if(*str == '\0') break;
1723
+ str++;
1724
+ }
1725
+ } else {
1726
+ const char *ptr = ibuf;
1727
+ int size = isiz;
1728
+ while(size >= 0){
1729
+ const char *rp = ptr;
1730
+ const char *ep = ptr + size;
1731
+ while(rp < ep){
1732
+ if(*rp == '\0') break;
1733
+ rp++;
1734
+ }
1735
+ lua_pushlstring(lua, ptr, rp - ptr);
1736
+ lua_rawseti(lua, -2, lnum++);
1737
+ rp++;
1738
+ size -= rp - ptr;
1739
+ ptr = rp;
1740
+ }
1741
+ }
1742
+ lua_replace(lua, 1);
1743
+ lua_settop(lua, 1);
1744
+ return 1;
1745
+ }
1746
+
1747
+
1748
+ /* for _codec function */
1749
+ static int serv_codec(lua_State *lua){
1750
+ int argc = lua_gettop(lua);
1751
+ if(argc != 2){
1752
+ lua_pushstring(lua, "_codec: invalid arguments");
1753
+ lua_error(lua);
1754
+ }
1755
+ const char *mode = lua_tostring(lua, 1);
1756
+ size_t isiz;
1757
+ const char *ibuf = lua_tolstring(lua, 2, &isiz);
1758
+ if(!mode || !ibuf){
1759
+ lua_pushstring(lua, "_codec: invalid arguments");
1760
+ lua_error(lua);
1761
+ }
1762
+ char *obuf = NULL;
1763
+ int osiz = 0;
1764
+ if(*mode == '~'){
1765
+ mode++;
1766
+ if(!tcstricmp(mode, "url")){
1767
+ obuf = tcurldecode(ibuf, &osiz);
1768
+ } else if(!tcstricmp(mode, "base")){
1769
+ obuf = tcbasedecode(ibuf, &osiz);
1770
+ } else if(!tcstricmp(mode, "quote")){
1771
+ obuf = tcquotedecode(ibuf, &osiz);
1772
+ } else if(!tcstricmp(mode, "hex")){
1773
+ obuf = tchexdecode(ibuf, &osiz);
1774
+ } else if(!tcstricmp(mode, "pack")){
1775
+ obuf = tcpackdecode(ibuf, isiz, &osiz);
1776
+ } else if(!tcstricmp(mode, "tcbs")){
1777
+ obuf = tcbsdecode(ibuf, isiz, &osiz);
1778
+ } else if(!tcstricmp(mode, "deflate")){
1779
+ obuf = tcinflate(ibuf, isiz, &osiz);
1780
+ } else if(!tcstricmp(mode, "gzip")){
1781
+ obuf = tcgzipdecode(ibuf, isiz, &osiz);
1782
+ } else if(!tcstricmp(mode, "bzip")){
1783
+ obuf = tcbzipdecode(ibuf, isiz, &osiz);
1784
+ } else if(!tcstricmp(mode, "xml")){
1785
+ obuf = tcxmlunescape(ibuf);
1786
+ osiz = obuf ? strlen(obuf) : 0;
1787
+ }
1788
+ } else {
1789
+ if(!tcstricmp(mode, "url")){
1790
+ obuf = tcurlencode(ibuf, isiz);
1791
+ osiz = obuf ? strlen(obuf) : 0;
1792
+ } else if(!tcstricmp(mode, "base")){
1793
+ obuf = tcbaseencode(ibuf, isiz);
1794
+ osiz = obuf ? strlen(obuf) : 0;
1795
+ } else if(!tcstricmp(mode, "quote")){
1796
+ obuf = tcquoteencode(ibuf, isiz);
1797
+ osiz = obuf ? strlen(obuf) : 0;
1798
+ } else if(!tcstricmp(mode, "hex")){
1799
+ obuf = tchexencode(ibuf, isiz);
1800
+ osiz = obuf ? strlen(obuf) : 0;
1801
+ } else if(!tcstricmp(mode, "pack")){
1802
+ obuf = tcpackencode(ibuf, isiz, &osiz);
1803
+ } else if(!tcstricmp(mode, "tcbs")){
1804
+ obuf = tcbsencode(ibuf, isiz, &osiz);
1805
+ } else if(!tcstricmp(mode, "deflate")){
1806
+ obuf = tcdeflate(ibuf, isiz, &osiz);
1807
+ } else if(!tcstricmp(mode, "gzip")){
1808
+ obuf = tcgzipencode(ibuf, isiz, &osiz);
1809
+ } else if(!tcstricmp(mode, "bzip")){
1810
+ obuf = tcbzipencode(ibuf, isiz, &osiz);
1811
+ } else if(!tcstricmp(mode, "xml")){
1812
+ obuf = tcxmlescape(ibuf);
1813
+ osiz = obuf ? strlen(obuf) : 0;
1814
+ }
1815
+ }
1816
+ lua_settop(lua, 0);
1817
+ if(obuf){
1818
+ lua_pushlstring(lua, obuf, osiz);
1819
+ tcfree(obuf);
1820
+ } else {
1821
+ lua_pushnil(lua);
1822
+ }
1823
+ return 1;
1824
+ }
1825
+
1826
+
1827
+ /* for _hash function */
1828
+ static int serv_hash(lua_State *lua){
1829
+ int argc = lua_gettop(lua);
1830
+ if(argc != 2){
1831
+ lua_pushstring(lua, "_hash: invalid arguments");
1832
+ lua_error(lua);
1833
+ }
1834
+ const char *mode = lua_tostring(lua, 1);
1835
+ size_t isiz;
1836
+ const char *ibuf = lua_tolstring(lua, 2, &isiz);
1837
+ if(!mode || !ibuf){
1838
+ lua_pushstring(lua, "_hash: invalid arguments");
1839
+ lua_error(lua);
1840
+ }
1841
+ if(!tcstricmp(mode, "md5")){
1842
+ char obuf[48];
1843
+ tcmd5hash(ibuf, isiz, obuf);
1844
+ lua_settop(lua, 0);
1845
+ lua_pushstring(lua, obuf);
1846
+ } else if(!tcstricmp(mode, "md5raw")){
1847
+ char obuf[48];
1848
+ tcmd5hash(ibuf, isiz, obuf);
1849
+ int esiz;
1850
+ char *ebuf = tchexdecode(obuf, &esiz);
1851
+ lua_settop(lua, 0);
1852
+ lua_pushlstring(lua, ebuf, esiz);
1853
+ tcfree(ebuf);
1854
+ } else if(!tcstricmp(mode, "crc32")){
1855
+ uint32_t crc = tcgetcrc(ibuf, isiz);
1856
+ lua_settop(lua, 0);
1857
+ lua_pushnumber(lua, crc);
1858
+ } else {
1859
+ lua_settop(lua, 0);
1860
+ lua_pushnil(lua);
1861
+ }
1862
+ return 1;
1863
+ }
1864
+
1865
+
1866
+ /* for _bit function */
1867
+ static int serv_bit(lua_State *lua){
1868
+ int argc = lua_gettop(lua);
1869
+ if(argc < 2){
1870
+ lua_pushstring(lua, "_bit: invalid arguments");
1871
+ lua_error(lua);
1872
+ }
1873
+ const char *mode = lua_tostring(lua, 1);
1874
+ uint32_t num = lua_tonumber(lua, 2);
1875
+ uint32_t aux = argc > 2 ? lua_tonumber(lua, 3) : 0;
1876
+ if(!mode){
1877
+ lua_pushstring(lua, "_bit: invalid arguments");
1878
+ lua_error(lua);
1879
+ } else if(!tcstricmp(mode, "and")){
1880
+ num &= aux;
1881
+ } else if(!tcstricmp(mode, "or")){
1882
+ num |= aux;
1883
+ } else if(!tcstricmp(mode, "xor")){
1884
+ num ^= aux;
1885
+ } else if(!tcstricmp(mode, "not")){
1886
+ num = ~num;
1887
+ } else if(!tcstricmp(mode, "left")){
1888
+ num <<= aux;
1889
+ } else if(!tcstricmp(mode, "right")){
1890
+ num >>= aux;
1891
+ } else {
1892
+ lua_pushstring(lua, "_bit: invalid arguments");
1893
+ lua_error(lua);
1894
+ }
1895
+ lua_settop(lua, 0);
1896
+ lua_pushnumber(lua, num);
1897
+ return 1;
1898
+ }
1899
+
1900
+
1901
+ /* for _strstr function */
1902
+ static int serv_strstr(lua_State *lua){
1903
+ int argc = lua_gettop(lua);
1904
+ if(argc < 2){
1905
+ lua_pushstring(lua, "_strstr: invalid arguments");
1906
+ lua_error(lua);
1907
+ }
1908
+ const char *str = lua_tostring(lua, 1);
1909
+ const char *pat = lua_tostring(lua, 2);
1910
+ if(!str || !pat){
1911
+ lua_pushstring(lua, "_strstr: invalid arguments");
1912
+ lua_error(lua);
1913
+ }
1914
+ const char *alt = argc > 2 ? lua_tostring(lua, 3) : NULL;
1915
+ if(alt){
1916
+ TCXSTR *xstr = tcxstrnew();
1917
+ int plen = strlen(pat);
1918
+ int alen = strlen(alt);
1919
+ if(plen > 0){
1920
+ char *pv;
1921
+ while((pv = strstr(str, pat)) != NULL){
1922
+ tcxstrcat(xstr, str, pv - str);
1923
+ tcxstrcat(xstr, alt, alen);
1924
+ str = pv + plen;
1925
+ }
1926
+ }
1927
+ tcxstrcat2(xstr, str);
1928
+ lua_settop(lua, 0);
1929
+ lua_pushstring(lua, tcxstrptr(xstr));
1930
+ tcxstrdel(xstr);
1931
+ } else {
1932
+ char *pv = strstr(str, pat);
1933
+ if(pv){
1934
+ int idx = pv - str + 1;
1935
+ lua_settop(lua, 0);
1936
+ lua_pushinteger(lua, idx);
1937
+ } else {
1938
+ lua_settop(lua, 0);
1939
+ lua_pushinteger(lua, 0);
1940
+ }
1941
+ }
1942
+ return 1;
1943
+ }
1944
+
1945
+
1946
+ /* for _regex function */
1947
+ static int serv_regex(lua_State *lua){
1948
+ int argc = lua_gettop(lua);
1949
+ if(argc < 2){
1950
+ lua_pushstring(lua, "_regex: invalid arguments");
1951
+ lua_error(lua);
1952
+ }
1953
+ const char *str = lua_tostring(lua, 1);
1954
+ const char *regex = lua_tostring(lua, 2);
1955
+ if(!str || !regex){
1956
+ lua_pushstring(lua, "_regex: invalid arguments");
1957
+ lua_error(lua);
1958
+ }
1959
+ const char *alt = argc > 2 ? lua_tostring(lua, 3) : NULL;
1960
+ if(alt){
1961
+ char *res = tcregexreplace(str, regex, alt);
1962
+ lua_settop(lua, 0);
1963
+ lua_pushstring(lua, res);
1964
+ tcfree(res);
1965
+ } else {
1966
+ if(tcregexmatch(str, regex)){
1967
+ lua_settop(lua, 0);
1968
+ lua_pushboolean(lua, true);
1969
+ } else {
1970
+ lua_settop(lua, 0);
1971
+ lua_pushboolean(lua, false);
1972
+ }
1973
+ }
1974
+ return 1;
1975
+ }
1976
+
1977
+
1978
+ /* for _ucs function */
1979
+ static int serv_ucs(lua_State *lua){
1980
+ int argc = lua_gettop(lua);
1981
+ if(argc != 1){
1982
+ lua_pushstring(lua, "ucs: invalid arguments");
1983
+ lua_error(lua);
1984
+ }
1985
+ if(lua_type(lua, 1) == LUA_TTABLE){
1986
+ int anum = lua_objlen(lua, 1);
1987
+ uint16_t *ary = tcmalloc(sizeof(*ary) * anum + 1);
1988
+ for(int i = 1; i <= anum; i++){
1989
+ lua_rawgeti(lua, 1, i);
1990
+ ary[i-1] = lua_tointeger(lua, 2);
1991
+ lua_pop(lua, 1);
1992
+ }
1993
+ char *str = tcmalloc(anum * 3 + 1);
1994
+ tcstrucstoutf(ary, anum, str);
1995
+ lua_settop(lua, 0);
1996
+ lua_pushstring(lua, str);
1997
+ tcfree(str);
1998
+ tcfree(ary);
1999
+ } else {
2000
+ size_t len;
2001
+ const char *str = lua_tolstring(lua, 1, &len);
2002
+ if(!str){
2003
+ lua_pushstring(lua, "ucs: invalid arguments");
2004
+ lua_error(lua);
2005
+ }
2006
+ uint16_t *ary = tcmalloc(sizeof(*ary) * len + 1);
2007
+ int anum;
2008
+ tcstrutftoucs(str, ary, &anum);
2009
+ lua_settop(lua, 0);
2010
+ lua_createtable(lua, anum, 0);
2011
+ for(int i = 0; i < anum; i++){
2012
+ lua_pushinteger(lua, ary[i]);
2013
+ lua_rawseti(lua, 1, i + 1);
2014
+ }
2015
+ tcfree(ary);
2016
+ }
2017
+ return 1;
2018
+ }
2019
+
2020
+
2021
+ /* for _dist function */
2022
+ static int serv_dist(lua_State *lua){
2023
+ int argc = lua_gettop(lua);
2024
+ if(argc < 2){
2025
+ lua_pushstring(lua, "dist: invalid arguments");
2026
+ lua_error(lua);
2027
+ }
2028
+ const char *astr = lua_tostring(lua, 1);
2029
+ const char *bstr = lua_tostring(lua, 2);
2030
+ bool utf = argc > 2 ? lua_toboolean(lua, 3) : false;
2031
+ if(!astr || !bstr){
2032
+ lua_pushstring(lua, "dist: invalid arguments");
2033
+ lua_error(lua);
2034
+ }
2035
+ int rv = utf ? tcstrdistutf(astr, bstr) : tcstrdist(astr, bstr);
2036
+ lua_settop(lua, 0);
2037
+ lua_pushnumber(lua, rv);
2038
+ return 1;
2039
+ }
2040
+
2041
+
2042
+ /* for _isect function */
2043
+ static int serv_isect(lua_State *lua){
2044
+ int argc = lua_gettop(lua);
2045
+ if(argc == 1 && lua_type(lua, 1) == LUA_TTABLE){
2046
+ int len = lua_objlen(lua, 1);
2047
+ for(int i = 1; i <= len; i++){
2048
+ lua_rawgeti(lua, 1, i);
2049
+ if(lua_type(lua, -1) == LUA_TTABLE){
2050
+ argc++;
2051
+ } else {
2052
+ lua_pop(lua, 1);
2053
+ break;
2054
+ }
2055
+ }
2056
+ if(argc > 1){
2057
+ lua_remove(lua, 1);
2058
+ argc--;
2059
+ }
2060
+ }
2061
+ int tnum = 0;
2062
+ int rnum = 0;
2063
+ for(int i = 1; i <= argc; i++){
2064
+ if(lua_type(lua, i) != LUA_TTABLE) continue;
2065
+ int len = lua_objlen(lua, i);
2066
+ if(len < 1){
2067
+ lua_settop(lua, 0);
2068
+ lua_newtable(lua);
2069
+ return 1;
2070
+ }
2071
+ tnum++;
2072
+ rnum += len;
2073
+ }
2074
+ if(tnum == 2){
2075
+ TCMAP *former = NULL;
2076
+ TCMAP *latter = NULL;
2077
+ for(int i = 1; i <= argc; i++){
2078
+ if(lua_type(lua, i) != LUA_TTABLE) continue;
2079
+ int len = lua_objlen(lua, i);
2080
+ if(former){
2081
+ latter = tcmapnew2(tclmin(len, tcmaprnum(former)));
2082
+ for(int j = 1; j <= len; j++){
2083
+ lua_rawgeti(lua, i, j);
2084
+ size_t size;
2085
+ const char *ptr = lua_tolstring(lua, -1, &size);
2086
+ if(ptr){
2087
+ int vsiz;
2088
+ if(tcmapget(former, ptr, size, &vsiz)) tcmapput(latter, ptr, size, "", 0);
2089
+ }
2090
+ lua_pop(lua, 1);
2091
+ }
2092
+ break;
2093
+ } else {
2094
+ former = tcmapnew2(len);
2095
+ for(int j = 1; j <= len; j++){
2096
+ lua_rawgeti(lua, i, j);
2097
+ size_t size;
2098
+ const char *ptr = lua_tolstring(lua, -1, &size);
2099
+ if(ptr) tcmapput(former, ptr, size, "", 0);
2100
+ lua_pop(lua, 1);
2101
+ }
2102
+ }
2103
+ }
2104
+ lua_settop(lua, 0);
2105
+ if(latter){
2106
+ lua_createtable(lua, (int)tcmaprnum(latter), 0);
2107
+ tcmapiterinit(latter);
2108
+ int ridx = 1;
2109
+ const char *kbuf;
2110
+ int ksiz;
2111
+ while((kbuf = tcmapiternext(latter, &ksiz)) != NULL){
2112
+ lua_pushlstring(lua, kbuf, ksiz);
2113
+ lua_rawseti(lua, 1, ridx++);
2114
+ }
2115
+ tcmapdel(latter);
2116
+ } else {
2117
+ lua_newtable(lua);
2118
+ }
2119
+ if(former) tcmapdel(former);
2120
+ } else {
2121
+ TCMAP *freq = tcmapnew2(rnum);
2122
+ for(int i = 1; i <= argc; i++){
2123
+ if(lua_type(lua, i) != LUA_TTABLE) continue;
2124
+ int len = lua_objlen(lua, i);
2125
+ TCMAP *uniq = tcmapnew2(len);
2126
+ for(int j = 1; j <= len; j++){
2127
+ lua_rawgeti(lua, i, j);
2128
+ size_t size;
2129
+ const char *ptr = lua_tolstring(lua, -1, &size);
2130
+ if(ptr){
2131
+ int vsiz;
2132
+ if(!tcmapget(uniq, ptr, size, &vsiz)){
2133
+ tcmapaddint(freq, ptr, size, 1);
2134
+ tcmapput(uniq, ptr, size, "", 0);
2135
+ }
2136
+ }
2137
+ lua_pop(lua, 1);
2138
+ }
2139
+ tcmapdel(uniq);
2140
+ }
2141
+ lua_settop(lua, 0);
2142
+ lua_createtable(lua, (int)tcmaprnum(freq), 0);
2143
+ tcmapiterinit(freq);
2144
+ int ridx = 1;
2145
+ const char *kbuf;
2146
+ int ksiz;
2147
+ while((kbuf = tcmapiternext(freq, &ksiz)) != NULL){
2148
+ int vsiz;
2149
+ const char *vbuf = tcmapiterval(kbuf, &vsiz);
2150
+ int num = *(int *)vbuf;
2151
+ if(num != tnum) continue;
2152
+ lua_pushlstring(lua, kbuf, ksiz);
2153
+ lua_rawseti(lua, 1, ridx++);
2154
+ }
2155
+ tcmapdel(freq);
2156
+ }
2157
+ return 1;
2158
+ }
2159
+
2160
+
2161
+ /* for _union function */
2162
+ static int serv_union(lua_State *lua){
2163
+ int argc = lua_gettop(lua);
2164
+ if(argc == 1 && lua_type(lua, 1) == LUA_TTABLE){
2165
+ int len = lua_objlen(lua, 1);
2166
+ for(int i = 1; i <= len; i++){
2167
+ lua_rawgeti(lua, 1, i);
2168
+ if(lua_type(lua, -1) == LUA_TTABLE){
2169
+ argc++;
2170
+ } else {
2171
+ lua_pop(lua, 1);
2172
+ break;
2173
+ }
2174
+ }
2175
+ if(argc > 1){
2176
+ lua_remove(lua, 1);
2177
+ argc--;
2178
+ }
2179
+ }
2180
+ int rnum = 0;
2181
+ for(int i = 1; i <= argc; i++){
2182
+ if(lua_type(lua, i) != LUA_TTABLE) continue;
2183
+ rnum += lua_objlen(lua, i);
2184
+ }
2185
+ TCMAP *result = tcmapnew2(rnum);
2186
+ for(int i = 1; i <= argc; i++){
2187
+ if(lua_type(lua, i) != LUA_TTABLE) continue;
2188
+ int len = lua_objlen(lua, i);
2189
+ for(int j = 1; j <= len; j++){
2190
+ lua_rawgeti(lua, i, j);
2191
+ size_t size;
2192
+ const char *ptr = lua_tolstring(lua, -1, &size);
2193
+ if(ptr) tcmapput(result, ptr, size, "", 0);
2194
+ lua_pop(lua, 1);
2195
+ }
2196
+ }
2197
+ lua_settop(lua, 0);
2198
+ lua_createtable(lua, (int)tcmaprnum(result), 0);
2199
+ tcmapiterinit(result);
2200
+ int ridx = 1;
2201
+ const char *kbuf;
2202
+ int ksiz;
2203
+ while((kbuf = tcmapiternext(result, &ksiz)) != NULL){
2204
+ lua_pushlstring(lua, kbuf, ksiz);
2205
+ lua_rawseti(lua, 1, ridx++);
2206
+ }
2207
+ tcmapdel(result);
2208
+ return 1;
2209
+ }
2210
+
2211
+
2212
+ /* for _time function */
2213
+ static int serv_time(lua_State *lua){
2214
+ int argc = lua_gettop(lua);
2215
+ if(argc != 0){
2216
+ lua_pushstring(lua, "_time: invalid arguments");
2217
+ lua_error(lua);
2218
+ }
2219
+ lua_settop(lua, 0);
2220
+ lua_pushnumber(lua, tctime());
2221
+ return 1;
2222
+ }
2223
+
2224
+
2225
+ /* for _sleep function */
2226
+ static int serv_sleep(lua_State *lua){
2227
+ int argc = lua_gettop(lua);
2228
+ if(argc != 1){
2229
+ lua_pushstring(lua, "_sleep: invalid arguments");
2230
+ lua_error(lua);
2231
+ }
2232
+ double sec = lua_tonumber(lua, 1);
2233
+ if(!lua_isnumber(lua, 1)){
2234
+ lua_pushstring(lua, "_sleep: invalid arguments");
2235
+ lua_error(lua);
2236
+ }
2237
+ lua_settop(lua, 0);
2238
+ lua_pushboolean(lua, tcsleep(sec));
2239
+ return 1;
2240
+ }
2241
+
2242
+
2243
+ /* for stat function */
2244
+ static int serv_stat(lua_State *lua){
2245
+ int argc = lua_gettop(lua);
2246
+ if(argc != 1){
2247
+ lua_pushstring(lua, "_stat: invalid arguments");
2248
+ lua_error(lua);
2249
+ }
2250
+ const char *path = lua_tostring(lua, 1);
2251
+ if(!path){
2252
+ lua_pushstring(lua, "_stat: invalid arguments");
2253
+ lua_error(lua);
2254
+ }
2255
+ struct stat sbuf;
2256
+ if(lstat(path, &sbuf) == 0){
2257
+ lua_settop(lua, 0);
2258
+ lua_newtable(lua);
2259
+ lua_pushnumber(lua, sbuf.st_dev);
2260
+ lua_setfield(lua, -2, "dev");
2261
+ lua_pushnumber(lua, sbuf.st_ino);
2262
+ lua_setfield(lua, -2, "ino");
2263
+ lua_pushnumber(lua, sbuf.st_mode);
2264
+ lua_setfield(lua, -2, "mode");
2265
+ lua_pushnumber(lua, sbuf.st_nlink);
2266
+ lua_setfield(lua, -2, "nlink");
2267
+ lua_pushnumber(lua, sbuf.st_uid);
2268
+ lua_setfield(lua, -2, "uid");
2269
+ lua_pushnumber(lua, sbuf.st_gid);
2270
+ lua_setfield(lua, -2, "gid");
2271
+ lua_pushnumber(lua, sbuf.st_rdev);
2272
+ lua_setfield(lua, -2, "rdev");
2273
+ lua_pushnumber(lua, sbuf.st_size);
2274
+ lua_setfield(lua, -2, "size");
2275
+ lua_pushnumber(lua, sbuf.st_blksize);
2276
+ lua_setfield(lua, -2, "blksize");
2277
+ lua_pushnumber(lua, sbuf.st_blocks);
2278
+ lua_setfield(lua, -2, "blocks");
2279
+ lua_pushnumber(lua, sbuf.st_atime);
2280
+ lua_setfield(lua, -2, "atime");
2281
+ lua_pushnumber(lua, sbuf.st_mtime);
2282
+ lua_setfield(lua, -2, "mtime");
2283
+ lua_pushnumber(lua, sbuf.st_ctime);
2284
+ lua_setfield(lua, -2, "ctime");
2285
+ lua_pushboolean(lua, S_ISREG(sbuf.st_mode));
2286
+ lua_setfield(lua, -2, "_regular");
2287
+ lua_pushboolean(lua, S_ISDIR(sbuf.st_mode));
2288
+ lua_setfield(lua, -2, "_directory");
2289
+ bool readable = false;
2290
+ bool writable = false;
2291
+ bool executable = false;
2292
+ if(sbuf.st_uid == geteuid()){
2293
+ if(sbuf.st_mode & S_IRUSR) readable = true;
2294
+ if(sbuf.st_mode & S_IWUSR) writable = true;
2295
+ if(sbuf.st_mode & S_IXUSR) executable = true;
2296
+ }
2297
+ if(sbuf.st_gid == getegid()){
2298
+ if(sbuf.st_mode & S_IRGRP) readable = true;
2299
+ if(sbuf.st_mode & S_IWGRP) writable = true;
2300
+ if(sbuf.st_mode & S_IXGRP) executable = true;
2301
+ }
2302
+ if(sbuf.st_mode & S_IROTH) readable = true;
2303
+ if(sbuf.st_mode & S_IWOTH) writable = true;
2304
+ if(sbuf.st_mode & S_IXOTH) executable = true;
2305
+ lua_pushboolean(lua, readable);
2306
+ lua_setfield(lua, -2, "_readable");
2307
+ lua_pushboolean(lua, writable);
2308
+ lua_setfield(lua, -2, "_writable");
2309
+ lua_pushboolean(lua, executable);
2310
+ lua_setfield(lua, -2, "_executable");
2311
+ char *rpath = tcrealpath(path);
2312
+ if(rpath){
2313
+ lua_pushstring(lua, rpath);
2314
+ lua_setfield(lua, -2, "_realpath");
2315
+ tcfree(rpath);
2316
+ }
2317
+ } else {
2318
+ lua_settop(lua, 0);
2319
+ lua_pushnil(lua);
2320
+ }
2321
+ return 1;
2322
+ }
2323
+
2324
+
2325
+ /* for _glob function */
2326
+ static int serv_glob(lua_State *lua){
2327
+ int argc = lua_gettop(lua);
2328
+ if(argc != 1){
2329
+ lua_pushstring(lua, "_glob: invalid arguments");
2330
+ lua_error(lua);
2331
+ }
2332
+ const char *pattern = lua_tostring(lua, 1);
2333
+ if(!pattern){
2334
+ lua_pushstring(lua, "_glob: invalid arguments");
2335
+ lua_error(lua);
2336
+ }
2337
+ TCLIST *paths = tcglobpat(pattern);
2338
+ int pnum = tclistnum(paths);
2339
+ lua_settop(lua, 0);
2340
+ lua_createtable(lua, pnum, 0);
2341
+ for(int i = 0; i < pnum; i++){
2342
+ int size;
2343
+ const char *buf = tclistval(paths, i, &size);
2344
+ lua_pushlstring(lua, buf, size);
2345
+ lua_rawseti(lua, -2, i + 1);
2346
+ }
2347
+ tclistdel(paths);
2348
+ return 1;
2349
+ }
2350
+
2351
+
2352
+ /* for _remove function */
2353
+ static int serv_remove(lua_State *lua){
2354
+ int argc = lua_gettop(lua);
2355
+ if(argc != 1){
2356
+ lua_pushstring(lua, "_remove: invalid arguments");
2357
+ lua_error(lua);
2358
+ }
2359
+ const char *path = lua_tostring(lua, 1);
2360
+ if(!path){
2361
+ lua_pushstring(lua, "_remove: invalid arguments");
2362
+ lua_error(lua);
2363
+ }
2364
+ bool rv = tcremovelink(path);
2365
+ lua_settop(lua, 0);
2366
+ lua_pushboolean(lua, rv);
2367
+ return 1;
2368
+ }
2369
+
2370
+
2371
+ /* for _mkdir function */
2372
+ static int serv_mkdir(lua_State *lua){
2373
+ int argc = lua_gettop(lua);
2374
+ if(argc != 1){
2375
+ lua_pushstring(lua, "_mkdir: invalid arguments");
2376
+ lua_error(lua);
2377
+ }
2378
+ const char *path = lua_tostring(lua, 1);
2379
+ if(!path){
2380
+ lua_pushstring(lua, "_mkdir: invalid arguments");
2381
+ lua_error(lua);
2382
+ }
2383
+ bool rv = mkdir(path, 00755) == 0;
2384
+ lua_settop(lua, 0);
2385
+ lua_pushboolean(lua, rv);
2386
+ return 1;
2387
+ }
2388
+
2389
+
2390
+ #endif
2391
+
2392
+
2393
+
2394
+ // END OF FILE