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

Reduce risk of timing attack on canmakepayment #415

Open
ianbjacobs opened this issue Apr 26, 2023 · 1 comment
Open

Reduce risk of timing attack on canmakepayment #415

ianbjacobs opened this issue Apr 26, 2023 · 1 comment

Comments

@ianbjacobs
Copy link
Contributor

(Below I quote previous text from the Chrome team, moving it from this pull request [1] to an issue)
[1] w3c/webpayments#261

In a timing attack, a colluding website (https://site.example) first fires a server-call to the tracker (https://tracker.example), informing the tracker that it is about to construct a Payment Request. The colluding website then does so, and a "canmakepayment" event is fired to the tracker's (already-installed) payment app. Whilst this event contains no user data after the above mitigations, the service worker (or native application) still has 1p context and so can message its own server with its concept of the user's identity. The https://tracker.example server then
attempts to match up the initial server-call with the canmakepayment event, and thus track the user.

Possible Mitigations

One option would be to partition the Service Worker's storage, which would remove its ability to access the 1p user information when handling the "canmakepayment" event. However once a service worker opens a Payment Handler window (which is a 1p context) in the "paymentrequest" event, it can receive the payment app’s 1p identity for the user through postMessage() and store it for later usage, thus negating the partitioning. In addition, a user agent has no way to partition the storage of an OS-native (e.g., Android) app.

As an alternative, we have been considering a push model, in which installed payment apps can proactively 'push' their response boolean (true/false) down to the browser for future "canmakepayment" events. Then, when a Payment Request is constructed, the browser just uses the cached value rather than call into the Service Worker.

A final option would be to remove "canmakepayment"/IS_READY_TO_PAY entirely, although we have not yet determined whether that is feasible. (It certainly seems like it would break use-cases.)

@stephenmcgruer
Copy link
Collaborator

Thanks Ian! (cc @rsolomakhin )

cc @johannhof - this is similar to other network attacks we've been discussing over the last few months, so I thought you should be aware. The attack is roughly:

Attackers: colluding websites flowers.example and tracker.example

Pre-requisite: tracker.example has registered a web-based payment app, by creating a PaymentRequest object for https://tracker.example and calling show() on it. This will show UI (once #416 is addressed), but it only has to happen once and even if the user closes the modal the app will still be installed. This does not need to happen on tracker.example, it can be initiated from any website.

Attack:

  1. User visits flowers.example
  2. flowers.example issues a fetch() to tracker.example, saying "I am flowers.example, and I am about to create a Payment Request"
    • tracker.example's server makes note of this request, and also records the IP address, geolocation, etc
  3. flowers.example creates a PaymentRequest object with a supportedMethods of https://tracker.example
    • This does not show any UI (because they have not called show()).
  4. Chrome sends a "canmakepayment" event to the service worker for tracker.example's web-app
  5. The tracker.example service worker receives the "canmakepayment" event (which contains no data about flowers.example or the user, see Limit information available during canmakepayment event #413), but is in a 'first party' context.
  6. The tracker.example service worker issues a fetch() to tracker.example, saying "I just received a canmakepayment event"
    • This fetch includes cookies for tracker.example, for example a tracking identifier id=abcd1234
    • tracker.example's server makes note of this request, and also records the IP address, geolocation, etc.
      7 . The tracker.example server joins the two network-side logs, and concludes that user abcd1234 is visiting flowers.example

(repeat attack across other colluding websites, allowing the user to be tracked across the web).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants