-
Notifications
You must be signed in to change notification settings - Fork 180
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
How can we trust authenticator data flags in fmt:none response from .create()
?
#1698
Comments
I did some searching before posting this and found #1088 (and #1095 by extension) but these seemed too focused on potential MITM attacks. Maybe I'm supposed to infer that Secure Context + CSP are your primary defenses against entirely fabricated I'm just having a hard time reconciling advice floating around that both "UV is required for passwordless" and "you probably don't need attestation statements" when it's only direct attestation statements that guarantee that UV was performed because |
IMO the "unwritten" attitude in the webauthn community is that if you request "attest:none" then you only are asking for a single-factor being a public-key. Everything else is "off the cards" and you need to combine this with other factors to create an MFA setup. If you want to "trust" UV, you need to do attestation checks and validate the supplier etc. This is because you are now putting your sole-trust into one device as a self-contained multi-factor authenticator (per nist sp800-63b) and so you should validate the authenticity of that device if it is to be used in this manner. To add to this you also then need to request extensions as well because the other elements of the creation options are UX hints, not enforcement. This largely is a case of "webauthn as a spec is a kitchen sink" of trying to fit multiple workflows into a single standard, without it being written what the "ways are" to hold it correctly. But to muddy this water, you then get devices like CTAP2.0 that will always give UV=true on discouraged during .create() but never during .get() which is super confusing to both the RP and the User. |
The short answer is that indeed, you "cannot" trust the authenticator data flags without a trusted attestation (this applies equally to self attestation, as the public key can be replaced along with the signature), but the longer answer is that it depends on your threat model, what you mean by "trust", and whose trust you're talking about. Let's consider a few scenarios: 1. UV on the user's initiativeIn this scenario, the RP doesn't really care what authenticator is being used, it only wants to enable users to customize their authentication experience. For example, some users may choose an authenticator that always requires UV, even if the RP doesn't care about UV. As long as that user trusts their chosen authenticator, they can be assured that UV is required to access their account if they don't have any other sign-in option set up. So in this case the RP "trusts" the user to choose what's best for them, and the user "trusts" their own choice of authenticator. Attestation is not necessary, because the RP only cares about getting a signature from an already-registered public key. 2. UV as a "best effort"In this scenario, the RP may require UV for some interactions, for example as an alternative to a traditional password, but isn't really worried about the flag's authenticity. If the user happens to be using an honest authenticator and browser, which most users probably will, then this gives a reasonable assurance that UV was probably actually performed. There's still the possibility that some users might use a homegrown software authenticator that lies about the flags for user convenience, but if so, that's the user's responsibility. Perhaps a bigger issue is if the user is using a public computer infected with malware, but the malware can only tamper with the flags during the initial registration ceremony, not any subsequent authentication ceremonies if the registration was done securely. And if there's malware on the client, it can just take over the account after a successful login anyway. So in this case the RP is nudging the user towards higher security, and for most users most of the time, that nudge will be enough. The RP might request and store attestation statements for future reference - for example to warn users if an authenticator model is discovered to be insecure - but it's not strictly necessary since much like the previous scenario, the RP largely "trusts" the user to not do anything stupid. Especially if the RP also factors in other signals like geolocation data, this might be the best balance of security, usability and customizability. 3. UV strictly requiredIn this scenario, the RP requires UV and requires that the flag be verifiably authentic. For example, the RP may be subject to legal regulations that require certain security properties. In this case the RP simply must require attestation and only allow explicitly trusted authenticators, because there's no other way to know that the user, authenticator and/or browser isn't lying. It doesn't matter if the user wants something else, because the RP is compelled by law to forbid anything not known to be secure and trustworthy. So depending on the situation, your answer to "how can we trust [...]" will vary greatly since "trust" might mean different things. But yeah, strictly speaking the RP has no guarantee that the flags are authentic with "none" or "self" attestation. |
@emlun Thank you for the typing all of that out. I really appreciate your insight, and how you framed it as graduated approaches to building trust in security models that incorporate WebAuthn.
This sounds like the model of trust most RPs will end up with as passwordless auth becomes more ubiquitous, especially non-IdPs that roll their own UX. It makes sense that most users will interact with WebAuthn using typical authenticators (if only platform ones in the consumer space), and that there are other ways for an attacker to gain access to a user's account on a compromised machine that leave the user with more problems than WebAuthn authentication concerns. Thank you again. You've definitely helped me talk about this with others more intelligently going forward 🎉 |
I was asked recently how we can trust the
uv
flag in particular inauthData
that's returned from a call to.create()
when a"none"
-formatted attestation statement is returned.I went to refresh my memory by taking a look at the spec and realized that if an RP never requests direct attestation then there's nothing preventing anyone from messing with the flags because there's no signature over
authData
. Does it not make sense for an authenticator generating a response for.create()
to at least provide a signature overauthData
andclientDataJSON
, like we get back from.get()
?If there's no need for this, then can someone please help me explain to others why this isn't a problem if they want to ensure that user verification actually took place during registration?
The text was updated successfully, but these errors were encountered: