summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNikos Mavrogiannopoulos <nmav@gnutls.org>2017-07-01 10:50:57 +0200
committerNikos Mavrogiannopoulos <nmav@gnutls.org>2017-07-01 11:04:01 +0200
commit3c36d980d447251b34677c21bd4a141829c045f6 (patch)
tree0984edb40f5d59156633a60cce55cde5c12867ad
parent4115dda443f38119ad46262f7f4adc78cfa1bf83 (diff)
downloadgnutls-3c36d980d447251b34677c21bd4a141829c045f6.tar.gz
OCSP: find_signercert: improved DER length calculation
Previously we were assuming a fixed amount of length bytes which is not correct for all possible lengths. Use libtasn1 to decode the length field. Resolves: #223 Signed-off-by: Nikos Mavrogiannopoulos <nmav@gnutls.org>
-rw-r--r--lib/x509/ocsp.c30
1 files changed, 24 insertions, 6 deletions
diff --git a/lib/x509/ocsp.c b/lib/x509/ocsp.c
index 68e721eaac..321a676b3c 100644
--- a/lib/x509/ocsp.c
+++ b/lib/x509/ocsp.c
@@ -1923,9 +1923,10 @@ static gnutls_x509_crt_t find_signercert(gnutls_ocsp_resp_t resp)
for (i = 0; i < ncerts; i++) {
if (keyid.data != NULL) {
- uint8_t digest[128]; /* to support longer key IDs */
+ uint8_t digest[64]; /* to support longer key IDs */
gnutls_datum_t spki;
size_t digest_size = sizeof(digest);
+ int len;
_gnutls_debug_log("checking key ID against SPK identifier\n");
@@ -1946,19 +1947,36 @@ static gnutls_x509_crt_t find_signercert(gnutls_ocsp_resp_t resp)
&spki);
if (rc < 0 || spki.size < 6) {
signercert = NULL;
- goto quit;
+ continue;
}
/* For some reason the protocol requires we skip the
* tag, length and number of unused bits.
*/
- spki.data += 5;
- spki.size -= 5;
- rc = gnutls_hash_fast(GNUTLS_DIG_SHA1, spki.data, spki.size, digest);
+ if (spki.data[0] != 0x03) { /* bit string */
+ gnutls_assert();
+ signercert = NULL;
+ continue;
+ }
+
+ rc = asn1_get_length_der(spki.data+1, spki.size-1, &len);
+ if (rc <= 0) {
+ gnutls_assert();
+ signercert = NULL;
+ continue;
+ }
+ len += 1+1; /* skip unused bits as well */
+ if (len >= (int)spki.size) {
+ gnutls_assert();
+ signercert = NULL;
+ continue;
+ }
+
+ rc = gnutls_hash_fast(GNUTLS_DIG_SHA1, spki.data+len, spki.size-len, digest);
if (rc < 0) {
gnutls_assert();
signercert = NULL;
- goto quit;
+ continue;
}
if ((20 == keyid.size) &&