castrum 0.9.4 → 0.9.7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (61) hide show
  1. package/Cargo.lock +28 -44
  2. package/Cargo.toml +21 -4
  3. package/README.md +8 -6
  4. package/castrum.darwin-arm64.node +0 -0
  5. package/castrum.darwin-x64.node +0 -0
  6. package/castrum.linux-arm64-gnu.node +0 -0
  7. package/castrum.linux-arm64-musl.node +0 -0
  8. package/castrum.linux-x64-gnu.node +0 -0
  9. package/castrum.linux-x64-musl.node +0 -0
  10. package/castrum.linux-x64-v3-gnu.node +0 -0
  11. package/castrum.win32-x64-msvc.node +0 -0
  12. package/dist/index.d.ts +164 -0
  13. package/dist/index.js +4460 -3648
  14. package/docs/API.md +1 -0
  15. package/docs/ARCHITECTURE.md +1 -1
  16. package/docs/CASE_STUDY.md +4 -2
  17. package/docs/ENVIRONMENT.md +9 -2
  18. package/docs/FFI_BUN_GUIDE.md +166 -9
  19. package/docs/HOW_TO_ADD_AN_OP.md +34 -0
  20. package/docs/REPO_MAP.md +16 -5
  21. package/docs/RND-CONCURRENCY.md +772 -0
  22. package/docs/bun-builtins-decision-matrix.md +4 -1
  23. package/index.ts +5 -0
  24. package/package.json +172 -163
  25. package/rust/crypto/pbkdf2.rs +9 -0
  26. package/rust/crypto/session.rs +164 -7
  27. package/rust/ffi/crypto.rs +119 -29
  28. package/rust/ffi/mod.rs +1 -0
  29. package/rust/ffi/task.rs +172 -0
  30. package/rust/ffi/tests.rs +173 -0
  31. package/rust/http/form.rs +6 -2
  32. package/rust/http/query_parser.rs +53 -22
  33. package/rust/ingress/native_route.rs +131 -140
  34. package/rust/ingress/pipeline.rs +3 -3
  35. package/rust/ingress/tests.rs +5 -4
  36. package/rust/json/json_ser.rs +13 -11
  37. package/rust/lib.rs +1 -0
  38. package/rust/task/completion.rs +119 -0
  39. package/rust/task/mod.rs +65 -0
  40. package/rust/task/ops.rs +503 -0
  41. package/rust/task/runtime.rs +220 -0
  42. package/rust/task/tests.rs +231 -0
  43. package/rust/util/bytes.rs +238 -51
  44. package/src/ingress/health.ts +1 -2
  45. package/src/native/ffi/build/codecs.ts +29 -7
  46. package/src/native/ffi/build/compress.ts +8 -0
  47. package/src/native/ffi/build/instances.ts +54 -2
  48. package/src/native/ffi/build/metrics.ts +23 -7
  49. package/src/native/ffi/build/task.ts +79 -0
  50. package/src/native/ffi/build/util.ts +18 -0
  51. package/src/native/ffi/build.ts +2 -0
  52. package/src/native/ffi/selftest.ts +3 -1
  53. package/src/native/ffi/types.ts +57 -0
  54. package/src/native/ffi.ts +85 -14
  55. package/src/native/loader.ts +53 -3
  56. package/src/rust-ffi/scalar/http.ts +54 -16
  57. package/src/rust-ffi/text.ts +25 -3
  58. package/src/shared/bytes.ts +19 -0
  59. package/src/task/index.ts +24 -0
  60. package/src/task/op.ts +171 -0
  61. package/src/task/runtime.ts +568 -0
package/Cargo.lock CHANGED
@@ -108,9 +108,9 @@ checksum = "72b3254f16251a8381aa12e40e3c4d2f0199f8c6508fbecb9d91f575e0fbb8c6"
108
108
 
109
109
  [[package]]
110
110
  name = "base64"
