kobako 0.27.0 → 0.29.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (183) hide show
  1. checksums.yaml +4 -4
  2. data/.release-please-manifest.json +1 -1
  3. data/CHANGELOG.md +241 -0
  4. data/Cargo.lock +132 -126
  5. data/README.md +240 -147
  6. data/ROADMAP.md +28 -22
  7. data/SECURITY.md +2 -2
  8. data/crates/kobako-runtime/CHANGELOG.md +117 -0
  9. data/crates/kobako-runtime/Cargo.toml +27 -6
  10. data/crates/kobako-runtime/README.md +16 -10
  11. data/crates/kobako-runtime/src/dispatch.rs +8 -0
  12. data/crates/kobako-runtime/src/error.rs +8 -9
  13. data/crates/kobako-runtime/src/filesystem/directory/spelling.rs +194 -0
  14. data/crates/kobako-runtime/src/filesystem/directory.rs +1082 -0
  15. data/crates/kobako-runtime/src/filesystem/memory.rs +1100 -0
  16. data/crates/kobako-runtime/src/filesystem/overlay/exclusive.rs +88 -0
  17. data/crates/kobako-runtime/src/filesystem/overlay/stack.rs +808 -0
  18. data/crates/kobako-runtime/src/filesystem/overlay.rs +1955 -0
  19. data/crates/kobako-runtime/src/filesystem/path.rs +60 -0
  20. data/crates/kobako-runtime/src/filesystem/temporary.rs +167 -0
  21. data/crates/kobako-runtime/src/filesystem.rs +392 -0
  22. data/crates/kobako-runtime/src/grant.rs +20 -0
  23. data/crates/kobako-runtime/src/lib.rs +12 -2
  24. data/crates/kobako-runtime/src/mount.rs +178 -0
  25. data/crates/kobako-runtime/src/profile.rs +4 -4
  26. data/crates/kobako-runtime/src/runtime.rs +43 -17
  27. data/crates/kobako-runtime/src/snapshot.rs +33 -15
  28. data/crates/kobako-runtime/src/yielder.rs +14 -6
  29. data/crates/kobako-transport/CHANGELOG.md +45 -0
  30. data/crates/kobako-transport/Cargo.toml +1 -1
  31. data/crates/kobako-transport/README.md +21 -12
  32. data/crates/kobako-transport/src/abi.rs +11 -14
  33. data/crates/kobako-transport/src/envelope/bytes.rs +18 -6
  34. data/crates/kobako-transport/src/envelope/compile_reply.rs +139 -0
  35. data/crates/kobako-transport/src/envelope/fault.rs +2 -1
  36. data/crates/kobako-transport/src/envelope/outcome.rs +17 -16
  37. data/crates/kobako-transport/src/envelope/preamble.rs +513 -0
  38. data/crates/kobako-transport/src/envelope/reply.rs +103 -61
  39. data/crates/kobako-transport/src/envelope/request.rs +305 -0
  40. data/crates/kobako-transport/src/envelope/run.rs +1 -2
  41. data/crates/kobako-transport/src/envelope/tag.rs +49 -0
  42. data/crates/kobako-transport/src/envelope/unsupported.rs +105 -0
  43. data/crates/kobako-transport/src/envelope.rs +19 -12
  44. data/crates/kobako-transport/src/lib.rs +0 -2
  45. data/crates/kobako-wasmtime/CHANGELOG.md +163 -0
  46. data/crates/kobako-wasmtime/Cargo.toml +23 -16
  47. data/crates/kobako-wasmtime/README.md +6 -4
  48. data/crates/kobako-wasmtime/src/abi.rs +67 -36
  49. data/crates/kobako-wasmtime/src/ambient.rs +64 -5
  50. data/crates/kobako-wasmtime/src/cache.rs +204 -127
  51. data/crates/kobako-wasmtime/src/capture.rs +4 -11
  52. data/crates/kobako-wasmtime/src/config.rs +69 -15
  53. data/crates/kobako-wasmtime/src/descriptors.rs +167 -0
  54. data/crates/kobako-wasmtime/src/dispatch.rs +95 -87
  55. data/crates/kobako-wasmtime/src/driver.rs +174 -125
  56. data/crates/kobako-wasmtime/src/exports.rs +88 -34
  57. data/crates/kobako-wasmtime/src/guest_mem.rs +151 -138
  58. data/crates/kobako-wasmtime/src/imports.rs +46 -0
  59. data/crates/kobako-wasmtime/src/instance_pre.rs +19 -58
  60. data/crates/kobako-wasmtime/src/invocation.rs +84 -412
  61. data/crates/kobako-wasmtime/src/io.rs +89 -0
  62. data/crates/kobako-wasmtime/src/lib.rs +7 -24
  63. data/crates/kobako-wasmtime/src/limiter.rs +253 -0
  64. data/crates/kobako-wasmtime/src/preview1/args.rs +60 -0
  65. data/crates/kobako-wasmtime/src/preview1/beneath.rs +188 -0
  66. data/crates/kobako-wasmtime/src/preview1/differential/mount.rs +609 -0
  67. data/crates/kobako-wasmtime/src/preview1/differential.rs +372 -0
  68. data/crates/kobako-wasmtime/src/preview1/errno.rs +267 -0
  69. data/crates/kobako-wasmtime/src/preview1/fd.rs +672 -0
  70. data/crates/kobako-wasmtime/src/preview1/memory.rs +205 -0
  71. data/crates/kobako-wasmtime/src/preview1/mount_view.rs +2499 -0
  72. data/crates/kobako-wasmtime/src/preview1/path.rs +421 -0
  73. data/crates/kobako-wasmtime/src/preview1/poll.rs +333 -0
  74. data/crates/kobako-wasmtime/src/preview1/sock.rs +30 -0
  75. data/crates/kobako-wasmtime/src/preview1.rs +461 -0
  76. data/crates/kobako-wasmtime/src/trap.rs +66 -59
  77. data/crates/kobako-wasmtime/src/wasi.rs +317 -0
  78. data/crates/kobako-wasmtime/tests/compile_posture.rs +43 -0
  79. data/crates/kobako-wasmtime/tests/guest_file.rs +1054 -0
  80. data/crates/kobako-wasmtime/tests/preamble_flags.rs +70 -0
  81. data/crates/kobako-wasmtime/tests/snippet_compile.rs +95 -0
  82. data/crates/kobako-wasmtime/tests/support/mod.rs +30 -0
  83. data/crates/kobako-wasmtime/tests/unanswered_call.rs +86 -0
  84. data/crates/kobako-wasmtime/tests/unsupported_call.rs +51 -0
  85. data/data/kobako.wasm +0 -0
  86. data/ext/kobako/Cargo.toml +4 -2
  87. data/ext/kobako/src/runtime/bridge.rs +177 -113
  88. data/ext/kobako/src/runtime/errors.rs +26 -32
  89. data/ext/kobako/src/runtime/escape.rs +53 -0
  90. data/ext/kobako/src/runtime/filesystem/grants.rs +91 -0
  91. data/ext/kobako/src/runtime/filesystem/ruby.rs +400 -0
  92. data/ext/kobako/src/runtime/filesystem.rs +236 -0
  93. data/ext/kobako/src/runtime/gvl.rs +11 -13
  94. data/ext/kobako/src/runtime/pinned_value.rs +31 -0
  95. data/ext/kobako/src/runtime/snapshot.rs +127 -0
  96. data/ext/kobako/src/runtime.rs +190 -312
  97. data/lib/kobako/capture.rb +1 -4
  98. data/lib/kobako/catalog/extensions.rb +21 -59
  99. data/lib/kobako/catalog/flags.rb +29 -0
  100. data/lib/kobako/catalog/grants.rb +30 -0
  101. data/lib/kobako/catalog/handles.rb +7 -54
  102. data/lib/kobako/catalog/mount.rb +27 -0
  103. data/lib/kobako/catalog/services.rb +17 -60
  104. data/lib/kobako/catalog/snippets.rb +41 -69
  105. data/lib/kobako/catalog.rb +13 -10
  106. data/lib/kobako/codec/decoder.rb +10 -28
  107. data/lib/kobako/codec/encoder.rb +3 -22
  108. data/lib/kobako/codec/error.rb +6 -27
  109. data/lib/kobako/codec/ext_types.rb +72 -94
  110. data/lib/kobako/codec/handle_walk.rb +65 -130
  111. data/lib/kobako/codec/nesting.rb +3 -8
  112. data/lib/kobako/codec/state.rb +21 -11
  113. data/lib/kobako/codec/utils.rb +6 -34
  114. data/lib/kobako/codec/value_budget.rb +86 -0
  115. data/lib/kobako/codec.rb +10 -22
  116. data/lib/kobako/constant_name.rb +8 -0
  117. data/lib/kobako/context.rb +83 -117
  118. data/lib/kobako/errors.rb +57 -132
  119. data/lib/kobako/execution.rb +16 -21
  120. data/lib/kobako/extension.rb +23 -40
  121. data/lib/kobako/filesystem.rb +38 -0
  122. data/lib/kobako/handle.rb +7 -12
  123. data/lib/kobako/outcome.rb +51 -80
  124. data/lib/kobako/payload/arguments.rb +1 -16
  125. data/lib/kobako/payload.rb +4 -12
  126. data/lib/kobako/pool.rb +25 -55
  127. data/lib/kobako/runtime.rb +7 -21
  128. data/lib/kobako/sandbox.rb +128 -137
  129. data/lib/kobako/sandbox_options.rb +71 -90
  130. data/lib/kobako/snippet/bytecode.rb +11 -0
  131. data/lib/kobako/snippet/source.rb +1 -16
  132. data/lib/kobako/snippet.rb +2 -10
  133. data/lib/kobako/transport/block_failure.rb +35 -0
  134. data/lib/kobako/transport/call.rb +1 -14
  135. data/lib/kobako/transport/dispatcher.rb +127 -206
  136. data/lib/kobako/transport/error.rb +6 -20
  137. data/lib/kobako/transport/exposure.rb +10 -17
  138. data/lib/kobako/transport/reflection.rb +108 -63
  139. data/lib/kobako/transport/run.rb +17 -71
  140. data/lib/kobako/transport/yielder.rb +20 -94
  141. data/lib/kobako/transport.rb +4 -15
  142. data/lib/kobako/unresolved.rb +4 -11
  143. data/lib/kobako/usage.rb +2 -6
  144. data/lib/kobako/version.rb +1 -1
  145. data/lib/kobako.rb +1 -0
  146. data/sig/kobako/catalog/extensions.rbs +2 -2
  147. data/sig/kobako/catalog/flags.rbs +13 -0
  148. data/sig/kobako/catalog/grants.rbs +13 -0
  149. data/sig/kobako/catalog/mount.rbs +28 -0
  150. data/sig/kobako/catalog/services.rbs +3 -5
  151. data/sig/kobako/catalog/snippets.rbs +5 -5
  152. data/sig/kobako/catalog.rbs +1 -0
  153. data/sig/kobako/codec/ext_types.rbs +10 -8
  154. data/sig/kobako/codec/handle_walk.rbs +9 -7
  155. data/sig/kobako/codec/state.rbs +7 -1
  156. data/sig/kobako/codec/utils.rbs +2 -2
  157. data/sig/kobako/codec/value_budget.rbs +23 -0
  158. data/sig/kobako/codec.rbs +4 -2
  159. data/sig/kobako/constant_name.rbs +3 -0
  160. data/sig/kobako/context.rbs +15 -8
  161. data/sig/kobako/errors.rbs +10 -4
  162. data/sig/kobako/filesystem.rbs +88 -0
  163. data/sig/kobako/guest_yielder.rbs +9 -0
  164. data/sig/kobako/outcome.rbs +6 -8
  165. data/sig/kobako/pool.rbs +1 -1
  166. data/sig/kobako/runtime.rbs +21 -45
  167. data/sig/kobako/sandbox.rbs +11 -1
  168. data/sig/kobako/sandbox_options.rbs +25 -7
  169. data/sig/kobako/snapshot.rbs +20 -0
  170. data/sig/kobako/snippet/bytecode.rbs +12 -0
  171. data/sig/kobako/transport/block_failure.rbs +13 -0
  172. data/sig/kobako/transport/dispatcher.rbs +15 -19
  173. data/sig/kobako/transport/exposure.rbs +1 -1
  174. data/sig/kobako/transport/reflection.rbs +19 -4
  175. data/sig/kobako/transport/run.rbs +1 -3
  176. data/sig/kobako/transport/yielder.rbs +5 -9
  177. data/sig/kobako/transport.rbs +9 -8
  178. metadata +75 -10
  179. data/crates/kobako-transport/src/envelope/invocation_frames.rs +0 -241
  180. data/crates/kobako-wasmtime/src/frames.rs +0 -273
  181. data/lib/kobako/snippet/binary.rb +0 -26
  182. data/rust-toolchain.toml +0 -15
  183. data/sig/kobako/snippet/binary.rbs +0 -12
