@danielsimonjr/mathts-functions 0.68.4 → 0.69.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.
@@ -1,597 +0,0 @@
1
- var __defProp = Object.defineProperty;
2
- var __export = (target, all) => {
3
- for (var name in all)
4
- __defProp(target, name, { get: all[name], enumerable: true });
5
- };
6
-
7
- // src/wasm/integrity.ts
8
- import {
9
- sha384OfBuffer,
10
- loadWasmManifest,
11
- verifyWasmIntegrity
12
- } from "@danielsimonjr/mathts-core/internal";
13
-
14
- // src/wasm/resolve.ts
15
- import { resolvePackagedWasm, defaultWasmLocation } from "@danielsimonjr/mathts-core/internal";
16
- async function resolveBrowserWasm(metaUrl, wasmFile) {
17
- let dir = new URL(".", metaUrl);
18
- for (let depth = 0; depth < 8; depth++) {
19
- const candidates = [new URL(`wasm/${wasmFile}`, dir), new URL(`dist/wasm/${wasmFile}`, dir)];
20
- for (const candidate of candidates) {
21
- try {
22
- const res = await fetch(candidate.href, { method: "HEAD" });
23
- if (res.ok) return candidate.href;
24
- } catch {
25
- }
26
- }
27
- const parent = new URL("../", dir);
28
- if (parent.href === dir.href) break;
29
- dir = parent;
30
- }
31
- return new URL(`./wasm/${wasmFile}`, metaUrl).href;
32
- }
33
-
34
- // src/wasm/WasmLoader.ts
35
- var WasmLoader = class _WasmLoader {
36
- static instance = null;
37
- wasmModule = null;
38
- compiledModule = null;
39
- loading = null;
40
- isNode;
41
- lastMetrics = null;
42
- constructor() {
43
- this.isNode = typeof process !== "undefined" && process.versions?.node !== void 0;
44
- }
45
- static getInstance() {
46
- if (!_WasmLoader.instance) {
47
- _WasmLoader.instance = new _WasmLoader();
48
- }
49
- return _WasmLoader.instance;
50
- }
51
- /**
52
- * Load the WASM module
53
- */
54
- async load(wasmPath) {
55
- if (this.wasmModule) {
56
- return this.wasmModule;
57
- }
58
- if (this.loading) {
59
- return this.loading;
60
- }
61
- this.loading = this.loadModule(wasmPath);
62
- try {
63
- this.wasmModule = await this.loading;
64
- } catch (error) {
65
- this.compiledModule = null;
66
- throw error;
67
- } finally {
68
- this.loading = null;
69
- }
70
- return this.wasmModule;
71
- }
72
- /**
73
- * Precompile the WASM module without instantiation
74
- * Useful for build-time or startup optimization
75
- */
76
- async precompile(wasmPath) {
77
- if (this.compiledModule) return;
78
- const path = wasmPath || await this.getDefaultWasmPath();
79
- const startTime = performance.now();
80
- if (this.isNode) {
81
- const fs = await import("fs");
82
- const { promisify } = await import("util");
83
- const readFile = promisify(fs.readFile);
84
- const buffer = await readFile(path);
85
- await verifyWasmIntegrity(buffer, path);
86
- this.compiledModule = await WebAssembly.compile(buffer);
87
- } else {
88
- const manifest = await loadWasmManifest(path);
89
- if (!manifest && typeof WebAssembly.compileStreaming === "function") {
90
- this.compiledModule = await WebAssembly.compileStreaming(fetch(path));
91
- } else {
92
- const response = await fetch(path);
93
- const buffer = await response.arrayBuffer();
94
- await verifyWasmIntegrity(buffer, path, { manifest });
95
- this.compiledModule = await WebAssembly.compile(buffer);
96
- }
97
- }
98
- this.lastMetrics = {
99
- fileReadMs: 0,
100
- compileMs: performance.now() - startTime,
101
- instantiateMs: 0,
102
- totalMs: performance.now() - startTime,
103
- fromCache: false
104
- };
105
- }
106
- async loadModule(wasmPath) {
107
- const path = wasmPath || await this.getDefaultWasmPath();
108
- const totalStart = performance.now();
109
- if (this.compiledModule) {
110
- const instStart = performance.now();
111
- const instance = await WebAssembly.instantiate(this.compiledModule, this.getImports());
112
- this.lastMetrics = {
113
- fileReadMs: 0,
114
- compileMs: 0,
115
- instantiateMs: performance.now() - instStart,
116
- totalMs: performance.now() - totalStart,
117
- fromCache: true
118
- };
119
- return instance.exports;
120
- }
121
- if (this.isNode) {
122
- return this.loadNodeWasm(path, totalStart);
123
- } else {
124
- return this.loadBrowserWasm(path, totalStart);
125
- }
126
- }
127
- /**
128
- * Get the WASM binary path.
129
- *
130
- * AssemblyScript is the sole WASM backend (`mathts-as.wasm`); the legacy
131
- * native WASM toolchain was removed (migration complete 2026-06-26).
132
- *
133
- * Returns an async result because the Node branch dynamically imports
134
- * `node:url` (fileURLToPath) so the path is resolved relative to this
135
- * source file's location rather than process.cwd(). The browser branch
136
- * probes candidate URLs with `fetch(..., { method: 'HEAD' })` for the same
137
- * reason Node walks the filesystem — see {@link resolveBrowserWasm}.
138
- */
139
- async getDefaultWasmPath() {
140
- const wasmFile = "mathts-as.wasm";
141
- if (this.isNode) {
142
- const packaged = await resolvePackagedWasm(import.meta.url, wasmFile);
143
- if (packaged) return packaged;
144
- return defaultWasmLocation(import.meta.url, wasmFile);
145
- }
146
- return resolveBrowserWasm(import.meta.url, wasmFile);
147
- }
148
- async loadNodeWasm(path, totalStart) {
149
- const fs = await import("fs");
150
- const { promisify } = await import("util");
151
- const readFile = promisify(fs.readFile);
152
- const readStart = performance.now();
153
- const buffer = await readFile(path);
154
- const readEnd = performance.now();
155
- await verifyWasmIntegrity(buffer, path);
156
- const compileStart = performance.now();
157
- this.compiledModule = await WebAssembly.compile(buffer);
158
- const compileEnd = performance.now();
159
- const instStart = performance.now();
160
- const instance = await WebAssembly.instantiate(this.compiledModule, this.getImports());
161
- const instEnd = performance.now();
162
- this.lastMetrics = {
163
- fileReadMs: readEnd - readStart,
164
- compileMs: compileEnd - compileStart,
165
- instantiateMs: instEnd - instStart,
166
- totalMs: performance.now() - totalStart,
167
- fromCache: false
168
- };
169
- return instance.exports;
170
- }
171
- async loadBrowserWasm(path, totalStart) {
172
- const manifest = await loadWasmManifest(path);
173
- if (!manifest && typeof WebAssembly.instantiateStreaming === "function") {
174
- const instStart2 = performance.now();
175
- const result = await WebAssembly.instantiateStreaming(fetch(path), this.getImports());
176
- this.compiledModule = result.module;
177
- this.lastMetrics = {
178
- fileReadMs: 0,
179
- // Combined with compile in streaming
180
- compileMs: 0,
181
- // Combined in streaming
182
- instantiateMs: performance.now() - instStart2,
183
- totalMs: performance.now() - totalStart,
184
- fromCache: false
185
- };
186
- return result.instance.exports;
187
- }
188
- const readStart = performance.now();
189
- const response = await fetch(path);
190
- const buffer = await response.arrayBuffer();
191
- const readEnd = performance.now();
192
- await verifyWasmIntegrity(buffer, path, { manifest });
193
- const compileStart = performance.now();
194
- this.compiledModule = await WebAssembly.compile(buffer);
195
- const compileEnd = performance.now();
196
- const instStart = performance.now();
197
- const instance = await WebAssembly.instantiate(this.compiledModule, this.getImports());
198
- const instEnd = performance.now();
199
- this.lastMetrics = {
200
- fileReadMs: readEnd - readStart,
201
- compileMs: compileEnd - compileStart,
202
- instantiateMs: instEnd - instStart,
203
- totalMs: performance.now() - totalStart,
204
- fromCache: false
205
- };
206
- return instance.exports;
207
- }
208
- getImports() {
209
- return {
210
- env: {
211
- abort: (msg, file, line, column) => {
212
- console.error("WASM abort", { msg, file, line, column });
213
- throw new Error("WASM abort");
214
- },
215
- seed: () => Date.now()
216
- },
217
- Math,
218
- Date
219
- };
220
- }
221
- /**
222
- * Get the loaded WASM module
223
- */
224
- getModule() {
225
- return this.wasmModule;
226
- }
227
- /**
228
- * Get the compiled WASM module (for caching/serialization)
229
- */
230
- getCompiledModule() {
231
- return this.compiledModule;
232
- }
233
- /**
234
- * Check if WASM is loaded
235
- */
236
- isLoaded() {
237
- return this.wasmModule !== null;
238
- }
239
- /**
240
- * Check if WASM is precompiled
241
- */
242
- isPrecompiled() {
243
- return this.compiledModule !== null;
244
- }
245
- /**
246
- * Get loading performance metrics
247
- */
248
- getLoadingMetrics() {
249
- return this.lastMetrics;
250
- }
251
- /**
252
- * Run garbage collection
253
- */
254
- collect() {
255
- const module = this.wasmModule;
256
- if (!module) return;
257
- module.__collect();
258
- }
259
- /**
260
- * Reset the loader (for testing)
261
- */
262
- reset() {
263
- this.wasmModule = null;
264
- this.compiledModule = null;
265
- this.loading = null;
266
- this.lastMetrics = null;
267
- }
268
- };
269
- var wasmLoader = WasmLoader.getInstance();
270
- var INTEGRITY_FAILURE = "WASM integrity check failed";
271
- async function loadWasm(wasmPath) {
272
- try {
273
- await wasmLoader.load(wasmPath);
274
- return true;
275
- } catch (error) {
276
- if (error instanceof Error && error.message.startsWith(INTEGRITY_FAILURE)) throw error;
277
- return false;
278
- }
279
- }
280
- function isWasmLoaded() {
281
- return wasmLoader.isLoaded();
282
- }
283
-
284
- // src/wasm/policy.ts
285
- var WASM_DISPATCH_POLICY = {
286
- // Element-wise (public `abs`, `sin`, ... on a Float64Array).
287
- array_abs_ptr: { min: 1024 },
288
- // 0.76/0.55 · 0.44/0.42 · 0.54/0.54 · 0.49/0.71
289
- array_log10_ptr: { min: 1024 },
290
- // 0.89/0.82 · 0.70/0.77 · 0.70/0.72 · 0.76/0.83
291
- array_sin_ptr: { min: 1024, max: 131072 },
292
- // 0.76/0.77 · 0.72/0.75 · (0.92/0.81 · 0.79/0.96)
293
- array_log1p_ptr: { min: 1024, max: 16384 },
294
- // 0.82/0.88 · (1.09/1.24 ...)
295
- array_cos_ptr: { min: 16384 },
296
- // (1.54/0.79) · 0.64/0.61 · 0.62/0.62 · 0.79/0.69
297
- array_atanh_ptr: { min: 16384 },
298
- // (0.93/0.85) · 0.70/0.73 · 0.77/0.78 · 0.81/0.83
299
- array_log_ptr: { min: 16384 },
300
- // (0.92/0.86) · 0.80/0.77 · 0.80/0.79 · 0.84/0.83
301
- array_sec_ptr: { min: 16384, max: 1048576 },
302
- // 0.76/0.79 · 0.76/0.83 · (0.90/0.88)
303
- // A fused chain keeps its data in WASM memory between ops: (sin, exp) 0.36-0.49 and
304
- // (tanh, expm1), both of which lose alone, 0.64-0.77, at every size.
305
- fused_chain: { min: 1024 },
306
- // Least-squares fits (public polyFit / chebyshevFit / legendreFit): 0.34-0.67.
307
- poly_fit_f64: { min: 1024 },
308
- cheb_fit_f64: { min: 1024 },
309
- legendre_fit_f64: { min: 1024 },
310
- // Only the largest measured size wins: lgamma 0.77/0.78, sort (median, quantile)
311
- // 0.78/0.81 and 0.77/0.79 at 1M; 131K was 0.90-1.05.
312
- lgamma_f64: { min: 1048576 },
313
- sort_f64: { min: 1048576 }
314
- };
315
- var overrides = null;
316
- function wasmPolicyAllows(kernel, n) {
317
- const own = (o, k) => Object.prototype.hasOwnProperty.call(o, k);
318
- const band = overrides !== null && own(overrides, kernel) ? overrides[kernel] : overrides !== null && own(overrides, "*") ? overrides["*"] : WASM_DISPATCH_POLICY[kernel];
319
- return band != null && n >= band.min && (band.max === void 0 || n < band.max);
320
- }
321
-
322
- // src/wasm/bridges/common.ts
323
- function getWasm() {
324
- try {
325
- return wasmLoader.getModule();
326
- } catch {
327
- return null;
328
- }
329
- }
330
- function isAsWasm(wasm) {
331
- return !!wasm && typeof wasm["array_sin_ptr"] === "function";
332
- }
333
- var scratchBase = -1;
334
- function ensureScratch(mem, need) {
335
- if (scratchBase < 0) scratchBase = mem.buffer.byteLength;
336
- if (scratchBase + need > mem.buffer.byteLength) {
337
- mem.grow(Math.ceil((scratchBase + need - mem.buffer.byteLength) / 65536));
338
- }
339
- return scratchBase;
340
- }
341
- function runUnaryPtr(mem, fn, xs) {
342
- const n = xs.length;
343
- try {
344
- const need = 2 * n * 8;
345
- const base = ensureScratch(mem, need);
346
- const inOff = base;
347
- const outOff = base + n * 8;
348
- new Float64Array(mem.buffer, inOff, n).set(xs);
349
- fn(inOff, outOff, n);
350
- const result = new Float64Array(n);
351
- result.set(new Float64Array(mem.buffer, outOff, n));
352
- return result;
353
- } catch {
354
- return null;
355
- }
356
- }
357
- function runChainPtr(mem, fns, xs) {
358
- const n = xs.length;
359
- try {
360
- const need = 2 * n * 8;
361
- const base = ensureScratch(mem, need);
362
- const bufA = base;
363
- const bufB = base + n * 8;
364
- new Float64Array(mem.buffer, bufA, n).set(xs);
365
- let cur = bufA;
366
- let other = bufB;
367
- for (const fn of fns) {
368
- fn(cur, other, n);
369
- const t = cur;
370
- cur = other;
371
- other = t;
372
- }
373
- const result = new Float64Array(n);
374
- result.set(new Float64Array(mem.buffer, cur, n));
375
- return result;
376
- } catch {
377
- return null;
378
- }
379
- }
380
- var AS_ID_ARRAY_BUFFER = 1;
381
- var AS_ID_FLOAT64_ARRAY = 5;
382
- var AS_ID_INT32_ARRAY = 6;
383
- var AS_HEADER_BYTES = 12;
384
- function resetAsHeap(mod) {
385
- if (typeof mod.heap_reset === "function") mod.heap_reset();
386
- }
387
- function asAllocHeader(mod, byteLength, typeId) {
388
- const bufferPtr = mod.__pin(mod.__new(byteLength, AS_ID_ARRAY_BUFFER)) >>> 0;
389
- const headerPtr = mod.__new(AS_HEADER_BYTES, typeId) >>> 0;
390
- mod.__pin(headerPtr);
391
- const dv = new DataView(mod.memory.buffer);
392
- dv.setUint32(headerPtr + 0, bufferPtr, true);
393
- dv.setUint32(headerPtr + 4, bufferPtr, true);
394
- dv.setUint32(headerPtr + 8, byteLength, true);
395
- return { headerPtr, bufferPtr };
396
- }
397
- function asUnpin(mod, a) {
398
- mod.__unpin(a.headerPtr);
399
- mod.__unpin(a.bufferPtr);
400
- }
401
- function asReadReturnedF64(mod, headerPtr) {
402
- const dv = new DataView(mod.memory.buffer);
403
- const dataStart = dv.getUint32((headerPtr >>> 0) + 4, true);
404
- const byteLength = dv.getUint32((headerPtr >>> 0) + 8, true);
405
- return new Float64Array(new Float64Array(mod.memory.buffer, dataStart, byteLength >>> 3));
406
- }
407
- function asReadReturnedI32(mod, headerPtr) {
408
- const dv = new DataView(mod.memory.buffer);
409
- const dataStart = dv.getUint32((headerPtr >>> 0) + 4, true);
410
- const byteLength = dv.getUint32((headerPtr >>> 0) + 8, true);
411
- return new Int32Array(new Int32Array(mod.memory.buffer, dataStart, byteLength >>> 2));
412
- }
413
- function withAsF64(wasm, inputs, body) {
414
- const mod = wasm;
415
- if (typeof mod.__new !== "function" || typeof mod.__unpin !== "function") return null;
416
- const allocs = [];
417
- try {
418
- const headers = [];
419
- for (const arr of inputs) {
420
- const a = asAllocHeader(mod, arr.length * 8, AS_ID_FLOAT64_ARRAY);
421
- new Float64Array(mod.memory.buffer, a.bufferPtr, arr.length).set(arr);
422
- allocs.push(a);
423
- headers.push(a.headerPtr);
424
- }
425
- return body(mod, headers);
426
- } catch {
427
- return null;
428
- } finally {
429
- for (const a of allocs) {
430
- try {
431
- asUnpin(mod, a);
432
- } catch {
433
- }
434
- }
435
- try {
436
- resetAsHeap(mod);
437
- } catch {
438
- }
439
- }
440
- }
441
- function withAsI32(wasm, inputs, body) {
442
- const mod = wasm;
443
- if (typeof mod.__new !== "function" || typeof mod.__unpin !== "function") return null;
444
- const allocs = [];
445
- try {
446
- const headers = [];
447
- for (const arr of inputs) {
448
- const a = asAllocHeader(mod, arr.length * 4, AS_ID_INT32_ARRAY);
449
- new Int32Array(mod.memory.buffer, a.bufferPtr, arr.length).set(arr);
450
- allocs.push(a);
451
- headers.push(a.headerPtr);
452
- }
453
- return body(mod, headers);
454
- } catch {
455
- return null;
456
- } finally {
457
- for (const a of allocs) {
458
- try {
459
- asUnpin(mod, a);
460
- } catch {
461
- }
462
- }
463
- try {
464
- resetAsHeap(mod);
465
- } catch {
466
- }
467
- }
468
- }
469
- function makeUnaryArrayDispatch(cfg) {
470
- return (xs) => {
471
- if (xs.length >= cfg.threshold && wasmPolicyAllows(cfg.name, xs.length)) {
472
- const wasm = getWasm();
473
- if (wasm && isAsWasm(wasm)) {
474
- const out = withAsF64(
475
- wasm,
476
- [xs],
477
- (mod, [h]) => asReadReturnedF64(mod, mod[cfg.name](h))
478
- );
479
- if (out) return out;
480
- }
481
- }
482
- return cfg.js(xs);
483
- };
484
- }
485
-
486
- // src/wasm/sort/wasm-bridge.ts
487
- var WASM_SORT_THRESHOLD = 16384;
488
- function cmpNanLast(a, b) {
489
- if (a < b) return -1;
490
- if (a > b) return 1;
491
- if (a === b) return 0;
492
- if (Number.isNaN(a) && Number.isNaN(b)) return 0;
493
- if (Number.isNaN(a)) return 1;
494
- return -1;
495
- }
496
- function sortF64JS(data) {
497
- const arr = Array.from(data);
498
- arr.sort(cmpNanLast);
499
- for (let i = 0; i < arr.length; i++) data[i] = arr[i];
500
- return data;
501
- }
502
- function argsortF64JS(data) {
503
- const n = data.length;
504
- const indices = new Int32Array(n);
505
- for (let i = 0; i < n; i++) indices[i] = i;
506
- const arr = Array.from(indices);
507
- arr.sort((i, j) => cmpNanLast(data[i], data[j]));
508
- for (let k = 0; k < n; k++) indices[k] = arr[k];
509
- return indices;
510
- }
511
- function rankF64JS(data) {
512
- const n = data.length;
513
- const argsort = argsortF64JS(data);
514
- const rank = new Int32Array(n);
515
- for (let k = 0; k < n; k++) rank[argsort[k]] = k;
516
- return rank;
517
- }
518
- function sortF64Dispatch(data) {
519
- const n = data.length;
520
- if (n >= WASM_SORT_THRESHOLD && wasmPolicyAllows("sort_f64", n)) {
521
- const wasm = getWasm();
522
- if (wasm && isAsWasm(wasm)) {
523
- try {
524
- const sorted = withAsF64(
525
- wasm,
526
- [data],
527
- (mod, [h]) => asReadReturnedF64(mod, mod["sort_f64"](h))
528
- );
529
- if (sorted && sorted.length === n) {
530
- data.set(sorted);
531
- return data;
532
- }
533
- } catch {
534
- }
535
- }
536
- }
537
- return sortF64JS(data);
538
- }
539
- function argsortF64Dispatch(data) {
540
- const n = data.length;
541
- if (n >= WASM_SORT_THRESHOLD && wasmPolicyAllows("argsort_f64", n)) {
542
- const wasm = getWasm();
543
- if (wasm && isAsWasm(wasm)) {
544
- try {
545
- const idx = withAsF64(
546
- wasm,
547
- [data],
548
- (mod, [h]) => asReadReturnedI32(mod, mod["argsort_f64"](h))
549
- );
550
- if (idx && idx.length === n) return idx;
551
- } catch {
552
- }
553
- }
554
- }
555
- return argsortF64JS(data);
556
- }
557
- function rankF64Dispatch(data) {
558
- const n = data.length;
559
- if (n >= WASM_SORT_THRESHOLD && wasmPolicyAllows("rank_f64", n)) {
560
- const wasm = getWasm();
561
- if (wasm && isAsWasm(wasm)) {
562
- try {
563
- const ranks = withAsF64(
564
- wasm,
565
- [data],
566
- (mod, [h]) => asReadReturnedI32(mod, mod["rank_f64"](h))
567
- );
568
- if (ranks && ranks.length === n) return ranks;
569
- } catch {
570
- }
571
- }
572
- }
573
- return rankF64JS(data);
574
- }
575
-
576
- export {
577
- __export,
578
- loadWasm,
579
- isWasmLoaded,
580
- wasmPolicyAllows,
581
- getWasm,
582
- isAsWasm,
583
- runUnaryPtr,
584
- runChainPtr,
585
- asReadReturnedF64,
586
- asReadReturnedI32,
587
- withAsF64,
588
- withAsI32,
589
- makeUnaryArrayDispatch,
590
- WASM_SORT_THRESHOLD,
591
- sortF64JS,
592
- argsortF64JS,
593
- rankF64JS,
594
- sortF64Dispatch,
595
- argsortF64Dispatch,
596
- rankF64Dispatch
597
- };
@@ -1,18 +0,0 @@
1
- import {
2
- WASM_SORT_THRESHOLD,
3
- argsortF64Dispatch,
4
- argsortF64JS,
5
- rankF64Dispatch,
6
- rankF64JS,
7
- sortF64Dispatch,
8
- sortF64JS
9
- } from "./chunk-5A2EZLXV.js";
10
- export {
11
- WASM_SORT_THRESHOLD,
12
- argsortF64Dispatch,
13
- argsortF64JS,
14
- rankF64Dispatch,
15
- rankF64JS,
16
- sortF64Dispatch,
17
- sortF64JS
18
- };