confium_tc_frost_p256/
sign.rs1use crate::keys::Keypair;
8use p256::ecdsa::{Signature, signature::Signer};
9use thiserror::Error;
10
11#[derive(Debug, Clone)]
13pub struct Signed {
14 pub der_bytes: Vec<u8>,
16 pub fixed_bytes: Vec<u8>,
18}
19
20#[derive(Debug, Error)]
22pub enum SignError {
23 #[error("signing failed: {0}")]
25 Sign(String),
26}
27
28pub fn sign_message(keypair: &Keypair, message: &[u8]) -> Result<Signed, SignError> {
30 let signing_key = keypair.to_signing_key();
31 let sig: Signature = signing_key
32 .try_sign(message)
33 .map_err(|e| SignError::Sign(format!("p256 sign: {e:?}")))?;
34 Ok(Signed {
35 der_bytes: sig.to_der().to_bytes().to_vec(),
36 fixed_bytes: sig.to_bytes().to_vec(),
37 })
38}
39
40#[cfg(test)]
41mod tests {
42 use super::*;
43 use crate::keys::generate_keypair;
44 use p256::ecdsa::signature::Verifier;
45
46 #[test]
47 fn sign_and_verify_round_trip() {
48 let keypair = generate_keypair();
49 let msg = b"hello, threshold world";
50 let signed = sign_message(&keypair, msg).unwrap();
51
52 let verifying = keypair.to_verifying_key();
53 let sig = Signature::from_der(&signed.der_bytes).unwrap();
54 verifying.verify(msg, &sig).unwrap();
55 }
56
57 #[test]
58 fn signature_bytes_are_distinct() {
59 let keypair = generate_keypair();
60 let s1 = sign_message(&keypair, b"message one").unwrap();
61 let s2 = sign_message(&keypair, b"message two").unwrap();
62 assert_ne!(s1.der_bytes, s2.der_bytes);
63 }
64
65 #[test]
66 fn fixed_size_signature_is_64_bytes() {
67 let keypair = generate_keypair();
68 let signed = sign_message(&keypair, b"x").unwrap();
69 assert_eq!(signed.fixed_bytes.len(), 64);
70 }
71}