@ai-ecoverse/slicc-kernel 1.146.2 → 1.146.4

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.
@@ -931,6 +931,10 @@ var init_ranged = __esm({
931
931
  pin() {
932
932
  this.pinned = true;
933
933
  this.pages.pin();
934
+ this.prefetch();
935
+ }
936
+ prefetch() {
937
+ this.fresh();
934
938
  this.fetch(this.pages.missing(0, this.pages.length));
935
939
  }
936
940
  reset(size) {
@@ -1301,6 +1305,9 @@ function errnoError(code2, path, direct) {
1301
1305
  const err = syncError(code2, `sync-sab bridge, '${path}'`);
1302
1306
  return direct ? Object.assign(err, { direct }) : err;
1303
1307
  }
1308
+ function holdSeen(seen) {
1309
+ return { gen: seen.gen, ino: seen.ino, ...seen.nofollow ? { nofollow: true } : {} };
1310
+ }
1304
1311
  function createSyncFsSabBridge(transport, opts = {}) {
1305
1312
  const direct = opts.direct ? { direct: true } : {};
1306
1313
  const timeoutMs2 = opts.timeoutMs ?? SYNC_FS_REQUEST_TIMEOUT_MS;
@@ -1473,9 +1480,7 @@ function createSyncFsSabBridge(transport, opts = {}) {
1473
1480
  hold: (path, held2, open, handle, want = 0, seen = {}) => {
1474
1481
  const mode = (held2 ? 1 : 0) | (open ? 2 : 0);
1475
1482
  if (mode === 3) {
1476
- const at = seen.gen !== void 0 ? { gen: seen.gen } : {};
1477
- const link = seen.nofollow ? { nofollow: true } : {};
1478
- return json2({ op: "hold", path, mode: mode | want, ...at, ...link }, path);
1483
+ return json2({ op: "hold", path, mode: mode | want, ...holdSeen(seen) }, path);
1479
1484
  }
1480
1485
  run({ op: "hold", path, mode, ...handle !== void 0 ? { handle } : {} }, path);
1481
1486
  return void 0;
@@ -1757,6 +1762,7 @@ function renameFollower(Fs, bridgeOf, call2) {
1757
1762
  open,
1758
1763
  follow: follow3,
1759
1764
  track(node, on) {
1765
+ node.live.bound = on && node.live.stat?.ino !== void 0 ? node.live.stat : void 0;
1760
1766
  if (!on) {
1761
1767
  open.delete(node);
1762
1768
  return;
@@ -1782,6 +1788,35 @@ function followingOnce(write2, follow3) {
1782
1788
  write2();
1783
1789
  }
1784
1790
  }
1791
+ function openReplaced(h, dir, name2, moving) {
1792
+ let node;
1793
+ try {
1794
+ node = h.Fs.lookupNode?.(dir, name2);
1795
+ } catch {
1796
+ return void 0;
1797
+ }
1798
+ if (!node || node === moving || node.live?.openCount === 0 || !h.Fs.isFile(node.mode))
1799
+ return void 0;
1800
+ const st = freshStat(h, node);
1801
+ if ((st.nlink ?? 1) > 1) return void 0;
1802
+ const ranged = h.rangedOf(node);
1803
+ if (ranged) ranged.prefetch();
1804
+ else h.ensureLoaded(node);
1805
+ return { node, st };
1806
+ }
1807
+ function renamedOver(h, dir, name2, moving, rename) {
1808
+ const replaced = openReplaced(h, dir, name2, moving);
1809
+ rename();
1810
+ if (replaced) {
1811
+ h.rangedOf(replaced.node)?.pin();
1812
+ orphaned(h, replaced.node, replaced.st);
1813
+ }
1814
+ try {
1815
+ const existing = h.Fs.lookupNode?.(dir, name2);
1816
+ if (existing && existing !== moving) h.Fs.hashRemoveNode?.(existing);
1817
+ } catch {
1818
+ }
1819
+ }
1785
1820
  function renameThrough(h, node, from, to) {
1786
1821
  const seq = h.call(() => h.bridgeOf(node).rename(from, to));
1787
1822
  h.ownRename(h.bridgeOf(node), typeof seq === "number" ? seq : void 0);
@@ -1798,6 +1833,13 @@ function heldStream(h, stream, change) {
1798
1833
  }
1799
1834
  }
1800
1835
  }
1836
+ function adopted(node, st, asked) {
1837
+ const bound = node.live.openCount > 0 ? node.live.bound : void 0;
1838
+ if (bound && st.ino !== bound.ino) return false;
1839
+ filled(node.live, st, asked);
1840
+ node.mode = modeFromStat(st, exactIn(node));
1841
+ return true;
1842
+ }
1801
1843
  function createHelpers(Fs, ops) {
1802
1844
  const bridgeOf = (node) => node.mount.opts.bridge;
1803
1845
  const fileIo = (node) => pinnedIo(bridgeOf(node), node.live.handle);
@@ -1854,8 +1896,7 @@ function createHelpers(Fs, ops) {
1854
1896
  if (!cachedStat(node, Fs.isDir(node.mode), view)) {
1855
1897
  const asked = { statGen: view?.now(), filledAt: performance.now() };
1856
1898
  const st = call2(() => bridgeOf(node).lstat(liveNodePath(linked.holder(node))));
1857
- filled(node.live, st, asked);
1858
- node.mode = modeFromStat(st, exactIn(node));
1899
+ if (!adopted(node, st, asked)) return node.live.bound;
1859
1900
  }
1860
1901
  return node.live.stat;
1861
1902
  }
@@ -2107,12 +2148,7 @@ function createNodeOps(h) {
2107
2148
  const from = liveNodePath(oldNode);
2108
2149
  const to = childPath(newDir, newName);
2109
2150
  flushNode(oldNode);
2110
- renameThrough(h, oldNode, from, to);
2111
- try {
2112
- const existing = Fs.lookupNode?.(newDir, newName);
2113
- if (existing && existing !== oldNode) Fs.hashRemoveNode?.(existing);
2114
- } catch {
2115
- }
2151
+ renamedOver(h, newDir, newName, oldNode, () => renameThrough(h, oldNode, from, to));
2116
2152
  oldNode.name = newName;
2117
2153
  oldNode.parent = newDir;
2118
2154
  oldNode.live.stat = void 0;
@@ -2192,7 +2228,7 @@ function appendThrough(h, stream, bytes) {
2192
2228
  }
2193
2229
  function holdLive(bridge, node, on, want) {
2194
2230
  const s = node.live;
2195
- const seen = on && s.stat ? { gen: s.stat.gen } : void 0;
2231
+ const seen = on && s.stat ? { gen: s.stat.gen, ...s.stat.ino !== void 0 ? { ino: s.stat.ino } : {} } : void 0;
2196
2232
  return bridge.hold?.(liveNodePath(node), on, true, s.handle, want, seen);
2197
2233
  }
2198
2234
  function dropOpen(s) {
@@ -2927,7 +2963,7 @@ var KERNEL_VERSION, OS_RELEASE;
2927
2963
  var init_version = __esm({
2928
2964
  "src/version.ts"() {
2929
2965
  "use strict";
2930
- KERNEL_VERSION = true ? "1.146.2" : "0.0.0-dev";
2966
+ KERNEL_VERSION = true ? "1.146.4" : "0.0.0-dev";
2931
2967
  OS_RELEASE = "6.0.0-slicc";
2932
2968
  }
2933
2969
  });
@@ -6075,6 +6111,8 @@ var init_procfs = __esm({
6075
6111
  slicc_cwd_checks: (listing2) => `${listing2.cwdChecks ?? 0}
6076
6112
  `,
6077
6113
  slicc_rename_ack_busy: (listing2) => `${listing2.renameAcks?.busy ?? 0}
6114
+ `,
6115
+ slicc_stale_fds: (listing2) => `${listing2.staleFds ?? 0}
6078
6116
  `,
6079
6117
  slicc_rename_acks: (listing2) => {
6080
6118
  const samples = [...listing2.renameAcks?.ackMs ?? []].sort((a, b) => a - b);
@@ -7326,6 +7364,7 @@ var init_wasi_files = __esm({
7326
7364
  maxFile;
7327
7365
  handle;
7328
7366
  moved;
7367
+ bound;
7329
7368
  constructor(fs, path, empty, maxFile, size, version, watch) {
7330
7369
  this.fs = fs;
7331
7370
  this.where = path;
@@ -7372,6 +7411,10 @@ var init_wasi_files = __esm({
7372
7411
  if (this.ranged) this.ranged.pin();
7373
7412
  else this.load();
7374
7413
  }
7414
+ prefetch() {
7415
+ if (this.ranged) this.ranged.prefetch();
7416
+ else this.load();
7417
+ }
7375
7418
  load() {
7376
7419
  const view = this.watch?.view;
7377
7420
  if (this.data && view && this.watch && !this.dirty) {
@@ -9389,6 +9432,15 @@ var init_wasi_fds = __esm({
9389
9432
  for (const p of this.buffers.keys()) if (within(p, path)) return true;
9390
9433
  return false;
9391
9434
  }
9435
+ replacing(path) {
9436
+ for (const [p, buffer] of this.buffers) {
9437
+ if (!within(p, path)) continue;
9438
+ try {
9439
+ buffer.prefetch();
9440
+ } catch {
9441
+ }
9442
+ }
9443
+ }
9392
9444
  unlinking(path, linked) {
9393
9445
  const buffer = this.buffers.get(path);
9394
9446
  if (buffer && this.survives(buffer, linked)) buffer.flush();
@@ -9525,10 +9577,9 @@ var init_wasi_fds = __esm({
9525
9577
  if (exclusive && !(oflags & OFLAGS.DIRECTORY) && this.madeAtOnce(path, mode)) {
9526
9578
  return this.regular(path, void 0, oflags, rights, fdflags, mode, true);
9527
9579
  }
9528
- if ((exclusive || nofollow) && this.isLink(path)) {
9529
- throw new WasiError(exclusive ? "EEXIST" : "ELOOP");
9530
- }
9531
- const s = this.statOrMissing(path);
9580
+ if (exclusive && !nofollow && this.isLink(path)) throw new WasiError("EEXIST");
9581
+ const s = nofollow ? this.lstatOrMissing(path) : this.statOrMissing(path);
9582
+ if (s?.isSymbolicLink) throw new WasiError(exclusive ? "EEXIST" : "ELOOP");
9532
9583
  if (exclusive && s) throw new WasiError("EEXIST");
9533
9584
  if (s?.escape !== void 0) {
9534
9585
  refuseWrite({ readonly: true }, oflags, rights);
@@ -9547,6 +9598,11 @@ var init_wasi_fds = __esm({
9547
9598
  return this.regular(path, s, oflags, rights, fdflags, mode);
9548
9599
  }
9549
9600
  nofollow = false;
9601
+ inos = /* @__PURE__ */ new WeakMap();
9602
+ otherFile(buffer, st) {
9603
+ const ino = this.inos.get(buffer);
9604
+ return ino !== void 0 && st?.ino !== void 0 && ino !== st.ino;
9605
+ }
9550
9606
  openSpecial(path, oflags, rights, fdflags, exclusive) {
9551
9607
  if (exclusive && namedDevice(path)) throw new WasiError("EEXIST");
9552
9608
  const device2 = deviceOf(path);
@@ -9604,6 +9660,7 @@ var init_wasi_fds = __esm({
9604
9660
  buffer = void 0;
9605
9661
  }
9606
9662
  buffer ??= this.sharing(path, existing);
9663
+ if (buffer && this.nofollow && this.otherFile(buffer, existing)) buffer = void 0;
9607
9664
  const want = wantOf2(oflags, rights);
9608
9665
  if (buffer) {
9609
9666
  if (this.fs.owners) this.fs.access?.(path, want, "open");
@@ -9628,7 +9685,8 @@ var init_wasi_fds = __esm({
9628
9685
  const asked = (want & 4 ? HOLD_READ : 0) | (want & 2 ? HOLD_WRITE : 0) | (made ? HOLD_CREATED : 0);
9629
9686
  const handle = this.fs.hold?.(path, true, true, void 0, this.fs.owners ? asked : 0, {
9630
9687
  gen: st.gen,
9631
- ...this.nofollow ? { nofollow: true } : {}
9688
+ ...this.nofollow ? { nofollow: true } : {},
9689
+ ...st.ino !== void 0 ? { ino: st.ino } : {}
9632
9690
  });
9633
9691
  const io = handle !== void 0 && this.fs.pinned ? this.fs.pinned(handle) : this.fs;
9634
9692
  const view = this.fs.changes;
@@ -9647,7 +9705,9 @@ var init_wasi_fds = __esm({
9647
9705
  );
9648
9706
  const buffer = new FileBuffer(io, path, empty, st.maxFile, ranged, st.version, watch);
9649
9707
  buffer.moved = (missing2) => this.followRenames(missing2);
9708
+ buffer.bound = st;
9650
9709
  buffer.handle = handle;
9710
+ if (st.ino !== void 0) this.inos.set(buffer, st.ino);
9651
9711
  this.buffers.set(path, buffer);
9652
9712
  const id = this.identity(st);
9653
9713
  if (id !== void 0) this.know(buffer, id);
@@ -9730,6 +9790,14 @@ var init_wasi_fds = __esm({
9730
9790
  return false;
9731
9791
  }
9732
9792
  }
9793
+ lstatOrMissing(path) {
9794
+ try {
9795
+ return this.fs.lstat(path);
9796
+ } catch (e) {
9797
+ if (e.code === "ENOENT") return void 0;
9798
+ throw e;
9799
+ }
9800
+ }
9733
9801
  statOrMissing(path) {
9734
9802
  try {
9735
9803
  return this.fs.stat(path);
@@ -11404,6 +11472,7 @@ var init_wasi_host = __esm({
11404
11472
  const to = at(fd2, p2, l2);
11405
11473
  fds.flushPath(from);
11406
11474
  const replaced = fds.holdsUnder(to) ? linkedElsewhere(o.fs, to) : void 0;
11475
+ if (replaced === void 0) fds.replacing(to);
11407
11476
  const seq = o.fs.rename(from, to);
11408
11477
  fds.renamed(from, to, replaced);
11409
11478
  fds.ownRename(typeof seq === "number" ? seq : void 0);
@@ -11704,13 +11773,21 @@ var init_wasi_host = __esm({
11704
11773
  }
11705
11774
  localFilestat(file) {
11706
11775
  const { buffer } = file;
11707
- if (buffer.isOrphan()) return this.statOrphanable(file.path, file.size(), false, true);
11776
+ if (buffer.isOrphan()) {
11777
+ const bound2 = buffer.bound;
11778
+ if (!bound2) return this.statOrphanable(file.path, file.size(), false, true);
11779
+ return { ...this.sized(file.path, bound2, file.size()), nlink: 0n };
11780
+ }
11708
11781
  let s;
11709
11782
  try {
11710
11783
  s = this.o.fs.stat(file.path);
11711
11784
  } catch {
11712
11785
  s = this.keptStat(buffer.handle);
11713
11786
  }
11787
+ const bound = buffer.bound;
11788
+ if (s && bound?.ino !== void 0 && s.ino !== bound.ino) {
11789
+ s = this.keptStat(buffer.handle) ?? bound;
11790
+ }
11714
11791
  return this.sized(file.path, s, file.size());
11715
11792
  }
11716
11793
  keptStat(handle) {