1
//! Re-exporting Ed25519 implementations, and related utilities.
2
//!
3
//! Here we re-export types from [`ed25519_dalek`] that implement the
4
//! Ed25519 signature algorithm.  (TODO: Eventually, this module
5
//! should probably be replaced with a wrapper that uses the ed25519
6
//! trait and the Signature trait.)
7
//!
8
//! We additionally provide an `Ed25519Identity` type to represent the
9
//! unvalidated Ed25519 "identity keys" that we use throughout the Tor
10
//! protocol to uniquely identify a relay.
11

            
12
use base64ct::{Base64Unpadded, Encoding as _};
13
use curve25519_dalek::Scalar;
14
use std::fmt::{self, Debug, Display, Formatter};
15
use subtle::{Choice, ConstantTimeEq};
16

            
17
#[cfg(feature = "memquota-memcost")]
18
use {derive_deftly::Deftly, tor_memquota::derive_deftly_template_HasMemoryCost};
19

            
20
use ed25519_dalek::hazmat::ExpandedSecretKey;
21
use ed25519_dalek::{Signer as _, Verifier as _};
22

            
23
use crate::util::{ct::CtByteArray, rng::RngCompat};
24

            
25
/// An Ed25519 signature.
26
///
27
/// See [`ed25519_dalek::Signature`] for more information.
28
#[derive(Clone, Copy, Debug, Eq, PartialEq)]
29
pub struct Signature(pub(crate) ed25519_dalek::Signature);
30

            
31
/// An Ed25519 keypair.
32
///
33
/// (We do not provide a separate "private key only" type.)
34
///
35
/// See [`ed25519_dalek::SigningKey`] for more information.
36
#[derive(Debug)]
37
pub struct Keypair(pub(crate) ed25519_dalek::SigningKey);
38

            
39
/// An Ed25519 public key.
40
///
41
/// See [`ed25519_dalek::SigningKey`] for more information.
42
#[derive(Clone, Copy, Debug, Eq, PartialEq)]
43
pub struct PublicKey(pub(crate) ed25519_dalek::VerifyingKey);
44

            
45
impl<'a> From<&'a Keypair> for PublicKey {
46
1038
    fn from(value: &'a Keypair) -> Self {
47
1038
        PublicKey((&value.0).into())
48
1038
    }
49
}
50

            
51
impl PublicKey {
52
    /// Construct a public key from its byte representation.
53
76364
    pub fn from_bytes(bytes: &[u8; 32]) -> Result<Self, signature::Error> {
54
76364
        Ok(PublicKey(ed25519_dalek::VerifyingKey::from_bytes(bytes)?))
55
76364
    }
56

            
57
    /// Return a reference to the byte representation of this public key.
58
150540
    pub fn as_bytes(&self) -> &[u8; 32] {
59
150540
        self.0.as_bytes()
60
150540
    }
61
    /// Return the byte representation of this public key.
62
9310
    pub fn to_bytes(&self) -> [u8; 32] {
63
9310
        self.0.to_bytes()
64
9310
    }
65
    /// Verify a signature using this public key.
66
    ///
67
    /// See [`ed25519_dalek::VerifyingKey::verify`] for more information.
68
998
    pub fn verify(&self, message: &[u8], signature: &Signature) -> Result<(), signature::Error> {
69
998
        self.0.verify(message, &signature.0)
70
998
    }
71
}
72
impl Keypair {
73
    /// Generate a new random ed25519 keypair.
74
1333
    pub fn generate<R: rand_core::RngCore + rand_core::CryptoRng>(csprng: &mut R) -> Self {
75
1333
        Self(ed25519_dalek::SigningKey::generate(&mut RngCompat::new(
76
1333
            csprng,
77
1333
        )))
78
1333
    }
79
    /// Construct an ed25519 keypair from the byte representation of its secret key.
80
74
    pub fn from_bytes(bytes: &[u8; 32]) -> Self {
81
74
        Self(ed25519_dalek::SigningKey::from_bytes(bytes))
82
74
    }
83
    /// Return a reference to the byte representation of the secret key in this keypair.
84
4368
    pub fn as_bytes(&self) -> &[u8; 32] {
85
4368
        self.0.as_bytes()
86
4368
    }
87
    /// Return to the byte representation of the secret key in this keypair.
88
298
    pub fn to_bytes(&self) -> [u8; 32] {
89
298
        self.0.to_bytes()
90
298
    }
91
    /// Return the public key in this keypair.
92
79698
    pub fn verifying_key(&self) -> PublicKey {
93
79698
        PublicKey(*self.0.as_ref())
94
79698
    }
95
    /// Verify a signature generated with this keypair.
96
222
    pub fn verify(&self, message: &[u8], signature: &Signature) -> Result<(), signature::Error> {
97
222
        self.0.verify(message, &signature.0)
98
222
    }
99
    /// Sign a message using this keypair.
100
39886
    pub fn sign(&self, message: &[u8]) -> Signature {
101
39886
        Signature(self.0.sign(message))
102
39886
    }
103
}
104
impl Signature {
105
    /// Construct this signature from its byte representation.
106
24272
    pub fn from_bytes(bytes: &[u8; 64]) -> Self {
107
24272
        Self(ed25519_dalek::Signature::from_bytes(bytes))
108
24272
    }
109
    /// Return the byte representation of this signature.
110
45658
    pub fn to_bytes(&self) -> [u8; 64] {
111
45658
        self.0.to_bytes()
112
45658
    }
113
}
114
impl<'a> TryFrom<&'a [u8]> for PublicKey {
115
    type Error = signature::Error;
116

            
117
22496
    fn try_from(value: &'a [u8]) -> Result<Self, Self::Error> {
118
22496
        Ok(Self(ed25519_dalek::VerifyingKey::try_from(value)?))
119
22496
    }
120
}
121
impl<'a> From<&'a [u8; 32]> for Keypair {
122
7178
    fn from(value: &'a [u8; 32]) -> Self {
123
7178
        Self(ed25519_dalek::SigningKey::from(value))
124
7178
    }
125
}
126
impl From<[u8; 64]> for Signature {
127
5108
    fn from(value: [u8; 64]) -> Self {
128
5108
        Signature(value.into())
129
5108
    }
130
}
131
impl<'a> From<&'a [u8; 64]> for Signature {
132
    fn from(value: &'a [u8; 64]) -> Self {
133
        Signature(value.into())
134
    }
135
}
136

            
137
/// The length of an ED25519 identity, in bytes.
138
pub const ED25519_ID_LEN: usize = 32;
139

            
140
/// The length of an ED25519 signature, in bytes.
141
pub const ED25519_SIGNATURE_LEN: usize = 64;
142

            
143
/// A variant of [`Keypair`] containing an [`ExpandedSecretKey`].
144
///
145
/// In the Tor protocol, we use this type for blinded onion service identity keys
146
/// (KS_hs_blind_id).  Since their scalar values are computed, rather than taken
147
/// directly from a
148
/// SHA-512 transformation of a SecretKey, we cannot use the regular `Keypair`
149
/// type.
150
#[allow(clippy::exhaustive_structs)]
151
pub struct ExpandedKeypair {
152
    /// The secret part of the key.
153
    pub(crate) secret: ExpandedSecretKey,
154
    /// The public part of this key.
155
    ///
156
    /// NOTE: As with [`ed25519_dalek::SigningKey`], this public key _must_ be
157
    /// the public key matching `secret`.  Putting a different public key in
158
    /// here would enable a class of attacks against ed25519 and enable secret
159
    /// key recovery.
160
    pub(crate) public: PublicKey,
161
}
162

            
163
impl ExpandedKeypair {
164
    /// Return the public part of this expanded keypair.
165
48046
    pub fn public(&self) -> &PublicKey {
166
48046
        &self.public
167
48046
    }
168

            
169
    // NOTE: There is deliberately no secret() function.  If we had one, we
170
    // would be exposing an unescorted secret key, which is part of
171
    // ed25519::hazmat.
172

            
173
    /// Compute a signature over a message using this keypair.
174
5724
    pub fn sign(&self, message: &[u8]) -> Signature {
175
        use sha2::Sha512;
176
        // See notes on ExpandedKeypair about why this hazmat is okay to use.
177
5724
        Signature(ed25519_dalek::hazmat::raw_sign::<Sha512>(
178
5724
            &self.secret,
179
5724
            message,
180
5724
            &self.public.0,
181
5724
        ))
182
5724
    }
183

            
184
    /// Return a representation of the secret key in this keypair.
185
    ///
186
    /// (Since it is an expanded secret key, we represent it as its scalar part
187
    /// followed by its hash_prefix.)
188
6774
    pub fn to_secret_key_bytes(&self) -> [u8; 64] {
189
6774
        let mut output = [0_u8; 64];
190
6774
        output[0..32].copy_from_slice(&self.secret.scalar.to_bytes());
191
6774
        output[32..64].copy_from_slice(&self.secret.hash_prefix);
192
6774
        output
193
6774
    }
194

            
195
    /// Reconstruct a key from its byte representation as returned by
196
    /// `to_secret_key_bytes()`.
197
    ///
198
    /// Return None if the input cannot be the output of `to_secret_key_bytes()`.
199
    //
200
    // NOTE: Returning None is a bit silly, but that's what Dalek does.
201
22886
    pub fn from_secret_key_bytes(bytes: [u8; 64]) -> Option<Self> {
202
22886
        let scalar = Option::from(Scalar::from_bytes_mod_order(
203
22886
            bytes[0..32].try_into().expect("wrong length on slice"),
204
22886
        ))?;
205
22886
        let hash_prefix = bytes[32..64].try_into().expect("wrong length on slice");
206
22886
        let secret = ExpandedSecretKey {
207
22886
            scalar,
208
22886
            hash_prefix,
209
22886
        };
210
22886
        let public = PublicKey((&secret).into());
211
22886
        Some(Self { secret, public })
212
22886
    }
213

            
214
    // NOTE: There is deliberately no constructor here that takes a (secret,
215
    // public) pair.  If there were, you could construct a pair with a
216
    // mismatched public key.
217
}
218

            
219
impl<'a> From<&'a Keypair> for ExpandedKeypair {
220
742
    fn from(kp: &'a Keypair) -> ExpandedKeypair {
221
742
        ExpandedKeypair {
222
742
            secret: kp.as_bytes().into(),
223
742
            public: kp.into(),
224
742
        }
225
742
    }
226
}
227

            
228
impl From<ExpandedKeypair> for PublicKey {
229
    fn from(ekp: ExpandedKeypair) -> PublicKey {
230
        ekp.public
231
    }
232
}
233

            
234
/// An unchecked, unvalidated Ed25519 key.
235
///
236
/// This key is an "identity" in the sense that it identifies (up to) one
237
/// Ed25519 key.  It may also represent the identity for a particular entity,
238
/// such as a relay or an onion service.
239
///
240
/// This type is distinct from an Ed25519 [`PublicKey`] for several reasons:
241
///  * We're storing it in a compact format, whereas the public key
242
///    implementation might want an expanded form for more efficient key
243
///    validation.
244
///  * This type hasn't checked whether the bytes here actually _are_ a valid
245
///    Ed25519 public key.
246
#[derive(Clone, Copy, Hash, PartialOrd, Ord, Eq, PartialEq)]
247
#[cfg_attr(
248
    feature = "memquota-memcost",
249
    derive(Deftly),
250
    derive_deftly(HasMemoryCost)
251
)]
252
pub struct Ed25519Identity {
253
    /// A raw unchecked Ed25519 public key.
254
    id: CtByteArray<ED25519_ID_LEN>,
255
}
256

            
257
impl Ed25519Identity {
258
    /// Construct a new Ed25519 identity from a 32-byte sequence.
259
    ///
260
    /// This might or might not actually be a valid Ed25519 public key.
261
    ///
262
    /// ```
263
    /// use tor_llcrypto::pk::ed25519::{Ed25519Identity, PublicKey};
264
    ///
265
    /// let bytes = b"klsadjfkladsfjklsdafkljasdfsdsd!";
266
    /// let id = Ed25519Identity::new(*bytes);
267
    /// let pk: Result<PublicKey,_> = (&id).try_into();
268
    /// assert!(pk.is_ok());
269
    ///
270
    /// let bytes = b"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa";
271
    /// let id = Ed25519Identity::new(*bytes);
272
    /// let pk: Result<PublicKey,_> = (&id).try_into();
273
    /// assert!(pk.is_err());
274
    /// ```
275
2122838
    pub fn new(id: [u8; 32]) -> Self {
276
2122838
        Ed25519Identity { id: id.into() }
277
2122838
    }
278
    /// If `id` is of the correct length, wrap it in an Ed25519Identity.
279
1521588
    pub fn from_bytes(id: &[u8]) -> Option<Self> {
280
1521588
        Some(Ed25519Identity::new(id.try_into().ok()?))
281
1521588
    }
282
    /// Return a reference to the bytes in this key.
283
228068
    pub fn as_bytes(&self) -> &[u8] {
284
228068
        &self.id.as_ref()[..]
285
228068
    }
286
}
287

            
288
impl From<[u8; ED25519_ID_LEN]> for Ed25519Identity {
289
575942
    fn from(id: [u8; ED25519_ID_LEN]) -> Self {
290
575942
        Ed25519Identity::new(id)
291
575942
    }
292
}
293

            
294
impl From<Ed25519Identity> for [u8; ED25519_ID_LEN] {
295
14726
    fn from(value: Ed25519Identity) -> Self {
296
14726
        value.id.into()
297
14726
    }
298
}
299

            
300
impl From<PublicKey> for Ed25519Identity {
301
94498
    fn from(pk: PublicKey) -> Self {
302
94498
        (&pk).into()
303
94498
    }
304
}
305

            
306
impl From<&PublicKey> for Ed25519Identity {
307
133644
    fn from(pk: &PublicKey) -> Self {
308
133644
        // This unwrap is safe because the public key is always 32 bytes
309
133644
        // long.
310
133644
        Ed25519Identity::from_bytes(pk.as_bytes()).expect("Ed25519 public key had wrong length?")
311
133644
    }
312
}
313

            
314
impl TryFrom<&Ed25519Identity> for PublicKey {
315
    type Error = ed25519_dalek::SignatureError;
316
40774
    fn try_from(id: &Ed25519Identity) -> Result<PublicKey, Self::Error> {
317
40774
        PublicKey::from_bytes(id.id.as_ref())
318
40774
    }
319
}
320

            
321
impl TryFrom<Ed25519Identity> for PublicKey {
322
    type Error = ed25519_dalek::SignatureError;
323
26344
    fn try_from(id: Ed25519Identity) -> Result<PublicKey, Self::Error> {
324
26344
        (&id).try_into()
325
26344
    }
326
}
327

            
328
impl ConstantTimeEq for Ed25519Identity {
329
    fn ct_eq(&self, other: &Self) -> Choice {
330
        self.id.ct_eq(&other.id)
331
    }
332
}
333

            
334
impl Display for Ed25519Identity {
335
16872
    fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
336
16872
        write!(f, "{}", Base64Unpadded::encode_string(self.id.as_ref()))
337
16872
    }
