@ai-ecoverse/slicc-kernel 1.116.2 → 1.117.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.
- package/README.md +18 -1
- package/dist/kernel-worker.js +128 -23
- package/dist/kernel-worker.js.map +3 -3
- package/dist/node-process-worker.js +23 -8
- package/dist/node-process-worker.js.map +3 -3
- package/dist/node.js +128 -23
- package/dist/node.js.map +3 -3
- package/dist/process-worker.js +23 -8
- package/dist/process-worker.js.map +3 -3
- package/dist/types/kernel/fd-table.d.ts +1 -0
- package/dist/types/kernel/host-ops.d.ts +10 -1
- package/dist/types/kernel/locks.d.ts +11 -0
- package/dist/types/kernel/process.d.ts +2 -0
- package/dist/types/process/wasi/slicc-lock.d.ts +3 -0
- package/dist/types/process/wasi/wasi-fds.d.ts +3 -2
- package/package.json +1 -1
package/dist/node.js
CHANGED
|
@@ -931,7 +931,8 @@ function openPipe(capacity) {
|
|
|
931
931
|
},
|
|
932
932
|
close: () => pipe.closeRead(),
|
|
933
933
|
poll: () => ({ readable: pipe.readReady, writable: false, hangup: pipe.writersGone }),
|
|
934
|
-
changed: (signal) => pipe.changed(signal)
|
|
934
|
+
changed: (signal) => pipe.changed(signal),
|
|
935
|
+
identity: pipe
|
|
935
936
|
}),
|
|
936
937
|
write: new OpenFile({
|
|
937
938
|
write: async (bytes, signal) => {
|
|
@@ -943,7 +944,8 @@ function openPipe(capacity) {
|
|
|
943
944
|
},
|
|
944
945
|
close: () => pipe.closeWrite(),
|
|
945
946
|
poll: () => ({ readable: false, writable: pipe.writeReady, hangup: pipe.readersGone }),
|
|
946
|
-
changed: (signal) => pipe.changed(signal)
|
|
947
|
+
changed: (signal) => pipe.changed(signal),
|
|
948
|
+
identity: pipe
|
|
947
949
|
})
|
|
948
950
|
};
|
|
949
951
|
}
|
|
@@ -6576,7 +6578,7 @@ function satisfies(version, range2) {
|
|
|
6576
6578
|
}
|
|
6577
6579
|
|
|
6578
6580
|
// src/version.ts
|
|
6579
|
-
var KERNEL_VERSION = true ? "1.
|
|
6581
|
+
var KERNEL_VERSION = true ? "1.117.0" : "0.0.0-dev";
|
|
6580
6582
|
var OS_RELEASE = "6.0.0-slicc";
|
|
6581
6583
|
function procVersion() {
|
|
6582
6584
|
return `Linux version ${OS_RELEASE} (slicc-kernel ${KERNEL_VERSION}) #1 SMP PREEMPT_DYNAMIC
|
|
@@ -9720,6 +9722,7 @@ var FifoTable = class {
|
|
|
9720
9722
|
let open = true;
|
|
9721
9723
|
return new OpenFile({
|
|
9722
9724
|
fifo: path,
|
|
9725
|
+
identity: fifo,
|
|
9723
9726
|
...reads ? {
|
|
9724
9727
|
read: async (max, signal) => {
|
|
9725
9728
|
try {
|
|
@@ -13153,7 +13156,71 @@ function lockRange(start2, len) {
|
|
|
13153
13156
|
if (from < 0) throw new KernelError("EINVAL");
|
|
13154
13157
|
return { start: from, end };
|
|
13155
13158
|
}
|
|
13159
|
+
function changedAt(wakers, key, signal) {
|
|
13160
|
+
return new Promise((resolve2, reject) => {
|
|
13161
|
+
const set3 = wakers.get(key) ?? /* @__PURE__ */ new Set();
|
|
13162
|
+
wakers.set(key, set3);
|
|
13163
|
+
const done4 = () => {
|
|
13164
|
+
set3.delete(wake);
|
|
13165
|
+
if (set3.size === 0 && wakers.get(key) === set3) wakers.delete(key);
|
|
13166
|
+
signal.removeEventListener("abort", abort);
|
|
13167
|
+
};
|
|
13168
|
+
const wake = () => {
|
|
13169
|
+
done4();
|
|
13170
|
+
resolve2();
|
|
13171
|
+
};
|
|
13172
|
+
const abort = () => {
|
|
13173
|
+
done4();
|
|
13174
|
+
reject(new KernelError("EINTR"));
|
|
13175
|
+
};
|
|
13176
|
+
set3.add(wake);
|
|
13177
|
+
signal.addEventListener("abort", abort, { once: true });
|
|
13178
|
+
});
|
|
13179
|
+
}
|
|
13180
|
+
function wakeAt(wakers, key) {
|
|
13181
|
+
for (const wake of [...wakers.get(key) ?? []]) wake();
|
|
13182
|
+
}
|
|
13183
|
+
var FlockTable = class {
|
|
13184
|
+
held = /* @__PURE__ */ new Map();
|
|
13185
|
+
keys = /* @__PURE__ */ new WeakMap();
|
|
13186
|
+
wakers = /* @__PURE__ */ new Map();
|
|
13187
|
+
free(key, owner, kind) {
|
|
13188
|
+
for (const [other, has] of this.held.get(key) ?? [])
|
|
13189
|
+
if (other !== owner && (kind === "exclusive" || has === "exclusive")) return false;
|
|
13190
|
+
return true;
|
|
13191
|
+
}
|
|
13192
|
+
set(key, owner, kind) {
|
|
13193
|
+
const has = this.held.get(key)?.get(owner);
|
|
13194
|
+
if (has === kind) return true;
|
|
13195
|
+
if (has !== void 0) this.drop(owner);
|
|
13196
|
+
if (kind === "unlock") return true;
|
|
13197
|
+
if (!this.free(key, owner, kind)) return false;
|
|
13198
|
+
const holders = this.held.get(key) ?? /* @__PURE__ */ new Map();
|
|
13199
|
+
holders.set(owner, kind);
|
|
13200
|
+
this.held.set(key, holders);
|
|
13201
|
+
this.keys.set(owner, key);
|
|
13202
|
+
return true;
|
|
13203
|
+
}
|
|
13204
|
+
async wait(key, owner, kind, blocking) {
|
|
13205
|
+
if (this.set(key, owner, kind)) return;
|
|
13206
|
+
const signal = blocking();
|
|
13207
|
+
while (!this.set(key, owner, kind)) {
|
|
13208
|
+
if (signal.aborted) throw new KernelError("EINTR");
|
|
13209
|
+
await changedAt(this.wakers, key, signal);
|
|
13210
|
+
}
|
|
13211
|
+
}
|
|
13212
|
+
drop(owner) {
|
|
13213
|
+
const key = this.keys.get(owner);
|
|
13214
|
+
if (key === void 0) return;
|
|
13215
|
+
this.keys.delete(owner);
|
|
13216
|
+
const holders = this.held.get(key);
|
|
13217
|
+
holders?.delete(owner);
|
|
13218
|
+
if (holders?.size === 0) this.held.delete(key);
|
|
13219
|
+
wakeAt(this.wakers, key);
|
|
13220
|
+
}
|
|
13221
|
+
};
|
|
13156
13222
|
var LockTable = class {
|
|
13223
|
+
flocks = new FlockTable();
|
|
13157
13224
|
records = /* @__PURE__ */ new Map();
|
|
13158
13225
|
blocked = /* @__PURE__ */ new Map();
|
|
13159
13226
|
wakers = /* @__PURE__ */ new Map();
|
|
@@ -13211,28 +13278,10 @@ var LockTable = class {
|
|
|
13211
13278
|
return false;
|
|
13212
13279
|
}
|
|
13213
13280
|
changed(key, signal) {
|
|
13214
|
-
return
|
|
13215
|
-
const set3 = this.wakers.get(key) ?? /* @__PURE__ */ new Set();
|
|
13216
|
-
this.wakers.set(key, set3);
|
|
13217
|
-
const done4 = () => {
|
|
13218
|
-
set3.delete(wake);
|
|
13219
|
-
if (set3.size === 0 && this.wakers.get(key) === set3) this.wakers.delete(key);
|
|
13220
|
-
signal.removeEventListener("abort", abort);
|
|
13221
|
-
};
|
|
13222
|
-
const wake = () => {
|
|
13223
|
-
done4();
|
|
13224
|
-
resolve2();
|
|
13225
|
-
};
|
|
13226
|
-
const abort = () => {
|
|
13227
|
-
done4();
|
|
13228
|
-
reject(new KernelError("EINTR"));
|
|
13229
|
-
};
|
|
13230
|
-
set3.add(wake);
|
|
13231
|
-
signal.addEventListener("abort", abort, { once: true });
|
|
13232
|
-
});
|
|
13281
|
+
return changedAt(this.wakers, key, signal);
|
|
13233
13282
|
}
|
|
13234
13283
|
wake(key) {
|
|
13235
|
-
|
|
13284
|
+
wakeAt(this.wakers, key);
|
|
13236
13285
|
}
|
|
13237
13286
|
store(key, locks) {
|
|
13238
13287
|
if (locks.length === 0) this.records.delete(key);
|
|
@@ -13297,6 +13346,7 @@ var HOST_OPS = [
|
|
|
13297
13346
|
"lk-set",
|
|
13298
13347
|
"lk-get",
|
|
13299
13348
|
"lk-close",
|
|
13349
|
+
"flock",
|
|
13300
13350
|
"async-submit",
|
|
13301
13351
|
"async-wait",
|
|
13302
13352
|
"async-take",
|
|
@@ -13449,6 +13499,8 @@ async function hostSyscall(req, ctx) {
|
|
|
13449
13499
|
case "lk-get":
|
|
13450
13500
|
case "lk-close":
|
|
13451
13501
|
return recordLock2(req, ctx);
|
|
13502
|
+
case "flock":
|
|
13503
|
+
return flock(req, ctx);
|
|
13452
13504
|
case "async-submit":
|
|
13453
13505
|
if (!ctx.valid(req.req)) throw new KernelError("EINVAL");
|
|
13454
13506
|
if (req.ack) ctx.ops.ack(req.ack);
|
|
@@ -13471,6 +13523,17 @@ async function hostSyscall(req, ctx) {
|
|
|
13471
13523
|
return done2;
|
|
13472
13524
|
}
|
|
13473
13525
|
}
|
|
13526
|
+
var FLOCK_KINDS = /* @__PURE__ */ new Set(["shared", "exclusive", "unlock"]);
|
|
13527
|
+
async function flock(req, ctx) {
|
|
13528
|
+
const { locks, flockOf } = ctx;
|
|
13529
|
+
if (!locks || !flockOf) throw new KernelError("ENOLCK");
|
|
13530
|
+
if (!FLOCK_KINDS.has(req.kind)) throw new KernelError("EINVAL");
|
|
13531
|
+
const { key, owner } = await flockOf(req.fd);
|
|
13532
|
+
if (req.kind !== "unlock" && req.wait)
|
|
13533
|
+
await locks.flocks.wait(key, owner, req.kind, ctx.blocking);
|
|
13534
|
+
else if (!locks.flocks.set(key, owner, req.kind)) throw new KernelError("EAGAIN");
|
|
13535
|
+
return done2;
|
|
13536
|
+
}
|
|
13474
13537
|
async function recordLock2(req, ctx) {
|
|
13475
13538
|
const { locks, fileKey } = ctx;
|
|
13476
13539
|
if (!locks || !fileKey) throw new KernelError("ENOLCK");
|
|
@@ -17441,6 +17504,18 @@ var fileKeys = /* @__PURE__ */ new WeakMap();
|
|
|
17441
17504
|
function identityKey(st, path) {
|
|
17442
17505
|
return st.ino === void 0 ? path : `${st.dev ?? 0}:${st.ino}`;
|
|
17443
17506
|
}
|
|
17507
|
+
var objectIds = /* @__PURE__ */ new WeakMap();
|
|
17508
|
+
var nextObjectId = 1;
|
|
17509
|
+
function objectKey(file) {
|
|
17510
|
+
const at = file.tty ?? file.identity ?? file.pty ?? file;
|
|
17511
|
+
let id2 = objectIds.get(at);
|
|
17512
|
+
if (id2 === void 0) {
|
|
17513
|
+
id2 = nextObjectId++;
|
|
17514
|
+
objectIds.set(at, id2);
|
|
17515
|
+
}
|
|
17516
|
+
return `object:${id2}`;
|
|
17517
|
+
}
|
|
17518
|
+
var flockHooked = /* @__PURE__ */ new WeakSet();
|
|
17444
17519
|
var DYING = { ok: false, errno: "EINTR", message: "the process is being killed" };
|
|
17445
17520
|
var HOSTS_ONLY = new Resolver({ routes: new Routes() });
|
|
17446
17521
|
function timeLeft(req, started) {
|
|
@@ -17741,6 +17816,7 @@ var WasmProcess = class {
|
|
|
17741
17816
|
pid: this.pid,
|
|
17742
17817
|
owner: () => this.lockOwner(),
|
|
17743
17818
|
fileKey: (target, kind, setting) => this.lockKey(target, kind, setting),
|
|
17819
|
+
flockOf: (fd) => this.flockOf(fd),
|
|
17744
17820
|
locks: this.options.locks,
|
|
17745
17821
|
ops: this.asyncOps,
|
|
17746
17822
|
blocking: () => this.blockingSignal(cancelled),
|
|
@@ -17809,6 +17885,7 @@ var WasmProcess = class {
|
|
|
17809
17885
|
throw new KernelError("EBADF");
|
|
17810
17886
|
const known = file ? fileKeys.get(file) : this.pathKeys.get(target.path ?? "");
|
|
17811
17887
|
if (kind === "close" && !file && target.path !== void 0) this.pathKeys.delete(target.path);
|
|
17888
|
+
if (access2 && !access2.stat) return objectKey(access2);
|
|
17812
17889
|
const want = kind === "read" ? R_OK : kind === "write" ? W_OK : 0;
|
|
17813
17890
|
const path = await this.lockPath(target, want);
|
|
17814
17891
|
if (known !== void 0) return known;
|
|
@@ -17823,6 +17900,33 @@ var WasmProcess = class {
|
|
|
17823
17900
|
else if (this.pathKeys.size < 4096) this.pathKeys.set(path, key);
|
|
17824
17901
|
return key;
|
|
17825
17902
|
}
|
|
17903
|
+
async flockOf(fd) {
|
|
17904
|
+
const open = this.fds.get(fd);
|
|
17905
|
+
const { locks } = this.options;
|
|
17906
|
+
if (locks && !flockHooked.has(open)) {
|
|
17907
|
+
flockHooked.add(open);
|
|
17908
|
+
open.onClose(() => locks.flocks.drop(open));
|
|
17909
|
+
}
|
|
17910
|
+
return { key: await this.objectKeyOf(open), owner: open };
|
|
17911
|
+
}
|
|
17912
|
+
async objectKeyOf(open) {
|
|
17913
|
+
const { file } = open;
|
|
17914
|
+
const meta = file.heldMeta;
|
|
17915
|
+
if (meta && "device" in meta) return `device:${meta.device}`;
|
|
17916
|
+
if (meta && "dir" in meta) {
|
|
17917
|
+
const st2 = await this.options.fs.stat?.(meta.dir).catch(() => void 0);
|
|
17918
|
+
return st2 ? identityKey(st2, meta.dir) : objectKey(file);
|
|
17919
|
+
}
|
|
17920
|
+
const known = fileKeys.get(open);
|
|
17921
|
+
if (known !== void 0) return known;
|
|
17922
|
+
const vfs = await file.stat?.().catch(() => void 0);
|
|
17923
|
+
if (!vfs || vfs.orphan) return objectKey(file);
|
|
17924
|
+
const st = await this.options.fs.stat?.(vfs.path).catch(() => void 0);
|
|
17925
|
+
if (!st) return objectKey(file);
|
|
17926
|
+
const key = identityKey(st, vfs.path);
|
|
17927
|
+
fileKeys.set(open, key);
|
|
17928
|
+
return key;
|
|
17929
|
+
}
|
|
17826
17930
|
async dropRecordLocks(fd) {
|
|
17827
17931
|
const { locks } = this.options;
|
|
17828
17932
|
const owner = this.options.jobs?.shown(this.pid) ?? this.pid;
|
|
@@ -20103,6 +20207,7 @@ function scrubbed(inner, scrubber, idleMs = SCRUB_IDLE_MS) {
|
|
|
20103
20207
|
},
|
|
20104
20208
|
changed,
|
|
20105
20209
|
...file.tty ? { tty: file.tty } : {},
|
|
20210
|
+
identity: file.identity ?? file,
|
|
20106
20211
|
...file.clipboard ? { clipboard: file.clipboard } : {},
|
|
20107
20212
|
...file.write ? {
|
|
20108
20213
|
write: async (bytes, signal) => {
|