w3c / webcrypto

The W3C Web Cryptography API
https://w3c.github.io/webcrypto/
Other
267 stars 56 forks source link

Remove support for importing RSA and ECC keys with alternative OIDs #325

Closed twiss closed 1 year ago

twiss commented 2 years ago

The specification currently specifies a number of "alternative" OIDs for importing SPKI and PKCS8 keys that indicate the specific algorithm and hash to be used with the key. However, these OIDs are not widely supported, and if they are, the parameters are usually not checked, and instead the key is usually allowed to be imported and used with the wrong algorithm or hash. So, we drop support for these alternative OIDs, simplifying the spec and matching most implementations. The only implementation that seems to have implemented much (but not all) of this is Deno. So, @lucacasonato, are you OK with removing this? Cc @panva, as well.

Instead, JWK can be used to specify the concrete algorithm and parameters, if required.

For more background, see #307.


Preview | Diff

panva commented 2 years ago

I've recently aligned both the Deno and Node implementations with this very proposal.

colinbendell commented 1 year ago

Just want to call out that id-RSASSA-PSS is required in the ietf RSA blind signatures which is required for Private Access Tokens (and I think Private State Tokens will align with this spec in the near future). The implication is that we will see more demand for at least this oid because of these specs.

panva commented 1 year ago

Just want to call out that id-RSASSA-PSS is required in the ietf RSA blind signatures which is required for Private Access Tokens (and I think Private State Tokens will align with this spec in the near future). The implication is that we will see more demand for at least this oid because of these specs.

Can you point to the concrete requirements that lead to pkcs#8 or spki import of id-rsassa-pss oid keys?

colinbendell commented 1 year ago

Can you point to the concrete requirements that lead to pkcs#8 or spki import of id-rsassa-pss oid keys?

Is there something you are specifically looking for? Throughout the Privacy Pass Issuance Protocol spec (which the Private Access Tokens depends) it describes the concrete requirement to use id-rsassa-pss oids. Specifically, it is needed to verify a token. While the spec does not depend specifically on webcrypto, it is a web interop issue.

For example, if you use safari you can test Private-Access-Tokens. However, because of the browser deficiency, you can't actually test the RSASSA-PSS-VERIFY(). Firefox fortunately supports this oid and so you can copy the token and verify in firefox's implementation of cebcrypto.

panva commented 1 year ago

If I'm reading this right (a very cursory read, apologies, i will follow up in depth tho because this is on my agenda) the only need for rsassa-pss oid SPKI is so that the token_key_id and pkI can be computed out of the bytes of the key. Other than that, rsassa-pss verification can be done without an rsa-pss key.

If a different token key id scheme was to be used, e.g. similar to rfc7638 but including the rsa-pss parameters (which i think is the only reason to have the id calculated over the spki of rsa-pss oid key?) then webcrypto interop would be dealt with.

It would be great if this new work utilized what's generally available and not what has been an interop nightmare for many years now. What I mean is that out of all the webcrypto implementations I am aware of (chromium, firefox, safari, node.js, deno, bun, CF Workers/workerd, @peculiar/webcrypto, Vercel's Edge Runtime) only

The rest out right doesn't support it. And so, depending on a key oid that won't be accepted by most (and its parameters ignored by the ones that will), is a questionable choice.

In reality then, use of this oid will force web developers to deal with spki rather than jwk (which is interoperable already) by having to parse it outside of webcrypto using an asn1 parser (a big fragile pain point to begin with) to get the modulus, exponent, and parameters and then import it as a PS256/PS384/PS512 JWK anyway so that they can validate a signature.

twiss commented 1 year ago

Hi @colinbendell, thanks for raising this. However, it's not obvious to me what the best course of action would be, if we wanted to address this in earnest. These OIDs have been specified in Web Crypto for many years, and almost nobody implemented them. That suggests a lack of interest on the side of implementers. To address this, someone would need to write tests for importing and exporting keys using this OID, and advocate or even volunteer for implementing it. The latter might also not be simple, since it needs to be done in the crypto libraries, and it also adds extra complexity to re-serializing keys (see https://github.com/w3c/webcrypto/issues/307#issuecomment-995814432). Are you planning or willing to work on this, or do you know who would be?

colinbendell commented 1 year ago

the only need for rsassa-pss oid SPKI is so that the token_key_id and pkI can be computed out of the bytes of the key. Other than that, rsassa-pss verification can be done without an rsa-pss key.

For the verification process - correct. the sha256(SPKI) is used to verify against the token_key_id. The rest can be done with rsaEncryption public keys.

For the other roles (client to issuer, issuer to client), it depends on blinded signatures. I'm not sure which parts of this spec are unique to id-RSASSA-PSS though.

  • firefox considers id-RSASSA-PSS as a "synonym" to rsaEncryption for public keys, and ignores the parameters anyway
  • safari considers id-RSASSA-PSS as a "synonym" to rsaEncryption for public and private keys, but requires the parameters to be NULL

Thanks for this tip! Given this, I found a nice hack to repack the modulus without needing to do asn parsing that enables verification with webcrypto. It is certainly an unfortunate hack.

twiss commented 1 year ago

Thanks for this tip! Given this, I found a nice hack to repack the modulus without needing to do asn parsing that enables verification with webcrypto. It is certainly an unfortunate hack.

I'm not here to tell you what to do, but I would advise against relying on this, as even under the current spec text of the Web Crypto API (as well as with this PR merged), implementations are required to reject such a key.

If you're going to monkey-patch the key to make Web Crypto accept it, it would be better to change the OID to rsaEncryption as well, such that it's a valid SPKI key. Then, it will be accepted by all implementations of Web Crypto, and even still be valid after this PR is merged :)

colinbendell commented 1 year ago

If you're going to monkey-patch the key to make Web Crypto accept it, it would be better to change the OID to rsaEncryption as well, such that it's a valid SPKI key. Then, it will be accepted by all implementations of Web Crypto, and even still be valid after this PR is merged :)

Yea, that's exactly what I'm doing. Change the oid, set the lengths correctly. It's a valid key in the end. Functionally, using the b64 encoded der you can: "MIIBIjANBgkqhkiG9w0BAQEFA" + sPKI.slice(-367). Of course this only works for 2048bit modulus.