leviathan-crypto 2.0.1 → 2.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (93) hide show
  1. package/CLAUDE.md +171 -7
  2. package/LICENSE +4 -0
  3. package/README.md +109 -54
  4. package/SECURITY.md +125 -238
  5. package/dist/chacha20/cipher-suite.d.ts +10 -0
  6. package/dist/chacha20/cipher-suite.js +65 -2
  7. package/dist/chacha20/generator.d.ts +12 -0
  8. package/dist/chacha20/generator.js +91 -0
  9. package/dist/chacha20/index.d.ts +97 -1
  10. package/dist/chacha20/index.js +139 -11
  11. package/dist/chacha20/ops.d.ts +57 -6
  12. package/dist/chacha20/ops.js +93 -13
  13. package/dist/chacha20/pool-worker.js +12 -0
  14. package/dist/chacha20/types.d.ts +1 -32
  15. package/dist/ct-wasm.js +1 -1
  16. package/dist/ct.wasm +0 -0
  17. package/dist/docs/aead.md +66 -26
  18. package/dist/docs/architecture.md +600 -521
  19. package/dist/docs/argon2id.md +17 -14
  20. package/dist/docs/chacha20.md +146 -39
  21. package/dist/docs/exports.md +46 -10
  22. package/dist/docs/fortuna.md +339 -122
  23. package/dist/docs/init.md +24 -25
  24. package/dist/docs/loader.md +142 -47
  25. package/dist/docs/serpent.md +139 -41
  26. package/dist/docs/sha2.md +77 -19
  27. package/dist/docs/sha3.md +81 -15
  28. package/dist/docs/types.md +155 -15
  29. package/dist/docs/utils.md +171 -81
  30. package/dist/embedded/chacha20-pool-worker.d.ts +1 -0
  31. package/dist/embedded/chacha20-pool-worker.js +5 -0
  32. package/dist/embedded/kyber.d.ts +1 -1
  33. package/dist/embedded/kyber.js +1 -1
  34. package/dist/embedded/serpent-pool-worker.d.ts +1 -0
  35. package/dist/embedded/serpent-pool-worker.js +5 -0
  36. package/dist/fortuna.d.ts +14 -8
  37. package/dist/fortuna.js +144 -50
  38. package/dist/index.d.ts +8 -6
  39. package/dist/index.js +6 -5
  40. package/dist/init.d.ts +0 -2
  41. package/dist/init.js +83 -3
  42. package/dist/kyber/indcpa.js +4 -4
  43. package/dist/kyber/index.js +25 -5
  44. package/dist/kyber/kem.js +56 -1
  45. package/dist/kyber/suite.d.ts +1 -2
  46. package/dist/kyber/types.d.ts +1 -0
  47. package/dist/kyber/validate.d.ts +8 -4
  48. package/dist/kyber/validate.js +18 -14
  49. package/dist/kyber.wasm +0 -0
  50. package/dist/loader.d.ts +7 -2
  51. package/dist/loader.js +25 -28
  52. package/dist/ratchet/index.d.ts +6 -0
  53. package/dist/ratchet/index.js +37 -0
  54. package/dist/ratchet/kdf-chain.d.ts +13 -0
  55. package/dist/ratchet/kdf-chain.js +85 -0
  56. package/dist/ratchet/ratchet-keypair.d.ts +9 -0
  57. package/dist/ratchet/ratchet-keypair.js +61 -0
  58. package/dist/ratchet/root-kdf.d.ts +4 -0
  59. package/dist/ratchet/root-kdf.js +124 -0
  60. package/dist/ratchet/skipped-key-store.d.ts +14 -0
  61. package/dist/ratchet/skipped-key-store.js +154 -0
  62. package/dist/ratchet/types.d.ts +36 -0
  63. package/dist/ratchet/types.js +26 -0
  64. package/dist/serpent/cipher-suite.d.ts +10 -0
  65. package/dist/serpent/cipher-suite.js +135 -50
  66. package/dist/serpent/generator.d.ts +12 -0
  67. package/dist/serpent/generator.js +97 -0
  68. package/dist/serpent/index.d.ts +61 -1
  69. package/dist/serpent/index.js +92 -7
  70. package/dist/serpent/pool-worker.js +25 -101
  71. package/dist/serpent/serpent-cbc.d.ts +14 -4
  72. package/dist/serpent/serpent-cbc.js +50 -32
  73. package/dist/serpent/shared-ops.d.ts +83 -0
  74. package/dist/serpent/shared-ops.js +213 -0
  75. package/dist/serpent/types.d.ts +1 -5
  76. package/dist/sha2/hash.d.ts +2 -0
  77. package/dist/sha2/hash.js +53 -0
  78. package/dist/sha2/index.d.ts +1 -0
  79. package/dist/sha2/index.js +15 -1
  80. package/dist/sha3/hash.d.ts +2 -0
  81. package/dist/sha3/hash.js +53 -0
  82. package/dist/sha3/index.d.ts +17 -2
  83. package/dist/sha3/index.js +79 -7
  84. package/dist/stream/header.js +5 -5
  85. package/dist/stream/open-stream.js +36 -14
  86. package/dist/stream/seal-stream-pool.d.ts +1 -0
  87. package/dist/stream/seal-stream-pool.js +38 -8
  88. package/dist/stream/seal-stream.js +29 -11
  89. package/dist/types.d.ts +21 -0
  90. package/dist/utils.d.ts +7 -8
  91. package/dist/utils.js +73 -40
  92. package/dist/wasm-source.d.ts +9 -8
  93. package/package.json +79 -64
