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