Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix(exo)!: reject extra args by default #1890

Merged
merged 1 commit into from
Dec 11, 2023
Merged

Conversation

erights
Copy link
Contributor

@erights erights commented Dec 11, 2023

closes: #1888
refs: #1889 #1765 #1809 Agoric/agoric-sdk#8514 Agoric/agoric-sdk#8641

Description

Breaking change: Change method guard arguments matching rule to reject extra arguments by default.

Security Considerations

Prior to #1765 we (I) had a bad bug that enabled extra args to bypass intended input validation. This was a definite security risk. At the time of this writing, agoric-sdk does indeed depend on an endo prior to #1765 and so does suffer from this risk.
#1765 repairs the security risk per se, in that these extra arguments are silently dropped instead. But experience has shown that this lenient behavior masks bugs that are better caught and fixed. The purpose of this PR is to have the method guard by default reject argument lists with extra args beyond those declared. When we do upgrade agoric-sdk to depend on an endo fixing the original bug, we hope to upgrade it to one incorporating this PR, skipping the lenient behavior of #1765 completely.

This change from #1765 is a tradeoff. See "Upgrade Considerations" below, as well as the discussion in the #1888 issue, for the cost of doing so.

Note that neither #1765 nor this change has any effect on method guards with an explicit .rest. Likewise, such guards to not suffer from #1888 and so are not an issue. For any guard without an explicit .rest, after this PR you can restore the very lenient pre-#1765 behavior by adding an explicit .rest(M.any())

Throwing instead of dropping is consistent with “death before confusion”. In https://github.com/Agoric/agoric-sdk/pull/8514/files#diff-42f4291b619264addc7a7e12a8902cf3c60e5f797e97b5e4fa2a1e0c01d111ffR40, it was necessary to fix the shape of lookupAdmin on a name hub because dropping an argument caused subsequent updates to be applied to a prefix of the name path.

Scaling Considerations

None

Documentation Considerations

We need to document this new, less tolerant, guard behavior.

Testing Considerations

We need to test that we get the rejections this PR should generate, and that the error messages are reasonably understandable.

Upgrade Considerations

The motivation for the leniency of #1765 was to accommodate smoother versioning of APIs, where later versions of an API might add parameters not expected by earlier implementations of the API, and therefore not by guards representing those earlier versions of the API. This mirrors how JS works well enough to be less surprising to some folks. The cost of switching from #1765 to this PR is to lose such accommodations by default. However, when you do expect that a particular method may be extended with additional arguments, you can prepare by adding an explicit .rest(M.any()). But please, only use this lightly, only on specific methods that are likely to need it.

Without the ability to add extra args, the only remaining good choice for API evolution is new methods with new names. This is also familiar from JS as the "feature testing style": If a method with the new name exists, it operates in the new way. Otherwise fall back to the old way.

On the old endo that the current agoric-sdk depends on, there was no good way to do such feature testing remotely. Fortunately #1809 (already merged to endo master) introduces the GET_METHOD_NAMES and GET_INTERFACE_GUARD meta methods enabling such remote feature testing. This is still at the cost of an extra round trip, and so should be done once up front rather than on each invocation. OTOH, if done only up front, then the client may miss the opportunity to use the new functionality when the provider gets upgraded. So best is for the client to check once per incarnation, so that restarting or upgrading the client will let it notice and utilize the opportunity. This is a less surprising time for the client to change behavior anyway.

@erights erights self-assigned this Dec 11, 2023
@erights erights changed the base branch from master to kriskowal-sync-agoric-sdk-2023-11 December 11, 2023 02:34
@erights erights changed the title Markm 1888 reject extra args fix(exo)!: reject extra args by default Dec 11, 2023
@erights
Copy link
Contributor Author

erights commented Dec 11, 2023

@kriskowal what should I do about the generated yarn.lock changes?

@erights erights force-pushed the markm-1888-reject-extra-args branch 2 times, most recently from 9c307b5 to bf8269a Compare December 11, 2023 03:15
@erights erights marked this pull request as ready for review December 11, 2023 04:39
Copy link
Member

@michaelfig michaelfig left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM! I'm not sure of the downstream consequences of this change, but marking it as breaking (as you have) will at least prevent accidental use of this @endo/exo version.

@erights erights added the security blocker Required to make security claims on all expressly supported platforms label Dec 11, 2023
@erights erights changed the base branch from kriskowal-sync-agoric-sdk-2023-11 to master December 11, 2023 20:43
@erights
Copy link
Contributor Author

erights commented Dec 11, 2023

@kriskowal
No longer staged on #1889 as discussed. But still with the yarn.lock changes, which I still need feedback on.

@kriskowal
Copy link
Member

@kriskowal what should I do about the generated yarn.lock changes?

Nothing you’ve done should have caused the changes to yarn.lock. This suggests that if you ran yarn on master, you’d get the same changes. If that’s the case, it would be fine to submit them in a separate PR. But, for purposes of expedience, it’s fine to include a chore: Update yarn.lock commit. I do recommend a separate commit and to create a merge commit to preserve it when merging this PR.

@kriskowal
Copy link
Member

Beyond what’s in your description, throwing instead of dropping is consistent with “death before confusion”. In https://github.com/Agoric/agoric-sdk/pull/8514/files#diff-42f4291b619264addc7a7e12a8902cf3c60e5f797e97b5e4fa2a1e0c01d111ffR40, it was necessary to fix the shape of lookupAdmin on a name hub because dropping an argument caused subsequent updates to be applied to a prefix of the name path.

@erights
Copy link
Contributor Author

erights commented Dec 11, 2023

..., throwing instead of dropping is consistent with “death before confusion”. In https://github.com/Agoric/agoric-sdk/pull/8514/files#diff-42f4291b619264addc7a7e12a8902cf3c60e5f797e97b5e4fa2a1e0c01d111ffR40, it was necessary to fix the shape of lookupAdmin on a name hub because dropping an argument caused subsequent updates to be applied to a prefix of the name path.

Added to description

@erights erights mentioned this pull request Dec 11, 2023
@erights
Copy link
Contributor Author

erights commented Dec 11, 2023

@kriskowal what should I do about the generated yarn.lock changes?

Nothing you’ve done should have caused the changes to yarn.lock. This suggests that if you ran yarn on master, you’d get the same changes. If that’s the case, it would be fine to submit them in a separate PR. But, for purposes of expedience, it’s fine to include a chore: Update yarn.lock commit. I do recommend a separate commit and to create a merge commit to preserve it when merging this PR.

I went with the separate PR at #1892 . This PR no longer has these yarn.lock changes. I was glad to see that CI was clean anyway.

Which brings up an interesting issue: Should CI test if yarn would change yarn.lock? If it detects that it would, should CI fail? Issue a warning? Attn @kriskowal

@erights erights merged commit 281e318 into master Dec 11, 2023
14 checks passed
@erights erights deleted the markm-1888-reject-extra-args branch December 11, 2023 21:25
@kriskowal
Copy link
Member

There is a CI check to ensure yarn does not change yarn.lock.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
security blocker Required to make security claims on all expressly supported platforms
Projects
None yet
Development

Successfully merging this pull request may close these issues.

"Extra args dropped" was too lenient. Throw error instead
3 participants