00001
00002
00003 #include "pch.h"
00004
00005 #include "files.h"
00006 #include "hex.h"
00007 #include "base64.h"
00008 #include "modes.h"
00009 #include "cbcmac.h"
00010 #include "dmac.h"
00011 #include "idea.h"
00012 #include "des.h"
00013 #include "rc2.h"
00014 #include "arc4.h"
00015 #include "rc5.h"
00016 #include "blowfish.h"
00017 #include "diamond.h"
00018 #include "wake.h"
00019 #include "3way.h"
00020 #include "safer.h"
00021 #include "gost.h"
00022 #include "shark.h"
00023 #include "cast.h"
00024 #include "square.h"
00025 #include "seal.h"
00026 #include "rc6.h"
00027 #include "mars.h"
00028 #include "rijndael.h"
00029 #include "twofish.h"
00030 #include "serpent.h"
00031 #include "skipjack.h"
00032 #include "osrng.h"
00033 #include "zdeflate.h"
00034
00035 #include <stdlib.h>
00036 #include <time.h>
00037 #include <memory>
00038 #include <iostream>
00039 #include <iomanip>
00040
00041 #include "validate.h"
00042
00043 USING_NAMESPACE(CryptoPP)
00044 USING_NAMESPACE(std)
00045
00046 bool ValidateAll(bool thorough)
00047 {
00048 bool pass=TestSettings();
00049 pass=TestOS_RNG() && pass;
00050
00051 pass=ValidateCRC32() && pass;
00052 pass=ValidateAdler32() && pass;
00053 pass=ValidateMD2() && pass;
00054 pass=ValidateMD5() && pass;
00055 pass=ValidateSHA() && pass;
00056 pass=ValidateSHA2() && pass;
00057 pass=ValidateHAVAL() && pass;
00058 pass=ValidateTiger() && pass;
00059 pass=ValidateRIPEMD() && pass;
00060 pass=ValidatePanama() && pass;
00061
00062 pass=ValidateMD5MAC() && pass;
00063 pass=ValidateHMAC() && pass;
00064 pass=ValidateXMACC() && pass;
00065
00066 pass=ValidatePBKDF() && pass;
00067
00068 pass=ValidateDES() && pass;
00069 pass=ValidateCipherModes() && pass;
00070 pass=ValidateIDEA() && pass;
00071 pass=ValidateSAFER() && pass;
00072 pass=ValidateRC2() && pass;
00073 pass=ValidateARC4() && pass;
00074 pass=ValidateRC5() && pass;
00075 pass=ValidateBlowfish() && pass;
00076 pass=ValidateDiamond2() && pass;
00077 pass=ValidateThreeWay() && pass;
00078 pass=ValidateGOST() && pass;
00079 pass=ValidateSHARK() && pass;
00080 pass=ValidateCAST() && pass;
00081 pass=ValidateSquare() && pass;
00082 pass=ValidateSKIPJACK() && pass;
00083 pass=ValidateSEAL() && pass;
00084 pass=ValidateRC6() && pass;
00085 pass=ValidateMARS() && pass;
00086 pass=ValidateRijndael() && pass;
00087 pass=ValidateTwofish() && pass;
00088 pass=ValidateSerpent() && pass;
00089
00090 pass=ValidateBBS() && pass;
00091 pass=ValidateDH() && pass;
00092 pass=ValidateMQV() && pass;
00093 pass=ValidateRSA() && pass;
00094 pass=ValidateElGamal() && pass;
00095 pass=ValidateDLIES() && pass;
00096 pass=ValidateNR() && pass;
00097 pass=ValidateDSA(thorough) && pass;
00098 pass=ValidateLUC() && pass;
00099 pass=ValidateLUC_DH() && pass;
00100 pass=ValidateLUC_DL() && pass;
00101 pass=ValidateXTR_DH() && pass;
00102 pass=ValidateRabin() && pass;
00103 pass=ValidateRW() && pass;
00104
00105 pass=ValidateECP() && pass;
00106 pass=ValidateEC2N() && pass;
00107 pass=ValidateECDSA() && pass;
00108 pass=ValidateESIGN() && pass;
00109
00110 if (pass)
00111 cout << "\nAll tests passed!\n";
00112 else
00113 cout << "\nOops! Not all tests passed.\n";
00114
00115 return pass;
00116 }
00117
00118 bool TestSettings()
00119 {
00120 bool pass = true;
00121
00122 cout << "\nTesting Settings...\n\n";
00123
00124 if (*(word32 *)"\x01\x02\x03\x04" == 0x04030201L)
00125 {
00126 #ifdef IS_LITTLE_ENDIAN
00127 cout << "passed: ";
00128 #else
00129 cout << "FAILED: ";
00130 pass = false;
00131 #endif
00132 cout << "Your machine is little endian.\n";
00133 }
00134 else if (*(word32 *)"\x01\x02\x03\x04" == 0x01020304L)
00135 {
00136 #ifndef IS_LITTLE_ENDIAN
00137 cout << "passed: ";
00138 #else
00139 cout << "FAILED: ";
00140 pass = false;
00141 #endif
00142 cout << "Your machine is big endian.\n";
00143 }
00144 else
00145 {
00146 cout << "FAILED: Your machine is neither big endian nor little endian.\n";
00147 pass = false;
00148 }
00149
00150 if (sizeof(byte) == 1)
00151 cout << "passed: ";
00152 else
00153 {
00154 cout << "FAILED: ";
00155 pass = false;
00156 }
00157 cout << "sizeof(byte) == " << sizeof(byte) << endl;
00158
00159 if (sizeof(word16) == 2)
00160 cout << "passed: ";
00161 else
00162 {
00163 cout << "FAILED: ";
00164 pass = false;
00165 }
00166 cout << "sizeof(word16) == " << sizeof(word16) << endl;
00167
00168 if (sizeof(word32) == 4)
00169 cout << "passed: ";
00170 else
00171 {
00172 cout << "FAILED: ";
00173 pass = false;
00174 }
00175 cout << "sizeof(word32) == " << sizeof(word32) << endl;
00176
00177 #ifdef WORD64_AVAILABLE
00178 if (sizeof(word64) == 8)
00179 cout << "passed: ";
00180 else
00181 {
00182 cout << "FAILED: ";
00183 pass = false;
00184 }
00185 cout << "sizeof(word64) == " << sizeof(word64) << endl;
00186 #else
00187 if (sizeof(dword) >= 8)
00188 {
00189 cout << "FAILED: sizeof(dword) >= 8, but WORD64_AVAILABLE not defined" << endl;
00190 pass = false;
00191 }
00192 else
00193 cout << "passed: word64 not available" << endl;
00194 #endif
00195
00196 if (sizeof(dword) == 2*sizeof(word))
00197 cout << "passed: ";
00198 else
00199 {
00200 cout << "FAILED: ";
00201 pass = false;
00202 }
00203 cout << "sizeof(word) == " << sizeof(word) << ", sizeof(dword) == " << sizeof(dword) << endl;
00204
00205 dword test = (dword(1)<<WORD_BITS) + 2;
00206 if (HIGH_WORD(test) == 1 && LOW_WORD(test) == 2)
00207 cout << "passed: ";
00208 else
00209 {
00210 cout << "FAILED: ";
00211 pass = false;
00212 }
00213 cout << "HIGH_WORD() and LOW_WORD() macros\n";
00214
00215 if (!pass)
00216 {
00217 cout << "Some critical setting in config.h is in error. Please fix it and recompile." << endl;
00218 abort();
00219 }
00220 return pass;
00221 }
00222
00223 bool TestOS_RNG()
00224 {
00225 bool pass = true;
00226
00227 member_ptr<RandomNumberGenerator> rng;
00228 #ifdef BLOCKING_RNG_AVAILABLE
00229 try {rng.reset(new BlockingRng);}
00230 catch (OS_RNG_Err &) {}
00231 #endif
00232
00233 if (rng.get())
00234 {
00235 cout << "\nTesting operating system provided blocking random number generator...\n\n";
00236
00237 ArraySink *sink;
00238 RandomNumberSource test(*rng, UINT_MAX, false, new Deflator(sink=new ArraySink(NULL,0)));
00239 unsigned long total=0, length=0;
00240 time_t t = time(NULL), t1 = 0;
00241
00242
00243 while (total < 16 && (t1 < 10 || total*8 > (unsigned long)t1))
00244 {
00245 test.Pump(1);
00246 total += 1;
00247 t1 = time(NULL) - t;
00248 }
00249
00250 if (total < 16)
00251 {
00252 cout << "FAILED:";
00253 pass = false;
00254 }
00255 else
00256 cout << "passed:";
00257 cout << " it took " << t1 << " seconds to generate " << total << " bytes" << endl;
00258
00259 if (t1 < 2)
00260 {
00261
00262
00263 t = time(NULL);
00264 while (time(NULL) - t < 2)
00265 {
00266 test.Pump(1);
00267 total += 1;
00268 }
00269
00270
00271
00272 t = time(NULL);
00273 while (time(NULL) - t < 2)
00274 {
00275 test.Pump(1);
00276 total += 1;
00277 length += 1;
00278 }
00279
00280
00281 if (false)
00282 {
00283 cout << "FAILED:";
00284 pass = false;
00285 }
00286 else
00287 cout << "passed:";
00288 cout << " it generated " << length << " bytes in " << time(NULL) - t << " seconds" << endl;
00289 }
00290
00291 test.AttachedTransformation()->MessageEnd();
00292
00293 if (sink->TotalPutLength() < total)
00294 {
00295 cout << "FAILED:";
00296 pass = false;
00297 }
00298 else
00299 cout << "passed:";
00300 cout << " " << total << " generated bytes compressed to " << sink->TotalPutLength() << " bytes by DEFLATE" << endl;
00301 }
00302 else
00303 cout << "\nNo operating system provided blocking random number generator, skipping test." << endl;
00304
00305 rng.reset(NULL);
00306 #ifdef NONBLOCKING_RNG_AVAILABLE
00307 try {rng.reset(new NonblockingRng);}
00308 catch (OS_RNG_Err &) {}
00309 #endif
00310
00311 if (rng.get())
00312 {
00313 cout << "\nTesting operating system provided nonblocking random number generator...\n\n";
00314
00315 ArraySink *sink;
00316 RandomNumberSource test(*rng, 100000, true, new Deflator(sink=new ArraySink(NULL, 0)));
00317
00318 if (sink->TotalPutLength() < 100000)
00319 {
00320 cout << "FAILED:";
00321 pass = false;
00322 }
00323 else
00324 cout << "passed:";
00325 cout << " 100000 generated bytes compressed to " << sink->TotalPutLength() << " bytes by DEFLATE" << endl;
00326 }
00327 else
00328 cout << "\nNo operating system provided nonblocking random number generator, skipping test." << endl;
00329
00330 return pass;
00331 }
00332
00333
00334 typedef auto_ptr<BlockTransformation> apbt;
00335
00336 class CipherFactory
00337 {
00338 public:
00339 virtual unsigned int BlockSize() const =0;
00340 virtual unsigned int KeyLength() const =0;
00341
00342 virtual apbt NewEncryption(const byte *key) const =0;
00343 virtual apbt NewDecryption(const byte *key) const =0;
00344 };
00345
00346 template <class E, class D> class FixedRoundsCipherFactory : public CipherFactory
00347 {
00348 public:
00349 FixedRoundsCipherFactory(unsigned int keylen=0) : m_keylen(keylen?keylen:E::DEFAULT_KEYLENGTH) {}
00350 unsigned int BlockSize() const {return E::BLOCKSIZE;}
00351 unsigned int KeyLength() const {return m_keylen;}
00352
00353 apbt NewEncryption(const byte *key) const
00354 {return apbt(new E(key, m_keylen));}
00355 apbt NewDecryption(const byte *key) const
00356 {return apbt(new D(key, m_keylen));}
00357
00358 unsigned int m_keylen;
00359 };
00360
00361 template <class E, class D> class VariableRoundsCipherFactory : public CipherFactory
00362 {
00363 public:
00364 VariableRoundsCipherFactory(unsigned int keylen=0, unsigned int rounds=0)
00365 : m_keylen(keylen ? keylen : E::DEFAULT_KEYLENGTH), m_rounds(rounds ? rounds : E::DEFAULT_ROUNDS) {}
00366 unsigned int BlockSize() const {return E::BLOCKSIZE;}
00367 unsigned int KeyLength() const {return m_keylen;}
00368
00369 apbt NewEncryption(const byte *key) const
00370 {return apbt(new E(key, m_keylen, m_rounds));}
00371 apbt NewDecryption(const byte *key) const
00372 {return apbt(new D(key, m_keylen, m_rounds));}
00373
00374 unsigned int m_keylen, m_rounds;
00375 };
00376
00377 bool BlockTransformationTest(const CipherFactory &cg, BufferedTransformation &valdata, unsigned int tuples = 0xffff)
00378 {
00379 HexEncoder output(new FileSink(cout));
00380 SecByteBlock plain(cg.BlockSize()), cipher(cg.BlockSize()), out(cg.BlockSize()), outplain(cg.BlockSize());
00381 SecByteBlock key(cg.KeyLength());
00382 bool pass=true, fail;
00383
00384 while (valdata.MaxRetrievable() && tuples--)
00385 {
00386 valdata.Get(key, cg.KeyLength());
00387 valdata.Get(plain, cg.BlockSize());
00388 valdata.Get(cipher, cg.BlockSize());
00389
00390 apbt transE = cg.NewEncryption(key);
00391 transE->ProcessBlock(plain, out);
00392 fail = memcmp(out, cipher, cg.BlockSize()) != 0;
00393
00394 apbt transD = cg.NewDecryption(key);
00395 transD->ProcessBlock(out, outplain);
00396 fail=fail || memcmp(outplain, plain, cg.BlockSize());
00397
00398 pass = pass && !fail;
00399
00400 cout << (fail ? "FAILED " : "passed ");
00401 output.Put(key, cg.KeyLength());
00402 cout << " ";
00403 output.Put(outplain, cg.BlockSize());
00404 cout << " ";
00405 output.Put(out, cg.BlockSize());
00406 cout << endl;
00407 }
00408 return pass;
00409 }
00410
00411 class FilterTester : public Unflushable<Sink>
00412 {
00413 public:
00414 FilterTester(const byte *validOutput, unsigned int outputLen)
00415 : validOutput(validOutput), outputLen(outputLen), counter(0), fail(false) {}
00416 void PutByte(byte inByte)
00417 {
00418 if (counter >= outputLen || validOutput[counter] != inByte)
00419 {
00420 fail = true;
00421 assert(false);
00422 }
00423 counter++;
00424 }
00425 unsigned int Put2(const byte *inString, unsigned int length, int messageEnd, bool blocking)
00426 {
00427 while (length--)
00428 FilterTester::PutByte(*inString++);
00429
00430 if (messageEnd)
00431 if (counter != outputLen)
00432 {
00433 fail = true;
00434 assert(false);
00435 }
00436
00437 return 0;
00438 }
00439 bool GetResult()
00440 {
00441 return !fail;
00442 }
00443
00444 const byte *validOutput;
00445 unsigned int outputLen, counter;
00446 bool fail;
00447 };
00448
00449 bool TestFilter(BufferedTransformation &bt, const byte *in, unsigned int inLen, const byte *out, unsigned int outLen)
00450 {
00451 FilterTester *ft;
00452 bt.Attach(ft = new FilterTester(out, outLen));
00453
00454 while (inLen)
00455 {
00456 unsigned int randomLen = GlobalRNG().GenerateWord32(0, inLen);
00457 bt.Put(in, randomLen);
00458 in += randomLen;
00459 inLen -= randomLen;
00460 }
00461 bt.MessageEnd();
00462 return ft->GetResult();
00463 }
00464
00465 bool ValidateDES()
00466 {
00467 cout << "\nDES validation suite running...\n\n";
00468
00469 FileSource valdata(PKGDATA("descert.dat"), true, new HexDecoder);
00470 bool pass = BlockTransformationTest(FixedRoundsCipherFactory<DESEncryption, DESDecryption>(), valdata);
00471
00472 cout << "\nTesting EDE2, EDE3, and XEX3 variants...\n\n";
00473
00474 FileSource valdata1(PKGDATA("3desval.dat"), true, new HexDecoder);
00475 pass = BlockTransformationTest(FixedRoundsCipherFactory<DES_EDE2_Encryption, DES_EDE2_Decryption>(), valdata1, 1) && pass;
00476 pass = BlockTransformationTest(FixedRoundsCipherFactory<DES_EDE3_Encryption, DES_EDE3_Decryption>(), valdata1, 1) && pass;
00477 pass = BlockTransformationTest(FixedRoundsCipherFactory<DES_XEX3_Encryption, DES_XEX3_Decryption>(), valdata1, 1) && pass;
00478
00479 return pass;
00480 }
00481
00482 bool TestModeIV(SymmetricCipher &e, SymmetricCipher &d)
00483 {
00484 SecByteBlock lastIV;
00485 StreamTransformationFilter filter(e, new StreamTransformationFilter(d));
00486 byte plaintext[20480];
00487
00488 for (unsigned int i=1; i<sizeof(plaintext); i*=2)
00489 {
00490 SecByteBlock iv(e.IVSize());
00491 e.GetNextIV(iv);
00492
00493 if (iv == lastIV)
00494 return false;
00495 else
00496 lastIV = iv;
00497
00498 e.Resynchronize(iv);
00499 d.Resynchronize(iv);
00500
00501 unsigned int length = STDMAX(GlobalRNG().GenerateWord32(0, i), (word32)e.MinLastBlockSize());
00502 GlobalRNG().GenerateBlock(plaintext, length);
00503
00504 if (!TestFilter(filter, plaintext, length, plaintext, length))
00505 return false;
00506 }
00507
00508 return true;
00509 }
00510
00511 bool ValidateCipherModes()
00512 {
00513 cout << "\nTesting DES modes...\n\n";
00514 const byte key[] = {0x01,0x23,0x45,0x67,0x89,0xab,0xcd,0xef};
00515 const byte iv[] = {0x12,0x34,0x56,0x78,0x90,0xab,0xcd,0xef};
00516 const byte plain[] = {
00517 0x4e,0x6f,0x77,0x20,0x69,0x73,0x20,0x74,
00518 0x68,0x65,0x20,0x74,0x69,0x6d,0x65,0x20,
00519 0x66,0x6f,0x72,0x20,0x61,0x6c,0x6c,0x20};
00520 DESEncryption desE(key);
00521 DESDecryption desD(key);
00522 bool pass=true, fail;
00523
00524 {
00525
00526 const byte encrypted[] = {
00527 0x3f, 0xa4, 0x0e, 0x8a, 0x98, 0x4d, 0x48, 0x15,
00528 0x6a, 0x27, 0x17, 0x87, 0xab, 0x88, 0x83, 0xf9,
00529 0x89, 0x3d, 0x51, 0xec, 0x4b, 0x56, 0x3b, 0x53};
00530
00531 ECB_Mode_ExternalCipher::Encryption modeE(desE);
00532 fail = !TestFilter(StreamTransformationFilter(modeE, NULL, StreamTransformationFilter::NO_PADDING).Ref(),
00533 plain, sizeof(plain), encrypted, sizeof(encrypted));
00534 pass = pass && !fail;
00535 cout << (fail ? "FAILED " : "passed ") << "ECB encryption" << endl;
00536
00537 ECB_Mode_ExternalCipher::Decryption modeD(desD);
00538 fail = !TestFilter(StreamTransformationFilter(modeD, NULL, StreamTransformationFilter::NO_PADDING).Ref(),
00539 encrypted, sizeof(encrypted), plain, sizeof(plain));
00540 pass = pass && !fail;
00541 cout << (fail ? "FAILED " : "passed ") << "ECB decryption" << endl;
00542 }
00543 {
00544
00545 const byte encrypted[] = {
00546 0xE5, 0xC7, 0xCD, 0xDE, 0x87, 0x2B, 0xF2, 0x7C,
00547 0x43, 0xE9, 0x34, 0x00, 0x8C, 0x38, 0x9C, 0x0F,
00548 0x68, 0x37, 0x88, 0x49, 0x9A, 0x7C, 0x05, 0xF6};
00549
00550 CBC_Mode_ExternalCipher::Encryption modeE(desE, iv);
00551 fail = !TestFilter(StreamTransformationFilter(modeE, NULL, StreamTransformationFilter::NO_PADDING).Ref(),
00552 plain, sizeof(plain), encrypted, sizeof(encrypted));
00553 pass = pass && !fail;
00554 cout << (fail ? "FAILED " : "passed ") << "CBC encryption with no padding" << endl;
00555
00556 CBC_Mode_ExternalCipher::Decryption modeD(desD, iv);
00557 fail = !TestFilter(StreamTransformationFilter(modeD, NULL, StreamTransformationFilter::NO_PADDING).Ref(),
00558 encrypted, sizeof(encrypted), plain, sizeof(plain));
00559 pass = pass && !fail;
00560 cout << (fail ? "FAILED " : "passed ") << "CBC decryption with no padding" << endl;
00561
00562 fail = !TestModeIV(modeE, modeD);
00563 pass = pass && !fail;
00564 cout << (fail ? "FAILED " : "passed ") << "CBC mode IV generation" << endl;
00565 }
00566 {
00567
00568
00569 const byte encrypted[] = {
00570 0xE5, 0xC7, 0xCD, 0xDE, 0x87, 0x2B, 0xF2, 0x7C,
00571 0x43, 0xE9, 0x34, 0x00, 0x8C, 0x38, 0x9C, 0x0F,
00572 0x68, 0x37, 0x88, 0x49, 0x9A, 0x7C, 0x05, 0xF6,
00573 0x62, 0xC1, 0x6A, 0x27, 0xE4, 0xFC, 0xF2, 0x77};
00574
00575 CBC_Mode_ExternalCipher::Encryption modeE(desE, iv);
00576 fail = !TestFilter(StreamTransformationFilter(modeE).Ref(),
00577 plain, sizeof(plain), encrypted, sizeof(encrypted));
00578 pass = pass && !fail;
00579 cout << (fail ? "FAILED " : "passed ") << "CBC encryption with PKCS #7 padding" << endl;
00580
00581 CBC_Mode_ExternalCipher::Decryption modeD(desD, iv);
00582 fail = !TestFilter(StreamTransformationFilter(modeD).Ref(),
00583 encrypted, sizeof(encrypted), plain, sizeof(plain));
00584 pass = pass && !fail;
00585 cout << (fail ? "FAILED " : "passed ") << "CBC decryption with PKCS #7 padding" << endl;
00586 }
00587 {
00588
00589
00590 const byte encrypted[] = {
00591 0xE5, 0xC7, 0xCD, 0xDE, 0x87, 0x2B, 0xF2, 0x7C,
00592 0x43, 0xE9, 0x34, 0x00, 0x8C, 0x38, 0x9C, 0x0F,
00593 0x68, 0x37, 0x88, 0x49, 0x9A, 0x7C, 0x05, 0xF6,
00594 0x57, 0x25, 0x0C, 0x94, 0x83, 0xD5, 0x01, 0x79};
00595
00596 CBC_Mode_ExternalCipher::Encryption modeE(desE, iv);
00597 fail = !TestFilter(StreamTransformationFilter(modeE, NULL, StreamTransformationFilter::ONE_AND_ZEROS_PADDING).Ref(),
00598 plain, sizeof(plain), encrypted, sizeof(encrypted));
00599 pass = pass && !fail;
00600 cout << (fail ? "FAILED " : "passed ") << "CBC encryption with one-and-zeros padding" << endl;
00601
00602 CBC_Mode_ExternalCipher::Decryption modeD(desD, iv);
00603 fail = !TestFilter(StreamTransformationFilter(modeD, NULL, StreamTransformationFilter::ONE_AND_ZEROS_PADDING).Ref(),
00604 encrypted, sizeof(encrypted), plain, sizeof(plain));
00605 pass = pass && !fail;
00606 cout << (fail ? "FAILED " : "passed ") << "CBC decryption with one-and-zeros padding" << endl;
00607 }
00608 {
00609 const byte plain[] = {'a', 0, 0, 0, 0, 0, 0, 0};
00610
00611 const byte encrypted[] = {
00612 0x9B, 0x47, 0x57, 0x59, 0xD6, 0x9C, 0xF6, 0xD0};
00613
00614 CBC_Mode_ExternalCipher::Encryption modeE(desE, iv);
00615 fail = !TestFilter(StreamTransformationFilter(modeE, NULL, StreamTransformationFilter::ZEROS_PADDING).Ref(),
00616 plain, 1, encrypted, sizeof(encrypted));
00617 pass = pass && !fail;
00618 cout << (fail ? "FAILED " : "passed ") << "CBC encryption with zeros padding" << endl;
00619
00620 CBC_Mode_ExternalCipher::Decryption modeD(desD, iv);
00621 fail = !TestFilter(StreamTransformationFilter(modeD, NULL, StreamTransformationFilter::ZEROS_PADDING).Ref(),
00622 encrypted, sizeof(encrypted), plain, sizeof(plain));
00623 pass = pass && !fail;
00624 cout << (fail ? "FAILED " : "passed ") << "CBC decryption with zeros padding" << endl;
00625 }
00626 {
00627
00628
00629 const byte encrypted[] = {
00630 0xE5, 0xC7, 0xCD, 0xDE, 0x87, 0x2B, 0xF2, 0x7C,
00631 0x68, 0x37, 0x88, 0x49, 0x9A, 0x7C, 0x05, 0xF6,
00632 0x43, 0xE9, 0x34, 0x00, 0x8C, 0x38, 0x9C, 0x0F};
00633
00634 CBC_CTS_Mode_ExternalCipher::Encryption modeE(desE, iv);
00635 fail = !TestFilter(StreamTransformationFilter(modeE).Ref(),
00636 plain, sizeof(plain), encrypted, sizeof(encrypted));
00637 pass = pass && !fail;
00638 cout << (fail ? "FAILED " : "passed ") << "CBC encryption with ciphertext stealing (CTS)" << endl;
00639
00640 CBC_CTS_Mode_ExternalCipher::Decryption modeD(desD, iv);
00641 fail = !TestFilter(StreamTransformationFilter(modeD).Ref(),
00642 encrypted, sizeof(encrypted), plain, sizeof(plain));
00643 pass = pass && !fail;
00644 cout << (fail ? "FAILED " : "passed ") << "CBC decryption with ciphertext stealing (CTS)" << endl;
00645
00646 fail = !TestModeIV(modeE, modeD);
00647 pass = pass && !fail;
00648 cout << (fail ? "FAILED " : "passed ") << "CBC CTS IV generation" << endl;
00649 }
00650 {
00651
00652 const byte decryptionIV[] = {0x4D, 0xD0, 0xAC, 0x8F, 0x47, 0xCF, 0x79, 0xCE};
00653 const byte encrypted[] = {0x12, 0x34, 0x56};
00654
00655 byte stolenIV[8];
00656
00657 CBC_CTS_Mode_ExternalCipher::Encryption modeE(desE, iv);
00658 modeE.SetStolenIV(stolenIV);
00659 fail = !TestFilter(StreamTransformationFilter(modeE).Ref(),
00660 plain, 3, encrypted, sizeof(encrypted));
00661 fail = memcmp(stolenIV, decryptionIV, 8) != 0 || fail;
00662 pass = pass && !fail;
00663 cout << (fail ? "FAILED " : "passed ") << "CBC encryption with ciphertext and IV stealing" << endl;
00664
00665 CBC_CTS_Mode_ExternalCipher::Decryption modeD(desD, stolenIV);
00666 fail = !TestFilter(StreamTransformationFilter(modeD).Ref(),
00667 encrypted, sizeof(encrypted), plain, 3);
00668 pass = pass && !fail;
00669 cout << (fail ? "FAILED " : "passed ") << "CBC decryption with ciphertext and IV stealing" << endl;
00670 }
00671 {
00672 const byte encrypted[] = {
00673 0xF3,0x09,0x62,0x49,0xC7,0xF4,0x6E,0x51,
00674 0xA6,0x9E,0x83,0x9B,0x1A,0x92,0xF7,0x84,
00675 0x03,0x46,0x71,0x33,0x89,0x8E,0xA6,0x22};
00676
00677 CFB_Mode_ExternalCipher::Encryption modeE(desE, iv);
00678 fail = !TestFilter(StreamTransformationFilter(modeE).Ref(),
00679 plain, sizeof(plain), encrypted, sizeof(encrypted));
00680 pass = pass && !fail;
00681 cout << (fail ? "FAILED " : "passed ") << "CFB encryption" << endl;
00682
00683 CFB_Mode_ExternalCipher::Decryption modeD(desE, iv);
00684 fail = !TestFilter(StreamTransformationFilter(modeD).Ref(),
00685 encrypted, sizeof(encrypted), plain, sizeof(plain));
00686 pass = pass && !fail;
00687 cout << (fail ? "FAILED " : "passed ") << "CFB decryption" << endl;
00688
00689 fail = !TestModeIV(modeE, modeD);
00690 pass = pass && !fail;
00691 cout << (fail ? "FAILED " : "passed ") << "CFB mode IV generation" << endl;
00692 }
00693 {
00694 const byte plain[] = {
00695 0x4e,0x6f,0x77,0x20,0x69,0x73,0x20,0x74,0x68,0x65};
00696 const byte encrypted[] = {
00697 0xf3,0x1f,0xda,0x07,0x01,0x14,0x62,0xee,0x18,0x7f};
00698
00699 CFB_Mode_ExternalCipher::Encryption modeE(desE, iv, 1);
00700 fail = !TestFilter(StreamTransformationFilter(modeE).Ref(),
00701 plain, sizeof(plain), encrypted, sizeof(encrypted));
00702 pass = pass && !fail;
00703 cout << (fail ? "FAILED " : "passed ") << "CFB (8-bit feedback) encryption" << endl;
00704
00705 CFB_Mode_ExternalCipher::Decryption modeD(desE, iv, 1);
00706 fail = !TestFilter(StreamTransformationFilter(modeD).Ref(),
00707 encrypted, sizeof(encrypted), plain, sizeof(plain));
00708 pass = pass && !fail;
00709 cout << (fail ? "FAILED " : "passed ") << "CFB (8-bit feedback) decryption" << endl;
00710
00711 fail = !TestModeIV(modeE, modeD);
00712 pass = pass && !fail;
00713 cout << (fail ? "FAILED " : "passed ") << "CFB (8-bit feedback) IV generation" << endl;
00714 }
00715 {
00716 const byte encrypted[] = {
00717 0xf3,0x09,0x62,0x49,0xc7,0xf4,0x6e,0x51,
00718 0x35,0xf2,0x4a,0x24,0x2e,0xeb,0x3d,0x3f,
00719 0x3d,0x6d,0x5b,0xe3,0x25,0x5a,0xf8,0xc3};
00720
00721 OFB_Mode_ExternalCipher::Encryption modeE(desE, iv);
00722 fail = !TestFilter(StreamTransformationFilter(modeE).Ref(),
00723 plain, sizeof(plain), encrypted, sizeof(encrypted));
00724 pass = pass && !fail;
00725 cout << (fail ? "FAILED " : "passed ") << "OFB encryption" << endl;
00726
00727 OFB_Mode_ExternalCipher::Decryption modeD(desE, iv);
00728 fail = !TestFilter(StreamTransformationFilter(modeD).Ref(),
00729 encrypted, sizeof(encrypted), plain, sizeof(plain));
00730 pass = pass && !fail;
00731 cout << (fail ? "FAILED " : "passed ") << "OFB decryption" << endl;
00732
00733 fail = !TestModeIV(modeE, modeD);
00734 pass = pass && !fail;
00735 cout << (fail ? "FAILED " : "passed ") << "OFB IV generation" << endl;
00736 }
00737 {
00738 const byte encrypted[] = {
00739 0xF3, 0x09, 0x62, 0x49, 0xC7, 0xF4, 0x6E, 0x51,
00740 0x16, 0x3A, 0x8C, 0xA0, 0xFF, 0xC9, 0x4C, 0x27,
00741 0xFA, 0x2F, 0x80, 0xF4, 0x80, 0xB8, 0x6F, 0x75};
00742
00743 CTR_Mode_ExternalCipher::Encryption modeE(desE, iv);
00744 fail = !TestFilter(StreamTransformationFilter(modeE).Ref(),
00745 plain, sizeof(plain), encrypted, sizeof(encrypted));
00746 pass = pass && !fail;
00747 cout << (fail ? "FAILED " : "passed ") << "Counter Mode encryption" << endl;
00748
00749 CTR_Mode_ExternalCipher::Decryption modeD(desE, iv);
00750 fail = !TestFilter(StreamTransformationFilter(modeD).Ref(),
00751 encrypted, sizeof(encrypted), plain, sizeof(plain));
00752 pass = pass && !fail;
00753 cout << (fail ? "FAILED " : "passed ") << "Counter Mode decryption" << endl;
00754
00755 fail = !TestModeIV(modeE, modeD);
00756 pass = pass && !fail;
00757 cout << (fail ? "FAILED " : "passed ") << "Counter Mode IV generation" << endl;
00758 }
00759 {
00760 const byte plain[] = {
00761 0x37, 0x36, 0x35, 0x34, 0x33, 0x32, 0x31, 0x20,
00762 0x4e, 0x6f, 0x77, 0x20, 0x69, 0x73, 0x20, 0x74,
00763 0x68, 0x65, 0x20, 0x74, 0x69, 0x6d, 0x65, 0x20,
00764 0x66, 0x6f, 0x72, 0x20};
00765 const byte mac1[] = {
00766 0xf1, 0xd3, 0x0f, 0x68, 0x49, 0x31, 0x2c, 0xa4};
00767 const byte mac2[] = {
00768 0x35, 0x80, 0xC5, 0xC4, 0x6B, 0x81, 0x24, 0xE2};
00769
00770 CBC_MAC<DES> cbcmac(key);
00771 HashFilter cbcmacFilter(cbcmac);
00772 fail = !TestFilter(cbcmacFilter, plain, sizeof(plain), mac1, sizeof(mac1));
00773 pass = pass && !fail;
00774 cout << (fail ? "FAILED " : "passed ") << "CBC MAC" << endl;
00775
00776 DMAC<DES> dmac(key);
00777 HashFilter dmacFilter(dmac);
00778 fail = !TestFilter(dmacFilter, plain, sizeof(plain), mac2, sizeof(mac2));
00779 pass = pass && !fail;
00780 cout << (fail ? "FAILED " : "passed ") << "DMAC" << endl;
00781 }
00782
00783 return pass;
00784 }
00785
00786 bool ValidateIDEA()
00787 {
00788 cout << "\nIDEA validation suite running...\n\n";
00789
00790 FileSource valdata(PKGDATA("ideaval.dat"), true, new HexDecoder);
00791 return BlockTransformationTest(FixedRoundsCipherFactory<IDEAEncryption, IDEADecryption>(), valdata);
00792 }
00793
00794 bool ValidateSAFER()
00795 {
00796 cout << "\nSAFER validation suite running...\n\n";
00797
00798 FileSource valdata(PKGDATA("saferval.dat"), true, new HexDecoder);
00799 bool pass = true;
00800 pass = BlockTransformationTest(VariableRoundsCipherFactory<SAFER_K_Encryption, SAFER_K_Decryption>(8,6), valdata, 4) && pass;
00801 pass = BlockTransformationTest(VariableRoundsCipherFactory<SAFER_K_Encryption, SAFER_K_Decryption>(16,12), valdata, 4) && pass;
00802 pass = BlockTransformationTest(VariableRoundsCipherFactory<SAFER_SK_Encryption, SAFER_SK_Decryption>(8,6), valdata, 4) && pass;
00803 pass = BlockTransformationTest(VariableRoundsCipherFactory<SAFER_SK_Encryption, SAFER_SK_Decryption>(16,10), valdata, 4) && pass;
00804 return pass;
00805 }
00806
00807 bool ValidateRC2()
00808 {
00809 cout << "\nRC2 validation suite running...\n\n";
00810
00811 FileSource valdata(PKGDATA("rc2val.dat"), true, new HexDecoder);
00812 HexEncoder output(new FileSink(cout));
00813 SecByteBlock plain(RC2Encryption::BLOCKSIZE), cipher(RC2Encryption::BLOCKSIZE), out(RC2Encryption::BLOCKSIZE), outplain(RC2Encryption::BLOCKSIZE);
00814 SecByteBlock key(128);
00815 bool pass=true, fail;
00816
00817 while (valdata.MaxRetrievable())
00818 {
00819 byte keyLen, effectiveLen;
00820
00821 valdata.Get(keyLen);
00822 valdata.Get(effectiveLen);
00823 valdata.Get(key, keyLen);
00824 valdata.Get(plain, RC2Encryption::BLOCKSIZE);
00825 valdata.Get(cipher, RC2Encryption::BLOCKSIZE);
00826
00827 apbt transE(new RC2Encryption(key, keyLen, effectiveLen));
00828 transE->ProcessBlock(plain, out);
00829 fail = memcmp(out, cipher, RC2Encryption::BLOCKSIZE) != 0;
00830
00831 apbt transD(new RC2Decryption(key, keyLen, effectiveLen));
00832 transD->ProcessBlock(out, outplain);
00833 fail=fail || memcmp(outplain, plain, RC2Encryption::BLOCKSIZE);
00834
00835 pass = pass && !fail;
00836
00837 cout << (fail ? "FAILED " : "passed ");
00838 output.Put(key, keyLen);
00839 cout << " ";
00840 output.Put(outplain, RC2Encryption::BLOCKSIZE);
00841 cout << " ";
00842 output.Put(out, RC2Encryption::BLOCKSIZE);
00843 cout << endl;
00844 }
00845 return pass;
00846 }
00847
00848 bool ValidateARC4()
00849 {
00850 unsigned char Key0[] = {0x01,0x23,0x45,0x67,0x89,0xab,0xcd,0xef };
00851 unsigned char Input0[]={0x01,0x23,0x45,0x67,0x89,0xab,0xcd,0xef};
00852 unsigned char Output0[] = {0x75,0xb7,0x87,0x80,0x99,0xe0,0xc5,0x96};
00853
00854 unsigned char Key1[]={0x01,0x23,0x45,0x67,0x89,0xab,0xcd,0xef};
00855 unsigned char Input1[]={0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00};
00856 unsigned char Output1[]={0x74,0x94,0xc2,0xe7,0x10,0x4b,0x08,0x79};
00857
00858 unsigned char Key2[]={0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00};
00859 unsigned char Input2[]={0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00};
00860 unsigned char Output2[]={0xde,0x18,0x89,0x41,0xa3,0x37,0x5d,0x3a};
00861
00862 unsigned char Key3[]={0xef,0x01,0x23,0x45};
00863 unsigned char Input3[]={0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00};
00864 unsigned char Output3[]={0xd6,0xa1,0x41,0xa7,0xec,0x3c,0x38,0xdf,0xbd,0x61};
00865
00866 unsigned char Key4[]={ 0x01,0x23,0x45,0x67,0x89,0xab, 0xcd,0xef };
00867 unsigned char Input4[] =
00868 {0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00869 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00870 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00871 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00872 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00873 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00874 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00875 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00876 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00877 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00878 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00879 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00880 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00881 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00882 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00883 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00884 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00885 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00886 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00887 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00888 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00889 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00890 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00891 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00892 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00893 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00894 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00895 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00896 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00897 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00898 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00899 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00900 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00901 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00902 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00903 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00904 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00905 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00906 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00907 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00908 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00909 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00910 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00911 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00912 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00913 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00914 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00915 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00916 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00917 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00918 0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x01,
00919 0x01};
00920 unsigned char Output4[]= {
00921 0x75,0x95,0xc3,0xe6,0x11,0x4a,0x09,0x78,0x0c,0x4a,0xd4,
00922 0x52,0x33,0x8e,0x1f,0xfd,0x9a,0x1b,0xe9,0x49,0x8f,
00923 0x81,0x3d,0x76,0x53,0x34,0x49,0xb6,0x77,0x8d,0xca,
00924 0xd8,0xc7,0x8a,0x8d,0x2b,0xa9,0xac,0x66,0x08,0x5d,
00925 0x0e,0x53,0xd5,0x9c,0x26,0xc2,0xd1,0xc4,0x90,0xc1,
00926 0xeb,0xbe,0x0c,0xe6,0x6d,0x1b,0x6b,0x1b,0x13,0xb6,
00927 0xb9,0x19,0xb8,0x47,0xc2,0x5a,0x91,0x44,0x7a,0x95,
00928 0xe7,0x5e,0x4e,0xf1,0x67,0x79,0xcd,0xe8,0xbf,0x0a,
00929 0x95,0x85,0x0e,0x32,0xaf,0x96,0x89,0x44,0x4f,0xd3,
00930 0x77,0x10,0x8f,0x98,0xfd,0xcb,0xd4,0xe7,0x26,0x56,
00931 0x75,0x00,0x99,0x0b,0xcc,0x7e,0x0c,0xa3,0xc4,0xaa,
00932 0xa3,0x04,0xa3,0x87,0xd2,0x0f,0x3b,0x8f,0xbb,0xcd,
00933 0x42,0xa1,0xbd,0x31,0x1d,0x7a,0x43,0x03,0xdd,0xa5,
00934 0xab,0x07,0x88,0x96,0xae,0x80,0xc1,0x8b,0x0a,0xf6,
00935 0x6d,0xff,0x31,0x96,0x16,0xeb,0x78,0x4e,0x49,0x5a,
00936 0xd2,0xce,0x90,0xd7,0xf7,0x72,0xa8,0x17,0x47,0xb6,
00937 0x5f,0x62,0x09,0x3b,0x1e,0x0d,0xb9,0xe5,0xba,0x53,
00938 0x2f,0xaf,0xec,0x47,0x50,0x83,0x23,0xe6,0x71,0x32,
00939 0x7d,0xf9,0x44,0x44,0x32,0xcb,0x73,0x67,0xce,0xc8,
00940 0x2f,0x5d,0x44,0xc0,0xd0,0x0b,0x67,0xd6,0x50,0xa0,
00941 0x75,0xcd,0x4b,0x70,0xde,0xdd,0x77,0xeb,0x9b,0x10,
00942 0x23,0x1b,0x6b,0x5b,0x74,0x13,0x47,0x39,0x6d,0x62,
00943 0x89,0x74,0x21,0xd4,0x3d,0xf9,0xb4,0x2e,0x44,0x6e,
00944 0x35,0x8e,0x9c,0x11,0xa9,0xb2,0x18,0x4e,0xcb,0xef,
00945 0x0c,0xd8,0xe7,0xa8,0x77,0xef,0x96,0x8f,0x13,0x90,
00946 0xec,0x9b,0x3d,0x35,0xa5,0x58,0x5c,0xb0,0x09,0x29,
00947 0x0e,0x2f,0xcd,0xe7,0xb5,0xec,0x66,0xd9,0x08,0x4b,
00948 0xe4,0x40,0x55,0xa6,0x19,0xd9,0xdd,0x7f,0xc3,0x16,
00949 0x6f,0x94,0x87,0xf7,0xcb,0x27,0x29,0x12,0x42,0x64,
00950 0x45,0x99,0x85,0x14,0xc1,0x5d,0x53,0xa1,0x8c,0x86,
00951 0x4c,0xe3,0xa2,0xb7,0x55,0x57,0x93,0x98,0x81,0x26,
00952 0x52,0x0e,0xac,0xf2,0xe3,0x06,0x6e,0x23,0x0c,0x91,
00953 0xbe,0xe4,0xdd,0x53,0x04,0xf5,0xfd,0x04,0x05,0xb3,
00954 0x5b,0xd9,0x9c,0x73,0x13,0x5d,0x3d,0x9b,0xc3,0x35,
00955 0xee,0x04,0x9e,0xf6,0x9b,0x38,0x67,0xbf,0x2d,0x7b,
00956 0xd1,0xea,0xa5,0x95,0xd8,0xbf,0xc0,0x06,0x6f,0xf8,
00957 0xd3,0x15,0x09,0xeb,0x0c,0x6c,0xaa,0x00,0x6c,0x80,
00958 0x7a,0x62,0x3e,0xf8,0x4c,0x3d,0x33,0xc1,0x95,0xd2,
00959 0x3e,0xe3,0x20,0xc4,0x0d,0xe0,0x55,0x81,0x57,0xc8,
00960 0x22,0xd4,0xb8,0xc5,0x69,0xd8,0x49,0xae,0xd5,0x9d,
00961 0x4e,0x0f,0xd7,0xf3,0x79,0x58,0x6b,0x4b,0x7f,0xf6,
00962 0x84,0xed,0x6a,0x18,0x9f,0x74,0x86,0xd4,0x9b,0x9c,
00963 0x4b,0xad,0x9b,0xa2,0x4b,0x96,0xab,0xf9,0x24,0x37,
00964 0x2c,0x8a,0x8f,0xff,0xb1,0x0d,0x55,0x35,0x49,0x00,
00965 0xa7,0x7a,0x3d,0xb5,0xf2,0x05,0xe1,0xb9,0x9f,0xcd,
00966 0x86,0x60,0x86,0x3a,0x15,0x9a,0xd4,0xab,0xe4,0x0f,
00967 0xa4,0x89,0x34,0x16,0x3d,0xdd,0xe5,0x42,0xa6,0x58,
00968 0x55,0x40,0xfd,0x68,0x3c,0xbf,0xd8,0xc0,0x0f,0x12,
00969 0x12,0x9a,0x28,0x4d,0xea,0xcc,0x4c,0xde,0xfe,0x58,
00970 0xbe,0x71,0x37,0x54,0x1c,0x04,0x71,0x26,0xc8,0xd4,
00971 0x9e,0x27,0x55,0xab,0x18,0x1a,0xb7,0xe9,0x40,0xb0,
00972 0xc0};
00973
00974
00975 member_ptr<ARC4> arc4;
00976 bool pass=true, fail;
00977 int i;
00978
00979 cout << "\nARC4 validation suite running...\n\n";
00980
00981 arc4.reset(new ARC4(Key0, sizeof(Key0)));
00982 arc4->ProcessString(Input0, sizeof(Input0));
00983 fail = memcmp(Input0, Output0, sizeof(Input0)) != 0;
00984 cout << (fail ? "FAILED" : "passed") << " Test 0" << endl;
00985 pass = pass && !fail;
00986
00987 arc4.reset(new ARC4(Key1, sizeof(Key1)));
00988 arc4->ProcessString(Key1, Input1, sizeof(Key1));
00989 fail = memcmp(Output1, Key1, sizeof(Key1)) != 0;
00990 cout << (fail ? "FAILED" : "passed") << " Test 1" << endl;
00991 pass = pass && !fail;
00992
00993 arc4.reset(new ARC4(Key2, sizeof(Key2)));
00994 for (i=0, fail=false; i<sizeof(Input2); i++)
00995 if (arc4->ProcessByte(Input2[i]) != Output2[i])
00996 fail = true;
00997 cout << (fail ? "FAILED" : "passed") << " Test 2" << endl;
00998 pass = pass && !fail;
00999
01000 arc4.reset(new ARC4(Key3, sizeof(Key3)));
01001 for (i=0, fail=false; i<sizeof(Input3); i++)
01002 if (arc4->ProcessByte(Input3[i]) != Output3[i])
01003 fail = true;
01004 cout << (fail ? "FAILED" : "passed") << " Test 3" << endl;
01005 pass = pass && !fail;
01006
01007 arc4.reset(new ARC4(Key4, sizeof(Key4)));
01008 for (i=0, fail=false; i<sizeof(Input4); i++)
01009 if (arc4->ProcessByte(Input4[i]) != Output4[i])
01010 fail = true;
01011 cout << (fail ? "FAILED" : "passed") << " Test 4" << endl;
01012 pass = pass && !fail;
01013
01014 return pass;
01015 }
01016
01017 bool ValidateRC5()
01018 {
01019 cout << "\nRC5 validation suite running...\n\n";
01020
01021 FileSource valdata(PKGDATA("rc5val.dat"), true, new HexDecoder);
01022 return BlockTransformationTest(VariableRoundsCipherFactory<RC5Encryption, RC5Decryption>(16, 12), valdata);
01023 }
01024
01025 bool ValidateRC6()
01026 {
01027 cout << "\nRC6 validation suite running...\n\n";
01028
01029 FileSource valdata(PKGDATA("rc6val.dat"), true, new HexDecoder);
01030 bool pass = true;
01031 pass = BlockTransformationTest(FixedRoundsCipherFactory<RC6Encryption, RC6Decryption>(16), valdata, 2) && pass;
01032 pass = BlockTransformationTest(FixedRoundsCipherFactory<RC6Encryption, RC6Decryption>(24), valdata, 2) && pass;
01033 pass = BlockTransformationTest(FixedRoundsCipherFactory<RC6Encryption, RC6Decryption>(32), valdata, 2) && pass;
01034 return pass;
01035 }
01036
01037 bool ValidateMARS()
01038 {
01039 cout << "\nMARS validation suite running...\n\n";
01040
01041 FileSource valdata(PKGDATA("marsval.dat"), true, new HexDecoder);
01042 bool pass = true;
01043 pass = BlockTransformationTest(FixedRoundsCipherFactory<MARSEncryption, MARSDecryption>(16), valdata, 4) && pass;
01044 pass = BlockTransformationTest(FixedRoundsCipherFactory<MARSEncryption, MARSDecryption>(24), valdata, 3) && pass;
01045 pass = BlockTransformationTest(FixedRoundsCipherFactory<MARSEncryption, MARSDecryption>(32), valdata, 2) && pass;
01046 return pass;
01047 }
01048
01049 bool ValidateRijndael()
01050 {
01051 cout << "\nRijndael validation suite running...\n\n";
01052
01053 FileSource valdata(PKGDATA("rijndael.dat"), true, new HexDecoder);
01054 bool pass = true;
01055 pass = BlockTransformationTest(FixedRoundsCipherFactory<RijndaelEncryption, RijndaelDecryption>(16), valdata, 4) && pass;
01056 pass = BlockTransformationTest(FixedRoundsCipherFactory<RijndaelEncryption, RijndaelDecryption>(24), valdata, 3) && pass;
01057 pass = BlockTransformationTest(FixedRoundsCipherFactory<RijndaelEncryption, RijndaelDecryption>(32), valdata, 2) && pass;
01058 return pass;
01059 }
01060
01061 bool ValidateTwofish()
01062 {
01063 cout << "\nTwofish validation suite running...\n\n";
01064
01065 FileSource valdata(PKGDATA("twofishv.dat"), true, new HexDecoder);
01066 bool pass = true;
01067 pass = BlockTransformationTest(FixedRoundsCipherFactory<TwofishEncryption, TwofishDecryption>(16), valdata, 4) && pass;
01068 pass = BlockTransformationTest(FixedRoundsCipherFactory<TwofishEncryption, TwofishDecryption>(24), valdata, 3) && pass;
01069 pass = BlockTransformationTest(FixedRoundsCipherFactory<TwofishEncryption, TwofishDecryption>(32), valdata, 2) && pass;
01070 return pass;
01071 }
01072
01073 bool ValidateSerpent()
01074 {
01075 cout << "\nSerpent validation suite running...\n\n";
01076
01077 FileSource valdata(PKGDATA("serpentv.dat"), true, new HexDecoder);
01078 bool pass = true;
01079 pass = BlockTransformationTest(FixedRoundsCipherFactory<SerpentEncryption, SerpentDecryption>(16), valdata, 4) && pass;
01080 pass = BlockTransformationTest(FixedRoundsCipherFactory<SerpentEncryption, SerpentDecryption>(24), valdata, 3) && pass;
01081 pass = BlockTransformationTest(FixedRoundsCipherFactory<SerpentEncryption, SerpentDecryption>(32), valdata, 2) && pass;
01082 return pass;
01083 }
01084
01085 bool ValidateBlowfish()
01086 {
01087 cout << "\nBlowfish validation suite running...\n\n";
01088
01089 HexEncoder output(new FileSink(cout));
01090 char *key[]={"abcdefghijklmnopqrstuvwxyz", "Who is John Galt?"};
01091 byte *plain[]={(byte *)"BLOWFISH", (byte *)"\xfe\xdc\xba\x98\x76\x54\x32\x10"};
01092 byte *cipher[]={(byte *)"\x32\x4e\xd0\xfe\xf4\x13\xa2\x03", (byte *)"\xcc\x91\x73\x2b\x80\x22\xf6\x84"};
01093 byte out[8], outplain[8];
01094 bool pass=true, fail;
01095
01096 for (int i=0; i<2; i++)
01097 {
01098 ECB_Mode<Blowfish>::Encryption enc((byte *)key[i], strlen(key[i]));
01099 enc.ProcessData(out, plain[i], 8);
01100 fail = memcmp(out, cipher[i], 8) != 0;
01101
01102 ECB_Mode<Blowfish>::Decryption dec((byte *)key[i], strlen(key[i]));
01103 dec.ProcessData(outplain, cipher[i], 8);
01104 fail = fail || memcmp(outplain, plain[i], 8);
01105 pass = pass && !fail;
01106
01107 cout << (fail ? "FAILED " : "passed ");
01108 cout << '\"' << key[i] << '\"';
01109 for (int j=0; j<(signed int)(30-strlen(key[i])); j++)
01110 cout << ' ';
01111 output.Put(outplain, 8);
01112 cout << " ";
01113 output.Put(out, 8);
01114 cout << endl;
01115 }
01116 return pass;
01117 }
01118
01119 bool ValidateDiamond2()
01120 {
01121 cout << "\nDiamond2 validation suite running...\n\n";
01122
01123 FileSource valdata(PKGDATA("diamond.dat"), true, new HexDecoder);
01124 HexEncoder output(new FileSink(cout));
01125 byte key[32], plain[16], cipher[16], out[16], outplain[16];
01126 byte blocksize, rounds, keysize;
01127 bool pass=true, fail;
01128 member_ptr<BlockTransformation> diamond;
01129
01130 while (valdata.MaxRetrievable() >= 1)
01131 {
01132 valdata.Get(blocksize);
01133 valdata.Get(rounds);
01134 valdata.Get(keysize);
01135 valdata.Get(key, keysize);
01136 valdata.Get(plain, blocksize);
01137 valdata.Get(cipher, blocksize);
01138
01139 if (blocksize==16)
01140 diamond.reset(new Diamond2Encryption(key, keysize, rounds));
01141 else
01142 diamond.reset(new Diamond2LiteEncryption(key, keysize, rounds));
01143
01144 diamond->ProcessBlock(plain, out);
01145 fail=memcmp(out, cipher, blocksize) != 0;
01146
01147 if (blocksize==16)
01148 diamond.reset(new Diamond2Decryption(key, keysize, rounds));
01149 else
01150 diamond.reset(new Diamond2LiteDecryption(key, keysize, rounds));
01151
01152 diamond->ProcessBlock(out, outplain);
01153 fail=fail || memcmp(outplain, plain, blocksize);
01154
01155 pass = pass && !fail;
01156
01157 cout << (fail ? "FAILED " : "passed ");
01158 output.Put(key, keysize);
01159 cout << "\n ";
01160 output.Put(outplain, blocksize);
01161 cout << " ";
01162 output.Put(out, blocksize);
01163 cout << endl;
01164 }
01165 return pass;
01166 }
01167
01168 bool ValidateThreeWay()
01169 {
01170 cout << "\n3-WAY validation suite running...\n\n";
01171
01172 FileSource valdata(PKGDATA("3wayval.dat"), true, new HexDecoder);
01173 return BlockTransformationTest(FixedRoundsCipherFactory<ThreeWayEncryption, ThreeWayDecryption>(), valdata);
01174 }
01175
01176 bool ValidateGOST()
01177 {
01178 cout << "\nGOST validation suite running...\n\n";
01179
01180 FileSource valdata(PKGDATA("gostval.dat"), true, new HexDecoder);
01181 return BlockTransformationTest(FixedRoundsCipherFactory<GOSTEncryption, GOSTDecryption>(), valdata);
01182 }
01183
01184 bool ValidateSHARK()
01185 {
01186 cout << "\nSHARK validation suite running...\n\n";
01187
01188 #ifdef WORD64_AVAILABLE
01189 FileSource valdata(PKGDATA("sharkval.dat"), true, new HexDecoder);
01190 return BlockTransformationTest(FixedRoundsCipherFactory<SHARKEncryption, SHARKDecryption>(), valdata);
01191 #else
01192 cout << "word64 not available, skipping SHARK validation." << endl;
01193 return true;
01194 #endif
01195 }
01196
01197 bool ValidateCAST()
01198 {
01199 bool pass = true;
01200
01201 cout << "\nCAST-128 validation suite running...\n\n";
01202
01203 FileSource val128(PKGDATA("cast128v.dat"), true, new HexDecoder);
01204 pass = BlockTransformationTest(FixedRoundsCipherFactory<CAST128Encryption, CAST128Decryption>(16), val128, 1) && pass;
01205 pass = BlockTransformationTest(FixedRoundsCipherFactory<CAST128Encryption, CAST128Decryption>(10), val128, 1) && pass;
01206 pass = BlockTransformationTest(FixedRoundsCipherFactory<CAST128Encryption, CAST128Decryption>(5), val128, 1) && pass;
01207
01208 cout << "\nCAST-256 validation suite running...\n\n";
01209
01210 FileSource val256(PKGDATA("cast256v.dat"), true, new HexDecoder);
01211 pass = BlockTransformationTest(FixedRoundsCipherFactory<CAST256Encryption, CAST256Decryption>(16), val256, 1) && pass;
01212 pass = BlockTransformationTest(FixedRoundsCipherFactory<CAST256Encryption, CAST256Decryption>(24), val256, 1) && pass;
01213 pass = BlockTransformationTest(FixedRoundsCipherFactory<CAST256Encryption, CAST256Decryption>(32), val256, 1) && pass;
01214
01215 return pass;
01216 }
01217
01218 bool ValidateSquare()
01219 {
01220 cout << "\nSquare validation suite running...\n\n";
01221
01222 FileSource valdata(PKGDATA("squareva.dat"), true, new HexDecoder);
01223 return BlockTransformationTest(FixedRoundsCipherFactory<SquareEncryption, SquareDecryption>(), valdata);
01224 }
01225
01226 bool ValidateSKIPJACK()
01227 {
01228 cout << "\nSKIPJACK validation suite running...\n\n";
01229
01230 FileSource valdata(PKGDATA("skipjack.dat"), true, new HexDecoder);
01231 return BlockTransformationTest(FixedRoundsCipherFactory<SKIPJACKEncryption, SKIPJACKDecryption>(), valdata);
01232 }
01233
01234 bool ValidateSEAL()
01235 {
01236 byte input[] = {0x37,0xa0,0x05,0x95,0x9b,0x84,0xc4,0x9c,0xa4,0xbe,0x1e,0x05,0x06,0x73,0x53,0x0f,0x5f,0xb0,0x97,0xfd,0xf6,0xa1,0x3f,0xbd,0x6c,0x2c,0xde,0xcd,0x81,0xfd,0xee,0x7c};
01237 byte output[32];
01238 byte key[] = {0x67, 0x45, 0x23, 0x01, 0xef, 0xcd, 0xab, 0x89, 0x98, 0xba, 0xdc, 0xfe, 0x10, 0x32, 0x54, 0x76, 0xc3, 0xd2, 0xe1, 0xf0};
01239 byte iv[] = {0x01, 0x35, 0x77, 0xaf};
01240
01241 cout << "\nSEAL validation suite running...\n\n";
01242
01243 SEAL<>::Encryption seal(key);
01244 seal.Resynchronize(iv);
01245 unsigned int size = sizeof(input);
01246 bool pass = true;
01247
01248 memset(output, 1, size);
01249 seal.ProcessString(output, input, size);
01250 for (unsigned int i=0; i<size; i++)
01251 if (output[i] != 0)
01252 pass = false;
01253
01254 seal.Seek(1);
01255 output[1] = seal.ProcessByte(output[1]);
01256 seal.ProcessString(output+2, size-2);
01257 pass = pass && memcmp(output+1, input+1, size-1) == 0;
01258
01259 cout << (pass ? "passed" : "FAILED") << endl;
01260 return pass;
01261 }
01262
01263 bool ValidateBaseCode()
01264 {
01265 bool pass = true, fail;
01266 byte data[255];
01267 for (unsigned int i=0; i<255; i++)
01268 data[i] = i;
01269 const char *hexEncoded =
01270 "000102030405060708090A0B0C0D0E0F101112131415161718191A1B1C1D1E1F2021222324252627"
01271 "28292A2B2C2D2E2F303132333435363738393A3B3C3D3E3F404142434445464748494A4B4C4D4E4F"
01272 "505152535455565758595A5B5C5D5E5F606162636465666768696A6B6C6D6E6F7071727374757677"
01273 "78797A7B7C7D7E7F808182838485868788898A8B8C8D8E8F909192939495969798999A9B9C9D9E9F"
01274 "A0A1A2A3A4A5A6A7A8A9AAABACADAEAFB0B1B2B3B4B5B6B7B8B9BABBBCBDBEBFC0C1C2C3C4C5C6C7"
01275 "C8C9CACBCCCDCECFD0D1D2D3D4D5D6D7D8D9DADBDCDDDEDFE0E1E2E3E4E5E6E7E8E9EAEBECEDEEEF"
01276 "F0F1F2F3F4F5F6F7F8F9FAFBFCFDFE";
01277 const char *base64AndHexEncoded =
01278 "41414543417751464267634943516F4C4441304F4478415245684D554652595847426B6147787764"
01279 "486838674953496A4A43556D4A7967704B6973734C5334764D4445794D7A51310A4E6A63344F546F"
01280 "375044302B50304242516B4E4552555A4853456C4B5330784E546B395155564A5456465657563168"
01281 "5A576C746358563566594746695932526C5A6D646F615770720A6247317562334278636E4E306458"
01282 "5A3365486C3665337839666E2B4167594B44684957476834694A696F754D6A5936506B4A47536B35"
01283 "53566C7065596D5A71626E4A32656E3643680A6F714F6B7061616E714B6D717136797472712B7773"
01284 "624B7A744C573274376935757275387662362F774D484377385446787366497963724C7A4D334F7A"
01285 "39445230745055316462580A324E6E6132397A6433742F6734654C6A354F586D352B6A7036757673"
01286 "3765377638504879382F5431397666342B6672372F50332B0A";
01287
01288 cout << "\nBase64 and hex coding validation suite running...\n\n";
01289
01290 fail = !TestFilter(HexEncoder().Ref(), data, 255, (const byte *)hexEncoded, strlen(hexEncoded));
01291 cout << (fail ? "FAILED " : "passed ");
01292 cout << "Hex Encoding\n";
01293 pass = pass && !fail;
01294
01295 fail = !TestFilter(HexDecoder().Ref(), (const byte *)hexEncoded, strlen(hexEncoded), data, 255);
01296 cout << (fail ? "FAILED " : "passed ");
01297 cout << "Hex Decoding\n";
01298 pass = pass && !fail;
01299
01300 fail = !TestFilter(Base64Encoder(new HexEncoder).Ref(), data, 255, (const byte *)base64AndHexEncoded, strlen(base64AndHexEncoded));
01301 cout << (fail ? "FAILED " : "passed ");
01302 cout << "Base64 Encoding\n";
01303 pass = pass && !fail;
01304
01305 fail = !TestFilter(HexDecoder(new Base64Decoder).Ref(), (const byte *)base64AndHexEncoded, strlen(base64AndHexEncoded), data, 255);
01306 cout << (fail ? "FAILED " : "passed ");
01307 cout << "Base64 Decoding\n";
01308 pass = pass && !fail;
01309
01310 return pass;
01311 }