111
- version = "0.23.0"
111
+ version = "0.23.1"
112
112
  source = "registry+https://github.com/rust-lang/crates.io-index"
113
- checksum = "b25655df2c3cdd83c5e5b293b88acd880332b2ddadd7c30ac43144fdc0033da9"
113
+ checksum = "ac07cdecf99051d9a5238b80f35af32cdeba5b336e55d957b318b50137e18da5"
114
114
 
115
115
  [[package]]
116
116
  name = "base64ct"
@@ -233,11 +233,11 @@ checksum = "fc652a48c352aef3ea3aed32080501cf3ef6ed5da78602a020c991775b0aff04"
233
233
 
234
234
  [[package]]
235
235
  name = "castrum"
236
- version = "0.9.4"
236
+ version = "0.9.7"
237
237
  dependencies = [
238
238
  "argon2",
239
239
  "aws-lc-rs",
240
- "base64 0.23.0",
240
+ "base64 0.23.1",
241
241
  "bcrypt",
242
242
  "brotli",
243
243
  "core_affinity",
@@ -344,9 +344,9 @@ dependencies = [
344
344
 
345
345
  [[package]]
346
346
  name = "crc32fast"
347
- version = "1.5.0"
347
+ version = "1.5.1"
348
348
  source = "registry+https://github.com/rust-lang/crates.io-index"
349
- checksum = "9481c1c90cbf2ac953f07c8d4a58aa3945c425b7185c9154d67a65e4230da511"
349
+ checksum = "8498c871161e1742aaa9d52551b2d6ebdd4c3d45a3be423e3728f33b955be550"
350
350
  dependencies = [
351
351
  "cfg-if",
352
352
  ]
@@ -459,9 +459,9 @@ dependencies = [
459
459
 
460
460
  [[package]]
461
461
  name = "fancy-regex"
462
- version = "0.18.0"
462
+ version = "0.19.0"
463
463
  source = "registry+https://github.com/rust-lang/crates.io-index"
464
- checksum = "e1e1dacd0d2082dfcf1351c4bdd566bbe89a2b263235a2b50058f1e130a47277"
464
+ checksum = "476de73bddf2ef8490aa4ee8f1cf40b430bf1d56c48c22080e5186952cd580e6"
465
465
  dependencies = [
466
466
  "bit-set",
467
467
  "regex-automata",
@@ -528,12 +528,6 @@ version = "1.0.7"
528
528
  source = "registry+https://github.com/rust-lang/crates.io-index"
529
529
  checksum = "3f9eec918d3f24069decb9af1554cad7c880e2da24a9afd88aca000531ab82c1"
530
530
 
531
- [[package]]
532
- name = "foldhash"
533
- version = "0.1.5"
534
- source = "registry+https://github.com/rust-lang/crates.io-index"
535
- checksum = "d9c4f5dac5e15c24eb999c26181a6ca40b39fe946cbe4c263c7209467bc83af2"
536
-
537
531
  [[package]]
538
532
  name = "foldhash"
539
533
  version = "0.2.0"
@@ -690,17 +684,6 @@ dependencies = [
690
684
  "r-efi 6.0.0",
691
685
  ]
692
686
 
693
- [[package]]
694
- name = "hashbrown"
695
- version = "0.15.5"
696
- source = "registry+https://github.com/rust-lang/crates.io-index"
697
- checksum = "9229cfe53dfd69f0609a49f65461bd93001ea1ef889cd5529dd176593f5338a1"
698
- dependencies = [
699
- "allocator-api2",
700
- "equivalent",
701
- "foldhash 0.1.5",
702
- ]
703
-
704
687
  [[package]]
705
688
  name = "hashbrown"
706
689
  version = "0.17.1"
@@ -709,7 +692,7 @@ checksum = "ed5909b6e89a2db4456e54cd5f673791d7eca6732202bbf2a9cc504fe2f9b84a"
709
692
  dependencies = [
710
693
  "allocator-api2",
711
694
  "equivalent",
712
- "foldhash 0.2.0",
695
+ "foldhash",
713
696
  ]
714
697
 
715
698
  [[package]]
@@ -849,7 +832,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
849
832
  checksum = "d466e9454f08e4a911e14806c24e16fba1b4c121d1ea474396f396069cf949d9"
850
833
  dependencies = [
851
834
  "equivalent",
852
- "hashbrown 0.17.1",
835
+ "hashbrown",
853
836
  ]
854
837
 
855
838
  [[package]]
@@ -896,9 +879,9 @@ dependencies = [
896
879
 
897
880
  [[package]]
898
881
  name = "jsonschema"
899
- version = "0.48.5"
882
+ version = "0.49.9"
900
883
  source = "registry+https://github.com/rust-lang/crates.io-index"
901
- checksum = "f05a6cff806294a7699d48761d4ae2bdebab7fa2eef05e4a0b83320f0ff46901"
884
+ checksum = "59ec8a241beed129f06114aa68007e905ca350e7baeb6e17a7631bb7978d91b2"
902
885
  dependencies = [
903
886
  "ahash",
904
887
  "bytecount",
@@ -925,18 +908,18 @@ dependencies = [
925
908
 
926
909
  [[package]]
927
910
  name = "jsonschema-regex"
928
- version = "0.48.5"
911
+ version = "0.49.9"
929
912
  source = "registry+https://github.com/rust-lang/crates.io-index"
930
- checksum = "84708dd3f6c5327478a96f37378adb27deed6a626cf84d19de780d9e8ae84b17"
913
+ checksum = "91994f45017ed5e66aa8e59b8415f4cb033a6380d7200387b7cf117595fbdf85"
931
914
  dependencies = [
932
915
  "regex-syntax",
933
916
  ]
934
917
 
935
918
  [[package]]
936
919
  name = "jsonschema-value"
937
- version = "0.48.5"
920
+ version = "0.49.9"
938
921
  source = "registry+https://github.com/rust-lang/crates.io-index"
939
- checksum = "fd8c04ab4ce60e42c4e302d3bd9d184652bb56f212495d2eea23573bcbf72556"
922
+ checksum = "7ec7637f83e510868ae6ed625f7ebfbbde4554ee8ce49854caa5126a8b9b9ecb"
940
923
  dependencies = [
941
924
  "ahash",
942
925
  "bytecount",
@@ -1000,11 +983,11 @@ dependencies = [
1000
983
 
1001
984
  [[package]]
1002
985
  name = "lru"
1003
- version = "0.12.5"
986
+ version = "0.18.4"
1004
987
  source = "registry+https://github.com/rust-lang/crates.io-index"
1005
- checksum = "234cf4f4a04dc1f57e24b96cc0cd600cf2af460d4161ac5ecdd0af8e1f3b2a38"
988
+ checksum = "ff9840bcc50b71349309900da0ce7279aa336ae71d73250b07998932c7d97c25"
1006
989
  dependencies = [
1007
- "hashbrown 0.15.5",
990
+ "hashbrown",
1008
991
  ]
1009
992
 
1010
993
  [[package]]
@@ -1092,13 +1075,14 @@ dependencies = [
1092
1075
 
1093
1076
  [[package]]
1094
1077
  name = "napi"
1095
- version = "3.11.0"
1078
+ version = "3.12.2"
1096
1079
  source = "registry+https://github.com/rust-lang/crates.io-index"
1097
- checksum = "de33522036981030a75c231829566bc63414e08101a6f5ff4ac6cef19c8e0941"
1080
+ checksum = "58c5f4d5375213fdb7be2655e152386e82f026f9a5ba36a75556e11359aafe09"
1098
1081
  dependencies = [
1099
1082
  "bitflags",
1100
1083
  "ctor",
1101
1084
  "futures",
1085
+ "libc",
1102
1086
  "napi-build",
1103
1087
  "napi-sys",
1104
1088
  "nohash-hasher",
@@ -1109,9 +1093,9 @@ dependencies = [
1109
1093
 
1110
1094
  [[package]]
1111
1095
  name = "napi-build"
1112
- version = "2.3.2"
1096
+ version = "2.4.1"
1113
1097
  source = "registry+https://github.com/rust-lang/crates.io-index"
1114
- checksum = "c9c366d2c8c60b86fa632df75f745509b52f9128f91a6bad4c796e44abb505e1"
1098
+ checksum = "60fdf9b392c50e7c4170fa633bd909490ed7835cea4c046776d1a4dd8d2ae0ab"
1115
1099
 
1116
1100
  [[package]]
1117
1101
  name = "napi-derive"
@@ -1557,14 +1541,14 @@ dependencies = [
1557
1541
 
1558
1542
  [[package]]
1559
1543
  name = "referencing"
1560
- version = "0.48.5"
1544
+ version = "0.49.9"
1561
1545
  source = "registry+https://github.com/rust-lang/crates.io-index"
1562
- checksum = "980e77f5cfffc592c0e7dfb6d20770a0b96a6ab94d403de7454ed9799505e4ba"
1546
+ checksum = "6efa2154ea6f5ce0fdecdd2a8d18f2fa1a39a8fbba91564f555a592e4dce8278"
1563
1547
  dependencies = [
1564
1548
  "ahash",
1565
1549
  "fluent-uri",
1566
1550
  "getrandom 0.3.4",
1567
- "hashbrown 0.17.1",
1551
+ "hashbrown",
1568
1552
  "itoa",
1569
1553
  "micromap",
1570
1554
  "parking_lot",
@@ -1614,7 +1598,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
1614
1598
  checksum = "815cc8a37159a463064825246cadb07961e25cd9885908606f6d08a98d8f8874"
1615
1599
  dependencies = [
1616
1600
  "bytes",
1617
- "hashbrown 0.17.1",
1601
+ "hashbrown",
1618
1602
  "indexmap",
1619
1603
  "munge",
1620
1604
  "ptr_meta",
package/Cargo.toml CHANGED
@@ -1,8 +1,11 @@
1
1
  [package]
2
2
  name = "castrum"
3
3
  # Keep in sync with package.json "version" (single source of truth: the npm package).
4
- version = "0.9.4"
4
+ version = "0.9.7"
5
5
  edition = "2021"
6
+ # Keep in sync with package.json "license" (cargo-deny rejects a crate with no
7
+ # license expression).
8
+ license = "MIT"
6
9
 
7
10
  [lib]
8
11
  name = "castrum"
@@ -17,6 +20,7 @@ path = "rust/lib.rs"
17
20
  [[bin]]
18
21
  name = "native-bench"
19
22
  path = "rust/src/bin/native-bench.rs"
23
+ required-features = ["native-bench"]
20
24
 
21
25
  [dependencies]
22
26
  napi = { version = "3", features = ["napi10", "serde-json"] }
@@ -39,7 +43,7 @@ sonic-rs = { version = "0.5", features = ["sort_keys"] }
39
43
  # default-features=false: drop resolve-http + tls-aws-lc-rs which pull in
40
44
  # reqwest -> hyper/h2/tokio/rustls (large binary, attack surface). Format
41
45
  # validators (email etc.) are built-in and NOT feature-gated in 0.48.
42
- jsonschema = { version = "0.48", default-features = false, features = ["resolve-file"] }
46
+ jsonschema = { version = "0.49", default-features = false, features = ["resolve-file"] }
43
47
  aws-lc-rs = "1"
44
48
  # NOTE: base64 0.23 enables SIMD (SSE/AVX) by default via the `simd-unsafe`
45
49
  # feature (part of `default`); no explicit feature is needed.
@@ -70,7 +74,9 @@ core_affinity = "0.8"
70
74
  parking_lot = "0.12"
71
75
  xxhash-rust = { version = "0.8", features = ["xxh3"] }
72
76
  ipnet = "2"
73
- lru = "0.12"
77
+ # 0.18.2+ carries the RUSTSEC-2026-0253 fix (0.16.x is affected); keep this
78
+ # requirement at or above the fixed release so `cargo deny` / OSV stay green.
79
+ lru = "0.18.2"
74
80
  # Zero-cost hashing for fast_schema object-key lookups (default SipHash is slow
75
81
  # on short keys). Already a transitive dep, so no new download.
76
82
  rustc-hash = "2"
@@ -79,7 +85,7 @@ rustc-hash = "2"
79
85
  # lookahead/backrefs); fraction::BigFraction is the SAME exact-rational type used
80
86
  # for `multipleOf` divisibility. Both are already transitive deps, so no new
81
87
  # downloads — but they become direct deps so fast_schema can use them.
82
- fancy-regex = "0.18"
88
+ fancy-regex = "0.19"
83
89
  fraction = "0.15"
84
90
  # Exact cross-type number equality for enum/const/uniqueItems (same semantics
85
91
  # jsonschema uses via jsonschema-value's cmp::equal). Already transitive.
@@ -92,6 +98,10 @@ argon2 = "0.5"
92
98
  bcrypt = "0.16"
93
99
  # PBKDF2-HMAC-SHA256 (RustCrypto) — pure-Rust KDF.
94
100
  pbkdf2 = "0.12"
101
+ # sha2 is consumed ONLY by pbkdf2 (digest 0.10). Do NOT bump to 0.11: that
102
+ # moves `Sha256` to digest 0.11 while pbkdf2 0.12 still requires digest 0.10,
103
+ # so `pbkdf2_hmac::<Sha256>` stops compiling (E0277 CoreProxy). Revisit only
104
+ # together with a pbkdf2 release that depends on digest 0.11.
95
105
  sha2 = "0.10"
96
106
  # HTML templating (fast, safe, no eval).
97
107
  minijinja = "2"
@@ -112,6 +122,13 @@ proptest = "1"
112
122
  [features]
113
123
  default = ["fast-email"]
114
124
  fast-email = ["dep:fast_chemail"]
125
+ # Diagnostic-only gate for the `native-bench` binary (see the [[bin]] below):
126
+ # without this feature the bin is not a default target, so `napi build` — and
127
+ # therefore every shipped cross-compiled artifact — never links it. The napi
128
+ # cross toolchains cannot resolve the aws-lc-sys C symbols an executable needs
129
+ # (`undefined reference to __isoc23_sscanf`), while a cdylib tolerates them.
130
+ # Run it with: cargo run --release --features native-bench --bin native-bench
131
+ native-bench = []
115
132
 
116
133
  # Codify the CI clippy gate (`cargo clippy --all-targets -- -D warnings`) so a
117
134
  # bare local `cargo clippy` fails on the same lints — no flag drift between
package/README.md CHANGED
@@ -187,17 +187,19 @@ For coverage floors, the typecheck/test configs, and the full test matrix, see
187
187
  ## Publishing
188
188
 
189
189
  The package ships **all platform addons in a single tarball**. Push a `v*` tag
190
- and CI builds + publishes every platform to npm; or use `bun run publish:manual`
190
+ and CI builds + publishes every platform to npm; or use `bun run release:manual`
191
191
  for a quick single-platform release:
192
192
 
193
193
  ```bash
194
- bun run publish:manual -- --increment minor # bump + tag + build + publish
195
- bun run publish:manual:dry # print the plan, change nothing
194
+ bun run release minor # bump + verify + commit + tag (CI publishes)
195
+ bun run release:manual # same, but also builds + publishes locally
196
+ bun run release:dry # print the plan, change nothing
196
197
  ```
197
198
 
198
- Run `bun run check:version` before tagging (it verifies `package.json`,
199
- `Cargo.toml`, and `CHANGELOG.md` agree). See [`docs/REPO_MAP.md`](./docs/REPO_MAP.md)
200
- §6 for the full flow.
199
+ `bun run release` uses the shared canonical flow (`scripts/release.ts` +
200
+ `.release.json`), syncing `package.json`, `Cargo.toml`, `Cargo.lock`, and
201
+ `CHANGELOG.md`. Run `bun run check:version` before tagging (it verifies they
202
+ agree). See [`docs/REPO_MAP.md`](./docs/REPO_MAP.md) §6 for the full flow.
201
203
 
202
204
  ## Documentation
203
205
 
Binary file
Binary file
Binary file
Binary file
Binary file
Binary file
Binary file
Binary file
package/dist/index.d.ts CHANGED
@@ -2936,6 +2936,170 @@ export declare const rust: RustClient;
2936
2936
  export type ProvenClient = RustClient;
2937
2937
  /** The full `rust.*` surface, exposed for audit. Same object as `rust`. */
2938
2938
  export declare const proven: ProvenClient;
2939
+ /** Numeric op ids — mirror `rust/task/ops.rs`. */
2940
+ export declare const TASK_OP: {
2941
+ /** args `[u32 maxDecompressed LE][gzip bytes]` (0 = native 64 MiB default). */
2942
+ readonly gzipDecompress: 1;
2943
+ /** args `[u32 rounds][u32 dkLen][u32 saltLen][salt][password]`. */
2944
+ readonly pbkdf2Sha256: 2;
2945
+ /** `gzipDecompress` writing into a caller buffer (zero-copy output). */
2946
+ readonly gzipDecompressInto: 3;
2947
+ /** args `[u32 pwLen][u32 phcLen][password][phc]` → body is one byte (1 = match). */
2948
+ readonly argon2Verify: 4;
2949
+ /** args `[u32 maxDecompressed LE][brotli bytes]` (0 = native 64 MiB default). */
2950
+ readonly brotliDecompress: 5;
2951
+ /** `brotliDecompress` writing into a caller buffer (zero-copy output). */
2952
+ readonly brotliDecompressInto: 6;
2953
+ /** args `[u32 level][gzip bytes]` (level clamped to 0-9 natively). */
2954
+ readonly gzipCompress: 7;
2955
+ };
2956
+ /** A task op name (`gzipDecompress`). */
2957
+ export type TaskOpName = keyof typeof TASK_OP;
2958
+ /** Completion status codes (mirror `rust/task/ops.rs`). */
2959
+ export declare const TASK_STATUS_OK = 0;
2960
+ /** The op returned an error; the body is the UTF-8 error message. */
2961
+ export declare const TASK_STATUS_ERROR = 1;
2962
+ /** The task was cancelled before/while it ran; the body is empty. */
2963
+ export declare const TASK_STATUS_CANCELLED = 2;
2964
+ /**
2965
+ * Pack the `gzip.decompress` task args: `[u32 maxDecompressed LE][gzip bytes]`.
2966
+ *
2967
+ * @param data Compressed gzip bytes.
2968
+ * @param maxDecompressed Output cap in bytes; `undefined`/`0` selects the
2969
+ * native 64 MiB decompression-bomb default.
2970
+ * @param out Optional caller-owned destination (>= `4 + data.length`),
2971
+ * returned as a view. Native copies args on submit, so the
2972
+ * same buffer may be reused for the next submission — but
2973
+ * only while the caller stays SYNCHRONOUS (a zero-copy
2974
+ * retry re-submits after an await and must own its memory).
2975
+ * @returns A packed args buffer.
2976
+ */
2977
+ export declare function encodeGzipDecompressArgs(data: Uint8Array, maxDecompressed?: number, out?: Uint8Array): Uint8Array;
2978
+ /**
2979
+ * Pack the `brotli.decompress` task args: `[u32 maxDecompressed LE][bytes]`.
2980
+ *
2981
+ * @param data Compressed brotli bytes.
2982
+ * @param maxDecompressed Output cap in bytes (`undefined`/`0` → native 64 MiB).
2983
+ * @param out Optional caller-owned destination (see the gzip form).
2984
+ * @returns A packed args buffer.
2985
+ */
2986
+ export declare function encodeBrotliDecompressArgs(data: Uint8Array, maxDecompressed?: number, out?: Uint8Array): Uint8Array;
2987
+ /**
2988
+ * Pack the `gzip.compress` task HEADER: `[u32 level]`. The payload is passed
2989
+ * separately so it can be read in place (zero-copy input) instead of copied.
2990
+ *
2991
+ * @param level Deflate level (`0`-`9`, clamped natively).
2992
+ * @param out Optional caller-owned destination (>= 4 bytes).
2993
+ * @returns The 4-byte header.
2994
+ */
2995
+ export declare function encodeGzipCompressHeader(level?: number, out?: Uint8Array): Uint8Array;
2996
+ /**
2997
+ * Pack the `argon2id.verify` task args:
2998
+ * `[u32 pwLen][u32 phcLen][password][phc]`. No `out` parameter on purpose: a
2999
+ * shared scratch would keep a plaintext password alive far longer than a
3000
+ * per-call allocation, which is the wrong trade for a secret.
3001
+ *
3002
+ * @param password Candidate password bytes.
3003
+ * @param phc PHC string bytes (`$argon2id$...`).
3004
+ * @returns A packed args buffer owned by the caller (Rust copies it on submit).
3005
+ */
3006
+ export declare function encodeArgon2VerifyArgs(password: Uint8Array, phc: Uint8Array): Uint8Array;
3007
+ /**
3008
+ * Safe upper bound on the gzip size of `n` input bytes: deflate's worst case is
3009
+ * stored blocks (5 bytes per block) plus the 18-byte gzip wrapper. The 16 KiB
3010
+ * block assumption is deliberately conservative (real blocks are 64 KiB), so a
3011
+ * destination sized with this can never be too small — no retry round trip.
3012
+ *
3013
+ * @param n Uncompressed input length in bytes.
3014
+ * @returns An upper bound in bytes.
3015
+ */
3016
+ export declare function gzipCompressUpperBound(n: number): number;
3017
+ /**
3018
+ * Starting capacity for a brotli zero-copy destination. Brotli carries no
3019
+ * ISIZE trailer, so there is no exact hint: this is a ratio guess, and the
3020
+ * needed-size retry lands the exact size if it falls short.
3021
+ *
3022
+ * @param compressedLen Compressed input length in bytes.
3023
+ * @returns A capacity guess in bytes (floored at the runtime's zero-copy size).
3024
+ */
3025
+ export declare function brotliCapacityGuess(compressedLen: number): number;
3026
+ /**
3027
+ * Pack the `pbkdf2.sha256` task args:
3028
+ * `[u32 rounds][u32 dkLen][u32 saltLen][salt][password]`.
3029
+ *
3030
+ * @param password Password bytes (the PBKDF2 secret).
3031
+ * @param salt Salt bytes.
3032
+ * @param rounds Iteration count (clamped to >= 1 natively).
3033
+ * @param dkLen Derived-key length in bytes (default 32, capped at 1 MiB).
3034
+ * @returns A packed args buffer owned by the caller (Rust copies it on submit).
3035
+ */
3036
+ export declare function encodePbkdf2Args(password: Uint8Array, salt: Uint8Array, rounds: number, dkLen?: number): Uint8Array;
3037
+ /** Per-call options for an offloaded task. */
3038
+ export interface TaskRunOptions {
3039
+ /** Abort the task; it completes with a cancelled error. */
3040
+ signal?: AbortSignal;
3041
+ /** Decompress ops: output cap in bytes (default native 64 MiB bomb cap). */
3042
+ maxDecompressed?: number;
3043
+ /** `gzipCompress` only: deflate level `0`-`9` (default `6`). */
3044
+ level?: number;
3045
+ }
3046
+ /** Options for {@link TaskRuntime.pbkdf2Sha256}. */
3047
+ export interface Pbkdf2RunOptions extends TaskRunOptions {
3048
+ /** Iteration count (clamped to >= 1 natively). */
3049
+ rounds: number;
3050
+ /** Derived-key length in bytes (default 32). */
3051
+ dkLen?: number;
3052
+ }
3053
+ /** Runtime introspection snapshot. */
3054
+ export interface TaskStats {
3055
+ /** Pool worker count (0 when the pool has not started). */
3056
+ threads: number;
3057
+ /** Finished-but-undrained completions in the native ring. */
3058
+ pending: number;
3059
+ /** JS promises currently awaiting a completion. */
3060
+ inflight: number;
3061
+ /** Completions resolved since the runtime was created. */
3062
+ completed: number;
3063
+ /** Drain rounds run on the JS thread (one per doorbell, plus coalesced work). */
3064
+ drains: number;
3065
+ /** Largest number of completions carried by a single drain round. */
3066
+ maxBatch: number;
3067
+ /** Zero-copy attempts that had to retry at the exact needed size. */
3068
+ tooSmallRetries: number;
3069
+ }
3070
+ /** Off-thread task runtime handle. */
3071
+ export interface TaskRuntime {
3072
+ /** gzip-decompress `data` on a pool thread (keeps the 64 MiB bomb cap). */
3073
+ gzipDecompress(data: Uint8Array, options?: TaskRunOptions): Promise<Uint8Array>;
3074
+ /** brotli-decompress `data` on a pool thread (keeps the 64 MiB bomb cap). */
3075
+ brotliDecompress(data: Uint8Array, options?: TaskRunOptions): Promise<Uint8Array>;
3076
+ /** gzip-compress `data` on a pool thread. */
3077
+ gzipCompress(data: Uint8Array, options?: TaskRunOptions): Promise<Uint8Array>;
3078
+ /** Verify a password against a PHC string on a pool thread (10-200 ms CPU). */
3079
+ argon2Verify(password: Uint8Array, phc: Uint8Array, options?: TaskRunOptions): Promise<boolean>;
3080
+ /** PBKDF2-HMAC-SHA256 on a pool thread (10-200 ms CPU, 1-64 B output). */
3081
+ pbkdf2Sha256(password: Uint8Array, salt: Uint8Array, options: Pbkdf2RunOptions): Promise<Uint8Array>;
3082
+ /** Pool / ring / in-flight counters. */
3083
+ stats(): TaskStats;
3084
+ /** Cancel everything in flight, stop the pool, release the doorbell. */
3085
+ shutdown(): void;
3086
+ }
3087
+ /** Options for {@link createTaskRuntime}. */
3088
+ export interface TaskRuntimeOptions {
3089
+ /** Pool worker count; `0`/omitted → native default (cores − 1). */
3090
+ threads?: number;
3091
+ }
3092
+ /**
3093
+ * Get the off-thread task runtime (created on first use, then shared). Binds
3094
+ * the Bun ffi surface lazily.
3095
+ *
3096
+ * @example
3097
+ * ```ts
3098
+ * const tasks = createTaskRuntime()
3099
+ * const out = await tasks.gzipDecompress(compressed)
3100
+ * ```
3101
+ */
3102
+ export declare function createTaskRuntime(options?: TaskRuntimeOptions): TaskRuntime;
2939
3103
  /** Recommended implementation for an operation. */
2940
3104
  export type OpImpl = "native" | "js";
2941
3105
  /** A selection decision: recommended implementation + rationale note. */