From 1b4f248df256d1c50df9c69ffbf0048789c89d95 Mon Sep 17 00:00:00 2001 From: "Mark S. Miller" Date: Thu, 18 Jul 2024 15:15:23 -0700 Subject: [PATCH] fix(async-flow): fix endowment equate bug --- packages/async-flow/src/equate.js | 24 ++++++++++++++++-------- packages/async-flow/test/equate.test.js | 10 +++++----- 2 files changed, 21 insertions(+), 13 deletions(-) diff --git a/packages/async-flow/src/equate.js b/packages/async-flow/src/equate.js index f11df50e911..9bfa3bba4a3 100644 --- a/packages/async-flow/src/equate.js +++ b/packages/async-flow/src/equate.js @@ -31,7 +31,14 @@ export const makeEquate = bijection => { Fail`unequal ${g} vs ${h}`; return; } - if (bijection.has(g, h)) { + if (bijection.hasGuest(g) && bijection.guestToHost(g) === h) { + // Note that this can be true even when + // `bijection.hostToGuest(h) !== g` + // but only when the two guests represent the same host, as + // happens with unwrapping. That why we do this one-way test + // rather than the two way `bijection.has` test. + // Even in this one-way case, we have still satisfied + // the equate, so return. return; } const gPassStyle = passStyleOf(g); @@ -41,7 +48,8 @@ export const makeEquate = bijection => { // TODO when we do, delete the `throw Fail` line and uncomment // the two lines below it. // We *do* support passing a guest wrapper of a hostVow back - // to the host, but that would be cause by `bijection.has` above. + // to the host, but that would be caught by `bijection.guestToHost` + // test above. throw Fail`guest promises not yet passable`; // `init` does not yet do enough checking anyway. For this case, // we should ensure that h is a host wrapper of a guest promise, @@ -92,10 +100,10 @@ export const makeEquate = bijection => { case 'remotable': { // Note that we can send a guest wrapping of a host remotable // back to the host, - // but that should have already been taken care of by the - // `bijection.has` above. + // but that should have already been caught by the + // `bijection.guestToHost` above. throw Fail`cannot yet send guest remotables to host ${g} vs ${h}`; - // `init` does not yet do enough checking anyway. For this case, + // `unwrapInit` does not yet do enough checking anyway. For this case, // we should ensure that h is a host wrapper of a guest remotable, // which is a wrapping we don't yet support. // bijection.unwrapInit(g, h); @@ -104,10 +112,10 @@ export const makeEquate = bijection => { case 'promise': { // Note that we can send a guest wrapping of a host promise // (or vow) back to the host, - // but that should have already been taken care of by the - // `bijection.has` above. + // but that should have already been caught by the + // `bijection.guestToHost` above. throw Fail`cannot yet send guest promises to host ${g} vs ${h}`; - // `init` does not yet do enough checking anyway. For this case, + // `unwrapInit` does not yet do enough checking anyway. For this case, // we should ensure that h is a host wrapper of a guest promise, // which is a wrapping we don't yet support. // bijection.unwrapInit(g, h); diff --git a/packages/async-flow/test/equate.test.js b/packages/async-flow/test/equate.test.js index 5be4100794e..1ae04e08fe6 100644 --- a/packages/async-flow/test/equate.test.js +++ b/packages/async-flow/test/equate.test.js @@ -57,24 +57,24 @@ const testEquate = (t, zone, showOnConsole = false) => { bij.unwrapInit(g1, h1); t.notThrows(() => equate(g1, h1)); t.throws(() => equate(g1, h2), { - message: 'internal: g->h "[Alleged: g1]" -> "[Vow]" vs "[Alleged: h1]"', + message: 'unequal passStyles "remotable" vs "tagged"', }); t.throws(() => equate(g2, h1), { - message: 'internal: unexpected h->g "[Alleged: h1]" -> "[Alleged: g1]"', + message: 'unequal passStyles "promise" vs "remotable"', }); bij.unwrapInit(g2, h2); equate(g2, h2); t.throws(() => equate(g1, h2), { - message: 'internal: g->h "[Alleged: g1]" -> "[Vow]" vs "[Alleged: h1]"', + message: 'unequal passStyles "remotable" vs "tagged"', }); t.throws(() => equate(g2, h1), { - message: 'internal: g->h "[Promise]" -> "[Alleged: h1]" vs "[Vow]"', + message: 'unequal passStyles "promise" vs "remotable"', }); equate(harden([g1, g2]), harden([h1, h2])); t.throws(() => equate(harden([g1, g2]), harden([h1, h1])), { - message: '[1]: internal: g->h "[Promise]" -> "[Alleged: h1]" vs "[Vow]"', + message: '[1]: unequal passStyles "promise" vs "remotable"', }); const gErr1 = harden(makeError(X`error ${'redacted message'}`, URIError));