aboutsummaryrefslogtreecommitdiffstats
path: root/lib/ssl/src
diff options
context:
space:
mode:
authorIngela Andin <[email protected]>2018-07-06 14:47:41 +0200
committerGitHub <[email protected]>2018-07-06 14:47:41 +0200
commit0a6963fcc4a077a7b51669178271dc4ae4d7d3cb (patch)
treec4bf5844fc9067440e47985ec0f0791fc5d7bb77 /lib/ssl/src
parent023db8778e1ab091abe5743d880fbb9eba121b5e (diff)
parenta492841c3305ed680e364101a5fc8cd32602a737 (diff)
downloadotp-0a6963fcc4a077a7b51669178271dc4ae4d7d3cb.tar.gz
otp-0a6963fcc4a077a7b51669178271dc4ae4d7d3cb.tar.bz2
otp-0a6963fcc4a077a7b51669178271dc4ae4d7d3cb.zip
Merge pull request #1867 from IngelaAndin/ingela/ssl/no-ca-sign-restriction-TLS-1.2/ERL-381/OTP-15173
Ingela/ssl/no ca sign restriction tls 1.2/erl 381/otp 15173
Diffstat (limited to 'lib/ssl/src')
-rw-r--r--lib/ssl/src/ssl_cipher.erl2
-rw-r--r--lib/ssl/src/ssl_connection.erl28
-rw-r--r--lib/ssl/src/ssl_handshake.erl52
3 files changed, 27 insertions, 55 deletions
diff --git a/lib/ssl/src/ssl_cipher.erl b/lib/ssl/src/ssl_cipher.erl
index 754fc46404..50dadd0903 100644
--- a/lib/ssl/src/ssl_cipher.erl
+++ b/lib/ssl/src/ssl_cipher.erl
@@ -2709,6 +2709,8 @@ filter_suites_pubkey(ec, Ciphers, _, OtpCert) ->
ec_ecdhe_suites(Ciphers)),
filter_keyuse_suites(keyAgreement, Uses, CiphersSuites, ec_ecdh_suites(Ciphers)).
+filter_suites_signature(rsa, Ciphers, {3, N}) when N >= 3 ->
+ Ciphers;
filter_suites_signature(rsa, Ciphers, Version) ->
(Ciphers -- ecdsa_signed_suites(Ciphers, Version)) -- dsa_signed_suites(Ciphers, Version);
filter_suites_signature(dsa, Ciphers, Version) ->
diff --git a/lib/ssl/src/ssl_connection.erl b/lib/ssl/src/ssl_connection.erl
index c5f75894cd..d88704676f 100644
--- a/lib/ssl/src/ssl_connection.erl
+++ b/lib/ssl/src/ssl_connection.erl
@@ -791,6 +791,7 @@ certify(internal, #server_key_exchange{exchange_keys = Keys},
#state{role = client, negotiated_version = Version,
key_algorithm = Alg,
public_key_info = PubKeyInfo,
+ session = Session,
connection_states = ConnectionStates} = State, Connection)
when Alg == dhe_dss; Alg == dhe_rsa;
Alg == ecdhe_rsa; Alg == ecdhe_ecdsa;
@@ -812,7 +813,8 @@ certify(internal, #server_key_exchange{exchange_keys = Keys},
ConnectionStates, ssl:tls_version(Version), PubKeyInfo) of
true ->
calculate_secret(Params#server_key_params.params,
- State#state{hashsign_algorithm = HashSign},
+ State#state{hashsign_algorithm = HashSign,
+ session = session_handle_params(Params#server_key_params.params, Session)},
Connection);
false ->
handle_own_alert(?ALERT_REC(?FATAL, ?DECRYPT_ERROR),
@@ -1472,7 +1474,7 @@ connection_info(#state{sni_hostname = SNIHostname,
RecordCB = record_cb(Connection),
CipherSuiteDef = #{key_exchange := KexAlg} = ssl_cipher:suite_definition(CipherSuite),
IsNamedCurveSuite = lists:member(KexAlg,
- [ecdh_ecdsa, ecdhe_ecdsa, ecdh_rsa, ecdh_anon]),
+ [ecdh_ecdsa, ecdhe_ecdsa, ecdh_rsa, ecdhe_rsa, ecdh_anon]),
CurveInfo = case ECCCurve of
{namedCurve, Curve} when IsNamedCurveSuite ->
[{ecc, {named_curve, pubkey_cert_records:namedCurves(Curve)}}];
@@ -1576,11 +1578,9 @@ handle_peer_cert_key(client, _,
KeyAlg, #state{session = Session} = State) when KeyAlg == ecdh_rsa;
KeyAlg == ecdh_ecdsa ->
ECDHKey = public_key:generate_key(PublicKeyParams),
- {namedCurve, Oid} = PublicKeyParams,
- Curve = pubkey_cert_records:namedCurves(Oid), %% Need API function
PremasterSecret = ssl_handshake:premaster_secret(PublicKey, ECDHKey),
master_secret(PremasterSecret, State#state{diffie_hellman_keys = ECDHKey,
- session = Session#session{ecc = {named_curve, Curve}}});
+ session = Session#session{ecc = PublicKeyParams}});
%% We do currently not support cipher suites that use fixed DH.
%% If we want to implement that the following clause can be used
%% to extract DH parameters form cert.
@@ -1757,9 +1757,11 @@ key_exchange(#state{role = server, key_algorithm = Algo,
PrivateKey}),
State = Connection:queue_handshake(Msg, State0),
State#state{diffie_hellman_keys = DHKeys};
-key_exchange(#state{role = server, private_key = Key, key_algorithm = Algo} = State, _)
+key_exchange(#state{role = server, private_key = #'ECPrivateKey'{parameters = ECCurve} = Key, key_algorithm = Algo,
+ session = Session} = State, _)
when Algo == ecdh_ecdsa; Algo == ecdh_rsa ->
- State#state{diffie_hellman_keys = Key};
+ State#state{diffie_hellman_keys = Key,
+ session = Session#session{ecc = ECCurve}};
key_exchange(#state{role = server, key_algorithm = Algo,
hashsign_algorithm = HashSignAlgo,
private_key = PrivateKey,
@@ -1915,12 +1917,13 @@ key_exchange(#state{role = client,
key_exchange(#state{role = client,
key_algorithm = Algorithm,
negotiated_version = Version,
- diffie_hellman_keys = Keys} = State0, Connection)
+ session = Session,
+ diffie_hellman_keys = #'ECPrivateKey'{parameters = ECCurve} = Key} = State0, Connection)
when Algorithm == ecdhe_ecdsa; Algorithm == ecdhe_rsa;
Algorithm == ecdh_ecdsa; Algorithm == ecdh_rsa;
Algorithm == ecdh_anon ->
- Msg = ssl_handshake:key_exchange(client, ssl:tls_version(Version), {ecdh, Keys}),
- Connection:queue_handshake(Msg, State0);
+ Msg = ssl_handshake:key_exchange(client, ssl:tls_version(Version), {ecdh, Key}),
+ Connection:queue_handshake(Msg, State0#state{session = Session#session{ecc = ECCurve}});
key_exchange(#state{role = client,
ssl_options = SslOpts,
key_algorithm = psk,
@@ -2443,6 +2446,11 @@ cancel_timer(Timer) ->
erlang:cancel_timer(Timer),
ok.
+session_handle_params(#server_ecdh_params{curve = ECCurve}, Session) ->
+ Session#session{ecc = ECCurve};
+session_handle_params(_, Session) ->
+ Session.
+
register_session(client, Host, Port, #session{is_resumable = new} = Session0) ->
Session = Session0#session{is_resumable = true},
ssl_manager:register_session(Host, Port, Session),
diff --git a/lib/ssl/src/ssl_handshake.erl b/lib/ssl/src/ssl_handshake.erl
index 76fc7ae3d1..4d0bdd6386 100644
--- a/lib/ssl/src/ssl_handshake.erl
+++ b/lib/ssl/src/ssl_handshake.erl
@@ -1065,17 +1065,14 @@ select_hashsign(HashSigns, Cert, KeyExAlgo,
select_hashsign(HashSigns, Cert, KeyExAlgo, tls_v1:default_signature_algs(Version), Version);
select_hashsign(#hash_sign_algos{hash_sign_algos = HashSigns}, Cert, KeyExAlgo, SupportedHashSigns,
{Major, Minor}) when Major >= 3 andalso Minor >= 3 ->
- #'OTPCertificate'{tbsCertificate = TBSCert,
- signatureAlgorithm = {_,SignAlgo, _}} = public_key:pkix_decode_cert(Cert, otp),
+ #'OTPCertificate'{tbsCertificate = TBSCert} = public_key:pkix_decode_cert(Cert, otp),
#'OTPSubjectPublicKeyInfo'{algorithm = {_, SubjAlgo, _}} =
TBSCert#'OTPTBSCertificate'.subjectPublicKeyInfo,
- Sign = sign_algo(SignAlgo),
SubSign = sign_algo(SubjAlgo),
case lists:filter(fun({_, S} = Algos) when S == SubSign ->
- is_acceptable_hash_sign(Algos, Sign,
- SubSign, KeyExAlgo, SupportedHashSigns);
+ is_acceptable_hash_sign(Algos, KeyExAlgo, SupportedHashSigns);
(_) ->
false
end, HashSigns) of
@@ -2232,37 +2229,7 @@ sign_algo(Alg) ->
{_, Sign} =public_key:pkix_sign_types(Alg),
Sign.
-is_acceptable_hash_sign(Algos, _, _, KeyExAlgo, SupportedHashSigns) when
- KeyExAlgo == dh_dss;
- KeyExAlgo == dh_rsa;
- KeyExAlgo == ecdh_rsa;
- KeyExAlgo == ecdh_ecdsa
- ->
- %% *dh_* could be called only *dh in TLS-1.2
- is_acceptable_hash_sign(Algos, SupportedHashSigns);
-is_acceptable_hash_sign(Algos, rsa, ecdsa, ecdhe_rsa, SupportedHashSigns) ->
- is_acceptable_hash_sign(Algos, SupportedHashSigns);
-is_acceptable_hash_sign({_, rsa} = Algos, rsa, _, dhe_rsa, SupportedHashSigns) ->
- is_acceptable_hash_sign(Algos, SupportedHashSigns);
-is_acceptable_hash_sign({_, rsa} = Algos, rsa, rsa, ecdhe_rsa, SupportedHashSigns) ->
- is_acceptable_hash_sign(Algos, SupportedHashSigns);
-is_acceptable_hash_sign({_, rsa} = Algos, rsa, rsa, rsa, SupportedHashSigns) ->
- is_acceptable_hash_sign(Algos, SupportedHashSigns);
-is_acceptable_hash_sign({_, rsa} = Algos, rsa, _, srp_rsa, SupportedHashSigns) ->
- is_acceptable_hash_sign(Algos, SupportedHashSigns);
-is_acceptable_hash_sign({_, rsa} = Algos, rsa, _, rsa_psk, SupportedHashSigns) ->
- is_acceptable_hash_sign(Algos, SupportedHashSigns);
-is_acceptable_hash_sign({_, dsa} = Algos, dsa, _, dhe_dss, SupportedHashSigns) ->
- is_acceptable_hash_sign(Algos, SupportedHashSigns);
-is_acceptable_hash_sign({_, dsa} = Algos, dsa, _, srp_dss, SupportedHashSigns) ->
- is_acceptable_hash_sign(Algos, SupportedHashSigns);
-is_acceptable_hash_sign({_, ecdsa} = Algos, ecdsa, _, dhe_ecdsa, SupportedHashSigns) ->
- is_acceptable_hash_sign(Algos, SupportedHashSigns);
-is_acceptable_hash_sign({_, ecdsa} = Algos, ecdsa, ecdsa, ecdh_ecdsa, SupportedHashSigns) ->
- is_acceptable_hash_sign(Algos, SupportedHashSigns);
-is_acceptable_hash_sign({_, ecdsa} = Algos, ecdsa, ecdsa, ecdhe_ecdsa, SupportedHashSigns) ->
- is_acceptable_hash_sign(Algos, SupportedHashSigns);
-is_acceptable_hash_sign(_, _, _, KeyExAlgo, _) when
+is_acceptable_hash_sign( _, KeyExAlgo, _) when
KeyExAlgo == psk;
KeyExAlgo == dhe_psk;
KeyExAlgo == ecdhe_psk;
@@ -2271,8 +2238,9 @@ is_acceptable_hash_sign(_, _, _, KeyExAlgo, _) when
KeyExAlgo == ecdhe_anon
->
true;
-is_acceptable_hash_sign(_,_,_,_,_) ->
- false.
+is_acceptable_hash_sign(Algos,_, SupportedHashSigns) ->
+ is_acceptable_hash_sign(Algos, SupportedHashSigns).
+
is_acceptable_hash_sign(Algos, SupportedHashSigns) ->
lists:member(Algos, SupportedHashSigns).
@@ -2465,13 +2433,7 @@ cert_curve(Cert, ECCCurve0, CipherSuite) ->
#'OTPSubjectPublicKeyInfo'{algorithm = AlgInfo}
= TBSCert#'OTPTBSCertificate'.subjectPublicKeyInfo,
{namedCurve, Oid} = AlgInfo#'PublicKeyAlgorithm'.parameters,
- try pubkey_cert_records:namedCurves(Oid) of
- Curve ->
- {{named_curve, Curve}, CipherSuite}
- catch
- _:_ ->
- {no_curve, no_suite}
- end;
+ {{namedCurve, Oid}, CipherSuite};
_ ->
{ECCCurve0, CipherSuite}
end.