1%% 2%% %CopyrightBegin% 3%% 4%% Copyright Ericsson AB 2007-2020. 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: TLS-1.3 FSM 24%%---------------------------------------------------------------------- 25%% INITIAL_HELLO 26%% Client send 27%% first ClientHello 28%% | ---> CONFIG_ERROR 29%% | Send error to user 30%% | and shutdown 31%% | 32%% V 33%% RFC 8446 34%% A.1. Client 35%% 36%% START <----+ 37%% Send ClientHello | | Recv HelloRetryRequest 38%% [K_send = early data] | | 39%% v | 40%% / WAIT_SH ----+ 41%% | | Recv ServerHello 42%% | | K_recv = handshake 43%% Can | V 44%% send | WAIT_EE 45%% early | | Recv EncryptedExtensions 46%% data | +--------+--------+ 47%% | Using | | Using certificate 48%% | PSK | v 49%% | | WAIT_CERT_CR 50%% | | Recv | | Recv CertificateRequest 51%% | | Certificate | v 52%% | | | WAIT_CERT 53%% | | | | Recv Certificate 54%% | | v v 55%% | | WAIT_CV 56%% | | | Recv CertificateVerify 57%% | +> WAIT_FINISHED <+ 58%% | | Recv Finished 59%% \ | [Send EndOfEarlyData] 60%% | K_send = handshake 61%% | [Send Certificate [+ CertificateVerify]] 62%% Can send | Send Finished 63%% app data --> | K_send = K_recv = application 64%% after here v 65%% CONNECTED 66%% 67%% A.2. Server 68%% 69%% START <-----+ 70%% Recv ClientHello | | Send HelloRetryRequest 71%% v | 72%% RECVD_CH ----+ 73%% | Select parameters 74%% v 75%% NEGOTIATED 76%% | Send ServerHello 77%% | K_send = handshake 78%% | Send EncryptedExtensions 79%% | [Send CertificateRequest] 80%% Can send | [Send Certificate + CertificateVerify] 81%% app data | Send Finished 82%% after --> | K_send = application 83%% here +--------+--------+ 84%% No 0-RTT | | 0-RTT 85%% | | 86%% K_recv = handshake | | K_recv = early data 87%% [Skip decrypt errors] | +------> WAIT_EOED -+ 88%% | | Recv | | Recv EndOfEarlyData 89%% | | early data | | K_recv = handshake 90%% | +------------+ | 91%% | | 92%% +> WAIT_FLIGHT2 <--------+ 93%% | 94%% +--------+--------+ 95%% No auth | | Client auth 96%% | | 97%% | v 98%% | WAIT_CERT 99%% | Recv | | Recv Certificate 100%% | empty | v 101%% | Certificate | WAIT_CV 102%% | | | Recv 103%% | v | CertificateVerify 104%% +-> WAIT_FINISHED <---+ 105%% | Recv Finished 106%% | K_recv = application 107%% v 108%% CONNECTED 109 110-module(tls_connection_1_3). 111 112-include("ssl_alert.hrl"). 113-include("ssl_connection.hrl"). 114-include("tls_connection.hrl"). 115-include("tls_handshake.hrl"). 116-include("tls_handshake_1_3.hrl"). 117 118-behaviour(gen_statem). 119 120%% gen_statem callbacks 121-export([init/1, callback_mode/0, terminate/3, code_change/4, format_status/2]). 122 123%% gen_statem state functions 124-export([initial_hello/3, 125 config_error/3, 126 user_hello/3, 127 start/3, 128 negotiated/3, 129 wait_cert/3, 130 wait_cv/3, 131 wait_finished/3, 132 wait_sh/3, 133 wait_ee/3, 134 wait_cert_cr/3, 135 wait_eoed/3, 136 connection/3, 137 downgrade/3 138 ]). 139 140%% Internal API 141-export([setopts/3, 142 getopts/3, 143 send_key_update/2, 144 update_cipher_key/2]). 145 146%%==================================================================== 147%% Internal API 148%%==================================================================== 149 150setopts(Transport, Socket, Other) -> 151 tls_socket:setopts(Transport, Socket, Other). 152 153getopts(Transport, Socket, Tag) -> 154 tls_socket:getopts(Transport, Socket, Tag). 155 156send_key_update(Sender, Type) -> 157 KeyUpdate = tls_handshake_1_3:key_update(Type), 158 tls_sender:send_post_handshake(Sender, KeyUpdate). 159 160update_cipher_key(ConnStateName, #state{connection_states = CS0} = State0) -> 161 CS = update_cipher_key(ConnStateName, CS0), 162 State0#state{connection_states = CS}; 163update_cipher_key(ConnStateName, CS0) -> 164 #{security_parameters := SecParams0, 165 cipher_state := CipherState0} = ConnState0 = maps:get(ConnStateName, CS0), 166 HKDF = SecParams0#security_parameters.prf_algorithm, 167 CipherSuite = SecParams0#security_parameters.cipher_suite, 168 ApplicationTrafficSecret0 = SecParams0#security_parameters.application_traffic_secret, 169 ApplicationTrafficSecret = tls_v1:update_traffic_secret(HKDF, ApplicationTrafficSecret0), 170 171 %% Calculate traffic keys 172 KeyLength = tls_v1:key_length(CipherSuite), 173 {Key, IV} = tls_v1:calculate_traffic_keys(HKDF, KeyLength, ApplicationTrafficSecret), 174 175 SecParams = SecParams0#security_parameters{application_traffic_secret = ApplicationTrafficSecret}, 176 CipherState = CipherState0#cipher_state{key = Key, iv = IV}, 177 ConnState = ConnState0#{security_parameters => SecParams, 178 cipher_state => CipherState, 179 sequence_number => 0}, 180 CS0#{ConnStateName => ConnState}. 181 182%-------------------------------------------------------------------- 183%% gen_statem callbacks 184%%-------------------------------------------------------------------- 185callback_mode() -> 186 state_functions. 187 188init([Role, Sender, Host, Port, Socket, Options, User, CbInfo]) -> 189 State0 = #state{protocol_specific = Map} = initial_state(Role, Sender, 190 Host, Port, Socket, Options, User, CbInfo), 191 try 192 State = ssl_gen_statem:ssl_config(State0#state.ssl_options, Role, State0), 193 tls_gen_connection:initialize_tls_sender(State), 194 gen_statem:enter_loop(?MODULE, [], initial_hello, State) 195 catch throw:Error -> 196 EState = State0#state{protocol_specific = Map#{error => Error}}, 197 gen_statem:enter_loop(?MODULE, [], config_error, EState) 198 end. 199 200terminate({shutdown, {sender_died, Reason}}, _StateName, 201 #state{static_env = #static_env{socket = Socket, 202 transport_cb = Transport}} 203 = State) -> 204 ssl_gen_statem:handle_trusted_certs_db(State), 205 tls_gen_connection:close(Reason, Socket, Transport, undefined, undefined); 206terminate(Reason, StateName, State) -> 207 ssl_gen_statem:terminate(Reason, StateName, State). 208 209format_status(Type, Data) -> 210 ssl_gen_statem:format_status(Type, Data). 211 212code_change(_OldVsn, StateName, State, _) -> 213 {ok, StateName, State}. 214 215%-------------------------------------------------------------------- 216%% state callbacks 217%%-------------------------------------------------------------------- 218%%-------------------------------------------------------------------- 219-spec initial_hello(gen_statem:event_type(), 220 {start, timeout()} | term(), #state{}) -> 221 gen_statem:state_function_result(). 222%%-------------------------------------------------------------------- 223initial_hello(Type, Event, State) -> 224 ssl_gen_statem:?FUNCTION_NAME(Type, Event, State). 225 226%%-------------------------------------------------------------------- 227-spec config_error(gen_statem:event_type(), 228 {start, timeout()} | term(), #state{}) -> 229 gen_statem:state_function_result(). 230%%-------------------------------------------------------------------- 231config_error(Type, Event, State) -> 232 ssl_gen_statem:?FUNCTION_NAME(Type, Event, State). 233 234 235user_hello({call, From}, cancel, #state{connection_env = #connection_env{negotiated_version = Version}} 236 = State) -> 237 gen_statem:reply(From, ok), 238 ssl_gen_statem:handle_own_alert(?ALERT_REC(?FATAL, ?USER_CANCELED, user_canceled), 239 Version, ?FUNCTION_NAME, State); 240user_hello({call, From}, {handshake_continue, NewOptions, Timeout}, 241 #state{static_env = #static_env{role = Role}, 242 handshake_env = #handshake_env{hello = Hello}, 243 ssl_options = Options0} = State0) -> 244 Options = ssl:handle_options(NewOptions, Role, Options0#{handshake => full}), 245 State = ssl_gen_statem:ssl_config(Options, Role, State0), 246 Next = case Role of 247 client -> 248 wait_sh; 249 server -> 250 start 251 end, 252 {next_state, Next, State#state{start_or_recv_from = From}, 253 [{next_event, internal, Hello}, {{timeout, handshake}, Timeout, close}]}; 254user_hello(info, {'DOWN', _, _, _, _} = Event, State) -> 255 ssl_gen_statem:handle_info(Event, ?FUNCTION_NAME, State); 256user_hello(_, _, _) -> 257 {keep_state_and_data, [postpone]}. 258 259start(internal, #change_cipher_spec{}, State) -> 260 tls_gen_connection:next_event(?FUNCTION_NAME, no_record, State); 261start(internal, #client_hello{extensions = Extensions} = Hello, 262 #state{ssl_options = #{handshake := hello}, 263 start_or_recv_from = From, 264 handshake_env = HsEnv} = State) -> 265 {next_state, user_hello, 266 State#state{start_or_recv_from = undefined, 267 handshake_env = HsEnv#handshake_env{ 268 hello = Hello}}, [{reply, From, {ok, Extensions}}]}; 269start(internal, #client_hello{} = Hello, State0) -> 270 case tls_handshake_1_3:do_start(Hello, State0) of 271 #alert{} = Alert -> 272 ssl_gen_statem:handle_own_alert(Alert, {3,4}, start, State0); 273 {State, start} -> 274 {next_state, start, State, []}; 275 {State, negotiated} -> 276 {next_state, negotiated, State, [{next_event, internal, {start_handshake, undefined}}]}; 277 {State, negotiated, PSK} -> %% Session Resumption with PSK 278 {next_state, negotiated, State, [{next_event, internal, {start_handshake, PSK}}]} 279 end; 280start(internal, #server_hello{extensions = Extensions} = ServerHello, 281 #state{ssl_options = #{handshake := hello}, 282 handshake_env = HsEnv, 283 start_or_recv_from = From} 284 = State) -> 285 {next_state, user_hello, 286 State#state{start_or_recv_from = undefined, 287 handshake_env = HsEnv#handshake_env{ 288 hello = ServerHello}}, [{reply, From, {ok, Extensions}}]}; 289start(internal, #server_hello{} = ServerHello, State0) -> 290 case tls_handshake_1_3:do_start(ServerHello, State0) of 291 #alert{} = Alert -> 292 ssl_gen_statem:handle_own_alert(Alert, {3,4}, start, State0); 293 {State, NextState} -> 294 {next_state, NextState, State, []} 295 end; 296start(info, Msg, State) -> 297 tls_gen_connection:handle_info(Msg, ?FUNCTION_NAME, State); 298start(Type, Msg, State) -> 299 ssl_gen_statem:handle_common_event(Type, Msg, ?FUNCTION_NAME, State). 300 301negotiated(internal, #change_cipher_spec{}, State) -> 302 tls_gen_connection:next_event(?FUNCTION_NAME, no_record, State); 303negotiated(internal, Message, State0) -> 304 case tls_handshake_1_3:do_negotiated(Message, State0) of 305 #alert{} = Alert -> 306 ssl_gen_statem:handle_own_alert(Alert, {3,4}, negotiated, State0); 307 {State, NextState} -> 308 {next_state, NextState, State, []} 309 end; 310negotiated(info, Msg, State) -> 311 tls_gen_connection:handle_info(Msg, ?FUNCTION_NAME, State). 312 313wait_cert(internal, #change_cipher_spec{}, State0) -> 314 tls_gen_connection:next_event(?FUNCTION_NAME, no_record, State0); 315wait_cert(internal, 316 #certificate_1_3{} = Certificate, State0) -> 317 case tls_handshake_1_3:do_wait_cert(Certificate, State0) of 318 {#alert{} = Alert, State} -> 319 ssl_gen_statem:handle_own_alert(Alert, {3,4}, wait_cert, State); 320 {State, NextState} -> 321 tls_gen_connection:next_event(NextState, no_record, State) 322 end; 323wait_cert(info, Msg, State) -> 324 tls_gen_connection:handle_info(Msg, ?FUNCTION_NAME, State); 325wait_cert(Type, Msg, State) -> 326 ssl_gen_statem:handle_common_event(Type, Msg, ?FUNCTION_NAME, State). 327 328wait_cv(internal, #change_cipher_spec{}, State) -> 329 tls_gen_connection:next_event(?FUNCTION_NAME, no_record, State); 330wait_cv(internal, 331 #certificate_verify_1_3{} = CertificateVerify, State0) -> 332 case tls_handshake_1_3:do_wait_cv(CertificateVerify, State0) of 333 {#alert{} = Alert, State} -> 334 ssl_gen_statem:handle_own_alert(Alert, {3,4}, wait_cv, State); 335 {State, NextState} -> 336 tls_gen_connection:next_event(NextState, no_record, State) 337 end; 338wait_cv(info, Msg, State) -> 339 tls_gen_connection:handle_info(Msg, ?FUNCTION_NAME, State); 340wait_cv(Type, Msg, State) -> 341 ssl_gen_statem:handle_common_event(Type, Msg, ?FUNCTION_NAME, State). 342 343wait_finished(internal, #change_cipher_spec{}, State0) -> 344 tls_gen_connection:next_event(?FUNCTION_NAME, no_record, State0); 345wait_finished(internal, 346 #finished{} = Finished, State0) -> 347 case tls_handshake_1_3:do_wait_finished(Finished, State0) of 348 #alert{} = Alert -> 349 ssl_gen_statem:handle_own_alert(Alert, {3,4}, finished, State0); 350 State1 -> 351 {Record, State} = ssl_gen_statem:prepare_connection(State1, tls_gen_connection), 352 tls_gen_connection:next_event(connection, Record, State, 353 [{{timeout, handshake}, cancel}]) 354 end; 355wait_finished(info, Msg, State) -> 356 tls_gen_connection:handle_info(Msg, ?FUNCTION_NAME, State); 357wait_finished(Type, Msg, State) -> 358 ssl_gen_statem:handle_common_event(Type, Msg, ?FUNCTION_NAME, State). 359 360 361wait_sh(internal, #change_cipher_spec{}, State) -> 362 tls_gen_connection:next_event(?FUNCTION_NAME, no_record, State); 363wait_sh(internal, #server_hello{extensions = Extensions} = Hello, #state{ssl_options = #{handshake := hello}, 364 start_or_recv_from = From, 365 handshake_env = HsEnv} = State) -> 366 {next_state, user_hello, 367 State#state{start_or_recv_from = undefined, 368 handshake_env = HsEnv#handshake_env{ 369 hello = Hello}}, [{reply, From, {ok, Extensions}}]}; 370wait_sh(internal, #server_hello{} = Hello, State0) -> 371 case tls_handshake_1_3:do_wait_sh(Hello, State0) of 372 #alert{} = Alert -> 373 ssl_gen_statem:handle_own_alert(Alert, {3,4}, wait_sh, State0); 374 {State1, start, ServerHello} -> 375 %% hello_retry_request: go to start 376 {next_state, start, State1, [{next_event, internal, ServerHello}]}; 377 {State1, wait_ee} -> 378 tls_gen_connection:next_event(wait_ee, no_record, State1) 379 end; 380wait_sh(info, Msg, State) -> 381 tls_gen_connection:handle_info(Msg, ?FUNCTION_NAME, State); 382wait_sh(Type, Msg, State) -> 383 ssl_gen_statem:handle_common_event(Type, Msg, ?FUNCTION_NAME, State). 384 385 386wait_ee(internal, #change_cipher_spec{}, State) -> 387 tls_gen_connection:next_event(?FUNCTION_NAME, no_record, State); 388wait_ee(internal, #encrypted_extensions{} = EE, State0) -> 389 case tls_handshake_1_3:do_wait_ee(EE, State0) of 390 #alert{} = Alert -> 391 ssl_gen_statem:handle_own_alert(Alert, {3,4}, wait_ee, State0); 392 {State1, NextState} -> 393 tls_gen_connection:next_event(NextState, no_record, State1) 394 end; 395wait_ee(info, Msg, State) -> 396 tls_gen_connection:handle_info(Msg, ?FUNCTION_NAME, State); 397wait_ee(Type, Msg, State) -> 398 ssl_gen_statem:handle_common_event(Type, Msg, ?FUNCTION_NAME, State). 399 400 401wait_cert_cr(internal, #change_cipher_spec{}, State) -> 402 tls_gen_connection:next_event(?FUNCTION_NAME, no_record, State); 403wait_cert_cr(internal, #certificate_1_3{} = Certificate, State0) -> 404 case tls_handshake_1_3:do_wait_cert_cr(Certificate, State0) of 405 {#alert{} = Alert, State} -> 406 ssl_gen_statem:handle_own_alert(Alert, {3,4}, wait_cert_cr, State); 407 {State1, NextState} -> 408 tls_gen_connection:next_event(NextState, no_record, State1) 409 end; 410wait_cert_cr(internal, #certificate_request_1_3{} = CertificateRequest, State0) -> 411 case tls_handshake_1_3:do_wait_cert_cr(CertificateRequest, State0) of 412 #alert{} = Alert -> 413 ssl_gen_statem:handle_own_alert(Alert, {3,4}, wait_cert_cr, State0); 414 {State1, NextState} -> 415 tls_gen_connection:next_event(NextState, no_record, State1) 416 end; 417wait_cert_cr(info, Msg, State) -> 418 tls_gen_connection:handle_info(Msg, ?FUNCTION_NAME, State); 419wait_cert_cr(Type, Msg, State) -> 420 ssl_gen_statem:handle_common_event(Type, Msg, ?FUNCTION_NAME, State). 421 422wait_eoed(internal, #change_cipher_spec{}, State) -> 423 tls_gen_connection:next_event(?FUNCTION_NAME, no_record, State); 424wait_eoed(internal, #end_of_early_data{} = EOED, State0) -> 425 case tls_handshake_1_3:do_wait_eoed(EOED, State0) of 426 {#alert{} = Alert, State} -> 427 ssl_gen_statem:handle_own_alert(Alert, {3,4}, wait_eoed, State); 428 {State1, NextState} -> 429 tls_gen_connection:next_event(NextState, no_record, State1) 430 end; 431wait_eoed(info, Msg, State) -> 432 tls_gen_connection:handle_info(Msg, ?FUNCTION_NAME, State); 433wait_eoed(Type, Msg, State) -> 434 ssl_gen_statem:handle_common_event(Type, Msg, ?FUNCTION_NAME, State). 435 436connection(internal, #new_session_ticket{} = NewSessionTicket, State) -> 437 handle_new_session_ticket(NewSessionTicket, State), 438 tls_gen_connection:next_event(?FUNCTION_NAME, no_record, State); 439 440connection(internal, #key_update{} = KeyUpdate, State0) -> 441 case handle_key_update(KeyUpdate, State0) of 442 {ok, State} -> 443 tls_gen_connection:next_event(?FUNCTION_NAME, no_record, State); 444 {error, State, Alert} -> 445 ssl_gen_statem:handle_own_alert(Alert, {3,4}, connection, State), 446 tls_gen_connection:next_event(?FUNCTION_NAME, no_record, State) 447 end; 448connection({call, From}, negotiated_protocol, 449 #state{handshake_env = #handshake_env{alpn = undefined}} = State) -> 450 ssl_gen_statem:hibernate_after(?FUNCTION_NAME, State, [{reply, From, {error, protocol_not_negotiated}}]); 451connection({call, From}, negotiated_protocol, 452 #state{handshake_env = #handshake_env{alpn = SelectedProtocol, 453 negotiated_protocol = undefined}} = State) -> 454 ssl_gen_statem:hibernate_after(?FUNCTION_NAME, State, 455 [{reply, From, {ok, SelectedProtocol}}]); 456connection(Type, Event, State) -> 457 ssl_gen_statem:?FUNCTION_NAME(Type, Event, State). 458 459downgrade(internal, #new_session_ticket{} = NewSessionTicket, State) -> 460 _ = handle_new_session_ticket(NewSessionTicket, State), 461 {next_state, ?FUNCTION_NAME, State}; 462downgrade(Type, Event, State) -> 463 ssl_gen_statem:?FUNCTION_NAME(Type, Event, State). 464 465%-------------------------------------------------------------------- 466%% internal functions 467%%-------------------------------------------------------------------- 468initial_state(Role, Sender, Host, Port, Socket, {SSLOptions, SocketOptions, Trackers}, User, 469 {CbModule, DataTag, CloseTag, ErrorTag, PassiveTag}) -> 470 #{erl_dist := IsErlDist, 471 client_renegotiation := ClientRenegotiation} = SSLOptions, 472 MaxEarlyDataSize = init_max_early_data_size(Role), 473 ConnectionStates = tls_record:init_connection_states(Role, disabled, MaxEarlyDataSize), 474 UserMonitor = erlang:monitor(process, User), 475 InitStatEnv = #static_env{ 476 role = Role, 477 transport_cb = CbModule, 478 protocol_cb = tls_gen_connection, 479 data_tag = DataTag, 480 close_tag = CloseTag, 481 error_tag = ErrorTag, 482 passive_tag = PassiveTag, 483 host = Host, 484 port = Port, 485 socket = Socket, 486 trackers = Trackers 487 }, 488 #state{ 489 static_env = InitStatEnv, 490 handshake_env = #handshake_env{ 491 tls_handshake_history = ssl_handshake:init_handshake_history(), 492 renegotiation = {false, first}, 493 allow_renegotiate = ClientRenegotiation 494 }, 495 connection_env = #connection_env{user_application = {UserMonitor, User}}, 496 socket_options = SocketOptions, 497 ssl_options = SSLOptions, 498 session = #session{is_resumable = false, 499 session_id = ssl_session:legacy_session_id()}, 500 connection_states = ConnectionStates, 501 protocol_buffers = #protocol_buffers{}, 502 user_data_buffer = {[],0,[]}, 503 start_or_recv_from = undefined, 504 flight_buffer = [], 505 protocol_specific = #{sender => Sender, 506 active_n => internal_active_n(IsErlDist), 507 active_n_toggle => true 508 } 509 }. 510 511internal_active_n(true) -> 512 %% Start with a random number between 1 and ?INTERNAL_ACTIVE_N 513 %% In most cases distribution connections are established all at 514 %% the same time, and flow control engages with ?INTERNAL_ACTIVE_N for 515 %% all connections. Which creates a wave of "passive" messages, leading 516 %% to significant bump of memory & scheduler utilisation. Starting with 517 %% a random number between 1 and ?INTERNAL_ACTIVE_N helps to spread the 518 %% spike. 519 erlang:system_time() rem ?INTERNAL_ACTIVE_N + 1; 520internal_active_n(false) -> 521 case application:get_env(ssl, internal_active_n) of 522 {ok, N} when is_integer(N) -> 523 N; 524 _ -> 525 ?INTERNAL_ACTIVE_N 526 end. 527 528handle_new_session_ticket(_, #state{ssl_options = #{session_tickets := disabled}}) -> 529 ok; 530handle_new_session_ticket(#new_session_ticket{ticket_nonce = Nonce} = NewSessionTicket, 531 #state{connection_states = ConnectionStates, 532 ssl_options = #{session_tickets := SessionTickets, 533 server_name_indication := SNI}, 534 connection_env = #connection_env{user_application = {_, User}}}) 535 when SessionTickets =:= manual -> 536 #{security_parameters := SecParams} = 537 ssl_record:current_connection_state(ConnectionStates, read), 538 CipherSuite = SecParams#security_parameters.cipher_suite, 539 #{cipher := Cipher} = ssl_cipher_format:suite_bin_to_map(CipherSuite), 540 HKDF = SecParams#security_parameters.prf_algorithm, 541 RMS = SecParams#security_parameters.resumption_master_secret, 542 PSK = tls_v1:pre_shared_key(RMS, Nonce, HKDF), 543 send_ticket_data(User, NewSessionTicket, {Cipher, HKDF}, SNI, PSK); 544handle_new_session_ticket(#new_session_ticket{ticket_nonce = Nonce} = NewSessionTicket, 545 #state{connection_states = ConnectionStates, 546 ssl_options = #{session_tickets := SessionTickets, 547 server_name_indication := SNI}}) 548 when SessionTickets =:= auto -> 549 #{security_parameters := SecParams} = 550 ssl_record:current_connection_state(ConnectionStates, read), 551 CipherSuite = SecParams#security_parameters.cipher_suite, 552 #{cipher := Cipher} = ssl_cipher_format:suite_bin_to_map(CipherSuite), 553 HKDF = SecParams#security_parameters.prf_algorithm, 554 RMS = SecParams#security_parameters.resumption_master_secret, 555 PSK = tls_v1:pre_shared_key(RMS, Nonce, HKDF), 556 tls_client_ticket_store:store_ticket(NewSessionTicket, {Cipher, HKDF}, SNI, PSK). 557 558send_ticket_data(User, NewSessionTicket, CipherSuite, SNI, PSK) -> 559 Timestamp = erlang:system_time(seconds), 560 TicketData = #{cipher_suite => CipherSuite, 561 sni => SNI, 562 psk => PSK, 563 timestamp => Timestamp, 564 ticket => NewSessionTicket}, 565 User ! {ssl, session_ticket, TicketData}. 566 567handle_key_update(#key_update{request_update = update_not_requested}, State0) -> 568 %% Update read key in connection 569 {ok, update_cipher_key(current_read, State0)}; 570handle_key_update(#key_update{request_update = update_requested}, 571 #state{protocol_specific = #{sender := Sender}} = State0) -> 572 %% Update read key in connection 573 State1 = update_cipher_key(current_read, State0), 574 %% Send key_update and update sender's write key 575 case send_key_update(Sender, update_not_requested) of 576 ok -> 577 {ok, State1}; 578 {error, Reason} -> 579 {error, State1, ?ALERT_REC(?FATAL, ?INTERNAL_ERROR, Reason)} 580 end. 581 582init_max_early_data_size(client) -> 583 %% Disable trial decryption on the client side 584 %% Servers do trial decryption of max_early_data bytes of plain text. 585 %% Setting it to 0 means that a decryption error will result in an Alert. 586 0; 587init_max_early_data_size(server) -> 588 ssl_config:get_max_early_data_size(). 589 590