1 // This file was stolen from rust-crypto.
2 // Copyright 2012-2013 The Rust Project Developers. See the COPYRIGHT
3 // file at the top-level directory of this distribution and at
4 // http://rust-lang.org/COPYRIGHT.
6 // Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
7 // http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
8 // <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
9 // option. This file may not be copied, modified, or distributed
10 // except according to those terms.
12 #[cfg(not(feature = "fuzztarget"))]
15 use util::byte_utils::{slice_to_le32, le32_to_array};
17 #[derive(Clone, Copy, PartialEq, Eq)]
18 #[allow(non_camel_case_types)]
19 struct u32x4(pub u32, pub u32, pub u32, pub u32);
20 impl ::std::ops::Add for u32x4 {
22 fn add(self, rhs: u32x4) -> u32x4 {
23 u32x4(self.0.wrapping_add(rhs.0),
24 self.1.wrapping_add(rhs.1),
25 self.2.wrapping_add(rhs.2),
26 self.3.wrapping_add(rhs.3))
29 impl ::std::ops::Sub for u32x4 {
31 fn sub(self, rhs: u32x4) -> u32x4 {
32 u32x4(self.0.wrapping_sub(rhs.0),
33 self.1.wrapping_sub(rhs.1),
34 self.2.wrapping_sub(rhs.2),
35 self.3.wrapping_sub(rhs.3))
38 impl ::std::ops::BitXor for u32x4 {
40 fn bitxor(self, rhs: u32x4) -> u32x4 {
41 u32x4(self.0 ^ rhs.0, self.1 ^ rhs.1, self.2 ^ rhs.2, self.3 ^ rhs.3)
44 impl ::std::ops::Shr<u32x4> for u32x4 {
46 fn shr(self, rhs: u32x4) -> u32x4 {
47 u32x4(self.0 >> rhs.0, self.1 >> rhs.1, self.2 >> rhs.2, self.3 >> rhs.3)
50 impl ::std::ops::Shl<u32x4> for u32x4 {
52 fn shl(self, rhs: u32x4) -> u32x4 {
53 u32x4(self.0 << rhs.0, self.1 << rhs.1, self.2 << rhs.2, self.3 << rhs.3)
72 impl Clone for ChaCha20 { fn clone(&self) -> ChaCha20 { *self } }
74 macro_rules! swizzle {
75 ($b: expr, $c: expr, $d: expr) => {{
76 let u32x4(b10, b11, b12, b13) = $b;
77 $b = u32x4(b11, b12, b13, b10);
78 let u32x4(c10, c11, c12, c13) = $c;
79 $c = u32x4(c12, c13,c10, c11);
80 let u32x4(d10, d11, d12, d13) = $d;
81 $d = u32x4(d13, d10, d11, d12);
85 macro_rules! state_to_buffer {
86 ($state: expr, $output: expr) => {{
87 let u32x4(a1, a2, a3, a4) = $state.a;
88 let u32x4(b1, b2, b3, b4) = $state.b;
89 let u32x4(c1, c2, c3, c4) = $state.c;
90 let u32x4(d1, d2, d3, d4) = $state.d;
97 for i in 0..lens.len() {
98 $output[i*4..(i+1)*4].copy_from_slice(&le32_to_array(lens[i]));
105 $state.a = $state.a + $state.b;
106 rotate!($state.d, $state.a, S16);
107 $state.c = $state.c + $state.d;
108 rotate!($state.b, $state.c, S12);
109 $state.a = $state.a + $state.b;
110 rotate!($state.d, $state.a, S8);
111 $state.c = $state.c + $state.d;
112 rotate!($state.b, $state.c, S7);
116 macro_rules! rotate {
117 ($a: expr, $b: expr, $c:expr) => {{
121 $a = (v << $c) ^ right
125 const S32:u32x4 = u32x4(32, 32, 32, 32);
126 const S16:u32x4 = u32x4(16, 16, 16, 16);
127 const S12:u32x4 = u32x4(12, 12, 12, 12);
128 const S8:u32x4 = u32x4(8, 8, 8, 8);
129 const S7:u32x4 = u32x4(7, 7, 7, 7);
132 pub fn new(key: &[u8], nonce: &[u8]) -> ChaCha20 {
133 assert!(key.len() == 16 || key.len() == 32);
134 assert!(nonce.len() == 8 || nonce.len() == 12);
136 ChaCha20{ state: ChaCha20::expand(key, nonce), output: [0u8; 64], offset: 64 }
139 fn expand(key: &[u8], nonce: &[u8]) -> ChaChaState {
140 let constant = match key.len() {
141 16 => b"expand 16-byte k",
142 32 => b"expand 32-byte k",
147 slice_to_le32(&constant[0..4]),
148 slice_to_le32(&constant[4..8]),
149 slice_to_le32(&constant[8..12]),
150 slice_to_le32(&constant[12..16])
153 slice_to_le32(&key[0..4]),
154 slice_to_le32(&key[4..8]),
155 slice_to_le32(&key[8..12]),
156 slice_to_le32(&key[12..16])
158 c: if key.len() == 16 {
160 slice_to_le32(&key[0..4]),
161 slice_to_le32(&key[4..8]),
162 slice_to_le32(&key[8..12]),
163 slice_to_le32(&key[12..16])
167 slice_to_le32(&key[16..20]),
168 slice_to_le32(&key[20..24]),
169 slice_to_le32(&key[24..28]),
170 slice_to_le32(&key[28..32])
173 d: if nonce.len() == 16 {
175 slice_to_le32(&nonce[0..4]),
176 slice_to_le32(&nonce[4..8]),
177 slice_to_le32(&nonce[8..12]),
178 slice_to_le32(&nonce[12..16])
180 } else if nonce.len() == 12 {
183 slice_to_le32(&nonce[0..4]),
184 slice_to_le32(&nonce[4..8]),
185 slice_to_le32(&nonce[8..12])
191 slice_to_le32(&nonce[0..4]),
192 slice_to_le32(&nonce[4..8])
198 // put the the next 64 keystream bytes into self.output
199 fn update(&mut self) {
200 let mut state = self.state;
204 swizzle!(state.b, state.c, state.d);
206 swizzle!(state.d, state.c, state.b);
208 state.a = state.a + self.state.a;
209 state.b = state.b + self.state.b;
210 state.c = state.c + self.state.c;
211 state.d = state.d + self.state.d;
213 state_to_buffer!(state, self.output);
215 self.state.d = self.state.d + u32x4(1, 0, 0, 0);
216 let u32x4(c12, _, _, _) = self.state.d;
218 // we could increment the other counter word with an 8 byte nonce
219 // but other implementations like boringssl have this same
221 panic!("counter is exhausted");
227 #[inline] // Useful cause input may be 0s on stack that should be optimized out
228 pub fn process(&mut self, input: &[u8], output: &mut [u8]) {
229 assert!(input.len() == output.len());
230 let len = input.len();
233 // If there is no keystream available in the output buffer,
234 // generate the next block.
235 if self.offset == 64 {
239 // Process the min(available keystream, remaining input length).
240 let count = cmp::min(64 - self.offset, len - i);
241 // explicitly assert lengths to avoid bounds checks:
242 assert!(output.len() >= i + count);
243 assert!(input.len() >= i + count);
244 assert!(self.output.len() >= self.offset + count);
246 output[i + j] = input[i + j] ^ self.output[self.offset + j];
249 self.offset += count;
254 #[cfg(not(feature = "fuzztarget"))]
255 pub use self::real_chacha::ChaCha20;
257 #[cfg(feature = "fuzztarget")]
259 pub struct ChaCha20 {}
262 pub fn new(key: &[u8], nonce: &[u8]) -> ChaCha20 {
263 assert!(key.len() == 16 || key.len() == 32);
264 assert!(nonce.len() == 8 || nonce.len() == 12);
268 pub fn process(&mut self, input: &[u8], output: &mut [u8]) {
269 output.copy_from_slice(input);
273 #[cfg(feature = "fuzztarget")]
274 pub use self::fuzzy_chacha::ChaCha20;
278 use std::iter::repeat;
283 fn test_chacha20_256_tls_vectors() {
289 // taken from http://tools.ietf.org/html/draft-agl-tls-chacha20poly1305-04
290 let test_vectors = vec!(
293 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
294 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
295 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
296 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
298 nonce: [ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 ],
300 0x76, 0xb8, 0xe0, 0xad, 0xa0, 0xf1, 0x3d, 0x90,
301 0x40, 0x5d, 0x6a, 0xe5, 0x53, 0x86, 0xbd, 0x28,
302 0xbd, 0xd2, 0x19, 0xb8, 0xa0, 0x8d, 0xed, 0x1a,
303 0xa8, 0x36, 0xef, 0xcc, 0x8b, 0x77, 0x0d, 0xc7,
304 0xda, 0x41, 0x59, 0x7c, 0x51, 0x57, 0x48, 0x8d,
305 0x77, 0x24, 0xe0, 0x3f, 0xb8, 0xd8, 0x4a, 0x37,
306 0x6a, 0x43, 0xb8, 0xf4, 0x15, 0x18, 0xa1, 0x1c,
307 0xc3, 0x87, 0xb6, 0x69, 0xb2, 0xee, 0x65, 0x86,
311 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
312 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
313 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
314 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01,
316 nonce: [ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 ],
318 0x45, 0x40, 0xf0, 0x5a, 0x9f, 0x1f, 0xb2, 0x96,
319 0xd7, 0x73, 0x6e, 0x7b, 0x20, 0x8e, 0x3c, 0x96,
320 0xeb, 0x4f, 0xe1, 0x83, 0x46, 0x88, 0xd2, 0x60,
321 0x4f, 0x45, 0x09, 0x52, 0xed, 0x43, 0x2d, 0x41,
322 0xbb, 0xe2, 0xa0, 0xb6, 0xea, 0x75, 0x66, 0xd2,
323 0xa5, 0xd1, 0xe7, 0xe2, 0x0d, 0x42, 0xaf, 0x2c,
324 0x53, 0xd7, 0x92, 0xb1, 0xc4, 0x3f, 0xea, 0x81,
325 0x7e, 0x9a, 0xd2, 0x75, 0xae, 0x54, 0x69, 0x63,
329 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
330 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
331 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
332 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
334 nonce: [ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01 ],
336 0xde, 0x9c, 0xba, 0x7b, 0xf3, 0xd6, 0x9e, 0xf5,
337 0xe7, 0x86, 0xdc, 0x63, 0x97, 0x3f, 0x65, 0x3a,
338 0x0b, 0x49, 0xe0, 0x15, 0xad, 0xbf, 0xf7, 0x13,
339 0x4f, 0xcb, 0x7d, 0xf1, 0x37, 0x82, 0x10, 0x31,
340 0xe8, 0x5a, 0x05, 0x02, 0x78, 0xa7, 0x08, 0x45,
341 0x27, 0x21, 0x4f, 0x73, 0xef, 0xc7, 0xfa, 0x5b,
342 0x52, 0x77, 0x06, 0x2e, 0xb7, 0xa0, 0x43, 0x3e,
343 0x44, 0x5f, 0x41, 0xe3,
347 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
348 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
349 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
350 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
352 nonce: [ 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 ],
354 0xef, 0x3f, 0xdf, 0xd6, 0xc6, 0x15, 0x78, 0xfb,
355 0xf5, 0xcf, 0x35, 0xbd, 0x3d, 0xd3, 0x3b, 0x80,
356 0x09, 0x63, 0x16, 0x34, 0xd2, 0x1e, 0x42, 0xac,
357 0x33, 0x96, 0x0b, 0xd1, 0x38, 0xe5, 0x0d, 0x32,
358 0x11, 0x1e, 0x4c, 0xaf, 0x23, 0x7e, 0xe5, 0x3c,
359 0xa8, 0xad, 0x64, 0x26, 0x19, 0x4a, 0x88, 0x54,
360 0x5d, 0xdc, 0x49, 0x7a, 0x0b, 0x46, 0x6e, 0x7d,
361 0x6b, 0xbd, 0xb0, 0x04, 0x1b, 0x2f, 0x58, 0x6b,
365 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
366 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f,
367 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
368 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f,
370 nonce: [ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07 ],
372 0xf7, 0x98, 0xa1, 0x89, 0xf1, 0x95, 0xe6, 0x69,
373 0x82, 0x10, 0x5f, 0xfb, 0x64, 0x0b, 0xb7, 0x75,
374 0x7f, 0x57, 0x9d, 0xa3, 0x16, 0x02, 0xfc, 0x93,
375 0xec, 0x01, 0xac, 0x56, 0xf8, 0x5a, 0xc3, 0xc1,
376 0x34, 0xa4, 0x54, 0x7b, 0x73, 0x3b, 0x46, 0x41,
377 0x30, 0x42, 0xc9, 0x44, 0x00, 0x49, 0x17, 0x69,
378 0x05, 0xd3, 0xbe, 0x59, 0xea, 0x1c, 0x53, 0xf1,
379 0x59, 0x16, 0x15, 0x5c, 0x2b, 0xe8, 0x24, 0x1a,
380 0x38, 0x00, 0x8b, 0x9a, 0x26, 0xbc, 0x35, 0x94,
381 0x1e, 0x24, 0x44, 0x17, 0x7c, 0x8a, 0xde, 0x66,
382 0x89, 0xde, 0x95, 0x26, 0x49, 0x86, 0xd9, 0x58,
383 0x89, 0xfb, 0x60, 0xe8, 0x46, 0x29, 0xc9, 0xbd,
384 0x9a, 0x5a, 0xcb, 0x1c, 0xc1, 0x18, 0xbe, 0x56,
385 0x3e, 0xb9, 0xb3, 0xa4, 0xa4, 0x72, 0xf8, 0x2e,
386 0x09, 0xa7, 0xe7, 0x78, 0x49, 0x2b, 0x56, 0x2e,
387 0xf7, 0x13, 0x0e, 0x88, 0xdf, 0xe0, 0x31, 0xc7,
388 0x9d, 0xb9, 0xd4, 0xf7, 0xc7, 0xa8, 0x99, 0x15,
389 0x1b, 0x9a, 0x47, 0x50, 0x32, 0xb6, 0x3f, 0xc3,
390 0x85, 0x24, 0x5f, 0xe0, 0x54, 0xe3, 0xdd, 0x5a,
391 0x97, 0xa5, 0xf5, 0x76, 0xfe, 0x06, 0x40, 0x25,
392 0xd3, 0xce, 0x04, 0x2c, 0x56, 0x6a, 0xb2, 0xc5,
393 0x07, 0xb1, 0x38, 0xdb, 0x85, 0x3e, 0x3d, 0x69,
394 0x59, 0x66, 0x09, 0x96, 0x54, 0x6c, 0xc9, 0xc4,
395 0xa6, 0xea, 0xfd, 0xc7, 0x77, 0xc0, 0x40, 0xd7,
396 0x0e, 0xaf, 0x46, 0xf7, 0x6d, 0xad, 0x39, 0x79,
397 0xe5, 0xc5, 0x36, 0x0c, 0x33, 0x17, 0x16, 0x6a,
398 0x1c, 0x89, 0x4c, 0x94, 0xa3, 0x71, 0x87, 0x6a,
399 0x94, 0xdf, 0x76, 0x28, 0xfe, 0x4e, 0xaa, 0xf2,
400 0xcc, 0xb2, 0x7d, 0x5a, 0xaa, 0xe0, 0xad, 0x7a,
401 0xd0, 0xf9, 0xd4, 0xb6, 0xad, 0x3b, 0x54, 0x09,
402 0x87, 0x46, 0xd4, 0x52, 0x4d, 0x38, 0x40, 0x7a,
403 0x6d, 0xeb, 0x3a, 0xb7, 0x8f, 0xab, 0x78, 0xc9,
408 for tv in test_vectors.iter() {
409 let mut c = ChaCha20::new(&tv.key, &tv.nonce);
410 let input: Vec<u8> = repeat(0).take(tv.keystream.len()).collect();
411 let mut output: Vec<u8> = repeat(0).take(input.len()).collect();
412 c.process(&input[..], &mut output[..]);
413 assert_eq!(output, tv.keystream);
418 fn test_chacha20_256_tls_vectors_96_nonce() {
424 // taken from http://tools.ietf.org/html/draft-agl-tls-chacha20poly1305-04
425 let test_vectors = vec!(
428 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
429 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
430 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
431 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
433 nonce: [ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 ],
435 0x76, 0xb8, 0xe0, 0xad, 0xa0, 0xf1, 0x3d, 0x90,
436 0x40, 0x5d, 0x6a, 0xe5, 0x53, 0x86, 0xbd, 0x28,
437 0xbd, 0xd2, 0x19, 0xb8, 0xa0, 0x8d, 0xed, 0x1a,
438 0xa8, 0x36, 0xef, 0xcc, 0x8b, 0x77, 0x0d, 0xc7,
439 0xda, 0x41, 0x59, 0x7c, 0x51, 0x57, 0x48, 0x8d,
440 0x77, 0x24, 0xe0, 0x3f, 0xb8, 0xd8, 0x4a, 0x37,
441 0x6a, 0x43, 0xb8, 0xf4, 0x15, 0x18, 0xa1, 0x1c,
442 0xc3, 0x87, 0xb6, 0x69, 0xb2, 0xee, 0x65, 0x86,
446 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
447 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
448 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
449 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01,
451 nonce: [ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 ],
453 0x45, 0x40, 0xf0, 0x5a, 0x9f, 0x1f, 0xb2, 0x96,
454 0xd7, 0x73, 0x6e, 0x7b, 0x20, 0x8e, 0x3c, 0x96,
455 0xeb, 0x4f, 0xe1, 0x83, 0x46, 0x88, 0xd2, 0x60,
456 0x4f, 0x45, 0x09, 0x52, 0xed, 0x43, 0x2d, 0x41,
457 0xbb, 0xe2, 0xa0, 0xb6, 0xea, 0x75, 0x66, 0xd2,
458 0xa5, 0xd1, 0xe7, 0xe2, 0x0d, 0x42, 0xaf, 0x2c,
459 0x53, 0xd7, 0x92, 0xb1, 0xc4, 0x3f, 0xea, 0x81,
460 0x7e, 0x9a, 0xd2, 0x75, 0xae, 0x54, 0x69, 0x63,
464 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
465 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
466 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
467 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
469 nonce: [ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01 ],
471 0xde, 0x9c, 0xba, 0x7b, 0xf3, 0xd6, 0x9e, 0xf5,
472 0xe7, 0x86, 0xdc, 0x63, 0x97, 0x3f, 0x65, 0x3a,
473 0x0b, 0x49, 0xe0, 0x15, 0xad, 0xbf, 0xf7, 0x13,
474 0x4f, 0xcb, 0x7d, 0xf1, 0x37, 0x82, 0x10, 0x31,
475 0xe8, 0x5a, 0x05, 0x02, 0x78, 0xa7, 0x08, 0x45,
476 0x27, 0x21, 0x4f, 0x73, 0xef, 0xc7, 0xfa, 0x5b,
477 0x52, 0x77, 0x06, 0x2e, 0xb7, 0xa0, 0x43, 0x3e,
478 0x44, 0x5f, 0x41, 0xe3,
482 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
483 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
484 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
485 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
487 nonce: [ 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 ],
489 0xef, 0x3f, 0xdf, 0xd6, 0xc6, 0x15, 0x78, 0xfb,
490 0xf5, 0xcf, 0x35, 0xbd, 0x3d, 0xd3, 0x3b, 0x80,
491 0x09, 0x63, 0x16, 0x34, 0xd2, 0x1e, 0x42, 0xac,
492 0x33, 0x96, 0x0b, 0xd1, 0x38, 0xe5, 0x0d, 0x32,
493 0x11, 0x1e, 0x4c, 0xaf, 0x23, 0x7e, 0xe5, 0x3c,
494 0xa8, 0xad, 0x64, 0x26, 0x19, 0x4a, 0x88, 0x54,
495 0x5d, 0xdc, 0x49, 0x7a, 0x0b, 0x46, 0x6e, 0x7d,
496 0x6b, 0xbd, 0xb0, 0x04, 0x1b, 0x2f, 0x58, 0x6b,
500 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
501 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f,
502 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
503 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f,
505 nonce: [0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07 ],
507 0xf7, 0x98, 0xa1, 0x89, 0xf1, 0x95, 0xe6, 0x69,
508 0x82, 0x10, 0x5f, 0xfb, 0x64, 0x0b, 0xb7, 0x75,
509 0x7f, 0x57, 0x9d, 0xa3, 0x16, 0x02, 0xfc, 0x93,
510 0xec, 0x01, 0xac, 0x56, 0xf8, 0x5a, 0xc3, 0xc1,
511 0x34, 0xa4, 0x54, 0x7b, 0x73, 0x3b, 0x46, 0x41,
512 0x30, 0x42, 0xc9, 0x44, 0x00, 0x49, 0x17, 0x69,
513 0x05, 0xd3, 0xbe, 0x59, 0xea, 0x1c, 0x53, 0xf1,
514 0x59, 0x16, 0x15, 0x5c, 0x2b, 0xe8, 0x24, 0x1a,
515 0x38, 0x00, 0x8b, 0x9a, 0x26, 0xbc, 0x35, 0x94,
516 0x1e, 0x24, 0x44, 0x17, 0x7c, 0x8a, 0xde, 0x66,
517 0x89, 0xde, 0x95, 0x26, 0x49, 0x86, 0xd9, 0x58,
518 0x89, 0xfb, 0x60, 0xe8, 0x46, 0x29, 0xc9, 0xbd,
519 0x9a, 0x5a, 0xcb, 0x1c, 0xc1, 0x18, 0xbe, 0x56,
520 0x3e, 0xb9, 0xb3, 0xa4, 0xa4, 0x72, 0xf8, 0x2e,
521 0x09, 0xa7, 0xe7, 0x78, 0x49, 0x2b, 0x56, 0x2e,
522 0xf7, 0x13, 0x0e, 0x88, 0xdf, 0xe0, 0x31, 0xc7,
523 0x9d, 0xb9, 0xd4, 0xf7, 0xc7, 0xa8, 0x99, 0x15,
524 0x1b, 0x9a, 0x47, 0x50, 0x32, 0xb6, 0x3f, 0xc3,
525 0x85, 0x24, 0x5f, 0xe0, 0x54, 0xe3, 0xdd, 0x5a,
526 0x97, 0xa5, 0xf5, 0x76, 0xfe, 0x06, 0x40, 0x25,
527 0xd3, 0xce, 0x04, 0x2c, 0x56, 0x6a, 0xb2, 0xc5,
528 0x07, 0xb1, 0x38, 0xdb, 0x85, 0x3e, 0x3d, 0x69,
529 0x59, 0x66, 0x09, 0x96, 0x54, 0x6c, 0xc9, 0xc4,
530 0xa6, 0xea, 0xfd, 0xc7, 0x77, 0xc0, 0x40, 0xd7,
531 0x0e, 0xaf, 0x46, 0xf7, 0x6d, 0xad, 0x39, 0x79,
532 0xe5, 0xc5, 0x36, 0x0c, 0x33, 0x17, 0x16, 0x6a,
533 0x1c, 0x89, 0x4c, 0x94, 0xa3, 0x71, 0x87, 0x6a,
534 0x94, 0xdf, 0x76, 0x28, 0xfe, 0x4e, 0xaa, 0xf2,
535 0xcc, 0xb2, 0x7d, 0x5a, 0xaa, 0xe0, 0xad, 0x7a,
536 0xd0, 0xf9, 0xd4, 0xb6, 0xad, 0x3b, 0x54, 0x09,
537 0x87, 0x46, 0xd4, 0x52, 0x4d, 0x38, 0x40, 0x7a,
538 0x6d, 0xeb, 0x3a, 0xb7, 0x8f, 0xab, 0x78, 0xc9,
543 for tv in test_vectors.iter() {
544 let mut c = ChaCha20::new(&tv.key, &tv.nonce);
545 let input: Vec<u8> = repeat(0).take(tv.keystream.len()).collect();
546 let mut output: Vec<u8> = repeat(0).take(input.len()).collect();
547 c.process(&input[..], &mut output[..]);
548 assert_eq!(output, tv.keystream);