@@ -0,0 +1,20 @@
1
+ module Kobako
2
+ # One invocation's result — the whole Snapshot the driver produced.
3
+ class Snapshot
4
+ def outcome: () -> [String, Kobako::Outcome::panic_fields?]
5
+
6
+ def trap_error: () -> Kobako::TrapError?
7
+
8
+ def wall_time: () -> Float
9
+
10
+ def memory_peak: () -> Integer
11
+
12
+ def stdout: () -> String
13
+
14
+ def stdout_truncated?: () -> bool
15
+
16
+ def stderr: () -> String
17
+
18
+ def stderr_truncated?: () -> bool
19
+ end
20
+ end
@@ -0,0 +1,12 @@
1
+ module Kobako
2
+ module Snippet
3
+ class Bytecode < Data
4
+ KIND: Symbol
5
+
6
+ attr_reader body: String
7
+
8
+ def self.new: (body: String) -> Bytecode
9
+ | (String body) -> Bytecode
10
+ end
11
+ end
12
+ end
@@ -0,0 +1,13 @@
1
+ module Kobako
2
+ module Transport
3
+ class BlockFailure
4
+ @raised: Kobako::BlockError?
5
+
6
+ def initialize: () -> void
7
+
8
+ def remember: (Kobako::BlockError error) -> Kobako::BlockError
9
+
10
+ def fault_text: (Exception error) -> String?
11
+ end
12
+ end
13
+ end
@@ -9,39 +9,35 @@ module Kobako
9
9
 
