@tailwindcss/oxide-wasm32-wasi 0.0.0-insiders.bd9cf92 → 0.0.0-insiders.bdcd708
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.
- package/node_modules/@emnapi/core/dist/emnapi-core.cjs.js +1469 -511
- package/node_modules/@emnapi/core/dist/emnapi-core.cjs.min.d.ts +61 -5
- package/node_modules/@emnapi/core/dist/emnapi-core.cjs.min.js +1 -1
- package/node_modules/@emnapi/core/dist/emnapi-core.d.mts +61 -5
- package/node_modules/@emnapi/core/dist/emnapi-core.d.ts +61 -5
- package/node_modules/@emnapi/core/dist/emnapi-core.esm-bundler.js +1628 -523
- package/node_modules/@emnapi/core/dist/emnapi-core.js +1705 -585
- package/node_modules/@emnapi/core/dist/emnapi-core.min.d.mts +61 -5
- package/node_modules/@emnapi/core/dist/emnapi-core.min.js +1 -1
- package/node_modules/@emnapi/core/dist/emnapi-core.min.mjs +1 -1
- package/node_modules/@emnapi/core/dist/emnapi-core.mjs +1469 -511
- package/node_modules/@emnapi/core/package.json +2 -2
- package/node_modules/@emnapi/runtime/dist/emnapi.cjs.js +44 -14
- package/node_modules/@emnapi/runtime/dist/emnapi.cjs.min.d.ts +15 -7
- package/node_modules/@emnapi/runtime/dist/emnapi.cjs.min.js +1 -1
- package/node_modules/@emnapi/runtime/dist/emnapi.d.mts +15 -7
- package/node_modules/@emnapi/runtime/dist/emnapi.d.ts +15 -7
- package/node_modules/@emnapi/runtime/dist/emnapi.esm-bundler.js +45 -14
- package/node_modules/@emnapi/runtime/dist/emnapi.iife.d.ts +12 -6
- package/node_modules/@emnapi/runtime/dist/emnapi.iife.js +45 -14
- package/node_modules/@emnapi/runtime/dist/emnapi.js +45 -14
- package/node_modules/@emnapi/runtime/dist/emnapi.min.d.mts +15 -7
- package/node_modules/@emnapi/runtime/dist/emnapi.min.js +1 -1
- package/node_modules/@emnapi/runtime/dist/emnapi.min.mjs +1 -1
- package/node_modules/@emnapi/runtime/dist/emnapi.mjs +44 -14
- package/node_modules/@emnapi/runtime/package.json +1 -1
- package/node_modules/@emnapi/wasi-threads/dist/wasi-threads.cjs.js +67 -63
- package/node_modules/@emnapi/wasi-threads/dist/wasi-threads.cjs.min.d.ts +59 -2
- package/node_modules/@emnapi/wasi-threads/dist/wasi-threads.cjs.min.js +1 -1
- package/node_modules/@emnapi/wasi-threads/dist/wasi-threads.d.mts +59 -2
- package/node_modules/@emnapi/wasi-threads/dist/wasi-threads.d.ts +59 -2
- package/node_modules/@emnapi/wasi-threads/dist/wasi-threads.esm-bundler.js +67 -63
- package/node_modules/@emnapi/wasi-threads/dist/wasi-threads.js +67 -63
- package/node_modules/@emnapi/wasi-threads/dist/wasi-threads.min.d.mts +59 -2
- package/node_modules/@emnapi/wasi-threads/dist/wasi-threads.min.js +1 -1
- package/node_modules/@emnapi/wasi-threads/dist/wasi-threads.min.mjs +1 -1
- package/node_modules/@emnapi/wasi-threads/dist/wasi-threads.mjs +67 -63
- package/node_modules/@emnapi/wasi-threads/package.json +1 -1
- package/node_modules/@napi-rs/wasm-runtime/dist/fs-proxy.cjs +299 -0
- package/node_modules/@napi-rs/wasm-runtime/dist/fs.js +22125 -20726
- package/node_modules/@napi-rs/wasm-runtime/fs-proxy.js +294 -0
- package/node_modules/@napi-rs/wasm-runtime/package.json +25 -16
- package/node_modules/@napi-rs/wasm-runtime/runtime.cjs +1 -1
- package/node_modules/@napi-rs/wasm-runtime/runtime.js +8 -0
- package/node_modules/@tybys/wasm-util/dist/wasm-util.d.ts +6 -0
- package/node_modules/@tybys/wasm-util/dist/wasm-util.esm-bundler.js +215 -33
- package/node_modules/@tybys/wasm-util/dist/wasm-util.esm.js +215 -33
- package/node_modules/@tybys/wasm-util/dist/wasm-util.esm.min.js +1 -1
- package/node_modules/@tybys/wasm-util/dist/wasm-util.js +215 -33
- package/node_modules/@tybys/wasm-util/dist/wasm-util.min.js +1 -1
- package/node_modules/@tybys/wasm-util/lib/cjs/wasi/index.js +12 -14
- package/node_modules/@tybys/wasm-util/lib/cjs/wasi/path.js +142 -0
- package/node_modules/@tybys/wasm-util/lib/cjs/wasi/preview1.js +61 -19
- package/node_modules/@tybys/wasm-util/lib/mjs/wasi/index.mjs +12 -14
- package/node_modules/@tybys/wasm-util/lib/mjs/wasi/path.mjs +142 -0
- package/node_modules/@tybys/wasm-util/lib/mjs/wasi/preview1.mjs +61 -19
- package/node_modules/@tybys/wasm-util/package.json +1 -1
- package/node_modules/tslib/package.json +1 -1
- package/node_modules/tslib/tslib.es6.js +10 -1
- package/node_modules/tslib/tslib.es6.mjs +10 -1
- package/node_modules/tslib/tslib.js +42 -33
- package/package.json +7 -7
- package/tailwindcss-oxide.wasi-browser.js +7 -3
- package/tailwindcss-oxide.wasi.cjs +27 -4
- package/tailwindcss-oxide.wasm32-wasi.wasm +0 -0
- package/wasi-worker-browser.mjs +2 -0
- package/node_modules/@napi-rs/wasm-runtime/LICENSE +0 -43
- package/node_modules/@napi-rs/wasm-runtime/dist/runtime.js +0 -12285
- package/node_modules/@napi-rs/wasm-runtime/fs-proxy.cjs +0 -209
|
@@ -123,7 +123,6 @@ class ThreadManager {
|
|
|
123
123
|
constructor(options) {
|
|
124
124
|
var _a;
|
|
125
125
|
this.unusedWorkers = [];
|
|
126
|
-
this.runningWorkers = [];
|
|
127
126
|
this.pthreads = Object.create(null);
|
|
128
127
|
this.wasmModule = null;
|
|
129
128
|
this.wasmMemory = null;
|
|
@@ -148,6 +147,7 @@ class ThreadManager {
|
|
|
148
147
|
this._beforeLoad = options.beforeLoad;
|
|
149
148
|
}
|
|
150
149
|
this.printErr = (_a = options.printErr) !== null && _a !== void 0 ? _a : console.error.bind(console);
|
|
150
|
+
this.threadSpawn = options.threadSpawn;
|
|
151
151
|
}
|
|
152
152
|
init() {
|
|
153
153
|
if (!this._childThread) {
|
|
@@ -220,7 +220,6 @@ class ThreadManager {
|
|
|
220
220
|
delete this.pthreads[tid];
|
|
221
221
|
}
|
|
222
222
|
this.unusedWorkers.push(worker);
|
|
223
|
-
this.runningWorkers.splice(this.runningWorkers.indexOf(worker), 1);
|
|
224
223
|
delete worker.__emnapi_tid;
|
|
225
224
|
if (ENVIRONMENT_IS_NODE) {
|
|
226
225
|
worker.unref();
|
|
@@ -238,12 +237,17 @@ class ThreadManager {
|
|
|
238
237
|
if (worker.__emnapi_tid !== undefined) {
|
|
239
238
|
message = 'worker (tid = ' + worker.__emnapi_tid + ') sent an error!';
|
|
240
239
|
}
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
240
|
+
if ('message' in e) {
|
|
241
|
+
err(message + ' ' + e.message);
|
|
242
|
+
if (e.message.indexOf('RuntimeError') !== -1 || e.message.indexOf('unreachable') !== -1) {
|
|
243
|
+
try {
|
|
244
|
+
_this.terminateAllThreads();
|
|
245
|
+
}
|
|
246
|
+
catch (_) { }
|
|
245
247
|
}
|
|
246
|
-
|
|
248
|
+
}
|
|
249
|
+
else {
|
|
250
|
+
err(message);
|
|
247
251
|
}
|
|
248
252
|
reject(e);
|
|
249
253
|
throw e;
|
|
@@ -264,6 +268,12 @@ class ThreadManager {
|
|
|
264
268
|
this.cleanThread(worker, payload.tid);
|
|
265
269
|
}
|
|
266
270
|
}
|
|
271
|
+
else if (type === 'spawn-thread') {
|
|
272
|
+
this.threadSpawn(payload.startArg, payload.errorOrTid);
|
|
273
|
+
}
|
|
274
|
+
else if (type === 'terminate-all-threads') {
|
|
275
|
+
this.terminateAllThreads();
|
|
276
|
+
}
|
|
267
277
|
}
|
|
268
278
|
};
|
|
269
279
|
worker.onmessage = (e) => {
|
|
@@ -336,10 +346,6 @@ class ThreadManager {
|
|
|
336
346
|
}
|
|
337
347
|
else {
|
|
338
348
|
delete this.pthreads[tid];
|
|
339
|
-
const index = this.runningWorkers.indexOf(worker);
|
|
340
|
-
if (index !== -1) {
|
|
341
|
-
this.runningWorkers.splice(index, 1);
|
|
342
|
-
}
|
|
343
349
|
this.terminateWorker(worker);
|
|
344
350
|
delete worker.__emnapi_tid;
|
|
345
351
|
}
|
|
@@ -358,14 +364,14 @@ class ThreadManager {
|
|
|
358
364
|
};
|
|
359
365
|
}
|
|
360
366
|
terminateAllThreads() {
|
|
361
|
-
|
|
362
|
-
|
|
367
|
+
const runningWorkers = Object.values(this.pthreads);
|
|
368
|
+
for (let i = 0; i < runningWorkers.length; ++i) {
|
|
369
|
+
this.terminateWorker(runningWorkers[i]);
|
|
363
370
|
}
|
|
364
371
|
for (let i = 0; i < this.unusedWorkers.length; ++i) {
|
|
365
372
|
this.terminateWorker(this.unusedWorkers[i]);
|
|
366
373
|
}
|
|
367
374
|
this.unusedWorkers = [];
|
|
368
|
-
this.runningWorkers = [];
|
|
369
375
|
this.pthreads = Object.create(null);
|
|
370
376
|
this.preparePool();
|
|
371
377
|
}
|
|
@@ -507,18 +513,6 @@ class WASIThreads {
|
|
|
507
513
|
}
|
|
508
514
|
this.postMessage = postMessage;
|
|
509
515
|
const wasm64 = Boolean(options.wasm64);
|
|
510
|
-
const onMessage = (e) => {
|
|
511
|
-
if (e.data.__emnapi__) {
|
|
512
|
-
const type = e.data.__emnapi__.type;
|
|
513
|
-
const payload = e.data.__emnapi__.payload;
|
|
514
|
-
if (type === 'spawn-thread') {
|
|
515
|
-
threadSpawn(payload.startArg, payload.errorOrTid);
|
|
516
|
-
}
|
|
517
|
-
else if (type === 'terminate-all-threads') {
|
|
518
|
-
this.terminateAllThreads();
|
|
519
|
-
}
|
|
520
|
-
}
|
|
521
|
-
};
|
|
522
516
|
const threadSpawn = (startArg, errorOrTid) => {
|
|
523
517
|
var _a;
|
|
524
518
|
const EAGAIN = 6;
|
|
@@ -536,12 +530,12 @@ class WASIThreads {
|
|
|
536
530
|
return 1;
|
|
537
531
|
}
|
|
538
532
|
else {
|
|
539
|
-
return -
|
|
533
|
+
return -EAGAIN;
|
|
540
534
|
}
|
|
541
535
|
}
|
|
542
536
|
if (!isNewABI) {
|
|
543
537
|
const malloc = this.wasmInstance.exports.malloc;
|
|
544
|
-
errorOrTid = wasm64 ? Number(malloc(BigInt(8))) : malloc(8);
|
|
538
|
+
errorOrTid = wasm64 ? Number(malloc(BigInt(8))) : (malloc(8) >>> 0);
|
|
545
539
|
if (!errorOrTid) {
|
|
546
540
|
return -48;
|
|
547
541
|
}
|
|
@@ -579,10 +573,9 @@ class WASIThreads {
|
|
|
579
573
|
if (!worker) {
|
|
580
574
|
throw new Error('failed to get new worker');
|
|
581
575
|
}
|
|
582
|
-
PThread.addMessageEventListener(worker, onMessage);
|
|
583
576
|
tid = PThread.markId(worker);
|
|
584
577
|
if (ENVIRONMENT_IS_NODE) {
|
|
585
|
-
worker.
|
|
578
|
+
worker.unref();
|
|
586
579
|
}
|
|
587
580
|
worker.postMessage(createMessage('start', {
|
|
588
581
|
tid,
|
|
@@ -593,10 +586,6 @@ class WASIThreads {
|
|
|
593
586
|
if (typeof waitThreadStart === 'number') {
|
|
594
587
|
const waitResult = Atomics.wait(sab, 0, 0, waitThreadStart);
|
|
595
588
|
if (waitResult === 'timed-out') {
|
|
596
|
-
try {
|
|
597
|
-
PThread.cleanThread(worker, tid, true);
|
|
598
|
-
}
|
|
599
|
-
catch (_) { }
|
|
600
589
|
throw new Error('Spawning thread timed out. Please check if the worker is created successfully and if message is handled properly in the worker.');
|
|
601
590
|
}
|
|
602
591
|
}
|
|
@@ -605,15 +594,17 @@ class WASIThreads {
|
|
|
605
594
|
}
|
|
606
595
|
const r = Atomics.load(sab, 0);
|
|
607
596
|
if (r > 1) {
|
|
608
|
-
try {
|
|
609
|
-
PThread.cleanThread(worker, tid, true);
|
|
610
|
-
}
|
|
611
|
-
catch (_) { }
|
|
612
597
|
throw deserizeErrorFromBuffer(sab.buffer);
|
|
613
598
|
}
|
|
614
599
|
}
|
|
615
600
|
}
|
|
616
601
|
catch (e) {
|
|
602
|
+
if (worker !== undefined && tid !== undefined) {
|
|
603
|
+
try {
|
|
604
|
+
PThread.cleanThread(worker, tid, true);
|
|
605
|
+
}
|
|
606
|
+
catch (_) { }
|
|
607
|
+
}
|
|
617
608
|
Atomics.store(struct, 0, 1);
|
|
618
609
|
Atomics.store(struct, 1, EAGAIN);
|
|
619
610
|
Atomics.notify(struct, 1);
|
|
@@ -622,12 +613,11 @@ class WASIThreads {
|
|
|
622
613
|
return 1;
|
|
623
614
|
}
|
|
624
615
|
free(errorOrTid);
|
|
625
|
-
return -
|
|
616
|
+
return -EAGAIN;
|
|
626
617
|
}
|
|
627
618
|
Atomics.store(struct, 0, 0);
|
|
628
619
|
Atomics.store(struct, 1, tid);
|
|
629
620
|
Atomics.notify(struct, 1);
|
|
630
|
-
PThread.runningWorkers.push(worker);
|
|
631
621
|
if (!shouldWait) {
|
|
632
622
|
worker.whenLoaded.catch((err) => {
|
|
633
623
|
delete worker.whenLoaded;
|
|
@@ -642,6 +632,9 @@ class WASIThreads {
|
|
|
642
632
|
return tid;
|
|
643
633
|
};
|
|
644
634
|
this.threadSpawn = threadSpawn;
|
|
635
|
+
if (this.PThread) {
|
|
636
|
+
this.PThread.threadSpawn = threadSpawn;
|
|
637
|
+
}
|
|
645
638
|
}
|
|
646
639
|
getImportObject() {
|
|
647
640
|
return {
|
|
@@ -724,19 +717,21 @@ function patchWasiInstance(wasiThreads, wasi) {
|
|
|
724
717
|
return proc_exit.call(this, code);
|
|
725
718
|
};
|
|
726
719
|
}
|
|
727
|
-
|
|
728
|
-
|
|
729
|
-
|
|
730
|
-
|
|
731
|
-
|
|
732
|
-
|
|
733
|
-
catch (err) {
|
|
734
|
-
if (isTrapError(err)) {
|
|
735
|
-
_this.terminateAllThreads();
|
|
720
|
+
if (!_this.childThread) {
|
|
721
|
+
const start = wasi.start;
|
|
722
|
+
if (typeof start === 'function') {
|
|
723
|
+
wasi.start = function (instance) {
|
|
724
|
+
try {
|
|
725
|
+
return start.call(this, instance);
|
|
736
726
|
}
|
|
737
|
-
|
|
738
|
-
|
|
739
|
-
|
|
727
|
+
catch (err) {
|
|
728
|
+
if (isTrapError(err)) {
|
|
729
|
+
_this.terminateAllThreads();
|
|
730
|
+
}
|
|
731
|
+
throw err;
|
|
732
|
+
}
|
|
733
|
+
};
|
|
734
|
+
}
|
|
740
735
|
}
|
|
741
736
|
patched.add(wasi);
|
|
742
737
|
}
|
|
@@ -767,6 +762,7 @@ class ThreadMessageHandler {
|
|
|
767
762
|
}
|
|
768
763
|
this.postMessage = postMsg;
|
|
769
764
|
this.onLoad = options === null || options === void 0 ? void 0 : options.onLoad;
|
|
765
|
+
this.onError = typeof (options === null || options === void 0 ? void 0 : options.onError) === 'function' ? options.onError : (_type, err) => { throw err; };
|
|
770
766
|
this.instance = undefined;
|
|
771
767
|
this.messagesBeforeLoad = [];
|
|
772
768
|
}
|
|
@@ -781,13 +777,18 @@ class ThreadMessageHandler {
|
|
|
781
777
|
if ((_a = e === null || e === void 0 ? void 0 : e.data) === null || _a === void 0 ? void 0 : _a.__emnapi__) {
|
|
782
778
|
const type = e.data.__emnapi__.type;
|
|
783
779
|
const payload = e.data.__emnapi__.payload;
|
|
784
|
-
|
|
785
|
-
|
|
780
|
+
try {
|
|
781
|
+
if (type === 'load') {
|
|
782
|
+
this._load(payload);
|
|
783
|
+
}
|
|
784
|
+
else if (type === 'start') {
|
|
785
|
+
this.handleAfterLoad(e, () => {
|
|
786
|
+
this._start(payload);
|
|
787
|
+
});
|
|
788
|
+
}
|
|
786
789
|
}
|
|
787
|
-
|
|
788
|
-
this.
|
|
789
|
-
this._start(payload);
|
|
790
|
-
});
|
|
790
|
+
catch (err) {
|
|
791
|
+
this.onError(err, type);
|
|
791
792
|
}
|
|
792
793
|
}
|
|
793
794
|
}
|
|
@@ -811,7 +812,8 @@ class ThreadMessageHandler {
|
|
|
811
812
|
}
|
|
812
813
|
}
|
|
813
814
|
_start(payload) {
|
|
814
|
-
|
|
815
|
+
const wasi_thread_start = this.instance.exports.wasi_thread_start;
|
|
816
|
+
if (typeof wasi_thread_start !== 'function') {
|
|
815
817
|
const err = new TypeError('wasi_thread_start is not exported');
|
|
816
818
|
notifyPthreadCreateResult(payload.sab, 2, err);
|
|
817
819
|
throw err;
|
|
@@ -821,13 +823,15 @@ class ThreadMessageHandler {
|
|
|
821
823
|
const startArg = payload.arg;
|
|
822
824
|
notifyPthreadCreateResult(payload.sab, 1);
|
|
823
825
|
try {
|
|
824
|
-
|
|
826
|
+
wasi_thread_start(tid, startArg);
|
|
825
827
|
}
|
|
826
828
|
catch (err) {
|
|
827
|
-
if (
|
|
828
|
-
|
|
829
|
+
if (err !== 'unwind') {
|
|
830
|
+
throw err;
|
|
831
|
+
}
|
|
832
|
+
else {
|
|
833
|
+
return;
|
|
829
834
|
}
|
|
830
|
-
throw err;
|
|
831
835
|
}
|
|
832
836
|
postMessage(createMessage('cleanup-thread', { tid }));
|
|
833
837
|
}
|
|
@@ -0,0 +1,299 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
// @ts-check
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* @param {unknown} value
|
|
7
|
+
*/
|
|
8
|
+
const getType = (value) => {
|
|
9
|
+
if (value === undefined) return 0
|
|
10
|
+
if (value === null) return 1
|
|
11
|
+
const t = typeof value;
|
|
12
|
+
if (t === 'boolean') return 2
|
|
13
|
+
if (t === 'number') return 3
|
|
14
|
+
if (t === 'string') return 4
|
|
15
|
+
if (t === 'object') return 6
|
|
16
|
+
if (t === 'bigint') return 9
|
|
17
|
+
return -1
|
|
18
|
+
};
|
|
19
|
+
|
|
20
|
+
const RESPONSE_HEADER_SIZE = 16;
|
|
21
|
+
const RESPONSE_PAYLOAD_SIZE = 10240;
|
|
22
|
+
const RESPONSE_BUFFER_SIZE = RESPONSE_HEADER_SIZE + RESPONSE_PAYLOAD_SIZE;
|
|
23
|
+
|
|
24
|
+
/**
|
|
25
|
+
* @param {Int32Array} sab
|
|
26
|
+
* @param {Uint8Array} payload
|
|
27
|
+
*/
|
|
28
|
+
const writeResponsePayload = (sab, payload) => {
|
|
29
|
+
if (payload.length > RESPONSE_PAYLOAD_SIZE) {
|
|
30
|
+
throw new RangeError('payload overflow')
|
|
31
|
+
}
|
|
32
|
+
new Uint8Array(sab.buffer).set(payload, RESPONSE_HEADER_SIZE);
|
|
33
|
+
};
|
|
34
|
+
|
|
35
|
+
/**
|
|
36
|
+
* @param {import('memfs').IFs} memfs
|
|
37
|
+
* @param {any} value
|
|
38
|
+
* @param {ReturnType<typeof getType>} type
|
|
39
|
+
* @returns {Uint8Array}
|
|
40
|
+
*/
|
|
41
|
+
const encodeValue = (memfs, value, type) => {
|
|
42
|
+
switch (type) {
|
|
43
|
+
case 0:
|
|
44
|
+
case 1:
|
|
45
|
+
return new Uint8Array(0)
|
|
46
|
+
case 2: {
|
|
47
|
+
const view = new Int32Array(1);
|
|
48
|
+
view[0] = value ? 1 : 0;
|
|
49
|
+
return new Uint8Array(view.buffer)
|
|
50
|
+
}
|
|
51
|
+
case 3: {
|
|
52
|
+
const view = new Float64Array(1);
|
|
53
|
+
view[0] = value;
|
|
54
|
+
return new Uint8Array(view.buffer)
|
|
55
|
+
}
|
|
56
|
+
case 4: {
|
|
57
|
+
const view = new TextEncoder().encode(value);
|
|
58
|
+
return view
|
|
59
|
+
}
|
|
60
|
+
case 6: {
|
|
61
|
+
function storeConstructor(obj, memfs, processed = new WeakSet()) {
|
|
62
|
+
if (!obj || typeof obj !== 'object') {
|
|
63
|
+
return
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
if (processed.has(obj)) {
|
|
67
|
+
return
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
processed.add(obj);
|
|
71
|
+
|
|
72
|
+
const [entry] =
|
|
73
|
+
Object.entries(memfs).filter(([_, v]) => v === obj.constructor)[0] ??
|
|
74
|
+
[];
|
|
75
|
+
if (entry) {
|
|
76
|
+
Object.defineProperty(obj, '__constructor__', {
|
|
77
|
+
configurable: true,
|
|
78
|
+
writable: true,
|
|
79
|
+
enumerable: true,
|
|
80
|
+
value: entry,
|
|
81
|
+
});
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
for (const value of Object.values(obj)) {
|
|
85
|
+
storeConstructor(value, memfs, processed);
|
|
86
|
+
}
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
storeConstructor(value, memfs);
|
|
90
|
+
|
|
91
|
+
const json = JSON.stringify(value, (_, value) => {
|
|
92
|
+
if (typeof value === 'bigint') {
|
|
93
|
+
return `BigInt(${String(value)})`
|
|
94
|
+
}
|
|
95
|
+
if (value instanceof Error) {
|
|
96
|
+
return {
|
|
97
|
+
...value,
|
|
98
|
+
message: value.message,
|
|
99
|
+
stack: value.stack,
|
|
100
|
+
__error__: value.constructor.name,
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
return value
|
|
104
|
+
});
|
|
105
|
+
const view = new TextEncoder().encode(json);
|
|
106
|
+
return view
|
|
107
|
+
}
|
|
108
|
+
case 9: {
|
|
109
|
+
return new TextEncoder().encode(String(value))
|
|
110
|
+
}
|
|
111
|
+
case -1:
|
|
112
|
+
default:
|
|
113
|
+
throw new Error('unsupported data')
|
|
114
|
+
}
|
|
115
|
+
};
|
|
116
|
+
|
|
117
|
+
/**
|
|
118
|
+
* @param {typeof import('memfs')} memfs
|
|
119
|
+
* @param {Uint8Array} payload
|
|
120
|
+
* @param {number} type
|
|
121
|
+
* @returns {any}
|
|
122
|
+
*/
|
|
123
|
+
const decodeValue = (memfs, payload, type) => {
|
|
124
|
+
if (type === 0) return undefined
|
|
125
|
+
if (type === 1) return null
|
|
126
|
+
if (type === 2)
|
|
127
|
+
return Boolean(new Int32Array(payload.buffer, payload.byteOffset, 1)[0])
|
|
128
|
+
if (type === 3)
|
|
129
|
+
return new Float64Array(payload.buffer, payload.byteOffset, 1)[0]
|
|
130
|
+
if (type === 4) return new TextDecoder().decode(payload.slice())
|
|
131
|
+
if (type === 6) {
|
|
132
|
+
const obj = JSON.parse(
|
|
133
|
+
new TextDecoder().decode(payload.slice()),
|
|
134
|
+
(_key, value) => {
|
|
135
|
+
if (typeof value === 'string') {
|
|
136
|
+
const matched = value.match(/^BigInt\((-?\d+)\)$/);
|
|
137
|
+
if (matched && matched[1]) {
|
|
138
|
+
return BigInt(matched[1])
|
|
139
|
+
}
|
|
140
|
+
}
|
|
141
|
+
return value
|
|
142
|
+
},
|
|
143
|
+
);
|
|
144
|
+
|
|
145
|
+
function loadConstructor(obj, memfs, processed = new WeakSet()) {
|
|
146
|
+
if (!obj || typeof obj !== 'object') {
|
|
147
|
+
return
|
|
148
|
+
}
|
|
149
|
+
|
|
150
|
+
if (processed.has(obj)) {
|
|
151
|
+
return
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
processed.add(obj);
|
|
155
|
+
|
|
156
|
+
if (obj.__constructor__) {
|
|
157
|
+
const ctor = obj.__constructor__;
|
|
158
|
+
delete obj.__constructor__;
|
|
159
|
+
Object.setPrototypeOf(obj, memfs[ctor].prototype);
|
|
160
|
+
}
|
|
161
|
+
|
|
162
|
+
for (const value of Object.values(obj)) {
|
|
163
|
+
loadConstructor(value, memfs, processed);
|
|
164
|
+
}
|
|
165
|
+
}
|
|
166
|
+
|
|
167
|
+
loadConstructor(obj, memfs);
|
|
168
|
+
|
|
169
|
+
if (obj.__error__) {
|
|
170
|
+
const name = obj.__error__;
|
|
171
|
+
const ErrorConstructor = globalThis[name] || Error;
|
|
172
|
+
delete obj.__error__;
|
|
173
|
+
const err = new ErrorConstructor(obj.message);
|
|
174
|
+
Object.defineProperty(err, 'stack', {
|
|
175
|
+
configurable: true,
|
|
176
|
+
enumerable: false,
|
|
177
|
+
writable: true,
|
|
178
|
+
value: err.stack,
|
|
179
|
+
});
|
|
180
|
+
Object.defineProperty(err, Symbol.toStringTag, {
|
|
181
|
+
configurable: true,
|
|
182
|
+
enumerable: false,
|
|
183
|
+
writable: true,
|
|
184
|
+
value: name,
|
|
185
|
+
});
|
|
186
|
+
for (const [k, v] of Object.entries(obj)) {
|
|
187
|
+
if (k === 'message' || k === 'stack') continue
|
|
188
|
+
err[k] = v;
|
|
189
|
+
}
|
|
190
|
+
return err
|
|
191
|
+
}
|
|
192
|
+
return obj
|
|
193
|
+
}
|
|
194
|
+
if (type === 9) {
|
|
195
|
+
return BigInt(new TextDecoder().decode(payload.slice()))
|
|
196
|
+
}
|
|
197
|
+
throw new Error('unsupported data')
|
|
198
|
+
};
|
|
199
|
+
|
|
200
|
+
/**
|
|
201
|
+
* @param {import('memfs').IFs} fs
|
|
202
|
+
* @returns {(e: { data: { __fs__: { sab: Int32Array, type: keyof import('memfs').IFs, payload: any[] } } }) => void}
|
|
203
|
+
*/
|
|
204
|
+
// oxlint-disable-next-line no-unused-vars -- fixed in an upcoming release
|
|
205
|
+
const createOnMessage = (fs) =>
|
|
206
|
+
function onMessage(e) {
|
|
207
|
+
if (e.data.__fs__) {
|
|
208
|
+
/**
|
|
209
|
+
* 0..4 status(int32_t): 21(waiting) 0(success) 1(error)
|
|
210
|
+
* 5..8 type(napi_valuetype): 0(undefined) 1(null) 2(boolean) 3(number) 4(string) 6(jsonstring) 9(bigint) -1(unsupported)
|
|
211
|
+
* 9..16 payload_size(uint32_t) <= 10240
|
|
212
|
+
* 16..16 + payload_size payload_content
|
|
213
|
+
*/
|
|
214
|
+
const { sab, type, payload } = e.data.__fs__;
|
|
215
|
+
const fn = fs[type];
|
|
216
|
+
try {
|
|
217
|
+
const ret = fn.apply(fs, payload);
|
|
218
|
+
const t = getType(ret);
|
|
219
|
+
Atomics.store(sab, 1, t);
|
|
220
|
+
const v = encodeValue(fs, ret, t);
|
|
221
|
+
Atomics.store(sab, 2, v.length);
|
|
222
|
+
writeResponsePayload(sab, v);
|
|
223
|
+
Atomics.store(sab, 0, 0); // success
|
|
224
|
+
} catch (/** @type {any} */ err) {
|
|
225
|
+
let t = getType(err);
|
|
226
|
+
let v;
|
|
227
|
+
try {
|
|
228
|
+
if (t === -1) {
|
|
229
|
+
throw new Error('unsupported data')
|
|
230
|
+
}
|
|
231
|
+
v = encodeValue(fs, err, t);
|
|
232
|
+
} catch {
|
|
233
|
+
const fallback = (() => {
|
|
234
|
+
try {
|
|
235
|
+
return String(err)
|
|
236
|
+
} catch {
|
|
237
|
+
return 'Unserializable thrown value'
|
|
238
|
+
}
|
|
239
|
+
})();
|
|
240
|
+
t = getType(fallback);
|
|
241
|
+
v = encodeValue(fs, fallback, t);
|
|
242
|
+
}
|
|
243
|
+
if (v.length > RESPONSE_PAYLOAD_SIZE) {
|
|
244
|
+
const overflowErr = new RangeError('payload overflow');
|
|
245
|
+
t = getType(overflowErr);
|
|
246
|
+
v = encodeValue(fs, overflowErr, t);
|
|
247
|
+
}
|
|
248
|
+
Atomics.store(sab, 1, t);
|
|
249
|
+
Atomics.store(sab, 2, v.length);
|
|
250
|
+
writeResponsePayload(sab, v);
|
|
251
|
+
Atomics.store(sab, 0, 1); // error
|
|
252
|
+
} finally {
|
|
253
|
+
Atomics.notify(sab, 0);
|
|
254
|
+
}
|
|
255
|
+
}
|
|
256
|
+
};
|
|
257
|
+
|
|
258
|
+
/**
|
|
259
|
+
* @param {typeof import('memfs')} memfs
|
|
260
|
+
*/
|
|
261
|
+
const createFsProxy = (memfs) =>
|
|
262
|
+
new Proxy(
|
|
263
|
+
{},
|
|
264
|
+
{
|
|
265
|
+
get(_target, p, _receiver) {
|
|
266
|
+
/**
|
|
267
|
+
* @param {any[]} args
|
|
268
|
+
*/
|
|
269
|
+
return function (...args) {
|
|
270
|
+
const sab = new SharedArrayBuffer(RESPONSE_BUFFER_SIZE);
|
|
271
|
+
const i32arr = new Int32Array(sab);
|
|
272
|
+
Atomics.store(i32arr, 0, 21);
|
|
273
|
+
|
|
274
|
+
postMessage({
|
|
275
|
+
__fs__: {
|
|
276
|
+
sab: i32arr,
|
|
277
|
+
type: p,
|
|
278
|
+
payload: args,
|
|
279
|
+
},
|
|
280
|
+
});
|
|
281
|
+
|
|
282
|
+
Atomics.wait(i32arr, 0, 21);
|
|
283
|
+
|
|
284
|
+
const status = Atomics.load(i32arr, 0);
|
|
285
|
+
const type = Atomics.load(i32arr, 1);
|
|
286
|
+
const size = Atomics.load(i32arr, 2);
|
|
287
|
+
const content = new Uint8Array(sab, RESPONSE_HEADER_SIZE, size);
|
|
288
|
+
const value = decodeValue(memfs, content, type);
|
|
289
|
+
if (status === 1) {
|
|
290
|
+
throw value
|
|
291
|
+
}
|
|
292
|
+
return value
|
|
293
|
+
}
|
|
294
|
+
},
|
|
295
|
+
},
|
|
296
|
+
);
|
|
297
|
+
|
|
298
|
+
exports.createFsProxy = createFsProxy;
|
|
299
|
+
exports.createOnMessage = createOnMessage;
|