1% 2%% %CopyrightBegin% 3%% 4%% Copyright Ericsson AB 2007-2019. All Rights Reserved. 5%% 6%% Licensed under the Apache License, Version 2.0 (the "License"); 7%% you may not use this file except in compliance with the License. 8%% You may obtain a copy of the License at 9%% 10%% http://www.apache.org/licenses/LICENSE-2.0 11%% 12%% Unless required by applicable law or agreed to in writing, software 13%% distributed under the License is distributed on an "AS IS" BASIS, 14%% WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 15%% See the License for the specific language governing permissions and 16%% limitations under the License. 17%% 18%% %CopyrightEnd% 19%% 20 21%% 22%%---------------------------------------------------------------------- 23%% Purpose: Help functions for handling the SSL ciphers 24%% 25%%---------------------------------------------------------------------- 26 27-module(ssl_cipher). 28 29-include("ssl_internal.hrl"). 30-include("ssl_record.hrl"). 31-include("ssl_cipher.hrl"). 32-include("ssl_handshake.hrl"). 33-include("ssl_alert.hrl"). 34-include_lib("public_key/include/public_key.hrl"). 35 36-export([security_parameters/2, security_parameters/3, 37 cipher_init/3, nonce_seed/2, decipher/6, cipher/5, aead_encrypt/5, aead_decrypt/6, 38 suites/1, all_suites/1, crypto_support_filters/0, 39 chacha_suites/1, anonymous_suites/1, psk_suites/1, psk_suites_anon/1, 40 srp_suites/0, srp_suites_anon/0, 41 rc4_suites/1, des_suites/1, rsa_suites/1, 42 filter/3, filter_suites/1, filter_suites/2, 43 hash_algorithm/1, sign_algorithm/1, is_acceptable_hash/2, is_fallback/1, 44 random_bytes/1, calc_mac_hash/4, calc_mac_hash/6, 45 is_stream_ciphersuite/1]). 46 47-compile(inline). 48 49-type cipher_enum() :: integer(). 50 51-export_type([cipher_enum/0]). 52 53%%-------------------------------------------------------------------- 54-spec security_parameters(ssl_cipher_format:cipher_suite(), #security_parameters{}) -> 55 #security_parameters{}. 56%% Only security_parameters/2 should call security_parameters/3 with undefined as 57%% first argument. 58%%-------------------------------------------------------------------- 59 60security_parameters(?TLS_NULL_WITH_NULL_NULL = CipherSuite, SecParams) -> 61 security_parameters(undefined, CipherSuite, SecParams). 62 63%%-------------------------------------------------------------------- 64-spec security_parameters(ssl_record:ssl_version() | undefined, 65 ssl_cipher_format:cipher_suite(), #security_parameters{}) -> 66 #security_parameters{}. 67%% 68%% Description: Returns a security parameters record where the 69%% cipher values has been updated according to <CipherSuite> 70%%------------------------------------------------------------------- 71security_parameters(Version, CipherSuite, SecParams) -> 72 #{cipher := Cipher, mac := Hash, 73 prf := PrfHashAlg} = ssl_cipher_format:suite_definition(CipherSuite), 74 SecParams#security_parameters{ 75 cipher_suite = CipherSuite, 76 bulk_cipher_algorithm = bulk_cipher_algorithm(Cipher), 77 cipher_type = type(Cipher), 78 key_size = effective_key_bits(Cipher), 79 expanded_key_material_length = expanded_key_material(Cipher), 80 key_material_length = key_material(Cipher), 81 iv_size = iv_size(Cipher), 82 mac_algorithm = mac_algorithm(Hash), 83 prf_algorithm = prf_algorithm(PrfHashAlg, Version), 84 hash_size = hash_size(Hash)}. 85 86%%-------------------------------------------------------------------- 87-spec cipher_init(cipher_enum(), binary(), binary()) -> #cipher_state{}. 88%% 89%% Description: Initializes the #cipher_state according to BCA 90%%------------------------------------------------------------------- 91cipher_init(?RC4, IV, Key) -> 92 State = crypto:stream_init(rc4, Key), 93 #cipher_state{iv = IV, key = Key, state = State}; 94cipher_init(?AES_GCM, IV, Key) -> 95 <<Nonce:64>> = random_bytes(8), 96 #cipher_state{iv = IV, key = Key, nonce = Nonce, tag_len = 16}; 97cipher_init(?CHACHA20_POLY1305, IV, Key) -> 98 #cipher_state{iv = IV, key = Key, tag_len = 16}; 99cipher_init(_BCA, IV, Key) -> 100 %% Initialize random IV cache, not used for aead ciphers 101 #cipher_state{iv = IV, key = Key, state = <<>>}. 102 103nonce_seed(Seed, CipherState) -> 104 CipherState#cipher_state{nonce = Seed}. 105 106%%-------------------------------------------------------------------- 107-spec cipher(cipher_enum(), #cipher_state{}, binary(), iodata(), ssl_record:ssl_version()) -> 108 {binary(), #cipher_state{}}. 109%% 110%% Description: Encrypts the data and the MAC using chipher described 111%% by cipher_enum() and updating the cipher state 112%% Used for "MAC then Cipher" suites where first an HMAC of the 113%% data is calculated and the data plus the HMAC is ecncrypted. 114%%------------------------------------------------------------------- 115cipher(?NULL, CipherState, <<>>, Fragment, _Version) -> 116 {iolist_to_binary(Fragment), CipherState}; 117cipher(?RC4, CipherState = #cipher_state{state = State0}, Mac, Fragment, _Version) -> 118 GenStreamCipherList = [Fragment, Mac], 119 {State1, T} = crypto:stream_encrypt(State0, GenStreamCipherList), 120 {iolist_to_binary(T), CipherState#cipher_state{state = State1}}; 121cipher(?DES, CipherState, Mac, Fragment, Version) -> 122 block_cipher(fun(Key, IV, T) -> 123 crypto:block_encrypt(des_cbc, Key, IV, T) 124 end, block_size(des_cbc), CipherState, Mac, Fragment, Version); 125cipher(?'3DES', CipherState, Mac, Fragment, Version) -> 126 block_cipher(fun(<<K1:8/binary, K2:8/binary, K3:8/binary>>, IV, T) -> 127 crypto:block_encrypt(des3_cbc, [K1, K2, K3], IV, T) 128 end, block_size(des_cbc), CipherState, Mac, Fragment, Version); 129cipher(?AES_CBC, CipherState, Mac, Fragment, Version) -> 130 block_cipher(fun(Key, IV, T) when byte_size(Key) =:= 16 -> 131 crypto:block_encrypt(aes_cbc128, Key, IV, T); 132 (Key, IV, T) when byte_size(Key) =:= 32 -> 133 crypto:block_encrypt(aes_cbc256, Key, IV, T) 134 end, block_size(aes_128_cbc), CipherState, Mac, Fragment, Version). 135 136aead_encrypt(Type, Key, Nonce, Fragment, AdditionalData) -> 137 crypto:block_encrypt(aead_type(Type), Key, Nonce, {AdditionalData, Fragment}). 138 139aead_decrypt(Type, Key, Nonce, CipherText, CipherTag, AdditionalData) -> 140 crypto:block_decrypt(aead_type(Type), Key, Nonce, {AdditionalData, CipherText, CipherTag}). 141 142aead_type(?AES_GCM) -> 143 aes_gcm; 144aead_type(?CHACHA20_POLY1305) -> 145 chacha20_poly1305. 146 147build_cipher_block(BlockSz, Mac, Fragment) -> 148 TotSz = byte_size(Mac) + erlang:iolist_size(Fragment) + 1, 149 [Fragment, Mac, padding_with_len(TotSz, BlockSz)]. 150 151block_cipher(Fun, BlockSz, #cipher_state{key=Key, iv=IV} = CS0, 152 Mac, Fragment, {3, N}) 153 when N == 0; N == 1 -> 154 L = build_cipher_block(BlockSz, Mac, Fragment), 155 T = Fun(Key, IV, L), 156 NextIV = next_iv(T, IV), 157 {T, CS0#cipher_state{iv=NextIV}}; 158 159block_cipher(Fun, BlockSz, #cipher_state{key=Key, iv=IV, state = IV_Cache0} = CS0, 160 Mac, Fragment, {3, N}) 161 when N == 2; N == 3 -> 162 IV_Size = byte_size(IV), 163 <<NextIV:IV_Size/binary, IV_Cache/binary>> = 164 case IV_Cache0 of 165 <<>> -> 166 random_bytes(IV_Size bsl 5); % 32 IVs 167 _ -> 168 IV_Cache0 169 end, 170 L0 = build_cipher_block(BlockSz, Mac, Fragment), 171 L = [NextIV|L0], 172 T = Fun(Key, IV, L), 173 {T, CS0#cipher_state{iv=NextIV, state = IV_Cache}}. 174 175%%-------------------------------------------------------------------- 176-spec decipher(cipher_enum(), integer(), #cipher_state{}, binary(), 177 ssl_record:ssl_version(), boolean()) -> 178 {binary(), binary(), #cipher_state{}} | #alert{}. 179%% 180%% Description: Decrypts the data and the MAC using cipher described 181%% by cipher_enum() and updating the cipher state. 182%% Used for "MAC then Cipher" suites where first the data is decrypted 183%% and the an HMAC of the decrypted data is checked 184%%------------------------------------------------------------------- 185decipher(?NULL, _HashSz, CipherState, Fragment, _, _) -> 186 {Fragment, <<>>, CipherState}; 187decipher(?RC4, HashSz, CipherState = #cipher_state{state = State0}, Fragment, _, _) -> 188 try crypto:stream_decrypt(State0, Fragment) of 189 {State, Text} -> 190 GSC = generic_stream_cipher_from_bin(Text, HashSz), 191 #generic_stream_cipher{content = Content, mac = Mac} = GSC, 192 {Content, Mac, CipherState#cipher_state{state = State}} 193 catch 194 _:_ -> 195 %% This is a DECRYPTION_FAILED but 196 %% "differentiating between bad_record_mac and decryption_failed 197 %% alerts may permit certain attacks against CBC mode as used in 198 %% TLS [CBCATT]. It is preferable to uniformly use the 199 %% bad_record_mac alert to hide the specific type of the error." 200 ?ALERT_REC(?FATAL, ?BAD_RECORD_MAC, decryption_failed) 201 end; 202 203decipher(?DES, HashSz, CipherState, Fragment, Version, PaddingCheck) -> 204 block_decipher(fun(Key, IV, T) -> 205 crypto:block_decrypt(des_cbc, Key, IV, T) 206 end, CipherState, HashSz, Fragment, Version, PaddingCheck); 207decipher(?'3DES', HashSz, CipherState, Fragment, Version, PaddingCheck) -> 208 block_decipher(fun(<<K1:8/binary, K2:8/binary, K3:8/binary>>, IV, T) -> 209 crypto:block_decrypt(des3_cbc, [K1, K2, K3], IV, T) 210 end, CipherState, HashSz, Fragment, Version, PaddingCheck); 211decipher(?AES_CBC, HashSz, CipherState, Fragment, Version, PaddingCheck) -> 212 block_decipher(fun(Key, IV, T) when byte_size(Key) =:= 16 -> 213 crypto:block_decrypt(aes_cbc128, Key, IV, T); 214 (Key, IV, T) when byte_size(Key) =:= 32 -> 215 crypto:block_decrypt(aes_cbc256, Key, IV, T) 216 end, CipherState, HashSz, Fragment, Version, PaddingCheck). 217 218block_decipher(Fun, #cipher_state{key=Key, iv=IV} = CipherState0, 219 HashSz, Fragment, Version, PaddingCheck) -> 220 try 221 Text = Fun(Key, IV, Fragment), 222 NextIV = next_iv(Fragment, IV), 223 GBC = generic_block_cipher_from_bin(Version, Text, NextIV, HashSz), 224 Content = GBC#generic_block_cipher.content, 225 Mac = GBC#generic_block_cipher.mac, 226 CipherState1 = CipherState0#cipher_state{iv=GBC#generic_block_cipher.next_iv}, 227 case is_correct_padding(GBC, Version, PaddingCheck) of 228 true -> 229 {Content, Mac, CipherState1}; 230 false -> 231 %% decryption failed or invalid padding, 232 %% intentionally break Content to make 233 %% sure a packet with invalid padding 234 %% but otherwise correct data will fail 235 %% the MAC test later 236 {<<16#F0, Content/binary>>, Mac, CipherState1} 237 end 238 catch 239 _:_ -> 240 %% This is a DECRYPTION_FAILED but 241 %% "differentiating between bad_record_mac and decryption_failed 242 %% alerts may permit certain attacks against CBC mode as used in 243 %% TLS [CBCATT]. It is preferable to uniformly use the 244 %% bad_record_mac alert to hide the specific type of the error." 245 ?ALERT_REC(?FATAL, ?BAD_RECORD_MAC, decryption_failed) 246 end. 247 248%%-------------------------------------------------------------------- 249-spec suites(ssl_record:ssl_version()) -> [ssl_cipher_format:cipher_suite()]. 250%% 251%% Description: Returns a list of supported cipher suites. 252%%-------------------------------------------------------------------- 253suites({3, 0}) -> 254 ssl_v3:suites(); 255suites({3, Minor}) -> 256 tls_v1:suites(Minor); 257suites({_, Minor}) -> 258 dtls_v1:suites(Minor). 259 260all_suites({3, _} = Version) -> 261 suites(Version) 262 ++ chacha_suites(Version) 263 ++ psk_suites(Version) 264 ++ srp_suites() 265 ++ rc4_suites(Version) 266 ++ des_suites(Version) 267 ++ rsa_suites(Version); 268 269all_suites(Version) -> 270 dtls_v1:all_suites(Version). 271%%-------------------------------------------------------------------- 272-spec chacha_suites(ssl_record:ssl_version() | integer()) -> 273 [ssl_cipher_format:cipher_suite()]. 274%% 275%% Description: Returns list of the chacha cipher suites, only supported 276%% if explicitly set by user for now due to interop problems, proably need 277%% to be fixed in crypto. 278%%-------------------------------------------------------------------- 279chacha_suites({3, _}) -> 280 [?TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256, 281 ?TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256, 282 ?TLS_DHE_RSA_WITH_CHACHA20_POLY1305_SHA256]; 283chacha_suites(_) -> 284 []. 285 286%%-------------------------------------------------------------------- 287-spec anonymous_suites(ssl_record:ssl_version() | integer()) -> 288 [ssl_cipher_format:cipher_suite()]. 289%% 290%% Description: Returns a list of the anonymous cipher suites, only supported 291%% if explicitly set by user. Intended only for testing. 292%%-------------------------------------------------------------------- 293anonymous_suites({3, N}) -> 294 srp_suites_anon() ++ anonymous_suites(N); 295anonymous_suites({254, _} = Version) -> 296 dtls_v1:anonymous_suites(Version); 297anonymous_suites(N) 298 when N >= 3 -> 299 psk_suites_anon(N) ++ 300 [?TLS_DH_anon_WITH_AES_128_GCM_SHA256, 301 ?TLS_DH_anon_WITH_AES_256_GCM_SHA384, 302 ?TLS_DH_anon_WITH_AES_128_CBC_SHA256, 303 ?TLS_DH_anon_WITH_AES_256_CBC_SHA256, 304 ?TLS_ECDH_anon_WITH_AES_128_CBC_SHA, 305 ?TLS_ECDH_anon_WITH_AES_256_CBC_SHA, 306 ?TLS_ECDH_anon_WITH_3DES_EDE_CBC_SHA, 307 ?TLS_DH_anon_WITH_RC4_128_MD5]; 308anonymous_suites(2 = N) -> 309 psk_suites_anon(N) ++ 310 [?TLS_ECDH_anon_WITH_AES_128_CBC_SHA, 311 ?TLS_ECDH_anon_WITH_AES_256_CBC_SHA, 312 ?TLS_ECDH_anon_WITH_3DES_EDE_CBC_SHA, 313 ?TLS_DH_anon_WITH_DES_CBC_SHA, 314 ?TLS_DH_anon_WITH_RC4_128_MD5]; 315anonymous_suites(N) when N == 0; 316 N == 1 -> 317 psk_suites_anon(N) ++ 318 [?TLS_DH_anon_WITH_RC4_128_MD5, 319 ?TLS_DH_anon_WITH_3DES_EDE_CBC_SHA, 320 ?TLS_DH_anon_WITH_DES_CBC_SHA 321 ]. 322 323%%-------------------------------------------------------------------- 324-spec psk_suites(ssl_record:ssl_version() | integer()) -> [ssl_cipher_format:cipher_suite()]. 325%% 326%% Description: Returns a list of the PSK cipher suites, only supported 327%% if explicitly set by user. 328%%-------------------------------------------------------------------- 329psk_suites({3, N}) -> 330 psk_suites(N); 331psk_suites(N) 332 when N >= 3 -> 333 [ 334 ?TLS_RSA_PSK_WITH_AES_256_GCM_SHA384, 335 ?TLS_RSA_PSK_WITH_AES_256_CBC_SHA384, 336 ?TLS_RSA_PSK_WITH_AES_128_GCM_SHA256, 337 ?TLS_RSA_PSK_WITH_AES_128_CBC_SHA256 338 ] ++ psk_suites(0); 339psk_suites(_) -> 340 [?TLS_RSA_PSK_WITH_AES_256_CBC_SHA, 341 ?TLS_RSA_PSK_WITH_AES_128_CBC_SHA, 342 ?TLS_RSA_PSK_WITH_3DES_EDE_CBC_SHA, 343 ?TLS_RSA_PSK_WITH_RC4_128_SHA]. 344 345%%-------------------------------------------------------------------- 346-spec psk_suites_anon(ssl_record:ssl_version() | integer()) -> [ssl_cipher_format:cipher_suite()]. 347%% 348%% Description: Returns a list of the anonymous PSK cipher suites, only supported 349%% if explicitly set by user. 350%%-------------------------------------------------------------------- 351psk_suites_anon({3, N}) -> 352 psk_suites_anon(N); 353psk_suites_anon(N) 354 when N >= 3 -> 355 [ 356 ?TLS_DHE_PSK_WITH_AES_256_GCM_SHA384, 357 ?TLS_PSK_WITH_AES_256_GCM_SHA384, 358 ?TLS_ECDHE_PSK_WITH_AES_256_CBC_SHA384, 359 ?TLS_DHE_PSK_WITH_AES_256_CBC_SHA384, 360 ?TLS_PSK_WITH_AES_256_CBC_SHA384, 361 ?TLS_ECDHE_PSK_WITH_AES_128_GCM_SHA256, 362 ?TLS_DHE_PSK_WITH_AES_128_GCM_SHA256, 363 ?TLS_PSK_WITH_AES_128_GCM_SHA256, 364 ?TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256, 365 ?TLS_DHE_PSK_WITH_AES_128_CBC_SHA256, 366 ?TLS_PSK_WITH_AES_128_CBC_SHA256 367 ] ++ psk_suites_anon(0); 368psk_suites_anon(_) -> 369 [?TLS_DHE_PSK_WITH_AES_256_CBC_SHA, 370 ?TLS_PSK_WITH_AES_256_CBC_SHA, 371 ?TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA, 372 ?TLS_DHE_PSK_WITH_AES_128_CBC_SHA, 373 ?TLS_PSK_WITH_AES_128_CBC_SHA, 374 ?TLS_ECDHE_PSK_WITH_3DES_EDE_CBC_SHA, 375 ?TLS_DHE_PSK_WITH_3DES_EDE_CBC_SHA, 376 ?TLS_PSK_WITH_3DES_EDE_CBC_SHA, 377 ?TLS_ECDHE_PSK_WITH_RC4_128_SHA, 378 ?TLS_DHE_PSK_WITH_RC4_128_SHA, 379 ?TLS_PSK_WITH_RC4_128_SHA]. 380%%-------------------------------------------------------------------- 381-spec srp_suites() -> [ssl_cipher_format:cipher_suite()]. 382%% 383%% Description: Returns a list of the SRP cipher suites, only supported 384%% if explicitly set by user. 385%%-------------------------------------------------------------------- 386srp_suites() -> 387 [?TLS_SRP_SHA_RSA_WITH_3DES_EDE_CBC_SHA, 388 ?TLS_SRP_SHA_DSS_WITH_3DES_EDE_CBC_SHA, 389 ?TLS_SRP_SHA_RSA_WITH_AES_128_CBC_SHA, 390 ?TLS_SRP_SHA_DSS_WITH_AES_128_CBC_SHA, 391 ?TLS_SRP_SHA_RSA_WITH_AES_256_CBC_SHA, 392 ?TLS_SRP_SHA_DSS_WITH_AES_256_CBC_SHA]. 393 394%%-------------------------------------------------------------------- 395-spec srp_suites_anon() -> [ssl_cipher_format:cipher_suite()]. 396%% 397%% Description: Returns a list of the SRP anonymous cipher suites, only supported 398%% if explicitly set by user. 399%%-------------------------------------------------------------------- 400srp_suites_anon() -> 401 [?TLS_SRP_SHA_WITH_3DES_EDE_CBC_SHA, 402 ?TLS_SRP_SHA_WITH_AES_128_CBC_SHA, 403 ?TLS_SRP_SHA_WITH_AES_256_CBC_SHA]. 404 405%%-------------------------------------------------------------------- 406-spec rc4_suites(Version::ssl_record:ssl_version() | integer()) -> 407 [ssl_cipher_format:cipher_suite()]. 408%% 409%% Description: Returns a list of the RSA|(ECDH/RSA)| (ECDH/ECDSA) 410%% with RC4 cipher suites, only supported if explicitly set by user. 411%% Are not considered secure any more. Other RC4 suites already 412%% belonged to the user configured only category. 413%%-------------------------------------------------------------------- 414rc4_suites({3, 0}) -> 415 rc4_suites(0); 416rc4_suites({3, Minor}) -> 417 rc4_suites(Minor) ++ rc4_suites(0); 418rc4_suites(0) -> 419 [?TLS_RSA_WITH_RC4_128_SHA, 420 ?TLS_RSA_WITH_RC4_128_MD5]; 421rc4_suites(N) when N =< 3 -> 422 [?TLS_ECDHE_ECDSA_WITH_RC4_128_SHA, 423 ?TLS_ECDHE_RSA_WITH_RC4_128_SHA, 424 ?TLS_ECDH_ECDSA_WITH_RC4_128_SHA, 425 ?TLS_ECDH_RSA_WITH_RC4_128_SHA]. 426%%-------------------------------------------------------------------- 427-spec des_suites(Version::ssl_record:ssl_version()) -> [ssl_cipher_format:cipher_suite()]. 428%% 429%% Description: Returns a list of the cipher suites 430%% with DES cipher, only supported if explicitly set by user. 431%% Are not considered secure any more. 432%%-------------------------------------------------------------------- 433des_suites(_)-> 434 [?TLS_DHE_RSA_WITH_DES_CBC_SHA, 435 ?TLS_RSA_WITH_DES_CBC_SHA, 436 ?TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA, 437 ?TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA, 438 ?TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA, 439 ?TLS_DHE_DSS_WITH_3DES_EDE_CBC_SHA, 440 ?TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA, 441 ?TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA 442 ]. 443 444%%-------------------------------------------------------------------- 445-spec rsa_suites(Version::ssl_record:ssl_version() | integer()) -> [ssl_cipher_format:cipher_suite()]. 446%% 447%% Description: Returns a list of the RSA key exchange 448%% cipher suites, only supported if explicitly set by user. 449%% Are not considered secure any more. 450%%-------------------------------------------------------------------- 451rsa_suites({3, 0}) -> 452 rsa_suites(0); 453rsa_suites({3, Minor}) -> 454 rsa_suites(Minor) ++ rsa_suites(0); 455rsa_suites(0) -> 456 [?TLS_RSA_WITH_AES_256_CBC_SHA, 457 ?TLS_RSA_WITH_AES_128_CBC_SHA, 458 ?TLS_RSA_WITH_3DES_EDE_CBC_SHA 459 ]; 460rsa_suites(N) when N =< 3 -> 461 [ 462 ?TLS_RSA_WITH_AES_256_GCM_SHA384, 463 ?TLS_RSA_WITH_AES_256_CBC_SHA256, 464 ?TLS_RSA_WITH_AES_128_GCM_SHA256, 465 ?TLS_RSA_WITH_AES_128_CBC_SHA256 466 ]. 467 468%%-------------------------------------------------------------------- 469-spec filter(undefined | binary(), [ssl_cipher_format:cipher_suite()], 470 ssl_record:ssl_version()) -> [ssl_cipher_format:cipher_suite()]. 471%% 472%% Description: Select the cipher suites that can be used together with the 473%% supplied certificate. (Server side functionality) 474%%------------------------------------------------------------------- 475filter(undefined, Ciphers, _) -> 476 Ciphers; 477filter(DerCert, Ciphers0, Version) -> 478 OtpCert = public_key:pkix_decode_cert(DerCert, otp), 479 SigAlg = OtpCert#'OTPCertificate'.signatureAlgorithm, 480 PubKeyInfo = OtpCert#'OTPCertificate'.tbsCertificate#'OTPTBSCertificate'.subjectPublicKeyInfo, 481 PubKeyAlg = PubKeyInfo#'OTPSubjectPublicKeyInfo'.algorithm, 482 483 Ciphers = filter_suites_pubkey( 484 ssl_certificate:public_key_type(PubKeyAlg#'PublicKeyAlgorithm'.algorithm), 485 Ciphers0, Version, OtpCert), 486 {_, Sign} = public_key:pkix_sign_types(SigAlg#'SignatureAlgorithm'.algorithm), 487 filter_suites_signature(Sign, Ciphers, Version). 488 489%%-------------------------------------------------------------------- 490-spec filter_suites([ssl:erl_cipher_suite()] | [ssl_cipher_format:cipher_suite()], map()) -> 491 [ssl:erl_cipher_suite()] | [ssl_cipher_format:cipher_suite()]. 492%% 493%% Description: Filter suites using supplied filter funs 494%%------------------------------------------------------------------- 495filter_suites(Suites, Filters) -> 496 ApplyFilters = fun(Suite) -> 497 filter_suite(Suite, Filters) 498 end, 499 lists:filter(ApplyFilters, Suites). 500 501filter_suite(#{key_exchange := KeyExchange, 502 cipher := Cipher, 503 mac := Hash, 504 prf := Prf}, 505 #{key_exchange_filters := KeyFilters, 506 cipher_filters := CipherFilters, 507 mac_filters := HashFilters, 508 prf_filters := PrfFilters}) -> 509 all_filters(KeyExchange, KeyFilters) andalso 510 all_filters(Cipher, CipherFilters) andalso 511 all_filters(Hash, HashFilters) andalso 512 all_filters(Prf, PrfFilters); 513filter_suite(Suite, Filters) -> 514 filter_suite(ssl_cipher_format:suite_definition(Suite), Filters). 515 516%%-------------------------------------------------------------------- 517-spec filter_suites([ssl:erl_cipher_suite()] | [ssl_cipher_format:cipher_suite()]) -> 518 [ssl:erl_cipher_suite()] | [ssl_cipher_format:cipher_suite()]. 519%% 520%% Description: Filter suites for algorithms supported by crypto. 521%%------------------------------------------------------------------- 522filter_suites(Suites) -> 523 Filters = crypto_support_filters(), 524 filter_suites(Suites, Filters). 525 526all_filters(_, []) -> 527 true; 528all_filters(Value, [Filter| Rest]) -> 529 case Filter(Value) of 530 true -> 531 all_filters(Value, Rest); 532 false -> 533 false 534 end. 535crypto_support_filters() -> 536 Algos = crypto:supports(), 537 Hashs = proplists:get_value(hashs, Algos), 538 #{key_exchange_filters => 539 [fun(KeyExchange) -> 540 is_acceptable_keyexchange(KeyExchange, 541 proplists:get_value(public_keys, Algos)) 542 end], 543 cipher_filters => 544 [fun(Cipher) -> 545 is_acceptable_cipher(Cipher, 546 proplists:get_value(ciphers, Algos)) 547 end], 548 mac_filters => 549 [fun(Hash) -> 550 is_acceptable_hash(Hash, Hashs) 551 end], 552 prf_filters => 553 [fun(Prf) -> 554 is_acceptable_prf(Prf, 555 proplists:get_value(hashs, Algos)) 556 end]}. 557 558is_acceptable_keyexchange(KeyExchange, _Algos) when KeyExchange == psk; 559 KeyExchange == null -> 560 true; 561is_acceptable_keyexchange(KeyExchange, Algos) when KeyExchange == dh_anon; 562 KeyExchange == dhe_psk -> 563 proplists:get_bool(dh, Algos); 564is_acceptable_keyexchange(dhe_dss, Algos) -> 565 proplists:get_bool(dh, Algos) andalso 566 proplists:get_bool(dss, Algos); 567is_acceptable_keyexchange(dhe_rsa, Algos) -> 568 proplists:get_bool(dh, Algos) andalso 569 proplists:get_bool(rsa, Algos); 570is_acceptable_keyexchange(KeyExchange, Algos) when KeyExchange == ecdh_anon; 571 KeyExchange == ecdhe_psk -> 572 proplists:get_bool(ecdh, Algos); 573is_acceptable_keyexchange(KeyExchange, Algos) when KeyExchange == ecdh_ecdsa; 574 KeyExchange == ecdhe_ecdsa -> 575 proplists:get_bool(ecdh, Algos) andalso 576 proplists:get_bool(ecdsa, Algos); 577is_acceptable_keyexchange(KeyExchange, Algos) when KeyExchange == ecdh_rsa; 578 KeyExchange == ecdhe_rsa -> 579 proplists:get_bool(ecdh, Algos) andalso 580 proplists:get_bool(rsa, Algos); 581is_acceptable_keyexchange(KeyExchange, Algos) when KeyExchange == rsa; 582 KeyExchange == rsa_psk -> 583 proplists:get_bool(rsa, Algos); 584is_acceptable_keyexchange(srp_anon, Algos) -> 585 proplists:get_bool(srp, Algos); 586is_acceptable_keyexchange(srp_dss, Algos) -> 587 proplists:get_bool(srp, Algos) andalso 588 proplists:get_bool(dss, Algos); 589is_acceptable_keyexchange(srp_rsa, Algos) -> 590 proplists:get_bool(srp, Algos) andalso 591 proplists:get_bool(rsa, Algos); 592is_acceptable_keyexchange(_KeyExchange, _Algos) -> 593 false. 594 595is_acceptable_cipher(null, _Algos) -> 596 true; 597is_acceptable_cipher(rc4_128, Algos) -> 598 proplists:get_bool(rc4, Algos); 599is_acceptable_cipher(des_cbc, Algos) -> 600 proplists:get_bool(des_cbc, Algos); 601is_acceptable_cipher('3des_ede_cbc', Algos) -> 602 proplists:get_bool(des_ede3, Algos); 603is_acceptable_cipher(aes_128_cbc, Algos) -> 604 proplists:get_bool(aes_cbc128, Algos); 605is_acceptable_cipher(aes_256_cbc, Algos) -> 606 proplists:get_bool(aes_cbc256, Algos); 607is_acceptable_cipher(Cipher, Algos) 608 when Cipher == aes_128_gcm; 609 Cipher == aes_256_gcm -> 610 proplists:get_bool(aes_gcm, Algos); 611is_acceptable_cipher(Cipher, Algos) -> 612 proplists:get_bool(Cipher, Algos). 613 614is_acceptable_hash(null, _Algos) -> 615 true; 616is_acceptable_hash(aead, _Algos) -> 617 true; 618is_acceptable_hash(Hash, Algos) -> 619 proplists:get_bool(Hash, Algos). 620 621is_acceptable_prf(default_prf, _) -> 622 true; 623is_acceptable_prf(Prf, Algos) -> 624 proplists:get_bool(Prf, Algos). 625 626is_fallback(CipherSuites)-> 627 lists:member(?TLS_FALLBACK_SCSV, CipherSuites). 628 629 630%%-------------------------------------------------------------------- 631-spec random_bytes(integer()) -> binary(). 632 633%% 634%% Description: Generates cryptographically secure random sequence 635%%-------------------------------------------------------------------- 636random_bytes(N) -> 637 crypto:strong_rand_bytes(N). 638 639calc_mac_hash(Type, Version, 640 PlainFragment, #{sequence_number := SeqNo, 641 mac_secret := MacSecret, 642 security_parameters := 643 #security_parameters{mac_algorithm = MacAlgorithm}}) -> 644 calc_mac_hash(Type, Version, PlainFragment, MacAlgorithm, MacSecret, SeqNo). 645%% 646calc_mac_hash(Type, Version, PlainFragment, MacAlgorithm, MacSecret, SeqNo) -> 647 Length = erlang:iolist_size(PlainFragment), 648 mac_hash(Version, MacAlgorithm, MacSecret, SeqNo, Type, Length, PlainFragment). 649 650is_stream_ciphersuite(#{cipher := rc4_128}) -> 651 true; 652is_stream_ciphersuite(_) -> 653 false. 654%%-------------------------------------------------------------------- 655%%% Internal functions 656%%-------------------------------------------------------------------- 657mac_hash({_,_}, ?NULL, _MacSecret, _SeqNo, _Type, 658 _Length, _Fragment) -> 659 <<>>; 660mac_hash({3, 0}, MacAlg, MacSecret, SeqNo, Type, Length, Fragment) -> 661 ssl_v3:mac_hash(MacAlg, MacSecret, SeqNo, Type, Length, Fragment); 662mac_hash({3, N} = Version, MacAlg, MacSecret, SeqNo, Type, Length, Fragment) 663 when N =:= 1; N =:= 2; N =:= 3 -> 664 tls_v1:mac_hash(MacAlg, MacSecret, SeqNo, Type, Version, 665 Length, Fragment). 666 667bulk_cipher_algorithm(null) -> 668 ?NULL; 669bulk_cipher_algorithm(rc4_128) -> 670 ?RC4; 671bulk_cipher_algorithm(des_cbc) -> 672 ?DES; 673bulk_cipher_algorithm('3des_ede_cbc') -> 674 ?'3DES'; 675bulk_cipher_algorithm(Cipher) when Cipher == aes_128_cbc; 676 Cipher == aes_256_cbc -> 677 ?AES_CBC; 678bulk_cipher_algorithm(Cipher) when Cipher == aes_128_gcm; 679 Cipher == aes_256_gcm -> 680 ?AES_GCM; 681bulk_cipher_algorithm(chacha20_poly1305) -> 682 ?CHACHA20_POLY1305. 683 684type(Cipher) when Cipher == null; 685 Cipher == rc4_128 -> 686 ?STREAM; 687 688type(Cipher) when Cipher == des_cbc; 689 Cipher == '3des_ede_cbc'; 690 Cipher == aes_128_cbc; 691 Cipher == aes_256_cbc -> 692 ?BLOCK; 693type(Cipher) when Cipher == aes_128_gcm; 694 Cipher == aes_256_gcm; 695 Cipher == chacha20_poly1305 -> 696 ?AEAD. 697 698key_material(null) -> 699 0; 700key_material(rc4_128) -> 701 16; 702key_material(des_cbc) -> 703 8; 704key_material('3des_ede_cbc') -> 705 24; 706key_material(aes_128_cbc) -> 707 16; 708key_material(aes_256_cbc) -> 709 32; 710key_material(aes_128_gcm) -> 711 16; 712key_material(aes_256_gcm) -> 713 32; 714key_material(chacha20_poly1305) -> 715 32. 716 717expanded_key_material(null) -> 718 0; 719expanded_key_material(rc4_128) -> 720 16; 721expanded_key_material(Cipher) when Cipher == des_cbc -> 722 8; 723expanded_key_material('3des_ede_cbc') -> 724 24; 725expanded_key_material(Cipher) when Cipher == aes_128_cbc; 726 Cipher == aes_256_cbc; 727 Cipher == aes_128_gcm; 728 Cipher == aes_256_gcm; 729 Cipher == chacha20_poly1305 -> 730 unknown. 731 732effective_key_bits(null) -> 733 0; 734effective_key_bits(des_cbc) -> 735 56; 736effective_key_bits(Cipher) when Cipher == rc4_128; 737 Cipher == aes_128_cbc; 738 Cipher == aes_128_gcm -> 739 128; 740effective_key_bits('3des_ede_cbc') -> 741 168; 742effective_key_bits(Cipher) when Cipher == aes_256_cbc; 743 Cipher == aes_256_gcm; 744 Cipher == chacha20_poly1305 -> 745 256. 746 747iv_size(Cipher) when Cipher == null; 748 Cipher == rc4_128; 749 Cipher == chacha20_poly1305-> 750 0; 751iv_size(Cipher) when Cipher == aes_128_gcm; 752 Cipher == aes_256_gcm -> 753 4; 754iv_size(Cipher) -> 755 block_size(Cipher). 756 757block_size(Cipher) when Cipher == des_cbc; 758 Cipher == '3des_ede_cbc' -> 759 8; 760block_size(Cipher) when Cipher == aes_128_cbc; 761 Cipher == aes_256_cbc; 762 Cipher == aes_128_gcm; 763 Cipher == aes_256_gcm; 764 Cipher == chacha20_poly1305 -> 765 16. 766 767prf_algorithm(default_prf, {3, N}) when N >= 3 -> 768 ?SHA256; 769prf_algorithm(default_prf, {3, _}) -> 770 ?MD5SHA; 771prf_algorithm(Algo, _) -> 772 hash_algorithm(Algo). 773 774mac_algorithm(aead) -> 775 aead; 776mac_algorithm(Algo) -> 777 hash_algorithm(Algo). 778 779hash_algorithm(null) -> ?NULL; 780hash_algorithm(md5) -> ?MD5; 781hash_algorithm(sha) -> ?SHA; %% Only sha always refers to "SHA-1" 782hash_algorithm(sha224) -> ?SHA224; 783hash_algorithm(sha256) -> ?SHA256; 784hash_algorithm(sha384) -> ?SHA384; 785hash_algorithm(sha512) -> ?SHA512; 786hash_algorithm(?NULL) -> null; 787hash_algorithm(?MD5) -> md5; 788hash_algorithm(?SHA) -> sha; 789hash_algorithm(?SHA224) -> sha224; 790hash_algorithm(?SHA256) -> sha256; 791hash_algorithm(?SHA384) -> sha384; 792hash_algorithm(?SHA512) -> sha512; 793hash_algorithm(Other) when is_integer(Other) andalso ((Other >= 7) and (Other =< 223)) -> unassigned; 794hash_algorithm(Other) when is_integer(Other) andalso ((Other >= 224) and (Other =< 255)) -> Other. 795 796sign_algorithm(anon) -> ?ANON; 797sign_algorithm(rsa) -> ?RSA; 798sign_algorithm(dsa) -> ?DSA; 799sign_algorithm(ecdsa) -> ?ECDSA; 800sign_algorithm(?ANON) -> anon; 801sign_algorithm(?RSA) -> rsa; 802sign_algorithm(?DSA) -> dsa; 803sign_algorithm(?ECDSA) -> ecdsa; 804sign_algorithm(Other) when is_integer(Other) andalso ((Other >= 4) and (Other =< 223)) -> unassigned; 805sign_algorithm(Other) when is_integer(Other) andalso ((Other >= 224) and (Other =< 255)) -> Other. 806 807hash_size(null) -> 808 0; 809%% The AEAD MAC hash size is not used in the context 810%% of calculating the master secret. See RFC 5246 Section 6.2.3.3. 811hash_size(aead) -> 812 0; 813hash_size(md5) -> 814 16; 815hash_size(sha) -> 816 20; 817%% Uncomment when adding cipher suite that needs it 818%hash_size(sha224) -> 819% 28; 820hash_size(sha256) -> 821 32; 822hash_size(sha384) -> 823 48. 824%% Uncomment when adding cipher suite that needs it 825%hash_size(sha512) -> 826% 64. 827 828%% RFC 5246: 6.2.3.2. CBC Block Cipher 829%% 830%% Implementation note: Canvel et al. [CBCTIME] have demonstrated a 831%% timing attack on CBC padding based on the time required to compute 832%% the MAC. In order to defend against this attack, implementations 833%% MUST ensure that record processing time is essentially the same 834%% whether or not the padding is correct. In general, the best way to 835%% do this is to compute the MAC even if the padding is incorrect, and 836%% only then reject the packet. For instance, if the pad appears to be 837%% incorrect, the implementation might assume a zero-length pad and then 838%% compute the MAC. This leaves a small timing channel, since MAC 839%% performance depends to some extent on the size of the data fragment, 840%% but it is not believed to be large enough to be exploitable, due to 841%% the large block size of existing MACs and the small size of the 842%% timing signal. 843%% 844%% implementation note: 845%% We return the original (possibly invalid) PadLength in any case. 846%% An invalid PadLength will be caught by is_correct_padding/2 847%% 848generic_block_cipher_from_bin({3, N}, T, IV, HashSize) 849 when N == 0; N == 1 -> 850 Sz1 = byte_size(T) - 1, 851 <<_:Sz1/binary, ?BYTE(PadLength0)>> = T, 852 PadLength = if 853 PadLength0 >= Sz1 -> 0; 854 true -> PadLength0 855 end, 856 CompressedLength = byte_size(T) - PadLength - 1 - HashSize, 857 <<Content:CompressedLength/binary, Mac:HashSize/binary, 858 Padding:PadLength/binary, ?BYTE(PadLength0)>> = T, 859 #generic_block_cipher{content=Content, mac=Mac, 860 padding=Padding, padding_length=PadLength0, 861 next_iv = IV}; 862 863generic_block_cipher_from_bin({3, N}, T, IV, HashSize) 864 when N == 2; N == 3 -> 865 Sz1 = byte_size(T) - 1, 866 <<_:Sz1/binary, ?BYTE(PadLength)>> = T, 867 IVLength = byte_size(IV), 868 CompressedLength = byte_size(T) - IVLength - PadLength - 1 - HashSize, 869 <<NextIV:IVLength/binary, Content:CompressedLength/binary, Mac:HashSize/binary, 870 Padding:PadLength/binary, ?BYTE(PadLength)>> = T, 871 #generic_block_cipher{content=Content, mac=Mac, 872 padding=Padding, padding_length=PadLength, 873 next_iv = NextIV}. 874 875generic_stream_cipher_from_bin(T, HashSz) -> 876 Sz = byte_size(T), 877 CompressedLength = Sz - HashSz, 878 <<Content:CompressedLength/binary, Mac:HashSz/binary>> = T, 879 #generic_stream_cipher{content=Content, 880 mac=Mac}. 881 882is_correct_padding(#generic_block_cipher{padding_length = Len, 883 padding = Padding}, {3, 0}, _) -> 884 Len == byte_size(Padding); %% Only length check is done in SSL 3.0 spec 885%% For interoperability reasons it is possible to disable 886%% the padding check when using TLS 1.0, as it is not strictly required 887%% in the spec (only recommended), howerver this makes TLS 1.0 vunrable to the Poodle attack 888%% so by default this clause will not match 889is_correct_padding(GenBlockCipher, {3, 1}, false) -> 890 is_correct_padding(GenBlockCipher, {3, 0}, false); 891%% Padding must be checked in TLS 1.1 and after 892is_correct_padding(#generic_block_cipher{padding_length = Len, 893 padding = Padding}, _, _) -> 894 (Len == byte_size(Padding)) andalso (padding(Len) == Padding). 895 896padding(PadLen) -> 897 case PadLen of 898 0 -> <<>>; 899 1 -> <<1>>; 900 2 -> <<2,2>>; 901 3 -> <<3,3,3>>; 902 4 -> <<4,4,4,4>>; 903 5 -> <<5,5,5,5,5>>; 904 6 -> <<6,6,6,6,6,6>>; 905 7 -> <<7,7,7,7,7,7,7>>; 906 8 -> <<8,8,8,8,8,8,8,8>>; 907 9 -> <<9,9,9,9,9,9,9,9,9>>; 908 10 -> <<10,10,10,10,10,10,10,10,10,10>>; 909 11 -> <<11,11,11,11,11,11,11,11,11,11,11>>; 910 12 -> <<12,12,12,12,12,12,12,12,12,12,12,12>>; 911 13 -> <<13,13,13,13,13,13,13,13,13,13,13,13,13>>; 912 14 -> <<14,14,14,14,14,14,14,14,14,14,14,14,14,14>>; 913 15 -> <<15,15,15,15,15,15,15,15,15,15,15,15,15,15,15>>; 914 _ -> 915 binary:copy(<<PadLen>>, PadLen) 916 end. 917 918padding_with_len(TextLen, BlockSize) -> 919 case BlockSize - (TextLen rem BlockSize) of 920 0 -> <<0>>; 921 1 -> <<1,1>>; 922 2 -> <<2,2,2>>; 923 3 -> <<3,3,3,3>>; 924 4 -> <<4,4,4,4,4>>; 925 5 -> <<5,5,5,5,5,5>>; 926 6 -> <<6,6,6,6,6,6,6>>; 927 7 -> <<7,7,7,7,7,7,7,7>>; 928 8 -> <<8,8,8,8,8,8,8,8,8>>; 929 9 -> <<9,9,9,9,9,9,9,9,9,9>>; 930 10 -> <<10,10,10,10,10,10,10,10,10,10,10>>; 931 11 -> <<11,11,11,11,11,11,11,11,11,11,11,11>>; 932 12 -> <<12,12,12,12,12,12,12,12,12,12,12,12,12>>; 933 13 -> <<13,13,13,13,13,13,13,13,13,13,13,13,13,13>>; 934 14 -> <<14,14,14,14,14,14,14,14,14,14,14,14,14,14,14>>; 935 15 -> <<15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15>>; 936 PadLen -> 937 binary:copy(<<PadLen>>, PadLen + 1) 938 end. 939 940next_iv(Bin, IV) -> 941 BinSz = byte_size(Bin), 942 IVSz = byte_size(IV), 943 FirstPart = BinSz - IVSz, 944 <<_:FirstPart/binary, NextIV:IVSz/binary>> = Bin, 945 NextIV. 946 947filter_suites_pubkey(rsa, CiphersSuites0, _Version, OtpCert) -> 948 KeyUses = key_uses(OtpCert), 949 NotECDSAKeyed = (CiphersSuites0 -- ec_keyed_suites(CiphersSuites0)) 950 -- dss_keyed_suites(CiphersSuites0), 951 CiphersSuites = filter_keyuse_suites(keyEncipherment, KeyUses, 952 NotECDSAKeyed, 953 rsa_suites_encipher(CiphersSuites0)), 954 filter_keyuse_suites(digitalSignature, KeyUses, CiphersSuites, 955 rsa_ecdhe_dhe_suites(CiphersSuites)); 956filter_suites_pubkey(dsa, Ciphers, _, OtpCert) -> 957 KeyUses = key_uses(OtpCert), 958 NotECRSAKeyed = (Ciphers -- rsa_keyed_suites(Ciphers)) -- ec_keyed_suites(Ciphers), 959 filter_keyuse_suites(digitalSignature, KeyUses, NotECRSAKeyed, 960 dss_dhe_suites(Ciphers)); 961filter_suites_pubkey(ec, Ciphers, _, OtpCert) -> 962 Uses = key_uses(OtpCert), 963 NotRSADSAKeyed = (Ciphers -- rsa_keyed_suites(Ciphers)) -- dss_keyed_suites(Ciphers), 964 CiphersSuites = filter_keyuse_suites(digitalSignature, Uses, NotRSADSAKeyed, 965 ec_ecdhe_suites(Ciphers)), 966 filter_keyuse_suites(keyAgreement, Uses, CiphersSuites, ec_ecdh_suites(Ciphers)). 967 968filter_suites_signature(_, Ciphers, {3, N}) when N >= 3 -> 969 Ciphers; 970filter_suites_signature(rsa, Ciphers, Version) -> 971 (Ciphers -- ecdsa_signed_suites(Ciphers, Version)) -- dsa_signed_suites(Ciphers, Version); 972filter_suites_signature(dsa, Ciphers, Version) -> 973 (Ciphers -- ecdsa_signed_suites(Ciphers, Version)) -- rsa_signed_suites(Ciphers, Version); 974filter_suites_signature(ecdsa, Ciphers, Version) -> 975 (Ciphers -- rsa_signed_suites(Ciphers, Version)) -- dsa_signed_suites(Ciphers, Version). 976 977 978%% From RFC 5246 - Section 7.4.2. Server Certificate 979%% If the client provided a "signature_algorithms" extension, then all 980%% certificates provided by the server MUST be signed by a 981%% hash/signature algorithm pair that appears in that extension. Note 982%% that this implies that a certificate containing a key for one 983%% signature algorithm MAY be signed using a different signature 984%% algorithm (for instance, an RSA key signed with a DSA key). This is 985%% a departure from TLS 1.1, which required that the algorithms be the 986%% same. 987%% Note that this also implies that the DH_DSS, DH_RSA, 988%% ECDH_ECDSA, and ECDH_RSA key exchange algorithms do not restrict the 989%% algorithm used to sign the certificate. Fixed DH certificates MAY be 990%% signed with any hash/signature algorithm pair appearing in the 991%% extension. The names DH_DSS, DH_RSA, ECDH_ECDSA, and ECDH_RSA are 992%% historical. 993%% Note: DH_DSS and DH_RSA is not supported 994rsa_signed({3,N}) when N >= 3 -> 995 fun(rsa) -> true; 996 (dhe_rsa) -> true; 997 (ecdhe_rsa) -> true; 998 (rsa_psk) -> true; 999 (srp_rsa) -> true; 1000 (_) -> false 1001 end; 1002rsa_signed(_) -> 1003 fun(rsa) -> true; 1004 (dhe_rsa) -> true; 1005 (ecdhe_rsa) -> true; 1006 (ecdh_rsa) -> true; 1007 (rsa_psk) -> true; 1008 (srp_rsa) -> true; 1009 (_) -> false 1010 end. 1011%% Cert should be signed by RSA 1012rsa_signed_suites(Ciphers, Version) -> 1013 filter_suites(Ciphers, #{key_exchange_filters => [rsa_signed(Version)], 1014 cipher_filters => [], 1015 mac_filters => [], 1016 prf_filters => []}). 1017ecdsa_signed({3,N}) when N >= 3 -> 1018 fun(ecdhe_ecdsa) -> true; 1019 (_) -> false 1020 end; 1021ecdsa_signed(_) -> 1022 fun(ecdhe_ecdsa) -> true; 1023 (ecdh_ecdsa) -> true; 1024 (_) -> false 1025 end. 1026 1027%% Cert should be signed by ECDSA 1028ecdsa_signed_suites(Ciphers, Version) -> 1029 filter_suites(Ciphers, #{key_exchange_filters => [ecdsa_signed(Version)], 1030 cipher_filters => [], 1031 mac_filters => [], 1032 prf_filters => []}). 1033 1034rsa_keyed(dhe_rsa) -> 1035 true; 1036rsa_keyed(ecdhe_rsa) -> 1037 true; 1038rsa_keyed(rsa) -> 1039 true; 1040rsa_keyed(rsa_psk) -> 1041 true; 1042rsa_keyed(srp_rsa) -> 1043 true; 1044rsa_keyed(_) -> 1045 false. 1046 1047%% Certs key is an RSA key 1048rsa_keyed_suites(Ciphers) -> 1049 filter_suites(Ciphers, #{key_exchange_filters => [fun(Kex) -> rsa_keyed(Kex) end], 1050 cipher_filters => [], 1051 mac_filters => [], 1052 prf_filters => []}). 1053 1054%% RSA Certs key can be used for encipherment 1055rsa_suites_encipher(Ciphers) -> 1056 filter_suites(Ciphers, #{key_exchange_filters => [fun(rsa) -> true; 1057 (rsa_psk) -> true; 1058 (_) -> false 1059 end], 1060 cipher_filters => [], 1061 mac_filters => [], 1062 prf_filters => []}). 1063 1064dss_keyed(dhe_dss) -> 1065 true; 1066dss_keyed(spr_dss) -> 1067 true; 1068dss_keyed(_) -> 1069 false. 1070 1071%% Cert should be have DSS key (DSA) 1072dss_keyed_suites(Ciphers) -> 1073 filter_suites(Ciphers, #{key_exchange_filters => [fun(Kex) -> dss_keyed(Kex) end], 1074 cipher_filters => [], 1075 mac_filters => [], 1076 prf_filters => []}). 1077 1078%% Cert should be signed by DSS (DSA) 1079dsa_signed_suites(Ciphers, Version) -> 1080 filter_suites(Ciphers, #{key_exchange_filters => [dsa_signed(Version)], 1081 cipher_filters => [], 1082 mac_filters => [], 1083 prf_filters => []}). 1084dsa_signed(_) -> 1085 fun(dhe_dss) -> true; 1086 (_) -> false 1087 end. 1088 1089dss_dhe_suites(Ciphers) -> 1090 filter_suites(Ciphers, #{key_exchange_filters => [fun(dhe_dss) -> true; 1091 (_) -> false 1092 end], 1093 cipher_filters => [], 1094 mac_filters => [], 1095 prf_filters => []}). 1096 1097ec_keyed(ecdh_ecdsa) -> 1098 true; 1099ec_keyed(ecdh_rsa) -> 1100 true; 1101ec_keyed(ecdhe_ecdsa) -> 1102 true; 1103ec_keyed(_) -> 1104 false. 1105 1106%% Certs key is an ECC key 1107ec_keyed_suites(Ciphers) -> 1108 filter_suites(Ciphers, #{key_exchange_filters => [fun(Kex) -> ec_keyed(Kex) end], 1109 cipher_filters => [], 1110 mac_filters => [], 1111 prf_filters => []}). 1112 1113%% EC Certs key usage keyAgreement 1114ec_ecdh_suites(Ciphers)-> 1115 filter_suites(Ciphers, #{key_exchange_filters => [fun(ecdh_ecdsa) -> true; 1116 (_) -> false 1117 end], 1118 cipher_filters => [], 1119 mac_filters => [], 1120 prf_filters => []}). 1121 1122%% EC Certs key usage digitalSignature 1123ec_ecdhe_suites(Ciphers) -> 1124 filter_suites(Ciphers, #{key_exchange_filters => [fun(ecdhe_ecdsa) -> true; 1125 (ecdhe_rsa) -> true; 1126 (_) -> false 1127 end], 1128 cipher_filters => [], 1129 mac_filters => [], 1130 prf_filters => []}). 1131%% RSA Certs key usage digitalSignature 1132rsa_ecdhe_dhe_suites(Ciphers) -> 1133 filter_suites(Ciphers, #{key_exchange_filters => [fun(dhe_rsa) -> true; 1134 (ecdhe_rsa) -> true; 1135 (_) -> false 1136 end], 1137 cipher_filters => [], 1138 mac_filters => [], 1139 prf_filters => []}). 1140 1141key_uses(OtpCert) -> 1142 TBSCert = OtpCert#'OTPCertificate'.tbsCertificate, 1143 TBSExtensions = TBSCert#'OTPTBSCertificate'.extensions, 1144 Extensions = ssl_certificate:extensions_list(TBSExtensions), 1145 case ssl_certificate:select_extension(?'id-ce-keyUsage', Extensions) of 1146 undefined -> 1147 []; 1148 #'Extension'{extnValue = KeyUses} -> 1149 KeyUses 1150 end. 1151 1152%% If no key-usage extension is defined all key-usages are allowed 1153filter_keyuse_suites(_, [], CiphersSuites, _) -> 1154 CiphersSuites; 1155filter_keyuse_suites(Use, KeyUse, CipherSuits, Suites) -> 1156 case ssl_certificate:is_valid_key_usage(KeyUse, Use) of 1157 true -> 1158 CipherSuits; 1159 false -> 1160 CipherSuits -- Suites 1161 end. 1162