10
10
  BREAK_THROW: Symbol
11
11
 
12
- OWN_FAULTS: Hash[singleton(StandardError), String]
12
+ BARE_FAULTS: Hash[singleton(StandardError), String]
13
13
 
14
+ def self.dispatch: (Kobako::Transport::Call call, Kobako::Transport::_ServiceResolver resolver, Kobako::Transport::_HandleTable handles, Kobako::Transport::BlockFailure failure, Kobako::Transport::_GuestYielder guest_yielder) -> [Symbol, String, String?]
14
15
 
16
+ private
15
17
 
18
+ def self.run: (Kobako::Transport::Call call, Kobako::Transport::_ServiceResolver resolver, Kobako::Transport::_HandleTable handles, Kobako::Transport::Yielder? yielder) -> untyped
16
19
 
17
- def self?.dispatch: (Kobako::Transport::Call call, Kobako::Transport::_ServiceRegistry resolver, Kobako::Transport::_HandleTable handler, Kobako::Transport::_GuestYielder yield_to_guest) -> [bool, String, String?]
20
+ def self.decode_arguments: (String payload) -> [Kobako::Payload::Arguments, bool]
18
21
 
19
- def self?.run: (Kobako::Transport::Call call, Kobako::Transport::_ServiceRegistry resolver, Kobako::Transport::_HandleTable handler, Kobako::Transport::Yielder? yielder) -> untyped
22
+ def self.resolve_call_args: (Kobako::Payload::Arguments arguments, Kobako::Codec::_HandleTable handles, bool carried_handle) -> [Array[untyped], Hash[Symbol, untyped]]
20
23
 
21
- def self?.resolve_call_args: (Kobako::Payload::Arguments arguments, Kobako::Codec::_HandleTable handler, bool carried_handle) -> [Array[untyped], Hash[Symbol, untyped]]
24
+ def self.caught_fault: (StandardError error, Kobako::Transport::BlockFailure failure) -> [String, String]
22
25
 
23
- def self?.decode_arguments: (String payload) -> [Kobako::Payload::Arguments, bool]
26
+ def self.invoke: (Kobako::Transport::Exposure exposure, String method, Array[untyped] args, Hash[Symbol, untyped] kwargs, Kobako::Transport::Yielder? yielder) -> untyped
24
27
 
25
- def self?.caught_fault: (StandardError error, Kobako::Transport::Yielder? yielder) -> [String, String]
28
+ def self.reject_unreachable!: (Kobako::Transport::Exposure exposure, Symbol name) -> void
26
29
 
