@ai-ecoverse/slicc-kernel 1.90.0 → 1.92.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.
@@ -44,17 +44,20 @@ function hide(target, names) {
44
44
  }
45
45
  function vacate(target, names) {
46
46
  for (const name2 of names) {
47
- for (let at = target; at && at !== Object.prototype; ) {
48
- if (Object.getOwnPropertyDescriptor(at, name2)?.configurable) Reflect.deleteProperty(at, name2);
49
- at = Object.getPrototypeOf(at);
47
+ const holders = chain(target);
48
+ for (const holder of holders) {
49
+ if (Object.getOwnPropertyDescriptor(holder, name2)?.configurable) {
50
+ Reflect.deleteProperty(holder, name2);
51
+ }
50
52
  }
51
- Reflect.defineProperty(target, name2, {
53
+ const kept = holders.slice(1).some((holder) => Object.hasOwn(holder, name2));
54
+ const opened2 = Reflect.defineProperty(target, name2, {
52
55
  value: void 0,
53
56
  writable: true,
54
57
  enumerable: false,
55
58
  configurable: true
56
59
  });
57
- if (Reflect.get(target, name2) !== void 0) {
60
+ if (kept || !opened2 || Reflect.get(target, name2) !== void 0) {
58
61
  throw new Error(`slicc-kernel: cannot withhold ${name2} from a JS program`);
59
62
  }
60
63
  }
@@ -80,7 +83,6 @@ var init_lockdown = __esm({
80
83
  "cookieStore",
81
84
  "Worker",
82
85
  "SharedWorker",
83
- "BroadcastChannel",
84
86
  "postMessage",
85
87
  "close",
86
88
  "webkitRequestFileSystem",
@@ -97,7 +99,7 @@ var init_lockdown = __esm({
97
99
  "hid",
98
100
  "serial"
99
101
  ];
100
- OPEN_SLOTS = ["fetch", "WebSocket"];
102
+ OPEN_SLOTS = ["fetch", "WebSocket", "BroadcastChannel"];
101
103
  }
102
104
  });
103
105
 
@@ -255,6 +257,10 @@ var init_protocol = __esm({
255
257
  });
256
258
 
257
259
  // src/kernel/net/loopback-names.ts
260
+ function isKernelLoopbackHost(hostname) {
261
+ const host = hostname.replace(/^\[(.*)\]$/, "$1").replace(/\.$/, "").toLowerCase();
262
+ return host === "localhost" || host.endsWith(".localhost") || host === "0.0.0.0" || LOOPBACK_V4.test(host) || LOOPBACK_V6.has(host) || MAPPED_V4.test(host);
263
+ }
258
264
  function reserved(name2) {
259
265
  const lower = name2.toLowerCase();
260
266
  return lower === "localhost" || lower.endsWith(".localhost") || lower === HOST_LOOPBACK || lower === "wasmer.sh" || /^\d+(\.\d+){3}$/.test(lower);
@@ -278,7 +284,7 @@ function hostsFile(hostname = DEFAULT_HOSTNAME) {
278
284
  ""
279
285
  ].join("\n");
280
286
  }
281
- var HOST_LOOPBACK, HOST_LOOPBACK_ADDRESS, PAGE_LOOPBACK, PAGE_LOOPBACK_URL, DEFAULT_HOSTNAME, HOSTNAME_ADDRESS, LIBC_HOSTNAMES, LABEL;
287
+ var HOST_LOOPBACK, HOST_LOOPBACK_ADDRESS, PAGE_LOOPBACK, PAGE_LOOPBACK_URL, LOOPBACK_V4, LOOPBACK_V6, MAPPED_V4, DEFAULT_HOSTNAME, HOSTNAME_ADDRESS, LIBC_HOSTNAMES, LABEL;
282
288
  var init_loopback_names = __esm({
283
289
  "src/kernel/net/loopback-names.ts"() {
284
290
  "use strict";
@@ -286,6 +292,9 @@ var init_loopback_names = __esm({
286
292
  HOST_LOOPBACK_ADDRESS = [10, 0, 2, 2];
287
293
  PAGE_LOOPBACK = "kernel.localhost";
288
294
  PAGE_LOOPBACK_URL = `http://{port}.${PAGE_LOOPBACK}`;
295
+ LOOPBACK_V4 = /^127\.\d{1,3}\.\d{1,3}\.\d{1,3}$/;
296
+ LOOPBACK_V6 = /* @__PURE__ */ new Set(["::1", "::", "0:0:0:0:0:0:0:1"]);
297
+ MAPPED_V4 = /^::ffff:7f[0-9a-f]{2}:[0-9a-f]{1,4}$/;
289
298
  DEFAULT_HOSTNAME = "slicc";
290
299
  HOSTNAME_ADDRESS = "127.0.1.1";
291
300
  LIBC_HOSTNAMES = ["emscripten", "wasmer.sh"];
@@ -1128,6 +1137,7 @@ function toMs(v) {
1128
1137
  return v instanceof Date ? v.getTime() : v;
1129
1138
  }
1130
1139
  function wantOf(flags) {
1140
+ if (flags & O_PATH) return 0;
1131
1141
  const mode = flags & O_ACCMODE;
1132
1142
  const read2 = mode === 1 ? 0 : HOLD_READ;
1133
1143
  const write2 = mode !== 0 || (flags & O_TRUNC) !== 0 ? HOLD_WRITE : 0;
@@ -3762,12 +3772,12 @@ function anySelect(Fs, transport, read2, write2, timeoutMs) {
3762
3772
  const kernelRead = read2.filter((fd) => !own(fd));
3763
3773
  const kernelWrite = write2.filter((fd) => !own(fd));
3764
3774
  for (; ; ) {
3765
- const local2 = ownReady(Fs, read2.filter(own), write2.filter(own));
3766
- const pending = local2.read.length > 0 || local2.write.length > 0;
3775
+ const local3 = ownReady(Fs, read2.filter(own), write2.filter(own));
3776
+ const pending = local3.read.length > 0 || local3.write.length > 0;
3767
3777
  const slice = pending ? 0 : Math.min(SELECT_SLICE_MS, Math.max(0, deadline - Date.now()));
3768
3778
  const got = kernelSelect(Fs, transport, kernelRead, kernelWrite, slice);
3769
3779
  if (typeof got === "number") return got;
3770
- const ready = { read: [...local2.read, ...got.read], write: [...local2.write, ...got.write] };
3780
+ const ready = { read: [...local3.read, ...got.read], write: [...local3.write, ...got.write] };
3771
3781
  if (ready.read.length > 0 || ready.write.length > 0 || Date.now() >= deadline) {
3772
3782
  return ready;
3773
3783
  }
@@ -4285,7 +4295,7 @@ var KERNEL_VERSION, OS_RELEASE;
4285
4295
  var init_version = __esm({
4286
4296
  "src/version.ts"() {
4287
4297
  "use strict";
4288
- KERNEL_VERSION = true ? "1.90.0" : "0.0.0-dev";
4298
+ KERNEL_VERSION = true ? "1.92.0" : "0.0.0-dev";
4289
4299
  OS_RELEASE = "6.0.0-slicc";
4290
4300
  }
4291
4301
  });
@@ -6821,34 +6831,40 @@ function readyEvents(subs, ready) {
6821
6831
  hangup: ready.hangup?.includes(s.fd) === true
6822
6832
  }));
6823
6833
  }
6834
+ function selectOnce(deps, read2, write2, timeoutMs) {
6835
+ try {
6836
+ const ready = deps.kernel.call({ op: "fd-select", read: read2, write: write2, timeoutMs });
6837
+ return { ready, interrupted: false };
6838
+ } catch (e) {
6839
+ if (!deps.interruptWakes || e.code !== "EINTR") throw e;
6840
+ return { ready: { read: [], write: [] }, interrupted: true };
6841
+ }
6842
+ }
6843
+ function waitEvents(deps, subs, { events, read: read2, write: write2 }, entered) {
6844
+ const earliest = subs.reduce((min, s) => Math.min(min, s.deadline), Infinity);
6845
+ const timeout = () => {
6846
+ if (events.length > 0 || entered) return 0;
6847
+ return earliest === Infinity ? -1 : Math.max(0, Math.ceil(earliest - performance.now()));
6848
+ };
6849
+ for (; ; ) {
6850
+ const { ready, interrupted } = selectOnce(deps, read2, write2, timeout());
6851
+ events.push(...readyEvents(subs, ready));
6852
+ if (interrupted) return true;
6853
+ if (events.length > 0 || entered || earliest === Infinity) return false;
6854
+ if (performance.now() >= earliest) return false;
6855
+ }
6856
+ }
6824
6857
  function pollOneoff(deps, inPtr, outPtr, nsubs, neventsPtr) {
6825
6858
  if (nsubs === 0) return E.INVAL;
6826
- const { mem, kernel } = deps;
6859
+ const { mem } = deps;
6827
6860
  const subs = readSubscriptions(mem, inPtr, nsubs, deps.now);
6828
- const { events, read: read2, write: write2 } = classify(deps.fds, subs);
6829
- let interrupted = false;
6830
- const earliest = subs.reduce((min, s) => Math.min(min, s.deadline), Infinity);
6831
- const expired = () => performance.now() >= earliest;
6832
- if (read2.length > 0 || write2.length > 0 || events.length === 0) {
6833
- do {
6834
- let timeoutMs = -1;
6835
- if (events.length > 0) timeoutMs = 0;
6836
- else if (earliest !== Infinity)
6837
- timeoutMs = Math.max(0, Math.ceil(earliest - performance.now()));
6838
- let ready;
6839
- try {
6840
- ready = kernel.call({ op: "fd-select", read: read2, write: write2, timeoutMs });
6841
- } catch (e) {
6842
- if (!deps.interruptWakes || e.code !== "EINTR") throw e;
6843
- interrupted = true;
6844
- ready = { read: [], write: [] };
6845
- }
6846
- events.push(
6847
- ...readyEvents(subs, ready)
6848
- );
6849
- } while (events.length === 0 && !interrupted && earliest !== Infinity && !expired());
6850
- }
6861
+ const found = classify(deps.fds, subs);
6862
+ const { events, read: read2, write: write2 } = found;
6863
+ const entered = deps.entered === true && deps.interruptWakes !== true;
6864
+ const waits = read2.length > 0 || write2.length > 0 || events.length === 0;
6865
+ const interrupted = waits && waitEvents(deps, subs, found, entered);
6851
6866
  const after = performance.now();
6867
+ if (entered && events.length === 0 && !subs.some((s) => s.deadline <= after)) return E.INTR;
6852
6868
  for (const s of subs) {
6853
6869
  if (s.type === EVENTTYPE.CLOCK && (interrupted || s.deadline <= after)) {
6854
6870
  events.push({ userdata: s.userdata, error: E.SUCCESS, type: s.type });
@@ -7054,6 +7070,7 @@ var init_wasi_host = __esm({
7054
7070
  cache;
7055
7071
  startCwd;
7056
7072
  interruptWakes = false;
7073
+ entered = false;
7057
7074
  onRaise;
7058
7075
  muted;
7059
7076
  signals;
@@ -7277,7 +7294,8 @@ var init_wasi_host = __esm({
7277
7294
  fds: this.fds,
7278
7295
  kernel: this.o.kernel,
7279
7296
  now: (id) => this.now(id),
7280
- interruptWakes: this.interruptWakes
7297
+ interruptWakes: this.interruptWakes,
7298
+ entered: this.entered
7281
7299
  },
7282
7300
  inPtr,
7283
7301
  outPtr,
@@ -7294,7 +7312,7 @@ var init_wasi_host = __esm({
7294
7312
  this.mem.view().setUint32(nevents, 0, true);
7295
7313
  if (mask.deliverUnblocked()) return E.INTR;
7296
7314
  if (n > 0) return this.poll(inPtr, outPtr, n, nevents);
7297
- return this.suspend();
7315
+ return this.entered ? E.INTR : this.suspend();
7298
7316
  } finally {
7299
7317
  mask.deliverUnblocked();
7300
7318
  mask.restore(old);
@@ -8220,6 +8238,7 @@ function importsContext({
8220
8238
  fs,
8221
8239
  fds,
8222
8240
  syscall: call2,
8241
+ net: network(raw, call2),
8223
8242
  ...processes(host, call2, tid !== MAIN_TID),
8224
8243
  async: {
8225
8244
  submit: (req) => call2({ op: "async-submit", req }),
@@ -8255,6 +8274,30 @@ function importsContext({
8255
8274
  gid: { get: () => live().gid, enumerable: true }
8256
8275
  });
8257
8276
  }
8277
+ function loopbackHost(host) {
8278
+ if (host === "localhost") return "127.0.0.1";
8279
+ if (typeof host === "string" && LOOPBACK.test(host)) return host;
8280
+ throw new WasiError("EINVAL");
8281
+ }
8282
+ function network(raw, call2) {
8283
+ return {
8284
+ connect({ host, port: port2, nonblock = false }) {
8285
+ const to = loopbackHost(host);
8286
+ if (!Number.isInteger(port2) || port2 < 1 || port2 > 65535) throw new WasiError("EINVAL");
8287
+ const fd = call2({ op: "sock-open", domain: "inet" });
8288
+ const addr = { family: "inet", host: to, port: port2 };
8289
+ const r = raw({ op: "sock-connect", fd, addr, ...nonblock ? { nonblock: true } : {} });
8290
+ if (r.ok || nonblock && r.errno === "EINPROGRESS") return fd;
8291
+ raw({ op: "fd-close", fd });
8292
+ throw new WasiError(r.errno);
8293
+ },
8294
+ ready(fd) {
8295
+ const sel = call2({ op: "fd-select", read: [], write: [fd], timeoutMs: 0 });
8296
+ if (!sel.write.includes(fd)) return E.INPROGRESS;
8297
+ return call2({ op: "sock-getopt", fd, level: SOL_SOCKET, name: SO_ERROR });
8298
+ }
8299
+ };
8300
+ }
8258
8301
  function processes(host, call2, inThread) {
8259
8302
  const close = (fd) => void call2({ op: "fd-close", fd });
8260
8303
  const slot2 = (n, how, mine, theirs) => {
@@ -8312,7 +8355,7 @@ function processes(host, call2, inThread) {
8312
8355
  }
8313
8356
  };
8314
8357
  }
8315
- var UID2, STDIO;
8358
+ var UID2, LOOPBACK, SOL_SOCKET, SO_ERROR, STDIO;
8316
8359
  var init_wasi_imports = __esm({
8317
8360
  "src/process/wasi/wasi-imports.ts"() {
8318
8361
  "use strict";
@@ -8321,6 +8364,9 @@ var init_wasi_imports = __esm({
8321
8364
  init_wasi_threads();
8322
8365
  init_wasix_process();
8323
8366
  UID2 = 1e3;
8367
+ LOOPBACK = /^127\.\d{1,3}\.\d{1,3}\.\d{1,3}$/;
8368
+ SOL_SOCKET = 1;
8369
+ SO_ERROR = 4;
8324
8370
  STDIO = ["stdin", "stdout", "stderr"];
8325
8371
  }
8326
8372
  });
@@ -10045,7 +10091,7 @@ function readAddr(view, ptr) {
10045
10091
  function ipv6Host(bytes) {
10046
10092
  const zeros = (n) => bytes.subarray(0, n).every((b) => b === 0);
10047
10093
  if (zeros(16)) return "0.0.0.0";
10048
- if (zeros(15) && bytes[15] === 1) return LOOPBACK;
10094
+ if (zeros(15) && bytes[15] === 1) return LOOPBACK2;
10049
10095
  if (zeros(10) && bytes[10] === 255 && bytes[11] === 255) return bytes.subarray(12).join(".");
10050
10096
  const groups = [0, 2, 4, 6, 8, 10, 12, 14].map(
10051
10097
  (i) => (bytes[i] << 8 | bytes[i + 1]).toString(16)
@@ -10202,7 +10248,7 @@ function wasixSocketImports(host, preview1) {
10202
10248
  }
10203
10249
  };
10204
10250
  }
10205
- var INET4, INET6, UNIX, STREAM, ADDR_IP_SIZE, LOOPBACK, OPTIONS;
10251
+ var INET4, INET6, UNIX, STREAM, ADDR_IP_SIZE, LOOPBACK2, OPTIONS;
10206
10252
  var init_wasix_sockets = __esm({
10207
10253
  "src/process/wasi/wasix-sockets.ts"() {
10208
10254
  "use strict";
@@ -10214,7 +10260,7 @@ var init_wasix_sockets = __esm({
10214
10260
  UNIX = 3;
10215
10261
  STREAM = 1;
10216
10262
  ADDR_IP_SIZE = 18;
10217
- LOOPBACK = "127.0.0.1";
10263
+ LOOPBACK2 = "127.0.0.1";
10218
10264
  OPTIONS = {
10219
10265
  1: [1, 15],
10220
10266
  2: [1, 2],
@@ -10601,10 +10647,8 @@ var init_wasix_host = __esm({
10601
10647
  const v = mem.view();
10602
10648
  const timed = timeoutPtr !== 0 && v.getUint8(timeoutPtr) === 1;
10603
10649
  const ms = timed ? Number(v.getBigUint64(timeoutPtr + 8, true)) / 1e6 : Number.POSITIVE_INFINITY;
10604
- v.setUint8(
10605
- wokenPtr,
10606
- futexWait(i32(), ptr >> 2, expected | 0, ms, host.interrupted) ? 1 : 0
10607
- );
10650
+ const woken = host.entered || futexWait(i32(), ptr >> 2, expected | 0, ms, host.interrupted);
10651
+ v.setUint8(wokenPtr, woken ? 1 : 0);
10608
10652
  },
10609
10653
  futex_wake: (ptr, wokenPtr) => {
10610
10654
  Atomics.notify(i32(), ptr >> 2, 1);
@@ -10772,9 +10816,10 @@ function delivering(ns, table, host, driver, before) {
10772
10816
  }
10773
10817
  const fn = value2;
10774
10818
  out[name2] = (...args) => {
10819
+ host.entered = false;
10775
10820
  if (driver.idle) {
10776
10821
  before?.();
10777
- host.interrupted?.();
10822
+ host.entered = host.interrupted?.() === true;
10778
10823
  }
10779
10824
  return fn(...args);
10780
10825
  };
@@ -11439,6 +11484,13 @@ var init_async_sab = __esm({
11439
11484
  });
11440
11485
 
11441
11486
  // src/process/js/js-kernel.ts
11487
+ function umaskRequest(mask) {
11488
+ if (mask === void 0) return { op: "proc-umask" };
11489
+ if (!Number.isInteger(mask) || mask < 0 || mask > 511) {
11490
+ throw new JsCallError("EINVAL", "umask");
11491
+ }
11492
+ return { op: "proc-umask", mask };
11493
+ }
11442
11494
  function modeOf(mode) {
11443
11495
  if (!Number.isInteger(mode) || mode < 0 || mode > 4095) {
11444
11496
  throw new JsCallError("EINVAL", "chmod");
@@ -11920,7 +11972,8 @@ function openRequest(abs, o) {
11920
11972
  flags: flagsOf(o),
11921
11973
  position: 0,
11922
11974
  ...isExclusive(o) ? { exclusive: true } : o.create ? { create: true } : { existing: true },
11923
- ...o.truncate ? { truncate: true } : {}
11975
+ ...o.truncate ? { truncate: true } : {},
11976
+ ...o.create || isExclusive(o) ? { mode: o.mode === void 0 ? 438 : modeOf(o.mode) } : {}
11924
11977
  };
11925
11978
  }
11926
11979
  function index2(n, what) {
@@ -12383,11 +12436,20 @@ function plain(status2, text) {
12383
12436
  headers: { "content-type": "text/plain; charset=utf-8" }
12384
12437
  });
12385
12438
  }
12439
+ function local2(url) {
12440
+ return isKernelLoopbackHost(new URL(url).hostname);
12441
+ }
12386
12442
  function rewrite(hop, status2, location) {
12387
12443
  const next2 = new URL(location, hop.url);
12388
12444
  if (next2.protocol !== "http:" && next2.protocol !== "https:") {
12389
12445
  throw failed3(new JsCallError("EPROTONOSUPPORT", next2.protocol));
12390
12446
  }
12447
+ if (local2(next2.href) && !local2(hop.url)) {
12448
+ const from = new URL(hop.url).origin;
12449
+ throw failed3(
12450
+ new JsCallError("EACCES", `a redirect from ${from} into the kernel's loopback: ${next2.href}`)
12451
+ );
12452
+ }
12391
12453
  const toGet = (status2 === 301 || status2 === 302) && hop.method === "POST" || status2 === 303 && hop.method !== "GET" && hop.method !== "HEAD";
12392
12454
  const crossOrigin = next2.origin !== new URL(hop.url).origin;
12393
12455
  const headers = hop.headers.filter(
@@ -12556,13 +12618,15 @@ async function bodyOf(request, cap, signal) {
12556
12618
  return out;
12557
12619
  }
12558
12620
  function fetchOp(kernel) {
12559
- let traits;
12560
- const traitsOf = () => {
12561
- traits ??= kernel.json({ op: "net-traits" });
12562
- traits.catch(() => {
12563
- traits = void 0;
12621
+ const traits = /* @__PURE__ */ new Map();
12622
+ const traitsOf = (url) => {
12623
+ const own = local2(url);
12624
+ const known = traits.get(own) ?? kernel.json({ op: "net-traits", url });
12625
+ traits.set(own, known);
12626
+ known.catch(() => {
12627
+ traits.delete(own);
12564
12628
  });
12565
- return traits;
12629
+ return known;
12566
12630
  };
12567
12631
  const close = (handle) => kernel.raw({ op: "net-close", handle });
12568
12632
  const send = async (hop, signal) => {
@@ -12649,6 +12713,13 @@ function fetchOp(kernel) {
12649
12713
  });
12650
12714
  return withMeta(response, head.url, redirected);
12651
12715
  };
12716
+ const traitsAt = (at) => traitsOf(at).catch((err) => {
12717
+ throw failed3(err);
12718
+ });
12719
+ const redirect = async (hop, status2, location, known) => {
12720
+ const next2 = rewrite(hop, status2, location);
12721
+ return [next2, local2(next2.url) === local2(hop.url) ? known : await traitsAt(next2.url)];
12722
+ };
12652
12723
  return async (input, init) => {
12653
12724
  const request = new Request(input, init);
12654
12725
  const { signal } = request;
@@ -12658,9 +12729,7 @@ function fetchOp(kernel) {
12658
12729
  if (protocol !== "http:" && protocol !== "https:") {
12659
12730
  throw failed3(new JsCallError("EPROTONOSUPPORT", protocol));
12660
12731
  }
12661
- const known = await traitsOf().catch((err) => {
12662
- throw failed3(err);
12663
- });
12732
+ let known = await traitsAt(request.url);
12664
12733
  if (!known.manualRedirects && request.redirect !== "follow") {
12665
12734
  throw failed3(new JsCallError("ENOTSUP", `redirect: ${request.redirect}`));
12666
12735
  }
@@ -12686,7 +12755,7 @@ function fetchOp(kernel) {
12686
12755
  await close(head.handle);
12687
12756
  if (request.redirect === "error") throw failed3(new JsCallError("EREDIRECT", hop.url));
12688
12757
  if (hops >= MAX_REDIRECTS) throw failed3(new JsCallError("ELOOP", hop.url));
12689
- hop = rewrite(hop, head.status, location);
12758
+ [hop, known] = await redirect(hop, head.status, location, known);
12690
12759
  }
12691
12760
  };
12692
12761
  }
@@ -12694,6 +12763,7 @@ var CHUNK2, MAX_REDIRECTS, NULL_BODY, REDIRECTS, BODY_HEADERS, DECODED, CREDENTI
12694
12763
  var init_js_fetch = __esm({
12695
12764
  "src/process/js/js-fetch.ts"() {
12696
12765
  "use strict";
12766
+ init_loopback_names();
12697
12767
  init_js_kernel();
12698
12768
  CHUNK2 = 64 * 1024;
12699
12769
  MAX_REDIRECTS = 20;
@@ -12733,7 +12803,7 @@ function port(n) {
12733
12803
  function netOps(kernel, io) {
12734
12804
  const name2 = async (fd, peer) => addressOf(await kernel.json({ op: "sock-name", fd, peer }));
12735
12805
  const connection = async (fd) => {
12736
- const [local2, remote] = [await name2(fd, false), await name2(fd, true)];
12806
+ const [local3, remote] = [await name2(fd, false), await name2(fd, true)];
12737
12807
  const stop = new AbortController();
12738
12808
  let closed;
12739
12809
  const close = () => {
@@ -12758,7 +12828,7 @@ function netOps(kernel, io) {
12758
12828
  close: async () => void await shut(SHUT_WR),
12759
12829
  abort: () => close()
12760
12830
  });
12761
- return { fd, local: local2, remote, readable: readable3, writable: writable2, close };
12831
+ return { fd, local: local3, remote, readable: readable3, writable: writable2, close };
12762
12832
  };
12763
12833
  const resolve = async (host, signal) => {
12764
12834
  if (IPV4.test(host)) return host;
@@ -12834,8 +12904,8 @@ function netOps(kernel, io) {
12834
12904
  const failed5 = await kernel.json({
12835
12905
  op: "sock-getopt",
12836
12906
  fd,
12837
- level: SOL_SOCKET,
12838
- name: SO_ERROR
12907
+ level: SOL_SOCKET2,
12908
+ name: SO_ERROR2
12839
12909
  });
12840
12910
  if (failed5 !== 0) throw new JsCallError(errnoName(failed5), "connect");
12841
12911
  return connection(fd);
@@ -12843,7 +12913,7 @@ function netOps(kernel, io) {
12843
12913
  }
12844
12914
  };
12845
12915
  }
12846
- var SHUT_RD, SHUT_WR, IPV4, NEVER, SOL_SOCKET, SO_ERROR;
12916
+ var SHUT_RD, SHUT_WR, IPV4, NEVER, SOL_SOCKET2, SO_ERROR2;
12847
12917
  var init_js_net = __esm({
12848
12918
  "src/process/js/js-net.ts"() {
12849
12919
  "use strict";
@@ -12853,8 +12923,8 @@ var init_js_net = __esm({
12853
12923
  SHUT_WR = 1;
12854
12924
  IPV4 = /^\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}$/;
12855
12925
  NEVER = new AbortController().signal;
12856
- SOL_SOCKET = 1;
12857
- SO_ERROR = 4;
12926
+ SOL_SOCKET2 = 1;
12927
+ SO_ERROR2 = 4;
12858
12928
  }
12859
12929
  });
12860
12930
 
@@ -13257,7 +13327,8 @@ function syncPathOps(kernel, resolve, statOf, open) {
13257
13327
  mkdir: (path, options) => void kernel.call({
13258
13328
  op: "mkdir",
13259
13329
  path: resolve(path),
13260
- ...options?.recursive === false ? { exclusive: true } : {}
13330
+ ...options?.recursive === false ? { exclusive: true } : {},
13331
+ mode: options?.mode === void 0 ? 511 : modeOf(options.mode)
13261
13332
  }),
13262
13333
  rm: (path) => void kernel.call({ op: "rm", path: resolve(path) }),
13263
13334
  unlink: (path) => void kernel.call({ op: "unlink", path: resolve(path) }),
@@ -13281,8 +13352,14 @@ function syncPathOps(kernel, resolve, statOf, open) {
13281
13352
  kernel.call({ op: "fd-path-flush", path: abs });
13282
13353
  return kernel.bytes({ op: "read", path: abs });
13283
13354
  },
13284
- writeFile(path, data) {
13285
- const file = open(path, { write: true, create: true, truncate: true });
13355
+ writeFile(path, data, options) {
13356
+ const mode = options?.mode;
13357
+ const file = open(path, {
13358
+ write: true,
13359
+ create: true,
13360
+ truncate: true,
13361
+ ...mode !== void 0 ? { mode } : {}
13362
+ });
13286
13363
  try {
13287
13364
  file.write(0, typeof data === "string" ? encoder3.encode(data) : data);
13288
13365
  } finally {
@@ -13781,6 +13858,7 @@ function createContext(o) {
13781
13858
  },
13782
13859
  kill: killer({ self: o.pid, kernel, syncKernel, lane, writes, modes: terminal.modes }),
13783
13860
  cred: () => syncKernel.json({ op: "proc-cred" }),
13861
+ umask: (mask) => syncKernel.json(umaskRequest(mask)),
13784
13862
  setcred(change) {
13785
13863
  if (typeof change !== "object" || change === null || Array.isArray(change)) {
13786
13864
  throw new JsCallError("EINVAL", "setcred");
@@ -13827,6 +13905,7 @@ function createContext(o) {
13827
13905
  },
13828
13906
  sync,
13829
13907
  fetch: fetchOp(kernel),
13908
+ umask: async (mask) => await kernel.json(umaskRequest(mask)),
13830
13909
  sudo: async (args) => await kernel.json({
13831
13910
  op: "proc-sudo",
13832
13911
  args: [...args],
@@ -13976,7 +14055,8 @@ function pathOps(kernel, resolve, statOf, open) {
13976
14055
  mkdir: async (path, options) => void await kernel.call({
13977
14056
  op: "mkdir",
13978
14057
  path: resolve(path),
13979
- ...options?.recursive === false ? { exclusive: true } : {}
14058
+ ...options?.recursive === false ? { exclusive: true } : {},
14059
+ mode: options?.mode === void 0 ? 511 : modeOf(options.mode)
13980
14060
  }),
13981
14061
  rm: async (path) => void await kernel.call({ op: "rm", path: resolve(path) }),
13982
14062
  unlink: async (path) => void await kernel.call({ op: "unlink", path: resolve(path) }),
@@ -14000,8 +14080,14 @@ function pathOps(kernel, resolve, statOf, open) {
14000
14080
  await kernel.call({ op: "fd-path-flush", path: abs });
14001
14081
  return kernel.bytes({ op: "read", path: abs });
14002
14082
  },
14003
- async writeFile(path, data) {
14004
- const file = await open(path, { write: true, create: true, truncate: true });
14083
+ async writeFile(path, data, options) {
14084
+ const mode = options?.mode;
14085
+ const file = await open(path, {
14086
+ write: true,
14087
+ create: true,
14088
+ truncate: true,
14089
+ ...mode !== void 0 ? { mode } : {}
14090
+ });
14005
14091
  try {
14006
14092
  await file.write(0, typeof data === "string" ? encoder4.encode(data) : data);
14007
14093
  } finally {