SSL/TLS record tracing code (backport from HEAD).
[oweals/openssl.git] / ssl / s3_srvr.c
index fd0f41b5718b34f2b98b811a4c0137b43788ee55..ed7d34f724c2efe509b86f4d4f10c03e1f90c087 100644 (file)
@@ -1359,6 +1359,14 @@ int ssl3_get_client_hello(SSL *s)
                        goto f_err;
                        }
                ciphers=NULL;
+               /* Let cert callback update server certificates if required */
+               if (s->cert->cert_cb
+                       && s->cert->cert_cb(s, s->cert->cert_cb_arg) <= 0)
+                       {
+                       al=SSL_AD_INTERNAL_ERROR;
+                       SSLerr(SSL_F_SSL3_GET_CLIENT_HELLO,SSL_R_CERT_CB_ERROR);
+                       goto f_err;
+                       }
                c=ssl3_choose_cipher(s,s->session->ciphers,
                                     SSL_get_ciphers(s));
 
@@ -1418,6 +1426,16 @@ int ssl3_get_client_hello(SSL *s)
         * s->tmp.new_cipher    - the new cipher to use.
         */
 
+       /* Handles TLS extensions that we couldn't check earlier */
+       if (s->version >= SSL3_VERSION)
+               {
+               if (ssl_check_clienthello_tlsext_late(s) <= 0)
+                       {
+                       SSLerr(SSL_F_SSL3_GET_CLIENT_HELLO, SSL_R_CLIENTHELLO_TLSEXT);
+                       goto err;
+                       }
+               }
+
        if (ret < 0) ret=1;
        if (0)
                {
@@ -1689,8 +1707,8 @@ int ssl3_send_server_key_exchange(SSL *s)
                        ecdhp=cert->ecdh_tmp;
                        if (s->cert->ecdh_tmp_auto)
                                {
-                               /* Get NID of first shared curve */
-                               int nid = tls1_shared_curve(s, 0);
+                               /* Get NID of appropriate shared curve */
+                               int nid = tls1_shared_curve(s, -2);
                                if (nid != NID_undef)
                                        ecdhp = EC_KEY_new_by_curve_name(nid);
                                }
@@ -2059,9 +2077,11 @@ int ssl3_send_certificate_request(SSL *s)
 
                if (TLS1_get_version(s) >= TLS1_2_VERSION)
                        {
-                       nl = tls12_get_req_sig_algs(s, p + 2);
+                       const unsigned char *psigs;
+                       nl = tls12_get_psigalgs(s, &psigs);
                        s2n(nl, p);
-                       p += nl + 2;
+                       memcpy(p, psigs, nl);
+                       p += nl;
                        n += nl + 2;
                        }
 
@@ -3034,26 +3054,15 @@ int ssl3_get_cert_verify(SSL *s)
                {       
                if (TLS1_get_version(s) >= TLS1_2_VERSION)
                        {
-                       int sigalg = tls12_get_sigid(pkey);
-                       /* Should never happen */
-                       if (sigalg == -1)
-                               {
-                               SSLerr(SSL_F_SSL3_GET_CERT_VERIFY,ERR_R_INTERNAL_ERROR);
-                               al=SSL_AD_INTERNAL_ERROR;
-                               goto f_err;
-                               }
-                       /* Check key type is consistent with signature */
-                       if (sigalg != (int)p[1])
+                       int rv = tls12_check_peer_sigalg(&md, s, p, pkey);
+                       if (rv == -1)
                                {
-                               SSLerr(SSL_F_SSL3_GET_CERT_VERIFY,SSL_R_WRONG_SIGNATURE_TYPE);
-                               al=SSL_AD_DECODE_ERROR;
+                               al = SSL_AD_INTERNAL_ERROR;
                                goto f_err;
                                }
-                       md = tls12_get_hash(p[0]);
-                       if (md == NULL)
+                       else if (rv == 0)
                                {
-                               SSLerr(SSL_F_SSL3_GET_CERT_VERIFY,SSL_R_UNKNOWN_DIGEST);
-                               al=SSL_AD_DECODE_ERROR;
+                               al = SSL_AD_DECODE_ERROR;
                                goto f_err;
                                }
 #ifdef SSL_DEBUG
@@ -3332,7 +3341,7 @@ int ssl3_get_client_certificate(SSL *s)
                if (i <= 0)
                        {
                        al=ssl_verify_alarm_type(s->verify_result);
-                       SSLerr(SSL_F_SSL3_GET_CLIENT_CERTIFICATE,SSL_R_NO_CERTIFICATE_RETURNED);
+                       SSLerr(SSL_F_SSL3_GET_CLIENT_CERTIFICATE,SSL_R_CERTIFICATE_VERIFY_FAILED);
                        goto f_err;
                        }
                }
@@ -3669,6 +3678,8 @@ int tls1_send_server_supplemental_data(SSL *s)
 
                type = *(authz++);
                n2s(authz, len);
+               /* n2s increments authz by 2*/
+               i += 2;
 
                if (memchr(s->s3->tlsext_authz_client_types,
                           type,
@@ -3712,6 +3723,8 @@ int tls1_send_server_supplemental_data(SSL *s)
 
                type = *(authz++);
                n2s(authz, len);
+               /* n2s increments authz by 2 */
+               i += 2;
 
                if (memchr(s->s3->tlsext_authz_client_types,
                           type,