@agoric/swingset-liveslots 0.10.3-other-dev-1f26562.0 → 0.10.3-other-dev-3eb1a1d.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.
Files changed (77) hide show
  1. package/README.md +2 -0
  2. package/package.json +27 -19
  3. package/src/boyd-gc.js +598 -0
  4. package/src/cache.js +3 -2
  5. package/src/capdata.js +1 -2
  6. package/src/collectionManager.js +219 -103
  7. package/src/facetiousness.js +1 -1
  8. package/src/index.js +4 -2
  9. package/src/liveslots.js +131 -301
  10. package/src/message.js +5 -5
  11. package/src/parseVatSlots.js +1 -1
  12. package/src/types-index.d.ts +4 -0
  13. package/src/types-index.js +2 -0
  14. package/src/types.js +8 -2
  15. package/src/vatstore-iterators.js +2 -0
  16. package/src/virtualObjectManager.js +185 -71
  17. package/src/virtualReferences.js +135 -26
  18. package/src/watchedPromises.js +67 -17
  19. package/test/{test-baggage.js → baggage.test.js} +1 -2
  20. package/test/{test-cache.js → cache.test.js} +0 -1
  21. package/test/clear-collection.test.js +586 -0
  22. package/test/{test-collection-schema-refcount.js → collection-schema-refcount.test.js} +1 -2
  23. package/test/{test-collection-upgrade.js → collection-upgrade.test.js} +1 -3
  24. package/test/{test-collections.js → collections.test.js} +158 -14
  25. package/test/{test-dropped-collection-weakrefs.js → dropped-collection-weakrefs.test.js} +1 -2
  26. package/test/dropped-weakset-9939.test.js +80 -0
  27. package/test/dummyMeterControl.js +1 -1
  28. package/test/{test-durabilityChecks.js → durabilityChecks.test.js} +4 -4
  29. package/test/exo-utils.js +70 -0
  30. package/test/{test-facetiousness.js → facetiousness.test.js} +1 -2
  31. package/test/gc-and-finalize.js +30 -1
  32. package/test/gc-before-finalizer.test.js +230 -0
  33. package/test/gc-helpers.js +2 -3
  34. package/test/{test-gc-sensitivity.js → gc-sensitivity.test.js} +2 -2
  35. package/test/handled-promises.test.js +506 -0
  36. package/test/{test-initial-vrefs.js → initial-vrefs.test.js} +2 -3
  37. package/test/liveslots-helpers.js +12 -7
  38. package/test/{test-liveslots-mock-gc.js → liveslots-mock-gc.test.js} +101 -2
  39. package/test/{test-liveslots-real-gc.js → liveslots-real-gc.test.js} +62 -37
  40. package/test/{test-liveslots.js → liveslots.test.js} +14 -15
  41. package/test/mock-gc.js +1 -0
  42. package/test/storeGC/{test-lifecycle.js → lifecycle.test.js} +2 -2
  43. package/test/storeGC/{test-refcount-management.js → refcount-management.test.js} +1 -2
  44. package/test/storeGC/{test-scalar-store-kind.js → scalar-store-kind.test.js} +0 -1
  45. package/test/storeGC/{test-weak-key.js → weak-key.test.js} +1 -2
  46. package/test/strict-test-env-upgrade.test.js +94 -0
  47. package/test/util.js +2 -2
  48. package/test/vat-environment.test.js +65 -0
  49. package/test/vat-util.js +2 -2
  50. package/test/virtual-objects/{test-cease-recognition.js → cease-recognition.test.js} +2 -2
  51. package/test/virtual-objects/{test-cross-facet.js → cross-facet.test.js} +5 -4
  52. package/test/virtual-objects/{test-empty-data.js → empty-data.test.js} +1 -2
  53. package/test/virtual-objects/{test-facets.js → facets.test.js} +1 -2
  54. package/test/virtual-objects/{test-kind-changes.js → kind-changes.test.js} +2 -2
  55. package/test/virtual-objects/{test-reachable-vrefs.js → reachable-vrefs.test.js} +2 -2
  56. package/test/virtual-objects/{test-rep-tostring.js → rep-tostring.test.js} +3 -5
  57. package/test/virtual-objects/{test-retain-remotable.js → retain-remotable.test.js} +25 -24
  58. package/test/virtual-objects/set-debug-label-instances.js +1 -1
  59. package/test/virtual-objects/{test-state-shape.js → state-shape.test.js} +2 -2
  60. package/test/virtual-objects/{test-virtualObjectGC.js → virtualObjectGC.test.js} +2 -2
  61. package/test/virtual-objects/{test-virtualObjectManager.js → virtualObjectManager.test.js} +126 -8
  62. package/test/virtual-objects/{test-vo-real-gc.js → vo-real-gc.test.js} +8 -8
  63. package/test/virtual-objects/{test-weakcollections-vref-handling.js → weakcollections-vref-handling.test.js} +1 -2
  64. package/test/{test-vo-test-harness.js → vo-test-harness.test.js} +0 -1
  65. package/test/{test-vpid-liveslots.js → vpid-liveslots.test.js} +105 -5
  66. package/test/waitUntilQuiescent.js +2 -1
  67. package/test/weakset-dropped-remotable.test.js +50 -0
  68. package/tools/fakeCollectionManager.js +44 -0
  69. package/tools/fakeVirtualObjectManager.js +62 -0
  70. package/tools/fakeVirtualSupport.js +389 -0
  71. package/tools/prepare-strict-test-env.js +124 -0
  72. package/tools/prepare-test-env.js +13 -0
  73. package/tools/setup-vat-data.js +96 -0
  74. package/tools/vo-test-harness.js +143 -0
  75. package/CHANGELOG.md +0 -61
  76. package/test/kmarshal.js +0 -79
  77. package/test/test-handled-promises.js +0 -360
