script_core 0.2.2 → 0.2.7

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 (376) hide show
  1. checksums.yaml +4 -4
  2. data/.rubocop.yml +41 -45
  3. data/.travis.yml +2 -1
  4. data/Gemfile +3 -3
  5. data/README.md +7 -1
  6. data/bootstrap.sh +2 -2
  7. data/ext/enterprise_script_service/libseccomp/.travis.yml +24 -12
  8. data/ext/enterprise_script_service/libseccomp/CHANGELOG +32 -0
  9. data/ext/enterprise_script_service/libseccomp/CONTRIBUTING.md +37 -26
  10. data/ext/enterprise_script_service/libseccomp/CREDITS +11 -0
  11. data/ext/enterprise_script_service/libseccomp/README.md +21 -1
  12. data/ext/enterprise_script_service/libseccomp/configure.ac +13 -8
  13. data/ext/enterprise_script_service/libseccomp/doc/Makefile.am +6 -0
  14. data/ext/enterprise_script_service/libseccomp/doc/man/man3/seccomp_api_get.3 +12 -2
  15. data/ext/enterprise_script_service/libseccomp/doc/man/man3/seccomp_arch_add.3 +38 -6
  16. data/ext/enterprise_script_service/libseccomp/doc/man/man3/seccomp_attr_set.3 +53 -2
  17. data/ext/enterprise_script_service/libseccomp/doc/man/man3/seccomp_export_bpf.3 +20 -2
  18. data/ext/enterprise_script_service/libseccomp/doc/man/man3/seccomp_init.3 +9 -2
  19. data/ext/enterprise_script_service/libseccomp/doc/man/man3/seccomp_load.3 +32 -2
  20. data/ext/enterprise_script_service/libseccomp/doc/man/man3/seccomp_merge.3 +16 -2
  21. data/ext/enterprise_script_service/libseccomp/doc/man/man3/seccomp_notify_alloc.3 +113 -0
  22. data/ext/enterprise_script_service/libseccomp/doc/man/man3/seccomp_notify_fd.3 +1 -0
  23. data/ext/enterprise_script_service/libseccomp/doc/man/man3/seccomp_notify_free.3 +1 -0
  24. data/ext/enterprise_script_service/libseccomp/doc/man/man3/seccomp_notify_id_valid.3 +1 -0
  25. data/ext/enterprise_script_service/libseccomp/doc/man/man3/seccomp_notify_receive.3 +1 -0
  26. data/ext/enterprise_script_service/libseccomp/doc/man/man3/seccomp_notify_respond.3 +1 -0
  27. data/ext/enterprise_script_service/libseccomp/doc/man/man3/seccomp_rule_add.3 +64 -3
  28. data/ext/enterprise_script_service/libseccomp/doc/man/man3/seccomp_syscall_priority.3 +18 -3
  29. data/ext/enterprise_script_service/libseccomp/include/seccomp-syscalls.h +19 -0
  30. data/ext/enterprise_script_service/libseccomp/include/seccomp.h.in +116 -0
  31. data/ext/enterprise_script_service/libseccomp/src/.gitignore +2 -0
  32. data/ext/enterprise_script_service/libseccomp/src/Makefile.am +31 -17
  33. data/ext/enterprise_script_service/libseccomp/src/api.c +254 -58
  34. data/ext/enterprise_script_service/libseccomp/src/arch-aarch64.h +1 -9
  35. data/ext/enterprise_script_service/libseccomp/src/arch-arm.c +47 -2
  36. data/ext/enterprise_script_service/libseccomp/src/arch-arm.h +1 -9
  37. data/ext/enterprise_script_service/libseccomp/src/arch-gperf-generate +40 -0
  38. data/ext/enterprise_script_service/libseccomp/src/arch-mips.c +41 -4
  39. data/ext/enterprise_script_service/libseccomp/src/arch-mips.h +2 -10
  40. data/ext/enterprise_script_service/libseccomp/src/arch-mips64.c +41 -4
  41. data/ext/enterprise_script_service/libseccomp/src/arch-mips64.h +3 -11
  42. data/ext/enterprise_script_service/libseccomp/src/arch-mips64n32.c +41 -4
  43. data/ext/enterprise_script_service/libseccomp/src/arch-mips64n32.h +2 -10
  44. data/ext/enterprise_script_service/libseccomp/src/arch-parisc.h +1 -10
  45. data/ext/enterprise_script_service/libseccomp/src/arch-parisc64.c +3 -3
  46. data/ext/enterprise_script_service/libseccomp/src/arch-parisc64.h +29 -0
  47. data/ext/enterprise_script_service/libseccomp/src/arch-ppc.h +1 -9
  48. data/ext/enterprise_script_service/libseccomp/src/arch-ppc64.c +606 -8
  49. data/ext/enterprise_script_service/libseccomp/src/arch-ppc64.h +2 -10
  50. data/ext/enterprise_script_service/libseccomp/src/arch-riscv64.c +31 -0
  51. data/ext/enterprise_script_service/libseccomp/src/arch-riscv64.h +22 -0
  52. data/ext/enterprise_script_service/libseccomp/src/arch-s390.c +171 -12
  53. data/ext/enterprise_script_service/libseccomp/src/arch-s390.h +1 -17
  54. data/ext/enterprise_script_service/libseccomp/src/arch-s390x.c +166 -10
  55. data/ext/enterprise_script_service/libseccomp/src/arch-s390x.h +1 -20
  56. data/ext/enterprise_script_service/libseccomp/src/arch-syscall-dump.c +8 -1
  57. data/ext/enterprise_script_service/libseccomp/src/arch-syscall-validate +359 -143
  58. data/ext/enterprise_script_service/libseccomp/src/arch-x32.c +36 -2
  59. data/ext/enterprise_script_service/libseccomp/src/arch-x32.h +2 -10
  60. data/ext/enterprise_script_service/libseccomp/src/arch-x86.c +172 -10
  61. data/ext/enterprise_script_service/libseccomp/src/arch-x86.h +1 -14
  62. data/ext/enterprise_script_service/libseccomp/src/arch-x86_64.h +1 -9
  63. data/ext/enterprise_script_service/libseccomp/src/arch.c +11 -3
  64. data/ext/enterprise_script_service/libseccomp/src/arch.h +7 -0
  65. data/ext/enterprise_script_service/libseccomp/src/db.c +268 -57
  66. data/ext/enterprise_script_service/libseccomp/src/db.h +16 -2
  67. data/ext/enterprise_script_service/libseccomp/src/gen_bpf.c +503 -148
  68. data/ext/enterprise_script_service/libseccomp/src/gen_bpf.h +2 -1
  69. data/ext/enterprise_script_service/libseccomp/src/gen_pfc.c +165 -37
  70. data/ext/enterprise_script_service/libseccomp/src/python/libseccomp.pxd +37 -1
  71. data/ext/enterprise_script_service/libseccomp/src/python/seccomp.pyx +295 -5
  72. data/ext/enterprise_script_service/libseccomp/src/syscalls.c +56 -0
  73. data/ext/enterprise_script_service/libseccomp/src/syscalls.csv +470 -0
  74. data/ext/enterprise_script_service/libseccomp/src/syscalls.h +62 -0
  75. data/ext/enterprise_script_service/libseccomp/src/syscalls.perf.template +82 -0
  76. data/ext/enterprise_script_service/libseccomp/src/system.c +196 -16
  77. data/ext/enterprise_script_service/libseccomp/src/system.h +68 -13
  78. data/ext/enterprise_script_service/libseccomp/tests/.gitignore +10 -2
  79. data/ext/enterprise_script_service/libseccomp/tests/06-sim-actions.tests +1 -1
  80. data/ext/enterprise_script_service/libseccomp/tests/11-basic-basic_errors.c +5 -5
  81. data/ext/enterprise_script_service/libseccomp/tests/13-basic-attrs.c +35 -1
  82. data/ext/enterprise_script_service/libseccomp/tests/13-basic-attrs.py +10 -1
  83. data/ext/enterprise_script_service/libseccomp/tests/15-basic-resolver.c +4 -3
  84. data/ext/enterprise_script_service/libseccomp/tests/16-sim-arch_basic.c +12 -0
  85. data/ext/enterprise_script_service/libseccomp/tests/16-sim-arch_basic.py +1 -0
  86. data/ext/enterprise_script_service/libseccomp/tests/{18-sim-basic_whitelist.c → 18-sim-basic_allowlist.c} +0 -0
  87. data/ext/enterprise_script_service/libseccomp/tests/{18-sim-basic_whitelist.py → 18-sim-basic_allowlist.py} +0 -0
  88. data/ext/enterprise_script_service/libseccomp/tests/18-sim-basic_allowlist.tests +32 -0
  89. data/ext/enterprise_script_service/libseccomp/tests/23-sim-arch_all_le_basic.c +3 -0
  90. data/ext/enterprise_script_service/libseccomp/tests/23-sim-arch_all_le_basic.py +1 -0
  91. data/ext/enterprise_script_service/libseccomp/tests/30-sim-socket_syscalls.c +3 -0
  92. data/ext/enterprise_script_service/libseccomp/tests/30-sim-socket_syscalls.py +1 -0
  93. data/ext/enterprise_script_service/libseccomp/tests/30-sim-socket_syscalls.tests +33 -17
  94. data/ext/enterprise_script_service/libseccomp/tests/{34-sim-basic_blacklist.c → 34-sim-basic_denylist.c} +0 -0
  95. data/ext/enterprise_script_service/libseccomp/tests/{34-sim-basic_blacklist.py → 34-sim-basic_denylist.py} +0 -0
  96. data/ext/enterprise_script_service/libseccomp/tests/34-sim-basic_denylist.tests +32 -0
  97. data/ext/enterprise_script_service/libseccomp/tests/36-sim-ipc_syscalls.c +3 -0
  98. data/ext/enterprise_script_service/libseccomp/tests/36-sim-ipc_syscalls.py +1 -0
  99. data/ext/enterprise_script_service/libseccomp/tests/36-sim-ipc_syscalls.tests +25 -25
  100. data/ext/enterprise_script_service/libseccomp/tests/39-basic-api_level.c +24 -3
  101. data/ext/enterprise_script_service/libseccomp/tests/39-basic-api_level.py +16 -1
  102. data/ext/enterprise_script_service/libseccomp/tests/47-live-kill_process.c +3 -3
  103. data/ext/enterprise_script_service/libseccomp/tests/51-live-user_notification.c +112 -0
  104. data/ext/enterprise_script_service/libseccomp/tests/51-live-user_notification.py +60 -0
  105. data/ext/enterprise_script_service/libseccomp/tests/51-live-user_notification.tests +11 -0
  106. data/ext/enterprise_script_service/libseccomp/tests/52-basic-load.c +48 -0
  107. data/ext/enterprise_script_service/libseccomp/tests/52-basic-load.py +38 -0
  108. data/ext/enterprise_script_service/libseccomp/tests/52-basic-load.tests +11 -0
  109. data/ext/enterprise_script_service/libseccomp/tests/53-sim-binary_tree.c +156 -0
  110. data/ext/enterprise_script_service/libseccomp/tests/53-sim-binary_tree.py +95 -0
  111. data/ext/enterprise_script_service/libseccomp/tests/53-sim-binary_tree.tests +65 -0
  112. data/ext/enterprise_script_service/libseccomp/tests/54-live-binary_tree.c +128 -0
  113. data/ext/enterprise_script_service/libseccomp/tests/54-live-binary_tree.py +95 -0
  114. data/ext/enterprise_script_service/libseccomp/tests/54-live-binary_tree.tests +11 -0
  115. data/ext/enterprise_script_service/libseccomp/tests/55-basic-pfc_binary_tree.c +134 -0
  116. data/ext/enterprise_script_service/libseccomp/tests/55-basic-pfc_binary_tree.sh +46 -0
  117. data/ext/enterprise_script_service/libseccomp/tests/55-basic-pfc_binary_tree.tests +11 -0
  118. data/ext/enterprise_script_service/libseccomp/tests/56-basic-iterate_syscalls.c +90 -0
  119. data/ext/enterprise_script_service/libseccomp/tests/56-basic-iterate_syscalls.py +65 -0
  120. data/ext/enterprise_script_service/libseccomp/tests/56-basic-iterate_syscalls.tests +11 -0
  121. data/ext/enterprise_script_service/libseccomp/tests/57-basic-rawsysrc.c +64 -0
  122. data/ext/enterprise_script_service/libseccomp/tests/57-basic-rawsysrc.py +46 -0
  123. data/ext/enterprise_script_service/libseccomp/tests/57-basic-rawsysrc.tests +11 -0
  124. data/ext/enterprise_script_service/libseccomp/tests/58-live-tsync_notify.c +116 -0
  125. data/ext/enterprise_script_service/libseccomp/tests/58-live-tsync_notify.py +61 -0
  126. data/ext/enterprise_script_service/libseccomp/tests/58-live-tsync_notify.tests +11 -0
  127. data/ext/enterprise_script_service/libseccomp/tests/Makefile.am +34 -10
  128. data/ext/enterprise_script_service/libseccomp/tests/regression +10 -3
  129. data/ext/enterprise_script_service/libseccomp/tests/util.c +3 -3
  130. data/ext/enterprise_script_service/libseccomp/tools/Makefile.am +0 -3
  131. data/ext/enterprise_script_service/libseccomp/tools/check-syntax +1 -1
  132. data/ext/enterprise_script_service/libseccomp/tools/scmp_arch_detect.c +3 -0
  133. data/ext/enterprise_script_service/libseccomp/tools/scmp_bpf_disasm.c +4 -2
  134. data/ext/enterprise_script_service/libseccomp/tools/scmp_bpf_sim.c +4 -0
  135. data/ext/enterprise_script_service/libseccomp/tools/util.c +14 -12
  136. data/ext/enterprise_script_service/libseccomp/tools/util.h +7 -0
  137. data/ext/enterprise_script_service/mruby/.github/workflows/build.yml +106 -0
  138. data/ext/enterprise_script_service/mruby/.github/workflows/codeql-analysis.yml +51 -0
  139. data/ext/enterprise_script_service/mruby/.github/workflows/main.yml +24 -0
  140. data/ext/enterprise_script_service/mruby/.gitignore +3 -0
  141. data/ext/enterprise_script_service/mruby/.travis.yml +6 -9
  142. data/ext/enterprise_script_service/mruby/AUTHORS +1 -0
  143. data/ext/enterprise_script_service/mruby/Doxyfile +1 -1
  144. data/ext/enterprise_script_service/mruby/LICENSE +1 -1
  145. data/ext/enterprise_script_service/mruby/README.md +6 -2
  146. data/ext/enterprise_script_service/mruby/appveyor.yml +9 -12
  147. data/ext/enterprise_script_service/mruby/appveyor_config.rb +9 -0
  148. data/ext/enterprise_script_service/mruby/build_config.rb +6 -6
  149. data/ext/enterprise_script_service/mruby/doc/guides/compile.md +6 -2
  150. data/ext/enterprise_script_service/mruby/doc/guides/debugger.md +1 -1
  151. data/ext/enterprise_script_service/mruby/doc/guides/mrbconf.md +4 -8
  152. data/ext/enterprise_script_service/mruby/doc/limitations.md +10 -10
  153. data/ext/enterprise_script_service/mruby/doc/opcode.md +108 -95
  154. data/ext/enterprise_script_service/mruby/examples/targets/build_config_ArduinoDue.rb +2 -2
  155. data/ext/enterprise_script_service/mruby/examples/targets/build_config_IntelEdison.rb +2 -2
  156. data/ext/enterprise_script_service/mruby/examples/targets/build_config_IntelGalileo.rb +2 -2
  157. data/ext/enterprise_script_service/mruby/examples/targets/build_config_RX630.rb +2 -2
  158. data/ext/enterprise_script_service/mruby/examples/targets/build_config_chipKITMax32.rb +2 -2
  159. data/ext/enterprise_script_service/mruby/examples/targets/build_config_dreamcast_shelf.rb +108 -0
  160. data/ext/enterprise_script_service/mruby/include/mrbconf.h +10 -7
  161. data/ext/enterprise_script_service/mruby/include/mruby.h +24 -9
  162. data/ext/enterprise_script_service/mruby/include/mruby/array.h +4 -0
  163. data/ext/enterprise_script_service/mruby/include/mruby/boxing_nan.h +11 -2
  164. data/ext/enterprise_script_service/mruby/include/mruby/boxing_word.h +0 -10
  165. data/ext/enterprise_script_service/mruby/include/mruby/common.h +10 -0
  166. data/ext/enterprise_script_service/mruby/include/mruby/compile.h +11 -3
  167. data/ext/enterprise_script_service/mruby/include/mruby/dump.h +1 -17
  168. data/ext/enterprise_script_service/mruby/include/mruby/irep.h +10 -0
  169. data/ext/enterprise_script_service/mruby/include/mruby/istruct.h +4 -1
  170. data/ext/enterprise_script_service/mruby/include/mruby/khash.h +23 -5
  171. data/ext/enterprise_script_service/mruby/include/mruby/numeric.h +1 -0
  172. data/ext/enterprise_script_service/mruby/include/mruby/ops.h +3 -2
  173. data/ext/enterprise_script_service/mruby/include/mruby/proc.h +13 -8
  174. data/ext/enterprise_script_service/mruby/include/mruby/string.h +2 -1
  175. data/ext/enterprise_script_service/mruby/include/mruby/value.h +32 -41
  176. data/ext/enterprise_script_service/mruby/include/mruby/version.h +4 -4
  177. data/ext/enterprise_script_service/mruby/lib/mruby/build.rb +2 -30
  178. data/ext/enterprise_script_service/mruby/lib/mruby/build/command.rb +21 -46
  179. data/ext/enterprise_script_service/mruby/lib/mruby/gem.rb +9 -0
  180. data/ext/enterprise_script_service/mruby/lib/mruby/source.rb +3 -1
  181. data/ext/enterprise_script_service/mruby/mrbgems/default.gembox +7 -0
  182. data/ext/enterprise_script_service/mruby/mrbgems/mruby-array-ext/mrblib/array.rb +0 -31
  183. data/ext/enterprise_script_service/mruby/mrbgems/mruby-array-ext/src/array.c +5 -8
  184. data/ext/enterprise_script_service/mruby/mrbgems/mruby-array-ext/test/array.rb +0 -13
  185. data/ext/enterprise_script_service/mruby/mrbgems/mruby-bin-config/mrbgem.rake +5 -2
  186. data/ext/enterprise_script_service/mruby/mrbgems/mruby-bin-debugger/tools/mrdb/mrdb.c +0 -1
  187. data/ext/enterprise_script_service/mruby/mrbgems/mruby-bin-debugger/tools/mrdb/mrdbconf.h +5 -1
  188. data/ext/enterprise_script_service/mruby/mrbgems/mruby-bin-mirb/tools/mirb/mirb.c +7 -3
  189. data/ext/enterprise_script_service/mruby/mrbgems/mruby-bin-mrbc/tools/mrbc/mrbc.c +24 -21
  190. data/ext/enterprise_script_service/mruby/mrbgems/mruby-bin-mruby/mrbgem.rake +0 -1
  191. data/ext/enterprise_script_service/mruby/mrbgems/mruby-bin-mruby/tools/mruby/mruby.c +6 -2
  192. data/ext/enterprise_script_service/mruby/mrbgems/mruby-bin-strip/tools/mruby-strip/mruby-strip.c +6 -2
  193. data/ext/enterprise_script_service/mruby/mrbgems/mruby-class-ext/src/class.c +6 -1
  194. data/ext/enterprise_script_service/mruby/mrbgems/mruby-compiler/core/codegen.c +76 -48
  195. data/ext/enterprise_script_service/mruby/mrbgems/mruby-compiler/core/parse.y +107 -32
  196. data/ext/enterprise_script_service/mruby/mrbgems/mruby-compiler/core/y.tab.c +13153 -0
  197. data/ext/enterprise_script_service/mruby/mrbgems/mruby-compiler/mrbgem.rake +13 -15
  198. data/ext/enterprise_script_service/mruby/mrbgems/mruby-complex/mrblib/complex.rb +1 -1
  199. data/ext/enterprise_script_service/mruby/mrbgems/mruby-complex/src/complex.c +1 -2
  200. data/ext/enterprise_script_service/mruby/mrbgems/mruby-error/src/exception.c +3 -3
  201. data/ext/enterprise_script_service/mruby/mrbgems/mruby-eval/src/eval.c +3 -214
  202. data/ext/enterprise_script_service/mruby/mrbgems/mruby-eval/test/eval.rb +21 -0
  203. data/ext/enterprise_script_service/mruby/mrbgems/mruby-fiber/src/fiber.c +1 -2
  204. data/ext/enterprise_script_service/mruby/mrbgems/mruby-hash-ext/src/hash-ext.c +1 -3
  205. data/ext/enterprise_script_service/mruby/mrbgems/mruby-inline-struct/test/inline.c +3 -4
  206. data/ext/enterprise_script_service/mruby/mrbgems/mruby-io/include/mruby/ext/io.h +39 -7
  207. data/ext/enterprise_script_service/mruby/mrbgems/mruby-io/mrbgem.rake +2 -8
  208. data/ext/enterprise_script_service/mruby/mrbgems/mruby-io/mrblib/file_constants.rb +0 -16
  209. data/ext/enterprise_script_service/mruby/mrbgems/mruby-io/mrblib/io.rb +7 -12
  210. data/ext/enterprise_script_service/mruby/mrbgems/mruby-io/src/file.c +77 -32
  211. data/ext/enterprise_script_service/mruby/mrbgems/mruby-io/src/file_test.c +18 -36
  212. data/ext/enterprise_script_service/mruby/mrbgems/mruby-io/src/io.c +324 -122
  213. data/ext/enterprise_script_service/mruby/mrbgems/mruby-io/test/file.rb +18 -12
  214. data/ext/enterprise_script_service/mruby/mrbgems/mruby-io/test/io.rb +32 -0
  215. data/ext/enterprise_script_service/mruby/mrbgems/mruby-io/test/mruby_io_test.c +57 -49
  216. data/ext/enterprise_script_service/mruby/mrbgems/mruby-kernel-ext/src/kernel.c +6 -8
  217. data/ext/enterprise_script_service/mruby/mrbgems/mruby-metaprog/src/metaprog.c +15 -17
  218. data/ext/enterprise_script_service/mruby/mrbgems/mruby-metaprog/test/metaprog.rb +9 -0
  219. data/ext/enterprise_script_service/mruby/mrbgems/mruby-method/src/method.c +4 -5
  220. data/ext/enterprise_script_service/mruby/mrbgems/mruby-object-ext/src/object.c +3 -12
  221. data/ext/enterprise_script_service/mruby/mrbgems/mruby-objectspace/src/mruby_objectspace.c +0 -1
  222. data/ext/enterprise_script_service/mruby/mrbgems/mruby-pack/src/pack.c +113 -10
  223. data/ext/enterprise_script_service/mruby/mrbgems/mruby-print/src/print.c +6 -3
  224. data/ext/enterprise_script_service/mruby/mrbgems/mruby-proc-ext/src/proc.c +2 -2
  225. data/ext/enterprise_script_service/mruby/mrbgems/mruby-range-ext/src/range.c +1 -3
  226. data/ext/enterprise_script_service/mruby/mrbgems/mruby-rational/mrblib/rational.rb +1 -3
  227. data/ext/enterprise_script_service/mruby/mrbgems/mruby-rational/src/rational.c +9 -9
  228. data/ext/enterprise_script_service/mruby/mrbgems/mruby-sleep/src/mrb_sleep.c +1 -1
  229. data/ext/enterprise_script_service/mruby/mrbgems/mruby-socket/mrbgem.rake +1 -1
  230. data/ext/enterprise_script_service/mruby/mrbgems/mruby-socket/test/sockettest.c +3 -2
  231. data/ext/enterprise_script_service/mruby/mrbgems/mruby-sprintf/src/sprintf.c +62 -25
  232. data/ext/enterprise_script_service/mruby/mrbgems/mruby-sprintf/test/sprintf.rb +5 -23
  233. data/ext/enterprise_script_service/mruby/mrbgems/mruby-string-ext/src/string.c +4 -5
  234. data/ext/enterprise_script_service/mruby/mrbgems/mruby-struct/src/struct.c +5 -11
  235. data/ext/enterprise_script_service/mruby/mrbgems/mruby-symbol-ext/src/symbol.c +1 -1
  236. data/ext/enterprise_script_service/mruby/mrbgems/mruby-test/mrbgem.rake +1 -0
  237. data/ext/enterprise_script_service/mruby/mrbgems/mruby-time/src/time.c +11 -15
  238. data/ext/enterprise_script_service/mruby/mrblib/00class.rb +10 -0
  239. data/ext/enterprise_script_service/mruby/mrblib/hash.rb +3 -3
  240. data/ext/enterprise_script_service/mruby/src/array.c +25 -11
  241. data/ext/enterprise_script_service/mruby/src/backtrace.c +2 -2
  242. data/ext/enterprise_script_service/mruby/src/class.c +48 -32
  243. data/ext/enterprise_script_service/mruby/src/codedump.c +4 -0
  244. data/ext/enterprise_script_service/mruby/src/debug.c +8 -5
  245. data/ext/enterprise_script_service/mruby/src/dump.c +3 -65
  246. data/ext/enterprise_script_service/mruby/src/error.c +58 -7
  247. data/ext/enterprise_script_service/mruby/src/etc.c +13 -5
  248. data/ext/enterprise_script_service/mruby/src/fmt_fp.c +98 -21
  249. data/ext/enterprise_script_service/mruby/src/gc.c +15 -280
  250. data/ext/enterprise_script_service/mruby/src/hash.c +13 -21
  251. data/ext/enterprise_script_service/mruby/src/kernel.c +6 -9
  252. data/ext/enterprise_script_service/mruby/src/load.c +56 -30
  253. data/ext/enterprise_script_service/mruby/src/numeric.c +50 -70
  254. data/ext/enterprise_script_service/mruby/src/object.c +23 -5
  255. data/ext/enterprise_script_service/mruby/src/print.c +27 -3
  256. data/ext/enterprise_script_service/mruby/src/proc.c +26 -7
  257. data/ext/enterprise_script_service/mruby/src/range.c +4 -12
  258. data/ext/enterprise_script_service/mruby/src/state.c +34 -11
  259. data/ext/enterprise_script_service/mruby/src/string.c +93 -56
  260. data/ext/enterprise_script_service/mruby/src/symbol.c +13 -12
  261. data/ext/enterprise_script_service/mruby/src/vm.c +48 -53
  262. data/ext/enterprise_script_service/mruby/tasks/gitlab.rake +19 -22
  263. data/ext/enterprise_script_service/mruby/tasks/mrbgems.rake +1 -1
  264. data/ext/enterprise_script_service/mruby/tasks/toolchains/android.rake +46 -1
  265. data/ext/enterprise_script_service/mruby/tasks/toolchains/gcc.rake +3 -3
  266. data/ext/enterprise_script_service/mruby/tasks/toolchains/openwrt.rake +6 -6
  267. data/ext/enterprise_script_service/mruby/tasks/toolchains/visualcpp.rake +8 -8
  268. data/ext/enterprise_script_service/mruby/test/assert.rb +5 -4
  269. data/ext/enterprise_script_service/mruby/test/t/ensure.rb +8 -26
  270. data/ext/enterprise_script_service/mruby/test/t/exception.rb +2 -2
  271. data/ext/enterprise_script_service/mruby/test/t/kernel.rb +15 -24
  272. data/ext/enterprise_script_service/mruby/travis_config.rb +0 -14
  273. data/ext/enterprise_script_service/msgpack/.github/depends/boost.sh +56 -0
  274. data/ext/enterprise_script_service/msgpack/.github/workflows/coverage.yml +62 -0
  275. data/ext/enterprise_script_service/msgpack/.github/workflows/gha.yml +304 -0
  276. data/ext/enterprise_script_service/msgpack/CHANGELOG.md +11 -0
  277. data/ext/enterprise_script_service/msgpack/CMakeLists.txt +82 -39
  278. data/ext/enterprise_script_service/msgpack/Files.cmake +22 -12
  279. data/ext/enterprise_script_service/msgpack/QUICKSTART-C.md +26 -29
  280. data/ext/enterprise_script_service/msgpack/README.md +3 -2
  281. data/ext/enterprise_script_service/msgpack/appveyor.yml +6 -2
  282. data/ext/enterprise_script_service/msgpack/ci/build_cmake.sh +3 -1
  283. data/ext/enterprise_script_service/msgpack/cmake/CodeCoverage.cmake +55 -0
  284. data/ext/enterprise_script_service/msgpack/codecov.yml +36 -0
  285. data/ext/enterprise_script_service/msgpack/example/CMakeLists.txt +9 -5
  286. data/ext/enterprise_script_service/msgpack/example/boost/CMakeLists.txt +1 -1
  287. data/ext/enterprise_script_service/msgpack/example/c/CMakeLists.txt +17 -6
  288. data/ext/enterprise_script_service/msgpack/example/c/boundary.c +296 -0
  289. data/ext/enterprise_script_service/msgpack/example/c/jsonconv.c +419 -0
  290. data/ext/enterprise_script_service/msgpack/example/c/simple_c.c +1 -1
  291. data/ext/enterprise_script_service/msgpack/example/cpp03/CMakeLists.txt +3 -3
  292. data/ext/enterprise_script_service/msgpack/example/cpp11/CMakeLists.txt +2 -2
  293. data/ext/enterprise_script_service/msgpack/example/x3/CMakeLists.txt +2 -2
  294. data/ext/enterprise_script_service/msgpack/include/msgpack/pack.h +24 -1
  295. data/ext/enterprise_script_service/msgpack/include/msgpack/v1/adaptor/array_ref.hpp +5 -4
  296. data/ext/enterprise_script_service/msgpack/include/msgpack/v1/adaptor/boost/optional.hpp +4 -4
  297. data/ext/enterprise_script_service/msgpack/include/msgpack/v1/adaptor/cpp17/vector_byte.hpp +8 -8
  298. data/ext/enterprise_script_service/msgpack/include/msgpack/v1/adaptor/map.hpp +4 -4
  299. data/ext/enterprise_script_service/msgpack/include/msgpack/v1/adaptor/vector.hpp +4 -4
  300. data/ext/enterprise_script_service/msgpack/include/msgpack/v1/adaptor/vector_char.hpp +8 -8
  301. data/ext/enterprise_script_service/msgpack/include/msgpack/v1/adaptor/vector_unsigned_char.hpp +8 -8
  302. data/ext/enterprise_script_service/msgpack/include/msgpack/v1/adaptor/wstring.hpp +4 -4
  303. data/ext/enterprise_script_service/msgpack/include/msgpack/v3/unpack.hpp +6 -6
  304. data/ext/enterprise_script_service/msgpack/include/msgpack/version_master.h +2 -2
  305. data/ext/enterprise_script_service/msgpack/include/msgpack/zbuffer.h +4 -4
  306. data/ext/enterprise_script_service/msgpack/make_file_list.sh +38 -11
  307. data/ext/enterprise_script_service/msgpack/src/vrefbuffer.c +6 -0
  308. data/ext/enterprise_script_service/msgpack/test/CMakeLists.txt +86 -64
  309. data/ext/enterprise_script_service/msgpack/test/array_ref.cpp +4 -0
  310. data/ext/enterprise_script_service/msgpack/test/boost_fusion.cpp +4 -0
  311. data/ext/enterprise_script_service/msgpack/test/boost_optional.cpp +4 -0
  312. data/ext/enterprise_script_service/msgpack/test/boost_string_ref.cpp +4 -1
  313. data/ext/enterprise_script_service/msgpack/test/boost_string_view.cpp +4 -0
  314. data/ext/enterprise_script_service/msgpack/test/boost_variant.cpp +4 -0
  315. data/ext/enterprise_script_service/msgpack/test/buffer.cpp +4 -47
  316. data/ext/enterprise_script_service/msgpack/test/buffer_c.cpp +148 -0
  317. data/ext/enterprise_script_service/msgpack/test/carray.cpp +4 -0
  318. data/ext/enterprise_script_service/msgpack/test/cases.cpp +8 -4
  319. data/ext/enterprise_script_service/msgpack/test/convert.cpp +8 -4
  320. data/ext/enterprise_script_service/msgpack/test/fixint.cpp +4 -0
  321. data/ext/enterprise_script_service/msgpack/test/fixint_c.cpp +4 -0
  322. data/ext/enterprise_script_service/msgpack/test/fuzz_unpack_pack_fuzzer_cpp11.cpp +4 -0
  323. data/ext/enterprise_script_service/msgpack/test/iterator_cpp11.cpp +4 -0
  324. data/ext/enterprise_script_service/msgpack/test/json.cpp +4 -0
  325. data/ext/enterprise_script_service/msgpack/test/limit.cpp +8 -4
  326. data/ext/enterprise_script_service/msgpack/test/msgpack_basic.cpp +4 -0
  327. data/ext/enterprise_script_service/msgpack/test/msgpack_c.cpp +159 -0
  328. data/ext/enterprise_script_service/msgpack/test/msgpack_container.cpp +4 -0
  329. data/ext/enterprise_script_service/msgpack/test/msgpack_cpp11.cpp +32 -27
  330. data/ext/enterprise_script_service/msgpack/test/msgpack_cpp17.cpp +4 -0
  331. data/ext/enterprise_script_service/msgpack/test/msgpack_stream.cpp +4 -0
  332. data/ext/enterprise_script_service/msgpack/test/msgpack_tuple.cpp +4 -1
  333. data/ext/enterprise_script_service/msgpack/test/msgpack_vref.cpp +4 -0
  334. data/ext/enterprise_script_service/msgpack/test/msgpack_x3_parse.cpp +4 -0
  335. data/ext/enterprise_script_service/msgpack/test/object.cpp +4 -1
  336. data/ext/enterprise_script_service/msgpack/test/object_with_zone.cpp +12 -8
  337. data/ext/enterprise_script_service/msgpack/test/pack_unpack.cpp +30 -26
  338. data/ext/enterprise_script_service/msgpack/test/pack_unpack_c.cpp +4 -0
  339. data/ext/enterprise_script_service/msgpack/test/raw.cpp +4 -0
  340. data/ext/enterprise_script_service/msgpack/test/reference.cpp +4 -0
  341. data/ext/enterprise_script_service/msgpack/test/reference_cpp11.cpp +4 -0
  342. data/ext/enterprise_script_service/msgpack/test/reference_wrapper_cpp11.cpp +4 -0
  343. data/ext/enterprise_script_service/msgpack/test/shared_ptr_cpp11.cpp +4 -0
  344. data/ext/enterprise_script_service/msgpack/test/size_equal_only.cpp +4 -0
  345. data/ext/enterprise_script_service/msgpack/test/streaming.cpp +8 -4
  346. data/ext/enterprise_script_service/msgpack/test/streaming_c.cpp +4 -0
  347. data/ext/enterprise_script_service/msgpack/test/unique_ptr_cpp11.cpp +4 -0
  348. data/ext/enterprise_script_service/msgpack/test/user_class.cpp +16 -12
  349. data/ext/enterprise_script_service/msgpack/test/version.cpp +4 -0
  350. data/ext/enterprise_script_service/msgpack/test/visitor.cpp +4 -0
  351. data/ext/enterprise_script_service/msgpack/test/zone.cpp +4 -0
  352. data/lib/script_core/engine.rb +24 -5
  353. data/lib/script_core/executable.rb +4 -3
  354. data/lib/script_core/result.rb +1 -5
  355. data/lib/script_core/service_channel.rb +1 -0
  356. data/lib/script_core/version.rb +1 -1
  357. data/lib/tasks/script_core.rake +3 -1
  358. data/script_core.gemspec +2 -2
  359. data/spec/dummy/app/lib/script_engine.rb +64 -5
  360. metadata +68 -30
  361. data/ext/enterprise_script_service/libseccomp/src/arch-aarch64-syscalls.c +0 -559
  362. data/ext/enterprise_script_service/libseccomp/src/arch-arm-syscalls.c +0 -570
  363. data/ext/enterprise_script_service/libseccomp/src/arch-mips-syscalls.c +0 -562
  364. data/ext/enterprise_script_service/libseccomp/src/arch-mips64-syscalls.c +0 -562
  365. data/ext/enterprise_script_service/libseccomp/src/arch-mips64n32-syscalls.c +0 -562
  366. data/ext/enterprise_script_service/libseccomp/src/arch-parisc-syscalls.c +0 -542
  367. data/ext/enterprise_script_service/libseccomp/src/arch-ppc-syscalls.c +0 -559
  368. data/ext/enterprise_script_service/libseccomp/src/arch-ppc64-syscalls.c +0 -559
  369. data/ext/enterprise_script_service/libseccomp/src/arch-s390-syscalls.c +0 -626
  370. data/ext/enterprise_script_service/libseccomp/src/arch-s390x-syscalls.c +0 -626
  371. data/ext/enterprise_script_service/libseccomp/src/arch-x32-syscalls.c +0 -558
  372. data/ext/enterprise_script_service/libseccomp/src/arch-x86-syscalls.c +0 -692
  373. data/ext/enterprise_script_service/libseccomp/src/arch-x86_64-syscalls.c +0 -559
  374. data/ext/enterprise_script_service/libseccomp/tests/18-sim-basic_whitelist.tests +0 -32
  375. data/ext/enterprise_script_service/libseccomp/tests/34-sim-basic_blacklist.tests +0 -32
  376. data/ext/enterprise_script_service/msgpack/.travis.yml +0 -258
