diff options
author | Mark J. Cox <mark@openssl.org> | 1999-02-16 09:22:21 +0000 |
---|---|---|
committer | Mark J. Cox <mark@openssl.org> | 1999-02-16 09:22:21 +0000 |
commit | 413c4f45ed0508d2242638696b7665f499d68265 (patch) | |
tree | 5a5e667f7fc9cb548ab3b24dd02fff78e1b8f282 /ssl | |
parent | a8236c8c322101c273d14c62282f264555e147c4 (diff) |
Updates to the new SSL compression code
[Eric A. Young, (from changes to C2Net SSLeay, integrated by Mark Cox)]
Fix so that the version number in the master secret, when passed
via RSA, checks that if TLS was proposed, but we roll back to SSLv3
(because the server will not accept higher), that the version number
is 0x03,0x01, not 0x03,0x00
[Eric A. Young, (from changes to C2Net SSLeay, integrated by Mark Cox)]
Submitted by:
Reviewed by:
PR:
Diffstat (limited to 'ssl')
-rw-r--r-- | ssl/s23_clnt.c | 12 | ||||
-rw-r--r-- | ssl/s23_pkt.c | 2 | ||||
-rw-r--r-- | ssl/s23_srvr.c | 9 | ||||
-rw-r--r-- | ssl/s2_clnt.c | 16 | ||||
-rw-r--r-- | ssl/s2_enc.c | 2 | ||||
-rw-r--r-- | ssl/s2_srvr.c | 11 | ||||
-rw-r--r-- | ssl/s3_clnt.c | 73 | ||||
-rw-r--r-- | ssl/s3_enc.c | 21 | ||||
-rw-r--r-- | ssl/s3_lib.c | 25 | ||||
-rw-r--r-- | ssl/s3_pkt.c | 4 | ||||
-rw-r--r-- | ssl/s3_srvr.c | 101 | ||||
-rw-r--r-- | ssl/ssl.err | 257 | ||||
-rw-r--r-- | ssl/ssl.h | 503 | ||||
-rw-r--r-- | ssl/ssl3.h | 3 | ||||
-rw-r--r-- | ssl/ssl_algs.c | 3 | ||||
-rw-r--r-- | ssl/ssl_ciph.c | 90 | ||||
-rw-r--r-- | ssl/ssl_err.c | 5 | ||||
-rw-r--r-- | ssl/ssl_lib.c | 210 | ||||
-rw-r--r-- | ssl/ssl_locl.h | 17 | ||||
-rw-r--r-- | ssl/ssl_rsa.c | 4 | ||||
-rw-r--r-- | ssl/ssl_sess.c | 48 | ||||
-rw-r--r-- | ssl/ssl_txt.c | 17 | ||||
-rw-r--r-- | ssl/ssltest.c | 2 | ||||
-rw-r--r-- | ssl/t1_enc.c | 21 |
24 files changed, 955 insertions, 501 deletions
diff --git a/ssl/s23_clnt.c b/ssl/s23_clnt.c index 1b4c06838b..c0948fd2da 100644 --- a/ssl/s23_clnt.c +++ b/ssl/s23_clnt.c @@ -136,6 +136,13 @@ SSL *s; case SSL_ST_BEFORE|SSL_ST_CONNECT: case SSL_ST_OK|SSL_ST_CONNECT: + if (s->session != NULL) + { + SSLerr(SSL_F_SSL23_CONNECT,SSL_R_SSL23_DOING_SESSION_ID_REUSE); + ret= -1; + goto end; + } + s->server=0; if (cb != NULL) cb(s,SSL_CB_HANDSHAKE_START,1); /* s->version=TLS1_VERSION; */ @@ -161,7 +168,7 @@ SSL *s; ssl3_init_finished_mac(s); s->state=SSL23_ST_CW_CLNT_HELLO_A; - s->ctx->sess_connect++; + s->ctx->stats.sess_connect++; s->init_num=0; break; @@ -238,16 +245,19 @@ SSL *s; { *(d++)=TLS1_VERSION_MAJOR; *(d++)=TLS1_VERSION_MINOR; + s->client_version=TLS1_VERSION; } else if (!(s->options & SSL_OP_NO_SSLv3)) { *(d++)=SSL3_VERSION_MAJOR; *(d++)=SSL3_VERSION_MINOR; + s->client_version=SSL3_VERSION; } else if (!(s->options & SSL_OP_NO_SSLv2)) { *(d++)=SSL2_VERSION_MAJOR; *(d++)=SSL2_VERSION_MINOR; + s->client_version=SSL2_VERSION; } else { diff --git a/ssl/s23_pkt.c b/ssl/s23_pkt.c index c25c312772..99f909d50f 100644 --- a/ssl/s23_pkt.c +++ b/ssl/s23_pkt.c @@ -76,7 +76,7 @@ SSL *s; { s->rwstate=SSL_WRITING; i=BIO_write(s->wbio,&(buf[tot]),num); - if (i < 0) + if (i <= 0) { s->init_off=tot; s->init_num=num; diff --git a/ssl/s23_srvr.c b/ssl/s23_srvr.c index 6c8afeb857..d1f49e5ac3 100644 --- a/ssl/s23_srvr.c +++ b/ssl/s23_srvr.c @@ -134,6 +134,7 @@ SSL *s; case SSL_ST_BEFORE|SSL_ST_ACCEPT: case SSL_ST_OK|SSL_ST_ACCEPT: + s->server=1; if (cb != NULL) cb(s,SSL_CB_HANDSHAKE_START,1); /* s->version=SSL3_VERSION; */ @@ -157,7 +158,7 @@ SSL *s; ssl3_init_finished_mac(s); s->state=SSL23_ST_SR_CLNT_HELLO_A; - s->ctx->sess_accept++; + s->ctx->stats.sess_accept++; s->init_num=0; break; @@ -203,8 +204,10 @@ SSL *s; unsigned int csl,sil,cl; int n=0,j,tls1=0; int type=0,use_sslv2_strong=0; + int v[2]; /* read the initial header */ + v[0]=v[1]=0; if (s->state == SSL23_ST_SR_CLNT_HELLO_A) { if (!ssl3_setup_buffers(s)) goto err; @@ -221,12 +224,14 @@ SSL *s; /* SSLv2 header */ if ((p[3] == 0x00) && (p[4] == 0x02)) { + v[0]=p[3]; v[1]=p[4]; /* SSLv2 */ if (!(s->options & SSL_OP_NO_SSLv2)) type=1; } else if (p[3] == SSL3_VERSION_MAJOR) { + v[0]=p[3]; v[1]=p[4]; /* SSLv3/TLSv1 */ if (p[4] >= TLS1_VERSION_MINOR) { @@ -307,6 +312,7 @@ SSL *s; (p[1] == SSL3_VERSION_MAJOR) && (p[5] == SSL3_MT_CLIENT_HELLO)) { + v[0]=p[1]; v[1]=p[2]; /* true SSLv3 or tls1 */ if (p[2] >= TLS1_VERSION_MINOR) { @@ -486,6 +492,7 @@ next_bit: s->version=SSL3_VERSION; s->method=SSLv3_server_method(); } + s->client_version=(v[0]<<8)|v[1]; s->handshake_func=s->method->ssl_accept; } diff --git a/ssl/s2_clnt.c b/ssl/s2_clnt.c index 9c8037b48b..bbac33cf36 100644 --- a/ssl/s2_clnt.c +++ b/ssl/s2_clnt.c @@ -146,6 +146,7 @@ SSL *s; case SSL_ST_BEFORE|SSL_ST_CONNECT: case SSL_ST_OK|SSL_ST_CONNECT: + s->server=0; if (cb != NULL) cb(s,SSL_CB_HANDSHAKE_START,1); s->version=SSL2_VERSION; @@ -166,7 +167,7 @@ SSL *s; s->init_buf=buf; s->init_num=0; s->state=SSL2_ST_SEND_CLIENT_HELLO_A; - s->ctx->sess_connect++; + s->ctx->stats.sess_connect++; s->handshake_func=ssl2_connect; BREAK; @@ -249,8 +250,11 @@ SSL *s; break; case SSL_ST_OK: - BUF_MEM_free(s->init_buf); - s->init_buf=NULL; + if (s->init_buf != NULL) + { + BUF_MEM_free(s->init_buf); + s->init_buf=NULL; + } s->init_num=0; /* ERR_clear_error();*/ @@ -261,11 +265,11 @@ SSL *s; */ ssl_update_cache(s,SSL_SESS_CACHE_CLIENT); - if (s->hit) s->ctx->sess_hit++; + if (s->hit) s->ctx->stats.sess_hit++; ret=1; /* s->server=0; */ - s->ctx->sess_connect_good++; + s->ctx->stats.sess_connect_good++; if (cb != NULL) cb(s,SSL_CB_HANDSHAKE_DONE,1); @@ -538,7 +542,7 @@ SSL *s; if (s->state == SSL2_ST_SEND_CLIENT_MASTER_KEY_A) { - if (!ssl_cipher_get_evp(s->session->cipher,&c,&md)) + if (!ssl_cipher_get_evp(s->session,&c,&md,NULL)) { ssl2_return_error(s,SSL2_PE_NO_CIPHER); SSLerr(SSL_F_CLIENT_MASTER_KEY,SSL_R_PROBLEMS_MAPPING_CIPHER_FUNCTIONS); diff --git a/ssl/s2_enc.c b/ssl/s2_enc.c index b43056fa14..63ebf28748 100644 --- a/ssl/s2_enc.c +++ b/ssl/s2_enc.c @@ -69,7 +69,7 @@ int client; EVP_MD *md; int num; - if (!ssl_cipher_get_evp(s->session->cipher,&c,&md)) + if (!ssl_cipher_get_evp(s->session,&c,&md,NULL)) { ssl2_return_error(s,SSL2_PE_NO_CIPHER); SSLerr(SSL_F_SSL2_ENC_INIT,SSL_R_PROBLEMS_MAPPING_CIPHER_FUNCTIONS); diff --git a/ssl/s2_srvr.c b/ssl/s2_srvr.c index 8580ac6a8d..814e38f480 100644 --- a/ssl/s2_srvr.c +++ b/ssl/s2_srvr.c @@ -155,6 +155,7 @@ SSL *s; case SSL_ST_BEFORE|SSL_ST_ACCEPT: case SSL_ST_OK|SSL_ST_ACCEPT: + s->server=1; if (cb != NULL) cb(s,SSL_CB_HANDSHAKE_START,1); s->version=SSL2_VERSION; @@ -168,7 +169,7 @@ SSL *s; { ret= -1; goto end; } s->init_buf=buf; s->init_num=0; - s->ctx->sess_accept++; + s->ctx->stats.sess_accept++; s->handshake_func=ssl2_accept; s->state=SSL2_ST_GET_CLIENT_HELLO_A; BREAK; @@ -295,13 +296,14 @@ SSL *s; case SSL_ST_OK: BUF_MEM_free(s->init_buf); + ssl_free_wbio_buffer(s); s->init_buf=NULL; s->init_num=0; /* ERR_clear_error();*/ ssl_update_cache(s,SSL_SESS_CACHE_SERVER); - s->ctx->sess_accept_good++; + s->ctx->stats.sess_accept_good++; /* s->server=1; */ ret=1; @@ -336,9 +338,6 @@ static int get_client_master_key(s) SSL *s; { int export,i,n,keya,ek; -#if 0 - int error=0; -#endif unsigned char *p; SSL_CIPHER *cp; EVP_CIPHER *c; @@ -404,7 +403,7 @@ SSL *s; export=(s->session->cipher->algorithms & SSL_EXP)?1:0; - if (!ssl_cipher_get_evp(s->session->cipher,&c,&md)) + if (!ssl_cipher_get_evp(s->session,&c,&md,NULL)) { ssl2_return_error(s,SSL2_PE_NO_CIPHER); SSLerr(SSL_F_GET_CLIENT_MASTER_KEY,SSL_R_PROBLEMS_MAPPING_CIPHER_FUNCTIONS); diff --git a/ssl/s3_clnt.c b/ssl/s3_clnt.c index 363118835c..b2649ed998 100644 --- a/ssl/s3_clnt.c +++ b/ssl/s3_clnt.c @@ -134,7 +134,6 @@ SSL *s; long num1; void (*cb)()=NULL; int ret= -1; - BIO *under; int new_state,state,skip=0;; RAND_seed(&Time,sizeof(Time)); @@ -158,13 +157,14 @@ SSL *s; case SSL_ST_RENEGOTIATE: s->new_session=1; s->state=SSL_ST_CONNECT; - s->ctx->sess_connect_renegotiate++; + s->ctx->stats.sess_connect_renegotiate++; /* break */ case SSL_ST_BEFORE: case SSL_ST_CONNECT: case SSL_ST_BEFORE|SSL_ST_CONNECT: case SSL_ST_OK|SSL_ST_CONNECT: + s->server=0; if (cb != NULL) cb(s,SSL_CB_HANDSHAKE_START,1); if ((s->version & 0xff00 ) != 0x0300) @@ -197,7 +197,7 @@ SSL *s; ssl3_init_finished_mac(s); s->state=SSL3_ST_CW_CLNT_HELLO_A; - s->ctx->sess_connect++; + s->ctx->stats.sess_connect++; s->init_num=0; break; @@ -326,6 +326,11 @@ SSL *s; s->init_num=0; s->session->cipher=s->s3->tmp.new_cipher; + if (s->s3->tmp.new_compression == NULL) + s->session->compress_meth=0; + else + s->session->compress_meth= + s->s3->tmp.new_compression->id; if (!s->method->ssl3_enc->setup_key_block(s)) { ret= -1; @@ -401,33 +406,28 @@ SSL *s; /* clean a few things up */ ssl3_cleanup_key_block(s); - BUF_MEM_free(s->init_buf); - s->init_buf=NULL; - - if (!(s->s3->flags & SSL3_FLAGS_POP_BUFFER)) + if (s->init_buf != NULL) { - /* remove buffering */ - under=BIO_pop(s->wbio); - if (under != NULL) - s->wbio=under; - else - abort(); /* ok */ - - BIO_free(s->bbio); - s->bbio=NULL; + BUF_MEM_free(s->init_buf); + s->init_buf=NULL; } - /* else do it later */ + + /* If we are not 'joining' the last two packets, + * remove the buffering now */ + if (!(s->s3->flags & SSL3_FLAGS_POP_BUFFER)) + ssl_free_wbio_buffer(s); + /* else do it later in ssl3_write */ s->init_num=0; s->new_session=0; ssl_update_cache(s,SSL_SESS_CACHE_CLIENT); - if (s->hit) s->ctx->sess_hit++; + if (s->hit) s->ctx->stats.sess_hit++; ret=1; /* s->server=0; */ s->handshake_func=ssl3_connect; - s->ctx->sess_connect_good++; + s->ctx->stats.sess_connect_good++; if (cb != NULL) cb(s,SSL_CB_HANDSHAKE_DONE,1); @@ -473,8 +473,9 @@ SSL *s; { unsigned char *buf; unsigned char *p,*d; - int i; + int i,j; unsigned long Time,l; + SSL_COMP *comp; buf=(unsigned char *)s->init_buf->data; if (s->state == SSL3_ST_CW_CLNT_HELLO_A) @@ -498,6 +499,7 @@ SSL *s; *(p++)=s->version>>8; *(p++)=s->version&0xff; + s->client_version=s->version; /* Random stuff */ memcpy(p,s->s3->client_random,SSL3_RANDOM_SIZE); @@ -525,10 +527,18 @@ SSL *s; s2n(i,p); p+=i; - /* hardwire in the NULL compression algorithm. */ /* COMPRESSION */ - *(p++)=1; - *(p++)=0; + if (s->ctx->comp_methods == NULL) + j=0; + else + j=sk_num(s->ctx->comp_methods); + *(p++)=1+j; + for (i=0; i<j; i++) + { + comp=(SSL_COMP *)sk_value(s->ctx->comp_methods,i); + *(p++)=comp->id; + } + *(p++)=0; /* Add the NULL method */ l=(p-d); d=buf; @@ -556,6 +566,7 @@ SSL *s; int i,al,ok; unsigned int j; long n; + SSL_COMP *comp; n=ssl3_get_message(s, SSL3_ST_CR_SRVR_HELLO_A, @@ -649,12 +660,21 @@ SSL *s; /* lets get the compression algorithm */ /* COMPRESSION */ j= *(p++); - if (j != 0) + if (j == 0) + comp=NULL; + else + comp=ssl3_comp_find(s->ctx->comp_methods,j); + + if ((j != 0) && (comp == NULL)) { al=SSL_AD_ILLEGAL_PARAMETER; SSLerr(SSL_F_SSL3_GET_SERVER_HELLO,SSL_R_UNSUPPORTED_COMPRESSION_ALGORITHM); goto f_err; } + else + { + s->s3->tmp.new_compression=comp; + } if (p != (d+n)) { @@ -996,6 +1016,7 @@ SSL *s; /* else anonymous DH, so no certificate or pkey. */ s->session->cert->dh_tmp=dh; + dh=NULL; } else if ((alg & SSL_kDHr) || (alg & SSL_kDHd)) { @@ -1326,8 +1347,8 @@ SSL *s; rsa=pkey->pkey.rsa; } - tmp_buf[0]=s->version>>8; - tmp_buf[1]=s->version&0xff; + tmp_buf[0]=s->client_version>>8; + tmp_buf[1]=s->client_version&0xff; RAND_bytes(&(tmp_buf[2]),SSL_MAX_MASTER_KEY_LENGTH-2); s->session->master_key_length=SSL_MAX_MASTER_KEY_LENGTH; diff --git a/ssl/s3_enc.c b/ssl/s3_enc.c index c5c9a3be42..a655e12bec 100644 --- a/ssl/s3_enc.c +++ b/ssl/s3_enc.c @@ -144,7 +144,10 @@ int which; exp=(s->s3->tmp.new_cipher->algorithms & SSL_EXPORT)?1:0; c=s->s3->tmp.new_sym_enc; m=s->s3->tmp.new_hash; - comp=s->s3->tmp.new_compression; + if (s->s3->tmp.new_compression == NULL) + comp=NULL; + else + comp=s->s3->tmp.new_compression->method; key_block=s->s3->tmp.key_block; if (which & SSL3_CC_READ) @@ -169,8 +172,9 @@ int which; SSLerr(SSL_F_SSL3_CHANGE_CIPHER_STATE,SSL_R_COMPRESSION_LIBRARY_ERROR); goto err2; } - s->s3->rrec.comp=(unsigned char *) - Malloc(SSL3_RT_MAX_PLAIN_LENGTH); + if (s->s3->rrec.comp == NULL) + s->s3->rrec.comp=(unsigned char *) + Malloc(SSL3_RT_MAX_PLAIN_LENGTH); if (s->s3->rrec.comp == NULL) goto err; } @@ -280,11 +284,12 @@ SSL *s; EVP_CIPHER *c; EVP_MD *hash; int num,exp; + SSL_COMP *comp; if (s->s3->tmp.key_block_length != 0) return(1); - if (!ssl_cipher_get_evp(s->session->cipher,&c,&hash)) + if (!ssl_cipher_get_evp(s->session,&c,&hash,&comp)) { SSLerr(SSL_F_SSL3_SETUP_KEY_BLOCK,SSL_R_CIPHER_OR_HASH_UNAVAILABLE); return(0); @@ -292,11 +297,7 @@ SSL *s; s->s3->tmp.new_sym_enc=c; s->s3->tmp.new_hash=hash; -#ifdef ZLIB - s->s3->tmp.new_compression=COMP_zlib(); -#endif -/* s->s3->tmp.new_compression=COMP_rle(); */ -/* s->session->compress_meth= xxxxx */ + s->s3->tmp.new_compression=comp; exp=(s->session->cipher->algorithms & SSL_EXPORT)?1:0; @@ -454,7 +455,7 @@ unsigned char *p; unsigned char md_buf[EVP_MAX_MD_SIZE]; EVP_MD_CTX ctx; - memcpy(&ctx,in_ctx,sizeof(EVP_MD_CTX)); + EVP_MD_CTX_copy(&ctx,in_ctx); n=EVP_MD_CTX_size(&ctx); npad=(48/n)*n; diff --git a/ssl/s3_lib.c b/ssl/s3_lib.c index 495c1c334f..c64b760a44 100644 --- a/ssl/s3_lib.c +++ b/ssl/s3_lib.c @@ -486,6 +486,12 @@ SSL *s; if (s->s3->tmp.ca_names != NULL) sk_pop_free(s->s3->tmp.ca_names,X509_NAME_free); + if (s->s3->rrec.comp != NULL) + { + Free(s->s3->rrec.comp); + s->s3->rrec.comp=NULL; + } + rp=s->s3->rbuf.buf; wp=s->s3->wbuf.buf; @@ -493,11 +499,7 @@ SSL *s; if (rp != NULL) s->s3->rbuf.buf=rp; if (wp != NULL) s->s3->wbuf.buf=wp; - if (s->s3->rrec.comp != NULL) - { - Free(s->s3->rrec.comp); - s->s3->rrec.comp=NULL; - } + ssl_free_wbio_buffer(s); s->packet_length=0; s->s3->renegotiate=0; @@ -844,7 +846,6 @@ const char *buf; int len; { int ret,n; - BIO *under; #if 0 if (s->shutdown & SSL_SEND_SHUTDOWN) @@ -878,15 +879,12 @@ int len; if (n <= 0) return(n); s->rwstate=SSL_NOTHING; - /* We have flushed the buffer */ - under=BIO_pop(s->wbio); - s->wbio=under; - BIO_free(s->bbio); - s->bbio=NULL; + /* We have flushed the buffer, so remove it */ + ssl_free_wbio_buffer(s); + s->s3->flags&= ~SSL3_FLAGS_POP_BUFFER; + ret=s->s3->delay_buf_pop_ret; s->s3->delay_buf_pop_ret=0; - - s->s3->flags&= ~SSL3_FLAGS_POP_BUFFER; } else { @@ -987,4 +985,3 @@ need to go to SSL_ST_ACCEPT. return(ret); } - diff --git a/ssl/s3_pkt.c b/ssl/s3_pkt.c index b7edc8faf3..f5350bf1b7 100644 --- a/ssl/s3_pkt.c +++ b/ssl/s3_pkt.c @@ -872,7 +872,9 @@ start: if (((s->state&SSL_ST_MASK) == SSL_ST_OK) && !(s->s3->flags & SSL3_FLAGS_NO_RENEGOTIATE_CIPHERS)) { - s->state=SSL_ST_BEFORE; + s->state=SSL_ST_BEFORE|(s->server) + ?SSL_ST_ACCEPT + :SSL_ST_CONNECT; s->new_session=1; } n=s->handshake_func(s); diff --git a/ssl/s3_srvr.c b/ssl/s3_srvr.c index a827a58d49..a4c0744488 100644 --- a/ssl/s3_srvr.c +++ b/ssl/s3_srvr.c @@ -135,7 +135,6 @@ SSL *s; long num1; int ret= -1; CERT *ct; - BIO *under; int new_state,state,skip=0; RAND_seed(&Time,sizeof(Time)); @@ -178,6 +177,7 @@ SSL *s; case SSL_ST_BEFORE|SSL_ST_ACCEPT: case SSL_ST_OK|SSL_ST_ACCEPT: + s->server=1; if (cb != NULL) cb(s,SSL_CB_HANDSHAKE_START,1); if ((s->version>>8) != 3) @@ -217,11 +217,11 @@ SSL *s; { s->state=SSL3_ST_SR_CLNT_HELLO_A; ssl3_init_finished_mac(s); - s->ctx->sess_accept++; + s->ctx->stats.sess_accept++; } else { - s->ctx->sess_accept_renegotiate++; + s->ctx->stats.sess_accept_renegotiate++; s->state=SSL3_ST_SW_HELLO_REQ_A; } break; @@ -240,15 +240,6 @@ SSL *s; break; case SSL3_ST_SW_HELLO_REQ_C: - /* remove buffering on output */ - under=BIO_pop(s->wbio); - if (under != NULL) - s->wbio=under; - else - abort(); /* ok */ - BIO_free(s->bbio); - s->bbio=NULL; - s->state=SSL_ST_OK; ret=1; goto end; @@ -480,20 +471,14 @@ SSL *s; s->init_buf=NULL; /* remove buffering on output */ - under=BIO_pop(s->wbio); - if (under != NULL) - s->wbio=under; - else - abort(); /* ok */ - BIO_free(s->bbio); - s->bbio=NULL; + ssl_free_wbio_buffer(s); s->new_session=0; s->init_num=0; ssl_update_cache(s,SSL_SESS_CACHE_SERVER); - s->ctx->sess_accept_good++; + s->ctx->stats.sess_accept_good++; /* s->server=1; */ s->handshake_func=ssl3_accept; ret=1; @@ -567,8 +552,9 @@ SSL *s; int i,j,ok,al,ret= -1; long n; unsigned long id; - unsigned char *p,*d; + unsigned char *p,*d,*q; SSL_CIPHER *c; + SSL_COMP *comp=NULL; STACK *ciphers=NULL; /* We do this so that we will respond with our native type. @@ -595,6 +581,7 @@ SSL *s; /* The version number has already been checked in ssl3_get_message. * I a native TLSv1/SSLv3 method, the match must be correct except * perhaps for the first message */ +/* s->client_version=(((int)p[0])<<8)|(int)p[1]; */ p+=2; /* load the client random */ @@ -653,9 +640,16 @@ SSL *s; j=0; id=s->session->cipher->id; +#ifdef CIPHER_DEBUG + printf("client sent %d ciphers\n",sk_num(ciphers)); +#endif for (i=0; i<sk_num(ciphers); i++) { c=(SSL_CIPHER *)sk_value(ciphers,i); +#ifdef CIPHER_DEBUG + printf("client [%2d of %2d]:%s\n", + i,sk_num(ciphers),SSL_CIPHER_get_name(c)); +#endif if (c->id == id) { j=1; @@ -683,8 +677,11 @@ SSL *s; /* compression */ i= *(p++); + q=p; for (j=0; j<i; j++) + { if (p[j] == 0) break; + } p+=i; if (j >= i) @@ -695,6 +692,35 @@ SSL *s; goto f_err; } + /* Worst case, we will use the NULL compression, but if we have other + * options, we will now look for them. We have i-1 compression + * algorithms from the client, starting at q. */ + s->s3->tmp.new_compression=NULL; + if (s->ctx->comp_methods != NULL) + { /* See if we have a match */ + int m,nn,o,v,done=0; + + nn=sk_num(s->ctx->comp_methods); + for (m=0; m<nn; m++) + { + comp=(SSL_COMP *)sk_value(s->ctx->comp_methods,m); + v=comp->id; + for (o=0; o<i; o++) + { + if (v == q[o]) + { + done=1; + break; + } + } + if (done) break; + } + if (done) + s->s3->tmp.new_compression=comp; + else + comp=NULL; + } + /* TLS does not mind if there is extra stuff */ if (s->version == SSL3_VERSION) { @@ -708,13 +734,12 @@ SSL *s; } } - /* do nothing with compression */ - /* Given s->session->ciphers and ssl_get_ciphers_by_id(s), we must * pick a cipher */ if (!s->hit) { + s->session->compress_meth=(comp == NULL)?0:comp->id; if (s->session->ciphers != NULL) sk_free(s->session->ciphers); s->session->ciphers=ciphers; @@ -835,7 +860,10 @@ SSL *s; p+=i; /* put the compression method */ - *(p++)=0; + if (s->s3->tmp.new_compression == NULL) + *(p++)=0; + else + *(p++)=s->s3->tmp.new_compression->id; /* do the header */ l=(p-d); @@ -1266,13 +1294,26 @@ SSL *s; #if 1 /* If a bad decrypt, use a random master key */ if ((i != SSL_MAX_MASTER_KEY_LENGTH) || - ((p[0] != (s->version>>8)) || - (p[1] != (s->version & 0xff)))) + ((p[0] != (s->client_version>>8)) || + (p[1] != (s->client_version & 0xff)))) { - p[0]=(s->version>>8); - p[1]=(s->version & 0xff); - RAND_bytes(&(p[2]),SSL_MAX_MASTER_KEY_LENGTH-2); - i=SSL_MAX_MASTER_KEY_LENGTH; + int bad=1; + + if ((i == SSL_MAX_MASTER_KEY_LENGTH) && + (p[0] == (s->version>>8)) && + (p[1] == 0)) + { + if (s->options & SSL_OP_TLS_ROLLBACK_BUG) + bad=0; + } + if (bad) + { + p[0]=(s->version>>8); + p[1]=(s->version & 0xff); + RAND_bytes(&(p[2]),SSL_MAX_MASTER_KEY_LENGTH-2); + i=SSL_MAX_MASTER_KEY_LENGTH; + } + /* else, an SSLeay bug, ssl only server, tls client */ } #else if (i != SSL_MAX_MASTER_KEY_LENGTH) diff --git a/ssl/ssl.err b/ssl/ssl.err index 10ca9c5342..84256f905a 100644 --- a/ssl/ssl.err +++ b/ssl/ssl.err @@ -65,52 +65,55 @@ #define SSL_F_SSL_BYTES_TO_CIPHER_LIST 161 #define SSL_F_SSL_CERT_NEW 162 #define SSL_F_SSL_CHECK_PRIVATE_KEY 163 -#define SSL_F_SSL_CREATE_CIPHER_LIST 164 -#define SSL_F_SSL_CTX_CHECK_PRIVATE_KEY 165 -#define SSL_F_SSL_CTX_NEW 166 -#define SSL_F_SSL_CTX_SET_SSL_VERSION 167 -#define SSL_F_SSL_CTX_USE_CERTIFICATE 168 -#define SSL_F_SSL_CTX_USE_CERTIFICATE_ASN1 169 -#define SSL_F_SSL_CTX_USE_CERTIFICATE_FILE 170 -#define SSL_F_SSL_CTX_USE_PRIVATEKEY 171 -#define SSL_F_SSL_CTX_USE_PRIVATEKEY_ASN1 172 -#define SSL_F_SSL_CTX_USE_PRIVATEKEY_FILE 173 -#define SSL_F_SSL_CTX_USE_RSAPRIVATEKEY 174 -#define SSL_F_SSL_CTX_USE_RSAPRIVATEKEY_ASN1 175 -#define SSL_F_SSL_CTX_USE_RSAPRIVATEKEY_FILE 176 -#define SSL_F_SSL_DO_HANDSHAKE 177 -#define SSL_F_SSL_GET_NEW_SESSION 178 -#define SSL_F_SSL_GET_SERVER_SEND_CERT 179 -#define SSL_F_SSL_GET_SIGN_PKEY 180 -#define SSL_F_SSL_INIT_WBIO_BUFFER 181 -#define SSL_F_SSL_LOAD_CLIENT_CA_FILE 182 -#define SSL_F_SSL_NEW 183 -#define SSL_F_SSL_RSA_PRIVATE_DECRYPT 184 -#define SSL_F_SSL_RSA_PUBLIC_ENCRYPT 185 -#define SSL_F_SSL_SESSION_NEW 186 -#define SSL_F_SSL_SESSION_PRINT_FP 187 -#define SSL_F_SSL_SET_CERT 188 -#define SSL_F_SSL_SET_FD 189 -#define SSL_F_SSL_SET_PKEY 190 -#define SSL_F_SSL_SET_RFD 191 -#define SSL_F_SSL_SET_SESSION 192 -#define SSL_F_SSL_SET_WFD 193 -#define SSL_F_SSL_UNDEFINED_FUNCTION 194 -#define SSL_F_SSL_USE_CERTIFICATE 195 -#define SSL_F_SSL_USE_CERTIFICATE_ASN1 196 -#define SSL_F_SSL_USE_CERTIFICATE_FILE 197 -#define SSL_F_SSL_USE_PRIVATEKEY 198 -#define SSL_F_SSL_USE_PRIVATEKEY_ASN1 199 -#define SSL_F_SSL_USE_PRIVATEKEY_FILE 200 -#define SSL_F_SSL_USE_RSAPRIVATEKEY 201 -#define SSL_F_SSL_USE_RSAPRIVATEKEY_ASN1 202 -#define SSL_F_SSL_USE_RSAPRIVATEKEY_FILE 203 -#define SSL_F_SSL_VERIFY_CERT_CHAIN 204 -#define SSL_F_SSL_WRITE 205 -#define SSL_F_TLS1_CHANGE_CIPHER_STATE 206 -#define SSL_F_TLS1_ENC 207 -#define SSL_F_TLS1_SETUP_KEY_BLOCK 208 -#define SSL_F_WRITE_PENDING 209 +#define SSL_F_SSL_CLEAR 164 +#define SSL_F_SSL_COMP_ADD_COMPRESSION_METHOD 165 +#define SSL_F_SSL_CREATE_CIPHER_LIST 166 +#define SSL_F_SSL_CTX_ADD_COMPRESSION 167 +#define SSL_F_SSL_CTX_CHECK_PRIVATE_KEY 168 +#define SSL_F_SSL_CTX_NEW 169 +#define SSL_F_SSL_CTX_SET_SSL_VERSION 170 +#define SSL_F_SSL_CTX_USE_CERTIFICATE 171 +#define SSL_F_SSL_CTX_USE_CERTIFICATE_ASN1 172 +#define SSL_F_SSL_CTX_USE_CERTIFICATE_FILE 173 +#define SSL_F_SSL_CTX_USE_PRIVATEKEY 174 +#define SSL_F_SSL_CTX_USE_PRIVATEKEY_ASN1 175 +#define SSL_F_SSL_CTX_USE_PRIVATEKEY_FILE 176 +#define SSL_F_SSL_CTX_USE_RSAPRIVATEKEY 177 +#define SSL_F_SSL_CTX_USE_RSAPRIVATEKEY_ASN1 178 +#define SSL_F_SSL_CTX_USE_RSAPRIVATEKEY_FILE 179 +#define SSL_F_SSL_DO_HANDSHAKE 180 +#define SSL_F_SSL_GET_NEW_SESSION 181 +#define SSL_F_SSL_GET_SERVER_SEND_CERT 182 +#define SSL_F_SSL_GET_SIGN_PKEY 183 +#define SSL_F_SSL_INIT_WBIO_BUFFER 184 +#define SSL_F_SSL_LOAD_CLIENT_CA_FILE 185 +#define SSL_F_SSL_NEW 186 +#define SSL_F_SSL_RSA_PRIVATE_DECRYPT 187 +#define SSL_F_SSL_RSA_PUBLIC_ENCRYPT 188 +#define SSL_F_SSL_SESSION_NEW 189 +#define SSL_F_SSL_SESSION_PRINT_FP 190 +#define SSL_F_SSL_SET_CERT 191 +#define SSL_F_SSL_SET_FD 192 +#define SSL_F_SSL_SET_PKEY 193 +#define SSL_F_SSL_SET_RFD 194 +#define SSL_F_SSL_SET_SESSION 195 +#define SSL_F_SSL_SET_WFD 196 +#define SSL_F_SSL_UNDEFINED_FUNCTION 197 +#define SSL_F_SSL_USE_CERTIFICATE 198 +#define SSL_F_SSL_USE_CERTIFICATE_ASN1 199 +#define SSL_F_SSL_USE_CERTIFICATE_FILE 200 +#define SSL_F_SSL_USE_PRIVATEKEY 201 +#define SSL_F_SSL_USE_PRIVATEKEY_ASN1 202 +#define SSL_F_SSL_USE_PRIVATEKEY_FILE 203 +#define SSL_F_SSL_USE_RSAPRIVATEKEY 204 +#define SSL_F_SSL_USE_RSAPRIVATEKEY_ASN1 205 +#define SSL_F_SSL_USE_RSAPRIVATEKEY_FILE 206 +#define SSL_F_SSL_VERIFY_CERT_CHAIN 207 +#define SSL_F_SSL_WRITE 208 +#define SSL_F_TLS1_CHANGE_CIPHER_STATE 209 +#define SSL_F_TLS1_ENC 210 +#define SSL_F_TLS1_SETUP_KEY_BLOCK 211 +#define SSL_F_WRITE_PENDING 212 /* Reason codes. */ #define SSL_R_APP_DATA_IN_HANDSHAKE 100 @@ -201,39 +204,41 @@ #define SSL_R_NO_CIPHER_MATCH 185 #define SSL_R_NO_CLIENT_CERT_RECEIVED 186 #define SSL_R_NO_COMPRESSION_SPECIFIED 187 -#define SSL_R_NO_PRIVATEKEY 188 -#define SSL_R_NO_PRIVATE_KEY_ASSIGNED 189 -#define SSL_R_NO_PROTOCOLS_AVAILABLE 190 -#define SSL_R_NO_PUBLICKEY 191 -#define SSL_R_NO_SHARED_CIPHER 192 -#define SSL_R_NO_VERIFY_CALLBACK 193 -#define SSL_R_NULL_SSL_CTX 194 -#define SSL_R_NULL_SSL_METHOD_PASSED 195 -#define SSL_R_OLD_SESSION_CIPHER_NOT_RETURNED 196 -#define SSL_R_PACKET_LENGTH_TOO_LONG 197 -#define SSL_R_PEER_DID_NOT_RETURN_A_CERTIFICATE 198 -#define SSL_R_PEER_ERROR 199 -#define SSL_R_PEER_ERROR_CERTIFICATE 200 -#define SSL_R_PEER_ERROR_NO_CERTIFICATE 201 |