X-Git-Url: https://git.librecmc.org/?a=blobdiff_plain;f=ssl%2Fs3_srvr.c;h=ff2fd3082196cd9ca32257b5ad6e7de00eea96ab;hb=36d16f8ee0845d932e250286e8e236580470e35b;hp=ca39d6b1c8e97374f0749ef8a58fb870095e05a0;hpb=14f3d7c5ccd38875d5f3ee2007baec5a7240adc0;p=oweals%2Fopenssl.git diff --git a/ssl/s3_srvr.c b/ssl/s3_srvr.c index ca39d6b1c8..ff2fd30821 100644 --- a/ssl/s3_srvr.c +++ b/ssl/s3_srvr.c @@ -56,7 +56,7 @@ * [including the GNU Public Licence.] */ /* ==================================================================== - * Copyright (c) 1998-2003 The OpenSSL Project. All rights reserved. + * Copyright (c) 1998-2005 The OpenSSL Project. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -133,21 +133,14 @@ #include #include #include +#include +#include +#ifndef OPENSSL_NO_KRB5 #include +#endif #include -#include "cryptlib.h" static SSL_METHOD *ssl3_get_server_method(int ver); -static int ssl3_get_client_hello(SSL *s); -static int ssl3_check_client_hello(SSL *s); -static int ssl3_send_server_hello(SSL *s); -static int ssl3_send_server_key_exchange(SSL *s); -static int ssl3_send_certificate_request(SSL *s); -static int ssl3_send_server_done(SSL *s); -static int ssl3_get_client_key_exchange(SSL *s); -static int ssl3_get_client_certificate(SSL *s); -static int ssl3_get_cert_verify(SSL *s); -static int ssl3_send_hello_request(SSL *s); #ifndef OPENSSL_NO_ECDH static int nid2curve_id(int nid); @@ -626,7 +619,7 @@ end: return(ret); } -static int ssl3_send_hello_request(SSL *s) +int ssl3_send_hello_request(SSL *s) { unsigned char *p; @@ -648,14 +641,14 @@ static int ssl3_send_hello_request(SSL *s) return(ssl3_do_write(s,SSL3_RT_HANDSHAKE)); } -static int ssl3_check_client_hello(SSL *s) +int ssl3_check_client_hello(SSL *s) { int ok; long n; /* this function is called when we really expect a Certificate message, * so permit appropriate message length */ - n=ssl3_get_message(s, + n=s->method->ssl_get_message(s, SSL3_ST_SR_CERT_A, SSL3_ST_SR_CERT_B, -1, @@ -681,9 +674,10 @@ static int ssl3_check_client_hello(SSL *s) return 1; } -static int ssl3_get_client_hello(SSL *s) +int ssl3_get_client_hello(SSL *s) { int i,j,ok,al,ret= -1; + int cookie_len; long n; unsigned long id; unsigned char *p,*d,*q; @@ -702,7 +696,7 @@ static int ssl3_get_client_hello(SSL *s) s->first_packet=1; s->state=SSL3_ST_SR_CLNT_HELLO_B; } - n=ssl3_get_message(s, + n=s->method->ssl_get_message(s, SSL3_ST_SR_CLNT_HELLO_B, SSL3_ST_SR_CLNT_HELLO_C, SSL3_MT_CLIENT_HELLO, @@ -767,6 +761,68 @@ static int ssl3_get_client_hello(SSL *s) } p+=j; + + if (SSL_version(s) == DTLS1_VERSION) + { + /* cookie stuff */ + cookie_len = *(p++); + + if ( (SSL_get_options(s) & SSL_OP_COOKIE_EXCHANGE) && + s->d1->send_cookie == 0) + { + /* HelloVerifyMessage has already been sent */ + if ( cookie_len != s->d1->cookie_len) + { + al = SSL_AD_HANDSHAKE_FAILURE; + SSLerr(SSL_F_SSL3_GET_CLIENT_HELLO, SSL_R_COOKIE_MISMATCH); + goto f_err; + } + } + + /* + * The ClientHello may contain a cookie even if the + * HelloVerify message has not been sent--make sure that it + * does not cause an overflow. + */ + if ( cookie_len > sizeof(s->d1->rcvd_cookie)) + { + /* too much data */ + al = SSL_AD_DECODE_ERROR; + SSLerr(SSL_F_SSL3_GET_CLIENT_HELLO, SSL_R_COOKIE_MISMATCH); + goto f_err; + } + + /* verify the cookie if appropriate option is set. */ + if ( (SSL_get_options(s) & SSL_OP_COOKIE_EXCHANGE) && + cookie_len > 0) + { + memcpy(s->d1->rcvd_cookie, p, cookie_len); + + if ( s->ctx->app_verify_cookie_cb != NULL) + { + if ( s->ctx->app_verify_cookie_cb(s, s->d1->rcvd_cookie, + cookie_len) == 0) + { + al=SSL_AD_HANDSHAKE_FAILURE; + SSLerr(SSL_F_SSL3_GET_CLIENT_HELLO, + SSL_R_COOKIE_MISMATCH); + goto f_err; + } + /* else cookie verification succeeded */ + } + else if ( memcmp(s->d1->rcvd_cookie, s->d1->cookie, + s->d1->cookie_len) != 0) /* default verification */ + { + al=SSL_AD_HANDSHAKE_FAILURE; + SSLerr(SSL_F_SSL3_GET_CLIENT_HELLO, + SSL_R_COOKIE_MISMATCH); + goto f_err; + } + } + + p += cookie_len; + } + n2s(p,i); if ((i == 0) && (j != 0)) { @@ -980,7 +1036,7 @@ err: return(ret); } -static int ssl3_send_server_hello(SSL *s) +int ssl3_send_server_hello(SSL *s) { unsigned char *buf; unsigned char *p,*d; @@ -993,7 +1049,7 @@ static int ssl3_send_server_hello(SSL *s) p=s->s3->server_random; Time=time(NULL); /* Time */ l2n(Time,p); - RAND_pseudo_bytes(p,SSL3_RANDOM_SIZE-sizeof(Time)); + RAND_pseudo_bytes(p,SSL3_RANDOM_SIZE-4); /* Do the message type and length last */ d=p= &(buf[4]); @@ -1016,7 +1072,7 @@ static int ssl3_send_server_hello(SSL *s) s->session->session_id_length=0; sl=s->session->session_id_length; - if (sl > sizeof s->session->session_id) + if (sl > (int)sizeof(s->session->session_id)) { SSLerr(SSL_F_SSL3_SEND_SERVER_HELLO, ERR_R_INTERNAL_ERROR); return -1; @@ -1051,7 +1107,7 @@ static int ssl3_send_server_hello(SSL *s) return(ssl3_do_write(s,SSL3_RT_HANDSHAKE)); } -static int ssl3_send_server_done(SSL *s) +int ssl3_send_server_done(SSL *s) { unsigned char *p; @@ -1075,7 +1131,7 @@ static int ssl3_send_server_done(SSL *s) return(ssl3_do_write(s,SSL3_RT_HANDSHAKE)); } -static int ssl3_send_server_key_exchange(SSL *s) +int ssl3_send_server_key_exchange(SSL *s) { #ifndef OPENSSL_NO_RSA unsigned char *q; @@ -1494,7 +1550,7 @@ err: return(-1); } -static int ssl3_send_certificate_request(SSL *s) +int ssl3_send_certificate_request(SSL *s) { unsigned char *p,*d; int i,j,nl,off,n; @@ -1574,6 +1630,7 @@ static int ssl3_send_certificate_request(SSL *s) s->init_num += 4; #endif + s->state = SSL3_ST_SW_CERT_REQ_B; } /* SSL3_ST_SW_CERT_REQ_B */ @@ -1584,18 +1641,20 @@ err: static const int KDF1_SHA1_len = 20; -static void *KDF1_SHA1(void *in, size_t inlen, void *out, size_t outlen) +static void *KDF1_SHA1(const void *in, size_t inlen, void *out, size_t *outlen) { #ifndef OPENSSL_NO_SHA - if (outlen != SHA_DIGEST_LENGTH) + if (*outlen < SHA_DIGEST_LENGTH) return NULL; + else + *outlen = SHA_DIGEST_LENGTH; return SHA1(in, inlen, out); #else return NULL; #endif } -static int ssl3_get_client_key_exchange(SSL *s) +int ssl3_get_client_key_exchange(SSL *s) { int i,al,ok; long n; @@ -1620,7 +1679,7 @@ static int ssl3_get_client_key_exchange(SSL *s) BN_CTX *bn_ctx = NULL; #endif - n=ssl3_get_message(s, + n=s->method->ssl_get_message(s, SSL3_ST_SR_KEY_EXCH_A, SSL3_ST_SR_KEY_EXCH_B, SSL3_MT_CLIENT_KEY_EXCHANGE, @@ -1846,8 +1905,8 @@ static int ssl3_get_client_key_exchange(SSL *s) goto err; } - if (n != enc_ticket.length + authenticator.length + - enc_pms.length + 6) + if (n != (long)(enc_ticket.length + authenticator.length + + enc_pms.length + 6)) { SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE, SSL_R_DATA_LENGTH_TOO_LONG); @@ -2132,7 +2191,7 @@ err: return(-1); } -static int ssl3_get_cert_verify(SSL *s) +int ssl3_get_cert_verify(SSL *s) { EVP_PKEY *pkey=NULL; unsigned char *p; @@ -2141,7 +2200,7 @@ static int ssl3_get_cert_verify(SSL *s) int type=0,i,j; X509 *peer; - n=ssl3_get_message(s, + n=s->method->ssl_get_message(s, SSL3_ST_SR_CERT_VRFY_A, SSL3_ST_SR_CERT_VRFY_B, -1, @@ -2287,15 +2346,16 @@ end: return(ret); } -static int ssl3_get_client_certificate(SSL *s) +int ssl3_get_client_certificate(SSL *s) { int i,ok,al,ret= -1; X509 *x=NULL; unsigned long l,nc,llen,n; - unsigned char *p,*d,*q; + const unsigned char *p,*q; + unsigned char *d; STACK_OF(X509) *sk=NULL; - n=ssl3_get_message(s, + n=s->method->ssl_get_message(s, SSL3_ST_SR_CERT_A, SSL3_ST_SR_CERT_B, -1, @@ -2330,7 +2390,7 @@ static int ssl3_get_client_certificate(SSL *s) SSLerr(SSL_F_SSL3_GET_CLIENT_CERTIFICATE,SSL_R_WRONG_MESSAGE_TYPE); goto f_err; } - d=p=(unsigned char *)s->init_msg; + p=d=(unsigned char *)s->init_msg; if ((sk=sk_X509_new_null()) == NULL) {