cardano_crypto/key/
hash.rs

1//! Key hash types using Blake2b-224
2//!
3//! This module provides hash types for verification key hashes, matching the
4//! types used in cardano-api. All key hashes use Blake2b-224 (28 bytes).
5//!
6//! # Hash Types
7//!
8//! | Type | Description | Size |
9//! |------|-------------|------|
10//! | `KeyHash` | Generic verification key hash | 28 bytes |
11//! | `PaymentKeyHash` | Payment verification key hash | 28 bytes |
12//! | `StakeKeyHash` | Stake verification key hash | 28 bytes |
13//! | `PoolKeyHash` | Stake pool key hash (pool ID) | 28 bytes |
14//! | `VrfKeyHash` | VRF verification key hash | 28 bytes |
15//!
16//! # Examples
17//!
18//! ```rust
19//! use cardano_crypto::key::hash::{KeyHash, hash_verification_key};
20//!
21//! let vk = [0u8; 32]; // Ed25519 verification key
22//! let hash = hash_verification_key(&vk);
23//! assert_eq!(hash.len(), 28);
24//! ```
25
26use crate::hash::{Blake2b224, HashAlgorithm};
27
28/// Size of a key hash in bytes (Blake2b-224 = 28 bytes)
29pub const KEY_HASH_SIZE: usize = 28;
30
31/// Generic key hash type (Blake2b-224)
32///
33/// Used as the base type for all verification key hashes.
34pub type KeyHash = [u8; KEY_HASH_SIZE];
35
36/// Payment verification key hash
37///
38/// Hash of an Ed25519 payment verification key, used in addresses.
39pub type PaymentKeyHash = KeyHash;
40
41/// Stake verification key hash
42///
43/// Hash of an Ed25519 stake verification key, used in reward addresses.
44pub type StakeKeyHash = KeyHash;
45
46/// Stake pool key hash (Pool ID)
47///
48/// Hash of a stake pool's cold verification key. This is what identifies
49/// a stake pool on-chain and is displayed as the pool ID.
50pub type PoolKeyHash = KeyHash;
51
52/// VRF verification key hash
53///
54/// Hash of a VRF verification key, used to bind VRF keys to pools.
55pub type VrfKeyHash = KeyHash;
56
57/// Genesis key hash
58///
59/// Hash of a genesis verification key.
60pub type GenesisKeyHash = KeyHash;
61
62/// Genesis delegate key hash
63///
64/// Hash of a genesis delegate verification key.
65pub type GenesisDelegateKeyHash = KeyHash;
66
67/// DRep key hash
68///
69/// Hash of a delegated representative verification key for governance.
70pub type DRepKeyHash = KeyHash;
71
72/// Committee cold key hash
73///
74/// Hash of a constitutional committee cold verification key.
75pub type CommitteeColdKeyHash = KeyHash;
76
77/// Committee hot key hash
78///
79/// Hash of a constitutional committee hot verification key.
80pub type CommitteeHotKeyHash = KeyHash;
81
82/// Hash a verification key using Blake2b-224
83///
84/// This function hashes any 32-byte Ed25519 verification key to produce
85/// a 28-byte key hash.
86///
87/// # Arguments
88///
89/// * `vk` - 32-byte Ed25519 verification key
90///
91/// # Returns
92///
93/// 28-byte Blake2b-224 hash of the verification key
94///
95/// # Examples
96///
97/// ```rust
98/// use cardano_crypto::key::hash::hash_verification_key;
99///
100/// let vk = [0u8; 32];
101/// let hash = hash_verification_key(&vk);
102/// assert_eq!(hash.len(), 28);
103/// ```
104pub fn hash_verification_key(vk: &[u8; 32]) -> KeyHash {
105    let hash_vec = Blake2b224::hash(vk);
106    let mut result = [0u8; KEY_HASH_SIZE];
107    result.copy_from_slice(&hash_vec[..KEY_HASH_SIZE]);
108    result
109}
110
111/// Hash a raw byte slice using Blake2b-224
112///
113/// This function can hash verification keys of any size (e.g., VRF keys which are 32 bytes).
114///
115/// # Arguments
116///
117/// * `data` - Byte slice to hash
118///
119/// # Returns
120///
121/// 28-byte Blake2b-224 hash
122///
123/// # Examples
124///
125/// ```rust
126/// use cardano_crypto::key::hash::hash_raw;
127///
128/// let data = [0u8; 32];
129/// let hash = hash_raw(&data);
130/// assert_eq!(hash.len(), 28);
131/// ```
132pub fn hash_raw(data: &[u8]) -> KeyHash {
133    let hash_vec = Blake2b224::hash(data);
134    let mut result = [0u8; KEY_HASH_SIZE];
135    result.copy_from_slice(&hash_vec[..KEY_HASH_SIZE]);
136    result
137}
138
139/// Hash a payment verification key
140///
141/// # Arguments
142///
143/// * `vk` - 32-byte Ed25519 payment verification key
144///
145/// # Returns
146///
147/// Payment key hash (28 bytes)
148///
149/// # Examples
150///
151/// ```rust
152/// use cardano_crypto::key::hash::hash_payment_verification_key;
153///
154/// let vk = [0u8; 32];
155/// let hash = hash_payment_verification_key(&vk);
156/// assert_eq!(hash.len(), 28);
157/// ```
158pub fn hash_payment_verification_key(vk: &[u8; 32]) -> PaymentKeyHash {
159    hash_verification_key(vk)
160}
161
162/// Hash a stake verification key
163///
164/// # Arguments
165///
166/// * `vk` - 32-byte Ed25519 stake verification key
167///
168/// # Returns
169///
170/// Stake key hash (28 bytes)
171///
172/// # Examples
173///
174/// ```rust
175/// use cardano_crypto::key::hash::hash_stake_verification_key;
176///
177/// let vk = [0u8; 32];
178/// let hash = hash_stake_verification_key(&vk);
179/// assert_eq!(hash.len(), 28);
180/// ```
181pub fn hash_stake_verification_key(vk: &[u8; 32]) -> StakeKeyHash {
182    hash_verification_key(vk)
183}
184
185/// Hash a stake pool verification key to get the pool ID
186///
187/// # Arguments
188///
189/// * `vk` - 32-byte Ed25519 pool cold verification key
190///
191/// # Returns
192///
193/// Pool key hash / Pool ID (28 bytes)
194///
195/// # Examples
196///
197/// ```rust
198/// use cardano_crypto::key::hash::hash_pool_verification_key;
199///
200/// let vk = [0u8; 32];
201/// let pool_id = hash_pool_verification_key(&vk);
202/// assert_eq!(pool_id.len(), 28);
203/// ```
204pub fn hash_pool_verification_key(vk: &[u8; 32]) -> PoolKeyHash {
205    hash_verification_key(vk)
206}
207
208/// Hash a VRF verification key
209///
210/// # Arguments
211///
212/// * `vk` - 32-byte VRF verification key
213///
214/// # Returns
215///
216/// VRF key hash (28 bytes)
217///
218/// # Examples
219///
220/// ```rust
221/// use cardano_crypto::key::hash::hash_vrf_verification_key;
222///
223/// let vk = [0u8; 32];
224/// let hash = hash_vrf_verification_key(&vk);
225/// assert_eq!(hash.len(), 28);
226/// ```
227pub fn hash_vrf_verification_key(vk: &[u8; 32]) -> VrfKeyHash {
228    hash_verification_key(vk)
229}
230
231/// Hash a genesis verification key
232///
233/// # Arguments
234///
235/// * `vk` - 32-byte Ed25519 genesis verification key
236///
237/// # Returns
238///
239/// Genesis key hash (28 bytes)
240pub fn hash_genesis_verification_key(vk: &[u8; 32]) -> GenesisKeyHash {
241    hash_verification_key(vk)
242}
243
244/// Hash a genesis delegate verification key
245///
246/// # Arguments
247///
248/// * `vk` - 32-byte Ed25519 genesis delegate verification key
249///
250/// # Returns
251///
252/// Genesis delegate key hash (28 bytes)
253pub fn hash_genesis_delegate_verification_key(vk: &[u8; 32]) -> GenesisDelegateKeyHash {
254    hash_verification_key(vk)
255}
256
257/// Hash a DRep verification key
258///
259/// # Arguments
260///
261/// * `vk` - 32-byte Ed25519 DRep verification key
262///
263/// # Returns
264///
265/// DRep key hash (28 bytes)
266pub fn hash_drep_verification_key(vk: &[u8; 32]) -> DRepKeyHash {
267    hash_verification_key(vk)
268}
269
270/// Hash a committee cold verification key
271///
272/// # Arguments
273///
274/// * `vk` - 32-byte Ed25519 committee cold verification key
275///
276/// # Returns
277///
278/// Committee cold key hash (28 bytes)
279pub fn hash_committee_cold_verification_key(vk: &[u8; 32]) -> CommitteeColdKeyHash {
280    hash_verification_key(vk)
281}
282
283/// Hash a committee hot verification key
284///
285/// # Arguments
286///
287/// * `vk` - 32-byte Ed25519 committee hot verification key
288///
289/// # Returns
290///
291/// Committee hot key hash (28 bytes)
292pub fn hash_committee_hot_verification_key(vk: &[u8; 32]) -> CommitteeHotKeyHash {
293    hash_verification_key(vk)
294}
295
296// =============================================================================
297// Tests
298// =============================================================================
299
300#[cfg(test)]
301mod tests {
302    use super::*;
303
304    #[test]
305    fn test_key_hash_size() {
306        assert_eq!(KEY_HASH_SIZE, 28);
307    }
308
309    #[test]
310    fn test_hash_verification_key() {
311        let vk = [0u8; 32];
312        let hash = hash_verification_key(&vk);
313        assert_eq!(hash.len(), 28);
314
315        // Deterministic - same input should produce same output
316        let hash2 = hash_verification_key(&vk);
317        assert_eq!(hash, hash2);
318    }
319
320    #[test]
321    fn test_different_inputs_produce_different_hashes() {
322        let vk1 = [0u8; 32];
323        let mut vk2 = [0u8; 32];
324        vk2[0] = 1;
325
326        let hash1 = hash_verification_key(&vk1);
327        let hash2 = hash_verification_key(&vk2);
328
329        assert_ne!(hash1, hash2);
330    }
331
332    #[test]
333    fn test_hash_raw() {
334        let data = [0u8; 32];
335        let hash = hash_raw(&data);
336        assert_eq!(hash.len(), 28);
337
338        // Should match verification key hash for same 32-byte input
339        let vk_hash = hash_verification_key(&data);
340        assert_eq!(hash, vk_hash);
341    }
342
343    #[test]
344    fn test_payment_key_hash() {
345        let vk = [1u8; 32];
346        let hash = hash_payment_verification_key(&vk);
347        assert_eq!(hash.len(), 28);
348    }
349
350    #[test]
351    fn test_stake_key_hash() {
352        let vk = [2u8; 32];
353        let hash = hash_stake_verification_key(&vk);
354        assert_eq!(hash.len(), 28);
355    }
356
357    #[test]
358    fn test_pool_key_hash() {
359        let vk = [3u8; 32];
360        let pool_id = hash_pool_verification_key(&vk);
361        assert_eq!(pool_id.len(), 28);
362    }
363
364    #[test]
365    fn test_vrf_key_hash() {
366        let vk = [4u8; 32];
367        let hash = hash_vrf_verification_key(&vk);
368        assert_eq!(hash.len(), 28);
369    }
370
371    #[test]
372    fn test_governance_key_hashes() {
373        let vk = [5u8; 32];
374
375        let drep_hash = hash_drep_verification_key(&vk);
376        let cc_cold_hash = hash_committee_cold_verification_key(&vk);
377        let cc_hot_hash = hash_committee_hot_verification_key(&vk);
378
379        // All use same underlying hash function
380        assert_eq!(drep_hash, cc_cold_hash);
381        assert_eq!(cc_cold_hash, cc_hot_hash);
382    }
383
384    #[test]
385    fn test_known_hash_vector() {
386        // Test with a known input to verify Blake2b-224 output
387        let vk = [0u8; 32];
388        let hash = hash_verification_key(&vk);
389
390        // The hash should be deterministic
391        // Blake2b-224 of 32 zero bytes
392        let expected_vec = Blake2b224::hash(&[0u8; 32]);
393        assert_eq!(hash[..], expected_vec[..]);
394    }
395}