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

Order includes different number of names than CSR specifies (for CSR without subjectAltName) #233

Closed
znerol opened this issue Apr 25, 2019 · 11 comments

Comments

@znerol
Copy link

znerol commented Apr 25, 2019

Given a CSR which only has the CN field set without any subjectAltName, pebble returns Order includes different number of names than CSR specifies. This is likely because the check
in FinalizeOrder only takes values rfom CSR subjectAltName into account and disregards the CSR CN.

This happens whenever a CSR is generated from the command line using the -subj without -addext:

openssl req -new -subj "/CN=example.com"  -newkey rsa:2048 -nodes -keyout key.pem -out req.pem

In order to work around this issue, one has to generate a CSR which repeats the CN in subjectAltName. Older versions of openssl req are missing the -addext flag and hence one need to resort to a tmplate. E.g. (minimal):

[ req ]
distinguished_name  = req_dn
req_extensions      = req_ext

[ req_dn ]
commonName          = Common Name (eg, YOUR name)
commonName_default  = example.com

[ req_ext ]
subjectAltName      = DNS:example.com
@znerol znerol changed the title Order includes different number of names than CSR specifies for CSR without subjectAltName Order includes different number of names than CSR specifies (for CSR without subjectAltName) Apr 25, 2019
@cpu
Copy link
Contributor

cpu commented Apr 25, 2019

Hi @znerol,

Thanks for opening an issue. I'm afraid this is the expected behaviour. The subject common name field is deprecated and all CSRs should contain subject alternate names.

I believe Pebble has the same behaviour here as Boulder and so this also matches the production Let's Encrypt ACME v2 API.

In order to work around this issue, one has to generate a CSR which repeats the CN in subjectAltName.

You could also avoid the duplication by omitting the deprecated Subj. CN entirely and just providing the SAN.

Older versions of openssl req are missing the -addext flag and hence one need to resort to a tmplate:

Typically ACME clients handle the details of generating a CSR themselves and don't require the user to interact with openssl to generate one manually. It is unfortunate that old versions of openssl make it quite cumbersome to generate a CSR with SANs but I don't think that justifies changing Pebble's behaviour (especially since it won't match Boulder).

I hope that helps explain the situation! I'm going to close this issue since there isn't a change to be made based on the report.

Thanks!

@cpu cpu closed this as completed Apr 25, 2019
@znerol
Copy link
Author

znerol commented Apr 25, 2019

I am operating live Let's Encrypt certificates without any subjectAltName, so thanks for the heads-up in this regard.

znerol added a commit to znerol/ansible-role-certhub that referenced this issue Apr 26, 2019
@munnerz
Copy link
Contributor

munnerz commented Oct 1, 2019

@cpu sorry to dig up an old issue, but we're feeling a bit of pain with this at the moment too in cert-manager.

Is this behaviour (ignoring CNs altogether) mandated by the ACME spec? We've got a number of other ACME servers now being used with cert-manager, and we're cautious to implement/modify behaviour if it risks breaking other implementations. If it's mandated by the spec, we can at least tell them to go fix it 😄

I couldn't see any references to the terms 'CN', 'common name', 'SAN' or 'subject alternative' that seemed relevant in RFC8555.

cc @JoshVanL

@jsha
Copy link
Contributor

jsha commented Oct 1, 2019

RFC 2818 from May 2000 deprecates Common Name: https://tools.ietf.org/html/rfc2818#page-5

Also BRs 1.6.6 section 7.1.4.2.2: Subject Distinguished Name Fields: https://cabforum.org/wp-content/uploads/CA-Browser-Forum-BR-1.6.6.pdf

@munnerz
Copy link
Contributor

munnerz commented Oct 2, 2019

👍 but they are still used, and most CAs don't just ignore the CommonName field (and that's evidenced by boulder not just blindly signing certificates with the CommonName field set, as presumably browsers also use this field still).

My question is, is ignoring the CN here an ACME spec property, or could some ACME servers choose to sign a CSR that has CN: example.com and dnsNames: www.example.com if the account holder holds authorizations for example.com and www.example.com?

@munnerz
Copy link
Contributor

munnerz commented Oct 2, 2019

Otherwise, the (most specific) Common Name
   field in the Subject field of the certificate MUST be used. Although
   the use of the Common Name is existing practice, it is deprecated and
   Certification Authorities are encouraged to use the dNSName instead.

I see this in section 3.1 of rfc2818 - this implies to me that if a CSR does not specify any DNS SANs, the common name should be used instead. It seems the nature of the deprecation and exact, specific advice isn't particularly clear from my PoV though, as it does acknowledge that the field is deprecated and encourages CAs to use DNS SANs instead. Given that ACME already copies dnsNames[0] over to commonName, it just seems a bit inconsistent is all.

Given our ACME client (cert-manager) also works with other CAs, we've simply added additional validation that is run ahead of interacting with the ACME server to ensure that if a user requests a specific commonName, it must be present on the list of dnsNames (and if it isn't, we bail out before creating the order/interacting with the server).

My concern is that some CAs might request we relax this validation, although perhaps I'm wrong 😄

@cpu
Copy link
Contributor

cpu commented Oct 2, 2019

My question is, is ignoring the CN here an ACME spec property, or could some ACME servers choose to sign a CSR that has CN: example.com and dnsNames: www.example.com if the account holder holds authorizations for example.com and www.example.com?

Yes, some ACME server could choose to do that and there is no mechanism for advertising that policy with RFC 8555. Like @jsha mentioned if the certificate that was issued from that CSR chains to a root participating in the traditional browser root programs then it would be considered a misissuance by the baseline requirements (CN MUST be present as a dNSName SAN) but ACME deliberately doesn't encode/mandate CA policy where possible.

I think since this isn't a question specific to Pebble it would probably be better suited to the community forum's client development section, or the ACME mailing list. Does my answer sufficiently clarify things or does someone want to spin up a new thread to continue to talk it though?

Thanks!

@jvanasco
Copy link
Contributor

@cpu i'm fine with the behavior, but shouldn't this be added to the divergences doc?

https://github.com/letsencrypt/boulder/blob/master/docs/acme-divergences.md

@cpu
Copy link
Contributor

cpu commented Jan 30, 2020

@jvanasco I think this is better discussed as a Boulder issue but my opinion at the moment is that since there's not any text in RFC 8555 that discusses this topic there isn't a divergence from specification.

@jvanasco
Copy link
Contributor

@cpu Sorry for the confusion on this. I didn't realize the RFC only covered Acme v2. Acme V1 (and the production Boulder/Letsencrypt) allowed for the CSR subject to be "/CN=example.com" (possibly required it?); the Acme V2 only accepts the CSR subject as "/".

my client's acme-v1 test server was a custom app; i'm using pebble as I upgrade to v2 and all these small changes are popping up.

@cpu
Copy link
Contributor

cpu commented Jan 31, 2020

I didn't realize the RFC only covered Acme v2

Indeed, there's no spec for what's colloquially known as ACME v1. It co-evolved with the spec and so there's always been just a reference implementation and a list of divergences against a fixed draft.

Acme V1 (and the production Boulder/Letsencrypt) allowed for the CSR subject to be "/CN=example.com" (possibly required it?); the Acme V2 only accepts the CSR subject as "/".

@jvanasco Can you file a Boulder issue with full request logs from V1 and V2 showing what you're saying? Please include the CSRs. I'm not aware of a change in the CSR CN handling between protocol versions in Boulder.

Thanks,

@letsencrypt letsencrypt locked as off-topic and limited conversation to collaborators Jan 31, 2020
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

No branches or pull requests

5 participants