27
- def self?.invoke: (Kobako::Transport::Exposure exposure, String method, Array[untyped] args, Hash[Symbol, untyped] kwargs, ?Kobako::Transport::Yielder? yielder) -> untyped
30
+ def self.resolve_arg: (untyped value, Kobako::Codec::_HandleTable handles) -> untyped
28
31
 
29
- def self?.reject_unreachable!: (Kobako::Transport::Exposure exposure, Symbol name) -> void
32
+ def self.resolve_target: (String | Integer target, Kobako::Transport::_ServiceResolver resolver, Kobako::Transport::_HandleTable handles) -> Kobako::Transport::Exposure
30
33
 
34
+ def self.resolve_path: (String path, Kobako::Transport::_ServiceResolver resolver) -> Kobako::Transport::Exposure
31
35
 
32
- def self?.resolve_arg: (untyped value, Kobako::Codec::_HandleTable handler) -> untyped
36
+ def self.resolve_handle: (Integer id, Kobako::Transport::_HandleTable handles) -> Kobako::Transport::Exposure
33
37
 
34
- def self?.resolve_target: (String | Integer target, Kobako::Transport::_ServiceRegistry resolver, Kobako::Transport::_HandleTable handler) -> Kobako::Transport::Exposure
38
+ def self.encode_ok: (untyped value, Kobako::Codec::_HandleTable handles) -> String
35
39
 
36
- def self?.resolve_path: (String path, Kobako::Transport::_ServiceRegistry resolver) -> Kobako::Transport::Exposure
37
-
38
- def self?.resolve_handle: (Integer id, Kobako::Transport::_HandleTable handler) -> Kobako::Transport::Exposure
39
-
40
- def self?.encode_ok: (untyped value, Kobako::Codec::_HandleTable handler) -> String
41
-
42
- def self?.wrap_as_handle: (untyped value, Kobako::Codec::_HandleTable handler) -> Kobako::Handle
43
-
44
- def self?.fault: (String type, String message) -> [String, String]
40
+ def self.fault: (String type, String message) -> [String, String]
45
41
  end
46
42
  end
47
43
  end
@@ -37,7 +37,7 @@ module Kobako
37
37
 
38
38
  def self.with_singleton: (untyped object, Set[Symbol] names) -> Set[Symbol]
39
39
 
40
- def self.authored: (Module owner) -> Array[Symbol]
40
+ def self.authored_names:(Module owner) -> Array[Symbol]
41
41
  end
42
42
  end
43
43
  end
@@ -1,15 +1,30 @@
1
1
  module Kobako
2
2
  module Transport
3
3
  module Reflection
4
- META_OWNERS: Array[Module]
5
4
  GADGET_OWNERS: Array[Module]
6
5
  CALLABLE_ALLOW: Array[Symbol]
7
6
 
8
- def self?.refusal: (Kobako::Transport::Exposure exposure, Symbol name) -> String?
7
+ def self.refusal: (Kobako::Transport::Exposure exposure, Symbol name) -> String?
9
8
 
10
- def self?.ambient_refusal: (untyped target, Symbol name) -> String?
9
+ def self.authored?: (UnboundMethod method) -> bool
11
10
 
12
- def self?.ambient_owner?: (Module owner, untyped target) -> bool
11
+ private
12
+
13
+ def self.ambient_copy?: (UnboundMethod method) -> bool
14
+
15
+ def self.ambient_refusal: (untyped target, Symbol name) -> String?
16
+
17
+ def self.defined_refusal: (untyped target, Symbol name, Module klass) -> String?
18
+
19
+ def self.authored_for?: (untyped target, Symbol name, UnboundMethod method, Module klass) -> bool
20
+
21
+ def self.refused: (Symbol name) -> String
22
+
23
+ def self.owner_refusal: (untyped target, Symbol name, Module owner) -> String?
24
+
25
+ def self.lookup_class: (untyped target) -> Module
26
+
27
+ def self.ambient_owner?: (Module owner, untyped target) -> bool
13
28
  end
14
29
  end
15
30
  end
@@ -1,8 +1,6 @@
1
1
  module Kobako
2
2
  module Transport
3
3
  class Run < Data
4
- NAME_PATTERN: Regexp
5
-
6
4
  attr_reader entrypoint: Symbol
7
5
  attr_reader args: Array[Kobako::Codec::wire_value]
8
6
  attr_reader kwargs: Hash[Symbol, Kobako::Codec::wire_value]
@@ -11,7 +9,7 @@ module Kobako
11
9
 
12
10
  def initialize: (entrypoint: Symbol | String, ?args: Array[untyped], ?kwargs: Hash[untyped, untyped]) -> void
13
11
 
14
- def payload: (Kobako::Codec::_HandleTable handler) -> String
12
+ def payload: (Kobako::Codec::_HandleTable handles) -> String
15
13
 
16
14
  private
17
15
 
@@ -1,28 +1,24 @@
1
1
  module Kobako
2
2
  module Transport
3
3
  class Yielder
4
- @yield_to_guest: Kobako::Transport::_GuestYielder
4
+ @guest_yielder: Kobako::Transport::_GuestYielder
5
5
  @break_tag: Symbol
6
- @handler: Kobako::Codec::_HandleTable
6
+ @handles: Kobako::Codec::_HandleTable
7
+ @failure: Kobako::Transport::BlockFailure
7
8
  @active: bool
8
- @raised: Kobako::BlockError?
9
9
 
10
- def initialize: (Kobako::Transport::_GuestYielder yield_to_guest, Symbol break_tag, Kobako::Codec::_HandleTable handler) -> void
11
-
12
- def fault_text: (Exception error) -> String?
10
+ def initialize: (Kobako::Transport::_GuestYielder guest_yielder, Symbol break_tag, Kobako::Codec::_HandleTable handles, Kobako::Transport::BlockFailure failure) -> void
13
11
 
