1use alloc::borrow::ToOwned;
2use alloc::boxed::Box;
3use alloc::vec;
4use alloc::vec::Vec;
5
6use pki_types::ServerName;
7pub(super) use server_hello::CompleteServerHelloHandling;
8use subtle::ConstantTimeEq;
9
10use super::client_conn::ClientConnectionData;
11use super::hs::ClientContext;
12use crate::ConnectionTrafficSecrets;
13use crate::check::{inappropriate_handshake_message, inappropriate_message};
14use crate::client::common::{ClientAuthDetails, ServerCertDetails};
15use crate::client::{ClientConfig, hs};
16use crate::common_state::{CommonState, HandshakeKind, KxState, Side, State};
17use crate::conn::ConnectionRandoms;
18use crate::conn::kernel::{Direction, KernelContext, KernelState};
19use crate::crypto::KeyExchangeAlgorithm;
20use crate::enums::{AlertDescription, ContentType, HandshakeType, ProtocolVersion};
21use crate::error::{Error, InvalidMessage, PeerIncompatible, PeerMisbehaved};
22use crate::hash_hs::HandshakeHash;
23use crate::log::{debug, trace, warn};
24use crate::msgs::base::{Payload, PayloadU8, PayloadU16};
25use crate::msgs::ccs::ChangeCipherSpecPayload;
26use crate::msgs::handshake::{
27 CertificateChain, ClientDhParams, ClientEcdhParams, ClientKeyExchangeParams,
28 HandshakeMessagePayload, HandshakePayload, NewSessionTicketPayload,
29 NewSessionTicketPayloadTls13, ServerKeyExchangeParams, SessionId,
30};
31use crate::msgs::message::{Message, MessagePayload};
32use crate::msgs::persist;
33use crate::sign::Signer;
34use crate::suites::{PartiallyExtractedSecrets, SupportedCipherSuite};
35use crate::sync::Arc;
36use crate::tls12::{self, ConnectionSecrets, Tls12CipherSuite};
37use crate::verify::{self, DigitallySignedStruct};
38
39mod server_hello {
40 use super::*;
41 use crate::msgs::enums::ExtensionType;
42 use crate::msgs::handshake::{HasServerExtensions, ServerHelloPayload};
43
44 pub(in crate::client) struct CompleteServerHelloHandling {
45 pub(in crate::client) config: Arc<ClientConfig>,
46 pub(in crate::client) resuming_session: Option<persist::Tls12ClientSessionValue>,
47 pub(in crate::client) server_name: ServerName<'static>,
48 pub(in crate::client) randoms: ConnectionRandoms,
49 pub(in crate::client) using_ems: bool,
50 pub(in crate::client) transcript: HandshakeHash,
51 }
52
53 impl CompleteServerHelloHandling {
54 pub(in crate::client) fn handle_server_hello(
55 mut self,
56 cx: &mut ClientContext<'_>,
57 suite: &'static Tls12CipherSuite,
58 server_hello: &ServerHelloPayload,
59 tls13_supported: bool,
60 ) -> hs::NextStateOrError<'static> {
61 self.randoms
62 .server
63 .clone_from_slice(&server_hello.random.0[..]);
64
65 let has_downgrade_marker = self.randoms.server[24..] == tls12::DOWNGRADE_SENTINEL;
69 if tls13_supported && has_downgrade_marker {
70 return Err({
71 cx.common.send_fatal_alert(
72 AlertDescription::IllegalParameter,
73 PeerMisbehaved::AttemptedDowngradeToTls12WhenTls13IsSupported,
74 )
75 });
76 }
77
78 self.using_ems = server_hello.ems_support_acked();
80 if self.config.require_ems && !self.using_ems {
81 return Err({
82 cx.common.send_fatal_alert(
83 AlertDescription::HandshakeFailure,
84 PeerIncompatible::ExtendedMasterSecretExtensionRequired,
85 )
86 });
87 }
88
89 let must_issue_new_ticket = if server_hello
91 .find_extension(ExtensionType::SessionTicket)
92 .is_some()
93 {
94 debug!("Server supports tickets");
95 true
96 } else {
97 false
98 };
99
100 let may_send_cert_status = server_hello
103 .find_extension(ExtensionType::StatusRequest)
104 .is_some();
105 if may_send_cert_status {
106 debug!("Server may staple OCSP response");
107 }
108
109 if let Some(resuming) = self.resuming_session {
111 if resuming.session_id == server_hello.session_id {
112 debug!("Server agreed to resume");
113
114 if resuming.suite() != suite {
116 return Err(PeerMisbehaved::ResumptionOfferedWithVariedCipherSuite.into());
117 }
118
119 if resuming.extended_ms() != self.using_ems {
121 return Err(PeerMisbehaved::ResumptionOfferedWithVariedEms.into());
122 }
123
124 let secrets =
125 ConnectionSecrets::new_resume(self.randoms, suite, resuming.secret());
126 self.config.key_log.log(
127 "CLIENT_RANDOM",
128 &secrets.randoms.client,
129 &secrets.master_secret,
130 );
131 cx.common
132 .start_encryption_tls12(&secrets, Side::Client);
133
134 cx.common.peer_certificates = Some(
137 resuming
138 .server_cert_chain()
139 .clone()
140 .into_owned(),
141 );
142 cx.common.handshake_kind = Some(HandshakeKind::Resumed);
143 let cert_verified = verify::ServerCertVerified::assertion();
144 let sig_verified = verify::HandshakeSignatureValid::assertion();
145
146 return if must_issue_new_ticket {
147 Ok(Box::new(ExpectNewTicket {
148 config: self.config,
149 secrets,
150 resuming_session: Some(resuming),
151 session_id: server_hello.session_id,
152 server_name: self.server_name,
153 using_ems: self.using_ems,
154 transcript: self.transcript,
155 resuming: true,
156 cert_verified,
157 sig_verified,
158 }))
159 } else {
160 Ok(Box::new(ExpectCcs {
161 config: self.config,
162 secrets,
163 resuming_session: Some(resuming),
164 session_id: server_hello.session_id,
165 server_name: self.server_name,
166 using_ems: self.using_ems,
167 transcript: self.transcript,
168 ticket: None,
169 resuming: true,
170 cert_verified,
171 sig_verified,
172 }))
173 };
174 }
175 }
176
177 cx.common.handshake_kind = Some(HandshakeKind::Full);
178 Ok(Box::new(ExpectCertificate {
179 config: self.config,
180 resuming_session: None,
181 session_id: server_hello.session_id,
182 server_name: self.server_name,
183 randoms: self.randoms,
184 using_ems: self.using_ems,
185 transcript: self.transcript,
186 suite,
187 may_send_cert_status,
188 must_issue_new_ticket,
189 }))
190 }
191 }
192}
193
194struct ExpectCertificate {
195 config: Arc<ClientConfig>,
196 resuming_session: Option<persist::Tls12ClientSessionValue>,
197 session_id: SessionId,
198 server_name: ServerName<'static>,
199 randoms: ConnectionRandoms,
200 using_ems: bool,
201 transcript: HandshakeHash,
202 pub(super) suite: &'static Tls12CipherSuite,
203 may_send_cert_status: bool,
204 must_issue_new_ticket: bool,
205}
206
207impl State<ClientConnectionData> for ExpectCertificate {
208 fn handle<'m>(
209 mut self: Box<Self>,
210 _cx: &mut ClientContext<'_>,
211 m: Message<'m>,
212 ) -> hs::NextStateOrError<'m>
213 where
214 Self: 'm,
215 {
216 self.transcript.add_message(&m);
217 let server_cert_chain = require_handshake_msg_move!(
218 m,
219 HandshakeType::Certificate,
220 HandshakePayload::Certificate
221 )?;
222
223 if self.may_send_cert_status {
224 Ok(Box::new(ExpectCertificateStatusOrServerKx {
225 config: self.config,
226 resuming_session: self.resuming_session,
227 session_id: self.session_id,
228 server_name: self.server_name,
229 randoms: self.randoms,
230 using_ems: self.using_ems,
231 transcript: self.transcript,
232 suite: self.suite,
233 server_cert_chain,
234 must_issue_new_ticket: self.must_issue_new_ticket,
235 }))
236 } else {
237 let server_cert = ServerCertDetails::new(server_cert_chain, vec![]);
238
239 Ok(Box::new(ExpectServerKx {
240 config: self.config,
241 resuming_session: self.resuming_session,
242 session_id: self.session_id,
243 server_name: self.server_name,
244 randoms: self.randoms,
245 using_ems: self.using_ems,
246 transcript: self.transcript,
247 suite: self.suite,
248 server_cert,
249 must_issue_new_ticket: self.must_issue_new_ticket,
250 }))
251 }
252 }
253
254 fn into_owned(self: Box<Self>) -> hs::NextState<'static> {
255 self
256 }
257}
258
259struct ExpectCertificateStatusOrServerKx<'m> {
260 config: Arc<ClientConfig>,
261 resuming_session: Option<persist::Tls12ClientSessionValue>,
262 session_id: SessionId,
263 server_name: ServerName<'static>,
264 randoms: ConnectionRandoms,
265 using_ems: bool,
266 transcript: HandshakeHash,
267 suite: &'static Tls12CipherSuite,
268 server_cert_chain: CertificateChain<'m>,
269 must_issue_new_ticket: bool,
270}
271
272impl State<ClientConnectionData> for ExpectCertificateStatusOrServerKx<'_> {
273 fn handle<'m>(
274 self: Box<Self>,
275 cx: &mut ClientContext<'_>,
276 m: Message<'m>,
277 ) -> hs::NextStateOrError<'m>
278 where
279 Self: 'm,
280 {
281 match m.payload {
282 MessagePayload::Handshake {
283 parsed: HandshakeMessagePayload(HandshakePayload::ServerKeyExchange(..)),
284 ..
285 } => Box::new(ExpectServerKx {
286 config: self.config,
287 resuming_session: self.resuming_session,
288 session_id: self.session_id,
289 server_name: self.server_name,
290 randoms: self.randoms,
291 using_ems: self.using_ems,
292 transcript: self.transcript,
293 suite: self.suite,
294 server_cert: ServerCertDetails::new(self.server_cert_chain, vec![]),
295 must_issue_new_ticket: self.must_issue_new_ticket,
296 })
297 .handle(cx, m),
298 MessagePayload::Handshake {
299 parsed: HandshakeMessagePayload(HandshakePayload::CertificateStatus(..)),
300 ..
301 } => Box::new(ExpectCertificateStatus {
302 config: self.config,
303 resuming_session: self.resuming_session,
304 session_id: self.session_id,
305 server_name: self.server_name,
306 randoms: self.randoms,
307 using_ems: self.using_ems,
308 transcript: self.transcript,
309 suite: self.suite,
310 server_cert_chain: self.server_cert_chain,
311 must_issue_new_ticket: self.must_issue_new_ticket,
312 })
313 .handle(cx, m),
314 payload => Err(inappropriate_handshake_message(
315 &payload,
316 &[ContentType::Handshake],
317 &[
318 HandshakeType::ServerKeyExchange,
319 HandshakeType::CertificateStatus,
320 ],
321 )),
322 }
323 }
324
325 fn into_owned(self: Box<Self>) -> hs::NextState<'static> {
326 Box::new(ExpectCertificateStatusOrServerKx {
327 config: self.config,
328 resuming_session: self.resuming_session,
329 session_id: self.session_id,
330 server_name: self.server_name,
331 randoms: self.randoms,
332 using_ems: self.using_ems,
333 transcript: self.transcript,
334 suite: self.suite,
335 server_cert_chain: self.server_cert_chain.into_owned(),
336 must_issue_new_ticket: self.must_issue_new_ticket,
337 })
338 }
339}
340
341struct ExpectCertificateStatus<'a> {
342 config: Arc<ClientConfig>,
343 resuming_session: Option<persist::Tls12ClientSessionValue>,
344 session_id: SessionId,
345 server_name: ServerName<'static>,
346 randoms: ConnectionRandoms,
347 using_ems: bool,
348 transcript: HandshakeHash,
349 suite: &'static Tls12CipherSuite,
350 server_cert_chain: CertificateChain<'a>,
351 must_issue_new_ticket: bool,
352}
353
354impl State<ClientConnectionData> for ExpectCertificateStatus<'_> {
355 fn handle<'m>(
356 mut self: Box<Self>,
357 _cx: &mut ClientContext<'_>,
358 m: Message<'m>,
359 ) -> hs::NextStateOrError<'m>
360 where
361 Self: 'm,
362 {
363 self.transcript.add_message(&m);
364 let server_cert_ocsp_response = require_handshake_msg_move!(
365 m,
366 HandshakeType::CertificateStatus,
367 HandshakePayload::CertificateStatus
368 )?
369 .into_inner();
370
371 trace!(
372 "Server stapled OCSP response is {:?}",
373 &server_cert_ocsp_response
374 );
375
376 let server_cert = ServerCertDetails::new(self.server_cert_chain, server_cert_ocsp_response);
377
378 Ok(Box::new(ExpectServerKx {
379 config: self.config,
380 resuming_session: self.resuming_session,
381 session_id: self.session_id,
382 server_name: self.server_name,
383 randoms: self.randoms,
384 using_ems: self.using_ems,
385 transcript: self.transcript,
386 suite: self.suite,
387 server_cert,
388 must_issue_new_ticket: self.must_issue_new_ticket,
389 }))
390 }
391
392 fn into_owned(self: Box<Self>) -> hs::NextState<'static> {
393 Box::new(ExpectCertificateStatus {
394 config: self.config,
395 resuming_session: self.resuming_session,
396 session_id: self.session_id,
397 server_name: self.server_name,
398 randoms: self.randoms,
399 using_ems: self.using_ems,
400 transcript: self.transcript,
401 suite: self.suite,
402 server_cert_chain: self.server_cert_chain.into_owned(),
403 must_issue_new_ticket: self.must_issue_new_ticket,
404 })
405 }
406}
407
408struct ExpectServerKx<'a> {
409 config: Arc<ClientConfig>,
410 resuming_session: Option<persist::Tls12ClientSessionValue>,
411 session_id: SessionId,
412 server_name: ServerName<'static>,
413 randoms: ConnectionRandoms,
414 using_ems: bool,
415 transcript: HandshakeHash,
416 suite: &'static Tls12CipherSuite,
417 server_cert: ServerCertDetails<'a>,
418 must_issue_new_ticket: bool,
419}
420
421impl State<ClientConnectionData> for ExpectServerKx<'_> {
422 fn handle<'m>(
423 mut self: Box<Self>,
424 cx: &mut ClientContext<'_>,
425 m: Message<'m>,
426 ) -> hs::NextStateOrError<'m>
427 where
428 Self: 'm,
429 {
430 let opaque_kx = require_handshake_msg!(
431 m,
432 HandshakeType::ServerKeyExchange,
433 HandshakePayload::ServerKeyExchange
434 )?;
435 self.transcript.add_message(&m);
436
437 let kx = opaque_kx
438 .unwrap_given_kxa(self.suite.kx)
439 .ok_or_else(|| {
440 cx.common.send_fatal_alert(
441 AlertDescription::DecodeError,
442 InvalidMessage::MissingKeyExchange,
443 )
444 })?;
445
446 let mut kx_params = Vec::new();
448 kx.params.encode(&mut kx_params);
449 let server_kx = ServerKxDetails::new(kx_params, kx.dss);
450
451 #[cfg_attr(not(feature = "logging"), allow(unused_variables))]
452 {
453 match &kx.params {
454 ServerKeyExchangeParams::Ecdh(ecdhe) => {
455 debug!("ECDHE curve is {:?}", ecdhe.curve_params)
456 }
457 ServerKeyExchangeParams::Dh(dhe) => {
458 debug!("DHE params are p = {:?}, g = {:?}", dhe.dh_p, dhe.dh_g)
459 }
460 }
461 }
462
463 Ok(Box::new(ExpectServerDoneOrCertReq {
464 config: self.config,
465 resuming_session: self.resuming_session,
466 session_id: self.session_id,
467 server_name: self.server_name,
468 randoms: self.randoms,
469 using_ems: self.using_ems,
470 transcript: self.transcript,
471 suite: self.suite,
472 server_cert: self.server_cert,
473 server_kx,
474 must_issue_new_ticket: self.must_issue_new_ticket,
475 }))
476 }
477
478 fn into_owned(self: Box<Self>) -> hs::NextState<'static> {
479 Box::new(ExpectServerKx {
480 config: self.config,
481 resuming_session: self.resuming_session,
482 session_id: self.session_id,
483 server_name: self.server_name,
484 randoms: self.randoms,
485 using_ems: self.using_ems,
486 transcript: self.transcript,
487 suite: self.suite,
488 server_cert: self.server_cert.into_owned(),
489 must_issue_new_ticket: self.must_issue_new_ticket,
490 })
491 }
492}
493
494fn emit_certificate(
495 transcript: &mut HandshakeHash,
496 cert_chain: CertificateChain<'static>,
497 common: &mut CommonState,
498) {
499 let cert = Message {
500 version: ProtocolVersion::TLSv1_2,
501 payload: MessagePayload::handshake(HandshakeMessagePayload(HandshakePayload::Certificate(
502 cert_chain,
503 ))),
504 };
505
506 transcript.add_message(&cert);
507 common.send_msg(cert, false);
508}
509
510fn emit_client_kx(
511 transcript: &mut HandshakeHash,
512 kxa: KeyExchangeAlgorithm,
513 common: &mut CommonState,
514 pub_key: &[u8],
515) {
516 let mut buf = Vec::new();
517 match kxa {
518 KeyExchangeAlgorithm::ECDHE => ClientKeyExchangeParams::Ecdh(ClientEcdhParams {
519 public: PayloadU8::new(pub_key.to_vec()),
520 }),
521 KeyExchangeAlgorithm::DHE => ClientKeyExchangeParams::Dh(ClientDhParams {
522 public: PayloadU16::new(pub_key.to_vec()),
523 }),
524 }
525 .encode(&mut buf);
526 let pubkey = Payload::new(buf);
527
528 let ckx = Message {
529 version: ProtocolVersion::TLSv1_2,
530 payload: MessagePayload::handshake(HandshakeMessagePayload(
531 HandshakePayload::ClientKeyExchange(pubkey),
532 )),
533 };
534
535 transcript.add_message(&ckx);
536 common.send_msg(ckx, false);
537}
538
539fn emit_certverify(
540 transcript: &mut HandshakeHash,
541 signer: &dyn Signer,
542 common: &mut CommonState,
543) -> Result<(), Error> {
544 let message = transcript
545 .take_handshake_buf()
546 .ok_or_else(|| Error::General("Expected transcript".to_owned()))?;
547
548 let scheme = signer.scheme();
549 let sig = signer.sign(&message)?;
550 let body = DigitallySignedStruct::new(scheme, sig);
551
552 let m = Message {
553 version: ProtocolVersion::TLSv1_2,
554 payload: MessagePayload::handshake(HandshakeMessagePayload(
555 HandshakePayload::CertificateVerify(body),
556 )),
557 };
558
559 transcript.add_message(&m);
560 common.send_msg(m, false);
561 Ok(())
562}
563
564fn emit_ccs(common: &mut CommonState) {
565 let ccs = Message {
566 version: ProtocolVersion::TLSv1_2,
567 payload: MessagePayload::ChangeCipherSpec(ChangeCipherSpecPayload {}),
568 };
569
570 common.send_msg(ccs, false);
571}
572
573fn emit_finished(
574 secrets: &ConnectionSecrets,
575 transcript: &mut HandshakeHash,
576 common: &mut CommonState,
577) {
578 let vh = transcript.current_hash();
579 let verify_data = secrets.client_verify_data(&vh);
580 let verify_data_payload = Payload::new(verify_data);
581
582 let f = Message {
583 version: ProtocolVersion::TLSv1_2,
584 payload: MessagePayload::handshake(HandshakeMessagePayload(HandshakePayload::Finished(
585 verify_data_payload,
586 ))),
587 };
588
589 transcript.add_message(&f);
590 common.send_msg(f, true);
591}
592
593struct ServerKxDetails {
594 kx_params: Vec<u8>,
595 kx_sig: DigitallySignedStruct,
596}
597
598impl ServerKxDetails {
599 fn new(params: Vec<u8>, sig: DigitallySignedStruct) -> Self {
600 Self {
601 kx_params: params,
602 kx_sig: sig,
603 }
604 }
605}
606
607struct ExpectServerDoneOrCertReq<'a> {
611 config: Arc<ClientConfig>,
612 resuming_session: Option<persist::Tls12ClientSessionValue>,
613 session_id: SessionId,
614 server_name: ServerName<'static>,
615 randoms: ConnectionRandoms,
616 using_ems: bool,
617 transcript: HandshakeHash,
618 suite: &'static Tls12CipherSuite,
619 server_cert: ServerCertDetails<'a>,
620 server_kx: ServerKxDetails,
621 must_issue_new_ticket: bool,
622}
623
624impl State<ClientConnectionData> for ExpectServerDoneOrCertReq<'_> {
625 fn handle<'m>(
626 mut self: Box<Self>,
627 cx: &mut ClientContext<'_>,
628 m: Message<'m>,
629 ) -> hs::NextStateOrError<'m>
630 where
631 Self: 'm,
632 {
633 if matches!(
634 m.payload,
635 MessagePayload::Handshake {
636 parsed: HandshakeMessagePayload(HandshakePayload::CertificateRequest(_)),
637 ..
638 }
639 ) {
640 Box::new(ExpectCertificateRequest {
641 config: self.config,
642 resuming_session: self.resuming_session,
643 session_id: self.session_id,
644 server_name: self.server_name,
645 randoms: self.randoms,
646 using_ems: self.using_ems,
647 transcript: self.transcript,
648 suite: self.suite,
649 server_cert: self.server_cert,
650 server_kx: self.server_kx,
651 must_issue_new_ticket: self.must_issue_new_ticket,
652 })
653 .handle(cx, m)
654 } else {
655 self.transcript.abandon_client_auth();
656
657 Box::new(ExpectServerDone {
658 config: self.config,
659 resuming_session: self.resuming_session,
660 session_id: self.session_id,
661 server_name: self.server_name,
662 randoms: self.randoms,
663 using_ems: self.using_ems,
664 transcript: self.transcript,
665 suite: self.suite,
666 server_cert: self.server_cert,
667 server_kx: self.server_kx,
668 client_auth: None,
669 must_issue_new_ticket: self.must_issue_new_ticket,
670 })
671 .handle(cx, m)
672 }
673 }
674
675 fn into_owned(self: Box<Self>) -> hs::NextState<'static> {
676 Box::new(ExpectServerDoneOrCertReq {
677 config: self.config,
678 resuming_session: self.resuming_session,
679 session_id: self.session_id,
680 server_name: self.server_name,
681 randoms: self.randoms,
682 using_ems: self.using_ems,
683 transcript: self.transcript,
684 suite: self.suite,
685 server_cert: self.server_cert.into_owned(),
686 server_kx: self.server_kx,
687 must_issue_new_ticket: self.must_issue_new_ticket,
688 })
689 }
690}
691
692struct ExpectCertificateRequest<'a> {
693 config: Arc<ClientConfig>,
694 resuming_session: Option<persist::Tls12ClientSessionValue>,
695 session_id: SessionId,
696 server_name: ServerName<'static>,
697 randoms: ConnectionRandoms,
698 using_ems: bool,
699 transcript: HandshakeHash,
700 suite: &'static Tls12CipherSuite,
701 server_cert: ServerCertDetails<'a>,
702 server_kx: ServerKxDetails,
703 must_issue_new_ticket: bool,
704}
705
706impl State<ClientConnectionData> for ExpectCertificateRequest<'_> {
707 fn handle<'m>(
708 mut self: Box<Self>,
709 _cx: &mut ClientContext<'_>,
710 m: Message<'m>,
711 ) -> hs::NextStateOrError<'m>
712 where
713 Self: 'm,
714 {
715 let certreq = require_handshake_msg!(
716 m,
717 HandshakeType::CertificateRequest,
718 HandshakePayload::CertificateRequest
719 )?;
720 self.transcript.add_message(&m);
721 debug!("Got CertificateRequest {certreq:?}");
722
723 const NO_CONTEXT: Option<Vec<u8>> = None; let no_compression = None; let client_auth = ClientAuthDetails::resolve(
732 self.config
733 .client_auth_cert_resolver
734 .as_ref(),
735 Some(&certreq.canames),
736 &certreq.sigschemes,
737 NO_CONTEXT,
738 no_compression,
739 );
740
741 Ok(Box::new(ExpectServerDone {
742 config: self.config,
743 resuming_session: self.resuming_session,
744 session_id: self.session_id,
745 server_name: self.server_name,
746 randoms: self.randoms,
747 using_ems: self.using_ems,
748 transcript: self.transcript,
749 suite: self.suite,
750 server_cert: self.server_cert,
751 server_kx: self.server_kx,
752 client_auth: Some(client_auth),
753 must_issue_new_ticket: self.must_issue_new_ticket,
754 }))
755 }
756
757 fn into_owned(self: Box<Self>) -> hs::NextState<'static> {
758 Box::new(ExpectCertificateRequest {
759 config: self.config,
760 resuming_session: self.resuming_session,
761 session_id: self.session_id,
762 server_name: self.server_name,
763 randoms: self.randoms,
764 using_ems: self.using_ems,
765 transcript: self.transcript,
766 suite: self.suite,
767 server_cert: self.server_cert.into_owned(),
768 server_kx: self.server_kx,
769 must_issue_new_ticket: self.must_issue_new_ticket,
770 })
771 }
772}
773
774struct ExpectServerDone<'a> {
775 config: Arc<ClientConfig>,
776 resuming_session: Option<persist::Tls12ClientSessionValue>,
777 session_id: SessionId,
778 server_name: ServerName<'static>,
779 randoms: ConnectionRandoms,
780 using_ems: bool,
781 transcript: HandshakeHash,
782 suite: &'static Tls12CipherSuite,
783 server_cert: ServerCertDetails<'a>,
784 server_kx: ServerKxDetails,
785 client_auth: Option<ClientAuthDetails>,
786 must_issue_new_ticket: bool,
787}
788
789impl State<ClientConnectionData> for ExpectServerDone<'_> {
790 fn handle<'m>(
791 self: Box<Self>,
792 cx: &mut ClientContext<'_>,
793 m: Message<'m>,
794 ) -> hs::NextStateOrError<'m>
795 where
796 Self: 'm,
797 {
798 match m.payload {
799 MessagePayload::Handshake {
800 parsed: HandshakeMessagePayload(HandshakePayload::ServerHelloDone),
801 ..
802 } => {}
803 payload => {
804 return Err(inappropriate_handshake_message(
805 &payload,
806 &[ContentType::Handshake],
807 &[HandshakeType::ServerHelloDone],
808 ));
809 }
810 }
811
812 let mut st = *self;
813 st.transcript.add_message(&m);
814
815 cx.common.check_aligned_handshake()?;
816
817 trace!("Server cert is {:?}", st.server_cert.cert_chain);
818 debug!("Server DNS name is {:?}", st.server_name);
819
820 let suite = st.suite;
821
822 let (end_entity, intermediates) = st
836 .server_cert
837 .cert_chain
838 .split_first()
839 .ok_or(Error::NoCertificatesPresented)?;
840
841 let now = st.config.current_time()?;
842
843 let cert_verified = st
844 .config
845 .verifier
846 .verify_server_cert(
847 end_entity,
848 intermediates,
849 &st.server_name,
850 &st.server_cert.ocsp_response,
851 now,
852 )
853 .map_err(|err| {
854 cx.common
855 .send_cert_verify_error_alert(err)
856 })?;
857
858 let sig_verified = {
862 let mut message = Vec::new();
863 message.extend_from_slice(&st.randoms.client);
864 message.extend_from_slice(&st.randoms.server);
865 message.extend_from_slice(&st.server_kx.kx_params);
866
867 let sig = &st.server_kx.kx_sig;
869 if !SupportedCipherSuite::from(suite)
870 .usable_for_signature_algorithm(sig.scheme.algorithm())
871 {
872 warn!(
873 "peer signed kx with wrong algorithm (got {:?} expect {:?})",
874 sig.scheme.algorithm(),
875 suite.sign
876 );
877 return Err(PeerMisbehaved::SignedKxWithWrongAlgorithm.into());
878 }
879
880 st.config
881 .verifier
882 .verify_tls12_signature(&message, end_entity, sig)
883 .map_err(|err| {
884 cx.common
885 .send_cert_verify_error_alert(err)
886 })?
887 };
888 cx.common.peer_certificates = Some(st.server_cert.cert_chain.into_owned());
889
890 if let Some(client_auth) = &st.client_auth {
892 let certs = match client_auth {
893 ClientAuthDetails::Empty { .. } => CertificateChain::default(),
894 ClientAuthDetails::Verify { certkey, .. } => CertificateChain(certkey.cert.clone()),
895 };
896 emit_certificate(&mut st.transcript, certs, cx.common);
897 }
898
899 let kx_params = tls12::decode_kx_params::<ServerKeyExchangeParams>(
901 st.suite.kx,
902 cx.common,
903 &st.server_kx.kx_params,
904 )?;
905 let maybe_skxg = match &kx_params {
906 ServerKeyExchangeParams::Ecdh(ecdh) => st
907 .config
908 .find_kx_group(ecdh.curve_params.named_group, ProtocolVersion::TLSv1_2),
909 ServerKeyExchangeParams::Dh(dh) => {
910 let ffdhe_group = dh.as_ffdhe_group();
911
912 st.config
913 .provider
914 .kx_groups
915 .iter()
916 .find(|kxg| kxg.ffdhe_group() == Some(ffdhe_group))
917 .copied()
918 }
919 };
920 let Some(skxg) = maybe_skxg else {
921 return Err(cx.common.send_fatal_alert(
922 AlertDescription::IllegalParameter,
923 PeerMisbehaved::SelectedUnofferedKxGroup,
924 ));
925 };
926 cx.common.kx_state = KxState::Start(skxg);
927 let kx = skxg.start()?;
928
929 let mut transcript = st.transcript;
931 emit_client_kx(&mut transcript, st.suite.kx, cx.common, kx.pub_key());
932 let ems_seed = st
934 .using_ems
935 .then(|| transcript.current_hash());
936
937 if let Some(ClientAuthDetails::Verify { signer, .. }) = &st.client_auth {
939 emit_certverify(&mut transcript, signer.as_ref(), cx.common)?;
940 }
941
942 let secrets = ConnectionSecrets::from_key_exchange(
946 kx,
947 kx_params.pub_key(),
948 ems_seed,
949 st.randoms,
950 suite,
951 )
952 .map_err(|err| {
953 cx.common
954 .send_fatal_alert(AlertDescription::IllegalParameter, err)
955 })?;
956 cx.common.kx_state.complete();
957
958 emit_ccs(cx.common);
960
961 st.config.key_log.log(
963 "CLIENT_RANDOM",
964 &secrets.randoms.client,
965 &secrets.master_secret,
966 );
967 cx.common
968 .start_encryption_tls12(&secrets, Side::Client);
969 cx.common
970 .record_layer
971 .start_encrypting();
972
973 emit_finished(&secrets, &mut transcript, cx.common);
975
976 if st.must_issue_new_ticket {
977 Ok(Box::new(ExpectNewTicket {
978 config: st.config,
979 secrets,
980 resuming_session: st.resuming_session,
981 session_id: st.session_id,
982 server_name: st.server_name,
983 using_ems: st.using_ems,
984 transcript,
985 resuming: false,
986 cert_verified,
987 sig_verified,
988 }))
989 } else {
990 Ok(Box::new(ExpectCcs {
991 config: st.config,
992 secrets,
993 resuming_session: st.resuming_session,
994 session_id: st.session_id,
995 server_name: st.server_name,
996 using_ems: st.using_ems,
997 transcript,
998 ticket: None,
999 resuming: false,
1000 cert_verified,
1001 sig_verified,
1002 }))
1003 }
1004 }
1005
1006 fn into_owned(self: Box<Self>) -> hs::NextState<'static> {
1007 Box::new(ExpectServerDone {
1008 config: self.config,
1009 resuming_session: self.resuming_session,
1010 session_id: self.session_id,
1011 server_name: self.server_name,
1012 randoms: self.randoms,
1013 using_ems: self.using_ems,
1014 transcript: self.transcript,
1015 suite: self.suite,
1016 server_cert: self.server_cert.into_owned(),
1017 server_kx: self.server_kx,
1018 client_auth: self.client_auth,
1019 must_issue_new_ticket: self.must_issue_new_ticket,
1020 })
1021 }
1022}
1023
1024struct ExpectNewTicket {
1025 config: Arc<ClientConfig>,
1026 secrets: ConnectionSecrets,
1027 resuming_session: Option<persist::Tls12ClientSessionValue>,
1028 session_id: SessionId,
1029 server_name: ServerName<'static>,
1030 using_ems: bool,
1031 transcript: HandshakeHash,
1032 resuming: bool,
1033 cert_verified: verify::ServerCertVerified,
1034 sig_verified: verify::HandshakeSignatureValid,
1035}
1036
1037impl State<ClientConnectionData> for ExpectNewTicket {
1038 fn handle<'m>(
1039 mut self: Box<Self>,
1040 _cx: &mut ClientContext<'_>,
1041 m: Message<'m>,
1042 ) -> hs::NextStateOrError<'m>
1043 where
1044 Self: 'm,
1045 {
1046 self.transcript.add_message(&m);
1047
1048 let nst = require_handshake_msg_move!(
1049 m,
1050 HandshakeType::NewSessionTicket,
1051 HandshakePayload::NewSessionTicket
1052 )?;
1053
1054 Ok(Box::new(ExpectCcs {
1055 config: self.config,
1056 secrets: self.secrets,
1057 resuming_session: self.resuming_session,
1058 session_id: self.session_id,
1059 server_name: self.server_name,
1060 using_ems: self.using_ems,
1061 transcript: self.transcript,
1062 ticket: Some(nst),
1063 resuming: self.resuming,
1064 cert_verified: self.cert_verified,
1065 sig_verified: self.sig_verified,
1066 }))
1067 }
1068
1069 fn into_owned(self: Box<Self>) -> hs::NextState<'static> {
1070 self
1071 }
1072}
1073
1074struct ExpectCcs {
1076 config: Arc<ClientConfig>,
1077 secrets: ConnectionSecrets,
1078 resuming_session: Option<persist::Tls12ClientSessionValue>,
1079 session_id: SessionId,
1080 server_name: ServerName<'static>,
1081 using_ems: bool,
1082 transcript: HandshakeHash,
1083 ticket: Option<NewSessionTicketPayload>,
1084 resuming: bool,
1085 cert_verified: verify::ServerCertVerified,
1086 sig_verified: verify::HandshakeSignatureValid,
1087}
1088
1089impl State<ClientConnectionData> for ExpectCcs {
1090 fn handle<'m>(
1091 self: Box<Self>,
1092 cx: &mut ClientContext<'_>,
1093 m: Message<'m>,
1094 ) -> hs::NextStateOrError<'m>
1095 where
1096 Self: 'm,
1097 {
1098 match m.payload {
1099 MessagePayload::ChangeCipherSpec(..) => {}
1100 payload => {
1101 return Err(inappropriate_message(
1102 &payload,
1103 &[ContentType::ChangeCipherSpec],
1104 ));
1105 }
1106 }
1107 cx.common.check_aligned_handshake()?;
1110
1111 cx.common
1113 .record_layer
1114 .start_decrypting();
1115
1116 Ok(Box::new(ExpectFinished {
1117 config: self.config,
1118 secrets: self.secrets,
1119 resuming_session: self.resuming_session,
1120 session_id: self.session_id,
1121 server_name: self.server_name,
1122 using_ems: self.using_ems,
1123 transcript: self.transcript,
1124 ticket: self.ticket,
1125 resuming: self.resuming,
1126 cert_verified: self.cert_verified,
1127 sig_verified: self.sig_verified,
1128 }))
1129 }
1130
1131 fn into_owned(self: Box<Self>) -> hs::NextState<'static> {
1132 self
1133 }
1134}
1135
1136struct ExpectFinished {
1137 config: Arc<ClientConfig>,
1138 resuming_session: Option<persist::Tls12ClientSessionValue>,
1139 session_id: SessionId,
1140 server_name: ServerName<'static>,
1141 using_ems: bool,
1142 transcript: HandshakeHash,
1143 ticket: Option<NewSessionTicketPayload>,
1144 secrets: ConnectionSecrets,
1145 resuming: bool,
1146 cert_verified: verify::ServerCertVerified,
1147 sig_verified: verify::HandshakeSignatureValid,
1148}
1149
1150impl ExpectFinished {
1151 fn save_session(&mut self, cx: &ClientContext<'_>) {
1153 let (mut ticket, lifetime) = match self.ticket.take() {
1156 Some(nst) => (nst.ticket, nst.lifetime_hint),
1157 None => (Arc::new(PayloadU16::empty()), 0),
1158 };
1159
1160 if ticket.0.is_empty() {
1161 if let Some(resuming_session) = &mut self.resuming_session {
1162 ticket = resuming_session.ticket();
1163 }
1164 }
1165
1166 if self.session_id.is_empty() && ticket.0.is_empty() {
1167 debug!("Session not saved: server didn't allocate id or ticket");
1168 return;
1169 }
1170
1171 let Ok(now) = self.config.current_time() else {
1172 debug!("Could not get current time");
1173 return;
1174 };
1175
1176 let session_value = persist::Tls12ClientSessionValue::new(
1177 self.secrets.suite(),
1178 self.session_id,
1179 ticket,
1180 self.secrets.master_secret(),
1181 cx.common
1182 .peer_certificates
1183 .clone()
1184 .unwrap_or_default(),
1185 &self.config.verifier,
1186 &self.config.client_auth_cert_resolver,
1187 now,
1188 lifetime,
1189 self.using_ems,
1190 );
1191
1192 self.config
1193 .resumption
1194 .store
1195 .set_tls12_session(self.server_name.clone(), session_value);
1196 }
1197}
1198
1199impl State<ClientConnectionData> for ExpectFinished {
1200 fn handle<'m>(
1201 self: Box<Self>,
1202 cx: &mut ClientContext<'_>,
1203 m: Message<'m>,
1204 ) -> hs::NextStateOrError<'m>
1205 where
1206 Self: 'm,
1207 {
1208 let mut st = *self;
1209 let finished =
1210 require_handshake_msg!(m, HandshakeType::Finished, HandshakePayload::Finished)?;
1211
1212 cx.common.check_aligned_handshake()?;
1213
1214 let vh = st.transcript.current_hash();
1216 let expect_verify_data = st.secrets.server_verify_data(&vh);
1217
1218 let _fin_verified =
1221 match ConstantTimeEq::ct_eq(&expect_verify_data[..], finished.bytes()).into() {
1222 true => verify::FinishedMessageVerified::assertion(),
1223 false => {
1224 return Err(cx
1225 .common
1226 .send_fatal_alert(AlertDescription::DecryptError, Error::DecryptError));
1227 }
1228 };
1229
1230 st.transcript.add_message(&m);
1232
1233 st.save_session(cx);
1234
1235 if st.resuming {
1236 emit_ccs(cx.common);
1237 cx.common
1238 .record_layer
1239 .start_encrypting();
1240 emit_finished(&st.secrets, &mut st.transcript, cx.common);
1241 }
1242
1243 cx.common
1244 .start_traffic(&mut cx.sendable_plaintext);
1245 Ok(Box::new(ExpectTraffic {
1246 secrets: st.secrets,
1247 _cert_verified: st.cert_verified,
1248 _sig_verified: st.sig_verified,
1249 _fin_verified,
1250 }))
1251 }
1252
1253 fn handle_decrypt_error(&self) {
1257 if self.resuming {
1258 self.config
1259 .resumption
1260 .store
1261 .remove_tls12_session(&self.server_name);
1262 }
1263 }
1264
1265 fn into_owned(self: Box<Self>) -> hs::NextState<'static> {
1266 self
1267 }
1268}
1269
1270struct ExpectTraffic {
1272 secrets: ConnectionSecrets,
1273 _cert_verified: verify::ServerCertVerified,
1274 _sig_verified: verify::HandshakeSignatureValid,
1275 _fin_verified: verify::FinishedMessageVerified,
1276}
1277
1278impl State<ClientConnectionData> for ExpectTraffic {
1279 fn handle<'m>(
1280 self: Box<Self>,
1281 cx: &mut ClientContext<'_>,
1282 m: Message<'m>,
1283 ) -> hs::NextStateOrError<'m>
1284 where
1285 Self: 'm,
1286 {
1287 match m.payload {
1288 MessagePayload::ApplicationData(payload) => cx
1289 .common
1290 .take_received_plaintext(payload),
1291 payload => {
1292 return Err(inappropriate_message(
1293 &payload,
1294 &[ContentType::ApplicationData],
1295 ));
1296 }
1297 }
1298 Ok(self)
1299 }
1300
1301 fn export_keying_material(
1302 &self,
1303 output: &mut [u8],
1304 label: &[u8],
1305 context: Option<&[u8]>,
1306 ) -> Result<(), Error> {
1307 self.secrets
1308 .export_keying_material(output, label, context);
1309 Ok(())
1310 }
1311
1312 fn extract_secrets(&self) -> Result<PartiallyExtractedSecrets, Error> {
1313 self.secrets
1314 .extract_secrets(Side::Client)
1315 }
1316
1317 fn into_external_state(self: Box<Self>) -> Result<Box<dyn KernelState + 'static>, Error> {
1318 Ok(self)
1319 }
1320
1321 fn into_owned(self: Box<Self>) -> hs::NextState<'static> {
1322 self
1323 }
1324}
1325
1326impl KernelState for ExpectTraffic {
1327 fn update_secrets(&mut self, _: Direction) -> Result<ConnectionTrafficSecrets, Error> {
1328 Err(Error::General(
1329 "TLS 1.2 connections do not support traffic secret updates".into(),
1330 ))
1331 }
1332
1333 fn handle_new_session_ticket(
1334 &mut self,
1335 _cx: &mut KernelContext<'_>,
1336 _message: &NewSessionTicketPayloadTls13,
1337 ) -> Result<(), Error> {
1338 Err(Error::General(
1339 "TLS 1.2 session tickets may not be sent once the handshake has completed".into(),
1340 ))
1341 }
1342}