diff options
author | Dr. Stephen Henson <steve@openssl.org> | 2015-01-23 02:49:16 +0000 |
---|---|---|
committer | Dr. Stephen Henson <steve@openssl.org> | 2015-02-03 14:50:07 +0000 |
commit | 0cfb0e75b9dbf1a605c47e1b79c76d43a1f8344d (patch) | |
tree | cc9908361d4c930687b29e0457d46ea73a48e7de /ssl/t1_enc.c | |
parent | ddc06b35565d9f2888e8d946ee7ae292bc902afd (diff) |
Add extms support to master key generation.
Update master secret calculation to support extended master secret.
TLS 1.2 client authentication adds a complication because we need to
cache the handshake messages. This is simpllified however because
the point at which the handshake hashes are calculated for extended
master secret is identical to that required for TLS 1.2 client
authentication (immediately after client key exchange which is also
immediately before certificate verify).
Reviewed-by: Tim Hudson <tjh@openssl.org>
Reviewed-by: Matt Caswell <matt@openssl.org>
Diffstat (limited to 'ssl/t1_enc.c')
-rw-r--r-- | ssl/t1_enc.c | 45 |
1 files changed, 38 insertions, 7 deletions
diff --git a/ssl/t1_enc.c b/ssl/t1_enc.c index 666864e85c..ff6273f150 100644 --- a/ssl/t1_enc.c +++ b/ssl/t1_enc.c @@ -1070,13 +1070,41 @@ int tls1_generate_master_secret(SSL *s, unsigned char *out, unsigned char *p, len); #endif /* KSSL_DEBUG */ - - tls1_PRF(ssl_get_algorithm2(s), - TLS_MD_MASTER_SECRET_CONST, TLS_MD_MASTER_SECRET_CONST_SIZE, - s->s3->client_random, SSL3_RANDOM_SIZE, - co, col, - s->s3->server_random, SSL3_RANDOM_SIZE, - so, sol, p, len, s->session->master_key, buff, sizeof buff); + if (s->session->flags & SSL_SESS_FLAG_EXTMS) { + unsigned char hash[EVP_MAX_MD_SIZE * 2]; + int hashlen; + /* If we don't have any digests cache records */ + if (s->s3->handshake_buffer) { + /* + * keep record buffer: this wont affect client auth because we're + * freezing the buffer at the same point (after client key + * exchange and before certificate verify) + */ + s->s3->flags |= TLS1_FLAGS_KEEP_HANDSHAKE; + ssl3_digest_cached_records(s); + } + hashlen = ssl_handshake_hash(s, hash, sizeof(hash)); +#ifdef SSL_DEBUG + fprintf(stderr, "Handshake hashes:\n"); + BIO_dump_fp(stderr, (char *)hash, hashlen); +#endif + tls1_PRF(ssl_get_algorithm2(s), + TLS_MD_EXTENDED_MASTER_SECRET_CONST, + TLS_MD_EXTENDED_MASTER_SECRET_CONST_SIZE, + hash, hashlen, + co, col, + NULL, 0, + so, sol, p, len, s->session->master_key, buff, sizeof buff); + OPENSSL_cleanse(hash, hashlen); + } else { + tls1_PRF(ssl_get_algorithm2(s), + TLS_MD_MASTER_SECRET_CONST, + TLS_MD_MASTER_SECRET_CONST_SIZE, + s->s3->client_random, SSL3_RANDOM_SIZE, + co, col, + s->s3->server_random, SSL3_RANDOM_SIZE, + so, sol, p, len, s->session->master_key, buff, sizeof buff); + } #ifdef SSL_DEBUG fprintf(stderr, "Premaster Secret:\n"); BIO_dump_fp(stderr, (char *)p, len); @@ -1175,6 +1203,9 @@ int tls1_export_keying_material(SSL *s, unsigned char *out, size_t olen, if (memcmp(val, TLS_MD_MASTER_SECRET_CONST, TLS_MD_MASTER_SECRET_CONST_SIZE) == 0) goto err1; + if (memcmp(val, TLS_MD_EXTENDED_MASTER_SECRET_CONST, + TLS_MD_EXTENDED_MASTER_SECRET_CONST_SIZE) == 0) + goto err1; if (memcmp(val, TLS_MD_KEY_EXPANSION_CONST, TLS_MD_KEY_EXPANSION_CONST_SIZE) == 0) goto err1; |