@poe-platform/safe-bash 0.1.76 → 0.1.78

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.
@@ -4045,6 +4045,26 @@ function bindFileOutputBudget(context, budget) {
4045
4045
  if (!context.registerCleanup) throw new TypeError("Shell output budgets require invocation cleanup ownership");
4046
4046
  filesystemOutputBudgets.set(context.registerCleanup, budget);
4047
4047
  }
4048
+ async function writeFileOutput(context, bytes2, write2) {
4049
+ context.signal.throwIfAborted();
4050
+ const budget = context.registerCleanup && filesystemOutputBudgets.get(context.registerCleanup);
4051
+ let pending;
4052
+ const destination = { write(chunk) {
4053
+ context.signal.throwIfAborted();
4054
+ return pending = (async () => {
4055
+ await write2(chunk);
4056
+ })();
4057
+ } };
4058
+ try {
4059
+ await (budget?.(destination) ?? destination).write(bytes2);
4060
+ } catch (error) {
4061
+ await pending?.catch(() => {
4062
+ });
4063
+ context.signal.throwIfAborted();
4064
+ throw error;
4065
+ }
4066
+ context.signal.throwIfAborted();
4067
+ }
4048
4068
  async function openFileOutput(context, path, flag, incremental) {
4049
4069
  let pipe;
4050
4070
  let task;
@@ -16293,6 +16313,7 @@ var RegexExecutionError = class extends Error {
16293
16313
  }
16294
16314
  code;
16295
16315
  };
16316
+ var matchRangeLimits = Object.freeze({ perRow: 1e5, perReply: 1e5 });
16296
16317
  var exprMatchCeilings = Object.freeze({
16297
16318
  maxPatternBytes: 65536,
16298
16319
  maxSubjectBytes: 1048576,
@@ -16393,13 +16414,28 @@ function validateReply(value2, id, rows, signal) {
16393
16414
  throw new RegexExecutionError("MATCH", reply.error);
16394
16415
  }
16395
16416
  if (!("results" in reply) || !Array.isArray(reply.results) || reply.results.length !== rows.length) throw new RegexExecutionError("PROTOCOL", "invalid reply rows");
16396
- return reply.results.map((ranges, index) => {
16417
+ let total = 0;
16418
+ const lengths = [];
16419
+ for (let index = 0; index < reply.results.length; index++) {
16420
+ signal.throwIfAborted();
16421
+ const ranges = reply.results[index];
16422
+ const row = rows[index];
16423
+ if (!(ranges instanceof Float64Array)) throw new RegexExecutionError("PROTOCOL", "invalid match ranges");
16424
+ const length = ranges.length;
16425
+ if (length % 2 || length > 2 * (row.bytes.length + 1)) throw new RegexExecutionError("PROTOCOL", "invalid match ranges");
16426
+ if (!row.all && length > 2) throw new RegexExecutionError("PROTOCOL", "unexpected multiple matches");
16427
+ const count2 = length / 2;
16428
+ if (count2 > matchRangeLimits.perRow || count2 > matchRangeLimits.perReply - total) throw new RegexExecutionError("PROTOCOL", "match range limit exceeded");
16429
+ total += count2;
16430
+ lengths.push(length);
16431
+ }
16432
+ const results = reply.results.map((ranges, index) => {
16397
16433
  signal.throwIfAborted();
16398
- if (!(ranges instanceof Float64Array) || ranges.length % 2 || ranges.length > 2 * (rows[index].bytes.length + 1)) throw new RegexExecutionError("PROTOCOL", "invalid match ranges");
16434
+ const length = lengths[index];
16435
+ if (ranges.length !== length) throw new RegexExecutionError("PROTOCOL", "match ranges changed after admission");
16399
16436
  const result = [];
16400
16437
  const row = rows[index];
16401
- if (!row.all && ranges.length > 2) throw new RegexExecutionError("PROTOCOL", "unexpected multiple matches");
16402
- for (let offset = 0; offset < ranges.length; offset += 2) {
16438
+ for (let offset = 0; offset < length; offset += 2) {
16403
16439
  signal.throwIfAborted();
16404
16440
  const start = ranges[offset];
16405
16441
  const end = ranges[offset + 1];
@@ -16408,6 +16444,11 @@ function validateReply(value2, id, rows, signal) {
16408
16444
  }
16409
16445
  return result;
16410
16446
  });
16447
+ for (let index = 0; index < reply.results.length; index++) {
16448
+ signal.throwIfAborted();
16449
+ if (reply.results[index].length !== lengths[index]) throw new RegexExecutionError("PROTOCOL", "match ranges changed after admission");
16450
+ }
16451
+ return results;
16411
16452
  }
16412
16453
 
16413
16454
  // packages/safe-bash/src/commands/regex-execution/portable.ts
@@ -17523,7 +17564,7 @@ async function execute(program, context, files, quiet, budget) {
17523
17564
  appendedSize = 0;
17524
17565
  };
17525
17566
  const writeFile = async (file) => {
17526
- await context.fs.appendFile(virtualPath(context, file), bytes(pattern + "\n"), { signal: context.signal });
17567
+ await writeFileOutput(context, bytes(pattern + "\n"), (chunk) => context.fs.appendFile(virtualPath(context, file), chunk, { signal: context.signal }));
17527
17568
  };
17528
17569
  const matches = async (address) => address.kind === "number" ? number === address.number : address.kind === "last" ? (await peekNext()).done === true : getPattern(address.pattern).find(pattern, budget) !== void 0;
17529
17570
  for (let pc = 0; pc < program.length; ) {
@@ -17755,7 +17796,7 @@ function sedCommand(options3 = {}) {
17755
17796
  }
17756
17797
  const prepareOutputs = async () => {
17757
17798
  const paths = new Set(outputFiles.map((file) => virtualPath(context, file)));
17758
- for (const path of paths) await context.fs.writeFile(path, new Uint8Array(), { signal: context.signal });
17799
+ for (const path of paths) await writeFileOutput(context, new Uint8Array(), (chunk) => context.fs.writeFile(path, chunk, { signal: context.signal }));
17759
17800
  };
17760
17801
  if (inPlace !== void 0) {
17761
17802
  if (!files.length || files.includes("-")) throw new ProgramError("in-place editing requires named files");
@@ -17775,7 +17816,7 @@ function sedCommand(options3 = {}) {
17775
17816
  const result = await execute(program, child, [file], quiet, budget);
17776
17817
  const path = virtualPath(context, file);
17777
17818
  if (inPlace) await context.fs.copyFile(path, path + inPlace, { signal: context.signal });
17778
- await context.fs.writeFile(path, bytes(rewritten), { signal: context.signal });
17819
+ await writeFileOutput(context, bytes(rewritten), (chunk) => context.fs.writeFile(path, chunk, { signal: context.signal }));
17779
17820
  if (result.quit || result.status) return result.status;
17780
17821
  }
17781
17822
  return 0;