tls: use session
This commit is contained in:
parent
ec0662e752
commit
404804809e
|
@ -1,226 +0,0 @@
|
||||||
use p256::{EncodedPoint, AffinePoint, ecdh::EphemeralSecret, ecdh::SharedSecret};
|
|
||||||
use aes_gcm::{Aes128Gcm, Aes256Gcm};
|
|
||||||
use chacha20poly1305::{ChaCha20Poly1305, Key};
|
|
||||||
use ccm::{Ccm, consts::*};
|
|
||||||
use aes_gcm::aes::Aes128;
|
|
||||||
use aes_gcm::{AeadInPlace, NewAead};
|
|
||||||
use generic_array::GenericArray;
|
|
||||||
use rand_core::{ RngCore, CryptoRng };
|
|
||||||
use sha2::{ Digest, Sha256, Sha384, Sha512 };
|
|
||||||
use heapless::Vec;
|
|
||||||
use hkdf::Hkdf;
|
|
||||||
|
|
||||||
use crate::Error as TlsError;
|
|
||||||
use crate::tls_packet::CipherSuite as CipherSuiteField;
|
|
||||||
use crate::key::*;
|
|
||||||
|
|
||||||
// A structure representing the block cipher and the hashes
|
|
||||||
pub(crate) enum CipherSuite {
|
|
||||||
// Handshake is still proceeding, no cipher can be produced yet,
|
|
||||||
// Though hashes still has to be prepared for deriving key later,
|
|
||||||
// This enum offers all possible hashes that could be needed
|
|
||||||
// i.e. SHA256 and SHA384
|
|
||||||
Undetermined {
|
|
||||||
sha_256: Sha256,
|
|
||||||
sha_384: Sha384,
|
|
||||||
},
|
|
||||||
|
|
||||||
// Established cipher suites
|
|
||||||
// Contains a block cipher (GCM/CCM/ChaChaPoly)
|
|
||||||
// Contains a hash function (SHA256/SHA384)
|
|
||||||
TLS_AES_128_GCM_SHA256 {
|
|
||||||
aes_128_gcm: Aes128Gcm,
|
|
||||||
sha_256: Sha256,
|
|
||||||
},
|
|
||||||
TLS_AES_256_GCM_SHA384 {
|
|
||||||
aes_256_gcm: Aes256Gcm,
|
|
||||||
sha_384: Sha384,
|
|
||||||
},
|
|
||||||
TLS_CHACHA20_POLY1305_SHA256 {
|
|
||||||
chacha20_poly1305: ChaCha20Poly1305,
|
|
||||||
sha_256: Sha256,
|
|
||||||
},
|
|
||||||
TLS_AES_128_CCM_SHA256 {
|
|
||||||
ccm: Ccm<Aes128, U16, U12>,
|
|
||||||
sha_256: Sha256,
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
impl CipherSuite {
|
|
||||||
pub(crate) fn new() -> Self {
|
|
||||||
CipherSuite::Undetermined {
|
|
||||||
sha_256: Sha256::new(),
|
|
||||||
sha_384: Sha384::new(),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Assume no PSK, establish ciphersuite along side handshake secret
|
|
||||||
// Need to update hash function before calling
|
|
||||||
pub(crate) fn establish(
|
|
||||||
self,
|
|
||||||
field: CipherSuiteField,
|
|
||||||
ecdhe_shared: SharedSecret
|
|
||||||
) -> Self {
|
|
||||||
use CipherSuiteField::*;
|
|
||||||
|
|
||||||
let (sha_256, sha_384) = {
|
|
||||||
if let CipherSuite::Undetermined {
|
|
||||||
sha_256,
|
|
||||||
sha_384,
|
|
||||||
} = self {
|
|
||||||
(sha_256, sha_384)
|
|
||||||
} else {
|
|
||||||
// TODO: Implement key change
|
|
||||||
return self;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
match field {
|
|
||||||
TLS_AES_128_GCM_SHA256 | TLS_CHACHA20_POLY1305_SHA256 |
|
|
||||||
TLS_AES_128_CCM_SHA256 => {
|
|
||||||
// Compute early_secret in HKDF, without PSK
|
|
||||||
let empty_hash = Sha256::new().chain("");
|
|
||||||
let early_secret = Hkdf::<Sha256>::new(None, &[0; 32]);
|
|
||||||
|
|
||||||
// Calculate derived secret
|
|
||||||
let derived_secret = derive_secret(
|
|
||||||
&early_secret,
|
|
||||||
"derived",
|
|
||||||
empty_hash
|
|
||||||
);
|
|
||||||
|
|
||||||
// Calculate handshake secret in HKDF
|
|
||||||
let handshake_secret = Hkdf::<Sha256>::new(
|
|
||||||
Some(&derived_secret),
|
|
||||||
ecdhe_shared.as_bytes()
|
|
||||||
);
|
|
||||||
|
|
||||||
// Calculate client_handshake_traffic_secret
|
|
||||||
let client_handshake_traffic_secret = derive_secret(
|
|
||||||
&handshake_secret,
|
|
||||||
"c hs traffic",
|
|
||||||
sha_256.clone()
|
|
||||||
);
|
|
||||||
|
|
||||||
// Calculate server_handshake_traffic_secret
|
|
||||||
let server_handshake_traffic_secret = derive_secret(
|
|
||||||
&handshake_secret,
|
|
||||||
"c hs traffic",
|
|
||||||
sha_256.clone()
|
|
||||||
);
|
|
||||||
|
|
||||||
// let client_write_key = hkdf_expand_label(
|
|
||||||
//
|
|
||||||
// );
|
|
||||||
}
|
|
||||||
_ => todo!()
|
|
||||||
}
|
|
||||||
|
|
||||||
todo!()
|
|
||||||
|
|
||||||
// // Compute HKDF
|
|
||||||
// let (hash, empty_hash, hkdf) = match field {
|
|
||||||
// TLS_AES_128_GCM_SHA256 |
|
|
||||||
// TLS_CHACHA20_POLY1305_SHA256 |
|
|
||||||
// TLS_AES_128_CCM_SHA256 => {
|
|
||||||
// (
|
|
||||||
// sha_256,
|
|
||||||
// Sha256::new().chain(""),
|
|
||||||
// Hkdf::<Sha256>::new(None, &[0; 32])
|
|
||||||
// )
|
|
||||||
// },
|
|
||||||
// TLS_AES_256_GCM_SHA384 => {
|
|
||||||
// (
|
|
||||||
// sha_384,
|
|
||||||
// Sha384::new().chain(""),
|
|
||||||
// Hkdf::<Sha384>::new(None, &[0; 48])
|
|
||||||
// )
|
|
||||||
// }
|
|
||||||
// };
|
|
||||||
|
|
||||||
// // get_derived_secret, then insert ECDHE shared secret
|
|
||||||
// let derived_secret = derive_secret(hkdf, "derived", empty_hash);
|
|
||||||
|
|
||||||
// let (key, iv) = match field {
|
|
||||||
// TLS_AES_128_GCM_SHA256 |
|
|
||||||
// TLS_CHACHA20_POLY1305_SHA256 |
|
|
||||||
// TLS_AES_128_CCM_SHA256 => {
|
|
||||||
// let hkdf = Hkdf::<Sha256>::new(
|
|
||||||
// Some(&derived_secret),
|
|
||||||
// ecdhe_shared.as_bytes()
|
|
||||||
// );
|
|
||||||
// let client_handshake_traffic_secret = derive_secret(
|
|
||||||
// hkdf,
|
|
||||||
// "c hs traffic",
|
|
||||||
// sha256.clone(),
|
|
||||||
// );
|
|
||||||
// },
|
|
||||||
// TLS_AES_256_GCM_SHA384 => {
|
|
||||||
// Hkdf::<Sha384>::new(
|
|
||||||
// Some(&derived_secret),
|
|
||||||
// ecdhe_shared.as_bytes()
|
|
||||||
// )
|
|
||||||
// }
|
|
||||||
// };
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// macro_rules! impl_cipher {
|
|
||||||
// ($($cipher_name: ident),+) => {
|
|
||||||
// impl Cipher {
|
|
||||||
// pub(crate) fn encrypt<T>(&self, rng: &mut T, associated_data: &[u8], buffer: &mut Vec<u8>) -> core::result::Result<(), TlsError>
|
|
||||||
// where
|
|
||||||
// T: RngCore + CryptoRng
|
|
||||||
// {
|
|
||||||
// // All 4 supported Ciphers use a nonce of 12 bytes
|
|
||||||
// let mut nonce_array: [u8; 12] = [0; 12];
|
|
||||||
// rng.fill_bytes(&mut nonce_array);
|
|
||||||
// use Cipher::*;
|
|
||||||
// match self {
|
|
||||||
// $(
|
|
||||||
// $cipher_name(cipher) => {
|
|
||||||
// cipher.encrypt_in_place(
|
|
||||||
// &GenericArray::from_slice(&nonce_array),
|
|
||||||
// associated_data,
|
|
||||||
// buffer
|
|
||||||
// ).map_err(
|
|
||||||
// |_| TlsError::EncryptionError
|
|
||||||
// )
|
|
||||||
// }
|
|
||||||
// )+
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
|
|
||||||
// pub(crate) fn decrypt<T>(&self, rng: &mut T, associated_data: &[u8], buffer: &mut Vec<u8>) -> core::result::Result<(), TlsError>
|
|
||||||
// where
|
|
||||||
// T: RngCore + CryptoRng
|
|
||||||
// {
|
|
||||||
// // All 4 supported Ciphers use a nonce of 12 bytes
|
|
||||||
// let mut nonce_array: [u8; 12] = [0; 12];
|
|
||||||
// rng.fill_bytes(&mut nonce_array);
|
|
||||||
// use Cipher::*;
|
|
||||||
// match self {
|
|
||||||
// $(
|
|
||||||
// $cipher_name(cipher) => {
|
|
||||||
// cipher.decrypt_in_place(
|
|
||||||
// &GenericArray::from_slice(&nonce_array),
|
|
||||||
// associated_data,
|
|
||||||
// buffer
|
|
||||||
// ).map_err(
|
|
||||||
// |_| TlsError::EncryptionError
|
|
||||||
// )
|
|
||||||
// }
|
|
||||||
// )+
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
|
|
||||||
// impl_cipher!(
|
|
||||||
// TLS_AES_128_GCM_SHA256,
|
|
||||||
// TLS_AES_256_GCM_SHA384,
|
|
||||||
// TLS_CHACHA20_POLY1305_SHA256,
|
|
||||||
// TLS_AES_128_CCM_SHA256
|
|
||||||
// );
|
|
|
@ -6,7 +6,6 @@ extern crate alloc;
|
||||||
pub mod tls;
|
pub mod tls;
|
||||||
pub mod tls_packet;
|
pub mod tls_packet;
|
||||||
pub mod parse;
|
pub mod parse;
|
||||||
pub mod cipher_suite;
|
|
||||||
pub mod buffer;
|
pub mod buffer;
|
||||||
pub mod key;
|
pub mod key;
|
||||||
pub mod session;
|
pub mod session;
|
||||||
|
|
|
@ -411,6 +411,14 @@ impl Session {
|
||||||
pub(crate) fn get_tls_state(&self) -> TlsState {
|
pub(crate) fn get_tls_state(&self) -> TlsState {
|
||||||
self.state
|
self.state
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub(crate) fn has_completed_handshake(&self) -> bool {
|
||||||
|
self.state == TlsState::CONNECTED
|
||||||
|
}
|
||||||
|
|
||||||
|
pub(crate) fn receive_change_cipher_spec(&mut self) {
|
||||||
|
self.changed_cipher_spec = true;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, PartialEq, Eq, Clone, Copy)]
|
#[derive(Debug, PartialEq, Eq, Clone, Copy)]
|
||||||
|
|
127
src/tls.rs
127
src/tls.rs
|
@ -35,7 +35,6 @@ use alloc::vec::{ self, Vec };
|
||||||
use crate::Error as TlsError;
|
use crate::Error as TlsError;
|
||||||
use crate::tls_packet::*;
|
use crate::tls_packet::*;
|
||||||
use crate::parse::parse_tls_repr;
|
use crate::parse::parse_tls_repr;
|
||||||
use crate::cipher_suite::CipherSuite;
|
|
||||||
use crate::buffer::TlsBuffer;
|
use crate::buffer::TlsBuffer;
|
||||||
use crate::session::{Session, TlsRole};
|
use crate::session::{Session, TlsRole};
|
||||||
|
|
||||||
|
@ -55,14 +54,8 @@ pub(crate) enum TlsState {
|
||||||
// TODO: Group up all session_specific parameters into a separate structure
|
// TODO: Group up all session_specific parameters into a separate structure
|
||||||
pub struct TlsSocket<R: 'static + RngCore + CryptoRng>
|
pub struct TlsSocket<R: 'static + RngCore + CryptoRng>
|
||||||
{
|
{
|
||||||
state: RefCell<TlsState>,
|
|
||||||
tcp_handle: SocketHandle,
|
tcp_handle: SocketHandle,
|
||||||
rng: R,
|
rng: R,
|
||||||
secret: RefCell<Option<EphemeralSecret>>, // Used enum Option to allow later init
|
|
||||||
session_id: RefCell<Option<[u8; 32]>>, // init session specific field later
|
|
||||||
received_change_cipher_spec: RefCell<Option<bool>>,
|
|
||||||
cipher: RefCell<Option<CipherSuite>>,
|
|
||||||
handshake_sha256: RefCell<Sha256>,
|
|
||||||
session: RefCell<Session>,
|
session: RefCell<Session>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -79,14 +72,8 @@ impl<R: RngCore + CryptoRng> TlsSocket<R> {
|
||||||
let tcp_socket = TcpSocket::new(rx_buffer, tx_buffer);
|
let tcp_socket = TcpSocket::new(rx_buffer, tx_buffer);
|
||||||
let tcp_handle = sockets.add(tcp_socket);
|
let tcp_handle = sockets.add(tcp_socket);
|
||||||
TlsSocket {
|
TlsSocket {
|
||||||
state: RefCell::new(TlsState::START),
|
|
||||||
tcp_handle,
|
tcp_handle,
|
||||||
rng,
|
rng,
|
||||||
secret: RefCell::new(None),
|
|
||||||
session_id: RefCell::new(None),
|
|
||||||
received_change_cipher_spec: RefCell::new(None),
|
|
||||||
cipher: RefCell::new(None),
|
|
||||||
handshake_sha256: RefCell::new(Sha256::new()),
|
|
||||||
session: RefCell::new(
|
session: RefCell::new(
|
||||||
Session::new(TlsRole::Client)
|
Session::new(TlsRole::Client)
|
||||||
),
|
),
|
||||||
|
@ -130,8 +117,7 @@ impl<R: RngCore + CryptoRng> TlsSocket<R> {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Handle TLS handshake through TLS states
|
// Handle TLS handshake through TLS states
|
||||||
let state = self.state.clone().into_inner();
|
match self.session.borrow().get_tls_state() {
|
||||||
match state {
|
|
||||||
// Initiate TLS handshake
|
// Initiate TLS handshake
|
||||||
TlsState::START => {
|
TlsState::START => {
|
||||||
// Prepare field that is randomised,
|
// Prepare field that is randomised,
|
||||||
|
@ -142,7 +128,7 @@ impl<R: RngCore + CryptoRng> TlsSocket<R> {
|
||||||
self.rng.fill_bytes(&mut random);
|
self.rng.fill_bytes(&mut random);
|
||||||
self.rng.fill_bytes(&mut session_id);
|
self.rng.fill_bytes(&mut session_id);
|
||||||
let repr = TlsRepr::new()
|
let repr = TlsRepr::new()
|
||||||
.client_hello(&ecdh_secret, random, session_id);
|
.client_hello(&ecdh_secret, random, session_id.clone());
|
||||||
|
|
||||||
// Update hash function with client hello handshake
|
// Update hash function with client hello handshake
|
||||||
let mut array = [0; 2048];
|
let mut array = [0; 2048];
|
||||||
|
@ -150,29 +136,27 @@ impl<R: RngCore + CryptoRng> TlsSocket<R> {
|
||||||
buffer.enqueue_tls_repr(repr)?;
|
buffer.enqueue_tls_repr(repr)?;
|
||||||
let slice: &[u8] = buffer.into();
|
let slice: &[u8] = buffer.into();
|
||||||
|
|
||||||
// Update hash by handshake
|
// Send the packet
|
||||||
// Update with entire packet except the record layer
|
|
||||||
{
|
|
||||||
self.handshake_sha256.borrow_mut().update(&slice[5..]);
|
|
||||||
}
|
|
||||||
self.send_tls_slice(sockets, slice)?;
|
self.send_tls_slice(sockets, slice)?;
|
||||||
|
|
||||||
// Store session settings, i.e. secret, session_id
|
// Update TLS session
|
||||||
self.secret.replace(Some(ecdh_secret));
|
self.session.borrow_mut().client_update_for_ch(
|
||||||
self.session_id.replace(Some(session_id));
|
ecdh_secret,
|
||||||
self.received_change_cipher_spec.replace(Some(false));
|
session_id,
|
||||||
|
&slice[5..]
|
||||||
// Update the TLS state
|
);
|
||||||
self.state.replace(TlsState::WAIT_SH);
|
|
||||||
},
|
},
|
||||||
|
|
||||||
// TLS Client wait for Server Hello
|
// TLS Client wait for Server Hello
|
||||||
// No need to send anything
|
// No need to send anything
|
||||||
TlsState::WAIT_SH => {},
|
TlsState::WAIT_SH => {},
|
||||||
|
|
||||||
// TLS Client wait for certificate from TLS server
|
// TLS Client wait for certificate from TLS server
|
||||||
// No need to send anything
|
// No need to send anything
|
||||||
// Note: TLS server should normall send SH alongside EE
|
// Note: TLS server should normally send SH alongside EE
|
||||||
// TLS client should jump from WAIT_SH directly to WAIT_CERT_CR directly.
|
// TLS client should jump from WAIT_SH directly to WAIT_CERT_CR directly.
|
||||||
TlsState::WAIT_EE => {},
|
TlsState::WAIT_EE => {},
|
||||||
|
|
||||||
_ => todo!()
|
_ => todo!()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -191,13 +175,11 @@ impl<R: RngCore + CryptoRng> TlsSocket<R> {
|
||||||
self.process(repr)?;
|
self.process(repr)?;
|
||||||
}
|
}
|
||||||
|
|
||||||
Ok(self.state.clone().into_inner() == TlsState::CONNECTED)
|
Ok(self.session.borrow().has_completed_handshake())
|
||||||
}
|
}
|
||||||
|
|
||||||
// Process TLS ingress during handshake
|
// Process TLS ingress during handshake
|
||||||
fn process(&self, repr: TlsRepr) -> Result<()> {
|
fn process(&self, repr: TlsRepr) -> Result<()> {
|
||||||
let state = self.state.clone().into_inner();
|
|
||||||
|
|
||||||
// Change_cipher_spec check:
|
// Change_cipher_spec check:
|
||||||
// Must receive CCS before recv peer's FINISH message
|
// Must receive CCS before recv peer's FINISH message
|
||||||
// i.e. Must happen after START and before CONNECTED
|
// i.e. Must happen after START and before CONNECTED
|
||||||
|
@ -205,11 +187,11 @@ impl<R: RngCore + CryptoRng> TlsSocket<R> {
|
||||||
// CCS message only exist for compatibility reason,
|
// CCS message only exist for compatibility reason,
|
||||||
// Drop the message and update `received_change_cipher_spec`
|
// Drop the message and update `received_change_cipher_spec`
|
||||||
if repr.is_change_cipher_spec() {
|
if repr.is_change_cipher_spec() {
|
||||||
self.received_change_cipher_spec.replace(Some(true));
|
self.session.borrow_mut().receive_change_cipher_spec();
|
||||||
return Ok(())
|
return Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
match state {
|
match self.session.borrow().get_tls_state() {
|
||||||
// During WAIT_SH for a TLS client, client should wait for ServerHello
|
// During WAIT_SH for a TLS client, client should wait for ServerHello
|
||||||
TlsState::WAIT_SH => {
|
TlsState::WAIT_SH => {
|
||||||
// Legacy_protocol must be TLS 1.2
|
// Legacy_protocol must be TLS 1.2
|
||||||
|
@ -232,25 +214,37 @@ impl<R: RngCore + CryptoRng> TlsSocket<R> {
|
||||||
// supported_version: Must be TLS 1.3
|
// supported_version: Must be TLS 1.3
|
||||||
// key_share: Store key, must be in secp256r1
|
// key_share: Store key, must be in secp256r1
|
||||||
// (TODO: Support other key shares ^)
|
// (TODO: Support other key shares ^)
|
||||||
|
|
||||||
|
// "Cache" for ECDHE server public info
|
||||||
|
let mut server_public: Option<EncodedPoint> = None;
|
||||||
|
let mut selected_cipher: Option<CipherSuite> = None;
|
||||||
|
|
||||||
|
// Process the handshake data within ServerHello
|
||||||
let handshake_data = &repr.handshake.as_ref().unwrap().handshake_data;
|
let handshake_data = &repr.handshake.as_ref().unwrap().handshake_data;
|
||||||
if let HandshakeData::ServerHello(server_hello) = handshake_data {
|
if let HandshakeData::ServerHello(server_hello) = handshake_data {
|
||||||
|
|
||||||
// Check random: Cannot be SHA-256 of "HelloRetryRequest"
|
// Check random: Cannot be SHA-256 of "HelloRetryRequest"
|
||||||
if server_hello.random == HRR_RANDOM {
|
if server_hello.random == HRR_RANDOM {
|
||||||
// Abort communication
|
// Abort communication
|
||||||
todo!()
|
todo!()
|
||||||
}
|
}
|
||||||
|
|
||||||
// Check session_id_echo
|
// Check session_id_echo
|
||||||
// The socket should have a session_id after moving from START state
|
// The socket should have a session_id after moving from START state
|
||||||
if self.session_id.clone().into_inner().unwrap() != server_hello.session_id_echo {
|
if !self.session.borrow().verify_session_id_echo(server_hello.session_id_echo) {
|
||||||
// Abort communication
|
// Abort communication
|
||||||
todo!()
|
todo!()
|
||||||
}
|
}
|
||||||
// Store the cipher suite
|
|
||||||
let selected_cipher = server_hello.cipher_suite;
|
// Note the selected cipher suite
|
||||||
|
selected_cipher.replace(server_hello.cipher_suite);
|
||||||
|
|
||||||
|
// TLSv13 forbidden key compression
|
||||||
if server_hello.compression_method != 0 {
|
if server_hello.compression_method != 0 {
|
||||||
// Abort communciation
|
// Abort communciation
|
||||||
todo!()
|
todo!()
|
||||||
}
|
}
|
||||||
|
|
||||||
for extension in server_hello.extensions.iter() {
|
for extension in server_hello.extensions.iter() {
|
||||||
if extension.extension_type == ExtensionType::SupportedVersions {
|
if extension.extension_type == ExtensionType::SupportedVersions {
|
||||||
if let ExtensionData::SupportedVersions(
|
if let ExtensionData::SupportedVersions(
|
||||||
|
@ -285,43 +279,11 @@ impl<R: RngCore + CryptoRng> TlsSocket<R> {
|
||||||
// It is surely from secp256r1, no other groups are permitted
|
// It is surely from secp256r1, no other groups are permitted
|
||||||
// Convert untagged bytes into encoded point on p256 eliptic curve
|
// Convert untagged bytes into encoded point on p256 eliptic curve
|
||||||
// Slice the first byte out of the bytes
|
// Slice the first byte out of the bytes
|
||||||
let server_public = EncodedPoint::from_untagged_bytes(
|
server_public.replace(
|
||||||
|
EncodedPoint::from_untagged_bytes(
|
||||||
GenericArray::from_slice(&server_share.key_exchange[1..])
|
GenericArray::from_slice(&server_share.key_exchange[1..])
|
||||||
|
)
|
||||||
);
|
);
|
||||||
// TODO: Handle improper shared key
|
|
||||||
// Right now is causes a panic, only socket abort is needed
|
|
||||||
let secret = self.secret.replace(None);
|
|
||||||
let shared = secret.unwrap()
|
|
||||||
.diffie_hellman(&server_public)
|
|
||||||
.expect("Unsupported key");
|
|
||||||
// let cipher = match selected_cipher {
|
|
||||||
// CipherSuite::TLS_AES_128_GCM_SHA256 => {
|
|
||||||
// Cipher::TLS_AES_128_GCM_SHA256(
|
|
||||||
// todo!()
|
|
||||||
// )
|
|
||||||
// },
|
|
||||||
// CipherSuite::TLS_AES_256_GCM_SHA384 => {
|
|
||||||
// Cipher::TLS_AES_256_GCM_SHA384(
|
|
||||||
// Aes256Gcm::new(shared.as_bytes())
|
|
||||||
// )
|
|
||||||
// },
|
|
||||||
// CipherSuite::TLS_CHACHA20_POLY1305_SHA256 => {
|
|
||||||
// Cipher::TLS_CHACHA20_POLY1305_SHA256(
|
|
||||||
// ChaCha20Poly1305::new(shared.as_bytes())
|
|
||||||
// )
|
|
||||||
// },
|
|
||||||
// CipherSuite::TLS_AES_128_CCM_SHA256 => {
|
|
||||||
// Cipher::TLS_AES_128_CCM_SHA256(
|
|
||||||
// todo!()
|
|
||||||
// )
|
|
||||||
// },
|
|
||||||
// // CCM_8 is not supported
|
|
||||||
// // TODO: Abort communication
|
|
||||||
// CipherSuite::TLS_AES_128_CCM_8_SHA256 => {
|
|
||||||
// todo!()
|
|
||||||
// }
|
|
||||||
// };
|
|
||||||
// self.cipher.replace(Some(cipher));
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -331,21 +293,24 @@ impl<R: RngCore + CryptoRng> TlsSocket<R> {
|
||||||
todo!()
|
todo!()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Check that both selected_cipher and server_public were received
|
||||||
|
if selected_cipher.is_none() || server_public.is_none() {
|
||||||
|
// Abort communication
|
||||||
|
todo!()
|
||||||
|
}
|
||||||
|
|
||||||
// This is indeed a desirable ServerHello TLS repr
|
// This is indeed a desirable ServerHello TLS repr
|
||||||
// Reprocess ServerHello into a slice
|
// Reprocess ServerHello into a slice
|
||||||
// Update SHA256 hasher with the slice
|
// Update session with required parameter
|
||||||
let mut array = [0; 2048];
|
let mut array = [0; 2048];
|
||||||
let mut buffer = TlsBuffer::new(&mut array);
|
let mut buffer = TlsBuffer::new(&mut array);
|
||||||
buffer.enqueue_tls_repr(repr);
|
buffer.enqueue_tls_repr(repr);
|
||||||
let slice: &[u8] = buffer.into();
|
let slice: &[u8] = buffer.into();
|
||||||
{
|
self.session.borrow_mut().client_update_for_sh(
|
||||||
self.handshake_sha256
|
selected_cipher.unwrap(),
|
||||||
.borrow_mut()
|
server_public.unwrap(),
|
||||||
.update(&slice[5..]);
|
&slice[5..]
|
||||||
}
|
);
|
||||||
|
|
||||||
// Update TLS session state
|
|
||||||
self.state.replace(TlsState::WAIT_EE);
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue