1use crate::cipher::CipherRef;
55use crate::cipher_ctx::{CipherCtx, CipherCtxRef};
56use crate::error::ErrorStack;
57use crate::nid::Nid;
58use cfg_if::cfg_if;
59use foreign_types::ForeignTypeRef;
60use openssl_macros::corresponds;
61
62#[derive(Copy, Clone)]
63pub enum Mode {
64 Encrypt,
65 Decrypt,
66}
67
68#[derive(Copy, Clone, PartialEq, Eq)]
74pub struct Cipher(*const ffi::EVP_CIPHER);
75
76impl Cipher {
77 #[corresponds(EVP_get_cipherbynid)]
79 pub fn from_nid(nid: Nid) -> Option<Cipher> {
80 let ptr = unsafe { ffi::EVP_get_cipherbyname(ffi::OBJ_nid2sn(nid.as_raw())) };
81 if ptr.is_null() {
82 None
83 } else {
84 Some(Cipher(ptr))
85 }
86 }
87
88 #[corresponds(EVP_CIPHER_nid)]
90 pub fn nid(&self) -> Nid {
91 let nid = unsafe { ffi::EVP_CIPHER_nid(self.0) };
92 Nid::from_raw(nid)
93 }
94
95 pub fn aes_128_ecb() -> Cipher {
96 unsafe { Cipher(ffi::EVP_aes_128_ecb()) }
97 }
98
99 pub fn aes_128_cbc() -> Cipher {
100 unsafe { Cipher(ffi::EVP_aes_128_cbc()) }
101 }
102
103 #[cfg(not(any(boringssl, awslc)))]
104 pub fn aes_128_xts() -> Cipher {
105 unsafe { Cipher(ffi::EVP_aes_128_xts()) }
106 }
107
108 pub fn aes_128_ctr() -> Cipher {
109 unsafe { Cipher(ffi::EVP_aes_128_ctr()) }
110 }
111
112 #[cfg(not(boringssl))]
113 pub fn aes_128_cfb1() -> Cipher {
114 unsafe { Cipher(ffi::EVP_aes_128_cfb1()) }
115 }
116
117 #[cfg(not(boringssl))]
118 pub fn aes_128_cfb128() -> Cipher {
119 unsafe { Cipher(ffi::EVP_aes_128_cfb128()) }
120 }
121
122 #[cfg(not(boringssl))]
123 pub fn aes_128_cfb8() -> Cipher {
124 unsafe { Cipher(ffi::EVP_aes_128_cfb8()) }
125 }
126
127 pub fn aes_128_gcm() -> Cipher {
128 unsafe { Cipher(ffi::EVP_aes_128_gcm()) }
129 }
130
131 #[cfg(not(boringssl))]
132 pub fn aes_128_ccm() -> Cipher {
133 unsafe { Cipher(ffi::EVP_aes_128_ccm()) }
134 }
135
136 pub fn aes_128_ofb() -> Cipher {
137 unsafe { Cipher(ffi::EVP_aes_128_ofb()) }
138 }
139
140 #[cfg(all(ossl110, not(osslconf = "OPENSSL_NO_OCB")))]
142 pub fn aes_128_ocb() -> Cipher {
143 unsafe { Cipher(ffi::EVP_aes_128_ocb()) }
144 }
145
146 pub fn aes_192_ecb() -> Cipher {
147 unsafe { Cipher(ffi::EVP_aes_192_ecb()) }
148 }
149
150 pub fn aes_192_cbc() -> Cipher {
151 unsafe { Cipher(ffi::EVP_aes_192_cbc()) }
152 }
153
154 pub fn aes_192_ctr() -> Cipher {
155 unsafe { Cipher(ffi::EVP_aes_192_ctr()) }
156 }
157
158 #[cfg(not(boringssl))]
159 pub fn aes_192_cfb1() -> Cipher {
160 unsafe { Cipher(ffi::EVP_aes_192_cfb1()) }
161 }
162
163 #[cfg(not(boringssl))]
164 pub fn aes_192_cfb128() -> Cipher {
165 unsafe { Cipher(ffi::EVP_aes_192_cfb128()) }
166 }
167
168 #[cfg(not(boringssl))]
169 pub fn aes_192_cfb8() -> Cipher {
170 unsafe { Cipher(ffi::EVP_aes_192_cfb8()) }
171 }
172
173 pub fn aes_192_gcm() -> Cipher {
174 unsafe { Cipher(ffi::EVP_aes_192_gcm()) }
175 }
176
177 #[cfg(not(any(boringssl, awslc)))]
178 pub fn aes_192_ccm() -> Cipher {
179 unsafe { Cipher(ffi::EVP_aes_192_ccm()) }
180 }
181
182 pub fn aes_192_ofb() -> Cipher {
183 unsafe { Cipher(ffi::EVP_aes_192_ofb()) }
184 }
185
186 #[cfg(all(ossl110, not(osslconf = "OPENSSL_NO_OCB")))]
188 pub fn aes_192_ocb() -> Cipher {
189 unsafe { Cipher(ffi::EVP_aes_192_ocb()) }
190 }
191
192 pub fn aes_256_ecb() -> Cipher {
193 unsafe { Cipher(ffi::EVP_aes_256_ecb()) }
194 }
195
196 pub fn aes_256_cbc() -> Cipher {
197 unsafe { Cipher(ffi::EVP_aes_256_cbc()) }
198 }
199
200 #[cfg(not(boringssl))]
201 pub fn aes_256_xts() -> Cipher {
202 unsafe { Cipher(ffi::EVP_aes_256_xts()) }
203 }
204
205 pub fn aes_256_ctr() -> Cipher {
206 unsafe { Cipher(ffi::EVP_aes_256_ctr()) }
207 }
208
209 #[cfg(not(boringssl))]
210 pub fn aes_256_cfb1() -> Cipher {
211 unsafe { Cipher(ffi::EVP_aes_256_cfb1()) }
212 }
213
214 #[cfg(not(boringssl))]
215 pub fn aes_256_cfb128() -> Cipher {
216 unsafe { Cipher(ffi::EVP_aes_256_cfb128()) }
217 }
218
219 #[cfg(not(boringssl))]
220 pub fn aes_256_cfb8() -> Cipher {
221 unsafe { Cipher(ffi::EVP_aes_256_cfb8()) }
222 }
223
224 pub fn aes_256_gcm() -> Cipher {
225 unsafe { Cipher(ffi::EVP_aes_256_gcm()) }
226 }
227
228 #[cfg(not(boringssl))]
229 pub fn aes_256_ccm() -> Cipher {
230 unsafe { Cipher(ffi::EVP_aes_256_ccm()) }
231 }
232
233 pub fn aes_256_ofb() -> Cipher {
234 unsafe { Cipher(ffi::EVP_aes_256_ofb()) }
235 }
236
237 #[cfg(all(ossl110, not(osslconf = "OPENSSL_NO_OCB")))]
239 pub fn aes_256_ocb() -> Cipher {
240 unsafe { Cipher(ffi::EVP_aes_256_ocb()) }
241 }
242
243 #[cfg(not(osslconf = "OPENSSL_NO_BF"))]
244 pub fn bf_cbc() -> Cipher {
245 unsafe { Cipher(ffi::EVP_bf_cbc()) }
246 }
247
248 #[cfg(not(osslconf = "OPENSSL_NO_BF"))]
249 pub fn bf_ecb() -> Cipher {
250 unsafe { Cipher(ffi::EVP_bf_ecb()) }
251 }
252
253 #[cfg(not(osslconf = "OPENSSL_NO_BF"))]
254 pub fn bf_cfb64() -> Cipher {
255 unsafe { Cipher(ffi::EVP_bf_cfb64()) }
256 }
257
258 #[cfg(not(osslconf = "OPENSSL_NO_BF"))]
259 pub fn bf_ofb() -> Cipher {
260 unsafe { Cipher(ffi::EVP_bf_ofb()) }
261 }
262
263 pub fn des_cbc() -> Cipher {
264 unsafe { Cipher(ffi::EVP_des_cbc()) }
265 }
266
267 pub fn des_ecb() -> Cipher {
268 unsafe { Cipher(ffi::EVP_des_ecb()) }
269 }
270
271 pub fn des_ede3() -> Cipher {
272 unsafe { Cipher(ffi::EVP_des_ede3()) }
273 }
274
275 pub fn des_ede3_cbc() -> Cipher {
276 unsafe { Cipher(ffi::EVP_des_ede3_cbc()) }
277 }
278
279 pub fn des_ede3_ecb() -> Cipher {
280 unsafe { Cipher(ffi::EVP_des_ede3_ecb()) }
281 }
282
283 #[cfg(not(any(boringssl, awslc)))]
284 pub fn des_ede3_cfb64() -> Cipher {
285 unsafe { Cipher(ffi::EVP_des_ede3_cfb64()) }
286 }
287
288 #[cfg(not(any(boringssl, awslc)))]
289 pub fn des_ede3_cfb8() -> Cipher {
290 unsafe { Cipher(ffi::EVP_des_ede3_cfb8()) }
291 }
292
293 #[cfg(not(any(boringssl, awslc)))]
294 pub fn des_ede3_ofb() -> Cipher {
295 unsafe { Cipher(ffi::EVP_des_ede3_ofb()) }
296 }
297
298 #[cfg(not(osslconf = "OPENSSL_NO_RC4"))]
299 pub fn rc4() -> Cipher {
300 unsafe { Cipher(ffi::EVP_rc4()) }
301 }
302
303 #[cfg(not(osslconf = "OPENSSL_NO_CAMELLIA"))]
304 pub fn camellia_128_cbc() -> Cipher {
305 unsafe { Cipher(ffi::EVP_camellia_128_cbc()) }
306 }
307
308 #[cfg(not(osslconf = "OPENSSL_NO_CAMELLIA"))]
309 pub fn camellia_128_ecb() -> Cipher {
310 unsafe { Cipher(ffi::EVP_camellia_128_ecb()) }
311 }
312
313 #[cfg(not(osslconf = "OPENSSL_NO_CAMELLIA"))]
314 pub fn camellia_128_ofb() -> Cipher {
315 unsafe { Cipher(ffi::EVP_camellia_128_ofb()) }
316 }
317
318 #[cfg(not(osslconf = "OPENSSL_NO_CAMELLIA"))]
319 pub fn camellia_128_cfb128() -> Cipher {
320 unsafe { Cipher(ffi::EVP_camellia_128_cfb128()) }
321 }
322
323 #[cfg(not(osslconf = "OPENSSL_NO_CAMELLIA"))]
324 pub fn camellia_192_cbc() -> Cipher {
325 unsafe { Cipher(ffi::EVP_camellia_192_cbc()) }
326 }
327
328 #[cfg(not(osslconf = "OPENSSL_NO_CAMELLIA"))]
329 pub fn camellia_192_ecb() -> Cipher {
330 unsafe { Cipher(ffi::EVP_camellia_192_ecb()) }
331 }
332
333 #[cfg(not(osslconf = "OPENSSL_NO_CAMELLIA"))]
334 pub fn camellia_192_ofb() -> Cipher {
335 unsafe { Cipher(ffi::EVP_camellia_192_ofb()) }
336 }
337
338 #[cfg(not(osslconf = "OPENSSL_NO_CAMELLIA"))]
339 pub fn camellia_192_cfb128() -> Cipher {
340 unsafe { Cipher(ffi::EVP_camellia_192_cfb128()) }
341 }
342
343 #[cfg(not(osslconf = "OPENSSL_NO_CAMELLIA"))]
344 pub fn camellia_256_cbc() -> Cipher {
345 unsafe { Cipher(ffi::EVP_camellia_256_cbc()) }
346 }
347
348 #[cfg(not(osslconf = "OPENSSL_NO_CAMELLIA"))]
349 pub fn camellia_256_ecb() -> Cipher {
350 unsafe { Cipher(ffi::EVP_camellia_256_ecb()) }
351 }
352
353 #[cfg(not(osslconf = "OPENSSL_NO_CAMELLIA"))]
354 pub fn camellia_256_ofb() -> Cipher {
355 unsafe { Cipher(ffi::EVP_camellia_256_ofb()) }
356 }
357
358 #[cfg(not(osslconf = "OPENSSL_NO_CAMELLIA"))]
359 pub fn camellia_256_cfb128() -> Cipher {
360 unsafe { Cipher(ffi::EVP_camellia_256_cfb128()) }
361 }
362
363 #[cfg(not(osslconf = "OPENSSL_NO_CAST"))]
364 pub fn cast5_cbc() -> Cipher {
365 unsafe { Cipher(ffi::EVP_cast5_cbc()) }
366 }
367
368 #[cfg(not(osslconf = "OPENSSL_NO_CAST"))]
369 pub fn cast5_ecb() -> Cipher {
370 unsafe { Cipher(ffi::EVP_cast5_ecb()) }
371 }
372
373 #[cfg(not(osslconf = "OPENSSL_NO_CAST"))]
374 pub fn cast5_ofb() -> Cipher {
375 unsafe { Cipher(ffi::EVP_cast5_ofb()) }
376 }
377
378 #[cfg(not(osslconf = "OPENSSL_NO_CAST"))]
379 pub fn cast5_cfb64() -> Cipher {
380 unsafe { Cipher(ffi::EVP_cast5_cfb64()) }
381 }
382
383 #[cfg(all(any(ossl110, libressl), not(osslconf = "OPENSSL_NO_CHACHA")))]
385 pub fn chacha20() -> Cipher {
386 unsafe { Cipher(ffi::EVP_chacha20()) }
387 }
388
389 #[cfg(all(any(ossl110, libressl360, awslc), not(osslconf = "OPENSSL_NO_CHACHA")))]
391 pub fn chacha20_poly1305() -> Cipher {
392 unsafe { Cipher(ffi::EVP_chacha20_poly1305()) }
393 }
394
395 #[cfg(not(osslconf = "OPENSSL_NO_IDEA"))]
396 pub fn idea_cbc() -> Cipher {
397 unsafe { Cipher(ffi::EVP_idea_cbc()) }
398 }
399
400 #[cfg(not(osslconf = "OPENSSL_NO_IDEA"))]
401 pub fn idea_ecb() -> Cipher {
402 unsafe { Cipher(ffi::EVP_idea_ecb()) }
403 }
404
405 #[cfg(not(osslconf = "OPENSSL_NO_IDEA"))]
406 pub fn idea_ofb() -> Cipher {
407 unsafe { Cipher(ffi::EVP_idea_ofb()) }
408 }
409
410 #[cfg(not(osslconf = "OPENSSL_NO_IDEA"))]
411 pub fn idea_cfb64() -> Cipher {
412 unsafe { Cipher(ffi::EVP_idea_cfb64()) }
413 }
414
415 #[cfg(not(osslconf = "OPENSSL_NO_SEED"))]
416 pub fn seed_cbc() -> Cipher {
417 unsafe { Cipher(ffi::EVP_seed_cbc()) }
418 }
419
420 #[cfg(not(osslconf = "OPENSSL_NO_SEED"))]
421 pub fn seed_cfb128() -> Cipher {
422 unsafe { Cipher(ffi::EVP_seed_cfb128()) }
423 }
424
425 #[cfg(not(osslconf = "OPENSSL_NO_SEED"))]
426 pub fn seed_ecb() -> Cipher {
427 unsafe { Cipher(ffi::EVP_seed_ecb()) }
428 }
429
430 #[cfg(not(osslconf = "OPENSSL_NO_SEED"))]
431 pub fn seed_ofb() -> Cipher {
432 unsafe { Cipher(ffi::EVP_seed_ofb()) }
433 }
434
435 #[cfg(all(any(ossl111, libressl), not(osslconf = "OPENSSL_NO_SM4")))]
436 pub fn sm4_ecb() -> Cipher {
437 unsafe { Cipher(ffi::EVP_sm4_ecb()) }
438 }
439
440 #[cfg(all(any(ossl111, libressl), not(osslconf = "OPENSSL_NO_SM4")))]
441 pub fn sm4_cbc() -> Cipher {
442 unsafe { Cipher(ffi::EVP_sm4_cbc()) }
443 }
444
445 #[cfg(all(any(ossl111, libressl), not(osslconf = "OPENSSL_NO_SM4")))]
446 pub fn sm4_ctr() -> Cipher {
447 unsafe { Cipher(ffi::EVP_sm4_ctr()) }
448 }
449
450 #[cfg(all(any(ossl111, libressl), not(osslconf = "OPENSSL_NO_SM4")))]
451 pub fn sm4_cfb128() -> Cipher {
452 unsafe { Cipher(ffi::EVP_sm4_cfb128()) }
453 }
454
455 #[cfg(all(any(ossl111, libressl), not(osslconf = "OPENSSL_NO_SM4")))]
456 pub fn sm4_ofb() -> Cipher {
457 unsafe { Cipher(ffi::EVP_sm4_ofb()) }
458 }
459
460 #[cfg(not(osslconf = "OPENSSL_NO_RC2"))]
461 pub fn rc2_cbc() -> Cipher {
462 unsafe { Cipher(ffi::EVP_rc2_cbc()) }
463 }
464
465 #[cfg(not(osslconf = "OPENSSL_NO_RC2"))]
466 pub fn rc2_40_cbc() -> Cipher {
467 unsafe { Cipher(ffi::EVP_rc2_40_cbc()) }
468 }
469
470 pub unsafe fn from_ptr(ptr: *const ffi::EVP_CIPHER) -> Cipher {
476 Cipher(ptr)
477 }
478
479 #[allow(clippy::trivially_copy_pass_by_ref)]
480 pub fn as_ptr(&self) -> *const ffi::EVP_CIPHER {
481 self.0
482 }
483
484 #[allow(clippy::trivially_copy_pass_by_ref)]
486 pub fn key_len(&self) -> usize {
487 unsafe { EVP_CIPHER_key_length(self.0) as usize }
488 }
489
490 #[allow(clippy::trivially_copy_pass_by_ref)]
493 pub fn iv_len(&self) -> Option<usize> {
494 unsafe {
495 let len = EVP_CIPHER_iv_length(self.0) as usize;
496 if len == 0 {
497 None
498 } else {
499 Some(len)
500 }
501 }
502 }
503
504 #[allow(clippy::trivially_copy_pass_by_ref)]
510 pub fn block_size(&self) -> usize {
511 unsafe { EVP_CIPHER_block_size(self.0) as usize }
512 }
513
514 #[cfg(not(any(boringssl, awslc)))]
516 fn is_ccm(self) -> bool {
517 self == Cipher::aes_128_ccm() || self == Cipher::aes_256_ccm()
519 }
520
521 #[cfg(any(boringssl, awslc))]
522 fn is_ccm(self) -> bool {
523 false
524 }
525
526 #[cfg(all(ossl110, not(osslconf = "OPENSSL_NO_OCB")))]
528 fn is_ocb(self) -> bool {
529 self == Cipher::aes_128_ocb()
530 || self == Cipher::aes_192_ocb()
531 || self == Cipher::aes_256_ocb()
532 }
533
534 #[cfg(any(not(ossl110), osslconf = "OPENSSL_NO_OCB"))]
535 const fn is_ocb(self) -> bool {
536 false
537 }
538}
539
540unsafe impl Sync for Cipher {}
541unsafe impl Send for Cipher {}
542
543pub struct Crypter {
604 ctx: CipherCtx,
605}
606
607impl Crypter {
608 pub fn new(
616 t: Cipher,
617 mode: Mode,
618 key: &[u8],
619 iv: Option<&[u8]>,
620 ) -> Result<Crypter, ErrorStack> {
621 let mut ctx = CipherCtx::new()?;
622
623 let f = match mode {
624 Mode::Encrypt => CipherCtxRef::encrypt_init,
625 Mode::Decrypt => CipherCtxRef::decrypt_init,
626 };
627
628 f(
629 &mut ctx,
630 Some(unsafe { CipherRef::from_ptr(t.as_ptr() as *mut _) }),
631 None,
632 None,
633 )?;
634
635 ctx.set_key_length(key.len())?;
636
637 if let (Some(iv), Some(iv_len)) = (iv, t.iv_len()) {
638 if iv.len() != iv_len {
639 ctx.set_iv_length(iv.len())?;
640 }
641 }
642
643 f(&mut ctx, None, Some(key), iv)?;
644
645 Ok(Crypter { ctx })
646 }
647
648 pub fn pad(&mut self, padding: bool) {
653 self.ctx.set_padding(padding)
654 }
655
656 pub fn set_tag(&mut self, tag: &[u8]) -> Result<(), ErrorStack> {
660 self.ctx.set_tag(tag)
661 }
662
663 pub fn set_tag_len(&mut self, tag_len: usize) -> Result<(), ErrorStack> {
668 self.ctx.set_tag_length(tag_len)
669 }
670
671 pub fn set_data_len(&mut self, data_len: usize) -> Result<(), ErrorStack> {
676 self.ctx.set_data_len(data_len)
677 }
678
679 pub fn aad_update(&mut self, input: &[u8]) -> Result<(), ErrorStack> {
685 self.ctx.cipher_update(input, None)?;
686 Ok(())
687 }
688
689 pub fn update(&mut self, input: &[u8], output: &mut [u8]) -> Result<usize, ErrorStack> {
704 self.ctx.cipher_update(input, Some(output))
705 }
706
707 pub unsafe fn update_unchecked(
721 &mut self,
722 input: &[u8],
723 output: &mut [u8],
724 ) -> Result<usize, ErrorStack> {
725 self.ctx.cipher_update_unchecked(input, Some(output))
726 }
727
728 pub fn finalize(&mut self, output: &mut [u8]) -> Result<usize, ErrorStack> {
740 self.ctx.cipher_final(output)
741 }
742
743 pub fn get_tag(&self, tag: &mut [u8]) -> Result<(), ErrorStack> {
752 self.ctx.tag(tag)
753 }
754}
755
756pub fn encrypt(
787 t: Cipher,
788 key: &[u8],
789 iv: Option<&[u8]>,
790 data: &[u8],
791) -> Result<Vec<u8>, ErrorStack> {
792 cipher(t, Mode::Encrypt, key, iv, data)
793}
794
795pub fn decrypt(
826 t: Cipher,
827 key: &[u8],
828 iv: Option<&[u8]>,
829 data: &[u8],
830) -> Result<Vec<u8>, ErrorStack> {
831 cipher(t, Mode::Decrypt, key, iv, data)
832}
833
834fn cipher(
835 t: Cipher,
836 mode: Mode,
837 key: &[u8],
838 iv: Option<&[u8]>,
839 data: &[u8],
840) -> Result<Vec<u8>, ErrorStack> {
841 let mut c = Crypter::new(t, mode, key, iv)?;
842 let mut out = vec![0; data.len() + t.block_size()];
843 let count = c.update(data, &mut out)?;
844 let rest = c.finalize(&mut out[count..])?;
845 out.truncate(count + rest);
846 Ok(out)
847}
848
849pub fn encrypt_aead(
858 t: Cipher,
859 key: &[u8],
860 iv: Option<&[u8]>,
861 aad: &[u8],
862 data: &[u8],
863 tag: &mut [u8],
864) -> Result<Vec<u8>, ErrorStack> {
865 let mut c = Crypter::new(t, Mode::Encrypt, key, iv)?;
866 let mut out = vec![0; data.len() + t.block_size()];
867
868 let is_ccm = t.is_ccm();
869 if is_ccm || t.is_ocb() {
870 c.set_tag_len(tag.len())?;
871 if is_ccm {
872 c.set_data_len(data.len())?;
873 }
874 }
875
876 c.aad_update(aad)?;
877 let count = c.update(data, &mut out)?;
878 let rest = c.finalize(&mut out[count..])?;
879 c.get_tag(tag)?;
880 out.truncate(count + rest);
881 Ok(out)
882}
883
884pub fn decrypt_aead(
889 t: Cipher,
890 key: &[u8],
891 iv: Option<&[u8]>,
892 aad: &[u8],
893 data: &[u8],
894 tag: &[u8],
895) -> Result<Vec<u8>, ErrorStack> {
896 let mut c = Crypter::new(t, Mode::Decrypt, key, iv)?;
897 let mut out = vec![0; data.len() + t.block_size()];
898
899 let is_ccm = t.is_ccm();
900 if is_ccm || t.is_ocb() {
901 c.set_tag(tag)?;
902 if is_ccm {
903 c.set_data_len(data.len())?;
904 }
905 }
906
907 c.aad_update(aad)?;
908 let count = c.update(data, &mut out)?;
909
910 let rest = if t.is_ccm() {
911 0
912 } else {
913 c.set_tag(tag)?;
914 c.finalize(&mut out[count..])?
915 };
916
917 out.truncate(count + rest);
918 Ok(out)
919}
920
921cfg_if! {
922 if #[cfg(any(boringssl, ossl110, libressl, awslc))] {
923 use ffi::{EVP_CIPHER_block_size, EVP_CIPHER_iv_length, EVP_CIPHER_key_length};
924 } else {
925 use crate::LenType;
926
927 #[allow(bad_style)]
928 pub unsafe fn EVP_CIPHER_iv_length(ptr: *const ffi::EVP_CIPHER) -> LenType {
929 (*ptr).iv_len
930 }
931
932 #[allow(bad_style)]
933 pub unsafe fn EVP_CIPHER_block_size(ptr: *const ffi::EVP_CIPHER) -> LenType {
934 (*ptr).block_size
935 }
936
937 #[allow(bad_style)]
938 pub unsafe fn EVP_CIPHER_key_length(ptr: *const ffi::EVP_CIPHER) -> LenType {
939 (*ptr).key_len
940 }
941 }
942}
943
944#[cfg(test)]
945mod tests {
946 use super::*;
947 use hex::{self, FromHex};
948
949 #[test]
950 fn test_stream_cipher_output() {
951 let key = [0u8; 16];
952 let iv = [0u8; 16];
953 let mut c = super::Crypter::new(
954 super::Cipher::aes_128_ctr(),
955 super::Mode::Encrypt,
956 &key,
957 Some(&iv),
958 )
959 .unwrap();
960
961 assert_eq!(c.update(&[0u8; 15], &mut [0u8; 15]).unwrap(), 15);
962 assert_eq!(c.update(&[0u8; 1], &mut [0u8; 1]).unwrap(), 1);
963 assert_eq!(c.finalize(&mut [0u8; 0]).unwrap(), 0);
964 }
965
966 #[test]
969 fn test_aes_256_ecb() {
970 let k0 = [
971 0x00u8, 0x01u8, 0x02u8, 0x03u8, 0x04u8, 0x05u8, 0x06u8, 0x07u8, 0x08u8, 0x09u8, 0x0au8,
972 0x0bu8, 0x0cu8, 0x0du8, 0x0eu8, 0x0fu8, 0x10u8, 0x11u8, 0x12u8, 0x13u8, 0x14u8, 0x15u8,
973 0x16u8, 0x17u8, 0x18u8, 0x19u8, 0x1au8, 0x1bu8, 0x1cu8, 0x1du8, 0x1eu8, 0x1fu8,
974 ];
975 let p0 = [
976 0x00u8, 0x11u8, 0x22u8, 0x33u8, 0x44u8, 0x55u8, 0x66u8, 0x77u8, 0x88u8, 0x99u8, 0xaau8,
977 0xbbu8, 0xccu8, 0xddu8, 0xeeu8, 0xffu8,
978 ];
979 let c0 = [
980 0x8eu8, 0xa2u8, 0xb7u8, 0xcau8, 0x51u8, 0x67u8, 0x45u8, 0xbfu8, 0xeau8, 0xfcu8, 0x49u8,
981 0x90u8, 0x4bu8, 0x49u8, 0x60u8, 0x89u8,
982 ];
983 let mut c = super::Crypter::new(
984 super::Cipher::aes_256_ecb(),
985 super::Mode::Encrypt,
986 &k0,
987 None,
988 )
989 .unwrap();
990 c.pad(false);
991 let mut r0 = vec![0; c0.len() + super::Cipher::aes_256_ecb().block_size()];
992 let count = c.update(&p0, &mut r0).unwrap();
993 let rest = c.finalize(&mut r0[count..]).unwrap();
994 r0.truncate(count + rest);
995 assert_eq!(hex::encode(&r0), hex::encode(c0));
996
997 let mut c = super::Crypter::new(
998 super::Cipher::aes_256_ecb(),
999 super::Mode::Decrypt,
1000 &k0,
1001 None,
1002 )
1003 .unwrap();
1004 c.pad(false);
1005 let mut p1 = vec![0; r0.len() + super::Cipher::aes_256_ecb().block_size()];
1006 let count = c.update(&r0, &mut p1).unwrap();
1007 let rest = c.finalize(&mut p1[count..]).unwrap();
1008 p1.truncate(count + rest);
1009 assert_eq!(hex::encode(p1), hex::encode(p0));
1010 }
1011
1012 #[test]
1013 fn test_aes_256_cbc_decrypt() {
1014 let iv = [
1015 4_u8, 223_u8, 153_u8, 219_u8, 28_u8, 142_u8, 234_u8, 68_u8, 227_u8, 69_u8, 98_u8,
1016 107_u8, 208_u8, 14_u8, 236_u8, 60_u8,
1017 ];
1018 let data = [
1019 143_u8, 210_u8, 75_u8, 63_u8, 214_u8, 179_u8, 155_u8, 241_u8, 242_u8, 31_u8, 154_u8,
1020 56_u8, 198_u8, 145_u8, 192_u8, 64_u8, 2_u8, 245_u8, 167_u8, 220_u8, 55_u8, 119_u8,
1021 233_u8, 136_u8, 139_u8, 27_u8, 71_u8, 242_u8, 119_u8, 175_u8, 65_u8, 207_u8,
1022 ];
1023 let ciphered_data = [
1024 0x4a_u8, 0x2e_u8, 0xe5_u8, 0x6_u8, 0xbf_u8, 0xcf_u8, 0xf2_u8, 0xd7_u8, 0xea_u8,
1025 0x2d_u8, 0xb1_u8, 0x85_u8, 0x6c_u8, 0x93_u8, 0x65_u8, 0x6f_u8,
1026 ];
1027 let mut cr = super::Crypter::new(
1028 super::Cipher::aes_256_cbc(),
1029 super::Mode::Decrypt,
1030 &data,
1031 Some(&iv),
1032 )
1033 .unwrap();
1034 cr.pad(false);
1035 let mut unciphered_data = vec![0; data.len() + super::Cipher::aes_256_cbc().block_size()];
1036 let count = cr.update(&ciphered_data, &mut unciphered_data).unwrap();
1037 let rest = cr.finalize(&mut unciphered_data[count..]).unwrap();
1038 unciphered_data.truncate(count + rest);
1039
1040 let expected_unciphered_data = b"I love turtles.\x01";
1041
1042 assert_eq!(&unciphered_data, expected_unciphered_data);
1043 }
1044
1045 fn cipher_test(ciphertype: super::Cipher, pt: &str, ct: &str, key: &str, iv: &str) {
1046 let pt = Vec::from_hex(pt).unwrap();
1047 let ct = Vec::from_hex(ct).unwrap();
1048 let key = Vec::from_hex(key).unwrap();
1049 let iv = Vec::from_hex(iv).unwrap();
1050
1051 let computed = super::decrypt(ciphertype, &key, Some(&iv), &ct).unwrap();
1052 let expected = pt;
1053
1054 if computed != expected {
1055 println!("Computed: {}", hex::encode(&computed));
1056 println!("Expected: {}", hex::encode(&expected));
1057 if computed.len() != expected.len() {
1058 println!(
1059 "Lengths differ: {} in computed vs {} expected",
1060 computed.len(),
1061 expected.len()
1062 );
1063 }
1064 panic!("test failure");
1065 }
1066 }
1067
1068 #[test]
1069 #[cfg(not(any(boringssl, awslc)))]
1070 fn test_aes256_xts() {
1071 let pt = "77f4ef63d734ebd028508da66c22cdebdd52ecd6ee2ab0a50bc8ad0cfd692ca5fcd4e6dedc45df7f\
1074 6503f462611dc542";
1075 let ct = "ce7d905a7776ac72f240d22aafed5e4eb7566cdc7211220e970da634ce015f131a5ecb8d400bc9e8\
1076 4f0b81d8725dbbc7";
1077 let key = "b6bfef891f83b5ff073f2231267be51eb084b791fa19a154399c0684c8b2dfcb37de77d28bbda3b\
1078 4180026ad640b74243b3133e7b9fae629403f6733423dae28";
1079 let iv = "db200efb7eaaa737dbdf40babb68953f";
1080
1081 cipher_test(super::Cipher::aes_256_xts(), pt, ct, key, iv);
1082 }
1083
1084 #[test]
1085 fn test_aes128_ctr() {
1086 let pt = "6BC1BEE22E409F96E93D7E117393172AAE2D8A571E03AC9C9EB76FAC45AF8E5130C81C46A35CE411\
1087 E5FBC1191A0A52EFF69F2445DF4F9B17AD2B417BE66C3710";
1088 let ct = "874D6191B620E3261BEF6864990DB6CE9806F66B7970FDFF8617187BB9FFFDFF5AE4DF3EDBD5D35E\
1089 5B4F09020DB03EAB1E031DDA2FBE03D1792170A0F3009CEE";
1090 let key = "2B7E151628AED2A6ABF7158809CF4F3C";
1091 let iv = "F0F1F2F3F4F5F6F7F8F9FAFBFCFDFEFF";
1092
1093 cipher_test(super::Cipher::aes_128_ctr(), pt, ct, key, iv);
1094 }
1095
1096 #[test]
1097 #[cfg(not(any(boringssl, awslc)))]
1098 fn test_aes128_cfb1() {
1099 let pt = "6bc1";
1102 let ct = "68b3";
1103 let key = "2b7e151628aed2a6abf7158809cf4f3c";
1104 let iv = "000102030405060708090a0b0c0d0e0f";
1105
1106 cipher_test(super::Cipher::aes_128_cfb1(), pt, ct, key, iv);
1107 }
1108
1109 #[test]
1110 #[cfg(not(any(boringssl, awslc)))]
1111 fn test_aes128_cfb128() {
1112 let pt = "6bc1bee22e409f96e93d7e117393172a";
1113 let ct = "3b3fd92eb72dad20333449f8e83cfb4a";
1114 let key = "2b7e151628aed2a6abf7158809cf4f3c";
1115 let iv = "000102030405060708090a0b0c0d0e0f";
1116
1117 cipher_test(super::Cipher::aes_128_cfb128(), pt, ct, key, iv);
1118 }
1119
1120 #[test]
1121 #[cfg(not(any(boringssl, awslc)))]
1122 fn test_aes128_cfb8() {
1123 let pt = "6bc1bee22e409f96e93d7e117393172aae2d";
1124 let ct = "3b79424c9c0dd436bace9e0ed4586a4f32b9";
1125 let key = "2b7e151628aed2a6abf7158809cf4f3c";
1126 let iv = "000102030405060708090a0b0c0d0e0f";
1127
1128 cipher_test(super::Cipher::aes_128_cfb8(), pt, ct, key, iv);
1129 }
1130
1131 #[test]
1132 fn test_aes128_ofb() {
1133 let pt = "6bc1bee22e409f96e93d7e117393172aae2d8a571e03ac9c9eb76fac45af8e5130c81c46a35ce411e5fbc1191a0a52eff69f2445df4f9b17ad2b417be66c3710";
1136 let ct = "3b3fd92eb72dad20333449f8e83cfb4a7789508d16918f03f53c52dac54ed8259740051e9c5fecf64344f7a82260edcc304c6528f659c77866a510d9c1d6ae5e";
1137 let key = "2b7e151628aed2a6abf7158809cf4f3c";
1138 let iv = "000102030405060708090a0b0c0d0e0f";
1139
1140 cipher_test(super::Cipher::aes_128_ofb(), pt, ct, key, iv);
1141 }
1142
1143 #[test]
1144 fn test_aes192_ctr() {
1145 let pt = "6bc1bee22e409f96e93d7e117393172aae2d8a571e03ac9c9eb76fac45af8e5130c81c46a35ce411e5fbc1191a0a52eff69f2445df4f9b17ad2b417be66c3710";
1148 let ct = "1abc932417521ca24f2b0459fe7e6e0b090339ec0aa6faefd5ccc2c6f4ce8e941e36b26bd1ebc670d1bd1d665620abf74f78a7f6d29809585a97daec58c6b050";
1149 let key = "8e73b0f7da0e6452c810f32b809079e562f8ead2522c6b7b";
1150 let iv = "f0f1f2f3f4f5f6f7f8f9fafbfcfdfeff";
1151
1152 cipher_test(super::Cipher::aes_192_ctr(), pt, ct, key, iv);
1153 }
1154
1155 #[test]
1156 #[cfg(not(any(boringssl, awslc)))]
1157 fn test_aes192_cfb1() {
1158 let pt = "6bc1";
1161 let ct = "9359";
1162 let key = "8e73b0f7da0e6452c810f32b809079e562f8ead2522c6b7b";
1163 let iv = "000102030405060708090a0b0c0d0e0f";
1164
1165 cipher_test(super::Cipher::aes_192_cfb1(), pt, ct, key, iv);
1166 }
1167
1168 #[test]
1169 #[cfg(not(any(boringssl, awslc)))]
1170 fn test_aes192_cfb128() {
1171 let pt = "6bc1bee22e409f96e93d7e117393172aae2d8a571e03ac9c9eb76fac45af8e5130c81c46a35ce411e5fbc1191a0a52eff69f2445df4f9b17ad2b417be66c3710";
1174 let ct = "cdc80d6fddf18cab34c25909c99a417467ce7f7f81173621961a2b70171d3d7a2e1e8a1dd59b88b1c8e60fed1efac4c9c05f9f9ca9834fa042ae8fba584b09ff";
1175 let key = "8e73b0f7da0e6452c810f32b809079e562f8ead2522c6b7b";
1176 let iv = "000102030405060708090a0b0c0d0e0f";
1177
1178 cipher_test(super::Cipher::aes_192_cfb128(), pt, ct, key, iv);
1179 }
1180
1181 #[test]
1182 #[cfg(not(any(boringssl, awslc)))]
1183 fn test_aes192_cfb8() {
1184 let pt = "6bc1bee22e409f96e93d7e117393172aae2d";
1187 let ct = "cda2521ef0a905ca44cd057cbf0d47a0678a";
1188 let key = "8e73b0f7da0e6452c810f32b809079e562f8ead2522c6b7b";
1189 let iv = "000102030405060708090a0b0c0d0e0f";
1190
1191 cipher_test(super::Cipher::aes_192_cfb8(), pt, ct, key, iv);
1192 }
1193
1194 #[test]
1195 fn test_aes192_ofb() {
1196 let pt = "6bc1bee22e409f96e93d7e117393172aae2d8a571e03ac9c9eb76fac45af8e5130c81c46a35ce411e5fbc1191a0a52eff69f2445df4f9b17ad2b417be66c3710";
1199 let ct = "cdc80d6fddf18cab34c25909c99a4174fcc28b8d4c63837c09e81700c11004018d9a9aeac0f6596f559c6d4daf59a5f26d9f200857ca6c3e9cac524bd9acc92a";
1200 let key = "8e73b0f7da0e6452c810f32b809079e562f8ead2522c6b7b";
1201 let iv = "000102030405060708090a0b0c0d0e0f";
1202
1203 cipher_test(super::Cipher::aes_192_ofb(), pt, ct, key, iv);
1204 }
1205
1206 #[test]
1207 #[cfg(not(any(boringssl, awslc)))]
1208 fn test_aes256_cfb1() {
1209 let pt = "6bc1";
1210 let ct = "9029";
1211 let key = "603deb1015ca71be2b73aef0857d77811f352c073b6108d72d9810a30914dff4";
1212 let iv = "000102030405060708090a0b0c0d0e0f";
1213
1214 cipher_test(super::Cipher::aes_256_cfb1(), pt, ct, key, iv);
1215 }
1216
1217 #[test]
1218 #[cfg(not(any(boringssl, awslc)))]
1219 fn test_aes256_cfb128() {
1220 let pt = "6bc1bee22e409f96e93d7e117393172a";
1221 let ct = "dc7e84bfda79164b7ecd8486985d3860";
1222 let key = "603deb1015ca71be2b73aef0857d77811f352c073b6108d72d9810a30914dff4";
1223 let iv = "000102030405060708090a0b0c0d0e0f";
1224
1225 cipher_test(super::Cipher::aes_256_cfb128(), pt, ct, key, iv);
1226 }
1227
1228 #[test]
1229 #[cfg(not(any(boringssl, awslc)))]
1230 fn test_aes256_cfb8() {
1231 let pt = "6bc1bee22e409f96e93d7e117393172aae2d";
1232 let ct = "dc1f1a8520a64db55fcc8ac554844e889700";
1233 let key = "603deb1015ca71be2b73aef0857d77811f352c073b6108d72d9810a30914dff4";
1234 let iv = "000102030405060708090a0b0c0d0e0f";
1235
1236 cipher_test(super::Cipher::aes_256_cfb8(), pt, ct, key, iv);
1237 }
1238
1239 #[test]
1240 fn test_aes256_ofb() {
1241 let pt = "6bc1bee22e409f96e93d7e117393172aae2d8a571e03ac9c9eb76fac45af8e5130c81c46a35ce411e5fbc1191a0a52eff69f2445df4f9b17ad2b417be66c3710";
1244 let ct = "dc7e84bfda79164b7ecd8486985d38604febdc6740d20b3ac88f6ad82a4fb08d71ab47a086e86eedf39d1c5bba97c4080126141d67f37be8538f5a8be740e484";
1245 let key = "603deb1015ca71be2b73aef0857d77811f352c073b6108d72d9810a30914dff4";
1246 let iv = "000102030405060708090a0b0c0d0e0f";
1247
1248 cipher_test(super::Cipher::aes_256_ofb(), pt, ct, key, iv);
1249 }
1250
1251 #[test]
1252 fn test_des_ede3() {
1253 let pt = "9994f4c69d40ae4f34ff403b5cf39d4c8207ea5d3e19a5fd";
1254 let ct = "9e5c4297d60582f81071ac8ab7d0698d4c79de8b94c519858207ea5d3e19a5fd";
1255 let key = "010203040506070801020304050607080102030405060708";
1256 let iv = "5cc118306dc702e4";
1257
1258 cipher_test(super::Cipher::des_ede3(), pt, ct, key, iv);
1259 }
1260
1261 #[test]
1262 fn test_des_ede3_cbc() {
1263 let pt = "54686973206973206120746573742e";
1264 let ct = "6f2867cfefda048a4046ef7e556c7132";
1265 let key = "7cb66337f3d3c0fe7cb66337f3d3c0fe7cb66337f3d3c0fe";
1266 let iv = "0001020304050607";
1267
1268 cipher_test(super::Cipher::des_ede3_cbc(), pt, ct, key, iv);
1269 }
1270
1271 #[test]
1272 #[cfg(not(any(boringssl, awslc)))]
1273 fn test_des_ede3_cfb64() {
1274 let pt = "2b1773784b5889dc788477367daa98ad";
1275 let ct = "6f2867cfefda048a4046ef7e556c7132";
1276 let key = "7cb66337f3d3c0fe7cb66337f3d3c0fe7cb66337f3d3c0fe";
1277 let iv = "0001020304050607";
1278
1279 cipher_test(super::Cipher::des_ede3_cfb64(), pt, ct, key, iv);
1280 }
1281
1282 #[test]
1283 fn test_aes128_gcm() {
1284 let key = "23dc8d23d95b6fd1251741a64f7d4f41";
1285 let iv = "f416f48ad44d9efa1179e167";
1286 let pt = "6cb9b71dd0ccd42cdf87e8e396fc581fd8e0d700e360f590593b748e105390de";
1287 let aad = "45074844c97d515c65bbe37c210a5a4b08c21c588efe5c5f73c4d9c17d34dacddc0bb6a8a53f7bf477b9780c1c2a928660df87016b2873fe876b2b887fb5886bfd63216b7eaecc046372a82c047eb043f0b063226ee52a12c69b";
1288 let ct = "8ad20486778e87387efb3f2574e509951c0626816722018129e578b2787969d3";
1289 let tag = "91e1bc09";
1290
1291 let mut actual_tag = [0; 4];
1294 let out = encrypt_aead(
1295 Cipher::aes_128_gcm(),
1296 &Vec::from_hex(key).unwrap(),
1297 Some(&Vec::from_hex(iv).unwrap()),
1298 &Vec::from_hex(aad).unwrap(),
1299 &Vec::from_hex(pt).unwrap(),
1300 &mut actual_tag,
1301 )
1302 .unwrap();
1303 assert_eq!(ct, hex::encode(out));
1304 assert_eq!(tag, hex::encode(actual_tag));
1305
1306 let out = decrypt_aead(
1307 Cipher::aes_128_gcm(),
1308 &Vec::from_hex(key).unwrap(),
1309 Some(&Vec::from_hex(iv).unwrap()),
1310 &Vec::from_hex(aad).unwrap(),
1311 &Vec::from_hex(ct).unwrap(),
1312 &Vec::from_hex(tag).unwrap(),
1313 )
1314 .unwrap();
1315 assert_eq!(pt, hex::encode(out));
1316 }
1317
1318 #[test]
1319 #[cfg(not(any(boringssl, awslc)))]
1320 fn test_aes128_ccm() {
1321 let key = "3ee186594f110fb788a8bf8aa8be5d4a";
1322 let nonce = "44f705d52acf27b7f17196aa9b";
1323 let aad = "2c16724296ff85e079627be3053ea95adf35722c21886baba343bd6c79b5cb57";
1324
1325 let pt = "d71864877f2578db092daba2d6a1f9f4698a9c356c7830a1";
1326 let ct = "b4dd74e7a0cc51aea45dfb401a41d5822c96901a83247ea0";
1327 let tag = "d6965f5aa6e31302a9cc2b36";
1328
1329 let mut actual_tag = [0; 12];
1330 let out = encrypt_aead(
1331 Cipher::aes_128_ccm(),
1332 &Vec::from_hex(key).unwrap(),
1333 Some(&Vec::from_hex(nonce).unwrap()),
1334 &Vec::from_hex(aad).unwrap(),
1335 &Vec::from_hex(pt).unwrap(),
1336 &mut actual_tag,
1337 )
1338 .unwrap();
1339
1340 assert_eq!(ct, hex::encode(out));
1341 assert_eq!(tag, hex::encode(actual_tag));
1342
1343 let out = decrypt_aead(
1344 Cipher::aes_128_ccm(),
1345 &Vec::from_hex(key).unwrap(),
1346 Some(&Vec::from_hex(nonce).unwrap()),
1347 &Vec::from_hex(aad).unwrap(),
1348 &Vec::from_hex(ct).unwrap(),
1349 &Vec::from_hex(tag).unwrap(),
1350 )
1351 .unwrap();
1352 assert_eq!(pt, hex::encode(out));
1353 }
1354
1355 #[test]
1356 #[cfg(not(any(boringssl, awslc)))]
1357 fn test_aes128_ccm_verify_fail() {
1358 let key = "3ee186594f110fb788a8bf8aa8be5d4a";
1359 let nonce = "44f705d52acf27b7f17196aa9b";
1360 let aad = "2c16724296ff85e079627be3053ea95adf35722c21886baba343bd6c79b5cb57";
1361
1362 let ct = "b4dd74e7a0cc51aea45dfb401a41d5822c96901a83247ea0";
1363 let tag = "00005f5aa6e31302a9cc2b36";
1364
1365 let out = decrypt_aead(
1366 Cipher::aes_128_ccm(),
1367 &Vec::from_hex(key).unwrap(),
1368 Some(&Vec::from_hex(nonce).unwrap()),
1369 &Vec::from_hex(aad).unwrap(),
1370 &Vec::from_hex(ct).unwrap(),
1371 &Vec::from_hex(tag).unwrap(),
1372 );
1373 assert!(out.is_err());
1374 }
1375
1376 #[test]
1377 #[cfg(not(any(boringssl, awslc)))]
1378 fn test_aes256_ccm() {
1379 let key = "7f4af6765cad1d511db07e33aaafd57646ec279db629048aa6770af24849aa0d";
1380 let nonce = "dde2a362ce81b2b6913abc3095";
1381 let aad = "404f5df97ece7431987bc098cce994fc3c063b519ffa47b0365226a0015ef695";
1382
1383 let pt = "7ebef26bf4ecf6f0ebb2eb860edbf900f27b75b4a6340fdb";
1384 let ct = "353022db9c568bd7183a13c40b1ba30fcc768c54264aa2cd";
1385 let tag = "2927a053c9244d3217a7ad05";
1386
1387 let mut actual_tag = [0; 12];
1388 let out = encrypt_aead(
1389 Cipher::aes_256_ccm(),
1390 &Vec::from_hex(key).unwrap(),
1391 Some(&Vec::from_hex(nonce).unwrap()),
1392 &Vec::from_hex(aad).unwrap(),
1393 &Vec::from_hex(pt).unwrap(),
1394 &mut actual_tag,
1395 )
1396 .unwrap();
1397
1398 assert_eq!(ct, hex::encode(out));
1399 assert_eq!(tag, hex::encode(actual_tag));
1400
1401 let out = decrypt_aead(
1402 Cipher::aes_256_ccm(),
1403 &Vec::from_hex(key).unwrap(),
1404 Some(&Vec::from_hex(nonce).unwrap()),
1405 &Vec::from_hex(aad).unwrap(),
1406 &Vec::from_hex(ct).unwrap(),
1407 &Vec::from_hex(tag).unwrap(),
1408 )
1409 .unwrap();
1410 assert_eq!(pt, hex::encode(out));
1411 }
1412
1413 #[test]
1414 #[cfg(not(any(boringssl, awslc)))]
1415 fn test_aes256_ccm_verify_fail() {
1416 let key = "7f4af6765cad1d511db07e33aaafd57646ec279db629048aa6770af24849aa0d";
1417 let nonce = "dde2a362ce81b2b6913abc3095";
1418 let aad = "404f5df97ece7431987bc098cce994fc3c063b519ffa47b0365226a0015ef695";
1419
1420 let ct = "353022db9c568bd7183a13c40b1ba30fcc768c54264aa2cd";
1421 let tag = "0000a053c9244d3217a7ad05";
1422
1423 let out = decrypt_aead(
1424 Cipher::aes_256_ccm(),
1425 &Vec::from_hex(key).unwrap(),
1426 Some(&Vec::from_hex(nonce).unwrap()),
1427 &Vec::from_hex(aad).unwrap(),
1428 &Vec::from_hex(ct).unwrap(),
1429 &Vec::from_hex(tag).unwrap(),
1430 );
1431 assert!(out.is_err());
1432 }
1433
1434 #[test]
1435 #[cfg(all(ossl110, not(osslconf = "OPENSSL_NO_OCB")))]
1436 fn test_aes_128_ocb() {
1437 let key = "000102030405060708090a0b0c0d0e0f";
1438 let aad = "0001020304050607";
1439 let tag = "16dc76a46d47e1ead537209e8a96d14e";
1440 let iv = "000102030405060708090a0b";
1441 let pt = "0001020304050607";
1442 let ct = "92b657130a74b85a";
1443
1444 let mut actual_tag = [0; 16];
1445 let out = encrypt_aead(
1446 Cipher::aes_128_ocb(),
1447 &Vec::from_hex(key).unwrap(),
1448 Some(&Vec::from_hex(iv).unwrap()),
1449 &Vec::from_hex(aad).unwrap(),
1450 &Vec::from_hex(pt).unwrap(),
1451 &mut actual_tag,
1452 )
1453 .unwrap();
1454
1455 assert_eq!(ct, hex::encode(out));
1456 assert_eq!(tag, hex::encode(actual_tag));
1457
1458 let out = decrypt_aead(
1459 Cipher::aes_128_ocb(),
1460 &Vec::from_hex(key).unwrap(),
1461 Some(&Vec::from_hex(iv).unwrap()),
1462 &Vec::from_hex(aad).unwrap(),
1463 &Vec::from_hex(ct).unwrap(),
1464 &Vec::from_hex(tag).unwrap(),
1465 )
1466 .unwrap();
1467 assert_eq!(pt, hex::encode(out));
1468 }
1469
1470 #[test]
1471 #[cfg(all(ossl110, not(osslconf = "OPENSSL_NO_OCB")))]
1472 fn test_aes_128_ocb_fail() {
1473 let key = "000102030405060708090a0b0c0d0e0f";
1474 let aad = "0001020304050607";
1475 let tag = "16dc76a46d47e1ead537209e8a96d14e";
1476 let iv = "000000000405060708090a0b";
1477 let ct = "92b657130a74b85a";
1478
1479 let out = decrypt_aead(
1480 Cipher::aes_128_ocb(),
1481 &Vec::from_hex(key).unwrap(),
1482 Some(&Vec::from_hex(iv).unwrap()),
1483 &Vec::from_hex(aad).unwrap(),
1484 &Vec::from_hex(ct).unwrap(),
1485 &Vec::from_hex(tag).unwrap(),
1486 );
1487 assert!(out.is_err());
1488 }
1489
1490 #[test]
1491 #[cfg(any(ossl110, libressl))]
1492 fn test_chacha20() {
1493 let key = "0000000000000000000000000000000000000000000000000000000000000000";
1494 let iv = "00000000000000000000000000000000";
1495 let pt =
1496 "000000000000000000000000000000000000000000000000000000000000000000000000000000000\
1497 00000000000000000000000000000000000000000000000";
1498 let ct =
1499 "76b8e0ada0f13d90405d6ae55386bd28bdd219b8a08ded1aa836efcc8b770dc7da41597c5157488d7\
1500 724e03fb8d84a376a43b8f41518a11cc387b669b2ee6586";
1501
1502 cipher_test(Cipher::chacha20(), pt, ct, key, iv);
1503 }
1504
1505 #[test]
1506 #[cfg(any(ossl110, libressl360, awslc))]
1507 fn test_chacha20_poly1305() {
1508 let key = "808182838485868788898a8b8c8d8e8f909192939495969798999a9b9c9d9e9f";
1509 let iv = "070000004041424344454647";
1510 let aad = "50515253c0c1c2c3c4c5c6c7";
1511 let pt =
1512 "4c616469657320616e642047656e746c656d656e206f662074686520636c617373206f66202739393\
1513 a204966204920636f756c64206f6666657220796f75206f6e6c79206f6e652074697020666f722074\
1514 6865206675747572652c2073756e73637265656e20776f756c642062652069742e";
1515 let ct =
1516 "d31a8d34648e60db7b86afbc53ef7ec2a4aded51296e08fea9e2b5a736ee62d63dbea45e8ca967128\
1517 2fafb69da92728b1a71de0a9e060b2905d6a5b67ecd3b3692ddbd7f2d778b8c9803aee328091b58fa\
1518 b324e4fad675945585808b4831d7bc3ff4def08e4b7a9de576d26586cec64b6116";
1519 let tag = "1ae10b594f09e26a7e902ecbd0600691";
1520
1521 let mut actual_tag = [0; 16];
1522 let out = encrypt_aead(
1523 Cipher::chacha20_poly1305(),
1524 &Vec::from_hex(key).unwrap(),
1525 Some(&Vec::from_hex(iv).unwrap()),
1526 &Vec::from_hex(aad).unwrap(),
1527 &Vec::from_hex(pt).unwrap(),
1528 &mut actual_tag,
1529 )
1530 .unwrap();
1531 assert_eq!(ct, hex::encode(out));
1532 assert_eq!(tag, hex::encode(actual_tag));
1533
1534 let out = decrypt_aead(
1535 Cipher::chacha20_poly1305(),
1536 &Vec::from_hex(key).unwrap(),
1537 Some(&Vec::from_hex(iv).unwrap()),
1538 &Vec::from_hex(aad).unwrap(),
1539 &Vec::from_hex(ct).unwrap(),
1540 &Vec::from_hex(tag).unwrap(),
1541 )
1542 .unwrap();
1543 assert_eq!(pt, hex::encode(out));
1544 }
1545
1546 #[test]
1549 #[cfg(all(any(ossl111, libressl), not(osslconf = "OPENSSL_NO_SM4")))]
1550 fn test_sm4_ecb() {
1551 use std::mem;
1552
1553 let key = vec![
1554 0x01, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef, 0xfe, 0xdc, 0xba, 0x98, 0x76, 0x54,
1555 0x32, 0x10,
1556 ];
1557 let pt = vec![
1558 0x01, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef, 0xfe, 0xdc, 0xba, 0x98, 0x76, 0x54,
1559 0x32, 0x10,
1560 ];
1561 let ct = vec![
1562 0x68, 0x1e, 0xdf, 0x34, 0xd2, 0x06, 0x96, 0x5e, 0x86, 0xb3, 0xe9, 0x4f, 0x53, 0x6e,
1563 0x42, 0x46,
1564 ];
1565 let ct1 = vec![
1566 0x59, 0x52, 0x98, 0xc7, 0xc6, 0xfd, 0x27, 0x1f, 0x04, 0x02, 0xf8, 0x04, 0xc3, 0x3d,
1567 0x3f, 0x66,
1568 ];
1569
1570 let block_size = Cipher::sm4_ecb().block_size();
1571 let mut c = Crypter::new(Cipher::sm4_ecb(), Mode::Encrypt, &key, None).unwrap();
1572 c.pad(false);
1573
1574 let mut r = vec![0; pt.len() + Cipher::sm4_ecb().block_size()];
1576 let count = c.update(&pt, &mut r).unwrap();
1577 assert_eq!(ct, &r[..count]);
1578
1579 let mut r1 = vec![0; pt.len() + Cipher::sm4_ecb().block_size()];
1581 for _ in 0..999999 {
1582 c.update(&r[..block_size], &mut r1).unwrap();
1583 mem::swap(&mut r, &mut r1);
1584 }
1585 assert_eq!(ct1, &r[..count]);
1586 }
1587}