1 // validat1.cpp - originally written and placed in the public domain by Wei Dai and Jeffrey Walton
2 // Routines in this source file are only tested in Debug builds.
3 // Source files split in July 2018 to expedite compiles.
4
5 #include "pch.h"
6
7 #define CRYPTOPP_ENABLE_NAMESPACE_WEAK 1
8
9 #include "cryptlib.h"
10 #include "cpu.h"
11 #include "validate.h"
12
13 #include "secblock.h"
14 #include "gzip.h"
15 #include "zlib.h"
16
17 #if defined(CRYPTOPP_ALTIVEC_AVAILABLE)
18 # include "ppc_simd.h"
19 #endif
20
21 #include <iostream>
22 #include <iomanip>
23 #include <sstream>
24
25 // Aggressive stack checking with VS2005 SP1 and above.
26 #if (_MSC_FULL_VER >= 140050727)
27 # pragma strict_gs_check (on)
28 #endif
29
30 #if CRYPTOPP_MSC_VERSION
31 # pragma warning(disable: 4505 4355)
32 #endif
33
34 NAMESPACE_BEGIN(CryptoPP)
NAMESPACE_BEGIN(Test)35 NAMESPACE_BEGIN(Test)
36
37 #if defined(CRYPTOPP_EXTENDED_VALIDATION)
38 bool TestSecBlock()
39 {
40 std::cout << "\nTesting SecBlock...\n\n";
41
42 bool pass1=true, pass2=true, pass3=true, pass4=true, pass5=true, pass6=true, pass7=true, temp=false;
43
44 //************ Allocators ************//
45
46 {
47 std::basic_string<char, std::char_traits<char>, AllocatorWithCleanup<char, false> > s1;
48 std::basic_string<char, std::char_traits<char>, AllocatorWithCleanup<char, true> > s2;
49 s1.resize(1024); s2.resize(1024);
50
51 std::vector<byte, AllocatorWithCleanup<byte, false> > v1;
52 std::vector<byte, AllocatorWithCleanup<byte, true> > v2;
53 v1.resize(1024); v2.resize(1024);
54 }
55
56 //********** Zeroized block **********//
57
58 {
59 // NULL ptr with a size means to create a new SecBlock with all elements zero'd
60 SecByteBlock z1(NULLPTR, 256);
61 temp = true;
62
63 for (size_t i = 0; i < z1.size(); i++)
64 temp &= (z1[i] == 0);
65
66 pass1 &= temp;
67 if (!temp)
68 std::cout << "FAILED:";
69 else
70 std::cout << "passed:";
71 std::cout << " Zeroized byte array\n";
72
73 SecBlock<word32> z2(NULLPTR, 256);
74 temp = true;
75
76 for (size_t i = 0; i < z2.size(); i++)
77 temp &= (z2[i] == 0);
78
79 pass1 &= temp;
80 if (!temp)
81 std::cout << "FAILED:";
82 else
83 std::cout << "passed:";
84 std::cout << " Zeroized word32 array\n";
85
86 SecBlock<word64> z3(NULLPTR, 256);
87 temp = true;
88
89 for (size_t i = 0; i < z3.size(); i++)
90 temp &= (z3[i] == 0);
91
92 pass1 &= temp;
93 if (!temp)
94 std::cout << "FAILED:";
95 else
96 std::cout << "passed:";
97 std::cout << " Zeroized word64 array\n";
98
99 #if defined(CRYPTOPP_WORD128_AVAILABLE)
100 SecBlock<word128> z4(NULLPTR, 256);
101 temp = true;
102
103 for (size_t i = 0; i < z4.size(); i++)
104 temp &= (z4[i] == 0);
105
106 pass1 &= temp;
107 if (!temp)
108 std::cout << "FAILED:";
109 else
110 std::cout << "passed:";
111 std::cout << " Zeroized word128 array\n";
112 #endif
113 }
114
115 //********** Non-zero'd block **********//
116
117 {
118 SecByteBlock z1(NULLPTR, 256);
119 z1.SetMark(0);
120
121 SecBlock<word32> z2(NULLPTR, 256);
122 z2.SetMark(0);
123
124 SecBlock<word64> z3(NULLPTR, 256);
125 z3.SetMark(0);
126
127 #if defined(CRYPTOPP_WORD128_AVAILABLE)
128 SecBlock<word128> z4(NULLPTR, 256);
129 z4.SetMark(0);
130 #endif
131 }
132
133 //********** Assign **********//
134
135 try
136 {
137 SecByteBlock a, b;
138 temp = true;
139
140 a.Assign((const byte*)"a", 1);
141 b.Assign((const byte*)"b", 1);
142
143 temp &= (a.SizeInBytes() == 1);
144 temp &= (b.SizeInBytes() == 1);
145 temp &= (a[0] == 'a');
146 temp &= (b[0] == 'b');
147
148 a.Assign((const byte*)"ab", 2);
149 b.Assign((const byte*)"cd", 2);
150
151 temp &= (a.SizeInBytes() == 2);
152 temp &= (b.SizeInBytes() == 2);
153 temp &= (a[0] == 'a' && a[1] == 'b');
154 temp &= (b[0] == 'c' && b[1] == 'd');
155 }
156 catch(const Exception& /*ex*/)
157 {
158 temp = false;
159 }
160
161 pass2 &= temp;
162 if (!temp)
163 std::cout << "FAILED:";
164 else
165 std::cout << "passed:";
166 std::cout << " Assign byte\n";
167
168 try
169 {
170 SecBlock<word32> a, b;
171 temp = true;
172
173 word32 one[1] = {1}, two[1] = {2};
174 a.Assign(one, 1);
175 b.Assign(two, 1);
176
177 temp &= (a.SizeInBytes() == 4);
178 temp &= (b.SizeInBytes() == 4);
179 temp &= (a[0] == 1);
180 temp &= (b[0] == 2);
181
182 word32 three[2] = {1,2}, four[2] = {3,4};
183 a.Assign(three, 2);
184 b.Assign(four, 2);
185
186 temp &= (a.SizeInBytes() == 8);
187 temp &= (b.SizeInBytes() == 8);
188 temp &= (a[0] == 1 && a[1] == 2);
189 temp &= (b[0] == 3 && b[1] == 4);
190 }
191 catch(const Exception& /*ex*/)
192 {
193 temp = false;
194 }
195
196 pass2 &= temp;
197 if (!temp)
198 std::cout << "FAILED:";
199 else
200 std::cout << "passed:";
201 std::cout << " Assign word32\n";
202
203 try
204 {
205 SecBlock<word64> a, b;
206 temp = true;
207
208 word64 one[1] = {1}, two[1] = {2};
209 a.Assign(one, 1);
210 b.Assign(two, 1);
211
212 temp &= (a.SizeInBytes() == 8);
213 temp &= (b.SizeInBytes() == 8);
214 temp &= (a[0] == 1);
215 temp &= (b[0] == 2);
216
217 word64 three[2] = {1,2}, four[2] = {3,4};
218 a.Assign(three, 2);
219 b.Assign(four, 2);
220
221 temp &= (a.SizeInBytes() == 16);
222 temp &= (b.SizeInBytes() == 16);
223 temp &= (a[0] == 1 && a[1] == 2);
224 temp &= (b[0] == 3 && b[1] == 4);
225 }
226 catch(const Exception& /*ex*/)
227 {
228 temp = false;
229 }
230
231 pass2 &= temp;
232 if (!temp)
233 std::cout << "FAILED:";
234 else
235 std::cout << "passed:";
236 std::cout << " Assign word64\n";
237
238 #if defined(CRYPTOPP_WORD128_AVAILABLE)
239 try
240 {
241 SecBlock<word128> a, b;
242 temp = true;
243
244 word128 one[1] = {1}, two[1] = {2};
245 a.Assign(one, 1);
246 b.Assign(two, 1);
247
248 temp &= (a.SizeInBytes() == 16);
249 temp &= (b.SizeInBytes() == 16);
250 temp &= (a[0] == 1);
251 temp &= (b[0] == 2);
252
253 word128 three[2] = {1,2}, four[2] = {3,4};
254 a.Assign(three, 2);
255 b.Assign(four, 2);
256
257 temp &= (a.SizeInBytes() == 32);
258 temp &= (b.SizeInBytes() == 32);
259 temp &= (a[0] == 1 && a[1] == 2);
260 temp &= (b[0] == 3 && b[1] == 4);
261 }
262 catch(const Exception& /*ex*/)
263 {
264 temp = false;
265 }
266
267 pass2 &= temp;
268 if (!temp)
269 std::cout << "FAILED:";
270 else
271 std::cout << "passed:";
272 std::cout << " Assign word128\n";
273 #endif
274
275 //********** Append **********//
276
277 try
278 {
279 SecByteBlock a, b;
280 temp = true;
281
282 a.Assign((const byte*)"a", 1);
283 b.Assign((const byte*)"b", 1);
284
285 a += b;
286 temp &= (a.SizeInBytes() == 2);
287 temp &= (a[0] == 'a' && a[1] == 'b');
288
289 a.Assign((const byte*)"ab", 2);
290 b.Assign((const byte*)"cd", 2);
291
292 a += b;
293 temp &= (a.SizeInBytes() == 4);
294 temp &= (a[0] == 'a' && a[1] == 'b' && a[2] == 'c' && a[3] == 'd');
295
296 a.Assign((const byte*)"a", 1);
297
298 a += a;
299 temp &= (a.SizeInBytes() == 2);
300 temp &= (a[0] == 'a' && a[1] == 'a');
301
302 a.Assign((const byte*)"ab", 2);
303
304 a += a;
305 temp &= (a.SizeInBytes() == 4);
306 temp &= (a[0] == 'a' && a[1] == 'b' && a[2] == 'a' && a[3] == 'b');
307 }
308 catch(const Exception& /*ex*/)
309 {
310 temp = false;
311 }
312
313 pass3 &= temp;
314 if (!temp)
315 std::cout << "FAILED:";
316 else
317 std::cout << "passed:";
318 std::cout << " Append byte\n";
319
320 try
321 {
322 SecBlock<word32> a, b;
323 temp = true;
324
325 const word32 one[1] = {1}, two[1] = {2};
326 a.Assign(one, 1);
327 b.Assign(two, 1);
328
329 a += b;
330 temp &= (a.SizeInBytes() == 8);
331 temp &= (a[0] == 1 && a[1] == 2);
332
333 const word32 three[2] = {1,2}, four[2] = {3,4};
334 a.Assign(three, 2);
335 b.Assign(four, 2);
336
337 a += b;
338 temp &= (a.SizeInBytes() == 16);
339 temp &= (a[0] == 1 && a[1] == 2 && a[2] == 3 && a[3] == 4);
340
341 a.Assign(one, 1);
342
343 a += a;
344 temp &= (a.SizeInBytes() == 8);
345 temp &= (a[0] == 1 && a[1] == 1);
346
347 a.Assign(three, 2);
348
349 a += a;
350 temp &= (a.SizeInBytes() == 16);
351 temp &= (a[0] == 1 && a[1] == 2 && a[2] == 1 && a[3] == 2);
352 }
353 catch(const Exception& /*ex*/)
354 {
355 temp = false;
356 }
357
358 pass3 &= temp;
359 if (!temp)
360 std::cout << "FAILED:";
361 else
362 std::cout << "passed:";
363 std::cout << " Append word32\n";
364
365 try
366 {
367 SecBlock<word64> a, b;
368 temp = true;
369
370 const word64 one[1] = {1}, two[1] = {2};
371 a.Assign(one, 1);
372 b.Assign(two, 1);
373
374 a += b;
375 temp &= (a.SizeInBytes() == 16);
376 temp &= (a[0] == 1 && a[1] == 2);
377
378 const word64 three[2] = {1,2}, four[2] = {3,4};
379 a.Assign(three, 2);
380 b.Assign(four, 2);
381
382 a += b;
383 temp &= (a.SizeInBytes() == 32);
384 temp &= (a[0] == 1 && a[1] == 2 && a[2] == 3 && a[3] == 4);
385
386 a.Assign(one, 1);
387
388 a += a;
389 temp &= (a.SizeInBytes() == 16);
390 temp &= (a[0] == 1 && a[1] == 1);
391
392 a.Assign(three, 2);
393
394 a += a;
395 temp &= (a.SizeInBytes() == 32);
396 temp &= (a[0] == 1 && a[1] == 2 && a[2] == 1 && a[3] == 2);
397 }
398 catch(const Exception& /*ex*/)
399 {
400 temp = false;
401 }
402
403 pass3 &= temp;
404 if (!temp)
405 std::cout << "FAILED:";
406 else
407 std::cout << "passed:";
408 std::cout << " Append word64\n";
409
410 #if defined(CRYPTOPP_WORD128_AVAILABLE)
411 try
412 {
413 SecBlock<word128> a, b;
414 temp = true;
415
416 const word128 one[1] = {1}, two[1] = {2};
417 a.Assign(one, 1);
418 b.Assign(two, 1);
419
420 a += b;
421 temp &= (a.SizeInBytes() == 32);
422 temp &= (a[0] == 1 && a[1] == 2);
423
424 const word128 three[2] = {1,2}, four[2] = {3,4};
425 a.Assign(three, 2);
426 b.Assign(four, 2);
427
428 a += b;
429 temp &= (a.SizeInBytes() == 64);
430 temp &= (a[0] == 1 && a[1] == 2 && a[2] == 3 && a[3] == 4);
431
432 a.Assign(one, 1);
433
434 a += a;
435 temp &= (a.SizeInBytes() == 32);
436 temp &= (a[0] == 1 && a[1] == 1);
437
438 a.Assign(three, 2);
439
440 a += a;
441 temp &= (a.SizeInBytes() == 64);
442 temp &= (a[0] == 1 && a[1] == 2 && a[2] == 1 && a[3] == 2);
443 }
444 catch(const Exception& /*ex*/)
445 {
446 temp = false;
447 }
448
449 pass3 &= temp;
450 if (!temp)
451 std::cout << "FAILED:";
452 else
453 std::cout << "passed:";
454 std::cout << " Append word128\n";
455 #endif
456
457 //********** Concatenate **********//
458
459 // byte
460 try
461 {
462 SecByteBlock a, b, c;
463 temp = true;
464
465 a.Assign((const byte*)"a", 1);
466 b.Assign((const byte*)"b", 1);
467
468 c = a + b;
469 temp &= (a[0] == 'a');
470 temp &= (b[0] == 'b');
471 temp &= (c.SizeInBytes() == 2);
472 temp &= (c[0] == 'a' && c[1] == 'b');
473
474 a.Assign((const byte*)"ab", 2);
475 b.Assign((const byte*)"cd", 2);
476
477 c = a + b;
478 temp &= (a[0] == 'a' && a[1] == 'b');
479 temp &= (b[0] == 'c' && b[1] == 'd');
480 temp &= (c.SizeInBytes() == 4);
481 temp &= (c[0] == 'a' && c[1] == 'b' && c[2] == 'c' && c[3] == 'd');
482 }
483 catch(const Exception& /*ex*/)
484 {
485 temp = false;
486 }
487
488 pass4 &= temp;
489 if (!temp)
490 std::cout << "FAILED:";
491 else
492 std::cout << "passed:";
493 std::cout << " Concatenate byte\n";
494
495 // word32
496 try
497 {
498 SecBlock<word32> a, b, c;
499 temp = true;
500
501 const word32 one[1] = {1}, two[1] = {2};
502 a.Assign(one, 1);
503 b.Assign(two, 1);
504
505 c = a + b;
506 temp &= (a[0] == 1);
507 temp &= (b[0] == 2);
508 temp &= (c.SizeInBytes() == 8);
509 temp &= (c[0] == 1 && c[1] == 2);
510
511 const word32 three[2] = {1,2}, four[2] = {3,4};
512 a.Assign(three, 2);
513 b.Assign(four, 2);
514
515 c = a + b;
516 temp &= (a[0] == 1 && a[1] == 2);
517 temp &= (b[0] == 3 && b[1] == 4);
518 temp &= (c.SizeInBytes() == 16);
519 temp &= (c[0] == 1 && c[1] == 2 && c[2] == 3 && c[3] == 4);
520 }
521 catch(const Exception& /*ex*/)
522 {
523 temp = false;
524 }
525
526 pass4 &= temp;
527 if (!temp)
528 std::cout << "FAILED:";
529 else
530 std::cout << "passed:";
531 std::cout << " Concatenate word32\n";
532
533 // word64
534 try
535 {
536 SecBlock<word64> a, b, c;
537 temp = true;
538
539 const word64 one[1] = {1}, two[1] = {2};
540 a.Assign(one, 1);
541 b.Assign(two, 1);
542
543 c = a + b;
544 temp &= (a[0] == 1);
545 temp &= (b[0] == 2);
546 temp &= (c.SizeInBytes() == 16);
547 temp &= (c[0] == 1 && c[1] == 2);
548
549 const word64 three[2] = {1,2}, four[2] = {3,4};
550 a.Assign(three, 2);
551 b.Assign(four, 2);
552
553 c = a + b;
554 temp &= (a[0] == 1 && a[1] == 2);
555 temp &= (b[0] == 3 && b[1] == 4);
556 temp &= (c.SizeInBytes() == 32);
557 temp &= (c[0] == 1 && c[1] == 2 && c[2] == 3 && c[3] == 4);
558 }
559 catch(const Exception& /*ex*/)
560 {
561 temp = false;
562 }
563
564 pass4 &= temp;
565 if (!temp)
566 std::cout << "FAILED:";
567 else
568 std::cout << "passed:";
569 std::cout << " Concatenate word64\n";
570
571 #if defined(CRYPTOPP_WORD128_AVAILABLE)
572 try
573 {
574 SecBlock<word128> a, b, c;
575 temp = true;
576
577 const word128 one[1] = {1}, two[1] = {2};
578 a.Assign(one, 1);
579 b.Assign(two, 1);
580
581 c = a + b;
582 temp &= (a[0] == 1);
583 temp &= (b[0] == 2);
584 temp &= (c.SizeInBytes() == 32);
585 temp &= (c[0] == 1 && c[1] == 2);
586
587 const word128 three[2] = {1,2}, four[2] = {3,4};
588 a.Assign(three, 2);
589 b.Assign(four, 2);
590
591 c = a + b;
592 temp &= (a[0] == 1 && a[1] == 2);
593 temp &= (b[0] == 3 && b[1] == 4);
594 temp &= (c.SizeInBytes() == 64);
595 temp &= (c[0] == 1 && c[1] == 2 && c[2] == 3 && c[3] == 4);
596 }
597 catch(const Exception& /*ex*/)
598 {
599 temp = false;
600 }
601
602 pass4 &= temp;
603 if (!temp)
604 std::cout << "FAILED:";
605 else
606 std::cout << "passed:";
607 std::cout << " Concatenate word128\n";
608 #endif
609
610 //********** Equality **********//
611
612 // byte
613 try
614 {
615 static const byte str1[] = "abcdefghijklmnopqrstuvwxyz";
616 static const byte str2[] = "zyxwvutsrqponmlkjihgfedcba";
617 static const byte str3[] = "0123456789";
618
619 temp = true;
620 SecByteBlock a,b;
621
622 a.Assign(str1, COUNTOF(str1));
623 b.Assign(str1, COUNTOF(str1));
624 temp &= (a.operator==(b));
625
626 a.Assign(str3, COUNTOF(str3));
627 b.Assign(str3, COUNTOF(str3));
628 temp &= (a == b);
629
630 a.Assign(str1, COUNTOF(str1));
631 b.Assign(str2, COUNTOF(str2));
632 temp &= (a.operator!=(b));
633
634 a.Assign(str1, COUNTOF(str1));
635 b.Assign(str3, COUNTOF(str3));
636 temp &= (a != b);
637 }
638 catch(const Exception& /*ex*/)
639 {
640 temp = false;
641 }
642
643 pass5 &= temp;
644 if (!temp)
645 std::cout << "FAILED:";
646 else
647 std::cout << "passed:";
648 std::cout << " Equality byte\n";
649
650 // word32
651 try
652 {
653 static const word32 str1[] = {2,3,5,7,11,13,17,19,23,29,31,37,41,43,47,53,59,61,67,71,73,79,83,89,97};
654 static const word32 str2[] = {97,89,83,79,73,71,67,61,59,53,47,43,41,37,31,29,23,19,17,13,11,7,5,3,2};
655 static const word32 str3[] = {0,1,2,3,4,5,6,7,8,9};
656
657 temp = true;
658 SecBlock<word32> a,b;
659
660 a.Assign(str1, COUNTOF(str1));
661 b.Assign(str1, COUNTOF(str1));
662 temp &= (a.operator==(b));
663
664 a.Assign(str3, COUNTOF(str3));
665 b.Assign(str3, COUNTOF(str3));
666 temp &= (a == b);
667
668 a.Assign(str1, COUNTOF(str1));
669 b.Assign(str2, COUNTOF(str2));
670 temp &= (a.operator!=(b));
671
672 a.Assign(str1, COUNTOF(str1));
673 b.Assign(str3, COUNTOF(str3));
674 temp &= (a != b);
675 }
676 catch(const Exception& /*ex*/)
677 {
678 temp = false;
679 }
680
681 pass5 &= temp;
682 if (!temp)
683 std::cout << "FAILED:";
684 else
685 std::cout << "passed:";
686 std::cout << " Equality word32\n";
687
688 // word64
689 try
690 {
691 static const word64 str1[] = {2,3,5,7,11,13,17,19,23,29,31,37,41,43,47,53,59,61,67,71,73,79,83,89,97};
692 static const word64 str2[] = {97,89,83,79,73,71,67,61,59,53,47,43,41,37,31,29,23,19,17,13,11,7,5,3,2};
693 static const word64 str3[] = {0,1,2,3,4,5,6,7,8,9};
694
695 temp = true;
696 SecBlock<word64> a,b;
697
698 a.Assign(str1, COUNTOF(str1));
699 b.Assign(str1, COUNTOF(str1));
700 temp &= (a.operator==(b));
701
702 a.Assign(str3, COUNTOF(str3));
703 b.Assign(str3, COUNTOF(str3));
704 temp &= (a == b);
705
706 a.Assign(str1, COUNTOF(str1));
707 b.Assign(str2, COUNTOF(str2));
708 temp &= (a.operator!=(b));
709
710 a.Assign(str1, COUNTOF(str1));
711 b.Assign(str3, COUNTOF(str3));
712 temp &= (a != b);
713 }
714 catch(const Exception& /*ex*/)
715 {
716 temp = false;
717 }
718
719 pass5 &= temp;
720 if (!temp)
721 std::cout << "FAILED:";
722 else
723 std::cout << "passed:";
724 std::cout << " Equality word64\n";
725
726 #if defined(CRYPTOPP_WORD128_AVAILABLE)
727 // word128
728 try
729 {
730 static const word128 str1[] = {2,3,5,7,11,13,17,19,23,29,31,37,41,43,47,53,59,61,67,71,73,79,83,89,97};
731 static const word128 str2[] = {97,89,83,79,73,71,67,61,59,53,47,43,41,37,31,29,23,19,17,13,11,7,5,3,2};
732 static const word128 str3[] = {0,1,2,3,4,5,6,7,8,9};
733
734 temp = true;
735 SecBlock<word128> a,b;
736
737 a.Assign(str1, COUNTOF(str1));
738 b.Assign(str1, COUNTOF(str1));
739 temp &= (a.operator==(b));
740
741 a.Assign(str3, COUNTOF(str3));
742 b.Assign(str3, COUNTOF(str3));
743 temp &= (a == b);
744
745 a.Assign(str1, COUNTOF(str1));
746 b.Assign(str2, COUNTOF(str2));
747 temp &= (a.operator!=(b));
748
749 a.Assign(str1, COUNTOF(str1));
750 b.Assign(str3, COUNTOF(str3));
751 temp &= (a != b);
752 }
753 catch(const Exception& /*ex*/)
754 {
755 temp = false;
756 }
757
758 pass5 &= temp;
759 if (!temp)
760 std::cout << "FAILED:";
761 else
762 std::cout << "passed:";
763 std::cout << " Equality word128\n";
764 #endif
765
766 //********** Allocator Size/Overflow **********//
767
768 try
769 {
770 temp = false;
771
772 AllocatorBase<word32> A;
773 const size_t max = A.max_size();
774 SecBlock<word32> t(max+1);
775 }
776 catch(const Exception& /*ex*/)
777 {
778 temp = true;
779 }
780 catch(const std::exception& /*ex*/)
781 {
782 temp = true;
783 }
784
785 pass6 &= temp;
786 if (!temp)
787 std::cout << "FAILED:";
788 else
789 std::cout << "passed:";
790 std::cout << " Overflow word32\n";
791
792 try
793 {
794 temp = false;
795
796 AllocatorBase<word64> A;
797 const size_t max = A.max_size();
798 SecBlock<word64> t(max+1);
799 }
800 catch(const Exception& /*ex*/)
801 {
802 temp = true;
803 }
804 catch(const std::exception& /*ex*/)
805 {
806 temp = true;
807 }
808
809 pass6 &= temp;
810 if (!temp)
811 std::cout << "FAILED:";
812 else
813 std::cout << "passed:";
814 std::cout << " Overflow word64\n";
815
816 #if defined(CRYPTOPP_WORD128_AVAILABLE)
817 try
818 {
819 temp = false;
820
821 AllocatorBase<word128> A;
822 const size_t max = A.max_size();
823 SecBlock<word128> t(max+1);
824 }
825 catch(const Exception& /*ex*/)
826 {
827 temp = true;
828 }
829 catch(const std::exception& /*ex*/)
830 {
831 temp = true;
832 }
833
834 pass6 &= temp;
835 if (!temp)
836 std::cout << "FAILED:";
837 else
838 std::cout << "passed:";
839 std::cout << " Overflow word128\n";
840 #endif
841
842 //********** FixedSizeAllocatorWithCleanup and Grow **********//
843
844 // byte
845 try
846 {
847 static const unsigned int SIZE = 8;
848 SecBlockWithHint<byte, SIZE> block(SIZE);
849 memset(block, 0xaa, block.SizeInBytes());
850
851 temp = true;
852 block.CleanGrow(SIZE*2);
853 temp &= (block.size() == SIZE*2);
854
855 for (size_t i = 0; i < block.size()/2; i++)
856 temp &= (block[i] == 0xaa);
857 for (size_t i = block.size()/2; i < block.size(); i++)
858 temp &= (block[i] == 0);
859
860 block.CleanNew(SIZE*4);
861 temp &= (block.size() == SIZE*4);
862 for (size_t i = 0; i < block.size(); i++)
863 temp &= (block[i] == 0);
864 }
865 catch(const Exception& /*ex*/)
866 {
867 temp = false;
868 }
869 catch(const std::exception& /*ex*/)
870 {
871 temp = false;
872 }
873
874 pass7 &= temp;
875 if (!temp)
876 std::cout << "FAILED:";
877 else
878 std::cout << "passed:";
879 std::cout << " FixedSizeAllocator Grow with byte\n";
880
881 // word32
882 try
883 {
884 static const unsigned int SIZE = 8;
885 SecBlockWithHint<word32, SIZE> block(SIZE);
886 memset(block, 0xaa, block.SizeInBytes());
887
888 temp = true;
889 block.CleanGrow(SIZE*2);
890 temp &= (block.size() == SIZE*2);
891
892 for (size_t i = 0; i < block.size()/2; i++)
893 temp &= (block[i] == 0xaaaaaaaa);
894
895 for (size_t i = block.size()/2; i < block.size(); i++)
896 temp &= (block[i] == 0);
897
898 block.CleanNew(SIZE*4);
899 temp &= (block.size() == SIZE*4);
900 for (size_t i = 0; i < block.size(); i++)
901 temp &= (block[i] == 0);
902 }
903 catch(const Exception& /*ex*/)
904 {
905 temp = false;
906 }
907 catch(const std::exception& /*ex*/)
908 {
909 temp = false;
910 }
911
912 pass7 &= temp;
913 if (!temp)
914 std::cout << "FAILED:";
915 else
916 std::cout << "passed:";
917 std::cout << " FixedSizeAllocator Grow with word32\n";
918
919 // word64
920 try
921 {
922 static const unsigned int SIZE = 8;
923 SecBlockWithHint<word64, SIZE> block(SIZE);
924 memset(block, 0xaa, block.SizeInBytes());
925
926 temp = true;
927 block.CleanGrow(SIZE*2);
928 temp &= (block.size() == SIZE*2);
929
930 for (size_t i = 0; i < block.size()/2; i++)
931 temp &= (block[i] == W64LIT(0xaaaaaaaaaaaaaaaa));
932
933 for (size_t i = block.size()/2; i < block.size(); i++)
934 temp &= (block[i] == 0);
935
936 block.CleanNew(SIZE*4);
937 temp &= (block.size() == SIZE*4);
938 for (size_t i = 0; i < block.size(); i++)
939 temp &= (block[i] == 0);
940 }
941 catch(const Exception& /*ex*/)
942 {
943 temp = false;
944 }
945 catch(const std::exception& /*ex*/)
946 {
947 temp = false;
948 }
949
950 pass7 &= temp;
951 if (!temp)
952 std::cout << "FAILED:";
953 else
954 std::cout << "passed:";
955 std::cout << " FixedSizeAllocator Grow with word64\n";
956
957 #if defined(CRYPTOPP_WORD128_AVAILABLE)
958 // word128
959 try
960 {
961 static const unsigned int SIZE = 8;
962 SecBlock<word128, AllocatorWithCleanup<word128, true> > block(SIZE);
963 memset(block, 0xaa, block.SizeInBytes());
964
965 temp = true;
966 block.CleanGrow(SIZE*2);
967 temp &= (block.size() == SIZE*2);
968
969 for (size_t i = 0; i < block.size()/2; i++)
970 temp &= (block[i] == (((word128)W64LIT(0xaaaaaaaaaaaaaaaa) << 64U) | W64LIT(0xaaaaaaaaaaaaaaaa)));
971
972 for (size_t i = block.size()/2; i < block.size(); i++)
973 temp &= (block[i] == 0);
974
975 block.CleanNew(SIZE*4);
976 temp &= (block.size() == SIZE*4);
977 for (size_t i = 0; i < block.size(); i++)
978 temp &= (block[i] == 0);
979 }
980 catch(const Exception& /*ex*/)
981 {
982 temp = false;
983 }
984 catch(const std::exception& /*ex*/)
985 {
986 temp = false;
987 }
988
989 pass7 &= temp;
990 if (!temp)
991 std::cout << "FAILED:";
992 else
993 std::cout << "passed:";
994 std::cout << " FixedSizeAllocator Grow with word128\n";
995 #endif
996
997 return pass1 && pass2 && pass3 && pass4 && pass5 && pass6 && pass7;
998 }
999 #endif
1000
1001 #if defined(CRYPTOPP_EXTENDED_VALIDATION)
TestHuffmanCodes()1002 bool TestHuffmanCodes()
1003 {
1004 std::cout << "\nTesting Huffman codes...\n\n";
1005 bool pass=true;
1006
1007 static const size_t nCodes = 30;
1008 const unsigned int codeCounts[nCodes] = {
1009 1, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1010 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1011 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
1012
1013 static const unsigned int maxCodeBits = nCodes >> 1;
1014 unsigned int codeBits[nCodes] = {
1015 ~0u, ~0u, ~0u, ~0u, ~0u,
1016 ~0u, ~0u, ~0u, ~0u, ~0u,
1017 ~0u, ~0u, ~0u, ~0u, ~0u,
1018 };
1019
1020 try
1021 {
1022 HuffmanEncoder::GenerateCodeLengths(codeBits, maxCodeBits, codeCounts, nCodes);
1023 }
1024 catch(const Exception& /*ex*/)
1025 {
1026 pass=false;
1027 }
1028
1029 if (!pass)
1030 std::cout << "FAILED:";
1031 else
1032 std::cout << "passed:";
1033 std::cout << " GenerateCodeLengths" << std::endl;
1034
1035 // Try to crash the HuffmanDecoder
1036 for (unsigned int i=0; i<128; ++i)
1037 {
1038 try
1039 {
1040 byte data1[0xfff]; // Place on stack, avoid new
1041 unsigned int data2[0xff];
1042
1043 unsigned int len1 = GlobalRNG().GenerateWord32(4, 0xfff);
1044 GlobalRNG().GenerateBlock(data1, len1);
1045 unsigned int len2 = GlobalRNG().GenerateWord32(4, 0xff);
1046 GlobalRNG().GenerateBlock((byte*)data2, len2*sizeof(unsigned int));
1047
1048 ArraySource source(data1, len1, false);
1049 HuffmanDecoder decoder(data2, len2);
1050
1051 LowFirstBitReader reader(source);
1052 unsigned int val;
1053 for (unsigned int j=0; !source.AnyRetrievable(); ++j)
1054 decoder.Decode(reader, val);
1055 }
1056 catch (const Exception&) {}
1057 }
1058
1059 std::cout << "passed: HuffmanDecoder decode" << std::endl;
1060
1061 return pass;
1062 }
1063 #endif
1064
1065 #if defined(CRYPTOPP_EXTENDED_VALIDATION)
1066 # if defined(CRYPTOPP_ALTIVEC_AVAILABLE)
TestAltivecOps()1067 bool TestAltivecOps()
1068 {
1069 std::cout << "\nTesting Altivec operations...\n\n";
1070
1071 if (HasAltivec() == false)
1072 {
1073 std::cout << "\nAltivec not available, skipping test." << std::endl;
1074 return true;
1075 }
1076
1077 // These tests may seem superflous, but we really want to test the
1078 // Altivec/POWER4 implementation. That does not happen when POWER7
1079 // or POWER8 is available because we use POWER7's unaligned loads
1080 // and stores with POWER8's AES, SHA, etc. These tests enage
1081 // Altivec/POWER4 without POWER7, like on an old PowerMac.
1082
1083 //********** Unaligned loads and stores **********//
1084 bool pass1=true;
1085
1086 CRYPTOPP_ALIGN_DATA(16)
1087 byte dest[20], src[20] = {23,22,21,20,19,18,17,16,15,14,13,12,11,10,9,8,7,6,5,4};
1088 const byte st1[16] = {22,21,20,19,18,17,16,15,14,13,12,11,10,9,8,7};
1089 const byte st2[16] = {21,20,19,18,17,16,15,14,13,12,11,10,9,8,7,6};
1090 const byte st3[16] = {20,19,18,17,16,15,14,13,12,11,10,9,8,7,6,5};
1091
1092 VecStore(VecLoad(src), dest);
1093 pass1 = (0 == std::memcmp(src, dest, 16)) && pass1;
1094 CRYPTOPP_ASSERT(pass1);
1095
1096 VecStore(VecLoad(src+1), dest+1);
1097 pass1 = (0 == std::memcmp(st1, dest+1, 16)) && pass1;
1098 CRYPTOPP_ASSERT(pass1);
1099
1100 VecStore(VecLoad(src+2), dest+2);
1101 pass1 = (0 == std::memcmp(st2, dest+2, 16)) && pass1;
1102 CRYPTOPP_ASSERT(pass1);
1103
1104 VecStore(VecLoad(src+3), dest+3);
1105 pass1 = (0 == std::memcmp(st3, dest+3, 16)) && pass1;
1106 CRYPTOPP_ASSERT(pass1);
1107
1108 VecStoreBE(VecLoadBE(src), dest);
1109 pass1 = (0 == std::memcmp(src, dest, 16)) && pass1;
1110 CRYPTOPP_ASSERT(pass1);
1111
1112 VecStoreBE(VecLoadBE(src+1), dest+1);
1113 pass1 = (0 == std::memcmp(st1, dest+1, 16)) && pass1;
1114 CRYPTOPP_ASSERT(pass1);
1115
1116 VecStoreBE(VecLoadBE(src+2), dest+2);
1117 pass1 = (0 == std::memcmp(st2, dest+2, 16)) && pass1;
1118 CRYPTOPP_ASSERT(pass1);
1119
1120 VecStoreBE(VecLoadBE(src+3), dest+3);
1121 pass1 = (0 == std::memcmp(st3, dest+3, 16)) && pass1;
1122 CRYPTOPP_ASSERT(pass1);
1123
1124 #if (CRYPTOPP_LITTLE_ENDIAN)
1125 VecStore(VecLoadBE(src), dest);
1126 pass1 = (0 != std::memcmp(src, dest, 16)) && pass1;
1127 CRYPTOPP_ASSERT(pass1);
1128
1129 VecStoreBE(VecLoad(src), dest);
1130 pass1 = (0 != std::memcmp(src, dest, 16)) && pass1;
1131 CRYPTOPP_ASSERT(pass1);
1132 #endif
1133
1134 if (!pass1)
1135 std::cout << "FAILED:";
1136 else
1137 std::cout << "passed:";
1138 std::cout << " Altivec loads and stores" << std::endl;
1139
1140 //********** Shifts **********//
1141 bool pass2=true;
1142
1143 uint8x16_p val = {0xff,0xff,0xff,0xff, 0xff,0xff,0xff,0xff,
1144 0xff,0xff,0xff,0xff, 0xff,0xff,0xff,0xff};
1145
1146 pass2 = (VecEqual(val, VecShiftLeftOctet<0>(val))) && pass2;
1147 CRYPTOPP_ASSERT(pass2);
1148 pass2 = (VecEqual(val, VecShiftRightOctet<0>(val))) && pass2;
1149 CRYPTOPP_ASSERT(pass2);
1150
1151 uint8x16_p lsh1 = {0xff,0xff,0xff,0xff, 0xff,0xff,0xff,0xff,
1152 0xff,0xff,0xff,0xff, 0xff,0xff,0xff,0x00};
1153 uint8x16_p rsh1 = {0x00,0xff,0xff,0xff, 0xff,0xff,0xff,0xff,
1154 0xff,0xff,0xff,0xff, 0xff,0xff,0xff,0xff};
1155
1156 pass2 = (VecEqual(lsh1, VecShiftLeftOctet<1>(val))) && pass2;
1157 CRYPTOPP_ASSERT(pass2);
1158 pass2 = (VecEqual(rsh1, VecShiftRightOctet<1>(val))) && pass2;
1159 CRYPTOPP_ASSERT(pass2);
1160
1161 uint8x16_p lsh15 = {0xff,0x00,0x00,0x00, 0x00,0x00,0x00,0x00,
1162 0x00,0x00,0x00,0x00, 0x00,0x00,0x00,0x00};
1163 uint8x16_p rsh15 = {0x00,0x00,0x00,0x00, 0x00,0x00,0x00,0x00,
1164 0x00,0x00,0x00,0x00, 0x00,0x00,0x00,0xff};
1165
1166 pass2 = (VecEqual(lsh15, VecShiftLeftOctet<15>(val))) && pass2;
1167 CRYPTOPP_ASSERT(pass2);
1168 pass2 = (VecEqual(rsh15, VecShiftRightOctet<15>(val))) && pass2;
1169 CRYPTOPP_ASSERT(pass2);
1170
1171 uint8x16_p lsh16 = {0x00,0x00,0x00,0x00, 0x00,0x00,0x00,0x00,
1172 0x00,0x00,0x00,0x00, 0x00,0x00,0x00,0x00};
1173 uint8x16_p rsh16 = {0x00,0x00,0x00,0x00, 0x00,0x00,0x00,0x00,
1174 0x00,0x00,0x00,0x00, 0x00,0x00,0x00,0x00};
1175
1176 pass2 = (VecEqual(lsh16, VecShiftLeftOctet<16>(val))) && pass2;
1177 CRYPTOPP_ASSERT(pass2);
1178 pass2 = (VecEqual(rsh16, VecShiftRightOctet<16>(val))) && pass2;
1179 CRYPTOPP_ASSERT(pass2);
1180
1181 if (!pass2)
1182 std::cout << "FAILED:";
1183 else
1184 std::cout << "passed:";
1185 std::cout << " Altivec left and right shifts" << std::endl;
1186
1187 //********** Extraction **********//
1188 bool pass3=true;
1189
1190 const byte bex1[] = {0x1f,0x1e,0x1d,0x1c, 0x1b,0x1a,0x19,0x18,
1191 0x17,0x16,0x15,0x14, 0x13,0x12,0x11,0x10};
1192 const byte bex2[] = {0x00,0x00,0x00,0x00, 0x00,0x00,0x00,0x00,
1193 0x17,0x16,0x15,0x14, 0x13,0x12,0x11,0x10};
1194 const byte bex3[] = {0x00,0x00,0x00,0x00, 0x00,0x00,0x00,0x00,
1195 0x1f,0x1e,0x1d,0x1c, 0x1b,0x1a,0x19,0x18};
1196
1197 const uint8x16_p ex1 = (uint8x16_p)VecLoad(bex1);
1198 const uint8x16_p ex2 = (uint8x16_p)VecLoad(bex2);
1199 const uint8x16_p ex3 = (uint8x16_p)VecLoad(bex3);
1200
1201 pass3 = VecEqual(ex2, VecGetLow(ex1)) && pass3;
1202 CRYPTOPP_ASSERT(pass3);
1203 pass3 = VecEqual(ex3, VecGetHigh(ex1)) && pass3;
1204 CRYPTOPP_ASSERT(pass3);
1205
1206 uint8x16_p ex4 = VecShiftRightOctet<8>(VecShiftLeftOctet<8>(ex1));
1207 pass3 = VecEqual(ex4, VecGetLow(ex1)) && pass3;
1208 CRYPTOPP_ASSERT(pass3);
1209 uint8x16_p ex5 = VecShiftRightOctet<8>(ex1);
1210 pass3 = VecEqual(ex5, VecGetHigh(ex1)) && pass3;
1211 CRYPTOPP_ASSERT(pass3);
1212
1213 if (!pass3)
1214 std::cout << "FAILED:";
1215 else
1216 std::cout << "passed:";
1217 std::cout << " Altivec vector extraction" << std::endl;
1218
1219 return pass1 && pass2 && pass3;
1220 }
1221 #endif
1222 #endif
1223
1224 NAMESPACE_END // Test
1225 NAMESPACE_END // CryptoPP
1226