@@ -116,6 +116,12 @@ struct db_filter_attr {
116
116
  uint32_t api_tskip;
117
117
  /* SECCOMP_FILTER_FLAG_LOG related attributes */
118
118
  uint32_t log_enable;
119
+ /* SPEC_ALLOW related attributes */
120
+ uint32_t spec_allow;
121
+ /* SCMP_FLTATR_CTL_OPTIMIZE related attributes */
122
+ uint32_t optimize;
123
+ /* return the raw system return codes */
124
+ uint32_t api_sysrawrc;
119
125
  };
120
126
 
121
127
  struct db_filter {
@@ -124,6 +130,7 @@ struct db_filter {
124
130
 
125
131
  /* syscall filters, kept as a sorted single-linked list */
126
132
  struct db_sys_list *syscalls;
133
+ unsigned int syscall_cnt;
127
134
 
128
135
  /* list of rules used to build the filters, kept in order */
129
136
  struct db_api_rule_list *rules;
@@ -133,6 +140,7 @@ struct db_filter_snap {
133
140
  /* individual filters */
134
141
  struct db_filter **filters;
135
142
  unsigned int filter_cnt;
143
+ bool shadow;
136
144
 
137
145
  struct db_filter_snap *next;
138
146
  };
@@ -151,6 +159,10 @@ struct db_filter_col {
151
159
 
152
160
  /* transaction snapshots */
153
161
  struct db_filter_snap *snapshots;
162
+
163
+ /* notification fd that was returned from seccomp() */
164
+ int notify_fd;
165
+ bool notify_used;
154
166
  };
155
167
 
156
168
  /**
@@ -165,8 +177,6 @@ struct db_filter_col {
165
177
  #define db_list_foreach(iter,list) \
166
178
  for (iter = (list); iter != NULL; iter = iter->next)
167
179
 
168
- int db_action_valid(uint32_t action);
169
-
170
180
  struct db_api_rule_list *db_rule_dup(const struct db_api_rule_list *src);
171
181
 
172
182
  struct db_filter_col *db_col_init(uint32_t def_action);
@@ -175,12 +185,16 @@ void db_col_release(struct db_filter_col *col);
175
185
 
176
186
  int db_col_valid(struct db_filter_col *col);
177
187
 
188
+ int db_col_action_valid(const struct db_filter_col *col, uint32_t action);
189
+
178
190
  int db_col_merge(struct db_filter_col *col_dst, struct db_filter_col *col_src);
179
191
 
180
192
  int db_col_arch_exist(struct db_filter_col *col, uint32_t arch_token);
181
193
 
182
194
  int db_col_attr_get(const struct db_filter_col *col,
183
195
  enum scmp_filter_attr attr, uint32_t *value);
196
+ uint32_t db_col_attr_read(const struct db_filter_col *col,
197
+ enum scmp_filter_attr attr);
184
198
  int db_col_attr_set(struct db_filter_col *col,
185
199
  enum scmp_filter_attr attr, uint32_t value);
186
200
 
@@ -21,6 +21,7 @@
21
21
 
22
22
  #include <errno.h>
23
23
  #include <inttypes.h>
24
+ #include <limits.h>
24
25
  #include <stdlib.h>
25
26
  #include <stdio.h>
26
27
  #include <string.h>
@@ -45,6 +46,11 @@
45
46
  #define AINC_BLK 2
46
47
  #define AINC_PROG 64
47
48
 
49
+ /* binary tree definitions */
50
+ #define SYSCALLS_PER_NODE (4)
51
+ #define BTREE_HSH_INVALID (UINT64_MAX)
52
+ #define BTREE_SYSCALL_INVALID (UINT_MAX)
53
+
48
54
  struct acc_state {
49
55
  int32_t offset;
50
56
  uint32_t mask;
@@ -159,11 +165,14 @@ struct bpf_state {
159
165
  /* default action */
160
166
  uint64_t def_hsh;
161
167
 
162
- /* target arch - NOTE: be careful, temporary use only! */
163
- const struct arch_def *arch;
164
-
165
168
  /* bpf program */
166
169
  struct bpf_program *bpf;
170
+
171
+ /* WARNING - the following variables are temporary use only */
172
+ const struct arch_def *arch;
173
+ struct bpf_blk *b_head;
174
+ struct bpf_blk *b_tail;
175
+ struct bpf_blk *b_new;
167
176
  };
168
177
 
169
178
  /**
@@ -1143,6 +1152,318 @@ chain_failure:
1143
1152
  return NULL;
1144
1153
  }
1145
1154
 
1155
+ /**
1156
+ * Sort the syscalls by syscall number
1157
+ * @param syscalls the linked list of syscalls to be sorted
1158
+ * @param s_head the head of the linked list to be returned to the caller
1159
+ * @param s_tail the tail of the linked list to be returned to the caller
1160
+ */
1161
+ static void _sys_num_sort(struct db_sys_list *syscalls,
1162
+ struct db_sys_list **s_head,
1163
+ struct db_sys_list **s_tail)
1164
+ {
1165
+ struct db_sys_list *s_iter, *s_iter_b;
1166
+
1167
+ db_list_foreach(s_iter, syscalls) {
1168
+ if (*s_head != NULL) {
1169
+ s_iter_b = *s_head;
1170
+ while ((s_iter_b->pri_nxt != NULL) &&
1171
+ (s_iter->num <= s_iter_b->num))
1172
+ s_iter_b = s_iter_b->pri_nxt;
1173
+
1174
+ if (s_iter->num > s_iter_b->num) {
1175
+ s_iter->pri_prv = s_iter_b->pri_prv;
1176
+ s_iter->pri_nxt = s_iter_b;
1177
+ if (s_iter_b == *s_head) {
1178
+ (*s_head)->pri_prv = s_iter;
1179
+ *s_head = s_iter;
1180
+ } else {
1181
+ s_iter->pri_prv->pri_nxt = s_iter;
1182
+ s_iter->pri_nxt->pri_prv = s_iter;
1183
+ }
1184
+ } else {
1185
+ s_iter->pri_prv = *s_tail;
1186
+ s_iter->pri_nxt = NULL;
1187
+ s_iter->pri_prv->pri_nxt = s_iter;
1188
+ *s_tail = s_iter;
1189
+ }
1190
+ } else {
1191
+ *s_head = s_iter;
1192
+ *s_tail = s_iter;
1193
+ (*s_head)->pri_prv = NULL;
1194
+ (*s_head)->pri_nxt = NULL;
1195
+ }
1196
+ }
1197
+ }
1198
+
1199
+ /**
1200
+ * Sort the syscalls by priority
1201
+ * @param syscalls the linked list of syscalls to be sorted
1202
+ * @param s_head the head of the linked list to be returned to the caller
1203
+ * @param s_tail the tail of the linked list to be returned to the caller
1204
+ */
1205
+ static void _sys_priority_sort(struct db_sys_list *syscalls,
1206
+ struct db_sys_list **s_head,
1207
+ struct db_sys_list **s_tail)
1208
+ {
1209
+ struct db_sys_list *s_iter, *s_iter_b;
1210
+
1211
+ db_list_foreach(s_iter, syscalls) {
1212
+ if (*s_head != NULL) {
1213
+ s_iter_b = *s_head;
1214
+ while ((s_iter_b->pri_nxt != NULL) &&
1215
+ (s_iter->priority <= s_iter_b->priority))
1216
+ s_iter_b = s_iter_b->pri_nxt;
1217
+
1218
+ if (s_iter->priority > s_iter_b->priority) {
1219
+ s_iter->pri_prv = s_iter_b->pri_prv;
1220
+ s_iter->pri_nxt = s_iter_b;
1221
+ if (s_iter_b == *s_head) {
1222
+ (*s_head)->pri_prv = s_iter;
1223
+ *s_head = s_iter;
1224
+ } else {
1225
+ s_iter->pri_prv->pri_nxt = s_iter;
1226
+ s_iter->pri_nxt->pri_prv = s_iter;
1227
+ }
1228
+ } else {
1229
+ s_iter->pri_prv = *s_tail;
1230
+ s_iter->pri_nxt = NULL;
1231
+ s_iter->pri_prv->pri_nxt = s_iter;
1232
+ *s_tail = s_iter;
1233
+ }
1234
+ } else {
1235
+ *s_head = s_iter;
1236
+ *s_tail = s_iter;
1237
+ (*s_head)->pri_prv = NULL;
1238
+ (*s_head)->pri_nxt = NULL;
1239
+ }
1240
+ }
1241
+ }
1242
+
1243
+ /**
1244
+ * Sort the syscalls
1245
+ * @param syscalls the linked list of syscalls to be sorted
1246
+ * @param s_head the head of the linked list to be returned to the caller
1247
+ * @param s_tail the tail of the linked list to be returned to the caller
1248
+ *
1249
+ * Wrapper function for sorting syscalls
1250
+ *
1251
+ */
1252
+ static void _sys_sort(struct db_sys_list *syscalls,
1253
+ struct db_sys_list **s_head,
1254
+ struct db_sys_list **s_tail,
1255
+ uint32_t optimize)
1256
+ {
1257
+ if (optimize != 2)
1258
+ _sys_priority_sort(syscalls, s_head, s_tail);
1259
+ else
1260
+ /* sort by number for the binary tree */
1261
+ _sys_num_sort(syscalls, s_head, s_tail);
1262
+ }
1263
+
1264
+ /**
1265
+ * Insert an instruction into the BPF state and connect the linked list
1266
+ * @param state the BPF state
1267
+ * @param instr the instruction to insert
1268
+ * @param insert the BPF blk that represents the instruction
1269
+ * @param next the next BPF instruction in the linked list
1270
+ * @param existing_blk insert will be added to the end of this blk if non-NULL
1271
+ *
1272
+ * Insert a set of instructions into the BPF state and associate those
1273
+ * instructions with the bpf_blk called insert. The "next" field in the
1274
+ * newly inserted block will be linked with the "next" bpf_blk parameter.
1275
+ */
1276
+ static int _gen_bpf_insert(struct bpf_state *state, struct bpf_instr *instr,
1277
+ struct bpf_blk **insert, struct bpf_blk **next,
1278
+ struct bpf_blk *existing_blk)
1279
+ {
1280
+ int rc;
1281
+
1282
+ *insert = _blk_append(state, existing_blk, instr);
1283
+ if (*insert == NULL)
1284
+ return -ENOMEM;
1285
+ (*insert)->next = (*next);
1286
+ if (*next != NULL)
1287
+ (*next)->prev = (*insert);
1288
+ *next = *insert;
1289
+
1290
+ rc = _hsh_add(state, insert, 1);
1291
+ return rc;
1292
+ }
1293
+
1294
+ /**
1295
+ * Decide if we need to omit the syscall from the BPF filter
1296
+ * @param state the BPF state
1297
+ * @param syscall syscall being tested
1298
+ * @return true if syscall is to be skipped, false otherwise
1299
+ */
1300
+ static inline bool _skip_syscall(struct bpf_state *state,
1301
+ struct db_sys_list *syscall)
1302
+ {
1303
+ if (!syscall->valid)
1304
+ return true;
1305
+
1306
+ /* psuedo-syscalls should not be added to the filter unless explicity
1307
+ * requested via SCMP_FLTATR_API_TSKIP
1308
+ */
1309
+ if (((int)syscall->num < 0) &&
1310
+ (state->attr->api_tskip == 0 || syscall->num != -1))
1311
+ return true;
1312
+
1313
+ return false;
1314
+ }
1315
+
1316
+ /**
1317
+ * Calculate the number of syscalls that will be in the BPF filter
1318
+ * @param state the BPF state
1319
+ * @param s_tail the last syscall in the syscall linked list
1320
+ */
1321
+ static unsigned int _get_syscall_cnt(struct bpf_state *state,
1322
+ struct db_sys_list *s_tail)
1323
+ {
1324
+ struct db_sys_list *s_iter;
1325
+ unsigned int syscall_cnt = 0;
1326
+
1327
+ for (s_iter = s_tail; s_iter != NULL; s_iter = s_iter->pri_prv) {
1328
+ if (_skip_syscall(state, s_iter))
1329
+ continue;
1330
+
1331
+ syscall_cnt++;
1332
+ }
1333
+
1334
+ return syscall_cnt;
1335
+ }
1336
+
1337
+ /**
1338
+ * Calculate the number of levels in the binary tree
1339
+ * @param syscall_cnt the number of syscalls in this seccomp filter
1340
+ */
1341
+ static int _get_bintree_levels(unsigned int syscall_cnt)
1342
+ {
1343
+ unsigned int i = 2, max_level = SYSCALLS_PER_NODE * 2;
1344
+
1345
+ while (max_level < syscall_cnt) {
1346
+ max_level <<= 1;
1347
+ i++;
1348
+ }
1349
+
1350
+ return i;
1351
+ }
1352
+
1353
+ /**
1354
+ * Initialize the binary tree
1355
+ * @param bintree_hashes Array of hashes that store binary tree jump dests
1356
+ * @param bintree_syscalls Array of syscalls for the binary tree "if > " logic
1357
+ * @param bintree_levels Number of levels in the binary tree
1358
+ * @param syscall_cnt Number of syscalls in this filter
1359
+ * @param empty_cnt Number of empty slots needed to balance the tree
1360
+ *
1361
+ */
1362
+ static int _gen_bpf_init_bintree(uint64_t **bintree_hashes,
1363
+ unsigned int **bintree_syscalls,
1364
+ unsigned int *bintree_levels,
1365
+ unsigned int syscall_cnt,
1366
+ unsigned int *empty_cnt)
1367
+ {
1368
+ int i;
1369
+
1370
+ *bintree_levels = _get_bintree_levels(syscall_cnt);
1371
+
1372
+ if (*bintree_levels > 0) {
1373
+ *empty_cnt = ((unsigned int)(SYSCALLS_PER_NODE * 2) <<
1374
+ ((*bintree_levels) - 1)) - syscall_cnt;
1375
+ *bintree_hashes = zmalloc(sizeof(uint64_t) *
1376
+ (*bintree_levels));
1377
+ if (*bintree_hashes == NULL)
1378
+ return -ENOMEM;
1379
+
1380
+ *bintree_syscalls = zmalloc(sizeof(unsigned int) *
1381
+ (*bintree_levels));
1382
+ if (*bintree_syscalls == NULL)
1383
+ return -ENOMEM;
1384
+
1385
+ for (i = 0; i < *bintree_levels; i++) {
1386
+ (*bintree_syscalls)[i] = BTREE_SYSCALL_INVALID;
1387
+ (*bintree_hashes)[i] = BTREE_HSH_INVALID;
1388
+ }
1389
+ }
1390
+
1391
+ return 0;
1392
+ }
1393
+
1394
+ /**
1395
+ * Generate the binary tree
1396
+ * @param state the BPF state
1397
+ * @param bintree_hashes Array of hashes that store binary tree jump dests
1398
+ * @param bintree_syscalls Array of syscalls for the binary tree "if > " logic
1399
+ * @param bintree_levels Number of levels in the binary tree
1400
+ * @param total_cnt Total number of syscalls and empty slots in the bintree
1401
+ * @param cur_syscall Current syscall being processed
1402
+ * @param blks_added Number of BPF blocks added by this function
1403
+ *
1404
+ * Generate the BPF instruction blocks for the binary tree for cur_syscall.
1405
+ * If this syscall is at the end of the node, then this function will
1406
+ * create the requisite ifs and elses for the tree.
1407
+ */
1408
+ static int _gen_bpf_bintree(struct bpf_state *state, uint64_t *bintree_hashes,
1409
+ unsigned int *bintree_syscalls,
1410
+ unsigned int bintree_levels,
1411
+ unsigned int total_cnt, unsigned int cur_syscall,
1412
+ unsigned int *blks_added)
1413
+ {
1414
+ struct bpf_blk *b_bintree = NULL;
1415
+ struct bpf_instr instr;
1416
+ unsigned int level;
1417
+ int rc = 0, i, j;
1418
+
1419
+ for (i = bintree_levels - 1; i >= 0; i--) {
1420
+ level = SYSCALLS_PER_NODE << i;
1421
+
1422
+ if ((total_cnt % level) == 0) {
1423
+ /* save the "if greater than" syscall num */
1424
+ bintree_syscalls[i] = cur_syscall;
1425
+ /* save the hash for the jf case */
1426
+ bintree_hashes[i] = state->b_new->hash;
1427
+
1428
+ for (j = 0; j < i; j++) {
1429
+ if (bintree_syscalls[j] == BTREE_SYSCALL_INVALID ||
1430
+ bintree_hashes[j] == BTREE_HSH_INVALID)
1431
+ /* we are near the end of the binary
1432
+ * tree and the jump-to location is
1433
+ * not valid. skip this if-else
1434
+ */
1435
+ continue;
1436
+
1437
+ _BPF_INSTR(instr,
1438
+ _BPF_OP(state->arch, BPF_JMP + BPF_JGT),
1439
+ _BPF_JMP_NO,
1440
+ _BPF_JMP_NO,
1441
+ _BPF_K(state->arch, bintree_syscalls[j]));
1442
+ instr.jt = _BPF_JMP_HSH(b_bintree == NULL ?
1443
+ state->b_new->hash : b_bintree->hash);
1444
+ instr.jf = _BPF_JMP_HSH(bintree_hashes[j]);
1445
+ (*blks_added)++;
1446
+
1447
+ rc = _gen_bpf_insert(state, &instr,
1448
+ &b_bintree, &state->b_head, NULL);
1449
+ if (rc < 0)
1450
+ goto out;
1451
+ }
1452
+
1453
+ if (b_bintree != NULL)
1454
+ /* this is the last if in this "block".
1455
+ * save it off so the next binary tree
1456
+ * if can "else" to it.
1457
+ */
1458
+ bintree_hashes[j] = b_bintree->hash;
1459
+ break;
1460
+ }
1461
+ }
1462
+
1463
+ out:
1464
+ return rc;
1465
+ }
1466
+
1146
1467
  /**
1147
1468
  * Generate the BPF instruction blocks for a given syscall
1148
1469
  * @param state the BPF state
@@ -1222,94 +1543,44 @@ static struct bpf_blk *_gen_bpf_syscall(struct bpf_state *state,
1222
1543
  }
1223
1544
 
1224
1545
  /**
1225
- * Generate the BPF instruction blocks for a given filter/architecture
1546
+ * Loop through the syscalls in the db_filter and generate their bpf
1226
1547
  * @param state the BPF state
1227
1548
  * @param db the filter DB
1228
1549
  * @param db_secondary the secondary DB
1229
- *
1230
- * Generate the BPF instruction block for the given filter DB(s)/architecture(s)
1231
- * and return a pointer to the block on succes, NULL on failure. The resulting
1232
- * block assumes that the architecture token has already been loaded into the
1233
- * BPF accumulator.
1234
- *
1550
+ * @param Number of blocks added by this function
1235
1551
  */
1236
- static struct bpf_blk *_gen_bpf_arch(struct bpf_state *state,
1237
- const struct db_filter *db,
1238
- const struct db_filter *db_secondary)
1552
+ static int _gen_bpf_syscalls(struct bpf_state *state,
1553
+ const struct db_filter *db,
1554
+ const struct db_filter *db_secondary,
1555
+ unsigned int *blks_added, uint32_t optimize,
1556
+ unsigned int *bintree_levels)
1239
1557
  {
1240
- int rc;
1241
- unsigned int blk_cnt = 0;
1558
+ struct db_sys_list *s_head = NULL, *s_tail = NULL, *s_iter;
1559
+ unsigned int syscall_cnt, empty_cnt = 0;
1560
+ uint64_t *bintree_hashes = NULL, nxt_hsh;
1561
+ unsigned int *bintree_syscalls = NULL;
1242
1562
  bool acc_reset;
1243
- struct bpf_instr instr;
1244
- struct db_sys_list *s_head = NULL, *s_tail = NULL, *s_iter, *s_iter_b;
1245
- struct bpf_blk *b_head = NULL, *b_tail = NULL, *b_iter, *b_new;
1563
+ int rc = 0;
1246
1564
 
1247
1565
  state->arch = db->arch;
1566
+ state->b_head = NULL;
1567
+ state->b_tail = NULL;
1568
+ state->b_new = NULL;
1248
1569
 
1249
- /* sort the syscall list */
1250
- db_list_foreach(s_iter, db->syscalls) {
1251
- if (s_head != NULL) {
1252
- s_iter_b = s_head;
1253
- while ((s_iter_b->pri_nxt != NULL) &&
1254
- (s_iter->priority <= s_iter_b->priority))
1255
- s_iter_b = s_iter_b->pri_nxt;
1570
+ *blks_added = 0;
1256
1571
 
1257
- if (s_iter->priority > s_iter_b->priority) {
1258
- s_iter->pri_prv = s_iter_b->pri_prv;
1259
- s_iter->pri_nxt = s_iter_b;
1260
- if (s_iter_b == s_head) {
1261
- s_head->pri_prv = s_iter;
1262
- s_head = s_iter;
1263
- } else {
1264
- s_iter->pri_prv->pri_nxt = s_iter;
1265
- s_iter->pri_nxt->pri_prv = s_iter;
1266
- }
1267
- } else {
1268
- s_iter->pri_prv = s_tail;
1269
- s_iter->pri_nxt = NULL;
1270
- s_iter->pri_prv->pri_nxt = s_iter;
1271
- s_tail = s_iter;
1272
- }
1273
- } else {
1274
- s_head = s_iter;
1275
- s_tail = s_iter;
1276
- s_head->pri_prv = NULL;
1277
- s_head->pri_nxt = NULL;
1278
- }
1279
- }
1280
- if (db_secondary != NULL) {
1281
- db_list_foreach(s_iter, db_secondary->syscalls) {
1282
- if (s_head != NULL) {
1283
- s_iter_b = s_head;
1284
- while ((s_iter_b->pri_nxt != NULL) &&
1285
- (s_iter->priority <= s_iter_b->priority))
1286
- s_iter_b = s_iter_b->pri_nxt;
1287
-
1288
- if (s_iter->priority > s_iter_b->priority) {
1289
- s_iter->pri_prv = s_iter_b->pri_prv;
1290
- s_iter->pri_nxt = s_iter_b;
1291
- if (s_iter_b == s_head) {
1292
- s_head->pri_prv = s_iter;
1293
- s_head = s_iter;
1294
- } else {
1295
- s_iter->pri_prv->pri_nxt =
1296
- s_iter;
1297
- s_iter->pri_nxt->pri_prv =
1298
- s_iter;
1299
- }
1300
- } else {
1301
- s_iter->pri_prv = s_tail;
1302
- s_iter->pri_nxt = NULL;
1303
- s_iter->pri_prv->pri_nxt = s_iter;
1304
- s_tail = s_iter;
1305
- }
1306
- } else {
1307
- s_head = s_iter;
1308
- s_tail = s_iter;
1309
- s_head->pri_prv = NULL;
1310
- s_head->pri_nxt = NULL;
1311
- }
1312
- }
1572
+ /* sort the syscall list */
1573
+ _sys_sort(db->syscalls, &s_head, &s_tail, optimize);
1574
+ if (db_secondary != NULL)
1575
+ _sys_sort(db_secondary->syscalls, &s_head, &s_tail, optimize);
1576
+
1577
+ if (optimize == 2) {
1578
+ syscall_cnt = _get_syscall_cnt(state, s_tail);
1579
+ rc = _gen_bpf_init_bintree(&bintree_hashes, &bintree_syscalls,
1580
+ bintree_levels, syscall_cnt,
1581
+ &empty_cnt);
1582
+ if (rc < 0)
1583
+ goto out;
1313
1584
  }
1314
1585
 
1315
1586
  if ((state->arch->token == SCMP_ARCH_X86_64 ||
@@ -1318,34 +1589,115 @@ static struct bpf_blk *_gen_bpf_arch(struct bpf_state *state,
1318
1589
  else
1319
1590
  acc_reset = true;
1320
1591
 
1592
+ if (*bintree_levels > 0)
1593
+ /* The accumulator is reset when the first bintree "if" is
1594
+ * generated.
1595
+ */
1596
+ acc_reset = false;
1597
+
1598
+ syscall_cnt = 0;
1599
+
1321
1600
  /* create the syscall filters and add them to block list group */
1322
1601
  for (s_iter = s_tail; s_iter != NULL; s_iter = s_iter->pri_prv) {
1323
- if (!s_iter->valid)
1602
+ if (_skip_syscall(state, s_iter))
1324
1603
  continue;
1325
1604
 
1605
+ if (*bintree_levels > 0 &&
1606
+ ((syscall_cnt + empty_cnt) % SYSCALLS_PER_NODE) == 0)
1607
+ /* This is the last syscall in the node. go to the
1608
+ * default hash */
1609
+ nxt_hsh = state->def_hsh;
1610
+ else
1611
+ nxt_hsh = state->b_head == NULL ?
1612
+ state->def_hsh : state->b_head->hash;
1613
+
1326
1614
  /* build the syscall filter */
1327
- b_new = _gen_bpf_syscall(state, s_iter,
1328
- (b_head == NULL ?
1329
- state->def_hsh : b_head->hash),
1330
- (s_iter == s_head ?
1331
- acc_reset : false));
1332
- if (b_new == NULL)
1333
- goto arch_failure;
1615
+ state->b_new = _gen_bpf_syscall(state, s_iter, nxt_hsh,
1616
+ (s_iter == s_head ?
1617
+ acc_reset : false));
1618
+ if (state->b_new == NULL)
1619
+ goto out;
1334
1620
 
1335
1621
  /* add the filter to the list head */
1336
- b_new->prev = NULL;
1337
- b_new->next = b_head;
1338
- if (b_tail != NULL) {
1339
- b_head->prev = b_new;
1340
- b_head = b_new;
1622
+ state->b_new->prev = NULL;
1623
+ state->b_new->next = state->b_head;
1624
+ if (state->b_tail != NULL) {
1625
+ state->b_head->prev = state->b_new;
1626
+ state->b_head = state->b_new;
1341
1627
  } else {
1342
- b_head = b_new;
1343
- b_tail = b_head;
1628
+ state->b_head = state->b_new;
1629
+ state->b_tail = state->b_head;
1344
1630
  }
1345
1631
 
1346
- if (b_tail->next != NULL)
1347
- b_tail = b_tail->next;
1632
+ if (state->b_tail->next != NULL)
1633
+ state->b_tail = state->b_tail->next;
1634
+ (*blks_added)++;
1635
+ syscall_cnt++;
1636
+
1637
+ /* build the binary tree if and else logic */
1638
+ if (*bintree_levels > 0) {
1639
+ rc = _gen_bpf_bintree(state, bintree_hashes,
1640
+ bintree_syscalls,
1641
+ *bintree_levels,
1642
+ syscall_cnt + empty_cnt,
1643
+ s_iter->num, blks_added);
1644
+ if (rc < 0)
1645
+ goto out;
1646
+ }
1647
+ }
1648
+
1649
+ out:
1650
+ if (bintree_hashes != NULL)
1651
+ free(bintree_hashes);
1652
+ if (bintree_syscalls != NULL)
1653
+ free(bintree_syscalls);
1654
+
1655
+ return rc;
1656
+ }
1657
+
1658
+ /**
1659
+ * Generate the BPF instruction blocks for a given filter/architecture
1660
+ * @param state the BPF state
1661
+ * @param db the filter DB
1662
+ * @param db_secondary the secondary DB
1663
+ *
1664
+ * Generate the BPF instruction block for the given filter DB(s)/architecture(s)
1665
+ * and return a pointer to the block on succes, NULL on failure. The resulting
1666
+ * block assumes that the architecture token has already been loaded into the
1667
+ * BPF accumulator.
1668
+ *
1669
+ */
1670
+ static struct bpf_blk *_gen_bpf_arch(struct bpf_state *state,
1671
+ const struct db_filter *db,
1672
+ const struct db_filter *db_secondary,
1673
+ uint32_t optimize)
1674
+ {
1675
+ int rc;
1676
+ unsigned int blk_cnt = 0, blks_added = 0, bintree_levels = 0;
1677
+ struct bpf_instr instr;
1678
+ struct bpf_blk *b_iter, *b_bintree;
1679
+
1680
+ state->arch = db->arch;
1681
+
1682
+ /* create the syscall filters and add them to block list group */
1683
+ rc = _gen_bpf_syscalls(state, db, db_secondary, &blks_added, optimize,
1684
+ &bintree_levels);
1685
+ if (rc < 0)
1686
+ goto arch_failure;
1687
+ blk_cnt += blks_added;
1688
+
1689
+ if (bintree_levels > 0) {
1690
+ _BPF_INSTR(instr, _BPF_OP(state->arch, BPF_LD + BPF_ABS),
1691
+ _BPF_JMP_NO, _BPF_JMP_NO,
1692
+ _BPF_SYSCALL(state->arch));
1348
1693
  blk_cnt++;
1694
+
1695
+ rc = _gen_bpf_insert(state, &instr, &b_bintree,
1696
+ &state->b_head, NULL);
1697
+ if (rc < 0)
1698
+ goto arch_failure;
1699
+ b_bintree->acc_start = _ACC_STATE_UNDEF;
1700
+ b_bintree->acc_end = _ACC_STATE_OFFSET(_BPF_OFFSET_SYSCALL);
1349
1701
  }
1350
1702
 
1351
1703
  /* additional ABI filtering */
@@ -1353,10 +1705,10 @@ static struct bpf_blk *_gen_bpf_arch(struct bpf_state *state,
1353
1705
  state->arch->token == SCMP_ARCH_X32) && (db_secondary == NULL)) {
1354
1706
  _BPF_INSTR(instr, _BPF_OP(state->arch, BPF_LD + BPF_ABS),
1355
1707
  _BPF_JMP_NO, _BPF_JMP_NO, _BPF_SYSCALL(state->arch));
1356
- b_new = _blk_append(state, NULL, &instr);
1357
- if (b_new == NULL)
1708
+ state->b_new = _blk_append(state, NULL, &instr);
1709
+ if (state->b_new == NULL)
1358
1710
  goto arch_failure;
1359
- b_new->acc_end = _ACC_STATE_OFFSET(_BPF_OFFSET_SYSCALL);
1711
+ state->b_new->acc_end = _ACC_STATE_OFFSET(_BPF_OFFSET_SYSCALL);
1360
1712
  if (state->arch->token == SCMP_ARCH_X86_64) {
1361
1713
  /* filter out x32 */
1362
1714
  _BPF_INSTR(instr,
@@ -1364,12 +1716,12 @@ static struct bpf_blk *_gen_bpf_arch(struct bpf_state *state,
1364
1716
  _BPF_JMP_NO,
1365
1717
  _BPF_JMP_NO,
1366
1718
  _BPF_K(state->arch, X32_SYSCALL_BIT));
1367
- if (b_head != NULL)
1368
- instr.jf = _BPF_JMP_HSH(b_head->hash);
1719
+ if (state->b_head != NULL)
1720
+ instr.jf = _BPF_JMP_HSH(state->b_head->hash);
1369
1721
  else
1370
1722
  instr.jf = _BPF_JMP_HSH(state->def_hsh);
1371
- b_new = _blk_append(state, b_new, &instr);
1372
- if (b_new == NULL)
1723
+ state->b_new = _blk_append(state, state->b_new, &instr);
1724
+ if (state->b_new == NULL)
1373
1725
  goto arch_failure;
1374
1726
  /* NOTE: starting with Linux v4.8 the seccomp filters
1375
1727
  * are processed both when the syscall is
@@ -1383,8 +1735,8 @@ static struct bpf_blk *_gen_bpf_arch(struct bpf_state *state,
1383
1735
  _BPF_JMP_NO,
1384
1736
  _BPF_JMP_HSH(state->bad_arch_hsh),
1385
1737
  _BPF_K(state->arch, -1));
1386
- if (b_head != NULL)
1387
- instr.jt = _BPF_JMP_HSH(b_head->hash);
1738
+ if (state->b_head != NULL)
1739
+ instr.jt = _BPF_JMP_HSH(state->b_head->hash);
1388
1740
  else
1389
1741
  instr.jt = _BPF_JMP_HSH(state->def_hsh);
1390
1742
  blk_cnt++;
@@ -1395,22 +1747,17 @@ static struct bpf_blk *_gen_bpf_arch(struct bpf_state *state,
1395
1747
  _BPF_JMP_NO,
1396
1748
  _BPF_JMP_HSH(state->bad_arch_hsh),
1397
1749
  _BPF_K(state->arch, X32_SYSCALL_BIT));
1398
- if (b_head != NULL)
1399
- instr.jt = _BPF_JMP_HSH(b_head->hash);
1750
+ if (state->b_head != NULL)
1751
+ instr.jt = _BPF_JMP_HSH(state->b_head->hash);
1400
1752
  else
1401
1753
  instr.jt = _BPF_JMP_HSH(state->def_hsh);
1402
1754
  blk_cnt++;
1403
1755
  } else
1404
1756
  /* we should never get here */
1405
1757
  goto arch_failure;
1406
- b_new = _blk_append(state, b_new, &instr);
1407
- if (b_new == NULL)
1408
- goto arch_failure;
1409
- b_new->next = b_head;
1410
- if (b_head != NULL)
1411
- b_head->prev = b_new;
1412
- b_head = b_new;
1413
- rc = _hsh_add(state, &b_head, 1);
1758
+
1759
+ rc = _gen_bpf_insert(state, &instr, &state->b_new,
1760
+ &state->b_head, state->b_new);
1414
1761
  if (rc < 0)
1415
1762
  goto arch_failure;
1416
1763
  }
@@ -1419,34 +1766,29 @@ static struct bpf_blk *_gen_bpf_arch(struct bpf_state *state,
1419
1766
  _BPF_INSTR(instr, _BPF_OP(state->arch, BPF_JMP + BPF_JEQ),
1420
1767
  _BPF_JMP_NO, _BPF_JMP_NXT(blk_cnt++),
1421
1768
  _BPF_K(state->arch, state->arch->token_bpf));
1422
- if (b_head != NULL)
1423
- instr.jt = _BPF_JMP_HSH(b_head->hash);
1769
+ if (state->b_head != NULL)
1770
+ instr.jt = _BPF_JMP_HSH(state->b_head->hash);
1424
1771
  else
1425
1772
  instr.jt = _BPF_JMP_HSH(state->def_hsh);
1426
- b_new = _blk_append(state, NULL, &instr);
1427
- if (b_new == NULL)
1428
- goto arch_failure;
1429
- b_new->next = b_head;
1430
- if (b_head != NULL)
1431
- b_head->prev = b_new;
1432
- b_head = b_new;
1433
- rc = _hsh_add(state, &b_head, 1);
1773
+
1774
+ rc = _gen_bpf_insert(state, &instr, &state->b_new, &state->b_head,
1775
+ NULL);
1434
1776
  if (rc < 0)
1435
1777
  goto arch_failure;
1436
1778
 
1437
1779
  state->arch = NULL;
1438
- return b_head;
1780
+ return state->b_head;
1439
1781
 
1440
1782
  arch_failure:
1441
1783
  /* NOTE: we do the cleanup here and not just return an error as all of
1442
1784
  * the instruction blocks may not be added to the hash table when we
1443
1785
  * hit an error */
1444
1786
  state->arch = NULL;
1445
- b_iter = b_head;
1787
+ b_iter = state->b_head;
1446
1788
  while (b_iter != NULL) {
1447
- b_new = b_iter->next;
1789
+ state->b_new = b_iter->next;
1448
1790
  _blk_free(state, b_iter);
1449
- b_iter = b_new;
1791
+ b_iter = state->b_new;
1450
1792
  }
1451
1793
  return NULL;
1452
1794
  }
@@ -1653,9 +1995,6 @@ static int _gen_bpf_build_bpf(struct bpf_state *state,
1653
1995
  struct db_filter *db_secondary = NULL;
1654
1996
  struct arch_def pseudo_arch;
1655
1997
 
1656
- if (col->filter_cnt == 0)
1657
- return -EINVAL;
1658
-
1659
1998
  /* create a fake architecture definition for use in the early stages */
1660
1999
  memset(&pseudo_arch, 0, sizeof(pseudo_arch));
1661
2000
  pseudo_arch.endian = col->endian;
@@ -1714,7 +2053,8 @@ static int _gen_bpf_build_bpf(struct bpf_state *state,
1714
2053
  db_secondary = NULL;
1715
2054
 
1716
2055
  /* create the filter for the architecture(s) */
1717
- b_new = _gen_bpf_arch(state, col->filters[iter], db_secondary);
2056
+ b_new = _gen_bpf_arch(state, col->filters[iter], db_secondary,
2057
+ col->attr.optimize);
1718
2058
  if (b_new == NULL)
1719
2059
  return -ENOMEM;
1720
2060
  b_new->prev = b_tail;
@@ -1850,6 +2190,7 @@ static int _gen_bpf_build_bpf(struct bpf_state *state,
1850
2190
  break;
1851
2191
  default:
1852
2192
  /* fatal error */
2193
+ rc = -EFAULT;
1853
2194
  goto build_bpf_free_blks;
1854
2195
  }
1855
2196
  switch (i_iter->jf.type) {
@@ -1867,6 +2208,7 @@ static int _gen_bpf_build_bpf(struct bpf_state *state,
1867
2208
  break;
1868
2209
  default:
1869
2210
  /* fatal error */
2211
+ rc = -EFAULT;
1870
2212
  goto build_bpf_free_blks;
1871
2213
  }
1872
2214
  }
@@ -1888,8 +2230,10 @@ static int _gen_bpf_build_bpf(struct bpf_state *state,
1888
2230
  jmp_len += b_jmp->blk_cnt;
1889
2231
  b_jmp = b_jmp->next;
1890
2232
  }
1891
- if (b_jmp == NULL || jmp_len > _BPF_JMP_MAX)
2233
+ if (b_jmp == NULL || jmp_len > _BPF_JMP_MAX) {
2234
+ rc = -EFAULT;
1892
2235
  goto build_bpf_free_blks;
2236
+ }
1893
2237
  i_iter->jt = _BPF_JMP_IMM(jmp_len);
1894
2238
  }
1895
2239
  if (i_iter->jf.type == TGT_PTR_HSH) {
@@ -1900,8 +2244,10 @@ static int _gen_bpf_build_bpf(struct bpf_state *state,
1900
2244
  jmp_len += b_jmp->blk_cnt;
1901
2245
  b_jmp = b_jmp->next;
1902
2246
  }
1903
- if (b_jmp == NULL || jmp_len > _BPF_JMP_MAX)
2247
+ if (b_jmp == NULL || jmp_len > _BPF_JMP_MAX) {
2248
+ rc = -EFAULT;
1904
2249
  goto build_bpf_free_blks;
2250
+ }
1905
2251
  i_iter->jf = _BPF_JMP_IMM(jmp_len);
1906
2252
  }
1907
2253
  if (i_iter->k.type == TGT_PTR_HSH) {
@@ -1915,14 +2261,17 @@ static int _gen_bpf_build_bpf(struct bpf_state *state,
1915
2261
  jmp_len += b_jmp->blk_cnt;
1916
2262
  b_jmp = b_jmp->prev;
1917
2263
  }
1918
- if (b_jmp == NULL)
2264
+ if (b_jmp == NULL) {
2265
+ rc = -EFAULT;
1919
2266
  goto build_bpf_free_blks;
2267
+ }
1920
2268
  i_iter->k = _BPF_K(state->arch, jmp_len);
1921
2269
  }
1922
2270
  }
1923
2271
 
1924
2272
  /* build the bpf program */
1925
- if (_bpf_append_blk(state->bpf, b_iter) < 0)
2273
+ rc = _bpf_append_blk(state->bpf, b_iter);
2274
+ if (rc < 0)
1926
2275
  goto build_bpf_free_blks;
1927
2276
 
1928
2277
  /* we're done with the block, free it */
@@ -1940,37 +2289,43 @@ build_bpf_free_blks:
1940
2289
  __blk_free(state, b_iter);
1941
2290
  b_iter = b_jmp;
1942
2291
  }
1943
- return -EFAULT;
2292
+ return rc;
1944
2293
  }
1945
2294
 
1946
2295
  /**
1947
2296
  * Generate a BPF representation of the filter DB
1948
2297
  * @param col the seccomp filter collection
2298
+ * @param prgm_ptr the bpf program pointer
1949
2299
  *
1950
2300
  * This function generates a BPF representation of the given filter collection.
1951
- * Returns a pointer to a valid bpf_program on success, NULL on failure.
2301
+ * Returns zero on success, negative values on failure.
1952
2302
  *
1953
2303
  */
1954
- struct bpf_program *gen_bpf_generate(const struct db_filter_col *col)
2304
+ int gen_bpf_generate(const struct db_filter_col *col,
2305
+ struct bpf_program **prgm_ptr)
1955
2306
  {
1956
2307
  int rc;
1957
2308
  struct bpf_state state;
1958
2309
  struct bpf_program *prgm;
1959
2310
 
2311
+ if (col->filter_cnt == 0)
2312
+ return -EINVAL;
2313
+
1960
2314
  memset(&state, 0, sizeof(state));
1961
2315
  state.attr = &col->attr;
1962
2316
 
1963
- prgm = zmalloc(sizeof(*(prgm)));
1964
- if (prgm == NULL)
1965
- return NULL;
1966
- state.bpf = prgm;
2317
+ state.bpf = zmalloc(sizeof(*(prgm)));
2318
+ if (state.bpf == NULL)
2319
+ return -ENOMEM;
1967
2320
 
1968
2321
  rc = _gen_bpf_build_bpf(&state, col);
1969
- if (rc == 0)
2322
+ if (rc == 0) {
2323
+ *prgm_ptr = state.bpf;
1970
2324
  state.bpf = NULL;
2325
+ }
1971
2326
  _state_release(&state);
1972
2327
 
1973
- return prgm;
2328
+ return rc;
1974
2329
  }
1975
2330
 
1976
2331
  /**