make psq algos generic

This commit is contained in:
Georgio Nicolas
2025-06-04 20:43:28 +02:00
parent 6710e8df56
commit a7587eafb7
4 changed files with 88 additions and 39 deletions
Generated
+1
View File
@@ -4337,6 +4337,7 @@ version = "0.0.3-alpha.1"
source = "git+https://github.com/cryspen/libcrux#96abd9f2460ff92811a1c181662590d96c37949c"
dependencies = [
"libcrux-chacha20poly1305",
"libcrux-ecdh",
"libcrux-ed25519",
"libcrux-hkdf",
"libcrux-hmac",
+1 -1
View File
@@ -23,7 +23,7 @@ nym-crypto = { path = "../crypto", features = ["asymmetric", "serde"]}
libcrux-traits = { git = "https://github.com/cryspen/libcrux" }
libcrux-kem = { git = "https://github.com/cryspen/libcrux" }
libcrux-psq = { git = "https://github.com/cryspen/libcrux" }
libcrux-psq = { git = "https://github.com/cryspen/libcrux", features = ["test-utils"] }
rand = "0.9.1"
[dev-dependencies]
+6 -4
View File
@@ -18,18 +18,20 @@ mod test {
#[test]
fn test_kkt_psq_e2e() {
let mut rng = rand::rng();
// generate ed25519 keys
let mut secret_initiator: [u8; 32] = [0u8; 32];
rand::rng().fill_bytes(&mut secret_initiator);
rng.fill_bytes(&mut secret_initiator);
let initiator_ed25519_keypair = ed25519::KeyPair::from_secret(secret_initiator, 0);
let mut secret_responder: [u8; 32] = [0u8; 32];
rand::rng().fill_bytes(&mut secret_responder);
rng.fill_bytes(&mut secret_responder);
let responder_ed25519_keypair = ed25519::KeyPair::from_secret(secret_responder, 1);
// generate kem keypair
let (responder_kem_private_key, responder_kem_public_key) =
libcrux_kem::key_gen(libcrux_kem::Algorithm::MlKem768, &mut rand::rng()).unwrap();
libcrux_kem::key_gen(libcrux_kem::Algorithm::MlKem768, &mut rng).unwrap();
// initialize parties
let kkt_initiator: KKTInitiator<MlKem768> =
@@ -78,7 +80,7 @@ mod test {
PSQResponder::init(&responder_kem_private_key, &responder_kem_public_key);
let initiator_psq_msg = psq_initiator
.initiator_message(&received_responder_key)
.initiator_message(&mut rng, &received_responder_key)
.unwrap();
let (responder_psk, responder_psq_msg) = psq_responder
+80 -34
View File
@@ -5,13 +5,13 @@ use std::{marker::PhantomData, time::Duration};
use libcrux_psq::{
cred::Ed25519,
impls::MlKem768,
psk_registration::{Initiator, InitiatorMsg, Responder, ResponderMsg},
traits::PSQ,
};
use libcrux_traits::kem::KEM;
use nym_crypto::asymmetric::ed25519;
use rand::CryptoRng;
use crate::error::PSQError;
@@ -32,6 +32,23 @@ impl<'a, T: PSQ> PSQInitiator<'a, T> {
}
}
pub fn initiator_message(
&mut self,
rng: &mut impl CryptoRng,
responder_kem_public_key: &'a <T::InnerKEM as KEM>::EncapsulationKey,
) -> Result<InitiatorMsg<T::InnerKEM>, PSQError> {
let (state, message) = Initiator::send_initial_message::<Ed25519, T>(
&[0u8],
Duration::from_secs(3600),
&responder_kem_public_key,
&self.signing_keypair.private_key().to_bytes(),
&self.signing_keypair.public_key().to_bytes(),
rng,
)?;
self.state = Some(state);
Ok(message)
}
pub fn finalize(&self, responder_message: &ResponderMsg) -> Result<[u8; PSK_LENGTH], PSQError> {
match &self.state {
Some(state) => match state.complete_handshake(responder_message) {
@@ -43,24 +60,6 @@ impl<'a, T: PSQ> PSQInitiator<'a, T> {
}
}
impl<'a> PSQInitiator<'a, MlKem768> {
pub fn initiator_message(
&mut self,
responder_kem_public_key: &libcrux_kem::PublicKey,
) -> Result<InitiatorMsg<MlKem768>, PSQError> {
let (state, message) = Initiator::send_initial_message::<Ed25519, MlKem768>(
&[0u8],
Duration::from_secs(3600),
&responder_kem_public_key,
&self.signing_keypair.private_key().to_bytes(),
&self.signing_keypair.public_key().to_bytes(),
&mut rand::rng(),
)?;
self.state = Some(state);
Ok(message)
}
}
pub struct PSQResponder<'a, T: PSQ> {
kem_private_key: &'a <T::InnerKEM as KEM>::DecapsulationKey,
kem_public_key: &'a <T::InnerKEM as KEM>::EncapsulationKey,
@@ -77,14 +76,13 @@ impl<'a, T: PSQ> PSQResponder<'a, T> {
_t: PhantomData,
}
}
}
impl<'a> PSQResponder<'a, MlKem768> {
pub fn responder_msg(
&self,
initiator_verification_key: &'a ed25519::PublicKey,
initiator_message: &InitiatorMsg<MlKem768>,
initiator_message: &InitiatorMsg<T::InnerKEM>,
) -> Result<([u8; PSK_LENGTH], ResponderMsg), PSQError> {
let (registered_psk, responder_msg) = Responder::send::<Ed25519, MlKem768>(
let (registered_psk, responder_msg) = Responder::send::<Ed25519, T>(
&[0u8],
Duration::from_secs(3600),
&[0u8],
@@ -100,29 +98,31 @@ impl<'a> PSQResponder<'a, MlKem768> {
#[cfg(test)]
mod test {
use libcrux_psq::impls::MlKem768;
use libcrux_psq::impls::{MlKem768, XWingKemDraft06, X25519};
use libcrux_psq::traits::PSQ;
use libcrux_traits::kem::KEM;
use nym_crypto::asymmetric::ed25519;
use rand::prelude::*;
use super::{PSQInitiator, PSQResponder};
#[test]
fn test_psq_e2e() {
fn test_helper<T: PSQ>(
rng: &mut impl CryptoRng,
responder_kem_private_key: <T::InnerKEM as KEM>::DecapsulationKey,
responder_kem_public_key: <T::InnerKEM as KEM>::EncapsulationKey,
) {
// generate ed25519 keys
let mut secret_initiator: [u8; 32] = [0u8; 32];
rand::rng().fill_bytes(&mut secret_initiator);
rng.fill_bytes(&mut secret_initiator);
let initiator_ed25519_keypair = ed25519::KeyPair::from_secret(secret_initiator, 0);
// generate kem keypair
let (responder_kem_private_key, responder_kem_public_key) =
libcrux_kem::key_gen(libcrux_kem::Algorithm::MlKem768, &mut rand::rng()).unwrap();
let mut initiator: PSQInitiator<MlKem768> = PSQInitiator::init(&initiator_ed25519_keypair);
let responder: PSQResponder<MlKem768> =
let mut initiator: PSQInitiator<T> = PSQInitiator::init(&initiator_ed25519_keypair);
let responder: PSQResponder<T> =
PSQResponder::init(&responder_kem_private_key, &responder_kem_public_key);
let initiator_msg = initiator
.initiator_message(&responder_kem_public_key)
.initiator_message(rng, &responder_kem_public_key)
.unwrap();
let (responder_psk, responder_msg) = responder
@@ -133,4 +133,50 @@ mod test {
assert_eq!(initiator_psk, responder_psk);
}
#[test]
fn test_psq_e2e_mlkem() {
let mut rng = rand::rng();
// generate mlkem keypair
let (responder_kem_private_key, responder_kem_public_key) =
libcrux_kem::key_gen(libcrux_kem::Algorithm::MlKem768, &mut rng).unwrap();
test_helper::<MlKem768>(
&mut rng,
responder_kem_private_key,
responder_kem_public_key,
);
}
#[test]
fn test_psq_e2e_xwing() {
let mut rng = rand::rng();
// generate mlkem keypair
let (responder_kem_private_key, responder_kem_public_key) =
libcrux_kem::key_gen(libcrux_kem::Algorithm::XWingKemDraft06, &mut rand::rng())
.unwrap();
test_helper::<XWingKemDraft06>(
&mut rng,
responder_kem_private_key,
responder_kem_public_key,
);
}
#[test]
fn test_psq_e2e_dhkem() {
let mut rng = rand::rng();
// generate mlkem keypair
let (responder_kem_private_key, responder_kem_public_key) =
libcrux_kem::key_gen(libcrux_kem::Algorithm::X25519, &mut rand::rng()).unwrap();
test_helper::<X25519>(
&mut rng,
responder_kem_private_key,
responder_kem_public_key,
);
}
}