1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
use ed25519_dalek::{Signature as DalekSignature, Signer, SigningKey, Verifier, VerifyingKey};
use rand_core::CryptoRngCore;

use crate::{
    key_pair::{get_private_key, get_public_key, set_key_pair},
    Error,
};

pub const ED25519_PRIVATE_KEY_SIZE: usize = 32;
pub const ED25519_PUBLIC_KEY_SIZE: usize = 32;
pub const ED25519_KEY_PAIR_SIZE: usize = ED25519_PRIVATE_KEY_SIZE + ED25519_PUBLIC_KEY_SIZE;
pub const ED25519_SIGNATURE_SIZE: usize = 64;

pub type Ed25519PrivateKey = [u8; ED25519_PRIVATE_KEY_SIZE];
pub type Ed25519PublicKey = [u8; ED25519_PUBLIC_KEY_SIZE];
pub type Ed25519KeyPair = [u8; ED25519_KEY_PAIR_SIZE];
pub type Ed25519Signature = [u8; ED25519_SIGNATURE_SIZE];

pub fn ed25519_generate_key_pair<R: CryptoRngCore>(mut csprng: R) -> Ed25519KeyPair {
    let signing_key = SigningKey::generate(&mut csprng);
    let mut key_pair: Ed25519KeyPair = [0; ED25519_KEY_PAIR_SIZE];
    set_key_pair(
        &mut key_pair,
        signing_key.as_bytes(),
        signing_key.verifying_key().as_bytes(),
        ED25519_PRIVATE_KEY_SIZE,
    );
    key_pair
}

pub fn ed25519_get_private_key(key_pair: &Ed25519KeyPair) -> Ed25519PrivateKey {
    let mut private_key = [0; ED25519_PRIVATE_KEY_SIZE];
    get_private_key(&mut private_key, key_pair, ED25519_PRIVATE_KEY_SIZE);
    private_key
}

pub fn ed25519_get_public_key(key_pair: &Ed25519KeyPair) -> Ed25519PublicKey {
    let mut public_key = [0; ED25519_PUBLIC_KEY_SIZE];
    get_public_key(&mut public_key, key_pair, ED25519_PRIVATE_KEY_SIZE);
    public_key
}

pub fn ed25519_sign(key_pair: &Ed25519KeyPair, message: &[u8]) -> Result<Ed25519Signature, Error> {
    let signing_key = SigningKey::from_keypair_bytes(key_pair).or(Err(Error::SigningFailed))?;
    let signature = signing_key
        .try_sign(message)
        .or(Err(Error::SigningFailed))?;
    Ok(signature.into())
}

pub fn ed25519_verify(
    public_key: &Ed25519PublicKey,
    signature: &Ed25519Signature,
    message: &[u8],
) -> Result<(), Error> {
    let verifying_key = VerifyingKey::from_bytes(public_key).or(Err(Error::VerificationFailed))?;
    let signature = DalekSignature::from_slice(signature).or(Err(Error::VerificationFailed))?;
    verifying_key
        .verify(message, &signature)
        .or(Err(Error::VerificationFailed))
}

#[cfg(test)]
mod tests {
    use super::*;
    use alloc::vec;

    #[test]
    fn test_ed25519_sign() {
        let message = vec![72, 101, 108, 108, 111, 32, 87, 111, 114, 108, 100];
        let key_pair: Ed25519KeyPair = [
            187, 129, 5, 201, 47, 79, 117, 207, 153, 48, 200, 136, 139, 90, 233, 197, 234, 12, 195,
            165, 247, 82, 131, 84, 93, 59, 233, 61, 117, 254, 147, 254, 82, 97, 171, 66, 47, 97,
            89, 105, 150, 82, 88, 7, 31, 177, 30, 27, 118, 151, 80, 33, 122, 223, 215, 117, 191,
            254, 93, 244, 44, 57, 207, 226,
        ];
        let signature: Ed25519Signature = [
            120, 98, 147, 191, 39, 64, 138, 13, 210, 5, 188, 241, 245, 195, 130, 172, 212, 72, 202,
            247, 111, 18, 110, 65, 217, 45, 247, 184, 177, 186, 8, 241, 27, 210, 55, 77, 203, 164,
            177, 45, 45, 249, 249, 106, 112, 103, 249, 158, 64, 36, 99, 193, 25, 212, 59, 33, 32,
            213, 92, 178, 69, 9, 11, 15,
        ];
        assert_eq!(ed25519_sign(&key_pair, &message).unwrap(), signature);
    }

    #[test]
    fn test_ed25519_verify() {
        let public_key: Ed25519PublicKey = [
            82, 97, 171, 66, 47, 97, 89, 105, 150, 82, 88, 7, 31, 177, 30, 27, 118, 151, 80, 33,
            122, 223, 215, 117, 191, 254, 93, 244, 44, 57, 207, 226,
        ];
        let signature: Ed25519Signature = [
            120, 98, 147, 191, 39, 64, 138, 13, 210, 5, 188, 241, 245, 195, 130, 172, 212, 72, 202,
            247, 111, 18, 110, 65, 217, 45, 247, 184, 177, 186, 8, 241, 27, 210, 55, 77, 203, 164,
            177, 45, 45, 249, 249, 106, 112, 103, 249, 158, 64, 36, 99, 193, 25, 212, 59, 33, 32,
            213, 92, 178, 69, 9, 11, 15,
        ];
        let message = vec![72, 101, 108, 108, 111, 32, 87, 111, 114, 108, 100];
        ed25519_verify(&public_key, &signature, &message).unwrap();
    }
}