Skip to content

Ensure RSA keys are at least 2048 bits in length#17911

Merged
jm96441n merged 8 commits intomainfrom
NET-4173-rsa-key-length-inline-certs
Jun 28, 2023
Merged

Ensure RSA keys are at least 2048 bits in length#17911
jm96441n merged 8 commits intomainfrom
NET-4173-rsa-key-length-inline-certs

Conversation

@jm96441n
Copy link
Copy Markdown
Member

@jm96441n jm96441n commented Jun 27, 2023

Description

Envoy will silently reject RSA keys that are less than 2048 bits in length. The only way to find a key has been rejected is to go deep into the envoy config to see why. This introduces a change to reject invalid keys earlier and in a more user friendly way.

Testing & Reproduction steps

Links

PR Checklist

  • updated test coverage
  • external facing docs updated
  • appropriate backport labels added
  • not a security concern

@jm96441n jm96441n added pr/no-docs PR does not include docs and should not trigger reminder for cherrypicking them. theme/api-gw Track API gateway work backport/1.16 This release series is no longer active on CE. Use backport/ent/1.16. labels Jun 27, 2023

// Envoy will silently reject any keys that are less than 2048 bytes long
// https://github.com/envoyproxy/envoy/blob/main/source/extensions/transport_sockets/tls/context_impl.cc#L238
const MinKeyLength = 2048
Copy link
Copy Markdown
Contributor

@andrewstucki andrewstucki Jun 27, 2023

Choose a reason for hiding this comment

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

given the FIPS work on enterprise, wondering based on the conditional a couple lines below the linked envoy line:

        if (rsa_key_length != 2048 && rsa_key_length != 3072 && rsa_key_length != 4096) {
          throw EnvoyException(
              fmt::format("Failed to load certificate chain from {}, only RSA certificates with "
                          "2048-bit, 3072-bit or 4096-bit keys are supported in FIPS mode",
                          ctx.cert_chain_file_path_));
        } 

We may want to call:

func IsFIPS() bool {

and do some additional constraint checks and only allow you to create InlineCertificates with those exact bit lengths if built with FIPS... since in the FIPS-compliant envoy build (and due to the movement towards packaging envoy FIPS alongside dataplane we should be able to detect since we require the whole stack including the Consul servers to be FIPS-compliant at that point) any other key length will result in the same broken envoy instances... WDYT?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

that's a good call out! lemme modify this a bit

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

One other thing to call out is that you'll want to also do this in the k8s side of things on the gateway validation itself, somewhere like this:

https://github.com/hashicorp/consul-k8s/blob/d3f9b670ab8055f0fc8ea4061c2d3c40abeb047f/control-plane/api-gateway/binding/validation.go#L207-L213

Since we don't do any sort of status syncing to Kubernetes secret objects, invalid certificates referenced by a gateway get statuses reflected back only on the gateway. Rather than attempting a sync and having it be silently rejected by Consul, we should just skip the attempt at InlineCertificate creation and set a status on the Gateway object in Kubernetes saying, "the cert you're referencing has an invalid length" to inform the user.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

yeah I've got some code over in the ParseCertificates function currently that I'm gonna push up after this merges so implementations are similar-ish and will have mostly been code reviewed already

Copy link
Copy Markdown
Contributor

@andrewstucki andrewstucki left a comment

Choose a reason for hiding this comment

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

One small nit change for readability and I think this is good, also called out where you'll want to add some changes for the k8s code to propagate error statuses on certificates back to users, but that's separate from this.

Copy link
Copy Markdown
Contributor

@andrewstucki andrewstucki left a comment

Choose a reason for hiding this comment

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

Approving with this one change that's problematic and causing issues/the linter to fail.

@jm96441n jm96441n enabled auto-merge (squash) June 28, 2023 15:00
@jm96441n jm96441n merged commit 67a239a into main Jun 28, 2023
@jm96441n jm96441n deleted the NET-4173-rsa-key-length-inline-certs branch June 28, 2023 15:34
jm96441n added a commit that referenced this pull request Jun 28, 2023
* Ensure RSA keys are at least 2048 bits in length

* Add changelog

* update key length check for FIPS compliance

* Fix no new variables error and failing to return when error exists from
validating

* clean up code for better readability

* actually return value
jm96441n added a commit that referenced this pull request Jun 28, 2023
…ease/1.16.x (#17935)

* backport of commit 93ccfe4

* Ensure RSA keys are at least 2048 bits in length (#17911)

* Ensure RSA keys are at least 2048 bits in length

* Add changelog

* update key length check for FIPS compliance

* Fix no new variables error and failing to return when error exists from
validating

* clean up code for better readability

* actually return value

---------

Co-authored-by: jm96441n <[email protected]>