ring
ring copied to clipboard
RSAES-OAEP support
This is one of the algorithms described in RFC 8017, with a Python implementation here (docs, tests).
It is supported in quite a few languages (it is the default asymmetric cipher in Node for example), and would be useful for (e.g.) Google Play Services interoperability.
I wonder if using https://github.com/dignifiedquire/rust-rsa as a starting point would be acceptable? Some things would need to be substituted to properly integrate with ring primitives.
I have a Frankenstein prototype: I added RSAES-OAEP encryption to rust-rsa with some use of ring for mgf1. Some guidance would be appreciated to integrate properly into ring.
While porting the padding algorithm is easy, RSA encryption is the big missing piece in ring. The key is public but the message is secret, and figuring out how to use the biging Montgomery primitives properly to get an equivalent of BN_mod_exp_mont is difficult.
Edit: done.
Here is a proof of concept with encryption, which passes a port of the pycryptodome tests.
@g2p I commented on your proof of concept commits directly but I'll comment here first.
I see a few aspects of this:
- Generalize the RSA signing bigint computations so that they can be shared between RSA signing and RSA decryption, and between RSA signature verification and RSA encryption.
- Add a new RSA padding scheme for OAEP, that works similarly to how PSS (and, to a leser extent, PKCS#1 1.5) are implemented.
- Make the RSA signing API and the RSA encryption API thin wrappers around the shared logic from above.
Later, we may want to do more things: Add NIST test vectors, add BoringSSL test vectors, provide a way to indicate in the PKCS#8 for an RSA key that it should be used only for OAEP or only PSS or whatever, but these can be done later, in separate PRs.
Thank you for your comments. I'll try to work on it, either soon or next week.
The "fit" function fits the large integer into a buffer that is smaller than the naive estimate would be.
There was one thing I wanted to add to the public API, which was a way to build a public key struct from a single byte array, using der tags, but I didn't find a way to do the serialisation that would make the API usable to callers that don't want to serialize themselves. Not sure if that's exposed.
@g2p How's it going? Anything I can do to unblock you here?
Hey, Any news on this? Would love to see RSA Encryption in ring :)
I just did an analysis of my uses of OpenSSL in my opcua project to see what it would take to move away. One of the lacking features would be OAEP padding, however I also have some other more serious issues with X509 (out of scope) that need doing too.
My plan is to do an immediate release that has #937 merged, then a release that has RSA 1024 support and OAEP support soon after.
I have RSA OAEP decrypt/encrypt implemented locally and I am planning to post a PR for it after merging BoringSSL.
Hey! Any update here?
i'm also still interested in this!
This is in 0.17.0-alpha and I hope to ship a release with it soon. I don't recommend using 0.17.0-alpha.
This is in 0.17.0-alpha and I hope to ship a release with it soon. I don't recommend using 0.17.0-alpha.
So...0.17.0 shipped, and it includes a lot of refactoring to enable RSAES-OAEP, but I ended up not including RSAES-OAEP in the 0.17 releases so far. After more research and recent CVEs in other implementations, I decided it is best to be more conservative and implement additional side-channel countermeasures in the RSA decryption implementation. In particular, I want to implement RSA base blinding for RSA decryption before I expose RSA decryption to ring users.
Also with the release of 0.17.0, the 0.17.0-alpha series is no longer supported nor recommended.
// cc @complexspaces @kjvalencik
Thank you for the heads up @briansmith 👍. Do you have a rough idea what the priority for the extra hardening would be?
Also with the release of 0.17.0, the 0.17.0-alpha series is no longer supported nor recommended.
FWIW, this is particularly problematic for us at least. I understand they're no longer supported but other then switching to using the rsa crate (which AFAIK is not as optimized), there doesn't seem to be an option to take the recommended path. Especially with rustls moving all releases to use ring 0.17. With that aside, we appreciate the explicit notification.
If you'd be able to contribute towards the implementation, I can sketch out the design and review the PRs as they're posted. I will see if I can find my WIP that implements the rest of this work on top of the main branch. (Unfortunately, rebasing the rest of the work onto main was what I was working on when I took the long break, so it might take a little time.)