deadbolt_crypto/
lib.rs

1#![allow(dead_code)]
2#![allow(unused_imports)]
3
4extern crate secrecy;
5
6use secrecy::{Secret, SecretString};
7
8pub mod encryption;
9pub mod hash;
10pub mod rand;
11
12#[cfg(test)]
13mod tests {
14    use secrecy::ExposeSecret;
15    use secrecy::Secret;
16    use secrecy::SecretString;
17
18    use crate::encryption;
19    use crate::encryption::Encryption;
20    use crate::encryption::StreamEncryption;
21    use crate::hash::Hash;
22    use crate::hash::Hkdf;
23    use crate::hash::Hmac;
24    use crate::hash::PasswordHash;
25
26    use super::*;
27
28    #[test]
29    fn test_aes_encryption() {
30        let key = Secret::new(b"32_bytes_master_key_of_AES-256!!".to_vec());
31        let plaintext = b"yellow_submarine";
32        let mut aes = Encryption::new(&key);
33        let ciphertext = aes.encrypt(plaintext.to_vec(), 1).unwrap();
34
35        let decrypted = aes.decrypt(ciphertext.nonce, ciphertext.data, 1).unwrap();
36        assert_eq!(decrypted.data, plaintext);
37    }
38
39    #[test]
40    fn test_chacha_encryption() {
41        let key = Secret::new(b"32_bytes_master_key_of_ChaCha20!".to_vec());
42        let plaintext = b"yellow_submarine";
43        let mut aes = Encryption::new(&key);
44        let ciphertext = aes.encrypt(plaintext.to_vec(), 2).unwrap();
45
46        let decrypted = aes.decrypt(ciphertext.nonce, ciphertext.data, 2).unwrap();
47        assert_eq!(decrypted.data, plaintext);
48    }
49
50    #[test]
51    fn test_failed_decryption() {
52        let key = Secret::new(b"32_bytes_master_key_of_AES-256!!".to_vec());
53        let plaintext = b"yellow_submarine";
54        let mut aes = Encryption::new(&key);
55        let ciphertext = aes.encrypt(plaintext.to_vec(), 1).unwrap();
56
57        let incorrect_key = Secret::new(b"32_bytes_master_key_of_AES-256??".to_vec());
58        aes = Encryption::new(&incorrect_key);
59        let decrypted = aes.decrypt(ciphertext.nonce, ciphertext.data, 1);
60
61        assert!(decrypted.is_err());
62    }
63
64    #[test]
65    fn test_stream_encryption() {
66        let key = Secret::new(b"32_bytes_master_key_of_ChaCha8!!".to_vec());
67        let plaintext = b"yellow_submarine";
68        let ciphertext = StreamEncryption::encrypt(&key, plaintext.as_ref());
69
70        let decrypted = StreamEncryption::decrypt(&key, &ciphertext);
71        assert_eq!(decrypted, plaintext);
72    }
73
74    #[test]
75    fn test_hash() {
76        let message = b"yellow_submarine";
77        let digest = Hash::sha256(&message.to_vec());
78
79        assert_eq!(
80            "482ea0629467352543559ecbc2ce0c2010c2d0fac069ffc304f5cf15af0ff85e",
81            hex::encode(digest)
82        );
83    }
84
85    #[test]
86    fn test_hmac() {
87        let secret = Secret::new(b"some_secret!!".to_vec());
88        let digest_to_compare =
89            hex::decode("aa504f4e415b461fd97296b18ed12514e389743a4cb2599511d55557afa6729d")
90                .unwrap();
91        let mut mac = Hmac::new(&secret);
92        mac.update(b"test".as_ref());
93
94        assert!(mac.verify(&digest_to_compare).is_ok());
95    }
96
97    #[test]
98    fn test_key_derivation() {
99        let password: SecretString = SecretString::new("yellow_submarine".to_string());
100        let key_material =
101            PasswordHash::argon2d(password, "yellow_submarine".as_bytes(), 2, 1, 19 * 1024);
102
103        assert_eq!(key_material.expose_secret().len(), 32);
104        let output_key_material = Hkdf::expand(key_material);
105
106        let expected = hex::decode(
107            "\
108                a6956358323fb84f92b0e0ef12f6df793423e76589b89da56d0f0ed018d6dc54\
109                8735c1432cda528f981f25fc374fd6609cec138a56264c20f002d34a77b652c6",
110        )
111        .unwrap();
112
113        assert_eq!(output_key_material.expose_secret().to_vec(), expected);
114    }
115
116    #[test]
117    fn test_check_aes_reused_nonce() {
118        let key = Secret::new(b"32_bytes_master_key_of_AES-256!!".to_vec());
119        let plaintext = b"yellow_submarine";
120        let mut aes = Encryption::new(&key);
121        let ciphertext1 = aes.encrypt(plaintext.to_vec(), 1).unwrap();
122        let ciphertext2 = aes.encrypt(plaintext.to_vec(), 1).unwrap();
123
124        assert_ne!(ciphertext1.nonce, ciphertext2.nonce);
125    }
126
127    #[test]
128    fn test_check_chacha_reused_nonce() {
129        let key = Secret::new(b"32_bytes_master_key_of_ChaCha20!".to_vec());
130        let plaintext = b"yellow_submarine";
131        let mut aes = Encryption::new(&key);
132        let ciphertext1 = aes.encrypt(plaintext.to_vec(), 2).unwrap();
133        let ciphertext2 = aes.encrypt(plaintext.to_vec(), 2).unwrap();
134
135        assert_ne!(ciphertext1.nonce, ciphertext2.nonce);
136    }
137
138    #[test]
139    fn test_check_aes_tamper_resistant() {
140        let key = Secret::new(b"32_bytes_master_key_of_AES-256!!".to_vec());
141        let plaintext = b"yellow_submarine";
142        let mut aes = Encryption::new(&key);
143        let mut ciphertext = aes.encrypt(plaintext.to_vec(), 1).unwrap();
144
145        ciphertext.data[0] ^= 1;
146        let decryption1 = aes.decrypt(ciphertext.nonce, ciphertext.data.clone(), 1);
147
148        ciphertext.nonce[0] ^= 1;
149        let decryption2 = aes.decrypt(ciphertext.nonce, ciphertext.data, 1);
150
151        assert!(decryption1.is_err());
152        assert!(decryption2.is_err());
153    }
154
155    #[test]
156    fn test_check_chacha_tamper_resistant() {
157        let key = Secret::new(b"32_bytes_master_key_of_AES-256!!".to_vec());
158        let plaintext = b"yellow_submarine";
159        let mut aes = Encryption::new(&key);
160        let mut ciphertext = aes.encrypt(plaintext.to_vec(), 2).unwrap();
161
162        ciphertext.data[0] ^= 1;
163        let decryption1 = aes.decrypt(ciphertext.nonce, ciphertext.data.clone(), 2);
164
165        ciphertext.nonce[0] ^= 1;
166        let decryption2 = aes.decrypt(ciphertext.nonce, ciphertext.data, 2);
167
168        assert!(decryption1.is_err());
169        assert!(decryption2.is_err());
170    }
171}