14
12
  def yield: (*untyped args) -> untyped
15
13
 
16
14
  def to_proc: () -> Proc
17
15
 
18
- def invalidate!: () -> void
16
+ def invalidate: () -> void
19
17
 
20
18
  private
21
19
 
22
20
  def encode_args: (Array[untyped] args) -> String
23
21
 
24
- def remember: (Kobako::BlockError error) -> Kobako::BlockError
25
-
26
22
  def decode_body: (String body) -> [untyped, bool]
27
23
 
28
24
  def restore: (untyped value, bool carried_handle) -> untyped
@@ -1,8 +1,9 @@
1
1
  module Kobako
2
2
  module Transport
3
3
  # The guest re-entry callable a dispatch hands to a Yielder: invoked
4
- # with the encoded yield args, it returns the encoded Yield Reply.
5
- # The ext's Kobako::Runtime::GuestYielder is the production conformer;
4
+ # with the encoded yield args, it returns the decoded Yield Reply as an
5
+ # +[arm, body, klass]+ triple.
6
+ # The ext's Kobako::GuestYielder is the production conformer;
6
7
  # modelled structurally so the Transport layer needs no upward
7
8
  # dependency on Runtime.
8
9
  interface _GuestYielder
@@ -13,13 +14,13 @@ module Kobako
13
14
  # side already decoded off the core envelope and answering the arm and
14
15
  # body it puts on the Reply. Named here so the producer (Context) and the
15
16
  # consumer (Runtime) cannot declare it differently.
16
- type dispatch_proc = ^(String | Integer, String, bool, String, _GuestYielder) -> [bool, String, String?]
17
+ type dispatch_proc = ^(String | Integer, String, bool, String, _GuestYielder) -> [Symbol, String, String?]
17
18
 
18
- # The Service registry a dispatch resolves constant-path targets
19
- # against. The Sandbox's Kobako::Catalog::Services is the
20
- # production conformer; modelled structurally so the Transport
21
- # layer needs no upward dependency on Catalog.
22
- interface _ServiceRegistry
19
+ # What a dispatch resolves constant-path targets against. The
20
+ # invocation's Kobako::Context is the production conformer, so its
21
+ # overrides answer before the Sandbox's bindings; modelled structurally
22
+ # so the Transport layer needs no upward dependency on Orchestration.
23
+ interface _ServiceResolver
23
24
  def lookup: (String target) -> Exposure
24
25
  end
25
26
 
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: kobako
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.27.0
4
+ version: 0.29.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Aotokitsuruya
@@ -13,16 +13,22 @@ dependencies:
13
13
  name: msgpack
14
14
  requirement: !ruby/object:Gem::Requirement
15
15
  requirements:
16
- - - "~>"
16
+ - - ">="
17
+ - !ruby/object:Gem::Version
18
+ version: 1.8.2
19
+ - - "<"
17
20
  - !ruby/object:Gem::Version
18
- version: '1.7'
21
+ version: '2'
19
22
  type: :runtime
20
23
  prerelease: false
21
24
  version_requirements: !ruby/object:Gem::Requirement
22
25
  requirements:
23
- - - "~>"
26
+ - - ">="
27
+ - !ruby/object:Gem::Version
28
+ version: 1.8.2
29
+ - - "<"
24
30
  - !ruby/object:Gem::Version
25
- version: '1.7'
31
+ version: '2'
26
32
  - !ruby/object:Gem::Dependency
27
33
  name: rb_sys
28
34
  requirement: !ruby/object:Gem::Requirement
@@ -60,7 +66,18 @@ files:
60
66
  - crates/kobako-runtime/README.md
61
67
  - crates/kobako-runtime/src/dispatch.rs
62
68
  - crates/kobako-runtime/src/error.rs
69
+ - crates/kobako-runtime/src/filesystem.rs
70
+ - crates/kobako-runtime/src/filesystem/directory.rs
71
+ - crates/kobako-runtime/src/filesystem/directory/spelling.rs
72
+ - crates/kobako-runtime/src/filesystem/memory.rs
73
+ - crates/kobako-runtime/src/filesystem/overlay.rs
74
+ - crates/kobako-runtime/src/filesystem/overlay/exclusive.rs
75
+ - crates/kobako-runtime/src/filesystem/overlay/stack.rs
76
+ - crates/kobako-runtime/src/filesystem/path.rs
77
+ - crates/kobako-runtime/src/filesystem/temporary.rs
78
+ - crates/kobako-runtime/src/grant.rs
63
79
  - crates/kobako-runtime/src/lib.rs
80
+ - crates/kobako-runtime/src/mount.rs
64
81
  - crates/kobako-runtime/src/profile.rs
65
82
  - crates/kobako-runtime/src/runtime.rs
66
83
  - crates/kobako-runtime/src/snapshot.rs
@@ -72,12 +89,16 @@ files:
72
89
  - crates/kobako-transport/src/envelope.rs
73
90
  - crates/kobako-transport/src/envelope/bytes.rs
74
91
  - crates/kobako-transport/src/envelope/call.rs
92
+ - crates/kobako-transport/src/envelope/compile_reply.rs
75
93
  - crates/kobako-transport/src/envelope/error_record.rs
76
94
  - crates/kobako-transport/src/envelope/fault.rs
77
- - crates/kobako-transport/src/envelope/invocation_frames.rs
78
95
  - crates/kobako-transport/src/envelope/outcome.rs
96
+ - crates/kobako-transport/src/envelope/preamble.rs
79
97
  - crates/kobako-transport/src/envelope/reply.rs
