literate_crypto/pubkey/
ecc.rs

1//! Elliptic curve cryptography.
2
3use std::{fmt, marker::PhantomData};
4
5mod curve;
6mod ecdsa;
7mod num;
8mod schnorr;
9mod secp256k1;
10
11pub use {
12    curve::{Coordinates, Curve, InvalidPoint, Point},
13    ecdsa::{Ecdsa, EcdsaSignature},
14    num::Num,
15    schnorr::{
16        MultiSchnorr,
17        Schnorr,
18        SchnorrRandomness,
19        SchnorrSag,
20        SchnorrSagSignature,
21        SchnorrSignature,
22    },
23    secp256k1::Secp256k1,
24};
25
26#[derive(Debug)]
27pub struct PrivateKey<C>(num::Num, PhantomData<C>);
28
29impl<C> Clone for PrivateKey<C> {
30    fn clone(&self) -> Self {
31        *self
32    }
33}
34
35impl<C> Copy for PrivateKey<C> {}
36
37impl<C: Curve> PrivateKey<C> {
38    pub fn new(n: num::Num) -> Result<Self, InvalidPrivateKey> {
39        // Verify that the private key is reduced modulo N.
40        if n < C::N && n != Num::ZERO {
41            Ok(Self(n, Default::default()))
42        } else {
43            Err(InvalidPrivateKey)
44        }
45    }
46
47    /// Derive the [public key](PublicKey) from a private key.
48    ///
49    /// This is done by simply multiplying the private key with the [generator
50    /// point](crate::ecc::Curve::g).
51    pub fn derive(&self) -> PublicKey<C> {
52        PublicKey::new(self.0 * C::g()).unwrap()
53    }
54}
55
56#[derive(Debug)]
57pub struct PublicKey<C> {
58    x: Num,
59    y: Num,
60    _curve: PhantomData<C>,
61}
62
63impl<C> Clone for PublicKey<C> {
64    fn clone(&self) -> Self {
65        *self
66    }
67}
68
69impl<C> Copy for PublicKey<C> {}
70
71impl<C: Curve> PublicKey<C> {
72    pub fn new(p: Point<C>) -> Result<Self, InvalidPublicKey> {
73        match p.coordinates() {
74            Coordinates::Infinity => Err(InvalidPublicKey),
75            Coordinates::Finite(x, y) => Ok(Self {
76                x,
77                y,
78                _curve: Default::default(),
79            }),
80        }
81    }
82
83    pub fn point(&self) -> Point<C> {
84        Point::new(self.x, self.y).unwrap()
85    }
86
87    pub fn x(&self) -> Num {
88        self.x
89    }
90
91    pub fn y(&self) -> Num {
92        self.y
93    }
94}
95
96/// Error indicating that a private key is invalid.
97#[derive(Debug, Clone, Copy)]
98pub struct InvalidPrivateKey;
99
100impl fmt::Display for InvalidPrivateKey {
101    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
102        write!(f, "invalid private key")
103    }
104}
105
106impl std::error::Error for InvalidPrivateKey {}
107
108/// Error indicating that a public key is invalid.
109#[derive(Debug, Clone, Copy)]
110pub struct InvalidPublicKey;
111
112impl fmt::Display for InvalidPublicKey {
113    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
114        write!(f, "invalid public key")
115    }
116}
117
118impl std::error::Error for InvalidPublicKey {}