1 // Copyright 2023 The BoringSSL Authors
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 //     https://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14 
15 use crate::cipher::{
16     Cipher, CipherError, CipherInitPurpose, EvpAes128Ctr, EvpAes256Ctr, StreamCipher,
17 };
18 
19 /// AES-CTR-128 Cipher implementation.
20 pub struct Aes128Ctr(Cipher<EvpAes128Ctr>);
21 
22 impl StreamCipher for Aes128Ctr {
23     type Key = [u8; 16];
24     type Nonce = [u8; 16];
25 
26     /// Creates a new AES-128-CTR cipher instance from key material.
new(key: &Self::Key, nonce: &Self::Nonce) -> Self27     fn new(key: &Self::Key, nonce: &Self::Nonce) -> Self {
28         Self(Cipher::new(key, nonce, CipherInitPurpose::Encrypt))
29     }
30 
31     /// Applies the keystream in-place, advancing the counter state appropriately.
apply_keystream(&mut self, buffer: &mut [u8]) -> Result<(), CipherError>32     fn apply_keystream(&mut self, buffer: &mut [u8]) -> Result<(), CipherError> {
33         self.0.apply_keystream_in_place(buffer)
34     }
35 }
36 
37 /// AES-CTR-256 Cipher implementation.
38 pub struct Aes256Ctr(Cipher<EvpAes256Ctr>);
39 
40 impl StreamCipher for Aes256Ctr {
41     type Key = [u8; 32];
42     type Nonce = [u8; 16];
43 
44     /// Creates a new AES-256-CTR cipher instance from key material.
new(key: &Self::Key, nonce: &Self::Nonce) -> Self45     fn new(key: &Self::Key, nonce: &Self::Nonce) -> Self {
46         Self(Cipher::new(key, nonce, CipherInitPurpose::Encrypt))
47     }
48 
49     /// Applies the keystream in-place, advancing the counter state appropriately.
apply_keystream(&mut self, buffer: &mut [u8]) -> Result<(), CipherError>50     fn apply_keystream(&mut self, buffer: &mut [u8]) -> Result<(), CipherError> {
51         self.0.apply_keystream_in_place(buffer)
52     }
53 }
54 
55 #[cfg(test)]
56 mod test {
57     use super::*;
58     use crate::test_helpers::decode_hex;
59 
60     #[test]
aes_128_ctr_test_encrypt()61     fn aes_128_ctr_test_encrypt() {
62         // https://nvlpubs.nist.gov/nistpubs/Legacy/SP/nistspecialpublication800-38a.pdf F.5.1
63         let iv = decode_hex("f0f1f2f3f4f5f6f7f8f9fafbfcfdfeff");
64         let key = decode_hex("2b7e151628aed2a6abf7158809cf4f3c");
65 
66         let mut cipher = Aes128Ctr::new(&key, &iv);
67         let mut block: [u8; 16];
68         block = decode_hex("6bc1bee22e409f96e93d7e117393172a");
69 
70         cipher
71             .apply_keystream(&mut block)
72             .expect("Failed to apply keystream");
73 
74         let expected_ciphertext_1 = decode_hex("874d6191b620e3261bef6864990db6ce");
75         assert_eq!(expected_ciphertext_1, block);
76 
77         block = decode_hex("ae2d8a571e03ac9c9eb76fac45af8e51");
78         cipher
79             .apply_keystream(&mut block)
80             .expect("Failed to apply keystream");
81         let expected_ciphertext_2 = decode_hex("9806f66b7970fdff8617187bb9fffdff");
82         assert_eq!(expected_ciphertext_2, block);
83 
84         block = decode_hex("30c81c46a35ce411e5fbc1191a0a52ef");
85         cipher
86             .apply_keystream(&mut block)
87             .expect("Failed to apply keystream");
88         let expected_ciphertext_3 = decode_hex("5ae4df3edbd5d35e5b4f09020db03eab");
89         assert_eq!(expected_ciphertext_3, block);
90 
91         block = decode_hex("f69f2445df4f9b17ad2b417be66c3710");
92         cipher
93             .apply_keystream(&mut block)
94             .expect("Failed to apply keystream");
95         let expected_ciphertext_3 = decode_hex("1e031dda2fbe03d1792170a0f3009cee");
96         assert_eq!(expected_ciphertext_3, block);
97     }
98 
99     #[test]
aes_128_ctr_test_decrypt()100     fn aes_128_ctr_test_decrypt() {
101         // https://nvlpubs.nist.gov/nistpubs/Legacy/SP/nistspecialpublication800-38a.pdf F.5.2
102         let key = decode_hex("2b7e151628aed2a6abf7158809cf4f3c");
103         let iv = decode_hex("f0f1f2f3f4f5f6f7f8f9fafbfcfdfeff");
104         let mut cipher = Aes128Ctr::new(&key, &iv);
105 
106         let mut block: [u8; 16];
107         block = decode_hex("874d6191b620e3261bef6864990db6ce");
108         cipher
109             .apply_keystream(&mut block)
110             .expect("Failed to apply keystream");
111         let expected_plaintext_1 = decode_hex("6bc1bee22e409f96e93d7e117393172a");
112         assert_eq!(expected_plaintext_1, block);
113 
114         block = decode_hex("9806f66b7970fdff8617187bb9fffdff");
115         cipher
116             .apply_keystream(&mut block)
117             .expect("Failed to apply keystream");
118         let expected_plaintext_2 = decode_hex("ae2d8a571e03ac9c9eb76fac45af8e51");
119         assert_eq!(expected_plaintext_2, block);
120 
121         block = decode_hex("5ae4df3edbd5d35e5b4f09020db03eab");
122         cipher
123             .apply_keystream(&mut block)
124             .expect("Failed to apply keystream");
125         let expected_plaintext_3 = decode_hex("30c81c46a35ce411e5fbc1191a0a52ef");
126         assert_eq!(expected_plaintext_3, block);
127 
128         block = decode_hex("1e031dda2fbe03d1792170a0f3009cee");
129         cipher
130             .apply_keystream(&mut block)
131             .expect("Failed to apply keystream");
132         let expected_plaintext_3 = decode_hex("f69f2445df4f9b17ad2b417be66c3710");
133         assert_eq!(expected_plaintext_3, block);
134     }
135 
136     #[test]
aes_256_ctr_test_encrypt()137     pub fn aes_256_ctr_test_encrypt() {
138         // https://nvlpubs.nist.gov/nistpubs/Legacy/SP/nistspecialpublication800-38a.pdf F.5.5
139         let key = decode_hex("603deb1015ca71be2b73aef0857d77811f352c073b6108d72d9810a30914dff4");
140         let iv = decode_hex("f0f1f2f3f4f5f6f7f8f9fafbfcfdfeff");
141         let mut block: [u8; 16];
142         let mut cipher = Aes256Ctr::new(&key, &iv);
143 
144         block = decode_hex("6bc1bee22e409f96e93d7e117393172a");
145         cipher
146             .apply_keystream(&mut block)
147             .expect("Failed to apply keystream");
148         let expected_ciphertext_1 = decode_hex("601ec313775789a5b7a7f504bbf3d228");
149         assert_eq!(expected_ciphertext_1, block);
150 
151         block = decode_hex("ae2d8a571e03ac9c9eb76fac45af8e51");
152         cipher
153             .apply_keystream(&mut block)
154             .expect("Failed to apply keystream");
155         let expected_ciphertext_2 = decode_hex("f443e3ca4d62b59aca84e990cacaf5c5");
156         assert_eq!(expected_ciphertext_2, block);
157 
158         block = decode_hex("30c81c46a35ce411e5fbc1191a0a52ef");
159         cipher
160             .apply_keystream(&mut block)
161             .expect("Failed to apply keystream");
162         let expected_ciphertext_3 = decode_hex("2b0930daa23de94ce87017ba2d84988d");
163         assert_eq!(expected_ciphertext_3, block);
164 
165         block = decode_hex("f69f2445df4f9b17ad2b417be66c3710");
166         cipher
167             .apply_keystream(&mut block)
168             .expect("Failed to apply keystream");
169         let expected_ciphertext_3 = decode_hex("dfc9c58db67aada613c2dd08457941a6");
170         assert_eq!(expected_ciphertext_3, block);
171     }
172 
173     #[test]
aes_256_ctr_test_decrypt()174     fn aes_256_ctr_test_decrypt() {
175         // https://nvlpubs.nist.gov/nistpubs/Legacy/SP/nistspecialpublication800-38a.pdf F.5.6
176         let key = decode_hex("603deb1015ca71be2b73aef0857d77811f352c073b6108d72d9810a30914dff4");
177         let iv = decode_hex("f0f1f2f3f4f5f6f7f8f9fafbfcfdfeff");
178         let mut cipher = Aes256Ctr::new(&key, &iv);
179 
180         let mut block: [u8; 16];
181         block = decode_hex("601ec313775789a5b7a7f504bbf3d228");
182         cipher
183             .apply_keystream(&mut block)
184             .expect("Failed to apply keystream");
185         let expected_plaintext_1 = decode_hex("6bc1bee22e409f96e93d7e117393172a");
186         assert_eq!(expected_plaintext_1, block);
187 
188         block = decode_hex("f443e3ca4d62b59aca84e990cacaf5c5");
189         cipher
190             .apply_keystream(&mut block)
191             .expect("Failed to apply keystream");
192         let expected_plaintext_2 = decode_hex("ae2d8a571e03ac9c9eb76fac45af8e51");
193         assert_eq!(expected_plaintext_2, block);
194 
195         block = decode_hex("2b0930daa23de94ce87017ba2d84988d");
196         cipher
197             .apply_keystream(&mut block)
198             .expect("Failed to apply keystream");
199         let expected_plaintext_3 = decode_hex("30c81c46a35ce411e5fbc1191a0a52ef");
200         assert_eq!(expected_plaintext_3, block);
201 
202         block = decode_hex("dfc9c58db67aada613c2dd08457941a6");
203         cipher
204             .apply_keystream(&mut block)
205             .expect("Failed to apply keystream");
206         let expected_plaintext_3 = decode_hex("f69f2445df4f9b17ad2b417be66c3710");
207         assert_eq!(expected_plaintext_3, block);
208     }
209 }
210