smoldot 1.0.5 → 1.0.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.
- package/README.md +2 -2
- package/dist/cjs/internals/bytecode/wasm0.js +1 -1
- package/dist/cjs/internals/bytecode/wasm1.js +1 -1
- package/dist/cjs/internals/bytecode/wasm2.js +1 -1
- package/dist/cjs/internals/client.js +13 -1
- package/dist/cjs/internals/local-instance.d.ts +7 -3
- package/dist/cjs/internals/local-instance.js +22 -11
- package/dist/cjs/internals/remote-instance.js +14 -21
- package/dist/mjs/internals/bytecode/wasm0.js +1 -1
- package/dist/mjs/internals/bytecode/wasm1.js +1 -1
- package/dist/mjs/internals/bytecode/wasm2.js +1 -1
- package/dist/mjs/internals/client.js +13 -1
- package/dist/mjs/internals/local-instance.d.ts +7 -3
- package/dist/mjs/internals/local-instance.js +22 -11
- package/dist/mjs/internals/remote-instance.js +14 -21
- package/package.json +6 -7
|
@@ -68,6 +68,7 @@ function start(options, wasmModule, platformBindings) {
|
|
|
68
68
|
currentTaskName: null,
|
|
69
69
|
connections: new Map(),
|
|
70
70
|
addChainResults: [],
|
|
71
|
+
onExecutorShutdownOrWasmPanic: () => { },
|
|
71
72
|
chains: new Map(),
|
|
72
73
|
};
|
|
73
74
|
// Callback called during the execution of the instance.
|
|
@@ -97,6 +98,15 @@ function start(options, wasmModule, platformBindings) {
|
|
|
97
98
|
}
|
|
98
99
|
state.chains.clear();
|
|
99
100
|
state.currentTaskName = null;
|
|
101
|
+
const cb = state.onExecutorShutdownOrWasmPanic;
|
|
102
|
+
state.onExecutorShutdownOrWasmPanic = () => { };
|
|
103
|
+
cb();
|
|
104
|
+
break;
|
|
105
|
+
}
|
|
106
|
+
case "executor-shutdown": {
|
|
107
|
+
const cb = state.onExecutorShutdownOrWasmPanic;
|
|
108
|
+
state.onExecutorShutdownOrWasmPanic = () => { };
|
|
109
|
+
cb();
|
|
100
110
|
break;
|
|
101
111
|
}
|
|
102
112
|
case "log": {
|
|
@@ -342,7 +352,7 @@ function start(options, wasmModule, platformBindings) {
|
|
|
342
352
|
throw state.instance.error;
|
|
343
353
|
if (state.instance.status !== "ready")
|
|
344
354
|
throw new Error(); // Internal error. Never supposed to happen.
|
|
345
|
-
state.instance.instance.
|
|
355
|
+
state.instance.instance.shutdownExecutor();
|
|
346
356
|
state.instance = { status: "destroyed", error: new public_types_js_1.AlreadyDestroyedError() };
|
|
347
357
|
state.connections.forEach((connec) => connec.reset());
|
|
348
358
|
state.connections.clear();
|
|
@@ -358,6 +368,8 @@ function start(options, wasmModule, platformBindings) {
|
|
|
358
368
|
}
|
|
359
369
|
state.chains.clear();
|
|
360
370
|
state.currentTaskName = null;
|
|
371
|
+
// Wait for the `executor-shutdown` event to be generated.
|
|
372
|
+
yield new Promise((resolve) => state.onExecutorShutdownOrWasmPanic = resolve);
|
|
361
373
|
})
|
|
362
374
|
};
|
|
363
375
|
}
|
|
@@ -51,6 +51,8 @@ export type Event = {
|
|
|
51
51
|
} | {
|
|
52
52
|
ty: "wasm-panic";
|
|
53
53
|
message: string;
|
|
54
|
+
} | {
|
|
55
|
+
ty: "executor-shutdown";
|
|
54
56
|
} | {
|
|
55
57
|
ty: "new-connection";
|
|
56
58
|
connectionId: number;
|
|
@@ -95,12 +97,14 @@ export interface Instance {
|
|
|
95
97
|
addChain: (chainSpec: string, databaseContent: string, potentialRelayChains: number[], disableJsonRpc: boolean) => void;
|
|
96
98
|
removeChain: (chainId: number) => void;
|
|
97
99
|
/**
|
|
98
|
-
*
|
|
99
|
-
*
|
|
100
|
+
* Notifies the background executor that it should stop. Once it has effectively stopped,
|
|
101
|
+
* a `executor-shutdown` event will be generated.
|
|
102
|
+
* Note that the instance can technically still be used, and all the functions still work, but
|
|
103
|
+
* in practice nothing is being run in the background and as such it won't do much.
|
|
100
104
|
* Existing connections are *not* closed. It is the responsibility of the API user to close
|
|
101
105
|
* all connections.
|
|
102
106
|
*/
|
|
103
|
-
|
|
107
|
+
shutdownExecutor: () => void;
|
|
104
108
|
connectionOpened: (connectionId: number, info: {
|
|
105
109
|
type: 'single-stream';
|
|
106
110
|
handshake: 'multistream-select-noise-yamux';
|
|
@@ -44,6 +44,7 @@ function startLocalInstance(config, wasmModule, eventCallback) {
|
|
|
44
44
|
advanceExecutionPromise: null,
|
|
45
45
|
stdoutBuffer: "",
|
|
46
46
|
stderrBuffer: "",
|
|
47
|
+
onShutdownExecutorOrWasmPanic: () => { }
|
|
47
48
|
};
|
|
48
49
|
const smoldotJsBindings = {
|
|
49
50
|
// Must exit with an error. A human-readable message can be found in the WebAssembly
|
|
@@ -55,6 +56,8 @@ function startLocalInstance(config, wasmModule, eventCallback) {
|
|
|
55
56
|
len >>>= 0;
|
|
56
57
|
const message = buffer.utf8BytesToString(new Uint8Array(instance.exports.memory.buffer), ptr, len);
|
|
57
58
|
eventCallback({ ty: "wasm-panic", message });
|
|
59
|
+
state.onShutdownExecutorOrWasmPanic();
|
|
60
|
+
state.onShutdownExecutorOrWasmPanic = () => { };
|
|
58
61
|
throw new Error();
|
|
59
62
|
},
|
|
60
63
|
buffer_size: (bufferIndex) => {
|
|
@@ -287,6 +290,8 @@ function startLocalInstance(config, wasmModule, eventCallback) {
|
|
|
287
290
|
proc_exit: (retCode) => {
|
|
288
291
|
state.instance = null;
|
|
289
292
|
eventCallback({ ty: "wasm-panic", message: `proc_exit called: ${retCode}` });
|
|
293
|
+
state.onShutdownExecutorOrWasmPanic();
|
|
294
|
+
state.onShutdownExecutorOrWasmPanic = () => { };
|
|
290
295
|
throw new Error();
|
|
291
296
|
},
|
|
292
297
|
// Return the number of environment variables and the total size of all environment
|
|
@@ -339,6 +344,9 @@ function startLocalInstance(config, wasmModule, eventCallback) {
|
|
|
339
344
|
// Smoldot requires an initial call to the `init` function in order to do its internal
|
|
340
345
|
// configuration.
|
|
341
346
|
state.instance.exports.init(config.maxLogLevel);
|
|
347
|
+
// Promise that is notified when the `shutdownExecutor` function is called or when a Wasm
|
|
348
|
+
// panic happens.
|
|
349
|
+
const shutdownExecutorOrWasmPanicPromise = new Promise((resolve) => state.onShutdownExecutorOrWasmPanic = () => resolve("stop"));
|
|
342
350
|
(() => __awaiter(this, void 0, void 0, function* () {
|
|
343
351
|
const cpuRateLimit = config.cpuRateLimit;
|
|
344
352
|
// In order to avoid calling `setTimeout` too often, we accumulate sleep up until
|
|
@@ -346,13 +354,10 @@ function startLocalInstance(config, wasmModule, eventCallback) {
|
|
|
346
354
|
let missingSleep = 0;
|
|
347
355
|
let now = config.performanceNow();
|
|
348
356
|
while (true) {
|
|
349
|
-
const whenReadyAgain = new Promise((resolve) => state.advanceExecutionPromise = resolve);
|
|
357
|
+
const whenReadyAgain = new Promise((resolve) => state.advanceExecutionPromise = () => resolve("ready"));
|
|
350
358
|
if (!state.instance)
|
|
351
359
|
break;
|
|
352
|
-
|
|
353
|
-
if (outcome === 0) {
|
|
354
|
-
break;
|
|
355
|
-
}
|
|
360
|
+
state.instance.exports.advance_execution();
|
|
356
361
|
const afterExec = config.performanceNow();
|
|
357
362
|
const elapsed = afterExec - now;
|
|
358
363
|
now = afterExec;
|
|
@@ -369,9 +374,12 @@ function startLocalInstance(config, wasmModule, eventCallback) {
|
|
|
369
374
|
// really care for such extreme values.
|
|
370
375
|
if (missingSleep > 2147483646) // Doc says `> 2147483647`, but I don't really trust their pedanticism so let's be safe
|
|
371
376
|
missingSleep = 2147483646;
|
|
372
|
-
|
|
377
|
+
const sleepFinished = new Promise((resolve) => setTimeout(() => resolve("timeout"), missingSleep));
|
|
378
|
+
if ((yield Promise.race([sleepFinished, shutdownExecutorOrWasmPanicPromise])) === "stop")
|
|
379
|
+
break;
|
|
373
380
|
}
|
|
374
|
-
yield whenReadyAgain
|
|
381
|
+
if ((yield Promise.race([whenReadyAgain, shutdownExecutorOrWasmPanicPromise])) === "stop")
|
|
382
|
+
break;
|
|
375
383
|
const afterWait = config.performanceNow();
|
|
376
384
|
// `afterWait - now` is equal to how long we've waited for the `setTimeout` callback to
|
|
377
385
|
// trigger. While in principle `afterWait - now` should be roughly equal to
|
|
@@ -386,6 +394,9 @@ function startLocalInstance(config, wasmModule, eventCallback) {
|
|
|
386
394
|
missingSleep = -10000;
|
|
387
395
|
now = afterWait;
|
|
388
396
|
}
|
|
397
|
+
if (!state.instance)
|
|
398
|
+
return;
|
|
399
|
+
eventCallback({ ty: "executor-shutdown" });
|
|
389
400
|
}))();
|
|
390
401
|
return {
|
|
391
402
|
request: (request, chainId) => {
|
|
@@ -447,12 +458,12 @@ function startLocalInstance(config, wasmModule, eventCallback) {
|
|
|
447
458
|
return;
|
|
448
459
|
state.instance.exports.remove_chain(chainId);
|
|
449
460
|
},
|
|
450
|
-
|
|
461
|
+
shutdownExecutor: () => {
|
|
451
462
|
if (!state.instance)
|
|
452
463
|
return;
|
|
453
|
-
const
|
|
454
|
-
state.
|
|
455
|
-
|
|
464
|
+
const cb = state.onShutdownExecutorOrWasmPanic;
|
|
465
|
+
state.onShutdownExecutorOrWasmPanic = () => { };
|
|
466
|
+
cb();
|
|
456
467
|
},
|
|
457
468
|
connectionOpened: (connectionId, info) => {
|
|
458
469
|
if (!state.instance)
|
|
@@ -75,9 +75,8 @@ function connectToInstanceServer(config) {
|
|
|
75
75
|
const message = messageEvent.data;
|
|
76
76
|
// Update some local state.
|
|
77
77
|
switch (message.ty) {
|
|
78
|
-
case "wasm-panic":
|
|
79
|
-
|
|
80
|
-
state.connections.clear();
|
|
78
|
+
case "wasm-panic":
|
|
79
|
+
case "executor-shutdown": {
|
|
81
80
|
portToServer.close();
|
|
82
81
|
initialPort.close();
|
|
83
82
|
break;
|
|
@@ -171,7 +170,7 @@ function connectToInstanceServer(config) {
|
|
|
171
170
|
portToServer.postMessage(msg);
|
|
172
171
|
return item;
|
|
173
172
|
},
|
|
174
|
-
|
|
173
|
+
shutdownExecutor() {
|
|
175
174
|
const msg = { ty: "shutdown" };
|
|
176
175
|
portToServer.postMessage(msg);
|
|
177
176
|
},
|
|
@@ -231,12 +230,13 @@ function startInstanceServer(config, initPortToClient) {
|
|
|
231
230
|
}
|
|
232
231
|
break;
|
|
233
232
|
}
|
|
233
|
+
case "executor-shutdown":
|
|
234
234
|
case "wasm-panic": {
|
|
235
|
-
state.
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
235
|
+
if (state.onExecutorShutdownOrWasmPanic) {
|
|
236
|
+
const cb = state.onExecutorShutdownOrWasmPanic;
|
|
237
|
+
delete state.onExecutorShutdownOrWasmPanic;
|
|
238
|
+
cb();
|
|
239
|
+
}
|
|
240
240
|
break;
|
|
241
241
|
}
|
|
242
242
|
case "json-rpc-responses-non-empty": {
|
|
@@ -244,8 +244,6 @@ function startInstanceServer(config, initPortToClient) {
|
|
|
244
244
|
// from within the events callback itself.
|
|
245
245
|
// TODO: do better than setTimeout?
|
|
246
246
|
setTimeout(() => {
|
|
247
|
-
if (!state.instance)
|
|
248
|
-
return;
|
|
249
247
|
const numAccepted = state.acceptedJsonRpcResponses.get(event.chainId);
|
|
250
248
|
if (numAccepted == 0)
|
|
251
249
|
return;
|
|
@@ -274,6 +272,9 @@ function startInstanceServer(config, initPortToClient) {
|
|
|
274
272
|
const ev = event;
|
|
275
273
|
portToClient.postMessage(ev);
|
|
276
274
|
};
|
|
275
|
+
// We create the `Promise` ahead of time in order to potentially catch potential `wasm-panic`
|
|
276
|
+
// events as early as during initialization.
|
|
277
|
+
const execFinishedPromise = new Promise((resolve) => state.onExecutorShutdownOrWasmPanic = resolve);
|
|
277
278
|
state.instance = yield instance.startLocalInstance(Object.assign({ forbidTcp,
|
|
278
279
|
forbidWs,
|
|
279
280
|
forbidNonLocalWs,
|
|
@@ -283,8 +284,6 @@ function startInstanceServer(config, initPortToClient) {
|
|
|
283
284
|
maxLogLevel }, config), wasmModule, eventsCallback);
|
|
284
285
|
portToClient.onmessage = (messageEvent) => {
|
|
285
286
|
const message = messageEvent.data;
|
|
286
|
-
if (!state.instance)
|
|
287
|
-
return;
|
|
288
287
|
switch (message.ty) {
|
|
289
288
|
case "add-chain": {
|
|
290
289
|
state.instance.addChain(message.chainSpec, message.databaseContent, message.potentialRelayChains, message.disableJsonRpc);
|
|
@@ -311,10 +310,7 @@ function startInstanceServer(config, initPortToClient) {
|
|
|
311
310
|
break;
|
|
312
311
|
}
|
|
313
312
|
case "shutdown": {
|
|
314
|
-
|
|
315
|
-
state.onShutdown();
|
|
316
|
-
state.instance.startShutdown();
|
|
317
|
-
portToClient.close();
|
|
313
|
+
state.instance.shutdownExecutor();
|
|
318
314
|
break;
|
|
319
315
|
}
|
|
320
316
|
case "connection-reset": {
|
|
@@ -372,10 +368,7 @@ function startInstanceServer(config, initPortToClient) {
|
|
|
372
368
|
}
|
|
373
369
|
}
|
|
374
370
|
};
|
|
375
|
-
|
|
376
|
-
if (!state.instance)
|
|
377
|
-
return Promise.resolve();
|
|
378
|
-
return new Promise((resolve) => state.onShutdown = resolve);
|
|
371
|
+
return execFinishedPromise;
|
|
379
372
|
});
|
|
380
373
|
}
|
|
381
374
|
exports.startInstanceServer = startInstanceServer;
|