diff options
Diffstat (limited to 'src/lib')
| -rw-r--r-- | src/lib/libtls/tls_verify.c | 17 |
1 files changed, 11 insertions, 6 deletions
diff --git a/src/lib/libtls/tls_verify.c b/src/lib/libtls/tls_verify.c index acc034d9c1..a0c39b9dd4 100644 --- a/src/lib/libtls/tls_verify.c +++ b/src/lib/libtls/tls_verify.c | |||
| @@ -1,4 +1,4 @@ | |||
| 1 | /* $OpenBSD: tls_verify.c,v 1.25 2023/05/28 09:06:34 beck Exp $ */ | 1 | /* $OpenBSD: tls_verify.c,v 1.26 2023/05/29 14:12:36 beck Exp $ */ |
| 2 | /* | 2 | /* |
| 3 | * Copyright (c) 2014 Jeremie Courreges-Anglas <jca@openbsd.org> | 3 | * Copyright (c) 2014 Jeremie Courreges-Anglas <jca@openbsd.org> |
| 4 | * | 4 | * |
| @@ -224,6 +224,8 @@ tls_check_common_name(struct tls *ctx, X509 *cert, const char *name, | |||
| 224 | NID_commonName, lastpos); | 224 | NID_commonName, lastpos); |
| 225 | if (lastpos == -1) | 225 | if (lastpos == -1) |
| 226 | goto done; | 226 | goto done; |
| 227 | if (lastpos < 0) | ||
| 228 | goto err; | ||
| 227 | if (X509_NAME_get_index_by_NID(subject_name, NID_commonName, lastpos) | 229 | if (X509_NAME_get_index_by_NID(subject_name, NID_commonName, lastpos) |
| 228 | != -1) { | 230 | != -1) { |
| 229 | /* | 231 | /* |
| @@ -243,9 +245,7 @@ tls_check_common_name(struct tls *ctx, X509 *cert, const char *name, | |||
| 243 | data = X509_NAME_ENTRY_get_data(X509_NAME_get_entry(subject_name, | 245 | data = X509_NAME_ENTRY_get_data(X509_NAME_get_entry(subject_name, |
| 244 | lastpos)); | 246 | lastpos)); |
| 245 | /* | 247 | /* |
| 246 | * Fail if we cannot encode as UTF-8, if the CN is of invalid length, or | 248 | * Fail if we cannot encode the CN bytes as UTF-8. |
| 247 | * if the UTF-8 encoding of the string contains a 0 byte. We treat any | ||
| 248 | * certificate with such data in the CN as hostile and fail. | ||
| 249 | */ | 249 | */ |
| 250 | if ((common_name_len = ASN1_STRING_to_UTF8(&utf8_bytes, data)) < 0) { | 250 | if ((common_name_len = ASN1_STRING_to_UTF8(&utf8_bytes, data)) < 0) { |
| 251 | tls_set_errorx(ctx, "error verifying name '%s': " | 251 | tls_set_errorx(ctx, "error verifying name '%s': " |
| @@ -253,14 +253,19 @@ tls_check_common_name(struct tls *ctx, X509 *cert, const char *name, | |||
| 253 | "probably a malicious certificate", name); | 253 | "probably a malicious certificate", name); |
| 254 | goto err; | 254 | goto err; |
| 255 | } | 255 | } |
| 256 | 256 | /* | |
| 257 | * Fail if the CN is of invalid length. RFC 5280 specifies that a CN | ||
| 258 | * must be between 1 and 64 bytes long. | ||
| 259 | */ | ||
| 257 | if (common_name_len < 1 || common_name_len > 64) { | 260 | if (common_name_len < 1 || common_name_len > 64) { |
| 258 | tls_set_errorx(ctx, "error verifying name '%s': " | 261 | tls_set_errorx(ctx, "error verifying name '%s': " |
| 259 | "Common Name field has invalid length, " | 262 | "Common Name field has invalid length, " |
| 260 | "probably a malicious certificate", name); | 263 | "probably a malicious certificate", name); |
| 261 | goto err; | 264 | goto err; |
| 262 | } | 265 | } |
| 263 | 266 | /* | |
| 267 | * Fail if the resulting text contains a NUL byte. | ||
| 268 | */ | ||
| 264 | if (memchr(utf8_bytes, 0, common_name_len) != NULL) { | 269 | if (memchr(utf8_bytes, 0, common_name_len) != NULL) { |
| 265 | tls_set_errorx(ctx, "error verifying name '%s': " | 270 | tls_set_errorx(ctx, "error verifying name '%s': " |
| 266 | "NUL byte in Common Name field, " | 271 | "NUL byte in Common Name field, " |
