aboutsummaryrefslogtreecommitdiffstats
path: root/lib/ssl/src/ssl_handshake.erl
diff options
context:
space:
mode:
authorAndreas Schultz <[email protected]>2012-04-08 02:39:18 +0200
committerIngela Anderton Andin <[email protected]>2012-08-22 14:00:44 +0200
commitd848984efd05314abf2de8da6ddd4ee651f0da35 (patch)
treec56ce48d75c8c8ba74c99af46a59182575202d88 /lib/ssl/src/ssl_handshake.erl
parent7c9639c785bb6b3047788b6b27ddbafb8f5b0b08 (diff)
downloadotp-d848984efd05314abf2de8da6ddd4ee651f0da35.tar.gz
otp-d848984efd05314abf2de8da6ddd4ee651f0da35.tar.bz2
otp-d848984efd05314abf2de8da6ddd4ee651f0da35.zip
ssl: make PRF function selectable
TLS 1.2 allows to negotiate the used PRF, additional the default PRF uses a different hash. This change make the PRF selectable and hardwires the PRF for TLS < 1.2
Diffstat (limited to 'lib/ssl/src/ssl_handshake.erl')
-rw-r--r--lib/ssl/src/ssl_handshake.erl51
1 files changed, 27 insertions, 24 deletions
diff --git a/lib/ssl/src/ssl_handshake.erl b/lib/ssl/src/ssl_handshake.erl
index c7d5ca6903..1759c920cc 100644
--- a/lib/ssl/src/ssl_handshake.erl
+++ b/lib/ssl/src/ssl_handshake.erl
@@ -34,7 +34,7 @@
hello_request/0, certify/7, certificate/4,
client_certificate_verify/5, certificate_verify/5,
certificate_request/3, key_exchange/3, server_key_exchange_hash/2,
- finished/4, verify_connection/5, get_tls_handshake/3,
+ finished/5, verify_connection/6, get_tls_handshake/3,
decode_client_key/3, server_hello_done/0,
encode_handshake/2, init_handshake_history/0, update_handshake_history/2,
decrypt_premaster_secret/2, prf/5]).
@@ -401,10 +401,11 @@ master_secret(Version, PremasterSecret, ConnectionStates, Role) ->
ConnectionState =
ssl_record:pending_connection_state(ConnectionStates, read),
SecParams = ConnectionState#connection_state.security_parameters,
- #security_parameters{client_random = ClientRandom,
+ #security_parameters{prf_algorithm = PrfAlgo,
+ client_random = ClientRandom,
server_random = ServerRandom} = SecParams,
try master_secret(Version,
- calc_master_secret(Version,PremasterSecret,
+ calc_master_secret(Version,PrfAlgo,PremasterSecret,
ClientRandom, ServerRandom),
SecParams, ConnectionStates, Role)
catch
@@ -416,26 +417,26 @@ master_secret(Version, PremasterSecret, ConnectionStates, Role) ->
end.
%%--------------------------------------------------------------------
--spec finished(tls_version(), client | server, binary(), tls_handshake_history()) ->
+-spec finished(tls_version(), client | server, integer(), binary(), tls_handshake_history()) ->
#finished{}.
%%
%% Description: Creates a handshake finished message
%%-------------------------------------------------------------------
-finished(Version, Role, MasterSecret, {Handshake, _}) -> % use the current hashes
+finished(Version, Role, PrfAlgo, MasterSecret, {Handshake, _}) -> % use the current handshake
#finished{verify_data =
- calc_finished(Version, Role, MasterSecret, Handshake)}.
+ calc_finished(Version, Role, PrfAlgo, MasterSecret, Handshake)}.
%%--------------------------------------------------------------------
--spec verify_connection(tls_version(), #finished{}, client | server, binary(),
+-spec verify_connection(tls_version(), #finished{}, client | server, integer(), binary(),
tls_handshake_history()) -> verified | #alert{}.
%%
%% Description: Checks the ssl handshake finished message to verify
%% the connection.
%%-------------------------------------------------------------------
verify_connection(Version, #finished{verify_data = Data},
- Role, MasterSecret, {_, Handshake}) ->
+ Role, PrfAlgo, MasterSecret, {_, Handshake}) ->
%% use the previous hashes
- case calc_finished(Version, Role, MasterSecret, Handshake) of
+ case calc_finished(Version, Role, PrfAlgo, MasterSecret, Handshake) of
Data ->
verified;
_ ->
@@ -782,13 +783,14 @@ master_secret(Version, MasterSecret, #security_parameters{
client_random = ClientRandom,
server_random = ServerRandom,
hash_size = HashSize,
+ prf_algorithm = PrfAlgo,
key_material_length = KML,
expanded_key_material_length = EKML,
iv_size = IVS},
ConnectionStates, Role) ->
{ClientWriteMacSecret, ServerWriteMacSecret, ClientWriteKey,
ServerWriteKey, ClientIV, ServerIV} =
- setup_keys(Version, MasterSecret, ServerRandom,
+ setup_keys(Version, PrfAlgo, MasterSecret, ServerRandom,
ClientRandom, HashSize, KML, EKML, IVS),
ConnStates1 = ssl_record:set_master_secret(MasterSecret, ConnectionStates),
@@ -1117,34 +1119,35 @@ digitally_signed(Hash, #'RSAPrivateKey'{} = Key) ->
digitally_signed(Hash, #'DSAPrivateKey'{} = Key) ->
public_key:sign(Hash, none, Key).
-calc_master_secret({3,0}, PremasterSecret, ClientRandom, ServerRandom) ->
+calc_master_secret({3,0}, _PrfAlgo, PremasterSecret, ClientRandom, ServerRandom) ->
ssl_ssl3:master_secret(PremasterSecret, ClientRandom, ServerRandom);
-calc_master_secret({3,N},PremasterSecret, ClientRandom, ServerRandom)
+calc_master_secret({3,N}, _PrfAlgo, PremasterSecret, ClientRandom, ServerRandom)
when N == 1; N == 2 ->
- ssl_tls1:master_secret(PremasterSecret, ClientRandom, ServerRandom).
+ ssl_tls1:master_secret(?MD5SHA, PremasterSecret, ClientRandom, ServerRandom).
-setup_keys({3,0}, MasterSecret,
+setup_keys({3,0}, _PrfAlgo, MasterSecret,
ServerRandom, ClientRandom, HashSize, KML, EKML, IVS) ->
ssl_ssl3:setup_keys(MasterSecret, ServerRandom,
ClientRandom, HashSize, KML, EKML, IVS);
-setup_keys({3,1}, MasterSecret,
- ServerRandom, ClientRandom, HashSize, KML, _EKML, IVS) ->
- ssl_tls1:setup_keys(MasterSecret, ServerRandom, ClientRandom, HashSize,
+setup_keys({3,N}, _PrfAlgo, MasterSecret,
+ ServerRandom, ClientRandom, HashSize, KML, _EKML, IVS)
+ when N == 1; N == 2 ->
+ ssl_tls1:setup_keys(N, ?MD5SHA, MasterSecret, ServerRandom, ClientRandom, HashSize,
KML, IVS).
-calc_finished({3, 0}, Role, MasterSecret, Handshake) ->
+calc_finished({3, 0}, Role, _PrfAlgo, MasterSecret, Handshake) ->
ssl_ssl3:finished(Role, MasterSecret, lists:reverse(Handshake));
-calc_finished({3, N}, Role, MasterSecret, Handshake)
+calc_finished({3, N}, Role, _PrfAlgo, MasterSecret, Handshake)
when N == 1; N == 2 ->
- ssl_tls1:finished(Role, MasterSecret, lists:reverse(Handshake)).
+ ssl_tls1:finished(Role, N, ?MD5SHA, MasterSecret, lists:reverse(Handshake)).
-calc_certificate_verify({3, 0}, MasterSecret, Algorithm, Handshake) ->
- ssl_ssl3:certificate_verify(Algorithm, MasterSecret, lists:reverse(Handshake));
-calc_certificate_verify({3, N}, _, Algorithm, Handshake)
+calc_certificate_verify({3, 0}, HashAlgo, MasterSecret, Handshake) ->
+ ssl_ssl3:certificate_verify(HashAlgo, MasterSecret, lists:reverse(Handshake));
+calc_certificate_verify({3, N}, HashAlgo, _MasterSecret, Handshake)
when N == 1; N == 2 ->
- ssl_tls1:certificate_verify(Algorithm, lists:reverse(Handshake)).
+ ssl_tls1:certificate_verify(HashAlgo, N, lists:reverse(Handshake)).
key_exchange_alg(rsa) ->
?KEY_EXCHANGE_RSA;