summaryrefslogtreecommitdiff
path: root/src/lib/libssl/s3_srvr.c
diff options
context:
space:
mode:
authormiod <>2014-07-11 22:57:25 +0000
committermiod <>2014-07-11 22:57:25 +0000
commitc95157e4b6c5e281cb496ef41f9969df25abef91 (patch)
treed76e443b574ed3f2bb44b4cd1fdacdba22613ea8 /src/lib/libssl/s3_srvr.c
parent994822f5ed5b52cdb013f4acc6ea695367f1bd47 (diff)
downloadopenbsd-c95157e4b6c5e281cb496ef41f9969df25abef91.tar.gz
openbsd-c95157e4b6c5e281cb496ef41f9969df25abef91.tar.bz2
openbsd-c95157e4b6c5e281cb496ef41f9969df25abef91.zip
As reported by David Ramos, most consumer of ssl_get_message() perform late
bounds check, after reading the 2-, 3- or 4-byte size of the next chunk to process. But the size fields themselves are not checked for being entirely contained in the buffer. Since reading past your bounds is bad practice, and may not possible if you are using a secure memory allocator, we need to add the necessary bounds check, at the expense of some readability. As a bonus, a wrong size GOST session key will now trigger an error instead of a printf to stderr and it being handled as if it had the correct size. Creating this diff made my eyes bleed (in the real sense); reviewing it made guenther@'s and beck@'s eyes bleed too (in the literal sense). ok guenther@ beck@
Diffstat (limited to 'src/lib/libssl/s3_srvr.c')
-rw-r--r--src/lib/libssl/s3_srvr.c106
1 files changed, 65 insertions, 41 deletions
diff --git a/src/lib/libssl/s3_srvr.c b/src/lib/libssl/s3_srvr.c
index 66a4552237..89325b7be9 100644
--- a/src/lib/libssl/s3_srvr.c
+++ b/src/lib/libssl/s3_srvr.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: s3_srvr.c,v 1.74 2014/07/11 15:18:52 miod Exp $ */ 1/* $OpenBSD: s3_srvr.c,v 1.75 2014/07/11 22:57:25 miod Exp $ */
2/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) 2/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
3 * All rights reserved. 3 * All rights reserved.
4 * 4 *
@@ -894,18 +894,17 @@ ssl3_get_client_hello(SSL *s)
894 s->state = SSL3_ST_SR_CLNT_HELLO_B; 894 s->state = SSL3_ST_SR_CLNT_HELLO_B;
895 } 895 }
896 s->first_packet = 1; 896 s->first_packet = 1;
897 n = s->method->ssl_get_message(s, 897 n = s->method->ssl_get_message(s, SSL3_ST_SR_CLNT_HELLO_B,
898 SSL3_ST_SR_CLNT_HELLO_B, 898 SSL3_ST_SR_CLNT_HELLO_C, SSL3_MT_CLIENT_HELLO,
899 SSL3_ST_SR_CLNT_HELLO_C, 899 SSL3_RT_MAX_PLAIN_LENGTH, &ok);
900 SSL3_MT_CLIENT_HELLO,
901 SSL3_RT_MAX_PLAIN_LENGTH,
902 &ok);
903 900
904 if (!ok) 901 if (!ok)
905 return ((int)n); 902 return ((int)n);
906 s->first_packet = 0; 903 s->first_packet = 0;
907 d = p=(unsigned char *)s->init_msg; 904 d = p = (unsigned char *)s->init_msg;
908 905
906 if (2 > n)
907 goto truncated;
909 /* 908 /*
910 * Use version from inside client hello, not from record header. 909 * Use version from inside client hello, not from record header.
911 * (may differ: see RFC 2246, Appendix E, second paragraph) 910 * (may differ: see RFC 2246, Appendix E, second paragraph)
@@ -944,12 +943,17 @@ ssl3_get_client_hello(SSL *s)
944 return (1); 943 return (1);
945 } 944 }
946 945
946 if (p + SSL3_RANDOM_SIZE + 1 - d > n)
947 goto truncated;
948
947 /* load the client random */ 949 /* load the client random */
948 memcpy(s->s3->client_random, p, SSL3_RANDOM_SIZE); 950 memcpy(s->s3->client_random, p, SSL3_RANDOM_SIZE);
949 p += SSL3_RANDOM_SIZE; 951 p += SSL3_RANDOM_SIZE;
950 952
951 /* get the session-id */ 953 /* get the session-id */
952 j= *(p++); 954 j= *(p++);
955 if (p + j - d > n)
956 goto truncated;
953 957
954 s->hit = 0; 958 s->hit = 0;
955 /* 959 /*
@@ -988,6 +992,8 @@ ssl3_get_client_hello(SSL *s)
988 992
989 if (SSL_IS_DTLS(s)) { 993 if (SSL_IS_DTLS(s)) {
990 /* cookie stuff */ 994 /* cookie stuff */
995 if (p + 1 - d > n)
996 goto truncated;
991 cookie_len = *(p++); 997 cookie_len = *(p++);
992 998
993 /* 999 /*
@@ -1003,6 +1009,9 @@ ssl3_get_client_hello(SSL *s)
1003 goto f_err; 1009 goto f_err;
1004 } 1010 }
1005 1011
1012 if (p + cookie_len - d > n)
1013 goto truncated;
1014
1006 /* verify the cookie if appropriate option is set. */ 1015 /* verify the cookie if appropriate option is set. */
1007 if ((SSL_get_options(s) & SSL_OP_COOKIE_EXCHANGE) && 1016 if ((SSL_get_options(s) & SSL_OP_COOKIE_EXCHANGE) &&
1008 cookie_len > 0) { 1017 cookie_len > 0) {
@@ -1032,6 +1041,8 @@ ssl3_get_client_hello(SSL *s)
1032 p += cookie_len; 1041 p += cookie_len;
1033 } 1042 }
1034 1043
1044 if (p + 2 - d > n)
1045 goto truncated;
1035 n2s(p, i); 1046 n2s(p, i);
1036 if ((i == 0) && (j != 0)) { 1047 if ((i == 0) && (j != 0)) {
1037 /* we need a cipher if we are not resuming a session */ 1048 /* we need a cipher if we are not resuming a session */
@@ -1040,13 +1051,8 @@ ssl3_get_client_hello(SSL *s)
1040 SSL_R_NO_CIPHERS_SPECIFIED); 1051 SSL_R_NO_CIPHERS_SPECIFIED);
1041 goto f_err; 1052 goto f_err;
1042 } 1053 }
1043 if ((p + i) >= (d + n)) { 1054 if (p + i - d > n)
1044 /* not enough data */ 1055 goto truncated;
1045 al = SSL_AD_DECODE_ERROR;
1046 SSLerr(SSL_F_SSL3_GET_CLIENT_HELLO,
1047 SSL_R_LENGTH_MISMATCH);
1048 goto f_err;
1049 }
1050 if ((i > 0) && 1056 if ((i > 0) &&
1051 (ssl_bytes_to_cipher_list(s, p, i, &(ciphers)) == NULL)) { 1057 (ssl_bytes_to_cipher_list(s, p, i, &(ciphers)) == NULL)) {
1052 goto err; 1058 goto err;
@@ -1078,14 +1084,11 @@ ssl3_get_client_hello(SSL *s)
1078 } 1084 }
1079 1085
1080 /* compression */ 1086 /* compression */
1087 if (p + 1 - d > n)
1088 goto truncated;
1081 i= *(p++); 1089 i= *(p++);
1082 if ((p + i) > (d + n)) { 1090 if (p + i - d > n)
1083 /* not enough data */ 1091 goto truncated;
1084 al = SSL_AD_DECODE_ERROR;
1085 SSLerr(SSL_F_SSL3_GET_CLIENT_HELLO,
1086 SSL_R_LENGTH_MISMATCH);
1087 goto f_err;
1088 }
1089 for (j = 0; j < i; j++) { 1092 for (j = 0; j < i; j++) {
1090 if (p[j] == 0) 1093 if (p[j] == 0)
1091 break; 1094 break;
@@ -1247,6 +1250,9 @@ ssl3_get_client_hello(SSL *s)
1247 if (ret < 0) 1250 if (ret < 0)
1248 ret = 1; 1251 ret = 1;
1249 if (0) { 1252 if (0) {
1253truncated:
1254 al = SSL_AD_DECODE_ERROR;
1255 SSLerr(SSL_F_SSL3_GET_CLIENT_HELLO, SSL_R_BAD_PACKET_LENGTH);
1250f_err: 1256f_err:
1251 ssl3_send_alert(s, SSL3_AL_FATAL, al); 1257 ssl3_send_alert(s, SSL3_AL_FATAL, al);
1252 } 1258 }
@@ -1847,7 +1853,7 @@ ssl3_get_client_key_exchange(SSL *s)
1847 int i, al, ok; 1853 int i, al, ok;
1848 long n; 1854 long n;
1849 unsigned long alg_k; 1855 unsigned long alg_k;
1850 unsigned char *p; 1856 unsigned char *d, *p;
1851 RSA *rsa = NULL; 1857 RSA *rsa = NULL;
1852 EVP_PKEY *pkey = NULL; 1858 EVP_PKEY *pkey = NULL;
1853 BIGNUM *pub = NULL; 1859 BIGNUM *pub = NULL;
@@ -1863,7 +1869,7 @@ ssl3_get_client_key_exchange(SSL *s)
1863 SSL3_ST_SR_KEY_EXCH_B, SSL3_MT_CLIENT_KEY_EXCHANGE, 2048, &ok); 1869 SSL3_ST_SR_KEY_EXCH_B, SSL3_MT_CLIENT_KEY_EXCHANGE, 2048, &ok);
1864 if (!ok) 1870 if (!ok)
1865 return ((int)n); 1871 return ((int)n);
1866 p = (unsigned char *)s->init_msg; 1872 d = p = (unsigned char *)s->init_msg;
1867 1873
1868 alg_k = s->s3->tmp.new_cipher->algorithm_mkey; 1874 alg_k = s->s3->tmp.new_cipher->algorithm_mkey;
1869 1875
@@ -1897,6 +1903,8 @@ ssl3_get_client_key_exchange(SSL *s)
1897 1903
1898 /* TLS and [incidentally] DTLS{0xFEFF} */ 1904 /* TLS and [incidentally] DTLS{0xFEFF} */
1899 if (s->version > SSL3_VERSION && s->version != DTLS1_BAD_VER) { 1905 if (s->version > SSL3_VERSION && s->version != DTLS1_BAD_VER) {
1906 if (2 > n)
1907 goto truncated;
1900 n2s(p, i); 1908 n2s(p, i);
1901 if (n != i + 2) { 1909 if (n != i + 2) {
1902 if (!(s->options & SSL_OP_TLS_D5_BUG)) { 1910 if (!(s->options & SSL_OP_TLS_D5_BUG)) {
@@ -1919,6 +1927,8 @@ ssl3_get_client_key_exchange(SSL *s)
1919 /* SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE,SSL_R_BAD_RSA_DECRYPT); */ 1927 /* SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE,SSL_R_BAD_RSA_DECRYPT); */
1920 } 1928 }
1921 1929
1930 if (p + 2 - d > n) /* needed in the SSL3 case */
1931 goto truncated;
1922 if ((al == -1) && !((p[0] == (s->client_version >> 8)) && 1932 if ((al == -1) && !((p[0] == (s->client_version >> 8)) &&
1923 (p[1] == (s->client_version & 0xff)))) { 1933 (p[1] == (s->client_version & 0xff)))) {
1924 /* 1934 /*
@@ -1975,6 +1985,8 @@ ssl3_get_client_key_exchange(SSL *s)
1975 OPENSSL_cleanse(p, i); 1985 OPENSSL_cleanse(p, i);
1976 } else 1986 } else
1977 if (alg_k & (SSL_kEDH|SSL_kDHr|SSL_kDHd)) { 1987 if (alg_k & (SSL_kEDH|SSL_kDHr|SSL_kDHd)) {
1988 if (2 > n)
1989 goto truncated;
1978 n2s(p, i); 1990 n2s(p, i);
1979 if (n != i + 2) { 1991 if (n != i + 2) {
1980 if (!(s->options & SSL_OP_SSLEAY_080_CLIENT_DH_BUG)) { 1992 if (!(s->options & SSL_OP_SSLEAY_080_CLIENT_DH_BUG)) {
@@ -2206,6 +2218,8 @@ ssl3_get_client_key_exchange(SSL *s)
2206 client_pub_pkey) <= 0) 2218 client_pub_pkey) <= 0)
2207 ERR_clear_error(); 2219 ERR_clear_error();
2208 } 2220 }
2221 if (2 > n)
2222 goto truncated;
2209 /* Decrypt session key */ 2223 /* Decrypt session key */
2210 if (ASN1_get_object((const unsigned char **)&p, &Tlen, &Ttag, 2224 if (ASN1_get_object((const unsigned char **)&p, &Tlen, &Ttag,
2211 &Tclass, n) != V_ASN1_CONSTRUCTED || 2225 &Tclass, n) != V_ASN1_CONSTRUCTED ||
@@ -2242,11 +2256,14 @@ gerr:
2242 } else { 2256 } else {
2243 al = SSL_AD_HANDSHAKE_FAILURE; 2257 al = SSL_AD_HANDSHAKE_FAILURE;
2244 SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, 2258 SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE,
2245 SSL_R_UNKNOWN_CIPHER_TYPE); 2259 SSL_R_UNKNOWN_CIPHER_TYPE);
2246 goto f_err; 2260 goto f_err;
2247 } 2261 }
2248 2262
2249 return (1); 2263 return (1);
2264truncated:
2265 al = SSL_AD_DECODE_ERROR;
2266 SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, SSL_R_BAD_PACKET_LENGTH);
2250f_err: 2267f_err:
2251 ssl3_send_alert(s, SSL3_AL_FATAL, al); 2268 ssl3_send_alert(s, SSL3_AL_FATAL, al);
2252err: 2269err:
@@ -2338,6 +2355,8 @@ ssl3_get_cert_verify(SSL *s)
2338 al = SSL_AD_INTERNAL_ERROR; 2355 al = SSL_AD_INTERNAL_ERROR;
2339 goto f_err; 2356 goto f_err;
2340 } 2357 }
2358 if (2 > n)
2359 goto truncated;
2341 /* Check key type is consistent with signature */ 2360 /* Check key type is consistent with signature */
2342 if (sigalg != (int)p[1]) { 2361 if (sigalg != (int)p[1]) {
2343 SSLerr(SSL_F_SSL3_GET_CERT_VERIFY, 2362 SSLerr(SSL_F_SSL3_GET_CERT_VERIFY,
@@ -2355,14 +2374,12 @@ ssl3_get_cert_verify(SSL *s)
2355 p += 2; 2374 p += 2;
2356 n -= 2; 2375 n -= 2;
2357 } 2376 }
2377 if (2 > n)
2378 goto truncated;
2358 n2s(p, i); 2379 n2s(p, i);
2359 n -= 2; 2380 n -= 2;
2360 if (i > n) { 2381 if (i > n)
2361 SSLerr(SSL_F_SSL3_GET_CERT_VERIFY, 2382 goto truncated;
2362 SSL_R_LENGTH_MISMATCH);
2363 al = SSL_AD_DECODE_ERROR;
2364 goto f_err;
2365 }
2366 } 2383 }
2367 j = EVP_PKEY_size(pkey); 2384 j = EVP_PKEY_size(pkey);
2368 if ((i > j) || (n > j) || (n <= 0)) { 2385 if ((i > j) || (n > j) || (n <= 0)) {
@@ -2445,7 +2462,10 @@ ssl3_get_cert_verify(SSL *s)
2445 EVP_PKEY_CTX *pctx = EVP_PKEY_CTX_new(pkey, NULL); 2462 EVP_PKEY_CTX *pctx = EVP_PKEY_CTX_new(pkey, NULL);
2446 EVP_PKEY_verify_init(pctx); 2463 EVP_PKEY_verify_init(pctx);
2447 if (i != 64) { 2464 if (i != 64) {
2448 fprintf(stderr, "GOST signature length is %d", i); 2465 SSLerr(SSL_F_SSL3_GET_CERT_VERIFY,
2466 SSL_R_WRONG_SIGNATURE_SIZE);
2467 al = SSL_AD_DECODE_ERROR;
2468 goto f_err;
2449 } 2469 }
2450 for (idx = 0; idx < 64; idx++) { 2470 for (idx = 0; idx < 64; idx++) {
2451 signature[63 - idx] = p[idx]; 2471 signature[63 - idx] = p[idx];
@@ -2469,6 +2489,9 @@ ssl3_get_cert_verify(SSL *s)
2469 2489
2470 ret = 1; 2490 ret = 1;
2471 if (0) { 2491 if (0) {
2492truncated:
2493 al = SSL_AD_DECODE_ERROR;
2494 SSLerr(SSL_F_SSL3_GET_CERT_VERIFY, SSL_R_BAD_PACKET_LENGTH);
2472f_err: 2495f_err:
2473 ssl3_send_alert(s, SSL3_AL_FATAL, al); 2496 ssl3_send_alert(s, SSL3_AL_FATAL, al);
2474 } 2497 }
@@ -2490,7 +2513,6 @@ ssl3_get_client_certificate(SSL *s)
2490 X509 *x = NULL; 2513 X509 *x = NULL;
2491 unsigned long l, nc, llen, n; 2514 unsigned long l, nc, llen, n;
2492 const unsigned char *p, *q; 2515 const unsigned char *p, *q;
2493 unsigned char *d;
2494 STACK_OF(X509) *sk = NULL; 2516 STACK_OF(X509) *sk = NULL;
2495 2517
2496 n = s->method->ssl_get_message(s, SSL3_ST_SR_CERT_A, SSL3_ST_SR_CERT_B, 2518 n = s->method->ssl_get_message(s, SSL3_ST_SR_CERT_A, SSL3_ST_SR_CERT_B,
@@ -2528,7 +2550,7 @@ ssl3_get_client_certificate(SSL *s)
2528 SSL_R_WRONG_MESSAGE_TYPE); 2550 SSL_R_WRONG_MESSAGE_TYPE);
2529 goto f_err; 2551 goto f_err;
2530 } 2552 }
2531 p = d = (unsigned char *)s->init_msg; 2553 p = (const unsigned char *)s->init_msg;
2532 2554
2533 if ((sk = sk_X509_new_null()) == NULL) { 2555 if ((sk = sk_X509_new_null()) == NULL) {
2534 SSLerr(SSL_F_SSL3_GET_CLIENT_CERTIFICATE, 2556 SSLerr(SSL_F_SSL3_GET_CLIENT_CERTIFICATE,
@@ -2536,16 +2558,14 @@ ssl3_get_client_certificate(SSL *s)
2536 goto err; 2558 goto err;
2537 } 2559 }
2538 2560
2561 if (3 > n)
2562 goto truncated;
2539 n2l3(p, llen); 2563 n2l3(p, llen);
2540 if (llen + 3 != n) { 2564 if (llen + 3 != n)
2541 al = SSL_AD_DECODE_ERROR; 2565 goto truncated;
2542 SSLerr(SSL_F_SSL3_GET_CLIENT_CERTIFICATE,
2543 SSL_R_LENGTH_MISMATCH);
2544 goto f_err;
2545 }
2546 for (nc = 0; nc < llen;) { 2566 for (nc = 0; nc < llen;) {
2547 n2l3(p, l); 2567 n2l3(p, l);
2548 if ((l + nc + 3) > llen) { 2568 if (l + nc + 3 > llen) {
2549 al = SSL_AD_DECODE_ERROR; 2569 al = SSL_AD_DECODE_ERROR;
2550 SSLerr(SSL_F_SSL3_GET_CLIENT_CERTIFICATE, 2570 SSLerr(SSL_F_SSL3_GET_CLIENT_CERTIFICATE,
2551 SSL_R_CERT_LENGTH_MISMATCH); 2571 SSL_R_CERT_LENGTH_MISMATCH);
@@ -2635,6 +2655,10 @@ ssl3_get_client_certificate(SSL *s)
2635 2655
2636 ret = 1; 2656 ret = 1;
2637 if (0) { 2657 if (0) {
2658truncated:
2659 al = SSL_AD_DECODE_ERROR;
2660 SSLerr(SSL_F_SSL3_GET_CLIENT_CERTIFICATE,
2661 SSL_R_BAD_PACKET_LENGTH);
2638f_err: 2662f_err:
2639 ssl3_send_alert(s, SSL3_AL_FATAL, al); 2663 ssl3_send_alert(s, SSL3_AL_FATAL, al);
2640 } 2664 }