Adding encryption algorithm and removing unnecesssary info fields (#114)
This commit is contained in:
@@ -35,7 +35,6 @@ pub trait KeyExchange<D: Hash, KeyFormat: KeyPair> {
|
||||
server_s_sk: KeyFormat::Repr,
|
||||
id_u: Vec<u8>,
|
||||
id_s: Vec<u8>,
|
||||
info: Vec<u8>,
|
||||
e_info: Vec<u8>,
|
||||
) -> Result<(Vec<u8>, Self::KE2State, Self::KE2Message), ProtocolError>;
|
||||
|
||||
@@ -48,15 +47,13 @@ pub trait KeyExchange<D: Hash, KeyFormat: KeyPair> {
|
||||
client_s_sk: KeyFormat::Repr,
|
||||
id_u: Vec<u8>,
|
||||
id_s: Vec<u8>,
|
||||
info: Vec<u8>,
|
||||
e_info: Vec<u8>,
|
||||
) -> Result<(Vec<u8>, Vec<u8>, Vec<u8>, Self::KE3Message), ProtocolError>;
|
||||
) -> Result<(Vec<u8>, Vec<u8>, Self::KE3Message), ProtocolError>;
|
||||
|
||||
#[allow(clippy::type_complexity)]
|
||||
fn finish_ke(
|
||||
ke3_message: Self::KE3Message,
|
||||
ke2_state: &Self::KE2State,
|
||||
) -> Result<(Vec<u8>, Vec<u8>, Vec<u8>), ProtocolError>;
|
||||
) -> Result<Vec<u8>, ProtocolError>;
|
||||
|
||||
fn ke1_state_size() -> usize;
|
||||
|
||||
|
||||
@@ -35,6 +35,8 @@ static STR_3DH: &[u8] = b"3DH keys";
|
||||
static STR_CLIENT_MAC: &[u8] = b"client mac";
|
||||
static STR_HANDSHAKE_SECRET: &[u8] = b"handshake secret";
|
||||
static STR_SERVER_MAC: &[u8] = b"server mac";
|
||||
static STR_SERVER_ENC: &[u8] = b"server enc";
|
||||
static STR_ENCRYPTION_PAD: &[u8] = b"encryption pad";
|
||||
static STR_SESSION_SECRET: &[u8] = b"session secret";
|
||||
static STR_OPAQUE: &[u8] = b"OPAQUE ";
|
||||
|
||||
@@ -91,7 +93,6 @@ impl<D: Hash, KeyFormat: KeyPair> KeyExchange<D, KeyFormat> for TripleDH {
|
||||
server_s_sk: KeyFormat::Repr,
|
||||
id_u: Vec<u8>,
|
||||
id_s: Vec<u8>,
|
||||
info: Vec<u8>,
|
||||
e_info: Vec<u8>,
|
||||
) -> Result<(Vec<u8>, Self::KE2State, Self::KE2Message), ProtocolError> {
|
||||
let server_e_kp = KeyFormat::generate_random(rng)?;
|
||||
@@ -101,7 +102,7 @@ impl<D: Hash, KeyFormat: KeyPair> KeyExchange<D, KeyFormat> for TripleDH {
|
||||
server_nonce_bytes.into()
|
||||
};
|
||||
|
||||
let (session_secret, km2, km3) = derive_3dh_keys::<KeyFormat, D>(
|
||||
let (session_secret, km2, ke2, km3) = derive_3dh_keys::<KeyFormat, D>(
|
||||
TripleDHComponents {
|
||||
pk1: ke1_message.client_e_pk.clone(),
|
||||
sk1: server_e_kp.private().clone(),
|
||||
@@ -116,6 +117,17 @@ impl<D: Hash, KeyFormat: KeyPair> KeyExchange<D, KeyFormat> for TripleDH {
|
||||
&id_s,
|
||||
)?;
|
||||
|
||||
// Compute encryption of e_info
|
||||
let h = Hkdf::<D>::new(None, &ke2);
|
||||
let mut encryption_pad = vec![0u8; e_info.len()];
|
||||
h.expand(STR_ENCRYPTION_PAD, &mut encryption_pad)
|
||||
.map_err(|_| InternalPakeError::HkdfError)?;
|
||||
let ciphertext: Vec<u8> = encryption_pad
|
||||
.iter()
|
||||
.zip(e_info.iter())
|
||||
.map(|(&x1, &x2)| x1 ^ x2)
|
||||
.collect();
|
||||
|
||||
let mut hasher = D::new();
|
||||
hasher.update(&l1_bytes);
|
||||
let hashed_l1 = hasher.finalize();
|
||||
@@ -124,9 +136,8 @@ impl<D: Hash, KeyFormat: KeyPair> KeyExchange<D, KeyFormat> for TripleDH {
|
||||
&hashed_l1[..],
|
||||
&l2_bytes[..],
|
||||
&server_nonce[..],
|
||||
&serialize(&info, 2),
|
||||
&server_e_kp.public().to_arr(),
|
||||
&serialize(&e_info, 2),
|
||||
&serialize(&ciphertext, 2),
|
||||
]
|
||||
.concat();
|
||||
|
||||
@@ -153,9 +164,8 @@ impl<D: Hash, KeyFormat: KeyPair> KeyExchange<D, KeyFormat> for TripleDH {
|
||||
},
|
||||
KE2Message {
|
||||
server_nonce,
|
||||
info,
|
||||
server_e_pk: server_e_kp.public().clone(),
|
||||
e_info,
|
||||
e_info: ciphertext,
|
||||
mac,
|
||||
},
|
||||
))
|
||||
@@ -170,10 +180,8 @@ impl<D: Hash, KeyFormat: KeyPair> KeyExchange<D, KeyFormat> for TripleDH {
|
||||
client_s_sk: KeyFormat::Repr,
|
||||
id_u: Vec<u8>,
|
||||
id_s: Vec<u8>,
|
||||
info: Vec<u8>,
|
||||
e_info: Vec<u8>,
|
||||
) -> Result<(Vec<u8>, Vec<u8>, Vec<u8>, Self::KE3Message), ProtocolError> {
|
||||
let (session_secret, km2, km3) = derive_3dh_keys::<KeyFormat, D>(
|
||||
) -> Result<(Vec<u8>, Vec<u8>, Self::KE3Message), ProtocolError> {
|
||||
let (session_secret, km2, ke2, km3) = derive_3dh_keys::<KeyFormat, D>(
|
||||
TripleDHComponents {
|
||||
pk1: ke2_message.server_e_pk.clone(),
|
||||
sk1: ke1_state.client_e_sk.clone(),
|
||||
@@ -214,24 +222,25 @@ impl<D: Hash, KeyFormat: KeyPair> KeyExchange<D, KeyFormat> for TripleDH {
|
||||
hasher2.update(ke2_message.mac.to_vec());
|
||||
let hashed_transcript = hasher2.finalize();
|
||||
|
||||
let transcript_with_ke3 = [
|
||||
hashed_transcript.to_vec(),
|
||||
serialize(&info, 2),
|
||||
serialize(&e_info, 2),
|
||||
]
|
||||
.concat();
|
||||
|
||||
let mut client_mac =
|
||||
Hmac::<D>::new_varkey(&km3).map_err(|_| InternalPakeError::HmacError)?;
|
||||
client_mac.update(&transcript_with_ke3);
|
||||
client_mac.update(&hashed_transcript);
|
||||
|
||||
// Compute decryption of e_info
|
||||
let h = Hkdf::<D>::new(None, &ke2);
|
||||
let mut encryption_pad = vec![0u8; ke2_message.e_info.len()];
|
||||
h.expand(STR_ENCRYPTION_PAD, &mut encryption_pad)
|
||||
.map_err(|_| InternalPakeError::HkdfError)?;
|
||||
let plaintext: Vec<u8> = encryption_pad
|
||||
.iter()
|
||||
.zip(ke2_message.e_info.iter())
|
||||
.map(|(&x1, &x2)| x1 ^ x2)
|
||||
.collect();
|
||||
|
||||
Ok((
|
||||
ke2_message.info,
|
||||
ke2_message.e_info, // TODO: need to decrypt
|
||||
plaintext,
|
||||
session_secret.to_vec(),
|
||||
KE3Message {
|
||||
info,
|
||||
e_info,
|
||||
mac: client_mac.finalize().into_bytes(),
|
||||
},
|
||||
))
|
||||
@@ -241,15 +250,10 @@ impl<D: Hash, KeyFormat: KeyPair> KeyExchange<D, KeyFormat> for TripleDH {
|
||||
fn finish_ke(
|
||||
ke3_message: Self::KE3Message,
|
||||
ke2_state: &Self::KE2State,
|
||||
) -> Result<(Vec<u8>, Vec<u8>, Vec<u8>), ProtocolError> {
|
||||
let transcript_with_ke3 = [
|
||||
ke2_state.hashed_transcript.to_vec(),
|
||||
ke3_message.to_bytes_without_mac(),
|
||||
]
|
||||
.concat();
|
||||
) -> Result<Vec<u8>, ProtocolError> {
|
||||
let mut client_mac =
|
||||
Hmac::<D>::new_varkey(&ke2_state.km3).map_err(|_| InternalPakeError::HmacError)?;
|
||||
client_mac.update(&transcript_with_ke3);
|
||||
client_mac.update(&ke2_state.hashed_transcript);
|
||||
|
||||
if ke3_message.mac != client_mac.finalize().into_bytes() {
|
||||
return Err(ProtocolError::VerificationError(
|
||||
@@ -257,11 +261,7 @@ impl<D: Hash, KeyFormat: KeyPair> KeyExchange<D, KeyFormat> for TripleDH {
|
||||
));
|
||||
}
|
||||
|
||||
Ok((
|
||||
ke3_message.info,
|
||||
ke3_message.e_info, // TODO: need to decrypt
|
||||
ke2_state.session_secret.to_vec(),
|
||||
))
|
||||
Ok(ke2_state.session_secret.to_vec())
|
||||
}
|
||||
|
||||
fn ke1_state_size() -> usize {
|
||||
@@ -360,7 +360,6 @@ pub struct KE2State<HashLen: ArrayLength<u8>> {
|
||||
/// The second key exchange message
|
||||
pub struct KE2Message<HashLen: ArrayLength<u8>, KeyFormat: KeyPair> {
|
||||
server_nonce: GenericArray<u8, NonceLen>,
|
||||
info: Vec<u8>,
|
||||
server_e_pk: KeyFormat::Repr,
|
||||
e_info: Vec<u8>,
|
||||
mac: GenericArray<u8, HashLen>,
|
||||
@@ -401,7 +400,6 @@ impl<HashLen: ArrayLength<u8>, KeyFormat: KeyPair> KE2Message<HashLen, KeyFormat
|
||||
fn to_bytes_without_mac(&self) -> Vec<u8> {
|
||||
[
|
||||
&self.server_nonce[..],
|
||||
&serialize(&self.info, 2),
|
||||
&self.server_e_pk.to_arr(),
|
||||
&serialize(&self.e_info, 2),
|
||||
]
|
||||
@@ -416,15 +414,16 @@ impl<HashLen: ArrayLength<u8>, KeyFormat: KeyPair> TryFrom<&[u8]>
|
||||
|
||||
fn try_from(input: &[u8]) -> Result<Self, Self::Error> {
|
||||
let checked_nonce = check_slice_size_atleast(input, NONCE_LEN, "ke2_message nonce")?;
|
||||
let (info, remainder) = tokenize(&checked_nonce[NONCE_LEN..], 2)?;
|
||||
let checked_server_e_pk =
|
||||
check_slice_size_atleast(&remainder, KEY_LEN, "ke2_message server_e_pk")?;
|
||||
let checked_server_e_pk = check_slice_size_atleast(
|
||||
&checked_nonce[NONCE_LEN..],
|
||||
KEY_LEN,
|
||||
"ke2_message server_e_pk",
|
||||
)?;
|
||||
let (e_info, remainder) = tokenize(&checked_server_e_pk[KEY_LEN..], 2)?;
|
||||
let checked_mac = check_slice_size(&remainder, HashLen::to_usize(), "ke1_message mac")?;
|
||||
|
||||
Ok(Self {
|
||||
server_nonce: GenericArray::clone_from_slice(&checked_nonce[..NONCE_LEN]),
|
||||
info,
|
||||
server_e_pk: KeyFormat::Repr::from_bytes(&checked_server_e_pk[..KEY_LEN])?,
|
||||
e_info,
|
||||
mac: GenericArray::clone_from_slice(&checked_mac),
|
||||
@@ -442,29 +441,22 @@ struct TripleDHComponents<KeyFormat: KeyPair> {
|
||||
sk3: KeyFormat::Repr,
|
||||
}
|
||||
|
||||
// Consists of a shared secret, followed by two mac keys: (session_secret, km2, km3)
|
||||
// Consists of a shared secret, followed by two mac keys and an encryption key: (session_secret, km2, ke2, km3)
|
||||
type TripleDHDerivationResult<D> = (
|
||||
GenericArray<u8, <D as FixedOutput>::OutputSize>,
|
||||
GenericArray<u8, <D as FixedOutput>::OutputSize>,
|
||||
GenericArray<u8, <D as FixedOutput>::OutputSize>,
|
||||
GenericArray<u8, <D as FixedOutput>::OutputSize>,
|
||||
);
|
||||
|
||||
/// The third key exchange message
|
||||
pub struct KE3Message<HashLen: ArrayLength<u8>> {
|
||||
info: Vec<u8>,
|
||||
e_info: Vec<u8>,
|
||||
mac: GenericArray<u8, HashLen>,
|
||||
}
|
||||
|
||||
impl<HashLen: ArrayLength<u8>> ToBytes for KE3Message<HashLen> {
|
||||
fn to_bytes(&self) -> Vec<u8> {
|
||||
[self.to_bytes_without_mac(), self.mac.to_vec()].concat()
|
||||
}
|
||||
}
|
||||
|
||||
impl<HashLen: ArrayLength<u8>> KE3Message<HashLen> {
|
||||
fn to_bytes_without_mac(&self) -> Vec<u8> {
|
||||
[serialize(&self.info, 2), serialize(&self.e_info, 2)].concat()
|
||||
self.mac.to_vec()
|
||||
}
|
||||
}
|
||||
|
||||
@@ -472,13 +464,9 @@ impl<HashLen: ArrayLength<u8>> TryFrom<&[u8]> for KE3Message<HashLen> {
|
||||
type Error = PakeError;
|
||||
|
||||
fn try_from(bytes: &[u8]) -> Result<Self, Self::Error> {
|
||||
let (info, remainder) = tokenize(&bytes, 2)?;
|
||||
let (e_info, remainder) = tokenize(&remainder, 2)?;
|
||||
let checked_bytes = check_slice_size(&remainder, KEY_LEN, "ke3_message")?;
|
||||
let checked_bytes = check_slice_size(&bytes, KEY_LEN, "ke3_message")?;
|
||||
|
||||
Ok(Self {
|
||||
info,
|
||||
e_info,
|
||||
mac: GenericArray::clone_from_slice(&checked_bytes),
|
||||
})
|
||||
}
|
||||
@@ -520,6 +508,12 @@ fn derive_3dh_keys<KeyFormat: KeyPair, D: Hash>(
|
||||
b"",
|
||||
<D as Digest>::OutputSize::to_usize(),
|
||||
)?;
|
||||
let ke2 = hkdf_expand_label::<D>(
|
||||
&handshake_secret,
|
||||
&STR_SERVER_ENC,
|
||||
b"",
|
||||
<D as Digest>::OutputSize::to_usize(),
|
||||
)?;
|
||||
let km3 = hkdf_expand_label::<D>(
|
||||
&handshake_secret,
|
||||
&STR_CLIENT_MAC,
|
||||
@@ -530,6 +524,7 @@ fn derive_3dh_keys<KeyFormat: KeyPair, D: Hash>(
|
||||
Ok((
|
||||
GenericArray::clone_from_slice(&session_secret),
|
||||
GenericArray::clone_from_slice(&km2),
|
||||
GenericArray::clone_from_slice(&ke2),
|
||||
GenericArray::clone_from_slice(&km3),
|
||||
))
|
||||
}
|
||||
|
||||
+8
-9
@@ -15,8 +15,9 @@
|
||||
//! * a finite cyclic group along with a point representation,
|
||||
//! * a keypair type,
|
||||
//! * a key exchange protocol,
|
||||
//! * a hashing function, and
|
||||
//! * a slow hashing function.
|
||||
//! * a hashing function,
|
||||
//! * a slow hashing function, and
|
||||
//! * an authenticated encryption algorithm.
|
||||
//!
|
||||
//! We will use the following choices in this example:
|
||||
//! ```
|
||||
@@ -721,18 +722,16 @@
|
||||
//!
|
||||
//! A key exchange protocol typically supports the passing of data between the two parties before the exchange is complete, so as to bind the integrity
|
||||
//! and/or confidentiality of application-specific data to the security of the key exchange. During the login phase, the client and server can pass
|
||||
//! additional data alongside the first three messages of the protocol, with confidential data being supported for the second and third messages.
|
||||
//! additional data alongside the first two messages of the protocol, with confidential data being supported for the second message.
|
||||
//!
|
||||
//! The following three messages support passing of additional data:
|
||||
//! - The first login message, where the client can populate [ClientLoginStartParameters::WithInfo] with plaintext additional data, and
|
||||
//! the server can retrieve using the `plain_info` field of [ServerLoginStartResult].
|
||||
//! - The second login message, where the server can populate [ServerLoginStartParameters::WithInfo] with plaintext and confidential additional data,
|
||||
//! and the client can retrieve using the `plain_info` and `confidential_info` fields of [ClientLoginFinishResult].
|
||||
//! - The third login message, where the client can populate [ClientLoginFinishParameters::WithInfo] with plaintext and confidential
|
||||
//! additional info, and the server can retrieve using the `plain_info` and `confidential_info` fields of [ServerLoginFinishResult].
|
||||
//! - The second login message, where the server can populate [ServerLoginStartParameters::WithInfo] with confidential additional data,
|
||||
//! and the client can retrieve using the `confidential_info` field of [ClientLoginFinishResult].
|
||||
//!
|
||||
//! The `WithInfoAndIdentifiers` variant of each of these enums representing optional parameters can be used to specify these fields in addition to
|
||||
//! [custom identifiers](#custom-identifiers), with the ordering of the fields as `WithInfoAndIdentifiers(plain_info, confidential_info, username, server_name)`.
|
||||
//! For the second login message, the `WithInfoAndIdentifiers` variant can be used to specify these fields in addition to
|
||||
//! [custom identifiers](#custom-identifiers), with the ordering of the fields as `WithInfoAndIdentifiers(confidential_info, username, server_name)`.
|
||||
//!
|
||||
//!
|
||||
|
||||
|
||||
+33
-61
@@ -503,14 +503,8 @@ pub struct ClientLoginStartResult<CS: CipherSuite> {
|
||||
|
||||
/// Optional parameters for client login finish
|
||||
pub enum ClientLoginFinishParameters {
|
||||
/// Specifying a plaintext info and confidential info field that will be sent to the server
|
||||
WithInfo(Vec<u8>, Vec<u8>),
|
||||
/// Specifying a user identifier and server identifier that will be matched against the client
|
||||
WithIdentifiers(Vec<u8>, Vec<u8>),
|
||||
/// Specifying a plaintext info and confidential info that will be sent to the server,
|
||||
/// along with a user identifier and and server identifier that will be matched against the server
|
||||
/// (in that order)
|
||||
WithInfoAndIdentifiers(Vec<u8>, Vec<u8>, Vec<u8>, Vec<u8>),
|
||||
/// No info and no custom identifiers
|
||||
Default,
|
||||
}
|
||||
@@ -531,8 +525,6 @@ pub struct ClientLoginFinishResult<CS: CipherSuite> {
|
||||
pub export_key: GenericArray<u8, ExportKeySize>,
|
||||
/// The server's static public key
|
||||
pub server_s_pk: <CS::KeyFormat as KeyPair>::Repr,
|
||||
/// The plaintext info sent by the client
|
||||
pub plain_info: Vec<u8>,
|
||||
/// The confidential info sent by the client
|
||||
pub confidential_info: Vec<u8>,
|
||||
}
|
||||
@@ -628,15 +620,9 @@ impl<CS: CipherSuite> ClientLogin<CS> {
|
||||
l2: CredentialResponse<CS>,
|
||||
params: ClientLoginFinishParameters,
|
||||
) -> Result<ClientLoginFinishResult<CS>, ProtocolError> {
|
||||
let (info, e_info, optional_ids) = match params {
|
||||
ClientLoginFinishParameters::Default => (Vec::new(), Vec::new(), None),
|
||||
ClientLoginFinishParameters::WithInfo(info, e_info) => (info, e_info, None),
|
||||
ClientLoginFinishParameters::WithIdentifiers(id_u, id_s) => {
|
||||
(Vec::new(), Vec::new(), Some((id_u, id_s)))
|
||||
}
|
||||
ClientLoginFinishParameters::WithInfoAndIdentifiers(info, e_info, id_u, id_s) => {
|
||||
(info, e_info, Some((id_u, id_s)))
|
||||
}
|
||||
let optional_ids = match params {
|
||||
ClientLoginFinishParameters::Default => None,
|
||||
ClientLoginFinishParameters::WithIdentifiers(id_u, id_s) => Some((id_u, id_s)),
|
||||
};
|
||||
|
||||
let l2_beta_bytes = &l2.beta.to_arr()[..];
|
||||
@@ -673,21 +659,17 @@ impl<CS: CipherSuite> ClientLogin<CS> {
|
||||
]
|
||||
.concat();
|
||||
|
||||
let (plain_info, confidential_info, shared_secret, ke3_message) =
|
||||
CS::KeyExchange::generate_ke3(
|
||||
l2_bytes,
|
||||
l2.ke2_message,
|
||||
&self.ke1_state,
|
||||
l2.server_s_pk.clone(),
|
||||
client_s_sk,
|
||||
id_u,
|
||||
id_s,
|
||||
info,
|
||||
e_info,
|
||||
)?;
|
||||
let (confidential_info, shared_secret, ke3_message) = CS::KeyExchange::generate_ke3(
|
||||
l2_bytes,
|
||||
l2.ke2_message,
|
||||
&self.ke1_state,
|
||||
l2.server_s_pk.clone(),
|
||||
client_s_sk,
|
||||
id_u,
|
||||
id_s,
|
||||
)?;
|
||||
|
||||
Ok(ClientLoginFinishResult {
|
||||
plain_info,
|
||||
confidential_info,
|
||||
message: CredentialFinalization { ke3_message },
|
||||
shared_secret,
|
||||
@@ -718,19 +700,19 @@ impl<CS: CipherSuite> TryFrom<&[u8]> for ServerLogin<CS> {
|
||||
|
||||
/// Optional parameters for server login start
|
||||
pub enum ServerLoginStartParameters {
|
||||
/// Specifying a plaintext info and confidential info field that will be sent to the client
|
||||
WithInfo(Vec<u8>, Vec<u8>),
|
||||
/// Specifying a confidential info field that will be sent to the client
|
||||
WithInfo(Vec<u8>),
|
||||
/// Specifying a user identifier and server identifier that will be matched against the client
|
||||
WithIdentifiers(Vec<u8>, Vec<u8>),
|
||||
/// Specifying a plaintext info and confidential info that will be sent to the client,
|
||||
/// Specifying a confidential info field that will be sent to the client,
|
||||
/// along with a user identifier and and server identifier that will be matched against the client
|
||||
/// (in that order)
|
||||
WithInfoAndIdentifiers(Vec<u8>, Vec<u8>, Vec<u8>, Vec<u8>),
|
||||
WithInfoAndIdentifiers(Vec<u8>, Vec<u8>, Vec<u8>),
|
||||
}
|
||||
|
||||
impl Default for ServerLoginStartParameters {
|
||||
fn default() -> Self {
|
||||
Self::WithInfo(Vec::new(), Vec::new())
|
||||
Self::WithInfo(Vec::new())
|
||||
}
|
||||
}
|
||||
|
||||
@@ -748,10 +730,6 @@ pub struct ServerLoginStartResult<CS: CipherSuite> {
|
||||
pub struct ServerLoginFinishResult {
|
||||
/// The shared session secret between client and server
|
||||
pub shared_secret: Vec<u8>,
|
||||
/// The plaintext info sent by the client
|
||||
pub plain_info: Vec<u8>,
|
||||
/// The confidential info sent by the client
|
||||
pub confidential_info: Vec<u8>,
|
||||
}
|
||||
|
||||
impl<CS: CipherSuite> ServerLogin<CS> {
|
||||
@@ -805,13 +783,13 @@ impl<CS: CipherSuite> ServerLogin<CS> {
|
||||
.client_s_pk
|
||||
.ok_or(InternalPakeError::SealError)?;
|
||||
|
||||
let (info, e_info, optional_ids) = match params {
|
||||
ServerLoginStartParameters::WithInfo(info, e_info) => (info, e_info, None),
|
||||
let (e_info, optional_ids) = match params {
|
||||
ServerLoginStartParameters::WithInfo(e_info) => (e_info, None),
|
||||
ServerLoginStartParameters::WithIdentifiers(id_u, id_s) => {
|
||||
(Vec::new(), Vec::new(), Some((id_u, id_s)))
|
||||
(Vec::new(), Some((id_u, id_s)))
|
||||
}
|
||||
ServerLoginStartParameters::WithInfoAndIdentifiers(info, e_info, id_u, id_s) => {
|
||||
(info, e_info, Some((id_u, id_s)))
|
||||
ServerLoginStartParameters::WithInfoAndIdentifiers(e_info, id_u, id_s) => {
|
||||
(e_info, Some((id_u, id_s)))
|
||||
}
|
||||
};
|
||||
|
||||
@@ -851,7 +829,6 @@ impl<CS: CipherSuite> ServerLogin<CS> {
|
||||
server_s_sk.clone(),
|
||||
id_u,
|
||||
id_s,
|
||||
info,
|
||||
e_info,
|
||||
)?;
|
||||
|
||||
@@ -912,23 +889,18 @@ impl<CS: CipherSuite> ServerLogin<CS> {
|
||||
&self,
|
||||
message: CredentialFinalization<CS>,
|
||||
) -> Result<ServerLoginFinishResult, ProtocolError> {
|
||||
let (plain_info, confidential_info, shared_secret) =
|
||||
<CS::KeyExchange as KeyExchange<CS::Hash, CS::KeyFormat>>::finish_ke(
|
||||
message.ke3_message,
|
||||
&self.ke2_state,
|
||||
)
|
||||
.map_err(|e| match e {
|
||||
ProtocolError::VerificationError(PakeError::KeyExchangeMacValidationError) => {
|
||||
ProtocolError::VerificationError(PakeError::InvalidLoginError)
|
||||
}
|
||||
err => err,
|
||||
})?;
|
||||
let shared_secret = <CS::KeyExchange as KeyExchange<CS::Hash, CS::KeyFormat>>::finish_ke(
|
||||
message.ke3_message,
|
||||
&self.ke2_state,
|
||||
)
|
||||
.map_err(|e| match e {
|
||||
ProtocolError::VerificationError(PakeError::KeyExchangeMacValidationError) => {
|
||||
ProtocolError::VerificationError(PakeError::InvalidLoginError)
|
||||
}
|
||||
err => err,
|
||||
})?;
|
||||
|
||||
Ok(ServerLoginFinishResult {
|
||||
plain_info,
|
||||
confidential_info,
|
||||
shared_secret,
|
||||
})
|
||||
Ok(ServerLoginFinishResult { shared_secret })
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+17
-32
@@ -233,14 +233,11 @@ fn login_second_message_roundtrip() {
|
||||
let mut server_nonce = [0u8; NONCE_LEN];
|
||||
rng.fill_bytes(&mut server_nonce);
|
||||
|
||||
let mut info = [0u8; MAX_INFO_LENGTH];
|
||||
rng.fill_bytes(&mut info);
|
||||
let mut e_info = [0u8; MAX_INFO_LENGTH];
|
||||
rng.fill_bytes(&mut e_info);
|
||||
|
||||
let ke2m: Vec<u8> = [
|
||||
&server_nonce[..],
|
||||
&serialize(&info.to_vec(), 2),
|
||||
&server_e_kp.public(),
|
||||
&serialize(&e_info.to_vec(), 2),
|
||||
&mac[..],
|
||||
@@ -263,19 +260,10 @@ fn login_second_message_roundtrip() {
|
||||
#[test]
|
||||
fn login_third_message_roundtrip() {
|
||||
let mut rng = OsRng;
|
||||
let mut info = [0u8; MAX_INFO_LENGTH];
|
||||
rng.fill_bytes(&mut info);
|
||||
let mut e_info = [0u8; MAX_INFO_LENGTH];
|
||||
rng.fill_bytes(&mut e_info);
|
||||
let mut mac = [0u8; 32];
|
||||
rng.fill_bytes(&mut mac);
|
||||
|
||||
let input: Vec<u8> = [
|
||||
&serialize(&info.to_vec(), 2),
|
||||
&serialize(&e_info.to_vec(), 2),
|
||||
&mac[..],
|
||||
]
|
||||
.concat();
|
||||
let input: Vec<u8> = [&mac[..]].concat();
|
||||
|
||||
let l3 = CredentialFinalization::<Default>::deserialize(&input).unwrap();
|
||||
let l3_bytes = l3.serialize();
|
||||
@@ -328,8 +316,11 @@ fn ke1_message_roundtrip() {
|
||||
&client_e_kp.public(),
|
||||
]
|
||||
.concat();
|
||||
let reg =
|
||||
<TripleDH as KeyExchange<sha2::Sha256, crate::keypair::X25519KeyPair>>::KE1Message::try_from(&ke1m[..]).unwrap();
|
||||
let reg = <TripleDH as KeyExchange<
|
||||
sha2::Sha256,
|
||||
crate::keypair::X25519KeyPair,
|
||||
>>::KE1Message::try_from(&ke1m[..])
|
||||
.unwrap();
|
||||
let reg_bytes = reg.to_bytes();
|
||||
assert_eq!(reg_bytes, ke1m);
|
||||
}
|
||||
@@ -343,22 +334,22 @@ fn ke2_message_roundtrip() {
|
||||
rng.fill_bytes(&mut mac);
|
||||
let mut server_nonce = [0u8; NONCE_LEN];
|
||||
rng.fill_bytes(&mut server_nonce);
|
||||
let mut info = [0u8; MAX_INFO_LENGTH];
|
||||
rng.fill_bytes(&mut info);
|
||||
let mut e_info = [0u8; MAX_INFO_LENGTH];
|
||||
rng.fill_bytes(&mut e_info);
|
||||
|
||||
let ke2m: Vec<u8> = [
|
||||
&server_nonce[..],
|
||||
&serialize(&info.to_vec(), 2),
|
||||
&server_e_kp.public(),
|
||||
&serialize(&e_info.to_vec(), 2),
|
||||
&mac[..],
|
||||
]
|
||||
.concat();
|
||||
|
||||
let reg =
|
||||
<TripleDH as KeyExchange<sha2::Sha256, crate::keypair::X25519KeyPair>>::KE2Message::try_from(&ke2m[..]).unwrap();
|
||||
let reg = <TripleDH as KeyExchange<
|
||||
sha2::Sha256,
|
||||
crate::keypair::X25519KeyPair,
|
||||
>>::KE2Message::try_from(&ke2m[..])
|
||||
.unwrap();
|
||||
let reg_bytes = reg.to_bytes();
|
||||
assert_eq!(reg_bytes, ke2m);
|
||||
}
|
||||
@@ -366,22 +357,16 @@ fn ke2_message_roundtrip() {
|
||||
#[test]
|
||||
fn ke3_message_roundtrip() {
|
||||
let mut rng = OsRng;
|
||||
let mut info = [0u8; MAX_INFO_LENGTH];
|
||||
rng.fill_bytes(&mut info);
|
||||
let mut e_info = [0u8; MAX_INFO_LENGTH];
|
||||
rng.fill_bytes(&mut e_info);
|
||||
let mut mac = [0u8; 32];
|
||||
rng.fill_bytes(&mut mac);
|
||||
|
||||
let ke3m: Vec<u8> = [
|
||||
&serialize(&info.to_vec(), 2),
|
||||
&serialize(&e_info.to_vec(), 2),
|
||||
&mac[..],
|
||||
]
|
||||
.concat();
|
||||
let ke3m: Vec<u8> = [&mac[..]].concat();
|
||||
|
||||
let reg =
|
||||
<TripleDH as KeyExchange<sha2::Sha256, crate::keypair::X25519KeyPair>>::KE3Message::try_from(&ke3m[..]).unwrap();
|
||||
let reg = <TripleDH as KeyExchange<
|
||||
sha2::Sha256,
|
||||
crate::keypair::X25519KeyPair,
|
||||
>>::KE3Message::try_from(&ke3m[..])
|
||||
.unwrap();
|
||||
let reg_bytes = reg.to_bytes();
|
||||
assert_eq!(reg_bytes, ke3m);
|
||||
}
|
||||
|
||||
+28
-70
@@ -51,10 +51,7 @@ pub struct TestVectorParameters {
|
||||
pub client_nonce: Vec<u8>,
|
||||
pub server_nonce: Vec<u8>,
|
||||
pub info1: Vec<u8>,
|
||||
pub info2: Vec<u8>,
|
||||
pub einfo2: Vec<u8>,
|
||||
pub info3: Vec<u8>,
|
||||
pub einfo3: Vec<u8>,
|
||||
pub registration_request: Vec<u8>,
|
||||
pub registration_response: Vec<u8>,
|
||||
pub registration_upload: Vec<u8>,
|
||||
@@ -72,40 +69,37 @@ pub struct TestVectorParameters {
|
||||
|
||||
static TEST_VECTOR: &str = r#"
|
||||
{
|
||||
"client_s_pk": "037ffc2cece49ab487448c9b52debee00bfcc72f00c78668f9b160466cc5b25a",
|
||||
"client_s_sk": "e09f8a22c083743c60a2eb41640dc7174edd8863bb1a7482c12a02f08914db60",
|
||||
"client_e_pk": "61422d4437b43abca17d2297a3b519fc37b24e20cb45d14a91ffcb1bc2107a5c",
|
||||
"client_e_sk": "c831faece522d77c10625d1b0ea5592fb4ee45b042b4af4218d5702b087b136e",
|
||||
"server_s_pk": "2cd221b189b472badcc2d4984dba174fd2e016bcc2bc8110527a11f28cd4f54f",
|
||||
"server_s_sk": "986f09786edea821e346bd961cc0d727d5af77f88acda9bf2f95235716535f7c",
|
||||
"server_e_pk": "b282307ada534fbb7e91253e8a807d3a0c5adb0cbcfb39fe5bae5bfd407abf17",
|
||||
"server_e_sk": "f0d994f344f79aab474637090d6aeb6319c0a8123e21a18774fb4b21496a9963",
|
||||
"client_s_pk": "d762053e2da32c990b1edb22408138369282462feeaa68fc0acfd157c2745740",
|
||||
"client_s_sk": "b06303fb12bde8fb2875ffc052c0c0cdb4bbef7b6a32ec9bb4a00a3a56fb9545",
|
||||
"client_e_pk": "0375e9aa445b859a02e9ccacd45772758e560f8640ee067319a86374cd93a435",
|
||||
"client_e_sk": "c835f5854f1651c8551e24aee6ab1b81bf44e4cb906d0ac9fcf1aaa26ef3b872",
|
||||
"server_s_pk": "b7d6d756fb2b3972125245f53c042c53c8b3bf5e9d2b576809548c5510f33136",
|
||||
"server_s_sk": "b81e81698a315f4ee817e5c9bd4426db1bf8dd9fec2e6fc82639d08d90509e6f",
|
||||
"server_e_pk": "6ce63bc56b7b2141680b4fc4c8d3b4d09b903c5a2d657fc79432c586d0e9bd64",
|
||||
"server_e_sk": "a0f3efd594b41deaba4480cae066c658529b90754f5109f9b0b61d42266f234e",
|
||||
"id_u": "696455",
|
||||
"id_s": "696453",
|
||||
"password": "70617373776f7264",
|
||||
"blinding_factor": "26f30696f7a0d47fe3c5a08e2962880f413e805c013b59dde187df0d1667b003",
|
||||
"oprf_key": "b1126f88aa2377b1b56a81227c9f72c015dd6f94e1f8d88e4cb983016da50804",
|
||||
"envelope_nonce": "66ea20d6a122e7cb9872fd141f338c8009655963f8ba925ca801182c63921ce6",
|
||||
"client_nonce": "85320d740dc2d1b4e78e3c4d6e6ce474b3f2f5abe3c0e314555e310e9f5b7dde",
|
||||
"server_nonce": "2e1d659f03ad117e51acad7e8b8519472237aa0c7e9c35482185cefdaa972607",
|
||||
"blinding_factor": "78b54192e145ff02458385f8540fdf54e94c2a20f0a7f8f98944bc17af795e04",
|
||||
"oprf_key": "98a9232ccfda91d14ea305e5cfb4e552ab8aa972ac6c79befe15ccf9f4f2970a",
|
||||
"envelope_nonce": "46c395bdc879bfebae229024f0004721448e713643a341146310d50c84cef011",
|
||||
"client_nonce": "197b1147bb214fafde9f5ce6f5e903d69be0ca006c51ac8f949ce7ab73a828ed",
|
||||
"server_nonce": "73a56c702168d9d534429fd45c37390ed6f55b6ea79f2025e4584a04d35aa229",
|
||||
"info1": "696e666f31",
|
||||
"info2": "696e666f32",
|
||||
"einfo2": "65696e666f32",
|
||||
"info3": "696e666f33",
|
||||
"einfo3": "65696e666f33",
|
||||
"registration_request": "00205cebd79b362cbb48eab435801125e4646c4e56c9f19d720f1b7cdbca4c300ea8",
|
||||
"registration_response": "002075dfc31fff8a44bde1ed1fd8c9295b7516bce1fe7559692883ada956a423fa9c00202cd221b189b472badcc2d4984dba174fd2e016bcc2bc8110527a11f28cd4f54f",
|
||||
"registration_upload": "0166ea20d6a122e7cb9872fd141f338c8009655963f8ba925ca801182c63921ce600223c2deccbf09b5506d628137bd661b6de943a92fe762fd2b872c6adabc1e4c10ca2fb002c00202cd221b189b472badcc2d4984dba174fd2e016bcc2bc8110527a11f28cd4f54f000369645500036964530020dd6e96af9578ad04ef758070afdbb34ac695d2be131fed185ce746537cd02de60020037ffc2cece49ab487448c9b52debee00bfcc72f00c78668f9b160466cc5b25a",
|
||||
"credential_request": "00205cebd79b362cbb48eab435801125e4646c4e56c9f19d720f1b7cdbca4c300ea885320d740dc2d1b4e78e3c4d6e6ce474b3f2f5abe3c0e314555e310e9f5b7dde0005696e666f3161422d4437b43abca17d2297a3b519fc37b24e20cb45d14a91ffcb1bc2107a5c",
|
||||
"credential_response": "002075dfc31fff8a44bde1ed1fd8c9295b7516bce1fe7559692883ada956a423fa9c00202cd221b189b472badcc2d4984dba174fd2e016bcc2bc8110527a11f28cd4f54f0166ea20d6a122e7cb9872fd141f338c8009655963f8ba925ca801182c63921ce600223c2deccbf09b5506d628137bd661b6de943a92fe762fd2b872c6adabc1e4c10ca2fb002c00202cd221b189b472badcc2d4984dba174fd2e016bcc2bc8110527a11f28cd4f54f000369645500036964530020dd6e96af9578ad04ef758070afdbb34ac695d2be131fed185ce746537cd02de6f0d994f344f79aab474637090d6aeb6319c0a8123e21a18774fb4b21496a99630005696e666f32b282307ada534fbb7e91253e8a807d3a0c5adb0cbcfb39fe5bae5bfd407abf17000665696e666f32fb98272619ab5c17b860c2a59f194b88203080f641b96c278d10d69be004d2dd",
|
||||
"key_exchange": "0005696e666f33000665696e666f33a13c4265ac30d7e079e975a550571ee95e74149cdc83b8683ac12d3764ed779a",
|
||||
"client_registration_state": "26f30696f7a0d47fe3c5a08e2962880f413e805c013b59dde187df0d1667b00370617373776f7264",
|
||||
"client_login_state": "26f30696f7a0d47fe3c5a08e2962880f413e805c013b59dde187df0d1667b003c831faece522d77c10625d1b0ea5592fb4ee45b042b4af4218d5702b087b136e85320d740dc2d1b4e78e3c4d6e6ce474b3f2f5abe3c0e314555e310e9f5b7dde518be4c0634f9829245f95c3ead10fafa41c29be9c6ca976bff9a1a22a61895e70617373776f7264",
|
||||
"server_registration_state": "b1126f88aa2377b1b56a81227c9f72c015dd6f94e1f8d88e4cb983016da50804",
|
||||
"server_login_state": "cb5e5021406dab84937ee7964c288e2ea176f7533ef12c2f7836dfc0a034c0387088884ba8e2ed9703ebf185a91511426d4dff480bd7282057e49b0b0fc38d6fa58f4c40f986833c2773696694d51a0a36d9ee85b0aacfc9cdad34dd9ad90d61",
|
||||
"password_file": "b1126f88aa2377b1b56a81227c9f72c015dd6f94e1f8d88e4cb983016da50804037ffc2cece49ab487448c9b52debee00bfcc72f00c78668f9b160466cc5b25a0166ea20d6a122e7cb9872fd141f338c8009655963f8ba925ca801182c63921ce600223c2deccbf09b5506d628137bd661b6de943a92fe762fd2b872c6adabc1e4c10ca2fb002c00202cd221b189b472badcc2d4984dba174fd2e016bcc2bc8110527a11f28cd4f54f000369645500036964530020dd6e96af9578ad04ef758070afdbb34ac695d2be131fed185ce746537cd02de6",
|
||||
"export_key": "776947002cb41ad575506e82778313bb8d2767dd9d7ed3fd55f875071d833a2e",
|
||||
"shared_secret": "a58f4c40f986833c2773696694d51a0a36d9ee85b0aacfc9cdad34dd9ad90d61"
|
||||
"registration_request": "0020ed5ca18ae23e622694611af62744f21c70f68d495ce36ae17784f03d225b573c",
|
||||
"registration_response": "002078b592b789e7239481637419438333cbdcd3dd909534ac28e5473683d023719d0020b7d6d756fb2b3972125245f53c042c53c8b3bf5e9d2b576809548c5510f33136",
|
||||
"registration_upload": "0146c395bdc879bfebae229024f0004721448e713643a341146310d50c84cef0110022f6906b64d3d45c4d77dd8c002b841749f716efc9e3e2cff762004b4878e75c0a7abe002c0020b7d6d756fb2b3972125245f53c042c53c8b3bf5e9d2b576809548c5510f33136000369645500036964530020e4444a287fc0bc8921d0c6423d36948fa176f68671196592cb947984b082bacd0020d762053e2da32c990b1edb22408138369282462feeaa68fc0acfd157c2745740",
|
||||
"credential_request": "0020ed5ca18ae23e622694611af62744f21c70f68d495ce36ae17784f03d225b573c197b1147bb214fafde9f5ce6f5e903d69be0ca006c51ac8f949ce7ab73a828ed0005696e666f310375e9aa445b859a02e9ccacd45772758e560f8640ee067319a86374cd93a435",
|
||||
"credential_response": "002078b592b789e7239481637419438333cbdcd3dd909534ac28e5473683d023719d0020b7d6d756fb2b3972125245f53c042c53c8b3bf5e9d2b576809548c5510f331360146c395bdc879bfebae229024f0004721448e713643a341146310d50c84cef0110022f6906b64d3d45c4d77dd8c002b841749f716efc9e3e2cff762004b4878e75c0a7abe002c0020b7d6d756fb2b3972125245f53c042c53c8b3bf5e9d2b576809548c5510f33136000369645500036964530020e4444a287fc0bc8921d0c6423d36948fa176f68671196592cb947984b082bacda0f3efd594b41deaba4480cae066c658529b90754f5109f9b0b61d42266f234e6ce63bc56b7b2141680b4fc4c8d3b4d09b903c5a2d657fc79432c586d0e9bd6400061e51f6093a7669db4e4a493137440cada18dcff631462e349de1d043a14a7a1de77b85638fbd",
|
||||
"key_exchange": "11d1a3f15b490c059bfa06f7d0fae9cde9ff6af80270f3327161a362ec84570e",
|
||||
"client_registration_state": "78b54192e145ff02458385f8540fdf54e94c2a20f0a7f8f98944bc17af795e0470617373776f7264",
|
||||
"client_login_state": "78b54192e145ff02458385f8540fdf54e94c2a20f0a7f8f98944bc17af795e04c835f5854f1651c8551e24aee6ab1b81bf44e4cb906d0ac9fcf1aaa26ef3b872197b1147bb214fafde9f5ce6f5e903d69be0ca006c51ac8f949ce7ab73a828ed3a139e3e250129a1d3e7633052f853006a501e24b1d3c6ba6403aeb9cca7eda170617373776f7264",
|
||||
"server_registration_state": "98a9232ccfda91d14ea305e5cfb4e552ab8aa972ac6c79befe15ccf9f4f2970a",
|
||||
"server_login_state": "8be81bab99a1ce566adb4f33d14b012a8583f0ecf8b467bad1930a6adbf7178dcc8daa2de4be476dde1d8193f9fe7786601d7db0af7302c19501b516ad5e53329706a48a68a6bbf3dea894447a53b423fc5b5e561c9c3fa9b1b278d6790bbb74",
|
||||
"password_file": "98a9232ccfda91d14ea305e5cfb4e552ab8aa972ac6c79befe15ccf9f4f2970ad762053e2da32c990b1edb22408138369282462feeaa68fc0acfd157c27457400146c395bdc879bfebae229024f0004721448e713643a341146310d50c84cef0110022f6906b64d3d45c4d77dd8c002b841749f716efc9e3e2cff762004b4878e75c0a7abe002c0020b7d6d756fb2b3972125245f53c042c53c8b3bf5e9d2b576809548c5510f33136000369645500036964530020e4444a287fc0bc8921d0c6423d36948fa176f68671196592cb947984b082bacd",
|
||||
"export_key": "3cdf9ad930b46fad7855faab02a7f2e28282cc73f82fdd411f1a7f6c300c8ab1",
|
||||
"shared_secret": "9706a48a68a6bbf3dea894447a53b423fc5b5e561c9c3fa9b1b278d6790bbb74"
|
||||
}
|
||||
"#;
|
||||
|
||||
@@ -134,10 +128,7 @@ fn populate_test_vectors(values: &Value) -> TestVectorParameters {
|
||||
client_nonce: decode(&values, "client_nonce").unwrap(),
|
||||
server_nonce: decode(&values, "server_nonce").unwrap(),
|
||||
info1: decode(&values, "info1").unwrap(),
|
||||
info2: decode(&values, "info2").unwrap(),
|
||||
einfo2: decode(&values, "einfo2").unwrap(),
|
||||
info3: decode(&values, "info3").unwrap(),
|
||||
einfo3: decode(&values, "einfo3").unwrap(),
|
||||
registration_request: decode(&values, "registration_request").unwrap(),
|
||||
registration_response: decode(&values, "registration_response").unwrap(),
|
||||
registration_upload: decode(&values, "registration_upload").unwrap(),
|
||||
@@ -186,10 +177,7 @@ fn stringify_test_vectors(p: &TestVectorParameters) -> String {
|
||||
s.push_str(format!("\"client_nonce\": \"{}\",\n", hex::encode(&p.client_nonce)).as_str());
|
||||
s.push_str(format!("\"server_nonce\": \"{}\",\n", hex::encode(&p.server_nonce)).as_str());
|
||||
s.push_str(format!("\"info1\": \"{}\",\n", hex::encode(&p.info1)).as_str());
|
||||
s.push_str(format!("\"info2\": \"{}\",\n", hex::encode(&p.info2)).as_str());
|
||||
s.push_str(format!("\"einfo2\": \"{}\",\n", hex::encode(&p.einfo2)).as_str());
|
||||
s.push_str(format!("\"info3\": \"{}\",\n", hex::encode(&p.info3)).as_str());
|
||||
s.push_str(format!("\"einfo3\": \"{}\",\n", hex::encode(&p.einfo3)).as_str());
|
||||
s.push_str(
|
||||
format!(
|
||||
"\"registration_request\": \"{}\",\n",
|
||||
@@ -301,10 +289,7 @@ where
|
||||
rng.fill_bytes(&mut server_nonce);
|
||||
|
||||
let info1 = b"info1";
|
||||
let info2 = b"info2";
|
||||
let einfo2 = b"einfo2";
|
||||
let info3 = b"info3";
|
||||
let einfo3 = b"einfo3";
|
||||
|
||||
let mut blinding_factor_registration_rng = CycleRng::new(blinding_factor_raw.to_vec());
|
||||
let client_registration_start_result = ClientRegistration::<CS>::start(
|
||||
@@ -383,7 +368,6 @@ where
|
||||
server_s_kp.private(),
|
||||
client_login_start_result.message,
|
||||
ServerLoginStartParameters::WithInfoAndIdentifiers(
|
||||
info2.to_vec(),
|
||||
einfo2.to_vec(),
|
||||
id_u.to_vec(),
|
||||
id_s.to_vec(),
|
||||
@@ -397,12 +381,7 @@ where
|
||||
.state
|
||||
.finish(
|
||||
server_login_start_result.message,
|
||||
ClientLoginFinishParameters::WithInfoAndIdentifiers(
|
||||
info3.to_vec(),
|
||||
einfo3.to_vec(),
|
||||
id_u.to_vec(),
|
||||
id_s.to_vec(),
|
||||
),
|
||||
ClientLoginFinishParameters::WithIdentifiers(id_u.to_vec(), id_s.to_vec()),
|
||||
)
|
||||
.unwrap();
|
||||
let key_exchange_bytes = client_login_finish_result.message.to_bytes().to_vec();
|
||||
@@ -425,10 +404,7 @@ where
|
||||
client_nonce: client_nonce.to_vec(),
|
||||
server_nonce: server_nonce.to_vec(),
|
||||
info1: info1.to_vec(),
|
||||
info2: info2.to_vec(),
|
||||
einfo2: einfo2.to_vec(),
|
||||
info3: info3.to_vec(),
|
||||
einfo3: einfo3.to_vec(),
|
||||
registration_request: registration_request_bytes,
|
||||
registration_response: registration_response_bytes,
|
||||
registration_upload: registration_upload_bytes,
|
||||
@@ -582,7 +558,6 @@ fn test_credential_response() -> Result<(), ProtocolError> {
|
||||
CredentialRequest::<X255193dhNoSlowHash>::deserialize(¶meters.credential_request[..])
|
||||
.unwrap(),
|
||||
ServerLoginStartParameters::WithInfoAndIdentifiers(
|
||||
parameters.info2.to_vec(),
|
||||
parameters.einfo2.to_vec(),
|
||||
parameters.id_u,
|
||||
parameters.id_s,
|
||||
@@ -614,18 +589,9 @@ fn test_key_exchange() -> Result<(), ProtocolError> {
|
||||
CredentialResponse::<X255193dhNoSlowHash>::deserialize(
|
||||
¶meters.credential_response[..],
|
||||
)?,
|
||||
ClientLoginFinishParameters::WithInfoAndIdentifiers(
|
||||
parameters.info3.to_vec(),
|
||||
parameters.einfo3.to_vec(),
|
||||
parameters.id_u,
|
||||
parameters.id_s,
|
||||
),
|
||||
ClientLoginFinishParameters::WithIdentifiers(parameters.id_u, parameters.id_s),
|
||||
)?;
|
||||
|
||||
assert_eq!(
|
||||
hex::encode(¶meters.info2),
|
||||
hex::encode(&client_login_finish_result.plain_info)
|
||||
);
|
||||
assert_eq!(
|
||||
hex::encode(¶meters.einfo2),
|
||||
hex::encode(&client_login_finish_result.confidential_info)
|
||||
@@ -659,14 +625,6 @@ fn test_server_login_finish() -> Result<(), ProtocolError> {
|
||||
CredentialFinalization::try_from(¶meters.key_exchange[..])?,
|
||||
)?;
|
||||
|
||||
assert_eq!(
|
||||
hex::encode(parameters.info3),
|
||||
hex::encode(server_login_result.plain_info)
|
||||
);
|
||||
assert_eq!(
|
||||
hex::encode(parameters.einfo3),
|
||||
hex::encode(server_login_result.confidential_info)
|
||||
);
|
||||
assert_eq!(
|
||||
hex::encode(parameters.shared_secret),
|
||||
hex::encode(server_login_result.shared_secret)
|
||||
|
||||
Reference in New Issue
Block a user