poe-code 14.0.74 → 14.0.75

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.
Files changed (38) hide show
  1. package/dist/index.js +926 -84
  2. package/dist/index.js.map +4 -4
  3. package/dist/metafile.json +1 -1
  4. package/package.json +1 -1
  5. package/packages/safe-js/dist/chunks/{chunk-2J6W3YGB.js → chunk-BAJI3K4B.js} +2 -2
  6. package/packages/safe-js/dist/chunks/{chunk-YEZOXLY4.js → chunk-EOTY4PCT.js} +901 -84
  7. package/packages/safe-js/dist/chunks/chunk-EOTY4PCT.js.map +7 -0
  8. package/packages/safe-js/dist/cli.js +2 -2
  9. package/packages/safe-js/dist/core.js +1 -1
  10. package/packages/safe-js/dist/index.js +2 -2
  11. package/packages/safe-js/dist/interp/globals/regex.js +108 -2
  12. package/packages/safe-js/dist/interp/iteration.js +5 -2
  13. package/packages/safe-js/dist/interp/methods/regex-split.d.ts +3 -0
  14. package/packages/safe-js/dist/interp/methods/regex-split.js +102 -0
  15. package/packages/safe-js/dist/interp/methods/regex.d.ts +1 -1
  16. package/packages/safe-js/dist/interp/methods/regex.js +16 -5
  17. package/packages/safe-js/dist/interp/methods/regexp-iterator.d.ts +5 -1
  18. package/packages/safe-js/dist/interp/methods/regexp-iterator.js +59 -7
  19. package/packages/safe-js/dist/interp/methods/string.js +7 -7
  20. package/packages/safe-js/dist/interp/object-model.d.ts +1 -0
  21. package/packages/safe-js/dist/interp/object-model.js +4 -1
  22. package/packages/safe-js/dist/interp/regex/compile-guard.js +26 -4
  23. package/packages/safe-js/dist/interp/regex/engine.d.ts +4 -0
  24. package/packages/safe-js/dist/interp/regex/engine.js +230 -30
  25. package/packages/safe-js/dist/interp/regex/parse.d.ts +42 -4
  26. package/packages/safe-js/dist/interp/regex/parse.js +429 -25
  27. package/packages/safe-js/dist/interp/regexp-iterator.d.ts +4 -2
  28. package/packages/safe-js/dist/interp/regexp-iterator.js +6 -1
  29. package/packages/safe-js/dist/interp/values.js +5 -3
  30. package/packages/safe-js/dist/snapshot/dump-format.js +10 -2
  31. package/packages/safe-js/dist/snapshot/replay-data.d.ts +3 -0
  32. package/packages/safe-js/dist/snapshot/replay-data.js +14 -4
  33. package/packages/safe-js/dist/snapshot/restore.js +8 -2
  34. package/packages/safe-js/dist/snapshot/serialize.d.ts +3 -0
  35. package/packages/safe-js/dist/snapshot/serialize.js +4 -1
  36. package/packages/safe-js/dist/snapshot/validation.js +8 -0
  37. package/packages/safe-js/dist/chunks/chunk-YEZOXLY4.js.map +0 -7
  38. /package/packages/safe-js/dist/chunks/{chunk-2J6W3YGB.js.map → chunk-BAJI3K4B.js.map} +0 -0
@@ -19,7 +19,7 @@ import { invokeCancelableClosure, readPromiseCancellation, registerPromiseCancel
19
19
  import { parseRegex } from "./regex/parse.js";
20
20
  import { assertSandboxDataDepth } from "../graph-depth.js";
21
21
  import { sandboxErrorTypes } from "../error/shape.js";
22
- import { getGuestFunctionProperties, getSandboxPrototype, hasGuestObjectState, hasManagedDescriptors, isGuestClosure, isIntrinsicConstructor, registerGuestClosure } from "./object-model.js";
22
+ import { getGuestFunctionProperties, getSandboxPrototype, hasGuestObjectState, hasManagedDescriptors, hasNullObjectPrototype, isGuestClosure, isIntrinsicConstructor, registerGuestClosure, setSandboxPrototype } from "./object-model.js";
23
23
  import { copySandboxArgumentProperties, createSandboxArguments, getSandboxArgumentEntries, isSandboxArguments } from "./arguments.js";
24
24
  export { createSandboxArguments, isSandboxArguments } from "./arguments.js";
25
25
  export { isSandboxMap, isSandboxSet } from "./collection-brands.js";
@@ -612,7 +612,7 @@ function copyToSandbox(value, state, path = "<root>", cloneSandboxCollections =
612
612
  const copy = restoreSandboxRegExpIterator({ matcher: undefined, input: undefined, exhausted: true });
613
613
  state.seen.set(value, copy);
614
614
  const matcher = copyToSandbox(snapshot.matcher, state, `${path}.<matcher>`, true, depth + 1);
615
- if (matcher !== undefined && !isSandboxRegex(matcher))
615
+ if (matcher !== undefined && (snapshot.global === undefined ? !isSandboxRegex(matcher) : matcher === null || typeof matcher !== "object"))
616
616
  throw new TypeError("Invalid RegExp iterator matcher.");
617
617
  restoreSandboxRegExpIterator({ ...snapshot, matcher }, copy);
618
618
  for (const entry of getEnumerableObjectEntries(value, path)) {
@@ -781,6 +781,8 @@ function copyToSandbox(value, state, path = "<root>", cloneSandboxCollections =
781
781
  return existing;
782
782
  }
783
783
  const copy = createPlainObject(!cloneSandboxCollections || Object.getPrototypeOf(value) === null);
784
+ if (!state.structuredClone && hasNullObjectPrototype(value))
785
+ setSandboxPrototype(copy, null);
784
786
  state.seen.set(value, copy);
785
787
  const errorType = sandboxErrorTypes.get(value);
786
788
  if (errorType !== undefined)
@@ -978,7 +980,7 @@ function copyFromSandbox(value, state, path = "<root>", options, depth = 0) {
978
980
  if (existing !== undefined) {
979
981
  return existing;
980
982
  }
981
- const copy = createPlainObject(Object.getPrototypeOf(value) === null);
983
+ const copy = createPlainObject(hasNullObjectPrototype(value) || Object.getPrototypeOf(value) === null);
982
984
  state.seen.set(value, copy);
983
985
  for (const entry of getEnumerableObjectEntries(value, path)) {
984
986
  defineOwnDataProperty(copy, entry.key, copyFromSandbox(entry.value, state, joinPath(path, entry.key), options, depth + 1));
@@ -4,7 +4,7 @@ import { isSandboxRegExpIterator, regexpIteratorState } from "../interp/regexp-i
4
4
  import { hasCustomRegexProperties, serializeRegexProperties } from "./regexp-properties.js";
5
5
  export const EXECUTION_SEMANTICS = "jobs-v8";
6
6
  import { assertSnapshotGraphDepth } from "../graph-depth.js";
7
- import { hasGuestObjectState } from "../interp/object-model.js";
7
+ import { hasGuestObjectState, hasNullObjectPrototype } from "../interp/object-model.js";
8
8
  import { sandboxErrorTypes } from "../error/shape.js";
9
9
  import { getSandboxArgumentEntries, isSandboxArguments } from "../interp/arguments.js";
10
10
  import { serializeArguments } from "./arguments.js";
@@ -110,10 +110,16 @@ function serializeHeapReference(value, path, state) {
110
110
  if (isSandboxRegExpIterator(value)) {
111
111
  const snapshot = regexpIteratorState(value);
112
112
  const matcher = snapshot.matcher;
113
+ const serializedMatcher = snapshot.global === undefined && isSandboxRegex(matcher)
114
+ ? { kind: "regex", source: matcher.source, flags: matcher.flags, lastIndex: Number(matcher.lastIndex) }
115
+ : serializeDumpValue(matcher, `${path}.<matcher>`, state);
116
+ if (serializedMatcher === SKIP_VALUE)
117
+ throw new TypeError("Unsupported RegExp iterator matcher in public dump.");
113
118
  const entries = Object.create(null);
114
119
  state.heap[String(id)] = {
115
120
  kind: "regexp-iterator", exhausted: snapshot.exhausted,
116
- matcher: matcher === undefined ? { kind: "undefined" } : { kind: "regex", source: matcher.source, flags: matcher.flags, lastIndex: Number(matcher.lastIndex) },
121
+ matcher: serializedMatcher,
122
+ ...(snapshot.global === undefined ? {} : { global: snapshot.global, unicode: snapshot.unicode }),
117
123
  input: snapshot.input ?? { kind: "undefined" }, entries,
118
124
  symbolEntries: serializeSymbolProperties(value, entry => {
119
125
  const serialized = serializeDumpValue(entry, `${path}.[symbol]`, state);
@@ -192,6 +198,7 @@ function serializeHeapReference(value, path, state) {
192
198
  });
193
199
  state.heap[String(id)] = {
194
200
  kind: "object",
201
+ ...(hasNullObjectPrototype(value) ? { sandboxNullPrototype: true } : {}),
195
202
  entries: serializeObjectEntries(value, path, state),
196
203
  ...(symbolEntries.length === 0 ? {} : { symbolEntries }),
197
204
  ...(errorType === undefined ? {} : { errorType })
@@ -227,6 +234,7 @@ function indexHeapContainers(snapshot) {
227
234
  for (const [value, stat] of stats.entries()) {
228
235
  if (stat.count > 1 ||
229
236
  stat.cyclic ||
237
+ hasNullObjectPrototype(value) ||
230
238
  ownSerializableSymbolKeys(value).length > 0 ||
231
239
  isSandboxBox(value) ||
232
240
  isSandboxRegExpIterator(value) ||
@@ -32,6 +32,8 @@ type DataNode = {
32
32
  matcher: Atom;
33
33
  input: Atom;
34
34
  exhausted: boolean;
35
+ global?: boolean;
36
+ unicode?: boolean;
35
37
  properties: Properties;
36
38
  extensible: boolean;
37
39
  symbolEntries?: Array<SerializedSymbolProperty<Atom>>;
@@ -69,6 +71,7 @@ type DataNode = {
69
71
  symbolProperties?: Array<SerializedSymbolProperty<Atom>>;
70
72
  extensible: boolean;
71
73
  nullPrototype: boolean;
74
+ sandboxNullPrototype?: true;
72
75
  errorType?: SandboxErrorName;
73
76
  } | {
74
77
  kind: "arguments";
@@ -4,7 +4,7 @@ import { wellKnownSymbols } from "../interp/symbols.js";
4
4
  import { symbolData, serializeSymbolProperties } from "./symbols.js";
5
5
  import { isSandboxCollectionIterator, restoreSandboxCollectionIterator, snapshotCollectionIterator } from "../interp/collection-iterator.js";
6
6
  import { isSandboxRegExpIterator, regexpIteratorState, restoreSandboxRegExpIterator } from "../interp/regexp-iterator.js";
7
- import { hasGuestObjectState } from "../interp/object-model.js";
7
+ import { hasGuestObjectState, hasNullObjectPrototype, setSandboxPrototype } from "../interp/object-model.js";
8
8
  import { CompileScope } from "../interp/regex/compile-guard.js";
9
9
  import { float32DataProperties, isFloat32Array } from "../interp/float32.js";
10
10
  import { decodeFloat32Storage, encodeFloat32Storage } from "./float32array.js";
@@ -134,7 +134,8 @@ export function encodeReplayData(value, options = {}) {
134
134
  }
135
135
  let symbolIndex = 0;
136
136
  const symbolEntries = serializeSymbolProperties(entry, value => encode(value, depth + 1, [...path, { symbol: Math.floor(symbolIndex++ / 2) }]));
137
- nodes[id] = { kind: "regexp-iterator", matcher: child(snapshot.matcher, "<matcher>"), input: child(snapshot.input, "<input>"), exhausted: snapshot.exhausted, properties, extensible: Object.isExtensible(entry), symbolEntries };
137
+ nodes[id] = { kind: "regexp-iterator", matcher: child(snapshot.matcher, "<matcher>"), input: child(snapshot.input, "<input>"), exhausted: snapshot.exhausted, properties, extensible: Object.isExtensible(entry), symbolEntries,
138
+ ...(snapshot.global === undefined ? {} : { global: snapshot.global, unicode: snapshot.unicode }) };
138
139
  }
139
140
  else if (isSandboxCollectionIterator(entry)) {
140
141
  const snapshot = snapshotCollectionIterator(entry);
@@ -195,6 +196,7 @@ export function encodeReplayData(value, options = {}) {
195
196
  nodes[id] = {
196
197
  kind: Array.isArray(entry) ? "array" : "object",
197
198
  nullPrototype: prototype === null,
199
+ ...(hasNullObjectPrototype(entry) ? { sandboxNullPrototype: true } : {}),
198
200
  ...(errorType === undefined ? {} : { errorType }),
199
201
  extensible: Object.isExtensible(entry),
200
202
  properties,
@@ -365,11 +367,14 @@ export function decodeReplayData(input, options = {}, parent) {
365
367
  restored.set(id, result);
366
368
  const matcher = child(own(node, "matcher"));
367
369
  const input = child(own(node, "input"));
368
- if (matcher !== undefined && !isSandboxRegex(matcher))
370
+ if ((node.global !== undefined || node.unicode !== undefined) && (typeof node.global !== "boolean" || typeof node.unicode !== "boolean"))
371
+ throw new TypeError("Invalid replay RegExp iterator modes.");
372
+ if (matcher !== undefined && (node.global === undefined ? !isSandboxRegex(matcher) : matcher === null || typeof matcher !== "object"))
369
373
  throw new TypeError("Invalid replay RegExp iterator matcher.");
370
374
  if (input !== undefined && typeof input !== "string")
371
375
  throw new TypeError("Invalid replay RegExp iterator input.");
372
- restoreSandboxRegExpIterator({ matcher, input, exhausted }, result);
376
+ restoreSandboxRegExpIterator({ matcher, input, exhausted,
377
+ ...(node.global === undefined ? {} : { global: node.global, unicode: node.unicode }) }, result);
373
378
  defineProperties(result, record(own(node, "properties")), child, node.symbolEntries);
374
379
  if (!node.extensible)
375
380
  Object.preventExtensions(result);
@@ -450,6 +455,11 @@ export function decodeReplayData(input, options = {}, parent) {
450
455
  throw new TypeError("Invalid replay object metadata.");
451
456
  }
452
457
  const result = kind === "array" ? [] : Object.create(node.nullPrototype ? null : Object.prototype);
458
+ if (Object.hasOwn(node, "sandboxNullPrototype")) {
459
+ if (kind !== "object" || node.sandboxNullPrototype !== true)
460
+ throw new TypeError("Invalid replay object prototype.");
461
+ setSandboxPrototype(result, null);
462
+ }
453
463
  if (Object.hasOwn(node, "errorType")) {
454
464
  sandboxErrorTypes.set(result, node.errorType);
455
465
  }
@@ -439,11 +439,12 @@ function restoreHeapValue(id, state) {
439
439
  state.heapValueById.set(id, iterator);
440
440
  const matcher = deserializeValue(serialized.matcher, state);
441
441
  const input = deserializeValue(serialized.input, state);
442
- if (matcher !== undefined && !isSandboxRegex(matcher))
442
+ if (matcher !== undefined && (serialized.global === undefined ? !isSandboxRegex(matcher) : matcher === null || typeof matcher !== "object"))
443
443
  throw new TypeError("Invalid RegExp iterator matcher.");
444
444
  if (input !== undefined && typeof input !== "string")
445
445
  throw new TypeError("Invalid RegExp iterator input.");
446
- restoreSandboxRegExpIterator({ matcher, input, exhausted: serialized.exhausted }, iterator);
446
+ restoreSandboxRegExpIterator({ matcher: matcher, input, exhausted: serialized.exhausted,
447
+ ...(serialized.global === undefined ? {} : { global: serialized.global, unicode: serialized.unicode }) }, iterator);
447
448
  for (const [key, entry] of Object.entries(serialized.entries))
448
449
  Object.defineProperty(iterator, key, { value: deserializeValue(entry, state), enumerable: true, configurable: true, writable: true });
449
450
  restoreSymbolProperties(iterator, serialized.symbolEntries, entry => deserializeValue(entry, state));
@@ -478,6 +479,11 @@ function restoreHeapValue(id, state) {
478
479
  }
479
480
  const object = Object.create(null);
480
481
  state.heapValueById.set(id, object);
482
+ if (Object.hasOwn(serialized, "sandboxNullPrototype")) {
483
+ if (serialized.sandboxNullPrototype !== true)
484
+ throw new TypeError("Invalid object prototype.");
485
+ setSandboxPrototype(object, null);
486
+ }
481
487
  if (serialized.errorType !== undefined)
482
488
  sandboxErrorTypes.set(object, serialized.errorType);
483
489
  for (const [key, entry] of Object.entries(serialized.entries)) {
@@ -54,6 +54,8 @@ export type SerializedHeapValue = {
54
54
  matcher: SerializedSnapshotValue;
55
55
  input: SerializedSnapshotValue;
56
56
  exhausted: boolean;
57
+ global?: boolean;
58
+ unicode?: boolean;
57
59
  entries: Record<string, SerializedSnapshotValue>;
58
60
  symbolEntries?: Array<SerializedSymbolProperty<SerializedSnapshotValue>>;
59
61
  } | SerializedSymbol | BoxedData<SerializedSnapshotValue> | ({
@@ -73,6 +75,7 @@ export type SerializedHeapValue = {
73
75
  entries: Record<string, SerializedSnapshotValue>;
74
76
  }) | SerializedArguments<SerializedSnapshotValue> | SerializedArray<SerializedSnapshotValue> | {
75
77
  kind: "object";
78
+ sandboxNullPrototype?: true;
76
79
  entries: Record<string, SerializedSnapshotValue>;
77
80
  symbolEntries?: Array<SerializedSymbolProperty<SerializedSnapshotValue>>;
78
81
  errorType?: SandboxErrorName;
@@ -3,7 +3,7 @@ import { hasCustomRegexProperties, serializeRegexProperties } from "./regexp-pro
3
3
  import { ownSerializableSymbolKeys, serializeSymbol, serializeSymbolProperties } from "./symbols.js";
4
4
  import { collectionIteratorState, isSandboxCollectionIterator, snapshotCollectionIterator } from "../interp/collection-iterator.js";
5
5
  import { isSandboxRegExpIterator, regexpIteratorState } from "../interp/regexp-iterator.js";
6
- import { hasGuestObjectState } from "../interp/object-model.js";
6
+ import { hasGuestObjectState, hasNullObjectPrototype } from "../interp/object-model.js";
7
7
  import { sandboxErrorTypes } from "../error/shape.js";
8
8
  import { assertSnapshotGraphDepth } from "../graph-depth.js";
9
9
  import { serializeArguments } from "./arguments.js";
@@ -220,6 +220,7 @@ function serializeHeapReference(value, path, state) {
220
220
  const entries = Object.create(null);
221
221
  state.heap[String(id)] = {
222
222
  kind: "regexp-iterator", matcher: serializeValue(snapshot.matcher, `${path}.<matcher>`, state),
223
+ ...(snapshot.global === undefined ? {} : { global: snapshot.global, unicode: snapshot.unicode }),
223
224
  input: serializeValue(snapshot.input, `${path}.<input>`, state), exhausted: snapshot.exhausted, entries,
224
225
  symbolEntries: serializeSymbolProperties(value, entry => serializeValue(entry, `${path}.[symbol]`, state))
225
226
  };
@@ -283,6 +284,7 @@ function serializeHeapReference(value, path, state) {
283
284
  const errorType = sandboxErrorTypes.get(value);
284
285
  const serializedObject = {
285
286
  kind: "object",
287
+ ...(hasNullObjectPrototype(value) ? { sandboxNullPrototype: true } : {}),
286
288
  entries,
287
289
  ...(errorType === undefined ? {} : { errorType })
288
290
  };
@@ -359,6 +361,7 @@ function indexHeapContainers(input) {
359
361
  for (const [value, stat] of stats.entries()) {
360
362
  if (stat.count > 1 ||
361
363
  stat.cyclic ||
364
+ hasNullObjectPrototype(value) ||
362
365
  ownSerializableSymbolKeys(value).length > 0 ||
363
366
  (isSandboxRegex(value) && (hasCustomRegexProperties(value) || !Number.isSafeInteger(value.lastIndex) ||
364
367
  (typeof value.lastIndex === "number" && value.lastIndex < 0) || Object.is(value.lastIndex, -0))) ||
@@ -115,6 +115,8 @@ function validateDumpHeap(root, state) {
115
115
  continue;
116
116
  }
117
117
  if (entry.kind === "object") {
118
+ if (Object.hasOwn(entry, "sandboxNullPrototype") && entry.sandboxNullPrototype !== true)
119
+ fail("invalidValue", `${path}.sandboxNullPrototype`, "invalid object prototype");
118
120
  requireRecord(entry.entries, `${path}.entries`);
119
121
  continue;
120
122
  }
@@ -394,7 +396,11 @@ function validateTaggedValue(record, path, state) {
394
396
  return;
395
397
  case "array":
396
398
  case "arguments":
399
+ return;
397
400
  case "object":
401
+ if (Object.hasOwn(record, "sandboxNullPrototype") && record.sandboxNullPrototype !== true)
402
+ fail("invalidValue", `${path}.sandboxNullPrototype`, "invalid object prototype");
403
+ return;
398
404
  case "map":
399
405
  case "set":
400
406
  case "collection-iterator":
@@ -474,6 +480,8 @@ function validateHeapValue(value, path, state, heap) {
474
480
  if (record.kind === "set")
475
481
  requireArray(record.values, `${path}.values`, state);
476
482
  if (record.kind === "regexp-iterator") {
483
+ if ((record.global !== undefined || record.unicode !== undefined) && (typeof record.global !== "boolean" || typeof record.unicode !== "boolean"))
484
+ fail("invalidValue", path, "invalid RegExp iterator modes");
477
485
  if (typeof record.exhausted !== "boolean")
478
486
  fail("invalidValue", `${path}.exhausted`, "invalid iterator exhaustion");
479
487
  if (!Object.hasOwn(record, "matcher") || !Object.hasOwn(record, "input"))