98
+ - crates/kobako-transport/src/envelope/request.rs
80
99
  - crates/kobako-transport/src/envelope/run.rs
100
+ - crates/kobako-transport/src/envelope/tag.rs
101
+ - crates/kobako-transport/src/envelope/unsupported.rs
81
102
  - crates/kobako-transport/src/lib.rs
82
103
  - crates/kobako-wasmtime/CHANGELOG.md
83
104
  - crates/kobako-wasmtime/Cargo.toml
@@ -87,15 +108,38 @@ files:
87
108
  - crates/kobako-wasmtime/src/cache.rs
88
109
  - crates/kobako-wasmtime/src/capture.rs
89
110
  - crates/kobako-wasmtime/src/config.rs
111
+ - crates/kobako-wasmtime/src/descriptors.rs
90
112
  - crates/kobako-wasmtime/src/dispatch.rs
91
113
  - crates/kobako-wasmtime/src/driver.rs
92
114
  - crates/kobako-wasmtime/src/exports.rs
93
- - crates/kobako-wasmtime/src/frames.rs
94
115
  - crates/kobako-wasmtime/src/guest_mem.rs
116
+ - crates/kobako-wasmtime/src/imports.rs
95
117
  - crates/kobako-wasmtime/src/instance_pre.rs
96
118
  - crates/kobako-wasmtime/src/invocation.rs
119
+ - crates/kobako-wasmtime/src/io.rs
97
120
  - crates/kobako-wasmtime/src/lib.rs
121
+ - crates/kobako-wasmtime/src/limiter.rs
122
+ - crates/kobako-wasmtime/src/preview1.rs
123
+ - crates/kobako-wasmtime/src/preview1/args.rs
124
+ - crates/kobako-wasmtime/src/preview1/beneath.rs
125
+ - crates/kobako-wasmtime/src/preview1/differential.rs
126
+ - crates/kobako-wasmtime/src/preview1/differential/mount.rs
127
+ - crates/kobako-wasmtime/src/preview1/errno.rs
128
+ - crates/kobako-wasmtime/src/preview1/fd.rs
129
+ - crates/kobako-wasmtime/src/preview1/memory.rs
130
+ - crates/kobako-wasmtime/src/preview1/mount_view.rs
131
+ - crates/kobako-wasmtime/src/preview1/path.rs
132
+ - crates/kobako-wasmtime/src/preview1/poll.rs
133
+ - crates/kobako-wasmtime/src/preview1/sock.rs
98
134
  - crates/kobako-wasmtime/src/trap.rs
135
+ - crates/kobako-wasmtime/src/wasi.rs
136
+ - crates/kobako-wasmtime/tests/compile_posture.rs
137
+ - crates/kobako-wasmtime/tests/guest_file.rs
138
+ - crates/kobako-wasmtime/tests/preamble_flags.rs
139
+ - crates/kobako-wasmtime/tests/snippet_compile.rs
140
+ - crates/kobako-wasmtime/tests/support/mod.rs
141
+ - crates/kobako-wasmtime/tests/unanswered_call.rs
142
+ - crates/kobako-wasmtime/tests/unsupported_call.rs
99
143
  - data/kobako.wasm
100
144
  - ext/kobako/Cargo.toml
101
145
  - ext/kobako/extconf.rb
@@ -103,12 +147,21 @@ files:
103
147
  - ext/kobako/src/runtime.rs
104
148
  - ext/kobako/src/runtime/bridge.rs
105
149
  - ext/kobako/src/runtime/errors.rs
150
+ - ext/kobako/src/runtime/escape.rs
151
+ - ext/kobako/src/runtime/filesystem.rs
152
+ - ext/kobako/src/runtime/filesystem/grants.rs
153
+ - ext/kobako/src/runtime/filesystem/ruby.rs
106
154
  - ext/kobako/src/runtime/gvl.rs
155
+ - ext/kobako/src/runtime/pinned_value.rs
156
+ - ext/kobako/src/runtime/snapshot.rs
107
157
  - lib/kobako.rb
108
158
  - lib/kobako/capture.rb
109
159
  - lib/kobako/catalog.rb
110
160
  - lib/kobako/catalog/extensions.rb
161
+ - lib/kobako/catalog/flags.rb
162
+ - lib/kobako/catalog/grants.rb
111
163
  - lib/kobako/catalog/handles.rb
164
+ - lib/kobako/catalog/mount.rb
112
165
  - lib/kobako/catalog/services.rb
113
166
  - lib/kobako/catalog/snippets.rb
114
167
  - lib/kobako/codec.rb
@@ -120,10 +173,13 @@ files:
120
173
  - lib/kobako/codec/nesting.rb
121
174
  - lib/kobako/codec/state.rb
122
175
  - lib/kobako/codec/utils.rb
176
+ - lib/kobako/codec/value_budget.rb
177
+ - lib/kobako/constant_name.rb
123
178
  - lib/kobako/context.rb
124
179
  - lib/kobako/errors.rb
125
180
  - lib/kobako/execution.rb
126
181
  - lib/kobako/extension.rb
182
+ - lib/kobako/filesystem.rb
127
183
  - lib/kobako/handle.rb
128
184
  - lib/kobako/outcome.rb
129
185
  - lib/kobako/payload.rb
@@ -133,9 +189,10 @@ files:
133
189
  - lib/kobako/sandbox.rb
134
190
  - lib/kobako/sandbox_options.rb
135
191
  - lib/kobako/snippet.rb
136
- - lib/kobako/snippet/binary.rb
192
+ - lib/kobako/snippet/bytecode.rb
137
193
  - lib/kobako/snippet/source.rb
138
194
  - lib/kobako/transport.rb
195
+ - lib/kobako/transport/block_failure.rb
139
196
  - lib/kobako/transport/call.rb
140
197
  - lib/kobako/transport/dispatcher.rb
141
198
  - lib/kobako/transport/error.rb
@@ -147,12 +204,14 @@ files:
147
204
  - lib/kobako/usage.rb
148
205
  - lib/kobako/version.rb
149
206
  - release-please-config.json
150
- - rust-toolchain.toml
151
207
  - sig/kobako.rbs
152
208
  - sig/kobako/capture.rbs
153
209
  - sig/kobako/catalog.rbs
154
210
  - sig/kobako/catalog/extensions.rbs
211
+ - sig/kobako/catalog/flags.rbs
212
+ - sig/kobako/catalog/grants.rbs
155
213
  - sig/kobako/catalog/handles.rbs
214
+ - sig/kobako/catalog/mount.rbs
156
215
  - sig/kobako/catalog/services.rbs
157
216
  - sig/kobako/catalog/snippets.rbs
158
217
  - sig/kobako/codec.rbs
@@ -164,10 +223,14 @@ files:
164
223
  - sig/kobako/codec/nesting.rbs
165
224
  - sig/kobako/codec/state.rbs
166
225
  - sig/kobako/codec/utils.rbs
226
+ - sig/kobako/codec/value_budget.rbs
227
+ - sig/kobako/constant_name.rbs
167
228
  - sig/kobako/context.rbs
168
229
  - sig/kobako/errors.rbs
169
230
  - sig/kobako/execution.rbs
170
231
  - sig/kobako/extension.rbs
232
+ - sig/kobako/filesystem.rbs
233
+ - sig/kobako/guest_yielder.rbs
171
234
  - sig/kobako/handle.rbs
172
235
  - sig/kobako/outcome.rbs
173
236
  - sig/kobako/payload.rbs
@@ -176,10 +239,12 @@ files:
176
239
  - sig/kobako/runtime.rbs
177
240
  - sig/kobako/sandbox.rbs
178
241
  - sig/kobako/sandbox_options.rbs
242
+ - sig/kobako/snapshot.rbs
179
243
  - sig/kobako/snippet.rbs
180
- - sig/kobako/snippet/binary.rbs
244
+ - sig/kobako/snippet/bytecode.rbs
181
245
  - sig/kobako/snippet/source.rbs
182
246
  - sig/kobako/transport.rbs
247
+ - sig/kobako/transport/block_failure.rbs
183
248
  - sig/kobako/transport/call.rbs
184
249
  - sig/kobako/transport/dispatcher.rbs
185
250
  - sig/kobako/transport/error.rbs
