summaryrefslogtreecommitdiffstats
path: root/ssl/s3_srvr.c
diff options
context:
space:
mode:
authorDr. Stephen Henson <steve@openssl.org>2013-04-06 15:50:12 +0100
committerDr. Stephen Henson <steve@openssl.org>2013-09-18 13:46:02 +0100
commit65a87d3cc3c21bb54e6e813ee21ad049fea1310a (patch)
tree945c6b15877c4263588e251455ad534c04bd7a00 /ssl/s3_srvr.c
parentb60b9e7afe649a564db13dbf10ca571e973844c1 (diff)
Dual DTLS version methods.
Add new methods DTLS_*_method() which support both DTLS 1.0 and DTLS 1.2 and pick the highest version the peer supports during negotiation. As with SSL/TLS options can change this behaviour specifically SSL_OP_NO_DTLSv1 and SSL_OP_NO_DTLSv1_2. (cherry picked from commit c6913eeb762edffddecaaba5c84909d7a7962927) Conflicts: CHANGES
Diffstat (limited to 'ssl/s3_srvr.c')
-rw-r--r--ssl/s3_srvr.c29
1 files changed, 27 insertions, 2 deletions
diff --git a/ssl/s3_srvr.c b/ssl/s3_srvr.c
index 27e745c225..d9a21811e4 100644
--- a/ssl/s3_srvr.c
+++ b/ssl/s3_srvr.c
@@ -968,8 +968,9 @@ int ssl3_get_client_hello(SSL *s)
s->client_version=(((int)p[0])<<8)|(int)p[1];
p+=2;
- if ((s->version == DTLS1_VERSION && s->client_version > s->version) ||
- (s->version != DTLS1_VERSION && s->client_version < s->version))
+ if ((SSL_IS_DTLS(s) && s->client_version > s->version
+ && s->method->version != DTLS_ANY_VERSION) ||
+ (!SSL_IS_DTLS(s) && s->client_version < s->version))
{
SSLerr(SSL_F_SSL3_GET_CLIENT_HELLO, SSL_R_WRONG_VERSION_NUMBER);
if ((s->client_version>>8) == SSL3_VERSION_MAJOR)
@@ -1087,6 +1088,30 @@ int ssl3_get_client_hello(SSL *s)
}
p += cookie_len;
+ if (s->method->version == DTLS_ANY_VERSION)
+ {
+ /* Select version to use */
+ if (s->client_version <= DTLS1_2_VERSION &&
+ !(s->options & SSL_OP_NO_DTLSv1_2))
+ {
+ s->version = DTLS1_2_VERSION;
+ s->method = DTLSv1_2_server_method();
+ }
+ else if (s->client_version <= DTLS1_VERSION &&
+ !(s->options & SSL_OP_NO_DTLSv1))
+ {
+ s->version = DTLS1_VERSION;
+ s->method = DTLSv1_server_method();
+ }
+ else
+ {
+ SSLerr(SSL_F_SSL3_GET_CLIENT_HELLO, SSL_R_WRONG_VERSION_NUMBER);
+ s->version = s->client_version;
+ al = SSL_AD_PROTOCOL_VERSION;
+ goto f_err;
+ }
+ s->session->ssl_version = s->version;
+ }
}
n2s(p,i);