From 7c9af4b7eaaa3b811785cd7dad8a5d57dfe9e260 Mon Sep 17 00:00:00 2001 From: job Date: Mon, 6 Mar 2023 16:58:41 +0000 Subject: [PATCH] Ensure .cer and .crl outside-TBS signatures are sha256WithRSAEncryption Note: there is a potential for confusion in RFC 7935, the specification differentiates between 2 contexts: "in the certificate" and "CMS SignedData". In the CMS context, either rsaEncryption or sha256WithRSAEncryption can appear (and both *do* appear in the wild). However, RFC 7935 section 2 fourth paragraph starting with "In certificates, CRLs, ..." mandates that sha256WithRSAEncryption is used to sign .cer and .crl files: "The Object Identifier (OID) sha256WithRSAEncryption from RFC4055 MUST be used in these products." The above requirement matches observations on existing RPKI deployments. OK tb@ --- usr.sbin/rpki-client/cert.c | 18 +++++++++++++++++- usr.sbin/rpki-client/crl.c | 21 +++++++++++++++++++-- 2 files changed, 36 insertions(+), 3 deletions(-) diff --git a/usr.sbin/rpki-client/cert.c b/usr.sbin/rpki-client/cert.c index 7185fab736e..540e2b338e4 100644 --- a/usr.sbin/rpki-client/cert.c +++ b/usr.sbin/rpki-client/cert.c @@ -1,4 +1,4 @@ -/* $OpenBSD: cert.c,v 1.103 2023/03/06 16:04:52 job Exp $ */ +/* $OpenBSD: cert.c,v 1.104 2023/03/06 16:58:41 job Exp $ */ /* * Copyright (c) 2022 Theo Buehler * Copyright (c) 2021 Job Snijders @@ -647,9 +647,12 @@ cert_parse_pre(const char *fn, const unsigned char *der, size_t len) size_t i; X509 *x = NULL; X509_EXTENSION *ext = NULL; + const X509_ALGOR *palg; + const ASN1_OBJECT *cobj; ASN1_OBJECT *obj; EVP_PKEY *pkey; struct parse p; + int nid; /* just fail for empty buffers, the warning was printed elsewhere */ if (der == NULL) @@ -676,6 +679,19 @@ cert_parse_pre(const char *fn, const unsigned char *der, size_t len) goto out; } + X509_get0_signature(NULL, &palg, x); + if (palg == NULL) { + cryptowarnx("%s: X509_get0_signature", p.fn); + goto out; + } + X509_ALGOR_get0(&cobj, NULL, NULL, palg); + if ((nid = OBJ_obj2nid(cobj)) != NID_sha256WithRSAEncryption) { + warnx("%s: RFC 7935: wrong signature algorithm %s, want %s", + fn, OBJ_nid2ln(nid), + OBJ_nid2ln(NID_sha256WithRSAEncryption)); + goto out; + } + /* Look for X509v3 extensions. */ if ((extsz = X509_get_ext_count(x)) < 0) diff --git a/usr.sbin/rpki-client/crl.c b/usr.sbin/rpki-client/crl.c index da4eebfe7f7..98a2059fdc7 100644 --- a/usr.sbin/rpki-client/crl.c +++ b/usr.sbin/rpki-client/crl.c @@ -1,4 +1,4 @@ -/* $OpenBSD: crl.c,v 1.22 2023/02/21 10:18:47 tb Exp $ */ +/* $OpenBSD: crl.c,v 1.23 2023/03/06 16:58:41 job Exp $ */ /* * Copyright (c) 2019 Kristaps Dzonsons * @@ -20,6 +20,8 @@ #include #include +#include + #include "extern.h" struct crl * @@ -27,8 +29,10 @@ crl_parse(const char *fn, const unsigned char *der, size_t len) { const unsigned char *oder; struct crl *crl; + const X509_ALGOR *palg; + const ASN1_OBJECT *cobj; const ASN1_TIME *at; - int rc = 0; + int nid, rc = 0; /* just fail for empty buffers, the warning was printed elsewhere */ if (der == NULL) @@ -47,6 +51,19 @@ crl_parse(const char *fn, const unsigned char *der, size_t len) goto out; } + X509_CRL_get0_signature(crl->x509_crl, NULL, &palg); + if (palg == NULL) { + cryptowarnx("%s: X509_CRL_get0_signature", fn); + goto out; + } + X509_ALGOR_get0(&cobj, NULL, NULL, palg); + if ((nid = OBJ_obj2nid(cobj)) != NID_sha256WithRSAEncryption) { + warnx("%s: RFC 7935: wrong signature algorithm %s, want %s", + fn, OBJ_nid2ln(nid), + OBJ_nid2ln(NID_sha256WithRSAEncryption)); + goto out; + } + if ((crl->aki = x509_crl_get_aki(crl->x509_crl, fn)) == NULL) { warnx("x509_crl_get_aki failed"); goto out; -- 2.20.1