@@ -0,0 +1,65 @@
1
+ // @ts-nocheck
2
+ import '@endo/init/debug.js';
3
+ import test from 'ava';
4
+ import { Far } from '@endo/marshal';
5
+ import { kser } from '@agoric/kmarshal';
6
+ import { passStyleOf } from '@endo/pass-style';
7
+ import { PassStyleOfEndowmentSymbol } from '@endo/pass-style/endow.js';
8
+ import { makeLiveSlots } from '../src/index.js';
9
+ import { makeStartVat } from './util.js';
10
+ import { buildSyscall } from './liveslots-helpers.js';
11
+ import { makeMockGC } from './mock-gc.js';
12
+
13
+ test('vat globals', async t => {
14
+ const { syscall } = buildSyscall();
15
+ const gcTools = makeMockGC();
16
+ const buildRootObject = () => Far('root', {});
17
+ let called = 0;
18
+ let vatGlobals;
19
+ let inescapableGlobalProperties;
20
+ const vatNS = harden({ buildRootObject });
21
+ // buildVatNamespace
22
+ const bVN = async (vG, iGP) => {
23
+ called += 1;
24
+ vatGlobals = vG;
25
+ inescapableGlobalProperties = iGP;
26
+ return vatNS;
27
+ };
28
+
29
+ const ls = makeLiveSlots(syscall, 'vatA', {}, {}, gcTools, undefined, bVN);
30
+ t.is(called, 0); // not called yet
31
+ await ls.dispatch(makeStartVat(kser()));
32
+ t.is(called, 1);
33
+ t.truthy(vatGlobals);
34
+
35
+ // 'harden' is provided by SES (installed by the lockdown bundle),
36
+ // not liveslots
37
+ t.is(typeof vatGlobals.harden, 'undefined');
38
+
39
+ // but liveslots provides VatData
40
+ t.is(typeof vatGlobals.VatData, 'object');
41
+ t.is(typeof vatGlobals.VatData, 'object');
42
+ t.is(typeof vatGlobals.VatData.defineKind, 'function');
43
+ t.is(typeof vatGlobals.VatData.defineKindMulti, 'function');
44
+ t.is(typeof vatGlobals.VatData.defineDurableKind, 'function');
45
+ t.is(typeof vatGlobals.VatData.defineDurableKindMulti, 'function');
46
+ t.is(typeof vatGlobals.VatData.makeKindHandle, 'function');
47
+ t.is(typeof vatGlobals.VatData.canBeDurable, 'function');
48
+ t.is(typeof vatGlobals.VatData.providePromiseWatcher, 'function');
49
+ t.is(typeof vatGlobals.VatData.watchPromise, 'function');
50
+ t.is(typeof vatGlobals.VatData.makeScalarBigMapStore, 'function');
51
+ t.is(typeof vatGlobals.VatData.makeScalarBigWeakMapStore, 'function');
52
+ t.is(typeof vatGlobals.VatData.makeScalarBigSetStore, 'function');
53
+ t.is(typeof vatGlobals.VatData.makeScalarBigWeakSetStore, 'function');
54
+
55
+ t.is(typeof inescapableGlobalProperties.WeakMap, 'function');
56
+ t.not(inescapableGlobalProperties.WeakMap, WeakMap);
57
+ t.is(typeof inescapableGlobalProperties.WeakSet, 'function');
58
+ t.not(inescapableGlobalProperties.WeakSet, WeakSet);
59
+ t.is(
60
+ typeof inescapableGlobalProperties[PassStyleOfEndowmentSymbol],
61
+ 'function',
62
+ );
63
+ // this is the passStyleOf created by liveslots, with a real WeakMap
64
+ t.is(inescapableGlobalProperties[PassStyleOfEndowmentSymbol], passStyleOf);
65
+ });
package/test/vat-util.js CHANGED
@@ -1,8 +1,8 @@
1
1
  // this file is imported by some test vats, so don't import any non-pure
