Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ssl: Revert checking of legacy schemes #8886

Open
wants to merge 1 commit into
base: maint
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 12 additions & 2 deletions lib/ssl/src/ssl_cipher.erl
Original file line number Diff line number Diff line change
Expand Up @@ -560,10 +560,20 @@ hash_size(sha384) ->
hash_size(sha512) ->
64.

is_supported_sign({Hash, rsa} = SignAlgo, HashSigns) ->
%% Handle RSA and RSA_PSS_RSAE
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

should we mark this change as potentially incompatible?

is_supported_sign({Hash, rsa} = SignAlgo, HashSigns) -> %% ?rsaEncryption cert signalgo used
lists:member(SignAlgo, HashSigns) orelse
lists:member({Hash, rsa_pss_rsae}, HashSigns);
is_supported_sign(SignAlgo, HashSigns) ->
is_supported_sign(rsa_pkcs1_sha256 = SignAlgo, HashSigns) -> %% TLS-1.3 legacy scheme
lists:member(SignAlgo, HashSigns) orelse
lists:member(rsa_pss_rsae_sha256, HashSigns);
is_supported_sign(rsa_pkcs1_sha384 = SignAlgo, HashSigns) -> %% TLS-1.3 legacy scheme
lists:member(SignAlgo, HashSigns) orelse
lists:member(rsa_pss_rsae_sha384, HashSigns);
is_supported_sign(rsa_pkcs1_sha512 = SignAlgo, HashSigns) -> %% TLS-1.3 legacy scheme
lists:member(SignAlgo, HashSigns) orelse
lists:member(rsa_pss_rsae_sha512, HashSigns);
is_supported_sign(SignAlgo, HashSigns) -> %% Normal case, format (scheme or alg-pair) depends on version
lists:member(SignAlgo, HashSigns).

signature_scheme(rsa_pkcs1_sha256) -> ?RSA_PKCS1_SHA256;
Expand Down
2 changes: 1 addition & 1 deletion lib/ssl/src/ssl_handshake.erl
Original file line number Diff line number Diff line change
Expand Up @@ -1918,7 +1918,7 @@ client_signature_schemes(ClientHashSigns, undefined) ->
ClientHashSigns;
client_signature_schemes(_, #signature_algorithms_cert{
signature_scheme_list = ClientSignatureSchemes}) ->
ClientSignatureSchemes.
ssl_cipher:signature_schemes_1_2(ClientSignatureSchemes).


%%--------------------------------------------------------------------
Expand Down
18 changes: 14 additions & 4 deletions lib/ssl/src/tls_handshake.erl
Original file line number Diff line number Diff line change
Expand Up @@ -335,13 +335,13 @@ handle_client_hello(Version,
Renegotiation) ->
case tls_record:is_acceptable_version(Version, Versions) of
true ->
SupportedHashSigns =
ssl_handshake:supported_hashsigns(maps:get(signature_algs, SslOpts, undefined)),
SigAlgs = ssl_handshake:supported_hashsigns(maps:get(signature_algs, SslOpts, undefined)),
SigAlgsCert = signature_algs_cert(Version, SslOpts, SigAlgs),
Curves = maps:get(elliptic_curves, HelloExt, undefined),
ClientHashSigns = get_signature_ext(signature_algs, HelloExt, Version),
ClientSignatureSchemes = get_signature_ext(signature_algs_cert, HelloExt, Version),
AvailableHashSigns = ssl_handshake:available_signature_algs(
ClientHashSigns, SupportedHashSigns, Version),
ClientHashSigns, SigAlgs, Version),
ECCCurve = ssl_handshake:select_curve(Curves, SupportedECCs, ECCOrder),
{Type, #session{cipher_suite = CipherSuite,
own_certificates = [OwnCert |_]} = Session1}
Expand All @@ -356,7 +356,7 @@ handle_client_hello(Version,
#{key_exchange := KeyExAlg} = ssl_cipher_format:suite_bin_to_map(CipherSuite),
case ssl_handshake:select_hashsign({ClientHashSigns, ClientSignatureSchemes},
OwnCert, KeyExAlg,
SupportedHashSigns,
SigAlgsCert,
Version) of
#alert{} = Alert ->
throw(Alert);
Expand All @@ -372,6 +372,16 @@ handle_client_hello(Version,
throw(?ALERT_REC(?FATAL, ?PROTOCOL_VERSION))
end.

signature_algs_cert(Version, SslOpts, SigAlgs) when ?TLS_GTE(Version, ?TLS_1_2) ->
case maps:get(signature_algs_cert, SslOpts, undefined) of
undefined ->
SigAlgs;
SigAlgsCert ->
ssl_handshake:supported_hashsigns(SigAlgsCert)
end;
signature_algs_cert(_,_,_) ->
undefined.

handle_client_hello_extensions(Version, Type, Random, CipherSuites,
HelloExt, SslOpts, Session0, ConnectionStates0,
Renegotiation, HashSign) ->
Expand Down
18 changes: 13 additions & 5 deletions lib/ssl/test/ssl_cert_SUITE.erl
Original file line number Diff line number Diff line change
Expand Up @@ -399,11 +399,17 @@ do_init_per_group(dsa = Alg, Config0) ->
Config = ssl_test_lib:make_dsa_cert(Config0),
COpts = proplists:get_value(client_dsa_opts, Config),
SOpts = proplists:get_value(server_dsa_opts, Config),
ShaDSA = case Version of
{3, 3} ->
[{signature_algs, [{sha, dsa}]}];
_ ->
[]
end,
[{cert_key_alg, dsa},
{extra_client, ssl_test_lib:sig_algs(Alg, Version) ++
[{ciphers, ssl_test_lib:dsa_suites(Version)}]},
[{ciphers, ssl_test_lib:dsa_suites(Version)}] ++ ShaDSA},
{extra_server, ssl_test_lib:sig_algs(Alg, Version) ++
[{ciphers, ssl_test_lib:dsa_suites(Version)}]} |
[{ciphers, ssl_test_lib:dsa_suites(Version)}] ++ ShaDSA} |
lists:delete(cert_key_alg,
[{client_cert_opts, COpts},
{server_cert_opts, SOpts} |
Expand Down Expand Up @@ -1209,13 +1215,15 @@ custom_groups(Config) ->
%% of CertificateRequest does not contain the algorithm of the client certificate).
%% ssl client sends an empty certificate.
unsupported_sign_algo_cert_client_auth() ->
[{doc,"TLS 1.3 (backported to TLS-1.2) : Test client authentication with unsupported signature_algorithm_cert"}].
[{doc,"TLS 1.3 (backported to TLS-1.2) : Test client authentication with unsupported "
"signature_algorithm_cert"}].

unsupported_sign_algo_cert_client_auth(Config) ->
ClientOpts = ssl_test_lib:ssl_options(client_cert_opts, Config),
ServerOpts0 = ssl_test_lib:ssl_options(server_cert_opts, Config),
ServerOpts = [{verify, verify_peer},
{signature_algs, [rsa_pkcs1_sha256, rsa_pkcs1_sha384, rsa_pss_rsae_sha256, rsa_pss_pss_sha256]},
{signature_algs,
[rsa_pkcs1_sha256, rsa_pkcs1_sha384, rsa_pss_rsae_sha256, rsa_pss_pss_sha256]},
%% Skip rsa_pkcs1_sha256!
{signature_algs_cert, [rsa_pkcs1_sha384, rsa_pkcs1_sha512]},
{fail_if_no_peer_cert, true}|ServerOpts0],
Expand All @@ -1224,7 +1232,7 @@ unsupported_sign_algo_cert_client_auth(Config) ->
'tlsv1.3' ->
ssl_test_lib:basic_alert(ClientOpts, ServerOpts, Config, certificate_required);
_ ->
ssl_test_lib:basic_alert(ClientOpts, ServerOpts, Config, insufficient_security)
ssl_test_lib:basic_alert(ClientOpts, ServerOpts, Config, unsupported_certificate)
end.

%%--------------------------------------------------------------------
Expand Down
114 changes: 113 additions & 1 deletion lib/ssl/test/tls_1_3_version_SUITE.erl
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,14 @@
legacy_tls12_server_tls_client/1,
tls13_client_tls11_server/0,
tls13_client_tls11_server/1,
tls12_legacy_cert_sign/0,
tls12_legacy_cert_sign/1,
tls13_legacy_cert_sign/0,
tls13_legacy_cert_sign/1,
tls13_legacy_cert_sign_with_pss_rsae/0,
tls13_legacy_cert_sign_with_pss_rsae/1,
tls12_legacy_cert_sign_with_pss_rsae/0,
tls12_legacy_cert_sign_with_pss_rsae/1,
middle_box_tls13_client/0,
middle_box_tls13_client/1,
middle_box_tls12_enabled_client/0,
Expand Down Expand Up @@ -116,7 +124,11 @@ legacy_tests() ->
tls10_client_tls_server,
tls11_client_tls_server,
tls12_client_tls_server,
tls13_client_tls11_server
tls13_client_tls11_server,
tls13_legacy_cert_sign,
tls13_legacy_cert_sign_with_pss_rsae,
tls12_legacy_cert_sign,
tls12_legacy_cert_sign_with_pss_rsae
].

init_per_suite(Config) ->
Expand Down Expand Up @@ -342,6 +354,67 @@ legacy_tls12_server_tls_client(Config) when is_list(Config) ->
| ServerOpts0],
ssl_test_lib:basic_test(ClientOpts, ServerOpts, Config).


tls13_legacy_cert_sign() ->
[{doc,"Test that a TLS 1.3 client can connect to TLS-1.3 server with pkcs1_SHA2 cert"}].

tls13_legacy_cert_sign(Config) when is_list(Config) ->
ClientOpts = [{versions, ['tlsv1.3']},
{signature_algs, rsa_pss_rsae_algs() ++ legacy_rsa_algs()}],
ServerOpts = [{versions, ['tlsv1.3']},
{signature_algs, rsa_pss_rsae_algs()},
{signature_algs_cert, legacy_rsa_algs()}],

test_rsa_pcks1_cert(sha256, ClientOpts, ServerOpts, Config),
test_rsa_pcks1_cert(sha512, ClientOpts, ServerOpts, Config),
test_rsa_pcks1_cert(sha384, ClientOpts, ServerOpts, Config).

tls13_legacy_cert_sign_with_pss_rsae() ->
[{doc,"Test that a TLS 1.3 enabled client can connect to legacy TLS-1.2 server with legacy pkcs1_SHA2 cert"}].

tls13_legacy_cert_sign_with_pss_rsae(Config) when is_list(Config) ->
ClientOpts = [{versions, ['tlsv1.3', 'tlsv1.2']},
{signature_algs, rsa_pss_rsae_algs()},
{signature_algs_cert, legacy_rsa_algs()}
],
ServerOpts = [{versions, ['tlsv1.2']},
{signature_algs, rsa_pss_rsae_algs()},
{signature_algs_cert, legacy_rsa_algs()}
],

test_rsa_pcks1_cert(sha256, ClientOpts, ServerOpts, Config),
test_rsa_pcks1_cert(sha512, ClientOpts, ServerOpts, Config),
test_rsa_pcks1_cert(sha384, ClientOpts, ServerOpts, Config).

tls12_legacy_cert_sign() ->
[{doc,"Test that a TLS 1.2 client (with old configuration) can connect to TLS-1.2 server with pkcs1_SHA2 cert"}].

tls12_legacy_cert_sign(Config) when is_list(Config) ->
ClientOpts = [{versions, ['tlsv1.2']},
{signature_algs, rsa_algs()}],
ServerOpts = [{versions, ['tlsv1.2']},
{signature_algs, rsa_algs()}],

test_rsa_pcks1_cert(sha256, ClientOpts, ServerOpts, Config),
test_rsa_pcks1_cert(sha512, ClientOpts, ServerOpts, Config),
test_rsa_pcks1_cert(sha384, ClientOpts, ServerOpts, Config).

tls12_legacy_cert_sign_with_pss_rsae() ->
[{doc,"Test that a modern TLS 1.2 client can connect to TLS-1.2 server with legacy pkcs1_SHA2 cert"}].

tls12_legacy_cert_sign_with_pss_rsae(Config) when is_list(Config) ->
ClientOpts = [{versions, ['tlsv1.2']},
{signature_algs, rsa_pss_rsae_algs() ++ rsa_algs()}
],
ServerOpts = [{versions, ['tlsv1.2']},
{signature_algs, rsa_pss_rsae_algs()},
{signature_algs_cert, legacy_rsa_algs()}
],

test_rsa_pcks1_cert(sha256, ClientOpts, ServerOpts, Config),
test_rsa_pcks1_cert(sha512, ClientOpts, ServerOpts, Config),
test_rsa_pcks1_cert(sha384, ClientOpts, ServerOpts, Config).

middle_box_tls13_client() ->
[{doc,"Test that a TLS 1.3 client can connect to a 1.3 server with and without middle box compatible mode."}].
middle_box_tls13_client(Config) when is_list(Config) ->
Expand Down Expand Up @@ -529,3 +602,42 @@ create_bad_client_certfile(NewClientCertFile, ClientOpts) ->
ClientOTPTbsCert = ClientOTPCert#'OTPCertificate'.tbsCertificate,
NewClientDerCert = public_key:pkix_sign(ClientOTPTbsCert, Key),
ssl_test_lib:der_to_pem(NewClientCertFile, [{'Certificate', NewClientDerCert, not_encrypted}]).

test_rsa_pcks1_cert(SHA, COpts, SOpts, Config) ->
#{client_config := ClientOpts,
server_config := ServerOpts} = public_key:pkix_test_data(#{server_chain => #{root => root_key(SHA),
intermediates => intermediates(SHA, 1),
peer => peer_key(SHA)},
client_chain => #{root => root_key(SHA),
intermediates => intermediates(SHA, 1),
peer => peer_key(SHA)}}),
ssl_test_lib:basic_test(COpts ++ ClientOpts, SOpts ++ ServerOpts, Config).

root_key(SHA) ->
%% As rsa keygen is not guaranteed to be fast
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm not sure what comment above relates to.
If it explaining why hardcoded RSA key is used, maybe would be better to include that in single placed comment for ssl_test_lib:hardcode_rsa_key rather than having it in every place when this function is callled?

[{digest, SHA},{key, ssl_test_lib:hardcode_rsa_key(6)}].

peer_key(SHA) ->
%% As rsa keygen is not guaranteed to be fast
[{digest, SHA}, {key, ssl_test_lib:hardcode_rsa_key(5)}].

intermediates(SHA, N) when N =< 2 ->
Default = lists:duplicate(N, [{digest, SHA}]),
%% As rsa keygen is not guaranteed to be fast
hardcode_rsa_keys(Default, N, []).

hardcode_rsa_keys([], 0, Acc) ->
Acc;
hardcode_rsa_keys([Head | Tail], N, Acc) ->
hardcode_rsa_keys(Tail, N-1, [[{key, ssl_test_lib:hardcode_rsa_key(N)} | Head] | Acc]).


rsa_algs() ->
[{sha512, rsa}, {sha384, rsa}, {sha256, rsa}].

legacy_rsa_algs() ->
[rsa_pkcs1_sha512,rsa_pkcs1_sha384,rsa_pkcs1_sha256].

rsa_pss_rsae_algs() ->
[rsa_pss_rsae_sha512,rsa_pss_rsae_sha384,rsa_pss_rsae_sha256].

Loading