in neqo-transport/src/connection/mod.rs [2888:2935]
fn handshake(
&mut self,
now: Instant,
packet_version: Version,
space: PacketNumberSpace,
data: Option<&[u8]>,
) -> Res<()> {
qtrace!("[{self}] Handshake space={space} data={data:0x?}");
let was_authentication_pending =
*self.crypto.tls.state() == HandshakeState::AuthenticationPending;
let try_update = data.is_some();
match self.crypto.handshake(now, space, data)? {
HandshakeState::Authenticated(_) | HandshakeState::InProgress => (),
HandshakeState::AuthenticationPending => {
if !was_authentication_pending {
self.events.authentication_needed();
}
}
HandshakeState::EchFallbackAuthenticationPending(public_name) => self
.events
.ech_fallback_authentication_needed(public_name.clone()),
HandshakeState::Complete(_) => {
if !self.state.connected() {
self.set_connected(now)?;
}
}
_ => {
qerror!("Crypto state should not be new or failed after successful handshake");
return Err(Error::CryptoError(neqo_crypto::Error::InternalError));
}
}
// There is a chance that this could be called less often, but getting the
// conditions right is a little tricky, so call whenever CRYPTO data is used.
if try_update {
self.compatible_upgrade(packet_version)?;
// We have transport parameters, it's go time.
if self.tps.borrow().remote.is_some() {
self.set_initial_limits();
}
if self.crypto.install_keys(self.role)? {
self.saved_datagrams.make_available(Epoch::Handshake);
}
}
Ok(())
}