@@ -1,241 +0,0 @@
1
- //! The invocation frames — Frame 1's bound constant paths and Frame 3's
2
- //! preloaded snippets, the two both entry points read before running
3
- //! anything. The numbering skips Frame 2 because the `#eval` user source
4
- //! is raw UTF-8 with no envelope of its own.
5
- //!
6
- //! Both are mandatory-presence even when empty, so a reader never has to
7
- //! tell an absent frame from an empty one, and each frame's length reaches
8
- //! the guest from the channel's own prefix rather than from the envelope.
9
-
10
- use super::bytes::{Reader, Writer};
11
- use super::DecodeError;
12
-
13
- const SNIPPET_SOURCE: u8 = 0;
14
- const SNIPPET_BYTECODE: u8 = 1;
15
-
16
- /// Frame 1 — the bound constant paths the guest installs proxies from.
17
- /// Always present; an empty list means no Service is bound.
18
- #[derive(Debug, Clone, PartialEq, Eq, Default)]
19
- pub struct Bindings {
20
- pub paths: Vec<String>,
21
- }
22
-
23
- impl Bindings {
24
- pub fn decode(bytes: &[u8]) -> Result<Self, DecodeError> {
25
- let mut reader = Reader::new(bytes);
26
- let paths = reader.text_list()?;
27
- reader.finish()?;
28
- Ok(Bindings { paths })
29
- }
30
-
31
- pub fn encode(&self) -> Vec<u8> {
32
- let mut writer = Writer::new();
33
- writer.list(&self.paths);
34
- writer.into_bytes()
35
- }
36
- }
37
-
38
- /// One preloaded snippet. Source carries the filename the guest compiles
39
- /// under; bytecode does not, because its filename — when it has one — lives
40
- /// in the bytecode's own debug section.
41
- #[derive(Debug, Clone, PartialEq, Eq)]
42
- pub enum Snippet {
43
- Source { name: String, body: String },
44
- Bytecode { body: Vec<u8> },
45
- }
46
-
47
- /// Frame 3 — the preloaded snippets, in insertion order. Always present;
48
- /// a zero count means nothing was preloaded.
49
- #[derive(Debug, Clone, PartialEq, Eq, Default)]
50
- pub struct Snippets {
51
- pub entries: Vec<Snippet>,
52
- }
53
-
54
- impl Snippets {
55
- pub fn decode(bytes: &[u8]) -> Result<Self, DecodeError> {
56
- let mut reader = Reader::new(bytes);
57
- let count = reader.u32()? as usize;
58
- // Each entry costs at least a kind byte, so a count past the bytes
59
- // left cannot be satisfied; refusing it bounds the allocation.
60
- if count > reader.remaining().len() {
61
- return Err(DecodeError::new(
62
- "Frame 3 declares more entries than the frame holds",
63
- ));
64
- }
65
- let mut entries = Vec::with_capacity(count);
66
- for _ in 0..count {
67
- entries.push(match reader.u8()? {
68
- SNIPPET_SOURCE => Snippet::Source {
69
- name: reader.text()?.to_owned(),
70
- body: reader.text()?.to_owned(),
71
- },
72
- SNIPPET_BYTECODE => Snippet::Bytecode {
73
- body: reader.bytes()?.to_vec(),
74
- },
75
- _ => return Err(DecodeError::new("Frame 3 snippet kind must be 0 or 1")),
76
- });
77
- }
78
- reader.finish()?;
79
- Ok(Snippets { entries })
80
- }
81
-
82
- pub fn encode(&self) -> Vec<u8> {
83
- let mut writer = Writer::new();
84
- writer.u32(self.entries.len() as u32);
85
- for entry in &self.entries {
86
- match entry {
87
- Snippet::Source { name, body } => {
88
- writer
89
- .u8(SNIPPET_SOURCE)
90
- .bytes(name.as_bytes())
91
- .bytes(body.as_bytes());
92
- }
93
- Snippet::Bytecode { body } => {
94
- writer.u8(SNIPPET_BYTECODE).bytes(body);
95
- }
96
- }
97
- }
98
- writer.into_bytes()
99
- }
100
- }
101
-
102
- #[cfg(test)]
103
- mod tests {
104
- use super::*;
105
-
106
- // @behavior WE-050
107
- #[test]
108
- fn empty_bindings_round_trip() {
109
- let encoded = Bindings::default().encode();
110
- assert_eq!(
111
- Bindings::decode(&encoded),
112
- Ok(Bindings::default()),
113
- "a Sandbox with no bindings must send a present, empty Frame 1"
114
- );
115
- }
116
-
117
- // @behavior WE-051
118
- #[test]
119
- fn bindings_round_trip_every_path() {
120
- let bindings = Bindings {
121
- paths: vec!["MyService::KV".into(), "File".into()],
122
- };
123
- let encoded = bindings.encode();
124
- assert_eq!(
125
- Bindings::decode(&encoded),
126
- Ok(bindings),
127
- "Frame 1 must carry every bound path in order"
128
- );
129
- }
130
-
131
- // @behavior WE-052
132
- #[test]
133
- fn snippets_round_trip_both_kinds_in_order() {
134
- let snippets = Snippets {
135
- entries: vec![
136
- Snippet::Source {
137
- name: "Helper".into(),
138
- body: "def helper; end".into(),
139
- },
140
- Snippet::Bytecode {
141
- body: vec![0x52, 0x49, 0x54, 0x45],
142
- },
143
- ],
144
- };
145
- let encoded = snippets.encode();
146
- assert_eq!(
147
- Snippets::decode(&encoded),
148
- Ok(snippets),
149
- "Frame 3 must carry source and bytecode entries in insertion order"
150
- );
151
- }
152
-
153
- // @behavior WE-053
154
- #[test]
155
- fn an_empty_snippet_table_round_trips() {
156
- let encoded = Snippets::default().encode();
157
- assert_eq!(
158
- Snippets::decode(&encoded),
159
- Ok(Snippets::default()),
160
- "a Sandbox with no preloads must send a present, zero-count Frame 3"
161
- );
162
- }
163
-
164
- // @behavior WE-054
165
- #[test]
166
- fn golden_layout_pins_the_bindings_as_a_counted_list() {
167
- let bindings = Bindings {
168
- paths: vec!["A".into()],
169
- };
170
- assert_eq!(
171
- bindings.encode(),
172
- vec![
173
- 0, 0, 0, 1, // path count
174
- 0, 0, 0, 1, b'A',
175
- ],
176
- "Frame 1 must be a counted list of paths, so the count precedes the first entry"
177
- );
178
- }
179
-
180
- // @behavior WE-055
181
- #[test]
182
- fn golden_layout_pins_the_snippet_entry_shape() {
183
- let snippets = Snippets {
184
- entries: vec![
185
- Snippet::Source {
186
- name: "N".into(),
187
- body: "b".into(),
188
- },
189
- Snippet::Bytecode { body: vec![0x52] },
190
- ],
191
- };
192
- assert_eq!(
193
- snippets.encode(),
194
- vec![
195
- 0, 0, 0, 2, // entry count
196
- 0, // kind: source
197
- 0, 0, 0, 1, b'N', // name, source only
198
- 0, 0, 0, 1, b'b', // body
199
- 1, // kind: bytecode
200
- 0, 0, 0, 1, 0x52, // body, no name
201
- ],
202
- "a source entry must encode as kind byte 0 with a name and a bytecode entry as \
203
- kind byte 1 with none, so the two stay distinguishable by their tag alone"
204
- );
205
- }
206
-
207
- // @behavior WE-056
208
- #[test]
209
- fn an_unknown_snippet_kind_is_refused() {
210
- let bytes = {
211
- let mut w = Writer::new();
212
- w.u32(1).u8(9);
213
- w.into_bytes()
214
- };
215
- assert!(
216
- Snippets::decode(&bytes).is_err(),
217
- "a Frame 3 snippet kind that is neither source nor bytecode must be rejected"
218
- );
219
- }
220
-
221
- // @behavior WE-057
222
- #[test]
223
- fn a_snippet_count_the_frame_cannot_satisfy_is_refused() {
224
- let bytes = [0xff, 0xff, 0xff, 0xff];
225
- assert!(
226
- Snippets::decode(&bytes).is_err(),
227
- "a Frame 3 count larger than the frame must be rejected before any allocation"
228
- );
229
- }
230
-
231
- // @behavior WE-058
232
- #[test]
233
- fn trailing_bytes_after_a_frame_are_refused() {
234
- let mut encoded = Bindings::default().encode();
235
- encoded.push(0);
236
- assert!(
237
- Bindings::decode(&encoded).is_err(),
238
- "bytes past Frame 1's last field must fail loudly as a framing desync"
239
- );
240
- }
241
- }