2
2
  // modules
3
3
 
4
- import { Fail } from '@agoric/assert';
5
- import { kser, kunser } from './kmarshal.js';
4
+ import { Fail } from '@endo/errors';
5
+ import { kser, kunser } from '@agoric/kmarshal';
6
6
 
7
7
  export function extractMessage(vatDeliverObject) {
8
8
  const [type, ...vdoargs] = vatDeliverObject;
@@ -1,6 +1,6 @@
1
+ // @ts-nocheck
1
2
  /* global FinalizationRegistry WeakRef */
2
3
  import test from 'ava';
3
- import '@endo/init/debug.js';
4
4
 
5
5
  import { buildSyscall } from '../liveslots-helpers.js';
6
6
  import { makeVirtualReferenceManager } from '../../src/virtualReferences.js';
@@ -38,7 +38,7 @@ function weakKeyCheck(t, log, vref) {
38
38
  t.true(result === undefined || !result.startsWith(prefix), `ew:${result}`);
39
39
  }
40
40
 
41
- test('only enumerate virtual objects', async t => {
41
+ test('only enumerate virtual objects', t => {
42
42
  const { log, vrm } = makeVRM();
43
43
 
44
44
  // retiring a plain Remotable does a is-it-a-weak-key chck
@@ -1,5 +1,4 @@
1
1
  import test from 'ava';
2
- import '@endo/init/debug.js';
3
2
 
4
3
  import { makeFakeVirtualObjectManager } from '../../tools/fakeVirtualSupport.js';
5
4
 
@@ -15,7 +14,7 @@ function attack2(mut1, immut2) {
15
14
  Reflect.apply(mutableProto.set, immut2, [6]);
16
15
  }
17
16
 
18
- test('forbid cross-facet prototype attack', async t => {
17
+ test('forbid cross-facet prototype attack', t => {
19
18
  const vom = makeFakeVirtualObjectManager();
20
19
  const init = () => ({ value: 0 });
21
20
  const behavior = {
@@ -34,10 +33,12 @@ test('forbid cross-facet prototype attack', async t => {
34
33
  thing2.mutable.set(2);
35
34
 
36
35
  t.throws(() => attack1(thing1.mutable, thing2.immutable), {
37
- message: /^illegal cross-facet access/,
36
+ message:
37
+ '"In \\"set\\" method of (thing mutable)" may only be applied to a valid instance: "[Alleged: thing immutable]"',
38
38
  });
39
39
  t.throws(() => attack2(thing1.mutable, thing2.immutable), {
40
- message: /^illegal cross-facet access/,
40
+ message:
41
+ '"In \\"set\\" method of (thing mutable)" may only be applied to a valid instance: "[Alleged: thing immutable]"',
41
42
  });
42
43
  t.is(thing1.immutable.get(), 1);
43
44
  t.is(thing2.immutable.get(), 2);
@@ -1,9 +1,8 @@
1
1
  import test from 'ava';
2
- import '@endo/init/debug.js';
3
2
 
4
3
  import { makeFakeVirtualObjectManager } from '../../tools/fakeVirtualSupport.js';
5
4
 
6
- test('non-object initial data message', async t => {
5
+ test('non-object initial data message', t => {
7
6
  const vom = makeFakeVirtualObjectManager();
8
7
  const goodInit = () => ({ value: 0 });
9
8
  // 'badInit' is () => { value: 0 }
@@ -1,9 +1,8 @@
1
1
  import test from 'ava';
2
- import '@endo/init/debug.js';
3
2
 
4
3
  import { makeFakeVirtualObjectManager } from '../../tools/fakeVirtualSupport.js';
5
4
 
6
- test('facets', async t => {
5
+ test('facets', t => {
7
6
  const vom = makeFakeVirtualObjectManager();
8
7
  const init = () => ({ value: 0 });
9
8
  const behavior = {
@@ -1,10 +1,10 @@
1
+ // @ts-nocheck
1
2
  import test from 'ava';
2
- import '@endo/init/debug.js';
3
3
  import { Far } from '@endo/marshal';
4
+ import { kser } from '@agoric/kmarshal';
4
5
  import { makeFakeVirtualStuff } from '../../tools/fakeVirtualSupport.js';
5
6
  import { makeLiveSlots } from '../../src/liveslots.js';
6
7
  import { parseVatSlot } from '../../src/parseVatSlots.js';
7
- import { kser } from '../kmarshal.js';
8
8
  import { buildSyscall } from '../liveslots-helpers.js';
9
9
  import { makeStartVat, makeMessage } from '../util.js';
10
10
  import { makeMockGC } from '../mock-gc.js';
@@ -1,5 +1,5 @@
1
+ // @ts-nocheck
1
2
  import test from 'ava';
2
- import '@endo/init/debug.js';
3
3
 
4
4
  import { Remotable } from '@endo/marshal';
5
5
  import { initEmpty } from '@agoric/store';
@@ -7,7 +7,7 @@ import { initEmpty } from '@agoric/store';
7
7
  import { makeVatSlot } from '../../src/parseVatSlots.js';
8
8
  import { makeFakeVirtualStuff } from '../../tools/fakeVirtualSupport.js';
9
9
 
10
- test('VOM tracks reachable vrefs', async t => {
10
+ test('VOM tracks reachable vrefs', t => {
11
11
  const { vom, vrm, cm } = makeFakeVirtualStuff();
12
12
  const { defineKind } = vom;
13
13
  const { makeScalarBigWeakMapStore } = cm;
@@ -1,22 +1,20 @@
1
1
  import test from 'ava';
2
- import '@endo/init/debug.js';
3
2
  // this sets process.env.DEBUG = 'label-instances'
4
3
  import './set-debug-label-instances.js';
5
4
 
6
5
  import { passStyleOf } from '@endo/far';
7
6
 
8
7
  // this samples it
8
+ import { q } from '@endo/errors';
9
9
  import { makeFakeVirtualStuff } from '../../tools/fakeVirtualSupport.js';
10
10
  // all tests in this file will be run with DEBUG='label-instances'
11
11
  import { parseVatSlot } from '../../src/parseVatSlots.js';
12
12
 
13
- const { quote: q } = assert;
14
-
15
13
  const init = () => ({});
16
14
  const behavior = {};
17
15
  const facets = { foo: {}, bar: {} };
18
16
 
19
- test('representatives with label-instances', async t => {
17
+ test('representatives with label-instances', t => {
20
18
  const { fakeStuff, vom } = makeFakeVirtualStuff();
21
19
  const { getSlotForVal } = fakeStuff;
22
20
  const makeThing = vom.defineKind('thing', init, behavior);
@@ -33,7 +31,7 @@ test('representatives with label-instances', async t => {
33
31
  t.is(`${q(thing2)}`, `"[Alleged: thing#${thing2vref}]"`);
34
32
  });
35
33
 
36
- test('facets with label-instances', async t => {
34
+ test('facets with label-instances', t => {
37
35
  const { fakeStuff, vom } = makeFakeVirtualStuff();
38
36
  const { getSlotForVal } = fakeStuff;
39
37
  const makeThings = vom.defineKindMulti('thing', init, facets);
@@ -1,56 +1,57 @@
1
- /* global WeakRef */
1
+ // @ts-nocheck
2
2
  import test from 'ava';
3
- import '@endo/init/debug.js';
4
3
 
5
4
  import { Far } from '@endo/marshal';
6
5
  import { initEmpty } from '@agoric/store';
7
6
 
8
7
  import engineGC from '../engine-gc.js';
9
- import { makeGcAndFinalize } from '../gc-and-finalize.js';
8
+ import { makeGcAndFinalize, watchCollected } from '../gc-and-finalize.js';
10
9
  import { makeFakeVirtualStuff } from '../../tools/fakeVirtualSupport.js';
11
10
 
12
- function makeHeld() {
13
- const held = Far('held');
14
- const wr = new WeakRef(held);
11
+ function makeStashKit(name = 'held') {
12
+ const held = Far(name);
13
+ const collected = watchCollected(held);
15
14
  const ws = new WeakSet(); // note: real WeakSet, not vref-aware
16
15
  ws.add(held);
17
16
  function isHeld(obj) {
18
17
  return ws.has(obj);
19
18
  }
20
- return { held, wr, isHeld };
19
+ function isCollected() {
20
+ return collected.result;
21
+ }
22
+ return { held, isCollected, isHeld };
21
23
  }
22
24
 
23
25
  function prepareEphemeral(vom) {
24
- const ephemeral = Far('ephemeral');
25
- vom.registerEntry('o+12345', ephemeral);
26
- const wr = new WeakRef(ephemeral);
27
- return { wr };
26
+ const { held, isCollected } = makeStashKit('ephemeral');
27
+ vom.registerEntry('o+12345', held);
28
+ return { isCollected };
28
29
  }
29
30
 
30
31
  function stashRemotableOne(weakStore, key1) {
31
- const { held, wr, isHeld } = makeHeld();
32
+ const { held, isCollected, isHeld } = makeStashKit();
32
33
  weakStore.init(key1, held);
33
- return { wr, isHeld };
34
+ return { isCollected, isHeld };
34
35
  }
35
36
 
36
37
  function stashRemotableTwo(weakStore, key1) {
37
- const { held, wr, isHeld } = makeHeld();
38
+ const { held, isCollected, isHeld } = makeStashKit();
38
39
  weakStore.init(key1, 'initial');
39
40
  weakStore.set(key1, held);
40
- return { wr, isHeld };
41
+ return { isCollected, isHeld };
41
42
  }
42
43
 
43
44
  function stashRemotableThree(holderMaker) {
44
- const { held, wr, isHeld } = makeHeld();
45
+ const { held, isCollected, isHeld } = makeStashKit();
45
46
  const holder = holderMaker(held);
46
- return { wr, isHeld, holder };
47
+ return { isCollected, isHeld, holder };
47
48
  }
48
49
 
49
50
  function stashRemotableFour(holderMaker) {
50
- const { held, wr, isHeld } = makeHeld();
51
+ const { held, isCollected, isHeld } = makeStashKit();
51
52
  const holder = holderMaker('initial');
52
53
  holder.setHeld(held);
53
- return { wr, isHeld, holder };
54
+ return { isCollected, isHeld, holder };
54
55
  }
55
56
 
56
57
  test('remotables retained by virtualized data', async t => {
@@ -74,7 +75,7 @@ test('remotables retained by virtualized data', async t => {
74
75
  // false positive in the subsequent test
75
76
  const stash0 = prepareEphemeral(vom);
76
77
  await gcAndFinalize();
77
- t.falsy(stash0.wr.deref(), `caution: fake VOM didn't release Remotable`);
78
+ t.true(stash0.isCollected(), `caution: fake VOM didn't release Remotable`);
78
79
 
79
80
  // stash a Remotable in the value of a weakStore
80
81
  const key1 = makeKey();
@@ -84,14 +85,14 @@ test('remotables retained by virtualized data', async t => {
84
85
  // Representatives or Presences, so the value is not holding a strong
85
86
  // reference to the Remotable. The VOM is supposed to keep it alive, via
86
87
  // reachableRemotables.
87
- t.truthy(stash1.wr.deref());
88
+ t.false(stash1.isCollected());
88
89
  t.truthy(stash1.isHeld(weakStore.get(key1)));
89
90
 
90
91
  // do the same, but exercise weakStore.set instead of .init
91
92
  const key2 = makeKey();
92
93
  const stash2 = stashRemotableTwo(weakStore, key2);
93
94
  await gcAndFinalize();
94
- t.truthy(stash2.wr.deref());
95
+ t.false(stash2.isCollected());
95
96
  t.truthy(stash2.isHeld(weakStore.get(key2)));
96
97
 
97
98
  // now stash a Remotable in the state of a virtual object during init()
@@ -100,12 +101,12 @@ test('remotables retained by virtualized data', async t => {
100
101
  // Each state property is virtualized upon write (via the generated
101
102
  // setters). So again we rely on the VOM to keep the Remotable alive in
102
103
  // case someone retrieves it again.
103
- t.truthy(stash3.wr.deref());
104
+ t.false(stash3.isCollected());
104
105
  t.truthy(stash3.isHeld(stash3.holder.getHeld()));
105
106
 
106
107
  // same, but stash after init()
107
108
  const stash4 = stashRemotableFour(makeHolder);
108
109
  await gcAndFinalize();
109
- t.truthy(stash4.wr.deref());
110
+ t.false(stash4.isCollected());
110
111
  t.truthy(stash4.isHeld(stash4.holder.getHeld()));
111
112
  });
@@ -1,4 +1,4 @@
1
- /* global process */
1
+ /* eslint-env node */
2
2
 
3
3
  // put this in a separate module, so we can make it happen before
4
4
  // importing virtualObjectManager.js
@@ -1,10 +1,10 @@
1
+ // @ts-nocheck
1
2
  import test from 'ava';
2
- import '@endo/init/debug.js';
3
3
 
4
4
  import { Far } from '@endo/marshal';
5
+ import { kser, kslot } from '@agoric/kmarshal';
5
6
  import { M } from '@agoric/store';
6
7
  import { makeLiveSlots } from '../../src/liveslots.js';
7
- import { kser, kslot } from '../kmarshal.js';
8
8
  import { buildSyscall } from '../liveslots-helpers.js';
9
9
  import { makeStartVat, makeMessage } from '../util.js';
10
10
  import { makeMockGC } from '../mock-gc.js';
@@ -1,12 +1,12 @@
1
+ // @ts-nocheck
1
2
  import test from 'ava';
2
- import '@endo/init/debug.js';
3
3
 
4
4
  import { Far } from '@endo/marshal';
5
+ import { krefOf, kser, kslot } from '@agoric/kmarshal';
5
6
  import {
6
7
  setupTestLiveslots,
7
8
  findSyscallsByType,
8
9
  } from '../liveslots-helpers.js';
9
- import { krefOf, kser, kslot } from '../kmarshal.js';
10
10
  import { parseVatSlot } from '../../src/parseVatSlots.js';
11
11
 
12
12
  // Legs: