@scriptc/cli-darwin-x64 0.2.4 → 0.2.6

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 (434) hide show
  1. package/dist/THIRD_PARTY_NOTICES +1 -1
  2. package/dist/bin/scriptc +0 -0
  3. package/dist/bin/scriptc.json +1 -1
  4. package/dist/lib/declarations/scriptc-node-fallback.d.ts +972 -245
  5. package/dist/lib/declarations/scriptc-overrides.d.ts +5 -1
  6. package/dist/lib/declarations/scriptc.d.ts +22 -2
  7. package/dist/lib/llvm/bin/scriptc-llvm-codegen +0 -0
  8. package/dist/lib/llvm/package.json +1 -1
  9. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_array.o +0 -0
  10. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_assert.o +0 -0
  11. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_async.o +0 -0
  12. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_bytes.o +0 -0
  13. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_bytes_io.o +0 -0
  14. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_child.o +0 -0
  15. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_closure.o +0 -0
  16. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_console.o +0 -0
  17. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_context.o +0 -0
  18. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_copying.o +0 -0
  19. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_cycle.o +0 -0
  20. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_dgram.o +0 -0
  21. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_error.o +0 -0
  22. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_events.o +0 -0
  23. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_events_emitter.o +0 -0
  24. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_exception.o +0 -0
  25. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_fetch.o +0 -0
  26. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_file_handle.o +0 -0
  27. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_json.o +0 -0
  28. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_lib.o +0 -0
  29. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_map.o +0 -0
  30. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_number.o +0 -0
  31. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_object.o +0 -0
  32. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_readline.o +0 -0
  33. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_regex.o +0 -0
  34. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_shared.o +0 -0
  35. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_stream.o +0 -0
  36. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_string.o +0 -0
  37. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_tls.o +0 -0
  38. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_union.o +0 -0
  39. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default/scr_util_compare.o +0 -0
  40. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_array.o +0 -0
  41. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_assert.o +0 -0
  42. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_async.o +0 -0
  43. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_async_dyn.o +0 -0
  44. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_bigint.o +0 -0
  45. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_bigint_assert.o +0 -0
  46. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_bytes.o +0 -0
  47. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_bytes_io.o +0 -0
  48. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_child.o +0 -0
  49. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_closure.o +0 -0
  50. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_console.o +0 -0
  51. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_console_native.o +0 -0
  52. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_context.o +0 -0
  53. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_copying.o +0 -0
  54. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_crypto_async.o +0 -0
  55. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_cycle.o +0 -0
  56. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_dc.o +0 -0
  57. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_dgram.o +0 -0
  58. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_dyn_handle.o +0 -0
  59. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_dyn_invoke.o +0 -0
  60. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_error.o +0 -0
  61. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_events.o +0 -0
  62. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_events_emitter.o +0 -0
  63. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_exception.o +0 -0
  64. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_fetch.o +0 -0
  65. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_ffi.o +0 -0
  66. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_ffi_queue.o +0 -0
  67. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_file_handle.o +0 -0
  68. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_grapheme.o +0 -0
  69. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_http.o +0 -0
  70. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_http2.o +0 -0
  71. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_inspect.o +0 -0
  72. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_json.o +0 -0
  73. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_lib.o +0 -0
  74. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_loop_epoll.o +0 -0
  75. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_loop_kqueue.o +0 -0
  76. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_loop_wsapoll.o +0 -0
  77. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_map.o +0 -0
  78. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_net.o +0 -0
  79. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_node_builtin.o +0 -0
  80. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_number.o +0 -0
  81. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_object.o +0 -0
  82. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_path.o +0 -0
  83. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_qs.o +0 -0
  84. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_readline.o +0 -0
  85. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_regex.o +0 -0
  86. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_shared.o +0 -0
  87. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_stream.o +0 -0
  88. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_string.o +0 -0
  89. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_symbol.o +0 -0
  90. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_test.o +0 -0
  91. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_tls.o +0 -0
  92. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_tls_ca.o +0 -0
  93. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_union.o +0 -0
  94. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_url.o +0 -0
  95. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_url_params.o +0 -0
  96. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_util.o +0 -0
  97. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_util_compare.o +0 -0
  98. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_util_style.o +0 -0
  99. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_watch.o +0 -0
  100. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/default-workers/scr_zlib.o +0 -0
  101. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_array.o +0 -0
  102. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_assert.o +0 -0
  103. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_async.o +0 -0
  104. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_bytes.o +0 -0
  105. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_bytes_io.o +0 -0
  106. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_child.o +0 -0
  107. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_closure.o +0 -0
  108. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_console.o +0 -0
  109. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_context.o +0 -0
  110. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_copying.o +0 -0
  111. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_cycle.o +0 -0
  112. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_dgram.o +0 -0
  113. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_error.o +0 -0
  114. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_events.o +0 -0
  115. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_events_emitter.o +0 -0
  116. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_exception.o +0 -0
  117. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_file_handle.o +0 -0
  118. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_island.o +0 -0
  119. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_json.o +0 -0
  120. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_lib.o +0 -0
  121. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_map.o +0 -0
  122. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_number.o +0 -0
  123. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_object.o +0 -0
  124. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_readline.o +0 -0
  125. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_regex.o +0 -0
  126. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_shared.o +0 -0
  127. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_stream.o +0 -0
  128. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_string.o +0 -0
  129. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_tls.o +0 -0
  130. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_union.o +0 -0
  131. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic/scr_util_compare.o +0 -0
  132. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/dynamic-text-decoder-legacy/scr_bytes.o +0 -0
  133. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/text-decoder-legacy/scr_bytes.o +0 -0
  134. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/text-decoder-legacy-workers/scr_bytes.o +0 -0
  135. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/workers/scr_mailbox.o +0 -0
  136. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/workers/scr_message.o +0 -0
  137. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/workers/scr_worker.o +0 -0
  138. package/dist/lib/runtime-darwin-x64/artifacts/dev/runtime/workers/scr_worker_events.o +0 -0
  139. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_array.o +0 -0
  140. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_assert.o +0 -0
  141. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_bytes.o +0 -0
  142. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_bytes_io.o +0 -0
  143. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_closure.o +0 -0
  144. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_context.o +0 -0
  145. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_copying.o +0 -0
  146. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_cycle.o +0 -0
  147. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_error.o +0 -0
  148. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_events_emitter.o +0 -0
  149. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_exception.o +0 -0
  150. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_json.o +0 -0
  151. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_lib.o +0 -0
  152. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_map.o +0 -0
  153. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_number.o +0 -0
  154. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_object.o +0 -0
  155. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_regex.o +0 -0
  156. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_shared.o +0 -0
  157. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_string.o +0 -0
  158. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/default/scr_union.o +0 -0
  159. package/dist/lib/runtime-darwin-x64/artifacts/library-dev/runtime/text-decoder-legacy/scr_bytes.o +0 -0
  160. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_array.o +0 -0
  161. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_assert.o +0 -0
  162. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_bytes.o +0 -0
  163. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_bytes_io.o +0 -0
  164. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_closure.o +0 -0
  165. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_context.o +0 -0
  166. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_copying.o +0 -0
  167. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_cycle.o +0 -0
  168. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_error.o +0 -0
  169. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_events_emitter.o +0 -0
  170. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_exception.o +0 -0
  171. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_json.o +0 -0
  172. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_lib.o +0 -0
  173. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_map.o +0 -0
  174. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_number.o +0 -0
  175. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_object.o +0 -0
  176. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_regex.o +0 -0
  177. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_shared.o +0 -0
  178. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_string.o +0 -0
  179. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/default/scr_union.o +0 -0
  180. package/dist/lib/runtime-darwin-x64/artifacts/library-release/runtime/text-decoder-legacy/scr_bytes.o +0 -0
  181. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_array.o +0 -0
  182. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_assert.o +0 -0
  183. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_bytes.o +0 -0
  184. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_bytes_io.o +0 -0
  185. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_closure.o +0 -0
  186. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_console.o +0 -0
  187. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_context.o +0 -0
  188. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_copying.o +0 -0
  189. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_cycle.o +0 -0
  190. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_error.o +0 -0
  191. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_events_emitter.o +0 -0
  192. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_exception.o +0 -0
  193. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_inspect.o +0 -0
  194. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_json.o +0 -0
  195. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_lib.o +0 -0
  196. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_map.o +0 -0
  197. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_number.o +0 -0
  198. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_object.o +0 -0
  199. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_regex.o +0 -0
  200. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_shared.o +0 -0
  201. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_string.o +0 -0
  202. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_union.o +0 -0
  203. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/default/scr_zlib.o +0 -0
  204. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-dev/runtime/text-decoder-legacy/scr_bytes.o +0 -0
  205. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_array.o +0 -0
  206. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_assert.o +0 -0
  207. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_bytes.o +0 -0
  208. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_bytes_io.o +0 -0
  209. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_closure.o +0 -0
  210. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_console.o +0 -0
  211. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_context.o +0 -0
  212. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_copying.o +0 -0
  213. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_cycle.o +0 -0
  214. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_error.o +0 -0
  215. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_events_emitter.o +0 -0
  216. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_exception.o +0 -0
  217. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_inspect.o +0 -0
  218. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_json.o +0 -0
  219. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_lib.o +0 -0
  220. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_map.o +0 -0
  221. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_number.o +0 -0
  222. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_object.o +0 -0
  223. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_regex.o +0 -0
  224. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_shared.o +0 -0
  225. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_string.o +0 -0
  226. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_union.o +0 -0
  227. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/default/scr_zlib.o +0 -0
  228. package/dist/lib/runtime-darwin-x64/artifacts/library-thread-release/runtime/text-decoder-legacy/scr_bytes.o +0 -0
  229. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_array.o +0 -0
  230. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_assert.o +0 -0
  231. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_async.o +0 -0
  232. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_bytes.o +0 -0
  233. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_bytes_io.o +0 -0
  234. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_child.o +0 -0
  235. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_closure.o +0 -0
  236. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_console.o +0 -0
  237. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_context.o +0 -0
  238. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_copying.o +0 -0
  239. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_cycle.o +0 -0
  240. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_dgram.o +0 -0
  241. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_error.o +0 -0
  242. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_events.o +0 -0
  243. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_events_emitter.o +0 -0
  244. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_exception.o +0 -0
  245. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_fetch.o +0 -0
  246. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_file_handle.o +0 -0
  247. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_json.o +0 -0
  248. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_lib.o +0 -0
  249. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_map.o +0 -0
  250. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_number.o +0 -0
  251. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_object.o +0 -0
  252. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_readline.o +0 -0
  253. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_regex.o +0 -0
  254. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_shared.o +0 -0
  255. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_stream.o +0 -0
  256. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_string.o +0 -0
  257. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_tls.o +0 -0
  258. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_union.o +0 -0
  259. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default/scr_util_compare.o +0 -0
  260. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_array.o +0 -0
  261. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_assert.o +0 -0
  262. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_async.o +0 -0
  263. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_async_dyn.o +0 -0
  264. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_bigint.o +0 -0
  265. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_bigint_assert.o +0 -0
  266. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_bytes.o +0 -0
  267. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_bytes_io.o +0 -0
  268. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_child.o +0 -0
  269. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_closure.o +0 -0
  270. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_console.o +0 -0
  271. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_console_native.o +0 -0
  272. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_context.o +0 -0
  273. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_copying.o +0 -0
  274. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_crypto_async.o +0 -0
  275. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_cycle.o +0 -0
  276. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_dc.o +0 -0
  277. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_dgram.o +0 -0
  278. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_dyn_handle.o +0 -0
  279. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_dyn_invoke.o +0 -0
  280. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_error.o +0 -0
  281. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_events.o +0 -0
  282. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_events_emitter.o +0 -0
  283. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_exception.o +0 -0
  284. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_fetch.o +0 -0
  285. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_ffi.o +0 -0
  286. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_ffi_queue.o +0 -0
  287. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_file_handle.o +0 -0
  288. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_grapheme.o +0 -0
  289. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_http.o +0 -0
  290. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_http2.o +0 -0
  291. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_inspect.o +0 -0
  292. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_json.o +0 -0
  293. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_lib.o +0 -0
  294. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_loop_epoll.o +0 -0
  295. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_loop_kqueue.o +0 -0
  296. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_loop_wsapoll.o +0 -0
  297. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_map.o +0 -0
  298. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_net.o +0 -0
  299. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_node_builtin.o +0 -0
  300. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_number.o +0 -0
  301. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_object.o +0 -0
  302. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_path.o +0 -0
  303. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_qs.o +0 -0
  304. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_readline.o +0 -0
  305. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_regex.o +0 -0
  306. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_shared.o +0 -0
  307. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_stream.o +0 -0
  308. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_string.o +0 -0
  309. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_symbol.o +0 -0
  310. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_test.o +0 -0
  311. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_tls.o +0 -0
  312. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_tls_ca.o +0 -0
  313. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_union.o +0 -0
  314. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_url.o +0 -0
  315. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_url_params.o +0 -0
  316. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_util.o +0 -0
  317. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_util_compare.o +0 -0
  318. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_util_style.o +0 -0
  319. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_watch.o +0 -0
  320. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/default-workers/scr_zlib.o +0 -0
  321. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_array.o +0 -0
  322. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_assert.o +0 -0
  323. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_async.o +0 -0
  324. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_bytes.o +0 -0
  325. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_bytes_io.o +0 -0
  326. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_child.o +0 -0
  327. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_closure.o +0 -0
  328. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_console.o +0 -0
  329. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_context.o +0 -0
  330. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_copying.o +0 -0
  331. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_cycle.o +0 -0
  332. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_dgram.o +0 -0
  333. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_error.o +0 -0
  334. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_events.o +0 -0
  335. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_events_emitter.o +0 -0
  336. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_exception.o +0 -0
  337. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_file_handle.o +0 -0
  338. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_island.o +0 -0
  339. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_json.o +0 -0
  340. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_lib.o +0 -0
  341. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_map.o +0 -0
  342. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_number.o +0 -0
  343. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_object.o +0 -0
  344. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_readline.o +0 -0
  345. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_regex.o +0 -0
  346. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_shared.o +0 -0
  347. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_stream.o +0 -0
  348. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_string.o +0 -0
  349. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_tls.o +0 -0
  350. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_union.o +0 -0
  351. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic/scr_util_compare.o +0 -0
  352. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/dynamic-text-decoder-legacy/scr_bytes.o +0 -0
  353. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/text-decoder-legacy/scr_bytes.o +0 -0
  354. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/text-decoder-legacy-workers/scr_bytes.o +0 -0
  355. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/workers/scr_mailbox.o +0 -0
  356. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/workers/scr_message.o +0 -0
  357. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/workers/scr_worker.o +0 -0
  358. package/dist/lib/runtime-darwin-x64/artifacts/release/runtime/workers/scr_worker_events.o +0 -0
  359. package/dist/lib/runtime-darwin-x64/package.json +1 -1
  360. package/dist/lib/runtime-darwin-x64/runtime-pack.json +3318 -790
  361. package/dist/lib/runtime-sources/package.json +1 -1
  362. package/dist/lib/runtime-sources/src/scr_array.c +479 -46
  363. package/dist/lib/runtime-sources/src/scr_assert.c +3 -3
  364. package/dist/lib/runtime-sources/src/scr_async.c +401 -71
  365. package/dist/lib/runtime-sources/src/scr_async.test.ts +16 -6
  366. package/dist/lib/runtime-sources/src/scr_async_dyn.c +30 -30
  367. package/dist/lib/runtime-sources/src/scr_bytes.c +487 -221
  368. package/dist/lib/runtime-sources/src/scr_bytes.test.c +85 -0
  369. package/dist/lib/runtime-sources/src/scr_bytes_io.c +45 -64
  370. package/dist/lib/runtime-sources/src/scr_child.c +48 -30
  371. package/dist/lib/runtime-sources/src/scr_closure.c +21 -11
  372. package/dist/lib/runtime-sources/src/scr_console.c +27 -5
  373. package/dist/lib/runtime-sources/src/scr_context.c +167 -0
  374. package/dist/lib/runtime-sources/src/scr_context.test.c +118 -0
  375. package/dist/lib/runtime-sources/src/scr_context.test.ts +47 -0
  376. package/dist/lib/runtime-sources/src/scr_copying.c +13 -2
  377. package/dist/lib/runtime-sources/src/scr_cycle.c +112 -12
  378. package/dist/lib/runtime-sources/src/scr_dc.c +8 -8
  379. package/dist/lib/runtime-sources/src/scr_dgram.c +10 -7
  380. package/dist/lib/runtime-sources/src/scr_error.c +26 -14
  381. package/dist/lib/runtime-sources/src/scr_events.c +45 -31
  382. package/dist/lib/runtime-sources/src/scr_events_emitter.c +34 -1
  383. package/dist/lib/runtime-sources/src/scr_exception.c +26 -7
  384. package/dist/lib/runtime-sources/src/scr_fetch.c +23 -20
  385. package/dist/lib/runtime-sources/src/scr_fetch_curl.c +1 -1
  386. package/dist/lib/runtime-sources/src/scr_ffi.c +3 -3
  387. package/dist/lib/runtime-sources/src/scr_file_handle.c +1 -0
  388. package/dist/lib/runtime-sources/src/scr_http.c +20 -16
  389. package/dist/lib/runtime-sources/src/scr_http2.c +10 -8
  390. package/dist/lib/runtime-sources/src/scr_inspect.c +1 -0
  391. package/dist/lib/runtime-sources/src/scr_island.c +1 -1
  392. package/dist/lib/runtime-sources/src/scr_json.c +652 -189
  393. package/dist/lib/runtime-sources/src/scr_json.test.c +339 -1
  394. package/dist/lib/runtime-sources/src/scr_json.test.ts +59 -25
  395. package/dist/lib/runtime-sources/src/scr_key.h +92 -0
  396. package/dist/lib/runtime-sources/src/scr_lib.c +256 -136
  397. package/dist/lib/runtime-sources/src/scr_mailbox.c +233 -0
  398. package/dist/lib/runtime-sources/src/scr_mailbox.h +28 -0
  399. package/dist/lib/runtime-sources/src/scr_mailbox.test.c +86 -0
  400. package/dist/lib/runtime-sources/src/scr_mailbox.test.ts +46 -0
  401. package/dist/lib/runtime-sources/src/scr_map.c +240 -107
  402. package/dist/lib/runtime-sources/src/scr_message.c +443 -0
  403. package/dist/lib/runtime-sources/src/scr_message.h +14 -0
  404. package/dist/lib/runtime-sources/src/scr_message.test.c +152 -0
  405. package/dist/lib/runtime-sources/src/scr_message.test.ts +44 -0
  406. package/dist/lib/runtime-sources/src/scr_net.c +14 -12
  407. package/dist/lib/runtime-sources/src/scr_number.c +36 -4
  408. package/dist/lib/runtime-sources/src/scr_numeric.h +25 -0
  409. package/dist/lib/runtime-sources/src/scr_numeric.test.c +37 -0
  410. package/dist/lib/runtime-sources/src/scr_numeric.test.ts +33 -0
  411. package/dist/lib/runtime-sources/src/scr_object.c +9 -4
  412. package/dist/lib/runtime-sources/src/scr_path.c +1 -1
  413. package/dist/lib/runtime-sources/src/scr_readline.c +8 -8
  414. package/dist/lib/runtime-sources/src/scr_regex.c +351 -167
  415. package/dist/lib/runtime-sources/src/scr_runtime.h +207 -34
  416. package/dist/lib/runtime-sources/src/scr_shared.c +280 -0
  417. package/dist/lib/runtime-sources/src/scr_shared.test.c +113 -0
  418. package/dist/lib/runtime-sources/src/scr_shared.test.ts +45 -0
  419. package/dist/lib/runtime-sources/src/scr_stream.c +9 -9
  420. package/dist/lib/runtime-sources/src/scr_string.c +365 -141
  421. package/dist/lib/runtime-sources/src/scr_test.c +8 -8
  422. package/dist/lib/runtime-sources/src/scr_tls.c +12 -12
  423. package/dist/lib/runtime-sources/src/scr_tls_ca.c +34 -12
  424. package/dist/lib/runtime-sources/src/scr_union.c +10 -5
  425. package/dist/lib/runtime-sources/src/scr_util_compare.c +1 -0
  426. package/dist/lib/runtime-sources/src/scr_util_style.c +11 -11
  427. package/dist/lib/runtime-sources/src/scr_watch.c +16 -6
  428. package/dist/lib/runtime-sources/src/scr_worker.c +232 -0
  429. package/dist/lib/runtime-sources/src/scr_worker.h +42 -0
  430. package/dist/lib/runtime-sources/src/scr_worker.test.c +115 -0
  431. package/dist/lib/runtime-sources/src/scr_worker.test.ts +49 -0
  432. package/dist/lib/runtime-sources/src/scr_worker_events.c +443 -0
  433. package/dist/lib/runtime-sources/src/scr_zlib.c +6 -0
  434. package/package.json +1 -1
