Skip to content

Allow library users to bring their own crypto providers#268

Open
jcgruenhage wants to merge 9 commits intodjc:mainfrom
jcgruenhage:crypto-providers
Open

Allow library users to bring their own crypto providers#268
jcgruenhage wants to merge 9 commits intodjc:mainfrom
jcgruenhage:crypto-providers

Conversation

@jcgruenhage
Copy link

@jcgruenhage jcgruenhage commented Feb 25, 2026

Implements base for #267, allowing users to bring their own crypto.

Marked as draft for now, will un-draft once I've implemented (and tested) backends with other crypto libraries, like openssl and rustcrypto to validate this approach is viable.

@djc
Copy link
Owner

djc commented Feb 25, 2026

To pass the semver check, just add a commit that bumps the version to 0.9.0, please.

Copy link
Owner

@djc djc left a comment

Choose a reason for hiding this comment

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

Here's some early feedback. I like the direction overall!

@jcgruenhage
Copy link
Author

@djc do you have a preference regarding commits? Should I address the feedback in new commits, or are you fine with force pushes that amend existing commits?

@djc
Copy link
Owner

djc commented Feb 26, 2026

I generally prefer clean commits that do one thing, so would definitely prefer force pushes over addressing feedback in separate commits.

@jcgruenhage jcgruenhage marked this pull request as ready for review February 26, 2026 22:44
@jcgruenhage
Copy link
Author

I have locally tested this with an openssl provider and a CLI that creates and deactivates accounts on letsencrypt staging, with 2k/3k/4k RSA and P-256/P-384 key types, including cross key rollover, so I'm removing the draft state.

I'll push another time for working on the remaining unaddressed comments and splitting up the changes a bit further to help with reviewing the code.

@jcgruenhage jcgruenhage force-pushed the crypto-providers branch 2 times, most recently from 06fc20c to 0013fea Compare February 27, 2026 00:33
Copy link
Owner

@djc djc left a comment

Choose a reason for hiding this comment

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

Looking good, appreciate the clean commit history!

src/crypto.rs Outdated
}

#[cfg(feature = "ring")]
mod backend_ring {
Copy link
Owner

Choose a reason for hiding this comment

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

Nit: rename these to ring_crypto and aws_lc_rs_crypto maybe?

Copy link
Author

Choose a reason for hiding this comment

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

I've instead moved them to modules called ring and aws_lc_rs, nested beneath crypto. The benefit is that it allows easily diffing the two fairly similar modules.

@cpu
Copy link
Collaborator

cpu commented Feb 27, 2026

I'd like to give this branch a review as well, but won't have a chance for a couple days. Probably best to address djc's feedback up-front anyway :-)

@djc
Copy link
Owner

djc commented Feb 27, 2026

I'd like to give this branch a review as well, but won't have a chance for a couple days. Probably best to address djc's feedback up-front anyway :-)

Yup, won't merge without your review.

Copy link
Collaborator

@cpu cpu left a comment

Choose a reason for hiding this comment

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

This is really nice work, thank you!

I had a fair amount of feedback but I don't think any of it is super substantial.

src/types.rs Outdated
impl Jwk {
pub(crate) fn new(key: &crypto::EcdsaKeyPair) -> Self {
impl Jwk<'_> {
pub(crate) fn new(key: &crypto::EcdsaKeyPair) -> Jwk<'_> {
Copy link
Collaborator

Choose a reason for hiding this comment

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

Does this need to change from Self because of the lifetime?

#[cfg(feature = "ring")]
mod ring;

/// Cryptographic provider for ACME operations.
Copy link
Collaborator

Choose a reason for hiding this comment

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

It feels like it might be worth a sentence or two describing how this differs from a Rustls cryptography provider used for the TLS operations required for the ACME server HTTPS API, as opposed to the crypto operations required for the ACME protocol. WDYT?

}
}

struct BuiltinSha256;
Copy link
Collaborator

@cpu cpu Mar 8, 2026

Choose a reason for hiding this comment

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

nit: the "Builtin" part of this type name (and the HMAC) one seems a bit odd to me. Could we drop it? (Ditto for the ring mod equivalents)

static NEXT_PORT: AtomicU16 = AtomicU16::new(5555);
const RETRY_POLICY: RetryPolicy = RetryPolicy::new().backoff(1.0);

fn test_provider() -> &'static CryptoProvider {
Copy link
Collaborator

Choose a reason for hiding this comment

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

nit: put this above the static/consts?

pub struct KeyAuthorization(String);
pub struct KeyAuthorization {
inner: String,
sha256: &'static dyn Sha256,
Copy link
Collaborator

Choose a reason for hiding this comment

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

Would it be feasible/better to pre-compute the SHA256 in new() instead of holding on to the dyn Sha256 ref?

Comment on lines +321 to +322
/// Key type, must be `"OKP"`
kty: &'static str,
Copy link
Collaborator

Choose a reason for hiding this comment

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

If the field must always be a certain value, should we maybe handle it ourselves in the Jwk.thumb_sha256 based on self.alg or the variant of self.key? I think it means we'd have to have an internal type that has the kty field for the purposes of serde_json, but it removes one potential source of error from a buggy crypto provider. That seems lightly worth it to me, especially given how many footguns exist in JWS w.r.t "alg: none" and similar :-/

Same feedback applies to the Rsa.kty and Ec.kty fields if you think it's worth considering.

Copy link
Owner

Choose a reason for hiding this comment

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

Yeah, that sounds like an improvement.

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

Successfully merging this pull request may close these issues.

3 participants