338
}
339

            
340
impl Debug for Ed25519Identity {
341
5920
    fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
342
5920
        write!(f, "Ed25519Identity {{ {} }}", self)
343
5920
    }
344
}
345

            
346
impl safelog::Redactable for Ed25519Identity {
347
    /// Warning: This displays 12 bits of the ed25519 identity, which is
348
    /// enough to narrow down a public relay by a great deal.
349
74
    fn display_redacted(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
350
74
        write!(
351
74
            f,
352
74
            "{}…",
353
74
            &Base64Unpadded::encode_string(self.id.as_ref())[..2]
354
74
        )
355
74
    }
356

            
357
    fn debug_redacted(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
358
        write!(f, "Ed25519Identity {{ {} }}", self.redacted())
359
    }
360
}
361

            
362
impl serde::Serialize for Ed25519Identity {
363
17054
    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
364
17054
    where
365
17054
        S: serde::Serializer,
366
17054
    {
367
17054
        if serializer.is_human_readable() {
368
17052
            serializer.serialize_str(&Base64Unpadded::encode_string(self.id.as_ref()))
369
        } else {
370
2
            serializer.serialize_bytes(&self.id.as_ref()[..])
371
        }
372
17054
    }
373
}
374

            
375
impl<'de> serde::Deserialize<'de> for Ed25519Identity {
376
530
    fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
377
530
    where
378
530
        D: serde::Deserializer<'de>,
379
530
    {
380
530
        if deserializer.is_human_readable() {
381
            /// Helper for deserialization
382
            struct EdIdentityVisitor;
383
            impl<'de> serde::de::Visitor<'de> for EdIdentityVisitor {
384
                type Value = Ed25519Identity;
385
                fn expecting(&self, fmt: &mut std::fmt::Formatter<'_>) -> fmt::Result {
386
                    fmt.write_str("base64-encoded Ed25519 public key")
387
                }
388
526
                fn visit_str<E>(self, s: &str) -> Result<Self::Value, E>
389
526
                where
390
526
                    E: serde::de::Error,
391
526
                {
392
526
                    let bytes = Base64Unpadded::decode_vec(s).map_err(E::custom)?;
393
526
                    Ed25519Identity::from_bytes(&bytes)
394
526
                        .ok_or_else(|| E::custom("wrong length for Ed25519 public key"))
395
526
                }
396
            }
397

            
398
526
            deserializer.deserialize_str(EdIdentityVisitor)
399
        } else {
400
            /// Helper for deserialization
401
            struct EdIdentityVisitor;
402
            impl<'de> serde::de::Visitor<'de> for EdIdentityVisitor {
403
                type Value = Ed25519Identity;
404
                fn expecting(&self, fmt: &mut std::fmt::Formatter<'_>) -> fmt::Result {
405
                    fmt.write_str("ed25519 public key")
406
                }
407
4
                fn visit_bytes<E>(self, bytes: &[u8]) -> Result<Self::Value, E>
408
4
                where
409
4
                    E: serde::de::Error,
410
4
                {
411
4
                    Ed25519Identity::from_bytes(bytes)
412
4
                        .ok_or_else(|| E::custom("wrong length for ed25519 public key"))
413
4
                }
414
            }
415
4
            deserializer.deserialize_bytes(EdIdentityVisitor)
416
        }
417
530
    }
418
}
419

            
420
/// An ed25519 signature, plus the document that it signs and its
421
/// public key.
422
#[derive(Clone, Debug)]
423
#[cfg_attr(
424
    feature = "memquota-memcost",
425
    derive(Deftly),
426
    derive_deftly(HasMemoryCost)
427
)]
428
pub struct ValidatableEd25519Signature {
429
    /// The key that allegedly produced the signature
430
    #[cfg_attr(feature = "memquota-memcost", deftly(has_memory_cost(copy)))]
431
    key: PublicKey,
432
    /// The alleged signature
433
    #[cfg_attr(feature = "memquota-memcost", deftly(has_memory_cost(copy)))]
434
    sig: Signature,
435
    /// The entire body of text that is allegedly signed here.
436
    ///
437
    /// TODO: It's not so good to have this included here; it
438
    /// would be better to have a patch to ed25519_dalek to allow
439
    /// us to pre-hash the signed thing, and just store a digest.
440
    /// We can't use that with the 'prehash' variant of ed25519,
441
    /// since that has different constants.
442
    entire_text_of_signed_thing: Vec<u8>,
443
}
444

            
445
impl ValidatableEd25519Signature {
446
    /// Create a new ValidatableEd25519Signature
447
28050
    pub fn new(key: PublicKey, sig: Signature, text: &[u8]) -> Self {
448
28050
        ValidatableEd25519Signature {
449
28050
            key,
450
28050
            sig,
451
28050
            entire_text_of_signed_thing: text.into(),
452
28050
        }
453
28050
    }
454

            
455
    /// View the interior of this signature object.
456
16132
    pub(crate) fn as_parts(&self) -> (&PublicKey, &Signature, &[u8]) {
457
16132
        (&self.key, &self.sig, &self.entire_text_of_signed_thing[..])
458
16132
    }
459

            
460
    /// Return a reference to the underlying Signature.
461
444
    pub fn signature(&self) -> &Signature {
462
444
        &self.sig
463
444
    }
464
}
465

            
466
impl super::ValidatableSignature for ValidatableEd25519Signature {
467
448
    fn is_valid(&self) -> bool {
468
448
        self.key
469
448
            .verify(&self.entire_text_of_signed_thing[..], &self.sig)
470
448
            .is_ok()
471
448
    }
472

            
473
14282
    fn as_ed25519(&self) -> Option<&ValidatableEd25519Signature> {
474
14282
        Some(self)
475
14282
    }
476
}
477

            
478
/// Perform a batch verification operation on the provided signatures
479
///
480
/// Return `true` if _every_ signature is valid; otherwise return `false`.
481
///
482
/// Note that the mathematics for batch validation are slightly
483
/// different than those for normal one-signature validation.  Because
484
/// of this, it is possible for an ostensible signature that passes
485
/// one validation algorithm might fail the other.  (Well-formed
486
/// signatures generated by a correct Ed25519 implementation will
487
/// always pass both kinds of validation, and an attacker should not
488
/// be able to forge a signature that passes either kind.)
489
6586
pub fn validate_batch(sigs: &[&ValidatableEd25519Signature]) -> bool {
490
    use crate::pk::ValidatableSignature;
491
6586
    if sigs.is_empty() {
492
        // ed25519_dalek has nonzero cost for a batch-verification of
493
        // zero sigs.
494
1332
        true
495
5254
    } else if sigs.len() == 1 {
496
        // Validating one signature in the traditional way is faster.
497
74
        sigs[0].is_valid()
498
    } else {
499
5180
        let mut ed_msgs = Vec::new();
500
5180
        let mut ed_sigs = Vec::new();
501
5180
        let mut ed_pks = Vec::new();
502
21312
        for ed_sig in sigs {
503
16132
            let (pk, sig, msg) = ed_sig.as_parts();
504
16132
            ed_sigs.push(sig.0);
505
16132
            ed_pks.push(pk.0);
506
16132
            ed_msgs.push(msg);
507
16132
        }
508
5180
        ed25519_dalek::verify_batch(&ed_msgs[..], &ed_sigs[..], &ed_pks[..]).is_ok()
509
    }
510
6586
}
511

            
512
/// An object that has an Ed25519 [`PublicKey`].
513
pub trait Ed25519PublicKey {
514
    /// Get the Ed25519 [`PublicKey`].
515
    fn public_key(&self) -> PublicKey;
516
}
517

            
518
impl Ed25519PublicKey for Keypair {
519
34188
    fn public_key(&self) -> PublicKey {
520
34188
        Keypair::verifying_key(self)
521
34188
    }
522
}
523

            
524
/// An object that can generate Ed25519 signatures.
525
pub trait Ed25519SigningKey {
526
    /// Sign a message with this key.
527
    fn sign(&self, message: &[u8]) -> Signature;
528
}
529

            
530
impl Ed25519SigningKey for Keypair {
531
33596
    fn sign(&self, message: &[u8]) -> Signature {
532
33596
        Keypair::sign(self, message)
533
33596
    }
534
}
535
impl Ed25519SigningKey for ExpandedKeypair {
536
    fn sign(&self, message: &[u8]) -> Signature {
537
        ExpandedKeypair::sign(self, message)
538
    }
539
}