@@ -22,6 +22,7 @@
22
22
  * serializers (and the error messages here).
23
23
  */
24
24
  #include "scr_runtime.h"
25
+ #include "scr_key.h"
25
26
 
26
27
  static SCR_TL ScrDyn *scr_builtin_object_prototype;
27
28
 
@@ -159,7 +160,9 @@ void scr_jb_init(ScrJsonBuf *b) {
159
160
  }
160
161
 
161
162
  static void scr_jb_grow(ScrJsonBuf *b, size_t need) {
162
- if (b->len + need <= b->cap) return;
163
+ if (need > SIZE_MAX - sizeof(ScrStr) - 1 - b->len) scr_json_oom();
164
+ size_t required = b->len + need;
165
+ if (required <= b->cap) return;
163
166
  if (!b->data) { /* first allocation: len == 0 */
164
167
  size_t cap = scr_jb_hint >= need ? scr_jb_hint : need;
165
168
  ScrStr *s = scr_str_alloc_raw(0, cap);
@@ -168,7 +171,13 @@ static void scr_jb_grow(ScrJsonBuf *b, size_t need) {
168
171
  return;
169
172
  }
170
173
  size_t cap = b->cap;
171
- while (cap < b->len + need) cap *= 2;
174
+ while (cap < required) {
175
+ if (cap > (SIZE_MAX - sizeof(ScrStr) - 1) / 2) {
176
+ cap = required;
177
+ break;
178
+ }
179
+ cap *= 2;
180
+ }
172
181
  ScrStr *s = scr_str_regrow(SCR_JB_STR(b), cap);
173
182
  b->data = s->data;
174
183
  b->cap = cap;
@@ -186,7 +195,8 @@ void scr_jb_putc(ScrJsonBuf *b, char c) {
186
195
  b->data[b->len++] = c;
187
196
  }
188
197
 
189
- static void scr_jb_write(ScrJsonBuf *b, const char *s, size_t n) {
198
+ void scr_jb_write(ScrJsonBuf *b, const char *s, size_t n) {
199
+ if (n == 0) return;
190
200
  scr_jb_grow(b, n);
191
201
  memcpy(b->data + b->len, s, n);
192
202
  b->len += n;
@@ -198,6 +208,12 @@ void scr_jb_put_str(ScrJsonBuf *b, const ScrStr *s) {
198
208
 
199
209
  void scr_jb_puts(ScrJsonBuf *b, const char *s) { scr_jb_write(b, s, strlen(s)); }
200
210
 
211
+ void scr_jb_put_number(ScrJsonBuf *b, double v) {
212
+ char buf[32];
213
+ size_t n = scr_f64_to_str(v, buf);
214
+ scr_jb_write(b, buf, n);
215
+ }
216
+
201
217
  void scr_jb_put_f64(ScrJsonBuf *b, double v) {
202
218
  /* JSON.stringify number rules: non-finite → null, -0 → "0" (String(-0)
203
219
  * is "0" too, so scr_f64_to_str would agree — the zero test just makes
@@ -210,42 +226,82 @@ void scr_jb_put_f64(ScrJsonBuf *b, double v) {
210
226
  scr_jb_putc(b, '0');
211
227
  return;
212
228
  }
213
- char buf[32];
214
- size_t n = scr_f64_to_str(v, buf);
215
- scr_jb_write(b, buf, n);
216
- }
217
-
218
- void scr_jb_put_json_str(ScrJsonBuf *b, const ScrStr *s) {
219
- scr_jb_putc(b, '"');
220
- /* Bulk-copy runs of unescaped bytes (UTF-8 passes through verbatim,
221
- * like JS); escapes interrupt the run. */
222
- size_t i = 0, run = 0;
223
- while (i + run < s->len) {
224
- unsigned char c = (unsigned char)s->data[i + run];
225
- if (c != '"' && c != '\\' && c >= 0x20) {
226
- run++;
227
- continue;
228
- }
229
- scr_jb_write(b, s->data + i, run);
229
+ scr_jb_put_number(b, v);
230
+ }
231
+
232
+ /* Find the next quote, backslash or control byte. memcpy keeps the word
233
+ * loads unaligned-safe, and the length guard never reads past the input.
234
+ * The masks only decide whether to inspect a word byte by byte: borrow
235
+ * propagation may mark extra lanes, so it must not determine a byte index.
236
+ * High UTF-8 bytes are ordinary data, independent of host byte order. */
237
+ static size_t scr_json_plain_bytes(const char *data, size_t len) {
238
+ const uint64_t ones = UINT64_C(0x0101010101010101);
239
+ const uint64_t high = UINT64_C(0x8080808080808080);
240
+ size_t i = 0;
241
+ while (len - i >= sizeof(uint64_t)) {
242
+ uint64_t word;
243
+ memcpy(&word, data + i, sizeof word);
244
+ uint64_t quotes = word ^ (ones * '"');
245
+ uint64_t slashes = word ^ (ones * '\\');
246
+ uint64_t special = ((quotes - ones) & ~quotes) |
247
+ ((slashes - ones) & ~slashes) |
248
+ ((word - ones * 0x20) & ~word);
249
+ if (special & high) break;
250
+ i += sizeof word;
251
+ }
252
+ while (i < len) {
253
+ unsigned char c = (unsigned char)data[i];
254
+ if (c < 0x20 || c == '"' || c == '\\') break;
255
+ i++;
256
+ }
257
+ return i;
258
+ }
259
+
260
+ static void scr_jb_put_json_span(ScrJsonBuf *b, const char *data, size_t len) {
261
+ if (len > SIZE_MAX - 2) scr_json_oom();
262
+ size_t run = scr_json_plain_bytes(data, len);
263
+ /* The overwhelmingly common unescaped string needs one capacity check,
264
+ * including both quotes, and no per-byte builder calls. */
265
+ scr_jb_grow(b, run + 2);
266
+ b->data[b->len++] = '"';
267
+ if (run) memcpy(b->data + b->len, data, run);
268
+ b->len += run;
269
+ size_t i = run;
270
+ while (i < len) {
271
+ unsigned char c = (unsigned char)data[i++];
272
+ char escaped[6] = {'\\', 0, '0', '0', 0, 0};
273
+ size_t count = 2;
230
274
  switch (c) {
231
- case '"': scr_jb_puts(b, "\\\""); break;
232
- case '\\': scr_jb_puts(b, "\\\\"); break;
233
- case '\n': scr_jb_puts(b, "\\n"); break;
234
- case '\r': scr_jb_puts(b, "\\r"); break;
235
- case '\t': scr_jb_puts(b, "\\t"); break;
236
- case '\b': scr_jb_puts(b, "\\b"); break;
237
- case '\f': scr_jb_puts(b, "\\f"); break;
275
+ case '"': escaped[1] = '"'; break;
276
+ case '\\': escaped[1] = '\\'; break;
277
+ case '\n': escaped[1] = 'n'; break;
278
+ case '\r': escaped[1] = 'r'; break;
279
+ case '\t': escaped[1] = 't'; break;
280
+ case '\b': escaped[1] = 'b'; break;
281
+ case '\f': escaped[1] = 'f'; break;
238
282
  default: {
239
- char esc[8];
240
- snprintf(esc, sizeof esc, "\\u%04x", c);
241
- scr_jb_puts(b, esc);
242
- }
243
- }
244
- i += run + 1;
245
- run = 0;
283
+ static const char hex[] = "0123456789abcdef";
284
+ escaped[1] = 'u';
285
+ escaped[4] = hex[c >> 4];
286
+ escaped[5] = hex[c & 15];
287
+ count = 6;
288
+ }
289
+ }
290
+ run = scr_json_plain_bytes(data + i, len - i);
291
+ if (run > SIZE_MAX - count) scr_json_oom();
292
+ scr_jb_grow(b, count + run);
293
+ memcpy(b->data + b->len, escaped, count);
294
+ b->len += count;
295
+ if (run) memcpy(b->data + b->len, data + i, run);
296
+ b->len += run;
297
+ i += run;
246
298
  }
247
- scr_jb_write(b, s->data + i, run);
248
- scr_jb_putc(b, '"');
299
+ scr_jb_grow(b, 1);
300
+ b->data[b->len++] = '"';
301
+ }
302
+
303
+ void scr_jb_put_json_str(ScrJsonBuf *b, const ScrStr *s) {
304
+ scr_jb_put_json_span(b, s->data, s->len);
249
305
  }
250
306
 
251
307
  ScrStr *scr_jb_finish(ScrJsonBuf *b) {
@@ -264,6 +320,81 @@ ScrStr *scr_jb_finish(ScrJsonBuf *b) {
264
320
  return s;
265
321
  }
266
322
 
323
+ /* Write newline and a repeated gap with one reservation. Copies never
324
+ * overlap: each doubling reads only the already initialized prefix. */
325
+ static void scr_jb_indent(ScrJsonBuf *b, const char *gap, size_t gap_len, size_t depth) {
326
+ if (gap_len && depth > (SIZE_MAX - 1) / gap_len) scr_json_oom();
327
+ size_t count = gap_len * depth;
328
+ scr_jb_grow(b, count + 1);
329
+ b->data[b->len++] = '\n';
330
+ if (!count) return;
331
+ memcpy(b->data + b->len, gap, gap_len);
332
+ size_t filled = gap_len;
333
+ while (filled < count) {
334
+ size_t take = filled < count - filled ? filled : count - filled;
335
+ memcpy(b->data + b->len + filled, b->data + b->len, take);
336
+ filled += take;
337
+ }
338
+ b->len += count;
339
+ }
340
+
341
+ ScrStr *scr_json_indent(const ScrStr *compact, const char *gap, size_t gap_len) {
342
+ if (!gap_len) return scr_str_retain((ScrStr *)compact);
343
+ /* Node stops copying the gap at its first NUL but still inserts breaks
344
+ * and colon spaces when the original gap is nonempty. */
345
+ const char *end = memchr(gap, 0, gap_len);
346
+ if (end) gap_len = (size_t)(end - gap);
347
+ ScrJsonBuf b;
348
+ scr_jb_init(&b);
349
+ size_t depth = 0, start = 0, i = 0;
350
+ while (i < compact->len) {
351
+ char c = compact->data[i];
352
+ if (c == '"') {
353
+ /* Quoted punctuation is data. Scan ordinary runs and skip the byte
354
+ * after each backslash so an escaped quote cannot end this string. */
355
+ i++;
356
+ while (i < compact->len) {
357
+ i += scr_json_plain_bytes(compact->data + i, compact->len - i);
358
+ if (i == compact->len) break;
359
+ if (compact->data[i] == '\\') {
360
+ i += compact->len - i >= 2 ? 2 : 1;
361
+ } else {
362
+ i++;
363
+ break;
364
+ }
365
+ }
366
+ continue;
367
+ }
368
+ if (c == '{' || c == '[') {
369
+ char closer = c == '{' ? '}' : ']';
370
+ if (i + 1 < compact->len && compact->data[i + 1] == closer) {
371
+ i += 2;
372
+ continue;
373
+ }
374
+ scr_jb_write(&b, compact->data + start, i + 1 - start);
375
+ scr_jb_indent(&b, gap, gap_len, ++depth);
376
+ start = ++i;
377
+ continue;
378
+ }
379
+ if (c == '}' || c == ']') {
380
+ scr_jb_write(&b, compact->data + start, i - start);
381
+ scr_jb_indent(&b, gap, gap_len, --depth);
382
+ start = i++;
383
+ continue;
384
+ }
385
+ if (c == ',' || c == ':') {
386
+ scr_jb_write(&b, compact->data + start, i + 1 - start);
387
+ if (c == ',') scr_jb_indent(&b, gap, gap_len, depth);
388
+ else scr_jb_putc(&b, ' ');
389
+ start = ++i;
390
+ continue;
391
+ }
392
+ i++;
393
+ }
394
+ scr_jb_write(&b, compact->data + start, compact->len - start);
395
+ return scr_jb_finish(&b);
396
+ }
397
+
267
398
  /* ── circular-structure detection ──────────────────────────────────────
268
399
  * RECURSIVE record types permit runtime reference cycles; JSON.stringify
269
400
  * of a cyclic value throws V8's exact TypeError. The compiler-emitted
@@ -413,11 +544,110 @@ void scr_dyn_from_leave(void) {
413
544
  * strict alloc/free balance.
414
545
  */
415
546
  static SCR_TL ScrDyn *scr_builtin_array_prototype;
547
+
548
+ /* Property names are immutable and often repeated across simultaneously live
549
+ * objects. Entries own references to their bytes; this fixed weak table owns
550
+ * none. Collisions only reduce sharing, and the final release removes a weak
551
+ * entry before freeing storage. Long keys bypass lookup entirely. */
552
+ #define SCR_DYN_KEY_SHARE_SLOTS 256
553
+ #define SCR_DYN_KEY_SHARE_LENGTH 64
554
+ typedef struct {
555
+ size_t rc;
556
+ char bytes[];
557
+ } ScrDynKey;
558
+ typedef struct {
559
+ ScrDynKey *key;
560
+ size_t length;
561
+ } ScrDynKeySlot;
562
+ static SCR_TL ScrDynKeySlot scr_dyn_keys[SCR_DYN_KEY_SHARE_SLOTS];
563
+ #ifdef SCR_RC_AUDIT
564
+ static SCR_TL long scr_live_dyn_keys;
565
+ long scr_dyn_key_live_count(void) { return scr_live_dyn_keys; }
566
+ #endif
567
+
568
+ static size_t scr_dyn_key_slot(const char *key, size_t length) {
569
+ size_t hash = length;
570
+ for (size_t i = 0; i < length; i++) hash = hash * 31 + (unsigned char)key[i];
571
+ return hash % SCR_DYN_KEY_SHARE_SLOTS;
572
+ }
573
+
574
+ static char *scr_dyn_key_copy(const char *key, size_t length) {
575
+ ScrDynKeySlot *slot = length <= SCR_DYN_KEY_SHARE_LENGTH
576
+ ? &scr_dyn_keys[scr_dyn_key_slot(key, length)] : NULL;
577
+ if (slot && slot->key && slot->length == length &&
578
+ !memcmp(slot->key->bytes, key, length)) {
579
+ slot->key->rc++;
580
+ return slot->key->bytes;
581
+ }
582
+ if (length > SIZE_MAX - sizeof(ScrDynKey) - 1) scr_json_oom();
583
+ ScrDynKey *owned = malloc(sizeof *owned + length + 1);
584
+ if (!owned) scr_json_oom();
585
+ #ifdef SCR_RC_AUDIT
586
+ scr_live_dyn_keys++;
587
+ #endif
588
+ owned->rc = 1;
589
+ memcpy(owned->bytes, key, length);
590
+ owned->bytes[length] = '\0';
591
+ if (slot) *slot = (ScrDynKeySlot){owned, length};
592
+ return owned->bytes;
593
+ }
594
+
595
+ static void scr_dyn_key_release(char *key, size_t length) {
596
+ if (!key) return;
597
+ ScrDynKey *owned = (ScrDynKey *)(key - offsetof(ScrDynKey, bytes));
598
+ if (--owned->rc) return;
599
+ if (length <= SCR_DYN_KEY_SHARE_LENGTH) {
600
+ ScrDynKeySlot *slot = &scr_dyn_keys[scr_dyn_key_slot(key, length)];
601
+ if (slot->key == owned) slot->key = NULL;
602
+ }
603
+ #ifdef SCR_RC_AUDIT
604
+ scr_live_dyn_keys--;
605
+ #endif
606
+ free(owned);
607
+ }
608
+
416
609
  #ifndef SCR_RC_AUDIT
417
610
  static SCR_TL ScrDyn *scr_dyn_free_arr, *scr_dyn_free_obj, *scr_dyn_free_misc;
418
611
  static SCR_TL size_t scr_dyn_free_count;
419
612
  #define SCR_DYN_FREE_MAX 8192
613
+ /* Recycled small objects may retain key bytes, but never values or an
614
+ * unbounded document's keys. This budget applies across the whole pool. */
615
+ static SCR_TL size_t scr_dyn_cached_key_bytes;
616
+ #define SCR_DYN_KEY_CACHE_MAX ((size_t)64 * 1024)
617
+ #define SCR_DYN_KEY_CACHE_SLOTS 16
618
+ #define SCR_DYN_KEY_CACHE_LENGTH 64
619
+ #endif
620
+
621
+ static void scr_dyn_obj_drop_keys(ScrDyn *d, bool cache) {
622
+ for (size_t i = 0; i < d->v.obj.cap; i++) {
623
+ ScrDynEntry *entry = &d->v.obj.entries[i];
624
+ if (!entry->key) continue;
625
+ #ifndef SCR_RC_AUDIT
626
+ if (cache && d->v.obj.cap <= SCR_DYN_KEY_CACHE_SLOTS &&
627
+ entry->key_len <= SCR_DYN_KEY_CACHE_LENGTH &&
628
+ sizeof(ScrDynKey) + entry->key_len + 1 <= SCR_DYN_KEY_CACHE_MAX - scr_dyn_cached_key_bytes) {
629
+ scr_dyn_cached_key_bytes += sizeof(ScrDynKey) + entry->key_len + 1;
630
+ continue;
631
+ }
632
+ #else
633
+ (void)cache;
420
634
  #endif
635
+ scr_dyn_key_release(entry->key, entry->key_len);
636
+ entry->key = NULL;
637
+ entry->key_len = 0;
638
+ }
639
+ }
640
+
641
+ /* Primitive kinds cannot acquire properties or change kind while live, so
642
+ * an object property edge to one cannot participate in a cycle. Keep its RC edge
643
+ * out of trial deletion and release it in collected teardown instead. Other
644
+ * owners may still trace the same primitive through the uniform header ABI;
645
+ * our untraced reference keeps it alive until that teardown releases it.
646
+ * Entry metadata snapshots this decision during trace, before any white node
647
+ * can be freed. Teardown must never inspect the child's kind again. */
648
+ static bool scr_dyn_member_is_traced(const ScrDyn *value) {
649
+ return value && value->kind > SCR_DYN_STR && value->kind != SCR_DYN_UNDEF;
650
+ }
421
651
 
422
652
  /* Checked objects and functions can close over one another. All heap dyn
423
653
  * nodes carry a collector header so a captured unknown value has one uniform
@@ -425,19 +655,21 @@ static SCR_TL size_t scr_dyn_free_count;
425
655
  * capsules keep their conservative ownership edges. */
426
656
  void scr_dyn_trace_v(void *ptr, ScrTraceVisit visit, void *ctx) {
427
657
  ScrDyn *d = ptr;
428
- visit(d->prototype, ctx);
429
- visit(d->symbol_properties, ctx);
430
- visit(d->symbol_keys, ctx);
658
+ if (d->prototype) visit(d->prototype, ctx);
659
+ if (d->symbol_properties) visit(d->symbol_properties, ctx);
660
+ if (d->symbol_keys) visit(d->symbol_keys, ctx);
431
661
  switch (d->kind) {
432
662
  case SCR_DYN_ARR:
433
663
  for (size_t i = 0; i < d->v.arr.len; i++) visit(d->v.arr.items[i], ctx);
434
- visit(d->v.arr.properties, ctx);
664
+ if (d->v.arr.properties) visit(d->v.arr.properties, ctx);
435
665
  break;
436
666
  case SCR_DYN_OBJ:
437
667
  for (size_t i = 0; i < d->v.obj.len; i++) {
438
- visit(d->v.obj.entries[i].value, ctx);
439
- visit(d->v.obj.entries[i].getter, ctx);
440
- visit(d->v.obj.entries[i].setter, ctx);
668
+ ScrDynEntry *entry = &d->v.obj.entries[i];
669
+ entry->value_traced = scr_dyn_member_is_traced(entry->value);
670
+ if (entry->value_traced) visit(entry->value, ctx);
671
+ if (entry->getter) visit(entry->getter, ctx);
672
+ if (entry->setter) visit(entry->setter, ctx);
441
673
  }
442
674
  break;
443
675
  case SCR_DYN_FUNC: visit(d->v.fn.clo, ctx); break;
@@ -539,6 +771,12 @@ static ScrDyn *scr_dyn_alloc(ScrDynKind kind) {
539
771
  d->v.arr.presence = NULL;
540
772
  } else if (kind == SCR_DYN_OBJ) {
541
773
  d->v.obj.len = 0; /* cap/entries preserved */
774
+ if (d->v.obj.cap <= SCR_DYN_KEY_CACHE_SLOTS) {
775
+ for (size_t i = 0; i < d->v.obj.cap; i++) {
776
+ ScrDynEntry *entry = &d->v.obj.entries[i];
777
+ if (entry->key) scr_dyn_cached_key_bytes -= sizeof(ScrDynKey) + entry->key_len + 1;
778
+ }
779
+ }
542
780
  d->v.obj.source_identity = NULL;
543
781
  d->v.obj.source_access = NULL;
544
782
  } else {
@@ -565,6 +803,10 @@ static void scr_dyn_handle_release(void *h, ScrDynHandleTag tag);
565
803
  static bool scr_dyn_to_primitive_result_is_object(const ScrDyn *d);
566
804
 
567
805
  static void scr_dyn_dispose(ScrDyn *d, bool collected) {
806
+ if (d->kind == SCR_DYN_OBJ) {
807
+ free(d->v.obj.index);
808
+ d->v.obj.index = NULL;
809
+ }
568
810
  if (!collected) scr_dyn_release(d->prototype);
569
811
  if (!collected) scr_dyn_release(d->symbol_properties);
570
812
  if (!collected) scr_dyn_release(d->symbol_keys);
@@ -592,12 +834,15 @@ static void scr_dyn_dispose(ScrDyn *d, bool collected) {
592
834
  break;
593
835
  case SCR_DYN_OBJ:
594
836
  for (size_t i = 0; i < d->v.obj.len; i++) {
595
- free(d->v.obj.entries[i].key);
837
+ ScrDyn *value = d->v.obj.entries[i].value;
838
+ if (!collected || !d->v.obj.entries[i].value_traced) scr_dyn_release(value);
596
839
  if (!collected) {
597
- scr_dyn_release(d->v.obj.entries[i].value);
598
840
  scr_dyn_release(d->v.obj.entries[i].getter);
599
841
  scr_dyn_release(d->v.obj.entries[i].setter);
600
842
  }
843
+ d->v.obj.entries[i].value = NULL;
844
+ d->v.obj.entries[i].getter = NULL;
845
+ d->v.obj.entries[i].setter = NULL;
601
846
  }
602
847
  if (d->v.obj.source_identity) {
603
848
  d->v.obj.source_access(d->v.obj.source_identity, false);
@@ -646,6 +891,7 @@ static void scr_dyn_dispose(ScrDyn *d, bool collected) {
646
891
  #endif
647
892
  #ifndef SCR_RC_AUDIT
648
893
  if (!collected && scr_dyn_free_count < SCR_DYN_FREE_MAX) {
894
+ if (d->kind == SCR_DYN_OBJ) scr_dyn_obj_drop_keys(d, true);
649
895
  /* Pooled blocks retain their headers and count toward the bounded
650
896
  * allocated heap, but never remain in a candidate buffer. */
651
897
  scr_weak_dispose(d);
@@ -659,12 +905,17 @@ static void scr_dyn_dispose(ScrDyn *d, bool collected) {
659
905
  }
660
906
  #endif
661
907
  if (d->kind == SCR_DYN_ARR) free(d->v.arr.items);
662
- else if (d->kind == SCR_DYN_OBJ) free(d->v.obj.entries);
908
+ else if (d->kind == SCR_DYN_OBJ) {
909
+ scr_dyn_obj_drop_keys(d, false);
910
+ free(d->v.obj.entries);
911
+ }
663
912
  scr_cyc_free(d);
664
913
  }
665
914
 
666
915
  static void scr_dyn_gcfree(void *ptr) { scr_dyn_dispose(ptr, true); }
667
916
 
917
+ static void scr_dyn_destroy(void *ptr) { scr_dyn_dispose(ptr, false); }
918
+
668
919
  void scr_dyn_release(ScrDyn *d) {
669
920
  if (!d || d->rc == SIZE_MAX) return;
670
921
  if (--d->rc != 0) {
@@ -675,7 +926,84 @@ void scr_dyn_release(ScrDyn *d) {
675
926
  return;
676
927
  }
677
928
  scr_cyc_on_dead(d);
678
- scr_dyn_dispose(d, false);
929
+ scr_rc_destroy(d, scr_dyn_destroy);
930
+ }
931
+
932
+ /* Small objects retain their compact linear representation. A wide object
933
+ * owns a bucket index of entry positions; entries remain insertion ordered.
934
+ * No key/value ownership lives here, and callbacks never retain its slots. */
935
+ #define SCR_DYN_OBJECT_INDEX_MIN 32
936
+ typedef struct ScrDynObjectIndex {
937
+ size_t buckets;
938
+ size_t slots[]; /* zero is empty; occupied slots store entry + 1 */
939
+ } ScrDynObjectIndex;
940
+
941
+ static void scr_dyn_index_insert(ScrDynObjectIndex *index, const ScrDynEntry *entry, size_t position) {
942
+ size_t slot = scr_key_hash(entry->key, entry->key_len) & (index->buckets - 1);
943
+ while (index->slots[slot]) slot = (slot + 1) & (index->buckets - 1);
944
+ index->slots[slot] = position + 1;
945
+ }
946
+
947
+ /* Keep index allocation/probing outside compact object insertion and reads. */
948
+ static __attribute__((noinline)) void scr_dyn_index_append(ScrDyn *object) {
949
+ size_t count = object->v.obj.len;
950
+ ScrDynObjectIndex *index = object->v.obj.index;
951
+ if (!index || count > index->buckets / 2) {
952
+ size_t buckets = index ? index->buckets : 64;
953
+ while (count > buckets / 2) {
954
+ if (buckets > (SIZE_MAX - sizeof *index) / sizeof(size_t) / 2) scr_json_oom();
955
+ buckets *= 2;
956
+ }
957
+ free(index);
958
+ index = calloc(1, sizeof *index + buckets * sizeof(size_t));
959
+ if (!index) scr_json_oom();
960
+ index->buckets = buckets;
961
+ object->v.obj.index = index;
962
+ for (size_t i = 0; i < count; i++) scr_dyn_index_insert(index, &object->v.obj.entries[i], i);
963
+ } else {
964
+ scr_dyn_index_insert(index, &object->v.obj.entries[count - 1], count - 1);
965
+ }
966
+ }
967
+
968
+ /* A checked hint avoids repeating a linear walk for recurring property
969
+ * names. Slots store indices only, never object/key pointers. Every hit
970
+ * checks the current entry, so different shapes, deletion and reordering
971
+ * need no invalidation and collisions fall back to the ordinary search. */
972
+ #define SCR_DYN_PROPERTY_HINTS 64
973
+ static SCR_TL size_t scr_dyn_property_hints[SCR_DYN_PROPERTY_HINTS];
974
+
975
+ static ScrDynEntry *scr_dyn_find_linear_entry(const ScrDyn *object, const char *key, size_t length) {
976
+ for (size_t i = 0; i < object->v.obj.len; i++) {
977
+ ScrDynEntry *entry = &object->v.obj.entries[i];
978
+ if (entry->key_len == length && scr_key_equal(entry->key, key, length)) return entry;
979
+ }
980
+ return NULL;
981
+ }
982
+
983
+ static __attribute__((noinline)) ScrDynEntry *scr_dyn_find_indexed_entry(
984
+ const ScrDyn *object, const char *key, size_t length) {
985
+ const ScrDynObjectIndex *index = object->v.obj.index;
986
+ size_t slot = scr_key_hash(key, length) & (index->buckets - 1);
987
+ while (index->slots[slot]) {
988
+ ScrDynEntry *entry = &object->v.obj.entries[index->slots[slot] - 1];
989
+ if (entry->key_len == length && scr_key_equal(entry->key, key, length)) return entry;
990
+ slot = (slot + 1) & (index->buckets - 1);
991
+ }
992
+ return NULL;
993
+ }
994
+
995
+ static ScrDynEntry *scr_dyn_find_entry(const ScrDyn *object, const char *key, size_t length) {
996
+ if (object->kind != SCR_DYN_OBJ) return NULL;
997
+ if (object->v.obj.index) return scr_dyn_find_indexed_entry(object, key, length);
998
+ size_t slot = (length + (length ? (unsigned char)key[0] * 7u : 0)) % SCR_DYN_PROPERTY_HINTS;
999
+ size_t hint = scr_dyn_property_hints[slot];
1000
+ if (hint < object->v.obj.len) {
1001
+ ScrDynEntry *entry = &object->v.obj.entries[hint];
1002
+ if (entry->key_len == length && scr_key_equal(entry->key, key, length)) return entry;
1003
+ }
1004
+ ScrDynEntry *entry = scr_dyn_find_linear_entry(object, key, length);
1005
+ if (entry) scr_dyn_property_hints[slot] = (size_t)(entry - object->v.obj.entries);
1006
+ return entry;
679
1007
  }
680
1008
 
681
1009
  ScrDyn *scr_dyn_obj_get(const ScrDyn *d, const char *key, size_t key_len) {
@@ -683,20 +1011,13 @@ ScrDyn *scr_dyn_obj_get(const ScrDyn *d, const char *key, size_t key_len) {
683
1011
  scr_dyn_proxy_unsupported("raw object inspection");
684
1012
  return NULL;
685
1013
  }
686
- if (d->kind != SCR_DYN_OBJ) return NULL;
687
- for (size_t i = 0; i < d->v.obj.len; i++) {
688
- const ScrDynEntry *e = &d->v.obj.entries[i];
689
- if (e->key_len == key_len && memcmp(e->key, key, key_len) == 0) return e->value;
690
- }
691
- return NULL;
1014
+ ScrDynEntry *entry = scr_dyn_find_entry(d, key, key_len);
1015
+ return entry ? entry->value : NULL;
692
1016
  }
693
1017
 
694
1018
  bool scr_dyn_obj_enumerable(const ScrDyn *d, const char *key, size_t key_len) {
695
- for (size_t i = 0; i < d->v.obj.len; i++) {
696
- const ScrDynEntry *e = &d->v.obj.entries[i];
697
- if (e->key_len == key_len && memcmp(e->key, key, key_len) == 0) return e->enumerable;
698
- }
699
- return false;
1019
+ ScrDynEntry *entry = scr_dyn_find_entry(d, key, key_len);
1020
+ return entry && entry->enumerable;
700
1021
  }
701
1022
 
702
1023
  static const ScrDyn *scr_dyn_property_owner(const ScrDyn *object, const char *key, size_t length);
@@ -983,29 +1304,27 @@ ScrDyn *scr_dyn_arr_named_get(const ScrDyn *d, const ScrStr *key) {
983
1304
  return value;
984
1305
  }
985
1306
 
986
- /* Takes ownership of key (malloc'd) and value. Duplicate keys: the LATER
987
- * value wins (like JS JSON.parse) — the old value is released and the new
988
- * key buffer freed (the surviving entry keeps its original, equal key). */
989
- static void scr_dyn_obj_put(ScrDyn *obj, char *key, size_t key_len, ScrDyn *value) {
990
- for (size_t i = 0; i < obj->v.obj.len; i++) {
991
- ScrDynEntry *e = &obj->v.obj.entries[i];
992
- if (e->key_len == key_len && memcmp(e->key, key, key_len) == 0) {
993
- if (e->accessor || !e->writable) {
994
- free(key);
995
- scr_dyn_release(value);
996
- static const char message[] = "Cannot assign to read only property";
997
- scr_throw_error_msg(SCR_ERR_TYPE, message, sizeof message - 1);
998
- return;
999
- }
1000
- ScrDyn *old = e->value;
1001
- e->value = value;
1002
- scr_dyn_release(old);
1003
- free(key);
1307
+ /* Borrows key and takes ownership of value. Duplicate keys retain their
1308
+ * original spelling/storage and insertion position; the later value wins.
1309
+ * A recycled entry can reuse equal key bytes without a malloc/free pair. */
1310
+ static void scr_dyn_obj_put(ScrDyn *obj, const char *key, size_t key_len, ScrDyn *value) {
1311
+ /* Construction usually appends an absent name. Avoid a read hint that
1312
+ * repeats comparisons on compact objects; wide objects use their index. */
1313
+ ScrDynEntry *existing = obj->v.obj.index ? scr_dyn_find_entry(obj, key, key_len)
1314
+ : scr_dyn_find_linear_entry(obj, key, key_len);
1315
+ if (existing) {
1316
+ if (existing->accessor || !existing->writable) {
1317
+ scr_dyn_release(value);
1318
+ static const char message[] = "Cannot assign to read only property";
1319
+ scr_throw_error_msg(SCR_ERR_TYPE, message, sizeof message - 1);
1004
1320
  return;
1005
1321
  }
1322
+ ScrDyn *old = existing->value;
1323
+ existing->value = value;
1324
+ scr_dyn_release(old);
1325
+ return;
1006
1326
  }
1007
1327
  if (obj->non_extensible) {
1008
- free(key);
1009
1328
  scr_dyn_release(value);
1010
1329
  static const char message[] = "Cannot add property, object is not extensible";
1011
1330
  scr_throw_error_msg(SCR_ERR_TYPE, message, sizeof message - 1);
@@ -1015,11 +1334,16 @@ static void scr_dyn_obj_put(ScrDyn *obj, char *key, size_t key_len, ScrDyn *valu
1015
1334
  size_t cap = obj->v.obj.cap ? obj->v.obj.cap * 2 : 4;
1016
1335
  ScrDynEntry *entries = realloc(obj->v.obj.entries, cap * sizeof *entries);
1017
1336
  if (!entries) scr_json_oom();
1337
+ memset(entries + obj->v.obj.cap, 0, (cap - obj->v.obj.cap) * sizeof *entries);
1018
1338
  obj->v.obj.entries = entries;
1019
1339
  obj->v.obj.cap = cap;
1020
1340
  }
1021
1341
  ScrDynEntry *e = &obj->v.obj.entries[obj->v.obj.len++];
1022
- e->key = key;
1342
+ if (!e->key || e->key_len != key_len || memcmp(e->key, key, key_len)) {
1343
+ char *owned = scr_dyn_key_copy(key, key_len);
1344
+ scr_dyn_key_release(e->key, e->key_len);
1345
+ e->key = owned;
1346
+ }
1023
1347
  e->key_len = key_len;
1024
1348
  e->value = value;
1025
1349
  e->getter = NULL;
@@ -1028,6 +1352,7 @@ static void scr_dyn_obj_put(ScrDyn *obj, char *key, size_t key_len, ScrDyn *valu
1028
1352
  e->writable = true;
1029
1353
  e->enumerable = true;
1030
1354
  e->configurable = true;
1355
+ if (obj->v.obj.len >= SCR_DYN_OBJECT_INDEX_MIN) scr_dyn_index_append(obj);
1031
1356
  }
1032
1357
 
1033
1358
  /* ── dyn construction (compiler-emitted converters & overflow reads) ───── */
@@ -1088,6 +1413,22 @@ ScrDyn *scr_dyn_symbol_get(const ScrDyn *value, const ScrStr *key) {
1088
1413
  }
1089
1414
 
1090
1415
  ScrDyn *scr_dyn_new_num(double n) {
1416
+ /* Small integers are immutable primitives, just like the boolean and null
1417
+ * singletons. Initialize only touched slots; the table neither grows nor
1418
+ * owns heap references. Preserve negative zero as a distinct payload. */
1419
+ if (n >= -128 && n <= 255) {
1420
+ int value = (int)n;
1421
+ if ((double)value == n && (value != 0 || !signbit(n))) {
1422
+ static SCR_TL ScrDyn values[384];
1423
+ ScrDyn *cached = &values[value + 128];
1424
+ if (cached->rc == 0) {
1425
+ cached->rc = SIZE_MAX;
1426
+ cached->kind = SCR_DYN_NUM;
1427
+ cached->v.num = n;
1428
+ }
1429
+ return cached;
1430
+ }
1431
+ }
1091
1432
  ScrDyn *d = scr_dyn_alloc(SCR_DYN_NUM);
1092
1433
  d->v.num = n;
1093
1434
  return d;
@@ -1927,7 +2268,9 @@ bool scr_dyn_util_type_is(const ScrDyn *value, const ScrStr *probe) {
1927
2268
  if (!value) return false;
1928
2269
  if (value->kind == SCR_DYN_JSVAL) return scr_dyn_jsval_ops()->type_probe(value->v.jsval.cell, probe);
1929
2270
  #define PROBE(name) (probe->len == sizeof(name) - 1 && memcmp(probe->data, name, sizeof(name) - 1) == 0)
1930
- if (PROBE("isAnyArrayBuffer") || PROBE("isArrayBuffer")) return scr_array_buffer_is(value);
2271
+ if (PROBE("isAnyArrayBuffer")) return scr_buffer_storage_is(value);
2272
+ if (PROBE("isArrayBuffer")) return scr_array_buffer_is(value);
2273
+ if (PROBE("isSharedArrayBuffer")) return scr_shared_array_buffer_is(value);
1931
2274
  if (PROBE("isArrayBufferView")) return value->kind == SCR_DYN_BYTES;
1932
2275
  if (PROBE("isDataView")) return value->kind == SCR_DYN_BYTES && value->v.bytes->is_data_view;
1933
2276
  if (PROBE("isTypedArray")) return value->kind == SCR_DYN_BYTES && !value->v.bytes->is_data_view;
@@ -2165,7 +2508,7 @@ void scr_dyn_chunk_enc(bool utf8) { scr_dyn_chunk_utf8 = utf8; }
2165
2508
  * a Buffer-flavored bytes box, or a string inside a setEncoding window. */
2166
2509
  ScrDyn *scr_dyn_new_chunk(const ScrBytes *b) {
2167
2510
  if (scr_dyn_chunk_utf8) {
2168
- ScrStr *s = scr_str_new((const char *)b->data, b->len);
2511
+ ScrStr *s = scr_bytes_string(b, 0, b->len);
2169
2512
  ScrDyn *d = scr_dyn_new_str(s);
2170
2513
  scr_str_release(s);
2171
2514
  return d;
@@ -2343,7 +2686,7 @@ ScrDyn *scr_dyn_bind(ScrDyn *target, ScrDyn *const *args, size_t argc) {
2343
2686
  * always-linked core never references gated units. A missing tag at use
2344
2687
  * is an internal error: emitted programs install a unit's ops whenever
2345
2688
  * they can box its handles. */
2346
- static const ScrDynHandleOps *scr_dynh_ops[SCR_DYNH_COUNT];
2689
+ static SCR_TL const ScrDynHandleOps *scr_dynh_ops[SCR_DYNH_COUNT];
2347
2690
 
2348
2691
  void scr_dyn_handle_install(ScrDynHandleTag tag, const ScrDynHandleOps *ops) {
2349
2692
  scr_dynh_ops[tag] = ops;
@@ -2590,6 +2933,7 @@ ScrDyn *scr_dyn_new_handle(void *h, ScrDynHandleTag tag) {
2590
2933
  d->v.handle.ptr = scr_dyn_handle_ops(tag)->retain(h);
2591
2934
  d->v.handle.tag = tag;
2592
2935
  d->v.handle.traced = tag == SCR_DYNH_WEAK_MAP || tag == SCR_DYNH_WEAK_SET ||
2936
+ tag == SCR_DYNH_WORKER || tag == SCR_DYNH_MESSAGE_PORT ||
2593
2937
  ((tag == SCR_DYNH_SET || tag == SCR_DYNH_MAP) &&
2594
2938
  (((ScrMap *)h)->key_trace != NULL || ((ScrMap *)h)->val_trace != NULL));
2595
2939
  return d;
@@ -2599,8 +2943,8 @@ ScrDyn *scr_dyn_new_handle(void *h, ScrDynHandleTag tag) {
2599
2943
  * allocator view; the freelist stays private, and the release arm's
2600
2944
  * scr_promise_release edge installs HERE — a promise-free link never
2601
2945
  * references the fiber machinery (the unit-test subset links). */
2602
- void (*scr_dyn_promise_release_fn)(ScrPromise *p) = NULL;
2603
- bool (*scr_dyn_promise_identity_fn)(ScrPromise *a, ScrPromise *b) = NULL;
2946
+ SCR_TL void (*scr_dyn_promise_release_fn)(ScrPromise *p) = NULL;
2947
+ SCR_TL bool (*scr_dyn_promise_identity_fn)(ScrPromise *a, ScrPromise *b) = NULL;
2604
2948
 
2605
2949
  ScrDyn *scr_dyn_alloc_promise(void (*release_fn)(ScrPromise *p)) {
2606
2950
  scr_dyn_promise_release_fn = release_fn;
@@ -2765,7 +3109,15 @@ typedef struct {
2765
3109
  static SCR_TL ScrDynThisEnt *scr_dyn_this_stack;
2766
3110
  static SCR_TL size_t scr_dyn_this_n, scr_dyn_this_cap;
2767
3111
 
3112
+ static void scr_dyn_this_cleanup(void) {
3113
+ while (scr_dyn_this_n) scr_dyn_this_pop();
3114
+ free(scr_dyn_this_stack);
3115
+ scr_dyn_this_stack = NULL;
3116
+ scr_dyn_this_cap = 0;
3117
+ }
3118
+
2768
3119
  static ScrDynThisEnt *scr_dyn_this_grow(void) {
3120
+ if (!scr_dyn_this_stack) scr_atexit(scr_dyn_this_cleanup);
2769
3121
  if (scr_dyn_this_n == scr_dyn_this_cap) {
2770
3122
  size_t cap = scr_dyn_this_cap ? scr_dyn_this_cap * 2 : 8;
2771
3123
  ScrDynThisEnt *s = realloc(scr_dyn_this_stack, cap * sizeof *s);
@@ -2827,14 +3179,10 @@ static void scr_dyn_handle_key_set(ScrDyn *recv, ScrStr *key, ScrDyn *value) {
2827
3179
  scr_throw_error(SCR_ERR_ERROR, scr_jb_finish(&b));
2828
3180
  }
2829
3181
 
2830
- /* Public obj insertion: COPIES the key bytes (the internal put takes a
2831
- * malloc'd buffer), owns the value, later duplicate keys win. */
3182
+ /* Public obj insertion copies a new key only when needed, owns the value,
3183
+ * and preserves the existing entry for duplicate keys. */
2832
3184
  void scr_dyn_obj_set(ScrDyn *obj, const char *key, size_t key_len, ScrDyn *value) {
2833
- char *copy = malloc(key_len + 1);
2834
- if (!copy) scr_json_oom();
2835
- memcpy(copy, key, key_len);
2836
- copy[key_len] = '\0';
2837
- scr_dyn_obj_put(obj, copy, key_len, value);
3185
+ scr_dyn_obj_put(obj, key, key_len, value);
2838
3186
  }
2839
3187
 
2840
3188
  static ScrStr *scr_dyn_property_key(const ScrDyn *key) {
@@ -2842,12 +3190,7 @@ static ScrStr *scr_dyn_property_key(const ScrDyn *key) {
2842
3190
  }
2843
3191
 
2844
3192
  static ScrDynEntry *scr_dyn_entry(ScrDyn *obj, const ScrStr *key) {
2845
- if (obj->kind != SCR_DYN_OBJ) return NULL;
2846
- for (size_t i = 0; i < obj->v.obj.len; i++) {
2847
- ScrDynEntry *entry = &obj->v.obj.entries[i];
2848
- if (entry->key_len == key->len && memcmp(entry->key, key->data, key->len) == 0) return entry;
2849
- }
2850
- return NULL;
3193
+ return scr_dyn_find_entry(obj, key->data, key->len);
2851
3194
  }
2852
3195
 
2853
3196
  static bool scr_dyn_property_same_value(const ScrDyn *a, const ScrDyn *b) {
@@ -3030,6 +3373,7 @@ typedef struct {
3030
3373
  unsigned kind; /* 0: array, 1: string, 2: Map, 3: Set */
3031
3374
  unsigned selection; /* 0: values, 1: keys, 2: entries */
3032
3375
  bool array_like;
3376
+ bool step_done; /* completion of the last compiler-consumed step */
3033
3377
  double limit;
3034
3378
  } ScrNativeIterator;
3035
3379
 
@@ -3071,21 +3415,18 @@ static void scr_native_iterator_release(void *ptr) {
3071
3415
  free(iterator);
3072
3416
  }
3073
3417
 
3074
- static ScrDyn *scr_native_iterator_next(ScrNativeIterator *iterator) {
3418
+ /* Produce an owned value without allocating the protocol result. The
3419
+ * compiler uses this only after checking the captured next function; public
3420
+ * next() calls still receive a fresh, independently mutable result object. */
3421
+ static ScrDyn *scr_native_iterator_value(ScrNativeIterator *iterator, bool *done_out) {
3075
3422
  ScrDyn *source = iterator->source;
3076
- if (source && iterator->kind == 4) {
3077
- ScrDyn *result = scr_dyn_handle_ops_of(source)->iter_step(source->v.handle.ptr, &iterator->index, iterator->selection);
3078
- if (!result) return NULL;
3079
- if (scr_dyn_truthy(scr_dyn_obj_get(result, "done", 4))) {
3080
- iterator->source = NULL;
3081
- scr_dyn_release(source);
3082
- }
3083
- return result;
3084
- }
3423
+ /* An inherited indexed getter can advance this same iterator recursively.
3424
+ * Keep the source alive even if that nested call exhausts the iterator. */
3425
+ if (source) scr_dyn_retain(source);
3085
3426
  /* Native array capsules retain the live array, so refresh its view at each
3086
3427
  * step rather than iterating a snapshot taken when the iterator opened. */
3087
3428
  ScrDyn *view = source && source->kind == SCR_DYN_TYPED_REF ? scr_dyn_typed_ref_materialize(source) : NULL;
3088
- if (scr_exc_pending()) { scr_dyn_release(view); return NULL; }
3429
+ if (scr_exc_pending()) { scr_dyn_release(view); scr_dyn_release(source); return NULL; }
3089
3430
  ScrDyn *items = view ? view : source;
3090
3431
  ScrMap *map = source && (iterator->kind == 2 || iterator->kind == 3) ? source->v.handle.ptr : NULL;
3091
3432
  if (map) while (iterator->index < scr_map_iter_count(map) && !scr_map_iter_live(map, iterator->index)) iterator->index++;
@@ -3131,6 +3472,24 @@ static ScrDyn *scr_native_iterator_next(ScrNativeIterator *iterator) {
3131
3472
  scr_str_release(point);
3132
3473
  }
3133
3474
  scr_dyn_release(view);
3475
+ scr_dyn_release(source);
3476
+ *done_out = done;
3477
+ return value;
3478
+ }
3479
+
3480
+ static ScrDyn *scr_native_iterator_next(ScrNativeIterator *iterator) {
3481
+ ScrDyn *source = iterator->source;
3482
+ if (source && iterator->kind == 4) {
3483
+ ScrDyn *result = scr_dyn_handle_ops_of(source)->iter_step(source->v.handle.ptr, &iterator->index, iterator->selection);
3484
+ if (!result) return NULL;
3485
+ if (scr_dyn_truthy(scr_dyn_obj_get(result, "done", 4))) {
3486
+ iterator->source = NULL;
3487
+ scr_dyn_release(source);
3488
+ }
3489
+ return result;
3490
+ }
3491
+ bool done;
3492
+ ScrDyn *value = scr_native_iterator_value(iterator, &done);
3134
3493
  if (!value) return NULL;
3135
3494
  ScrDyn *result = scr_dyn_new_obj();
3136
3495
  scr_dyn_obj_set(result, "value", 5, value);
@@ -3180,6 +3539,28 @@ static ScrDyn *scr_native_handle_iterator_next_call(ScrClosure *closure, ScrDyn
3180
3539
  return scr_native_iterator_next_checked(4);
3181
3540
  }
3182
3541
 
3542
+ bool scr_dyn_iterator_can_step(const ScrDyn *iterator, const ScrDyn *next) {
3543
+ if (iterator->kind != SCR_DYN_HANDLE || iterator->v.handle.tag != SCR_DYNH_ITERATOR) return false;
3544
+ unsigned kind = ((ScrNativeIterator *)iterator->v.handle.ptr)->kind;
3545
+ if (kind > 3) return false;
3546
+ size_t index = kind == 3 ? 8 : kind == 2 ? 7 : kind == 1 ? 5 : 0;
3547
+ return next == scr_iterator_functions[index];
3548
+ }
3549
+
3550
+ ScrDyn *scr_dyn_iterator_step(const ScrDyn *value) {
3551
+ ScrNativeIterator *iterator = value->v.handle.ptr;
3552
+ bool done = false;
3553
+ ScrDyn *item = scr_native_iterator_value(iterator, &done);
3554
+ /* Publish after getters finish, so recursive steps cannot overwrite this
3555
+ * step's completion. No user code runs between step and step_done. */
3556
+ iterator->step_done = done;
3557
+ return item;
3558
+ }
3559
+
3560
+ bool scr_dyn_iterator_step_done(const ScrDyn *value) {
3561
+ return ((ScrNativeIterator *)value->v.handle.ptr)->step_done;
3562
+ }
3563
+
3183
3564
  static ScrDyn *scr_native_iterator_get(void *ptr, const char *key, size_t len) {
3184
3565
  if (len != 4 || memcmp(key, "next", 4)) return NULL;
3185
3566
  unsigned kind = ((ScrNativeIterator *)ptr)->kind;
@@ -3945,7 +4326,7 @@ ScrStr *scr_dyn_object_tag(const ScrDyn *d) {
3945
4326
  case SCR_DYN_OBJ: tag = "[object Object]"; break;
3946
4327
  case SCR_DYN_HANDLE:
3947
4328
  if ((d->v.handle.tag >= SCR_DYNH_ABORT_SIGNAL &&
3948
- d->v.handle.tag <= SCR_DYNH_ABORT_CONTROLLER) || d->v.handle.tag == SCR_DYNH_ARRAY_BUFFER ||
4329
+ d->v.handle.tag <= SCR_DYNH_ABORT_CONTROLLER) || d->v.handle.tag == SCR_DYNH_ARRAY_BUFFER || d->v.handle.tag == SCR_DYNH_SHARED_ARRAY_BUFFER ||
3949
4330
  d->v.handle.tag == SCR_DYNH_WEAK_MAP || d->v.handle.tag == SCR_DYNH_WEAK_SET ||
3950
4331
  d->v.handle.tag == SCR_DYNH_SET || d->v.handle.tag == SCR_DYNH_MAP || d->v.handle.tag == SCR_DYNH_REGEXP ||
3951
4332
  d->v.handle.tag == SCR_DYNH_DATE) {
@@ -4438,7 +4819,7 @@ ScrStr *scr_dyn_to_string(const ScrDyn *d, const ScrStr *enc) {
4438
4819
  return out;
4439
4820
  }
4440
4821
  if ((d->v.handle.tag >= SCR_DYNH_ABORT_SIGNAL &&
4441
- d->v.handle.tag <= SCR_DYNH_ABORT_CONTROLLER) || d->v.handle.tag == SCR_DYNH_ARRAY_BUFFER || d->v.handle.tag == SCR_DYNH_SET || d->v.handle.tag == SCR_DYNH_MAP) {
4822
+ d->v.handle.tag <= SCR_DYNH_ABORT_CONTROLLER) || d->v.handle.tag == SCR_DYNH_ARRAY_BUFFER || d->v.handle.tag == SCR_DYNH_SHARED_ARRAY_BUFFER || d->v.handle.tag == SCR_DYNH_SET || d->v.handle.tag == SCR_DYNH_MAP) {
4442
4823
  ScrJsonBuf b;
4443
4824
  scr_jb_init(&b);
4444
4825
  scr_jb_puts(&b, "[object ");
@@ -5483,10 +5864,7 @@ void scr_jb_put_dyn(ScrJsonBuf *b, const ScrDyn *d) {
5483
5864
  if (e->value->kind == SCR_DYN_JSVAL && scr_dyn_isl_typeof_is(e->value, "function")) continue; /* engine functions drop too */
5484
5865
  if (!first) scr_jb_putc(b, ',');
5485
5866
  first = false;
5486
- /* Keys escape exactly like string values (put_json_str quotes). */
5487
- ScrStr *k = scr_str_new(e->key, e->key_len);
5488
- scr_jb_put_json_str(b, k);
5489
- scr_str_release(k);
5867
+ scr_jb_put_json_span(b, e->key, e->key_len);
5490
5868
  scr_jb_putc(b, ':');
5491
5869
  scr_jb_put_dyn(b, e->value);
5492
5870
  }
@@ -5647,8 +6025,10 @@ static int32_t scr_json_hex4(ScrJsonP *p) {
5647
6025
  * slow path would produce) and returns -1. */
5648
6026
  static int scr_json_string_span(ScrJsonP *p, const char **span,
5649
6027
  size_t *span_len) {
5650
- size_t i = p->pos + 1;
5651
- while (i < p->len) {
6028
+ *span = p->s + p->pos + 1;
6029
+ *span_len = scr_json_plain_bytes(*span, p->len - p->pos - 1);
6030
+ size_t i = p->pos + 1 + *span_len;
6031
+ if (i < p->len) {
5652
6032
  unsigned char c = (unsigned char)p->s[i];
5653
6033
  if (c == '"') {
5654
6034
  *span = p->s + p->pos + 1;
@@ -5661,7 +6041,6 @@ static int scr_json_string_span(ScrJsonP *p, const char **span,
5661
6041
  scr_json_throw_pos("Bad control character in string literal", i);
5662
6042
  return -1;
5663
6043
  }
5664
- i++;
5665
6044
  }
5666
6045
  scr_json_throw_pos("Unterminated string", p->pos);
5667
6046
  return -1;
@@ -5669,11 +6048,13 @@ static int scr_json_string_span(ScrJsonP *p, const char **span,
5669
6048
 
5670
6049
  /* Slow path: parses the string literal at p->pos (the opening quote),
5671
6050
  * decoding escapes, into a +1 ScrStr. NULL on error (thrown). */
5672
- static ScrStr *scr_json_string_slow(ScrJsonP *p) {
6051
+ static ScrStr *scr_json_string_slow(ScrJsonP *p, size_t prefix) {
5673
6052
  size_t open = p->pos;
5674
6053
  p->pos++; /* opening quote */
5675
6054
  ScrJsonBuf b;
5676
6055
  scr_jb_init(&b);
6056
+ scr_jb_write(&b, p->s + p->pos, prefix);
6057
+ p->pos += prefix;
5677
6058
  for (;;) {
5678
6059
  if (p->pos >= p->len) {
5679
6060
  scr_jb_dispose(&b);
@@ -5691,8 +6072,9 @@ static ScrStr *scr_json_string_slow(ScrJsonP *p) {
5691
6072
  return NULL;
5692
6073
  }
5693
6074
  if (c != '\\') {
5694
- scr_jb_putc(&b, (char)c); /* raw UTF-8 passes through */
5695
- p->pos++;
6075
+ size_t run = scr_json_plain_bytes(p->s + p->pos, p->len - p->pos);
6076
+ scr_jb_write(&b, p->s + p->pos, run);
6077
+ p->pos += run;
5696
6078
  continue;
5697
6079
  }
5698
6080
  p->pos++; /* backslash */
@@ -5767,7 +6149,7 @@ static ScrStr *scr_json_string_scr(ScrJsonP *p) {
5767
6149
  int r = scr_json_string_span(p, &span, &span_len);
5768
6150
  if (r < 0) return NULL;
5769
6151
  if (r > 0) return scr_str_new(span, span_len);
5770
- return scr_json_string_slow(p);
6152
+ return scr_json_string_slow(p, span_len);
5771
6153
  }
5772
6154
 
5773
6155
  static ScrDyn *scr_json_value(ScrJsonP *p);
@@ -5846,20 +6228,17 @@ static ScrDyn *scr_json_number(ScrJsonP *p) {
5846
6228
  }
5847
6229
  exp10 += eneg ? -ev : ev;
5848
6230
  }
5849
- ScrDyn *d = scr_dyn_alloc(SCR_DYN_NUM);
5850
6231
  if (precise && exp10 >= -22 && exp10 <= 22) {
5851
6232
  double v = (double)mant; /* exact: mant < 10^15 < 2^53 */
5852
6233
  if (exp10 > 0) v *= scr_json_pow10[exp10];
5853
6234
  else if (exp10 < 0) v /= scr_json_pow10[-exp10];
5854
- d->v.num = neg ? -v : v;
5855
- return d;
6235
+ return scr_dyn_new_num(neg ? -v : v);
5856
6236
  }
5857
6237
  /* The validated span re-parses with strtod (correctly rounded, and the
5858
6238
  * grammar above is a strict subset of what strtod accepts). The ScrStr
5859
6239
  * data is NUL-terminated, and strtod stops at the first non-number char,
5860
6240
  * so parsing from `start` reads exactly the validated token. */
5861
- d->v.num = strtod(p->s + start, NULL);
5862
- return d;
6241
+ return scr_dyn_new_num(strtod(p->s + start, NULL));
5863
6242
  }
5864
6243
 
5865
6244
  static bool scr_json_lit(ScrJsonP *p, const char *word, size_t n) {
@@ -5926,10 +6305,12 @@ static ScrDyn *scr_json_object(ScrJsonP *p) {
5926
6305
  scr_json_throw_pos("Expected property name or '}'", p->pos);
5927
6306
  return NULL;
5928
6307
  }
5929
- /* Key: fast span path (no escapes) copies straight into the malloc'd
5930
- * key buffer; the slow path decodes into a ScrStr first. */
6308
+ /* Keep the key borrowed until insertion determines whether it already
6309
+ * exists or can reuse a recycled slot. Escaped keys own their decoded
6310
+ * string until the value has been parsed and inserted. */
5931
6311
  size_t key_len = 0;
5932
- char *key;
6312
+ const char *key;
6313
+ ScrStr *decoded_key = NULL;
5933
6314
  {
5934
6315
  const char *span;
5935
6316
  size_t span_len;
@@ -5939,27 +6320,21 @@ static ScrDyn *scr_json_object(ScrJsonP *p) {
5939
6320
  return NULL;
5940
6321
  }
5941
6322
  if (r > 0) {
5942
- key = malloc(span_len + 1);
5943
- if (!key) scr_json_oom();
5944
- memcpy(key, span, span_len);
5945
- key[span_len] = '\0';
6323
+ key = span;
5946
6324
  key_len = span_len;
5947
6325
  } else {
5948
- ScrStr *ks = scr_json_string_slow(p);
5949
- if (!ks) {
6326
+ decoded_key = scr_json_string_slow(p, span_len);
6327
+ if (!decoded_key) {
5950
6328
  scr_dyn_release(obj);
5951
6329
  return NULL;
5952
6330
  }
5953
- key = malloc(ks->len + 1);
5954
- if (!key) scr_json_oom();
5955
- memcpy(key, ks->data, ks->len + 1);
5956
- key_len = ks->len;
5957
- scr_str_release(ks);
6331
+ key = decoded_key->data;
6332
+ key_len = decoded_key->len;
5958
6333
  }
5959
6334
  }
5960
6335
  scr_json_ws(p);
5961
6336
  if (p->pos >= p->len || p->s[p->pos] != ':') {
5962
- free(key);
6337
+ scr_str_release(decoded_key);
5963
6338
  scr_dyn_release(obj);
5964
6339
  if (p->pos >= p->len) scr_json_throw("Unexpected end of JSON input");
5965
6340
  else scr_json_throw_pos("Expected ':' after property name", p->pos);
@@ -5968,11 +6343,12 @@ static ScrDyn *scr_json_object(ScrJsonP *p) {
5968
6343
  p->pos++; /* ':' */
5969
6344
  ScrDyn *value = scr_json_value(p);
5970
6345
  if (!value) {
5971
- free(key);
6346
+ scr_str_release(decoded_key);
5972
6347
  scr_dyn_release(obj);
5973
6348
  return NULL;
5974
6349
  }
5975
6350
  scr_dyn_obj_put(obj, key, key_len, value); /* later duplicate keys win */
6351
+ scr_str_release(decoded_key);
5976
6352
  scr_json_ws(p);
5977
6353
  if (p->pos >= p->len) {
5978
6354
  scr_dyn_release(obj);
@@ -6121,7 +6497,12 @@ static void scr_json_delete_member(ScrDyn *object, const ScrStr *key) {
6121
6497
  ScrDynEntry removed = *entry;
6122
6498
  memmove(entry, entry + 1, (object->v.obj.len - i - 1) * sizeof *entry);
6123
6499
  object->v.obj.len--;
6124
- free(removed.key);
6500
+ free(object->v.obj.index);
6501
+ object->v.obj.index = NULL;
6502
+ /* The moved tail aliases a live entry; spare slots own only their own
6503
+ * retained key bytes, never a second pointer to a surviving property. */
6504
+ memset(&object->v.obj.entries[object->v.obj.len], 0, sizeof *entry);
6505
+ scr_dyn_key_release(removed.key, removed.key_len);
6125
6506
  scr_dyn_release(removed.value);
6126
6507
  scr_dyn_release(removed.getter);
6127
6508
  scr_dyn_release(removed.setter);
@@ -6324,8 +6705,71 @@ static bool scr_json_omitted(const ScrDyn *value) {
6324
6705
 
6325
6706
  static void scr_json_gap(ScrJsonBuf *buffer, const ScrStr *gap, size_t depth) {
6326
6707
  if (!gap->len) return;
6327
- scr_jb_putc(buffer, '\n');
6328
- for (size_t i = 0; i < depth; i++) scr_jb_write(buffer, gap->data, gap->len);
6708
+ const char *end = memchr(gap->data, 0, gap->len);
6709
+ size_t length = end ? (size_t)(end - gap->data) : gap->len;
6710
+ scr_jb_indent(buffer, gap->data, length, depth);
6711
+ }
6712
+
6713
+ /* These primitive values cannot invoke toJSON or mutate a containing frame.
6714
+ * BigInts, functions and every reference kind keep the protocol walk. */
6715
+ static bool scr_json_plain_value(const ScrDyn *value) {
6716
+ switch (value->kind) {
6717
+ case SCR_DYN_NULL: case SCR_DYN_UNDEF: case SCR_DYN_SYMBOL:
6718
+ case SCR_DYN_BOOL: case SCR_DYN_NUM: case SCR_DYN_STR: return true;
6719
+ default: return false;
6720
+ }
6721
+ }
6722
+
6723
+ /* Prove the whole immediate container before writing any of it. Without a
6724
+ * replacer or executable children, entries cannot change and borrowed names
6725
+ * need neither a key snapshot nor repeated lookups. Numeric property names
6726
+ * keep the ordinary sorted-key walk; sparse/accessor arrays keep Get. This
6727
+ * proof is repeated per call, so later mutations never leave a stale fact. */
6728
+ static bool scr_json_plain_container(const ScrDyn *value) {
6729
+ if (value->kind == SCR_DYN_ARR) {
6730
+ if (value->v.arr.presence || value->v.arr.properties) return false;
6731
+ for (size_t i = 0; i < value->v.arr.len; i++)
6732
+ if (!scr_json_plain_value(value->v.arr.items[i])) return false;
6733
+ return true;
6734
+ }
6735
+ if (value->kind != SCR_DYN_OBJ) return false;
6736
+ for (size_t i = 0; i < value->v.obj.len; i++) {
6737
+ const ScrDynEntry *entry = &value->v.obj.entries[i];
6738
+ if (!entry->enumerable) continue;
6739
+ double index;
6740
+ if (entry->accessor || !scr_json_plain_value(entry->value) ||
6741
+ scr_dyn_key_is_index(entry->key, entry->key_len, &index)) return false;
6742
+ }
6743
+ return true;
6744
+ }
6745
+
6746
+ static bool scr_json_plain_write(ScrJsonBuf *buffer, const ScrDyn *value,
6747
+ const ScrStr *gap, size_t depth) {
6748
+ bool array = value->kind == SCR_DYN_ARR;
6749
+ size_t length = array ? value->v.arr.len : value->v.obj.len;
6750
+ scr_jb_putc(buffer, array ? '[' : '{');
6751
+ bool first = true;
6752
+ for (size_t i = 0; i < length; i++) {
6753
+ const ScrDynEntry *entry = array ? NULL : &value->v.obj.entries[i];
6754
+ if (entry && !entry->enumerable) continue;
6755
+ const ScrDyn *child = array ? value->v.arr.items[i] : entry->value;
6756
+ bool omitted = scr_json_omitted(child);
6757
+ if (!array && omitted) continue;
6758
+ if (!omitted && !scr_json_callback_depth(depth + 1)) return false;
6759
+ if (!first) scr_jb_putc(buffer, ',');
6760
+ first = false;
6761
+ scr_json_gap(buffer, gap, depth + 1);
6762
+ if (entry) {
6763
+ scr_jb_put_json_span(buffer, entry->key, entry->key_len);
6764
+ scr_jb_putc(buffer, ':');
6765
+ if (gap->len) scr_jb_putc(buffer, ' ');
6766
+ }
6767
+ if (omitted) scr_jb_puts(buffer, "null");
6768
+ else scr_dyn_json_write(buffer, child);
6769
+ }
6770
+ if (!first) scr_json_gap(buffer, gap, depth);
6771
+ scr_jb_putc(buffer, array ? ']' : '}');
6772
+ return true;
6329
6773
  }
6330
6774
 
6331
6775
  static bool scr_json_replaced_write(ScrJsonBuf *buffer, const ScrDyn *value,
@@ -6334,6 +6778,8 @@ static bool scr_json_replaced_write(ScrJsonBuf *buffer, const ScrDyn *value,
6334
6778
  ScrDyn *view = value->kind == SCR_DYN_TYPED_REF ? scr_dyn_typed_ref_materialize(value) : NULL;
6335
6779
  const ScrDyn *observed = view ? view : value;
6336
6780
  if (scr_exc_pending()) { scr_dyn_release(view); return false; }
6781
+ if (!view && replacer->kind == SCR_DYN_UNDEF && scr_json_plain_container(value))
6782
+ return scr_json_plain_write(buffer, value, gap, depth);
6337
6783
  if (observed->kind != SCR_DYN_OBJ && observed->kind != SCR_DYN_ARR && observed->kind != SCR_DYN_BYTES) {
6338
6784
  /* Engine objects need an engine callback bridge, not an opaque JSON
6339
6785
  * splice: that would silently skip all their children. */
@@ -6824,9 +7270,8 @@ static ScrDyn *scr_dyn_obj_read_receiver(const ScrDyn *d, const char *key, size_
6824
7270
  continue;
6825
7271
  }
6826
7272
  if (current->kind != SCR_DYN_OBJ) continue;
6827
- for (size_t i = 0; i < current->v.obj.len; i++) {
6828
- ScrDynEntry *entry = &current->v.obj.entries[i];
6829
- if (entry->key_len != key_len || memcmp(entry->key, key, key_len) != 0) continue;
7273
+ ScrDynEntry *entry = scr_dyn_find_entry(current, key, key_len);
7274
+ if (entry) {
6830
7275
  if (!entry->accessor) return scr_dyn_retain(entry->value);
6831
7276
  if (!entry->getter) return scr_dyn_retain(scr_dyn_undefined());
6832
7277
  ScrDyn *getter = scr_dyn_retain(entry->getter);
@@ -7094,15 +7539,9 @@ bool scr_dyn_reflect_set(ScrDyn *target, ScrDyn *raw_key, ScrDyn *value, ScrDyn
7094
7539
 
7095
7540
  /* The array-index test (ECMA: a canonical numeric string < 2^32-1). */
7096
7541
  static bool scr_dyn_key_is_index(const char *key, size_t len, double *out) {
7097
- if (len == 0 || len > 10) return false;
7098
- if (key[0] == '0' && len > 1) return false;
7099
- double v = 0;
7100
- for (size_t i = 0; i < len; i++) {
7101
- if (key[i] < '0' || key[i] > '9') return false;
7102
- v = v * 10 + (key[i] - '0');
7103
- }
7104
- if (v > 4294967294.0) return false;
7105
- *out = v;
7542
+ uint32_t index;
7543
+ if (!scr_key_array_index(key, len, &index)) return false;
7544
+ *out = index;
7106
7545
  return true;
7107
7546
  }
7108
7547
 
@@ -7120,34 +7559,31 @@ static ScrDyn *scr_dyn_objwalk_key(const char *key, size_t key_len) {
7120
7559
  ScrDyn *scr_dyn_obj_own_keys(const ScrDyn *v) {
7121
7560
  size_t n = v->v.obj.len;
7122
7561
  ScrDyn *keys = scr_dyn_new_arr();
7123
- bool *is_index = malloc(n ? n * sizeof *is_index : 1);
7124
- double *idx = malloc(n ? n * sizeof *idx : 1);
7125
- if (!is_index || !idx) scr_trap("scriptc: out of memory\n");
7126
- size_t index_count = 0;
7562
+ ScrKeyIndex *indices = NULL;
7563
+ size_t count = 0;
7127
7564
  for (size_t i = 0; i < n; i++) {
7128
- const ScrDynEntry *e = &v->v.obj.entries[i];
7129
- is_index[i] = scr_dyn_key_is_index(e->key, e->key_len, &idx[i]);
7130
- if (is_index[i]) index_count++;
7131
- }
7132
- double last = -1;
7133
- for (size_t done = 0; done < index_count; done++) {
7134
- size_t best = (size_t)-1;
7135
- for (size_t i = 0; i < n; i++) {
7136
- if (!is_index[i] || idx[i] <= last) continue;
7137
- if (best == (size_t)-1 || idx[i] < idx[best]) best = i;
7138
- }
7139
- if (best == (size_t)-1) break;
7140
- last = idx[best];
7141
- scr_dyn_arr_push(keys, scr_dyn_objwalk_key(v->v.obj.entries[best].key,
7142
- v->v.obj.entries[best].key_len));
7143
- }
7565
+ const ScrDynEntry *entry = &v->v.obj.entries[i];
7566
+ uint32_t index;
7567
+ if (!scr_key_array_index(entry->key, entry->key_len, &index)) continue;
7568
+ if (!indices) {
7569
+ if (n > SIZE_MAX / sizeof *indices) scr_json_oom();
7570
+ indices = malloc(n * sizeof *indices);
7571
+ if (!indices) scr_json_oom();
7572
+ }
7573
+ indices[count++] = (ScrKeyIndex){index, i};
7574
+ }
7575
+ scr_key_index_sort(indices, count);
7576
+ for (size_t i = 0; i < count; i++) {
7577
+ const ScrDynEntry *entry = &v->v.obj.entries[indices[i].entry];
7578
+ scr_dyn_arr_push(keys, scr_dyn_objwalk_key(entry->key, entry->key_len));
7579
+ }
7580
+ free(indices);
7144
7581
  for (size_t i = 0; i < n; i++) {
7145
- if (is_index[i]) continue;
7146
- scr_dyn_arr_push(keys, scr_dyn_objwalk_key(v->v.obj.entries[i].key,
7147
- v->v.obj.entries[i].key_len));
7582
+ const ScrDynEntry *entry = &v->v.obj.entries[i];
7583
+ uint32_t index;
7584
+ if (!scr_key_array_index(entry->key, entry->key_len, &index))
7585
+ scr_dyn_arr_push(keys, scr_dyn_objwalk_key(entry->key, entry->key_len));
7148
7586
  }
7149
- free(is_index);
7150
- free(idx);
7151
7587
  return keys;
7152
7588
  }
7153
7589
 
@@ -8310,6 +8746,14 @@ bool scr_array_buffer_is(const ScrDyn *value) {
8310
8746
  return value->kind == SCR_DYN_HANDLE && value->v.handle.tag == SCR_DYNH_ARRAY_BUFFER;
8311
8747
  }
8312
8748
 
8749
+ bool scr_shared_array_buffer_is(const ScrDyn *value) {
8750
+ return value->kind == SCR_DYN_HANDLE && value->v.handle.tag == SCR_DYNH_SHARED_ARRAY_BUFFER;
8751
+ }
8752
+
8753
+ bool scr_buffer_storage_is(const ScrDyn *value) {
8754
+ return scr_array_buffer_is(value) || scr_shared_array_buffer_is(value);
8755
+ }
8756
+
8313
8757
  bool scr_array_buffer_is_view(const ScrDyn *value) {
8314
8758
  return value->kind == SCR_DYN_BYTES;
8315
8759
  }
@@ -8318,8 +8762,9 @@ static ScrDyn *scr_array_buffer_get(void *h, const char *key, size_t len) {
8318
8762
  if ((len == 10 && memcmp(key, "byteLength", len) == 0) ||
8319
8763
  (len == 13 && memcmp(key, "maxByteLength", len) == 0))
8320
8764
  return scr_dyn_new_num(scr_bytes_byte_len(h));
8321
- if ((len == 9 && memcmp(key, "resizable", len) == 0) ||
8322
- (len == 8 && memcmp(key, "detached", len) == 0)) return scr_dyn_new_bool(false);
8765
+ if (len == 8 && !memcmp(key, "growable", len) && ((ScrBytes *)h)->shared) return scr_dyn_new_bool(false);
8766
+ if (!((ScrBytes *)h)->shared && ((len == 9 && memcmp(key, "resizable", len) == 0) ||
8767
+ (len == 8 && memcmp(key, "detached", len) == 0))) return scr_dyn_new_bool(false);
8323
8768
  return NULL;
8324
8769
  }
8325
8770
 
@@ -8338,6 +8783,7 @@ static ScrDyn *scr_array_buffer_invoke(void *h, ScrDyn *self, const char *method
8338
8783
  ScrBytes *view = scr_bytes_buffer_view(h, SCR_BYTES_U8, 0, false, 0);
8339
8784
  if (!view) return NULL;
8340
8785
  ScrBytes *copy = scr_bytes_slice(view, start, end);
8786
+ if (((ScrBytes *)h)->shared) scr_bytes_make_shared(copy);
8341
8787
  scr_bytes_release(view);
8342
8788
  ScrDyn *result = scr_array_buffer_from_bytes(copy);
8343
8789
  scr_bytes_release(copy);
@@ -8353,8 +8799,13 @@ ScrDyn *scr_array_buffer_from_bytes(ScrBytes *view) {
8353
8799
  "ArrayBuffer", &scr_bytes_retain_v, &scr_bytes_release_v,
8354
8800
  &scr_array_buffer_invoke, &scr_array_buffer_get, &scr_array_buffer_set, NULL,
8355
8801
  };
8356
- scr_dyn_handle_install(SCR_DYNH_ARRAY_BUFFER, &ops);
8357
- return scr_dyn_new_handle(view->backing ? view->backing : view, SCR_DYNH_ARRAY_BUFFER);
8802
+ static const ScrDynHandleOps shared_ops = {
8803
+ "SharedArrayBuffer", &scr_bytes_retain_v, &scr_bytes_release_v,
8804
+ &scr_array_buffer_invoke, &scr_array_buffer_get, &scr_array_buffer_set, NULL,
8805
+ };
8806
+ ScrDynHandleTag tag = view->shared ? SCR_DYNH_SHARED_ARRAY_BUFFER : SCR_DYNH_ARRAY_BUFFER;
8807
+ scr_dyn_handle_install(tag, view->shared ? &shared_ops : &ops);
8808
+ return scr_dyn_new_handle(view->backing ? view->backing : view, tag);
8358
8809
  }
8359
8810
 
8360
8811
  static ScrDyn *scr_ffi_fail(const char *message) {
@@ -8385,7 +8836,8 @@ ScrDyn *scr_ffi_argument(ScrDyn *value, ScrStr *type) {
8385
8836
  void *address = NULL;
8386
8837
  bool converted = value->kind == SCR_DYN_NULL || value->kind == SCR_DYN_UNDEF;
8387
8838
  ScrBytes *bytes = value->kind == SCR_DYN_BYTES ? value->v.bytes :
8388
- scr_array_buffer_is(value) ? value->v.handle.ptr : NULL;
8839
+ scr_buffer_storage_is(value) ? value->v.handle.ptr : NULL;
8840
+ if (bytes && bytes->shared) return scr_ffi_fail("Shared byte storage cannot expose an unmanaged native pointer");
8389
8841
  if (bytes) { address = bytes->data; converted = true; }
8390
8842
  if (value->kind == SCR_DYN_STR) {
8391
8843
  if (memchr(value->v.str->data, 0, value->v.str->len)) {
@@ -8635,6 +9087,7 @@ static ScrDyn *scr_ffi_memory_call(ScrClosure *closure, ScrDyn *const *args, siz
8635
9087
  scr_dyn_arg_type_fail("source", "an ArrayBuffer or ArrayBufferView", value);
8636
9088
  return NULL;
8637
9089
  }
9090
+ if (bytes->shared) return scr_ffi_fail("Shared byte storage cannot expose an unmanaged native pointer");
8638
9091
  ScrBigInt *pointer = scr_bigint_from_pointer(bytes->data);
8639
9092
  ScrDyn *result = scr_dyn_new_bigint(pointer);
8640
9093
  scr_bigint_release(pointer);
@@ -8822,7 +9275,7 @@ static int scr_weak_key(const ScrDyn *key, void **ptr, unsigned *kind) {
8822
9275
  *ptr = key->v.fn.class_obj ? (void *)key->v.fn.class_obj : (void *)key->v.fn.clo;
8823
9276
  *kind = key->v.fn.class_obj ? 3 : 2; return 1;
8824
9277
  case SCR_DYN_HANDLE:
8825
- if (key->v.handle.tag != SCR_DYNH_ARRAY_BUFFER && key->v.handle.tag != SCR_DYNH_WEAK_MAP &&
9278
+ if (key->v.handle.tag != SCR_DYNH_ARRAY_BUFFER && key->v.handle.tag != SCR_DYNH_SHARED_ARRAY_BUFFER && key->v.handle.tag != SCR_DYNH_WEAK_MAP &&
8826
9279
  key->v.handle.tag != SCR_DYNH_WEAK_SET && key->v.handle.tag != SCR_DYNH_STDIO &&
8827
9280
  key->v.handle.tag != SCR_DYNH_FETCH_REQUEST && key->v.handle.tag != SCR_DYNH_FETCH_RESPONSE &&
8828
9281
  key->v.handle.tag != SCR_DYNH_MAP && key->v.handle.tag != SCR_DYNH_SET) return -1;
@@ -9053,6 +9506,16 @@ ScrDyn *scr_array_buffer_new(ScrDyn *length) {
9053
9506
  return result;
9054
9507
  }
9055
9508
 
9509
+ ScrDyn *scr_shared_array_buffer_new(ScrDyn *length) {
9510
+ ScrDyn *buffer = scr_array_buffer_new(length);
9511
+ if (!buffer) return NULL;
9512
+ ScrBytes *storage = buffer->v.handle.ptr;
9513
+ scr_bytes_make_shared(storage);
9514
+ ScrDyn *result = scr_array_buffer_from_bytes(storage);
9515
+ scr_dyn_release(buffer);
9516
+ return result;
9517
+ }
9518
+
9056
9519
  double scr_array_buffer_byte_length_getter(void) {
9057
9520
  ScrDyn *receiver = scr_dyn_this_get();
9058
9521
  if (!scr_array_buffer_is(receiver)) {
@@ -9079,7 +9542,7 @@ ScrDyn *scr_array_buffer_byte_length_descriptor(ScrDyn *getter) {
9079
9542
 
9080
9543
  ScrBytes *scr_array_buffer_view(ScrBytesElem elem, const ScrDyn *buffer,
9081
9544
  const ScrDyn *offset, const ScrDyn *length) {
9082
- if (!scr_array_buffer_is(buffer)) {
9545
+ if (!scr_buffer_storage_is(buffer)) {
9083
9546
  // Non-buffer inputs use the length/iterable/array-like constructor.
9084
9547
  // Their extra arguments are evaluated by the caller, but not coerced.
9085
9548
  return scr_bytes_from_dyn(elem, buffer, false);
@@ -9114,7 +9577,7 @@ SCR_ARRAY_BUFFER_VIEW(f64, SCR_BYTES_F64)
9114
9577
  #undef SCR_ARRAY_BUFFER_VIEW
9115
9578
 
9116
9579
  ScrBytes *scr_array_buffer_view_dv(ScrDyn *buffer, ScrDyn *offset, ScrDyn *length) {
9117
- if (!scr_array_buffer_is(buffer)) {
9580
+ if (!scr_buffer_storage_is(buffer)) {
9118
9581
  static const char msg[] = "First argument to DataView constructor must be an ArrayBuffer";
9119
9582
  scr_throw_error_msg(SCR_ERR_TYPE, msg, sizeof msg - 1);
9120
9583
  return NULL;