package/dist/docs/init.md CHANGED
@@ -1,9 +1,8 @@
1
- # Module Initialization and WASM Loading
1
+ <img src="https://github.com/xero/leviathan-crypto/raw/main/docs/logo.svg" alt="logo" width="120" align="left" margin="10">
2
2
 
3
- > [!IMPORTANT]
4
- > Call `init()` before using any cryptographic class. It loads the WebAssembly
5
- > modules that perform cryptographic work, caches them in memory, and makes them
6
- > available to all wrapper classes.
3
+ ### Module Initialization and WASM Loading
4
+
5
+ Call `init()` before using any cryptographic class. It loads the WebAssembly modules that perform cryptographic work, caches them in memory, and makes them available to all wrapper classes.
7
6
 
8
7
  > ### Table of Contents
9
8
  > - [Overview](#overview)
@@ -63,7 +62,8 @@ The WASM module families. Each one backs a group of related classes.
63
62
  | Module | Classes it enables |
64
63
  |---|---|
65
64
  | `'serpent'` | `Serpent`, `SerpentCbc`, `SerpentCtr` |
66
- | `'serpent'` + `'sha2'` | `SerpentCipher`, `Seal` (with `SerpentCipher`), `SealStream`, `OpenStream`, `Fortuna` — see [aead.md](./aead.md) |
65
+ | `'serpent'` + `'sha2'` | `SerpentCipher`, `Seal` (with `SerpentCipher`), `SealStream`, `OpenStream` — see [aead.md](./aead.md) |
66
+ | `Fortuna` combinations | `Fortuna` accepts a `Generator` + `HashFn` pair. Valid module combinations: `'serpent' + 'sha2'`, `'serpent' + 'sha3'`, `'chacha20' + 'sha2'`, `'chacha20' + 'sha3'`. See [fortuna.md](./fortuna.md). |
67
67
  | `'chacha20'` | `ChaCha20`, `ChaCha20Poly1305`, `XChaCha20Poly1305` |
68
68
  | `'chacha20'` + `'sha2'` | `XChaCha20Cipher`, `Seal` (with `XChaCha20Cipher`), `SealStream`, `OpenStream` — see [aead.md](./aead.md) |
69
69
  | `'sha2'` | `SHA256`, `SHA384`, `SHA512`, `HMAC` (SHA-2 based), `HKDF` |
@@ -73,7 +73,7 @@ The WASM module families. Each one backs a group of related classes.
73
73
 
74
74
  ```typescript
75
75
  type WasmSource = string | URL | ArrayBuffer | Uint8Array
76
- | WebAssembly.Module | Response | Promise<Response>
76
+ | WebAssembly.Module | Response | PromiseLike<WasmSource>
77
77
  ```
78
78
 
79
79
  A value that resolves to a WASM binary. The loading strategy is inferred from
@@ -86,7 +86,13 @@ the type:
86
86
  | `ArrayBuffer` | Compiled directly via `WebAssembly.instantiate`. |
87
87
  | `Uint8Array` | Compiled directly via `WebAssembly.instantiate`. |
88
88
  | `WebAssembly.Module` | Already compiled. Instantiated immediately. |
89
- | `Response` / `Promise<Response>` | Streaming compilation via `WebAssembly.instantiateStreaming`. |
89
+ | `Response` | Streaming compilation via `WebAssembly.instantiateStreaming`. |
90
+ | `PromiseLike<WasmSource>` | Awaited and re-dispatched by the resolved runtime type. |
91
+
92
+ Any `PromiseLike<WasmSource>` is accepted — `Promise<ArrayBuffer>`,
93
+ `Promise<Uint8Array>`, `Promise<string>`, a `fetch()` response promise, and
94
+ nested thenables up to depth 3 all resolve transparently. See
95
+ [loader.md](./loader.md) for details.
90
96
 
91
97
  ---
92
98
 
@@ -190,17 +196,6 @@ Used by pool infrastructure to send compiled modules to workers. See
190
196
 
191
197
  ---
192
198
 
193
- #### _resetForTesting()
194
-
195
- ```typescript
196
- function _resetForTesting(): void
197
- ```
198
-
199
- Clears all cached WASM instances. Testing utility only. Do not use in
200
- production code.
201
-
202
- ---
203
-
204
199
  ## Usage Examples
205
200
 
206
201
  ### Embedded init (most common)
@@ -294,9 +289,13 @@ if (!isInitialized('sha2')) {
294
289
 
295
290
  ---
296
291
 
297
- > ## Cross-References
298
- >
299
- > - [index](./README.md) — Project Documentation index
300
- > - [architecture](./architecture.md) architecture overview, module relationships, buffer layouts, and build pipeline
301
- > - [loader](./loader.md) WASM binary loading strategies (internal details)
302
- > - [wasm](./wasm.md) WebAssembly primer: modules, instances, memory, and the init gate
292
+
293
+ ## Cross-References
294
+
295
+ | Document | Description |
296
+ | -------- | ----------- |
297
+ | [index](./README.md) | Project Documentation index |
298
+ | [architecture](./architecture.md) | architecture overview, module relationships, buffer layouts, and build pipeline |
299
+ | [loader](./loader.md) | WASM binary loading strategies (internal details) |
300
+ | [wasm](./wasm.md) | WebAssembly primer: modules, instances, memory, and the init gate |
301
+
@@ -1,23 +1,21 @@
1
- # WASM Binary Loading Strategies
1
+ <img src="https://github.com/xero/leviathan-crypto/raw/main/docs/logo.svg" alt="logo" width="120" align="left" margin="10">
2
2
 
3
- > [!NOTE]
4
- > Internal module used by `init()` that handles the actual loading and
5
- > instantiation of WebAssembly binaries. You normally do not interact
6
- > with this module directly.
3
+ ### WASM Binary Loading Strategies
4
+
5
+ Internal module used by `init()` that handles the actual loading and instantiation of WebAssembly binaries. You normally do not interact with this module directly.
7
6
 
8
7
  > ### Table of Contents
9
8
  > - [Overview](#overview)
10
9
  > - [Security Notes](#security-notes)
11
10
  > - [API Reference](#api-reference)
11
+ > - [Examples](#examples)
12
12
  > - [Internal Details](#internal-details)
13
13
 
14
14
  ---
15
15
 
16
16
  ## Overview
17
17
 
18
- When you call [`init()`](./init.md), it delegates the work of obtaining and compiling the
19
- WASM binary to the loader. The loading strategy is inferred from the
20
- `WasmSource` type, so no mode string is required:
18
+ When you call [`init()`](./init.md), it delegates the work of obtaining and compiling the WASM binary to the loader. The loading strategy is inferred from the `WasmSource` type, so no mode string is required:
21
19
 
22
20
  **Embedded string.** gzip-compressed, base64-encoded WASM bundled in the package. Decoded and decompressed at [`init()`](./init.md) time using `DecompressionStream`. No network requests. This is the default and simplest option.
23
21
 
@@ -29,8 +27,9 @@ WASM binary to the loader. The loading strategy is inferred from the
29
27
 
30
28
  **Response / Promise\<Response\>.** Streaming compilation from an in-flight or deferred fetch.
31
29
 
32
- All strategies produce the same result: a `WebAssembly.Instance` that the
33
- wrapper classes use to perform cryptographic operations.
30
+ **Any other thenable (`PromiseLike<WasmSource>`).** The loader `await`s the thenable and recursively re-dispatches by the runtime type of the resolved value. `Promise<ArrayBuffer>`, `Promise<Uint8Array>`, `Promise<string>` (gzip+base64 blob), and even nested `Promise<Promise<Response>>` all work. Nesting is capped at depth 3 — deeper chains throw a `TypeError: thenable nesting too deep (max 3)`.
31
+
32
+ All strategies produce the same result: a `WebAssembly.Instance` that the wrapper classes use to perform cryptographic operations.
34
33
 
35
34
  ---
36
35
 
@@ -48,8 +47,7 @@ wrapper classes use to perform cryptographic operations.
48
47
 
49
48
  ## API Reference
50
49
 
51
- These functions are exported from `loader.ts` and called by `init.ts`. They
52
- are not part of the public API. They are documented here for completeness and for contributors working on the internals.
50
+ These functions are exported from `loader.ts` and called by `init.ts`. They are not part of the public API. They are documented here for completeness and for contributors working on the internals.
53
51
 
54
52
  ### `loadWasm(source)`
55
53
  ```typescript
@@ -68,16 +66,16 @@ instance receives a fresh 3-page `WebAssembly.Memory`.
68
66
  | `ArrayBuffer` | `WebAssembly.instantiate()`. |
69
67
  | `Uint8Array` | `WebAssembly.instantiate()`. |
70
68
  | `WebAssembly.Module` | `WebAssembly.instantiate(module, imports)`. |
71
- | `Response` / `Promise<Response>` | `WebAssembly.instantiateStreaming()`. |
69
+ | `Response` | `WebAssembly.instantiateStreaming()`. |
70
+ | `PromiseLike<WasmSource>` | `await` the thenable, re-dispatch by resolved type (recursive, max depth 3). |
72
71
 
73
72
  **Throws:**
74
73
 
75
74
  - `TypeError` if `source` is null, numeric, or otherwise unrecognised.
76
75
  - `TypeError` with `"empty string"` if `source` is an empty string.
76
+ - `TypeError` with `"thenable nesting too deep (max 3)"` if a thenable source resolves to another thenable more than three levels deep.
77
77
 
78
- **Runtime guards:** `Response` and `Promise` checks are guarded with
79
- `typeof Response !== 'undefined'` to avoid `ReferenceError` in runtimes
80
- where these globals do not exist (Node < 18).
78
+ **Runtime guards:** `Response` and `Promise` checks are guarded with `typeof Response !== 'undefined'` to avoid `ReferenceError` in runtimes where these globals do not exist (Node < 18).
81
79
 
82
80
  ---
83
81
 
@@ -86,12 +84,9 @@ where these globals do not exist (Node < 18).
86
84
  async function compileWasm(source: WasmSource): Promise<WebAssembly.Module>
87
85
  ```
88
86
 
89
- Compiles a `WasmSource` to a `WebAssembly.Module` without instantiating it.
90
- Used by pool infrastructure to send a compiled module to workers. Each worker receives the `Module` and instantiates it with their own isolated memory.
87
+ Compiles a `WasmSource` to a `WebAssembly.Module` without instantiating it. Used by pool infrastructure to send a compiled module to workers. Each worker receives the `Module` and instantiates it with their own isolated memory.
91
88
 
92
- **Source type handling:** Same dispatch table as `loadWasm()`, but calls
93
- `WebAssembly.compile()` / `WebAssembly.compileStreaming()` instead of the
94
- `instantiate` variants. `WebAssembly.Module` sources are returned as-is.
89
+ **Source type handling:** Same dispatch table as `loadWasm()`, but calls `WebAssembly.compile()` / `WebAssembly.compileStreaming()` instead of the `instantiate` variants. `WebAssembly.Module` sources are returned as-is.
95
90
 
96
91
  **Throws:** Same as `loadWasm()`.
97
92
 
@@ -109,13 +104,114 @@ Decodes a gzip-compressed, base64-encoded WASM string to raw bytes.
109
104
 
110
105
  **Throws:**
111
106
 
112
- - `Error` if `DecompressionStream` is not available in the runtime.
113
- The error message directs the user to provide a URL, ArrayBuffer, or
114
- WebAssembly.Module source instead.
115
- - `Error` if base64 decoding fails (corrupt embedded blob).
107
+ - `Error` if `DecompressionStream` is not available in the runtime. The error message directs the user to provide a URL, ArrayBuffer, or WebAssembly.Module source instead.
108
+ - `RangeError` with message `'base64ToBytes: invalid base64 input'` if the input is not valid base64 (corrupt embedded blob, wrong-length string, or non-base64 characters). Propagated unchanged from the shared `base64ToBytes` utility.
109
+
110
+ Exported for use by the cipher-suite spawn paths that may need to decode blobs before passing pre-compiled modules to pool workers.
111
+
112
+ ---
113
+
114
+ # Examples
115
+
116
+ These examples show how to pass different source types to `init()` depending on your runtime, bundler, and deployment target.
117
+
118
+ ## Embedded (default, bundled)
119
+
120
+ Use the compressed WASM blobs included in the package. No network call. Ideal for browser bundles and Node servers.
121
+
122
+ ```typescript
123
+ import { init } from 'leviathan-crypto'
124
+ import { serpentWasm } from 'leviathan-crypto/serpent/embedded'
125
+ import { sha2Wasm } from 'leviathan-crypto/sha2/embedded'
126
+ import { chacha20Wasm } from 'leviathan-crypto/chacha20/embedded'
127
+ import { kyberWasm } from 'leviathan-crypto/kyber/embedded'
128
+
129
+ await init({
130
+ serpent: serpentWasm,
131
+ sha2: sha2Wasm,
132
+ chacha20: chacha20Wasm,
133
+ kyber: kyberWasm
134
+ })
135
+ ```
136
+
137
+ ## URL-based (streaming from CDN or public folder)
138
+
139
+ Fetch the `.wasm` file from a served asset. The browser streams and compiles while downloading. Requires `Content-Type: application/wasm`.
140
+
141
+ ```typescript
142
+ import { init } from 'leviathan-crypto'
143
+
144
+ // From a CDN
145
+ await init({
146
+ serpent: new URL('https://cdn.example.com/wasm/serpent.wasm'),
147
+ sha2: new URL('https://cdn.example.com/wasm/sha2.wasm'),
148
+ chacha20: new URL('https://cdn.example.com/wasm/chacha20.wasm'),
149
+ kyber: new URL('https://cdn.example.com/wasm/kyber.wasm')
150
+ })
151
+
152
+ // From a local /public folder
153
+ await init({
154
+ serpent: new URL('/assets/wasm/serpent.wasm', import.meta.url),
155
+ sha2: new URL('/assets/wasm/sha2.wasm', import.meta.url)
156
+ })
157
+ ```
158
+
159
+ ## Pre-compiled Module (edge runtimes, KV cache)
160
+
161
+ Compile the WASM once, cache the `WebAssembly.Module`, and reuse it across requests. Each instantiation gets its own isolated memory.
162
+
163
+ ```typescript
164
+ import { init, compileWasm } from 'leviathan-crypto/loader'
165
+ import { serpentWasm } from 'leviathan-crypto/serpent/embedded'
166
+
167
+ // Compile once (at module load time or in an init handler)
168
+ const serpentModule = await compileWasm(serpentWasm)
169
+
170
+ // Reuse across requests
171
+ async function handleRequest(req) {
172
+ await init({ serpent: serpentModule })
173
+ // Each request gets a fresh instance with isolated memory
174
+ // ...
175
+ }
176
+ ```
177
+
178
+ ## Deferred loading (lazy initialization)
179
+
180
+ Load the WASM only when needed. Pass a Promise that resolves to any valid source.
181
+
182
+ ```typescript
183
+ import { init } from 'leviathan-crypto'
184
+
185
+ const serpentPromise = fetch('/assets/wasm/serpent.wasm')
186
+ .then(res => res.arrayBuffer())
187
+
188
+ await init({
189
+ serpent: serpentPromise,
190
+ sha2: new URL('/assets/wasm/sha2.wasm', import.meta.url)
191
+ })
192
+ ```
193
+
194
+ ## Worker pool with pre-compiled modules
195
+
196
+ Pass a compiled `WebAssembly.Module` to workers so each worker instantiates it with isolated memory. Used internally by `SealStreamPool` for parallel encryption.
197
+
198
+ ```typescript
199
+ import { compileWasm } from 'leviathan-crypto/loader'
200
+ import { serpentWasm } from 'leviathan-crypto/serpent/embedded'
201
+
202
+ // Main thread: compile once
203
+ const serpentModule = await compileWasm(serpentWasm)
116
204
 
117
- Exported for use by pool worker launchers that need to decode blobs
118
- before spawning threads.
205
+ // Pass to worker via postMessage
206
+ worker.postMessage({ type: 'init', module: serpentModule })
207
+
208
+ // Inside worker: instantiate with isolated memory
209
+ self.onmessage = async (ev) => {
210
+ if (ev.data.type === 'init') {
211
+ await init({ serpent: ev.data.module })
212
+ }
213
+ }
214
+ ```
119
215
 
120
216
  ---
121
217
 
@@ -125,37 +221,36 @@ before spawning threads.
125
221
 
126
222
  Each module provides two paths to its embedded blob:
127
223
 
128
- | Path | Export | Used by |
129
- |----------------------------------------|-----------------|-----------------------------|
130
- | `src/ts/embedded/serpent.ts` | (raw blob) | Build artifact, gitignored |
131
- | `src/ts/serpent/embedded.ts` | `serpentWasm` | Consumer import |
224
+ | Path | Export | Used by |
225
+ |--------------------------------------------|--------------------|-------------------------------------------|
226
+ | `src/ts/embedded/serpent.ts` | (raw blob) | Build artifact, gitignored |
227
+ | `src/ts/serpent/embedded.ts` | `serpentWasm` | Consumer import |
228
+ | `src/ts/embedded/serpent-pool-worker.ts` | `WORKER_SOURCE` | Internal, consumed by `cipher-suite.ts` |
132
229
 
133
- The per-module `embedded.ts` re-exports the generated blob as a named
134
- export. Consumers import from the `/embedded` subpath:
230
+ The per-module `embedded.ts` re-exports the generated blob as a named export. Consumers import from the `/embedded` subpath:
135
231
  ```typescript
136
232
  import { serpentWasm } from 'leviathan-crypto/serpent/embedded'
137
233
  ```
138
234
 
139
- The `src/ts/embedded/` directory is generated by `scripts/embed-wasm.ts`
140
- and is gitignored. These files are not meant to be created or edited by hand.
235
+ The `src/ts/embedded/` directory is generated by `scripts/embed-wasm.ts` (WASM blobs) and `scripts/embed-workers.ts` (pool-worker IIFE bundles), and is gitignored. These files are not meant to be created or edited by hand.
141
236
 
142
237
  ### Embedded compression
143
238
 
144
- The embedded files contain gzip-compressed WASM encoded as base64.
145
- Compression reduces the embedded footprint from ~198 KB to ~33 KB across
146
- all four modules, with Serpent alone shrinking from ~167 KB to ~20 KB.
239
+ The embedded files contain gzip-compressed WASM encoded as base64. Compression reduces the embedded footprint from ~198 KB to ~33 KB across all four modules, with Serpent alone shrinking from \~167 KB to \~20 KB.
147
240
 
148
241
  ### Memory allocation
149
242
 
150
- Every WASM instance receives a `WebAssembly.Memory` with exactly 3 pages
151
- (192 KB total). The memory size is fixed; modules do not grow their memory at runtime. This is a deliberate design choice: fixed memory prevents
152
- unexpected allocations and makes the memory layout predictable and auditable.
243
+ Every WASM instance receives a `WebAssembly.Memory` with exactly 3 pages (192 KB total). The memory size is fixed; modules do not grow their memory at runtime. This is a deliberate design choice: fixed memory prevents unexpected allocations and makes the memory layout predictable and auditable.
153
244
 
154
245
  ---
155
246
 
156
- > ## Cross-References
157
- >
158
- > - [index](./README.md) — Project Documentation index
159
- > - [architecture](./architecture.md) architecture overview, module relationships, buffer layouts, and build pipeline
160
- > - [init](./init.md) the public `init()` API that uses this loader
161
- > - [wasm](./wasm.md) WebAssembly primer: modules, instances, and memory model
247
+
248
+ ## Cross-References
249
+
250
+ | Document | Description |
251
+ | -------- | ----------- |
252
+ | [index](./README.md) | Project Documentation index |
253
+ | [architecture](./architecture.md) | architecture overview, module relationships, buffer layouts, and build pipeline |
254
+ | [init](./init.md) | the public `init()` API that uses this loader |
255
+ | [wasm](./wasm.md) | WebAssembly primer: modules, instances, and memory model |
256
+