summaryrefslogtreecommitdiff
path: root/lib/libssl/s3_clnt.c
diff options
context:
space:
mode:
Diffstat (limited to 'lib/libssl/s3_clnt.c')
-rw-r--r--lib/libssl/s3_clnt.c85
1 files changed, 74 insertions, 11 deletions
diff --git a/lib/libssl/s3_clnt.c b/lib/libssl/s3_clnt.c
index 3596acf1de5..884b9f1efb8 100644
--- a/lib/libssl/s3_clnt.c
+++ b/lib/libssl/s3_clnt.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: s3_clnt.c,v 1.77 2014/07/11 15:44:53 miod Exp $ */
+/* $OpenBSD: s3_clnt.c,v 1.78 2014/07/11 22:57:25 miod Exp $ */
/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
* All rights reserved.
*
@@ -814,6 +814,8 @@ ssl3_get_server_hello(SSL *s)
d = p = (unsigned char *)s->init_msg;
+ if (2 > n)
+ goto truncated;
if ((p[0] != (s->version >> 8)) || (p[1] != (s->version & 0xff))) {
SSLerr(SSL_F_SSL3_GET_SERVER_HELLO, SSL_R_WRONG_SSL_VERSION);
s->version = (s->version&0xff00) | p[1];
@@ -823,6 +825,10 @@ ssl3_get_server_hello(SSL *s)
p += 2;
/* load the server hello data */
+
+ if (p + SSL3_RANDOM_SIZE + 1 - d > n)
+ goto truncated;
+
/* load the server random */
memcpy(s->s3->server_random, p, SSL3_RANDOM_SIZE);
p += SSL3_RANDOM_SIZE;
@@ -838,6 +844,9 @@ ssl3_get_server_hello(SSL *s)
goto f_err;
}
+ if (p + j + 2 - d > n)
+ goto truncated;
+
/*
* Check if we want to resume the session based on external
* pre-shared secret
@@ -935,6 +944,8 @@ ssl3_get_server_hello(SSL *s)
}
/* lets get the compression algorithm */
/* COMPRESSION */
+ if (p + 1 - d > n)
+ goto truncated;
if (*(p++) != 0) {
al = SSL_AD_ILLEGAL_PARAMETER;
SSLerr(SSL_F_SSL3_GET_SERVER_HELLO,
@@ -958,15 +969,15 @@ ssl3_get_server_hello(SSL *s)
}
}
- if (p != (d + n)) {
- /* wrong packet length */
- al = SSL_AD_DECODE_ERROR;
- SSLerr(SSL_F_SSL3_GET_SERVER_HELLO,
- SSL_R_BAD_PACKET_LENGTH);
- goto f_err;
- }
+ if (p != d + n)
+ goto truncated;
return (1);
+
+truncated:
+ /* wrong packet length */
+ al = SSL_AD_DECODE_ERROR;
+ SSLerr(SSL_F_SSL3_GET_SERVER_HELLO, SSL_R_BAD_PACKET_LENGTH);
f_err:
ssl3_send_alert(s, SSL3_AL_FATAL, al);
err:
@@ -1015,6 +1026,8 @@ ssl3_get_server_certificate(SSL *s)
goto err;
}
+ if (p + 3 - d > n)
+ goto truncated;
n2l3(p, llen);
if (llen + 3 != n) {
al = SSL_AD_DECODE_ERROR;
@@ -1023,6 +1036,8 @@ ssl3_get_server_certificate(SSL *s)
goto f_err;
}
for (nc = 0; nc < llen; ) {
+ if (p + 3 - d > n)
+ goto truncated;
n2l3(p, l);
if ((l + nc + 3) > llen) {
al = SSL_AD_DECODE_ERROR;
@@ -1094,7 +1109,7 @@ ssl3_get_server_certificate(SSL *s)
x = NULL;
al = SSL3_AL_FATAL;
SSLerr(SSL_F_SSL3_GET_SERVER_CERTIFICATE,
- SSL_R_UNABLE_TO_FIND_PUBLIC_KEY_PARAMETERS);
+ SSL_R_UNABLE_TO_FIND_PUBLIC_KEY_PARAMETERS);
goto f_err;
}
@@ -1103,7 +1118,7 @@ ssl3_get_server_certificate(SSL *s)
x = NULL;
al = SSL3_AL_FATAL;
SSLerr(SSL_F_SSL3_GET_SERVER_CERTIFICATE,
- SSL_R_UNKNOWN_CERTIFICATE_TYPE);
+ SSL_R_UNKNOWN_CERTIFICATE_TYPE);
goto f_err;
}
@@ -1137,6 +1152,11 @@ ssl3_get_server_certificate(SSL *s)
ret = 1;
if (0) {
+truncated:
+ /* wrong packet length */
+ al = SSL_AD_DECODE_ERROR;
+ SSLerr(SSL_F_SSL3_GET_SERVER_CERTIFICATE,
+ SSL_R_BAD_PACKET_LENGTH);
f_err:
ssl3_send_alert(s, SSL3_AL_FATAL, al);
}
@@ -1206,6 +1226,8 @@ ssl3_get_key_exchange(SSL *s)
ERR_R_MALLOC_FAILURE);
goto err;
}
+ if (2 > n)
+ goto truncated;
n2s(p, i);
param_len = i + 2;
if (param_len > n) {
@@ -1221,6 +1243,8 @@ ssl3_get_key_exchange(SSL *s)
}
p += i;
+ if (param_len + 2 > n)
+ goto truncated;
n2s(p, i);
param_len += i + 2;
if (param_len > n) {
@@ -1258,6 +1282,8 @@ ssl3_get_key_exchange(SSL *s)
ERR_R_DH_LIB);
goto err;
}
+ if (2 > n)
+ goto truncated;
n2s(p, i);
param_len = i + 2;
if (param_len > n) {
@@ -1273,6 +1299,8 @@ ssl3_get_key_exchange(SSL *s)
}
p += i;
+ if (param_len + 2 > n)
+ goto truncated;
n2s(p, i);
param_len += i + 2;
if (param_len > n) {
@@ -1288,6 +1316,8 @@ ssl3_get_key_exchange(SSL *s)
}
p += i;
+ if (param_len + 2 > n)
+ goto truncated;
n2s(p, i);
param_len += i + 2;
if (param_len > n) {
@@ -1376,6 +1406,8 @@ ssl3_get_key_exchange(SSL *s)
goto err;
}
+ if (param_len + 1 > n)
+ goto truncated;
encoded_pt_len = *p;
/* length of encoded point */
p += 1;
@@ -1435,6 +1467,8 @@ ssl3_get_key_exchange(SSL *s)
* Check key type is consistent
* with signature
*/
+ if (2 > n)
+ goto truncated;
if (sigalg != (int)p[1]) {
SSLerr(SSL_F_SSL3_GET_KEY_EXCHANGE,
SSL_R_WRONG_SIGNATURE_TYPE);
@@ -1453,11 +1487,13 @@ ssl3_get_key_exchange(SSL *s)
} else
md = EVP_sha1();
+ if (2 > n)
+ goto truncated;
n2s(p, i);
n -= 2;
j = EVP_PKEY_size(pkey);
- if ((i != n) || (n > j) || (n <= 0)) {
+ if (i != n || n > j) {
/* wrong packet length */
al = SSL_AD_DECODE_ERROR;
SSLerr(SSL_F_SSL3_GET_KEY_EXCHANGE,
@@ -1534,6 +1570,10 @@ ssl3_get_key_exchange(SSL *s)
EVP_PKEY_free(pkey);
EVP_MD_CTX_cleanup(&md_ctx);
return (1);
+truncated:
+ /* wrong packet length */
+ al = SSL_AD_DECODE_ERROR;
+ SSLerr(SSL_F_SSL3_GET_KEY_EXCHANGE, SSL_R_BAD_PACKET_LENGTH);
f_err:
ssl3_send_alert(s, SSL3_AL_FATAL, al);
err:
@@ -1606,13 +1646,26 @@ ssl3_get_certificate_request(SSL *s)
}
/* get the certificate types */
+ if (1 > n)
+ goto truncated;
ctype_num= *(p++);
if (ctype_num > SSL3_CT_NUMBER)
ctype_num = SSL3_CT_NUMBER;
+ if (p + ctype_num - d > n) {
+ SSLerr(SSL_F_SSL3_GET_CERTIFICATE_REQUEST,
+ SSL_R_DATA_LENGTH_TOO_LONG);
+ goto err;
+ }
+
for (i = 0; i < ctype_num; i++)
s->s3->tmp.ctype[i] = p[i];
p += ctype_num;
if (SSL_USE_SIGALGS(s)) {
+ if (p + 2 - d > n) {
+ SSLerr(SSL_F_SSL3_GET_CERTIFICATE_REQUEST,
+ SSL_R_DATA_LENGTH_TOO_LONG);
+ goto err;
+ }
n2s(p, llen);
/* Check we have enough room for signature algorithms and
* following length value.
@@ -1633,6 +1686,11 @@ ssl3_get_certificate_request(SSL *s)
}
/* get the CA RDNs */
+ if (p + 2 - d > n) {
+ SSLerr(SSL_F_SSL3_GET_CERTIFICATE_REQUEST,
+ SSL_R_DATA_LENGTH_TOO_LONG);
+ goto err;
+ }
n2s(p, llen);
if ((unsigned long)(p - d + llen) != n) {
@@ -1698,6 +1756,11 @@ cont:
ca_sk = NULL;
ret = 1;
+ if (0) {
+truncated:
+ SSLerr(SSL_F_SSL3_GET_CERTIFICATE_REQUEST,
+ SSL_R_BAD_PACKET_LENGTH);
+ }
err:
if (ca_sk != NULL)
sk_X509_NAME_pop_free(ca_sk, X509_NAME_free);