00001
00002
00003
00004
00005
00006 #if 0
00007 #ifndef CRYPTOPP_IMPORTS
00008 #define CRYPTOPP_DEFAULT_NO_DLL
00009 #endif
00010 #include "dll.h"
00011 #include "oids.h"
00012
00013 USING_NAMESPACE(CryptoPP)
00014 USING_NAMESPACE(std)
00015
00016 class LineBreakParser : public AutoSignaling<Bufferless<Filter> >
00017 {
00018 public:
00019 LineBreakParser(BufferedTransformation *attachment=NULL, byte lineEnd='\n')
00020 : m_lineEnd(lineEnd) {Detach(attachment);}
00021
00022 unsigned int Put2(const byte *begin, unsigned int length, int messageEnd, bool blocking)
00023 {
00024 if (!blocking)
00025 throw BlockingInputOnly("LineBreakParser");
00026
00027 unsigned int i, last = 0;
00028 for (i=0; i<length; i++)
00029 {
00030 if (begin[i] == m_lineEnd)
00031 {
00032 AttachedTransformation()->Put2(begin+last, i-last, GetAutoSignalPropagation(), blocking);
00033 last = i+1;
00034 }
00035 }
00036 if (last != i)
00037 AttachedTransformation()->Put2(begin+last, i-last, 0, blocking);
00038
00039 if (messageEnd && GetAutoSignalPropagation())
00040 {
00041 AttachedTransformation()->MessageEnd(GetAutoSignalPropagation()-1, blocking);
00042 AttachedTransformation()->MessageSeriesEnd(GetAutoSignalPropagation()-1, blocking);
00043 }
00044
00045 return 0;
00046 }
00047
00048 private:
00049 byte m_lineEnd;
00050 };
00051
00052 class TestDataParser : public Unflushable<FilterWithInputQueue>
00053 {
00054 public:
00055 enum DataType {OTHER, COUNT, KEY_T, IV, INPUT, OUTPUT};
00056
00057 TestDataParser(std::string algorithm, std::string test, std::string mode, unsigned int feedbackSize, bool encrypt, BufferedTransformation *attachment)
00058 : m_algorithm(algorithm), m_test(test), m_mode(mode), m_feedbackSize(feedbackSize)
00059 , m_firstLine(true), m_blankLineTransition(0)
00060 {
00061 Detach(attachment);
00062
00063 m_nameToType["COUNT"] = COUNT;
00064 m_nameToType["KEY"] = KEY_T;
00065 m_nameToType["KEYs"] = KEY_T;
00066 m_nameToType["key"] = KEY_T;
00067 m_nameToType["Key"] = KEY_T;
00068 m_nameToType["IV"] = IV;
00069 m_nameToType["IV1"] = IV;
00070 m_nameToType["CV"] = IV;
00071 m_nameToType["CV1"] = IV;
00072 m_nameToType["IB"] = IV;
00073 m_nameToType["TEXT"] = INPUT;
00074 m_nameToType["RESULT"] = OUTPUT;
00075 m_nameToType["Msg"] = INPUT;
00076 m_nameToType["Seed"] = INPUT;
00077 m_nameToType["V"] = INPUT;
00078 m_nameToType["DT"] = IV;
00079 SetEncrypt(encrypt);
00080
00081 if (m_algorithm == "DSS")
00082 {
00083 if (m_test == "prime")
00084 m_trigger = "Prime";
00085 else if (m_test == "pqg")
00086 m_trigger = "N";
00087 else if (m_test == "xy")
00088 m_trigger = "G";
00089 else if (m_test == "gensig")
00090 m_trigger = "Msg";
00091 else if (m_test == "versig")
00092 m_trigger = "Sig";
00093 else if (m_test == "verpqg")
00094 m_trigger = "c";
00095 }
00096 else if (m_algorithm == "HMAC")
00097 m_trigger = "Msg";
00098 else if (m_algorithm == "SHA2")
00099 m_trigger = (m_test == "MONTE") ? "Seed" : "Msg";
00100 else if (m_algorithm == "ECDSA")
00101 {
00102 if (m_test == "PKV")
00103 m_trigger = "Qy";
00104 else if (m_test == "KeyPair")
00105 m_trigger = "N";
00106 else if (m_test == "SigGen")
00107 m_trigger = "Msg";
00108 else if (m_test == "SigVer")
00109 m_trigger = "S";
00110 }
00111 else if (m_algorithm == "RNG")
00112 m_trigger = "V";
00113 else if (m_algorithm == "RSA")
00114 m_trigger = (m_test == "Ver") ? "S" : "Msg";
00115 }
00116
00117 void SetEncrypt(bool encrypt)
00118 {
00119 m_encrypt = encrypt;
00120 if (encrypt)
00121 {
00122 m_nameToType["PLAINTEXT"] = INPUT;
00123 m_nameToType["CIPHERTEXT"] = OUTPUT;
00124 m_nameToType["PT"] = INPUT;
00125 m_nameToType["CT"] = OUTPUT;
00126 }
00127 else
00128 {
00129 m_nameToType["PLAINTEXT"] = OUTPUT;
00130 m_nameToType["CIPHERTEXT"] = INPUT;
00131 m_nameToType["PT"] = OUTPUT;
00132 m_nameToType["CT"] = INPUT;
00133 }
00134
00135 if (m_algorithm == "AES" || m_algorithm == "TDES")
00136 {
00137 if (encrypt)
00138 {
00139 m_trigger = "PLAINTEXT";
00140 m_typeToName[OUTPUT] = "CIPHERTEXT";
00141 }
00142 else
00143 {
00144 m_trigger = "CIPHERTEXT";
00145 m_typeToName[OUTPUT] = "PLAINTEXT";
00146 }
00147 m_count = 0;
00148 }
00149 }
00150
00151 protected:
00152 void OutputData(std::string &output, const std::string &key, const std::string &data)
00153 {
00154 output += key;
00155 output += "= ";
00156 output += data;
00157 output += "\n";
00158 }
00159
00160 void OutputData(std::string &output, const std::string &key, int data)
00161 {
00162 OutputData(output, key, IntToString(data));
00163 }
00164
00165 void OutputData(std::string &output, const std::string &key, const SecByteBlock &data)
00166 {
00167 output += key;
00168 output += "= ";
00169 HexEncoder(new StringSink(output), false).Put(data, data.size());
00170 output += "\n";
00171 }
00172
00173 void OutputData(std::string &output, const std::string &key, const Integer &data, int size=-1)
00174 {
00175 SecByteBlock s(size < 0 ? data.MinEncodedSize() : size);
00176 data.Encode(s, s.size());
00177 OutputData(output, key, s);
00178 }
00179
00180 void OutputData(std::string &output, const std::string &key, const PolynomialMod2 &data, int size=-1)
00181 {
00182 SecByteBlock s(size < 0 ? data.MinEncodedSize() : size);
00183 data.Encode(s, s.size());
00184 OutputData(output, key, s);
00185 }
00186
00187 void OutputData(std::string &output, DataType t, const std::string &data)
00188 {
00189 if (m_algorithm == "SKIPJACK")
00190 {
00191 if (m_test == "KAT")
00192 {
00193 if (t == OUTPUT)
00194 output = m_line + data + "\n";
00195 }
00196 else
00197 {
00198 if (t != COUNT)
00199 {
00200 output += m_typeToName[t];
00201 output += "=";
00202 }
00203 output += data;
00204 output += t == OUTPUT ? "\n" : " ";
00205 }
00206 }
00207 else if (m_algorithm == "TDES" && t == KEY_T && m_typeToName[KEY_T].empty())
00208 {
00209 output += "KEY1 = ";
00210 output += data.substr(0, 16);
00211 output += "\nKEY2 = ";
00212 output += data.size() > 16 ? data.substr(16, 16) : data.substr(0, 16);
00213 output += "\nKEY3 = ";
00214 output += data.size() > 32 ? data.substr(32, 16) : data.substr(0, 16);
00215 output += "\n";
00216 }
00217 else
00218 {
00219 output += m_typeToName[t];
00220 output += " = ";
00221 output += data;
00222 output += "\n";
00223 }
00224 }
00225
00226 void OutputData(std::string &output, DataType t, int i)
00227 {
00228 OutputData(output, t, IntToString(i));
00229 }
00230
00231 void OutputData(std::string &output, DataType t, const SecByteBlock &data)
00232 {
00233 std::string hexData;
00234 StringSource(data.begin(), data.size(), true, new HexEncoder(new StringSink(hexData), false));
00235 OutputData(output, t, hexData);
00236 }
00237
00238 void OutputGivenData(std::string &output, DataType t, bool optional = false)
00239 {
00240 if (m_data.find(m_typeToName[t]) == m_data.end())
00241 {
00242 if (optional)
00243 return;
00244 throw Exception(Exception::OTHER_ERROR, "TestDataParser: key not found: " + m_typeToName[t]);
00245 }
00246
00247 OutputData(output, t, m_data[m_typeToName[t]]);
00248 }
00249
00250 template <class T>
00251 BlockCipher * NewBT(T *)
00252 {
00253 if (!m_encrypt && (m_mode == "ECB" || m_mode == "CBC"))
00254 return new typename T::Decryption;
00255 else
00256 return new typename T::Encryption;
00257 }
00258
00259 template <class T>
00260 SymmetricCipher * NewMode(T *, BlockCipher &bt, const byte *iv)
00261 {
00262 if (!m_encrypt)
00263 return new typename T::Decryption(bt, iv, m_feedbackSize/8);
00264 else
00265 return new typename T::Encryption(bt, iv, m_feedbackSize/8);
00266 }
00267
00268 static inline void Xor(SecByteBlock &z, const SecByteBlock &x, const SecByteBlock &y)
00269 {
00270 assert(x.size() == y.size());
00271 z.resize(x.size());
00272 xorbuf(z, x, y, x.size());
00273 }
00274
00275 SecByteBlock UpdateKey(SecByteBlock key, const SecByteBlock *text)
00276 {
00277 unsigned int innerCount = (m_algorithm == "AES") ? 1000 : 10000;
00278 int keySize = key.size(), blockSize = text[0].size();
00279 SecByteBlock x(keySize);
00280 for (int k=0; k<keySize;)
00281 {
00282 int pos = innerCount * blockSize - keySize + k;
00283 memcpy(x + k, text[pos / blockSize] + pos % blockSize, blockSize - pos % blockSize);
00284 k += blockSize - pos % blockSize;
00285 }
00286
00287 if (m_algorithm == "TDES" || m_algorithm == "DES")
00288 {
00289 for (int i=0; i<keySize; i+=8)
00290 {
00291 xorbuf(key+i, x+keySize-8-i, 8);
00292 DES::CorrectKeyParityBits(key+i);
00293 }
00294 }
00295 else
00296 xorbuf(key, x, keySize);
00297
00298 return key;
00299 }
00300
00301 static inline void AssignLeftMostBits(SecByteBlock &z, const SecByteBlock &x, unsigned int K)
00302 {
00303 z.Assign(x, K/8);
00304 }
00305
00306 template <class EC>
00307 void EC_KeyPair(string &output, int n, const OID &oid)
00308 {
00309 DL_GroupParameters_EC<EC> params(oid);
00310 for (int i=0; i<n; i++)
00311 {
00312 DL_PrivateKey_EC<EC> priv;
00313 DL_PublicKey_EC<EC> pub;
00314 priv.Initialize(m_rng, params);
00315 priv.MakePublicKey(pub);
00316
00317 OutputData(output, "d ", priv.GetPrivateExponent());
00318 OutputData(output, "Qx ", pub.GetPublicElement().x, params.GetCurve().GetField().MaxElementByteLength());
00319 OutputData(output, "Qy ", pub.GetPublicElement().y, params.GetCurve().GetField().MaxElementByteLength());
00320 }
00321 }
00322
00323 template <class EC>
00324 void EC_SigGen(string &output, const OID &oid)
00325 {
00326 DL_GroupParameters_EC<EC> params(oid);
00327 ECDSA<EC, SHA1>::PrivateKey priv;
00328 ECDSA<EC, SHA1>::PublicKey pub;
00329 priv.Initialize(m_rng, params);
00330 priv.MakePublicKey(pub);
00331
00332 ECDSA<EC, SHA1>::Signer signer(priv);
00333 SecByteBlock sig(signer.SignatureLength());
00334 StringSource(m_data["Msg"], true, new HexDecoder(new SignerFilter(m_rng, signer, new ArraySink(sig, sig.size()))));
00335 SecByteBlock R(sig, sig.size()/2), S(sig+sig.size()/2, sig.size()/2);
00336
00337 OutputData(output, "Qx ", pub.GetPublicElement().x, params.GetCurve().GetField().MaxElementByteLength());
00338 OutputData(output, "Qy ", pub.GetPublicElement().y, params.GetCurve().GetField().MaxElementByteLength());
00339 OutputData(output, "R ", R);
00340 OutputData(output, "S ", S);
00341 }
00342
00343 template <class EC>
00344 void EC_SigVer(string &output, const OID &oid)
00345 {
00346 SecByteBlock x(DecodeHex(m_data["Qx"]));
00347 SecByteBlock y(DecodeHex(m_data["Qy"]));
00348 Integer r((m_data["R"]+"h").c_str());
00349 Integer s((m_data["S"]+"h").c_str());
00350
00351 EC::FieldElement Qx(x, x.size());
00352 EC::FieldElement Qy(y, y.size());
00353 EC::Element Q(Qx, Qy);
00354
00355 DL_GroupParameters_EC<EC> params(oid);
00356 ECDSA<EC, SHA1>::PublicKey pub;
00357 pub.Initialize(params, Q);
00358 ECDSA<EC, SHA1>::Verifier verifier(pub);
00359
00360 SecByteBlock sig(verifier.SignatureLength());
00361 r.Encode(sig, sig.size()/2);
00362 s.Encode(sig+sig.size()/2, sig.size()/2);
00363
00364 SignatureVerificationFilter filter(verifier);
00365 filter.Put(sig, sig.size());
00366 StringSource(m_data["Msg"], true, new HexDecoder(new Redirector(filter, Redirector::DATA_ONLY)));
00367 filter.MessageEnd();
00368 byte b;
00369 filter.Get(b);
00370 OutputData(output, "Result ", b ? "P" : "F");
00371 }
00372
00373 template <class EC>
00374 static bool EC_PKV(RandomNumberGenerator &rng, const SecByteBlock &x, const SecByteBlock &y, const OID &oid)
00375 {
00376 EC::FieldElement Qx(x, x.size());
00377 EC::FieldElement Qy(y, y.size());
00378 EC::Element Q(Qx, Qy);
00379
00380 DL_GroupParameters_EC<EC> params(oid);
00381 ECDSA<EC, SHA1>::PublicKey pub;
00382 pub.Initialize(params, Q);
00383 return pub.Validate(rng, 3);
00384 }
00385
00386 template <class H, class Result>
00387 Result * CreateRSA2(const std::string &standard)
00388 {
00389 if (typeid(Result) == typeid(PK_Verifier))
00390 {
00391 if (standard == "R")
00392 return (Result *) new RSASS_ISO<H>::Verifier;
00393 else if (standard == "P")
00394 return (Result *) new RSASS<PSS, H>::Verifier;
00395 else if (standard == "1")
00396 return (Result *) new RSASS<PKCS1v15, H>::Verifier;
00397 }
00398 else if (typeid(Result) == typeid(PK_Signer))
00399 {
00400 if (standard == "R")
00401 return (Result *) new RSASS_ISO<H>::Signer;
00402 else if (standard == "P")
00403 return (Result *) new RSASS<PSS, H>::Signer;
00404 else if (standard == "1")
00405 return (Result *) new RSASS<PKCS1v15, H>::Signer;
00406 }
00407
00408 return NULL;
00409 }
00410
00411 template <class Result>
00412 Result * CreateRSA(const std::string &standard, const std::string &hash)
00413 {
00414 if (hash == "1")
00415 return CreateRSA2<SHA1, Result>(standard);
00416 else if (hash == "224")
00417 return CreateRSA2<SHA224, Result>(standard);
00418 else if (hash == "256")
00419 return CreateRSA2<SHA256, Result>(standard);
00420 else if (hash == "384")
00421 return CreateRSA2<SHA384, Result>(standard);
00422 else if (hash == "512")
00423 return CreateRSA2<SHA512, Result>(standard);
00424 else
00425 return NULL;
00426 }
00427
00428 virtual void DoTest()
00429 {
00430 std::string output;
00431
00432 if (m_algorithm == "DSS")
00433 {
00434 if (m_test == "sha")
00435 {
00436 assert(m_compactString.size() >= 2);
00437 assert(m_compactString[0] == m_compactString.size()-2);
00438 bool b = !!m_compactString[1];
00439 Integer m;
00440 unsigned int bitLength = 0;
00441
00442 for (unsigned int j = 2; j < m_compactString.size(); j++)
00443 {
00444 m <<= m_compactString[j];
00445 for (unsigned int k = 0; k < m_compactString[j]; k++)
00446 m.SetBit(k, b);
00447 bitLength += m_compactString[j];
00448 b = !b;
00449 }
00450 m_compactString.clear();
00451 assert(bitLength % 8 == 0);
00452
00453 SecByteBlock message(bitLength / 8);
00454 m.Encode(message, message.size());
00455 SHA sha;
00456
00457 if (m_bracketString == "SHS Type 3 Strings")
00458 {
00459 SecByteBlock m1;
00460 for (int j = 0; j < 100; j++)
00461 {
00462 for (word32 i = 1; i <= 50000; i++)
00463 {
00464 m1.resize(message.size() + j/4 + 3 + 4);
00465 memcpy(m1, message, message.size());
00466 memset(m1 + message.size(), 0, j/4 + 3);
00467 PutWord(false, BIG_ENDIAN_ORDER, m1 + m1.size() - 4, i);
00468 message.resize(sha.DigestSize());
00469 sha.CalculateDigest(message, m1, m1.size());
00470 }
00471 StringSource(message, message.size(), true, new HexEncoder(new StringSink(output)));
00472 output += " ^\n";
00473 AttachedTransformation()->Put((byte *)output.data(), output.size());
00474 output.resize(0);
00475 }
00476 }
00477 else
00478 {
00479 StringSource(message, message.size(), true, new HashFilter(sha, new HexEncoder(new StringSink(output))));
00480 output += " ^\n";
00481 AttachedTransformation()->Put((byte *)output.data(), output.size());
00482 }
00483 }
00484 else if (m_test == "prime")
00485 {
00486 Integer p((m_data["Prime"] + "h").c_str());
00487 OutputData(output, "result", VerifyPrime(m_rng, p, 2) ? "P" : "F");
00488 AttachedTransformation()->Put((byte *)output.data(), output.size());
00489 output.resize(0);
00490 }
00491 else if (m_test == "pqg")
00492 {
00493 int n = atol(m_data["N"].c_str());
00494 for (int i=0; i<n; i++)
00495 {
00496 Integer p, q, h, g;
00497 int counter;
00498
00499 SecByteBlock seed(SHA::DIGESTSIZE);
00500 do
00501 {
00502 m_rng.GenerateBlock(seed, seed.size());
00503 }
00504 while (!DSA::GeneratePrimes(seed, seed.size()*8, counter, p, 1024, q));
00505 h.Randomize(m_rng, 2, p-2);
00506 g = a_exp_b_mod_c(h, (p-1)/q, p);
00507
00508 OutputData(output, "P", p);
00509 OutputData(output, "Q", q);
00510 OutputData(output, "G", g);
00511 OutputData(output, "Seed", seed);
00512 OutputData(output, "H", h, p.ByteCount());
00513 OutputData(output, "c", counter);
00514 AttachedTransformation()->Put((byte *)output.data(), output.size());
00515 output.resize(0);
00516 }
00517 }
00518 else if (m_test == "xy")
00519 {
00520 Integer p((m_data["P"] + "h").c_str());
00521 Integer q((m_data["Q"] + "h").c_str());
00522 Integer g((m_data["G"] + "h").c_str());
00523
00524 for (int i=0; i<10; i++)
00525 {
00526 DSA::Signer priv(m_rng, p, q, g);
00527 DSA::Verifier pub(priv);
00528
00529 OutputData(output, "X", priv.GetKey().GetPrivateExponent());
00530 OutputData(output, "Y", pub.GetKey().GetPublicElement());
00531 AttachedTransformation()->Put((byte *)output.data(), output.size());
00532 output.resize(0);
00533 }
00534 }
00535 else if (m_test == "gensig")
00536 {
00537 Integer p((m_data["P"] + "h").c_str());
00538 Integer q((m_data["Q"] + "h").c_str());
00539 Integer g((m_data["G"] + "h").c_str());
00540 Integer x((m_data["X"] + "h").c_str());
00541 DSA::Signer signer(p, q, g, x);
00542
00543 SecByteBlock sig(signer.SignatureLength());
00544 StringSource(m_data["Msg"], true, new HexDecoder(new SignerFilter(m_rng, signer, new ArraySink(sig, sig.size()))));
00545 OutputData(output, "Sig", sig);
00546 AttachedTransformation()->Put((byte *)output.data(), output.size());
00547 output.resize(0);
00548 }
00549 else if (m_test == "versig")
00550 {
00551 Integer p((m_data["P"] + "h").c_str());
00552 Integer q((m_data["Q"] + "h").c_str());
00553 Integer g((m_data["G"] + "h").c_str());
00554 Integer y((m_data["Y"] + "h").c_str());
00555 DSA::Verifier verifier(p, q, g, y);
00556
00557 HexDecoder filter(new SignatureVerificationFilter(verifier));
00558 StringSource(m_data["Sig"], true, new Redirector(filter, Redirector::DATA_ONLY));
00559 StringSource(m_data["Msg"], true, new Redirector(filter, Redirector::DATA_ONLY));
00560 filter.MessageEnd();
00561 byte b;
00562 filter.Get(b);
00563 OutputData(output, "result", b ? "P" : "F");
00564 AttachedTransformation()->Put((byte *)output.data(), output.size());
00565 output.resize(0);
00566 }
00567 else if (m_test == "verpqg")
00568 {
00569 Integer p((m_data["P"] + "h").c_str());
00570 Integer q((m_data["Q"] + "h").c_str());
00571 Integer g((m_data["G"] + "h").c_str());
00572 Integer h((m_data["H"] + "h").c_str());
00573 int c = atol(m_data["c"].c_str());
00574 SecByteBlock seed(m_data["Seed"].size()/2);
00575 StringSource(m_data["Seed"], true, new HexDecoder(new ArraySink(seed, seed.size())));
00576
00577 Integer p1, q1;
00578 bool result = DSA::GeneratePrimes(seed, seed.size()*8, c, p1, 1024, q1, true);
00579 result = result && (p1 == p && q1 == q);
00580 result = result && g == a_exp_b_mod_c(h, (p-1)/q, p);
00581
00582 OutputData(output, "result", result ? "P" : "F");
00583 AttachedTransformation()->Put((byte *)output.data(), output.size());
00584 output.resize(0);
00585 }
00586
00587 return;
00588 }
00589
00590 if (m_algorithm == "ECDSA")
00591 {
00592 std::map<std::string, OID> name2oid;
00593 name2oid["P-192"] = ASN1::secp192r1();
00594 name2oid["P-224"] = ASN1::secp224r1();
00595 name2oid["P-256"] = ASN1::secp256r1();
00596 name2oid["P-384"] = ASN1::secp384r1();
00597 name2oid["P-521"] = ASN1::secp521r1();
00598 name2oid["K-163"] = ASN1::sect163k1();
00599 name2oid["K-233"] = ASN1::sect233k1();
00600 name2oid["K-283"] = ASN1::sect283k1();
00601 name2oid["K-409"] = ASN1::sect409k1();
00602 name2oid["K-571"] = ASN1::sect571k1();
00603 name2oid["B-163"] = ASN1::sect163r2();
00604 name2oid["B-233"] = ASN1::sect233r1();
00605 name2oid["B-283"] = ASN1::sect283r1();
00606 name2oid["B-409"] = ASN1::sect409r1();
00607 name2oid["B-571"] = ASN1::sect571r1();
00608
00609 if (m_test == "PKV")
00610 {
00611 bool pass;
00612 if (m_bracketString[0] == 'P')
00613 pass = EC_PKV<ECP>(m_rng, DecodeHex(m_data["Qx"]), DecodeHex(m_data["Qy"]), name2oid[m_bracketString]);
00614 else
00615 pass = EC_PKV<EC2N>(m_rng, DecodeHex(m_data["Qx"]), DecodeHex(m_data["Qy"]), name2oid[m_bracketString]);
00616
00617 OutputData(output, "Result ", pass ? "P" : "F");
00618 }
00619 else if (m_test == "KeyPair")
00620 {
00621 if (m_bracketString[0] == 'P')
00622 EC_KeyPair<ECP>(output, atol(m_data["N"].c_str()), name2oid[m_bracketString]);
00623 else
00624 EC_KeyPair<EC2N>(output, atol(m_data["N"].c_str()), name2oid[m_bracketString]);
00625 }
00626 else if (m_test == "SigGen")
00627 {
00628 if (m_bracketString[0] == 'P')
00629 EC_SigGen<ECP>(output, name2oid[m_bracketString]);
00630 else
00631 EC_SigGen<EC2N>(output, name2oid[m_bracketString]);
00632 }
00633 else if (m_test == "SigVer")
00634 {
00635 if (m_bracketString[0] == 'P')
00636 EC_SigVer<ECP>(output, name2oid[m_bracketString]);
00637 else
00638 EC_SigVer<EC2N>(output, name2oid[m_bracketString]);
00639 }
00640
00641 AttachedTransformation()->Put((byte *)output.data(), output.size());
00642 output.resize(0);
00643 return;
00644 }
00645
00646 if (m_algorithm == "RSA")
00647 {
00648 std::string shaAlg = m_data["SHAAlg"].substr(3);
00649
00650 if (m_test == "Ver")
00651 {
00652 Integer n((m_data["n"] + "h").c_str());
00653 Integer e((m_data["e"] + "h").c_str());
00654 RSA::PublicKey pub;
00655 pub.Initialize(n, e);
00656
00657 member_ptr<PK_Verifier> pV(CreateRSA<PK_Verifier>(m_mode, shaAlg));
00658 pV->AccessMaterial().AssignFrom(pub);
00659
00660 HexDecoder filter(new SignatureVerificationFilter(*pV));
00661 for (unsigned int i=m_data["S"].size(); i<pV->SignatureLength()*2; i++)
00662 filter.Put('0');
00663 StringSource(m_data["S"], true, new Redirector(filter, Redirector::DATA_ONLY));
00664 StringSource(m_data["Msg"], true, new Redirector(filter, Redirector::DATA_ONLY));
00665 filter.MessageEnd();
00666 byte b;
00667 filter.Get(b);
00668 OutputData(output, "Result ", b ? "P" : "F");
00669 }
00670 else
00671 {
00672 assert(m_test == "Gen");
00673 int modLen = atol(m_bracketString.substr(6).c_str());
00674 std::string &encodedKey = m_data["PrivKey"];
00675 RSA::PrivateKey priv;
00676
00677 if (!encodedKey.empty())
00678 {
00679 StringStore s(encodedKey);
00680 priv.BERDecode(s);
00681 if (priv.GetModulus().BitCount() != modLen)
00682 encodedKey.clear();
00683 }
00684
00685 if (encodedKey.empty())
00686 {
00687 priv.Initialize(m_rng, modLen);
00688 StringSink s(encodedKey);
00689 priv.DEREncode(s);
00690 OutputData(output, "n ", priv.GetModulus());
00691 OutputData(output, "e ", priv.GetPublicExponent(), modLen/8);
00692 }
00693
00694 member_ptr<PK_Signer> pS(CreateRSA<PK_Signer>(m_mode, shaAlg));
00695 pS->AccessMaterial().AssignFrom(priv);
00696
00697 SecByteBlock sig(pS->SignatureLength());
00698 StringSource(m_data["Msg"], true, new HexDecoder(new SignerFilter(m_rng, *pS, new ArraySink(sig, sig.size()))));
00699 OutputData(output, "SHAAlg ", m_data["SHAAlg"]);
00700 OutputData(output, "Msg ", m_data["Msg"]);
00701 OutputData(output, "S ", sig);
00702 }
00703
00704 AttachedTransformation()->Put((byte *)output.data(), output.size());
00705 output.resize(0);
00706 return;
00707 }
00708
00709 if (m_algorithm == "SHA2")
00710 {
00711 member_ptr<HashFunction> pHF;
00712
00713 if (m_mode == "224")
00714 pHF.reset(new SHA224);
00715 else if (m_mode == "256")
00716 pHF.reset(new SHA256);
00717 else if (m_mode == "384")
00718 pHF.reset(new SHA384);
00719 else if (m_mode == "512")
00720 pHF.reset(new SHA512);
00721
00722 if (m_test == "MONTE")
00723 {
00724 SecByteBlock seed = m_data2[INPUT];
00725 SecByteBlock MD[1003];
00726 int i,j;
00727
00728 for (j=0; j<100; j++)
00729 {
00730 MD[0] = MD[1] = MD[2] = seed;
00731 for (i=3; i<1003; i++)
00732 {
00733 SecByteBlock Mi = MD[i-3] + MD[i-2] + MD[i-1];
00734 MD[i].resize(pHF->DigestSize());
00735 pHF->CalculateDigest(MD[i], Mi, Mi.size());
00736 }
00737 seed = MD[1002];
00738 OutputData(output, "COUNT ", j);
00739 OutputData(output, "MD ", seed);
00740 AttachedTransformation()->Put((byte *)output.data(), output.size());
00741 output.resize(0);
00742 }
00743 }
00744 else
00745 {
00746 SecByteBlock tag(pHF->DigestSize());
00747 SecByteBlock &msg(m_data2[INPUT]);
00748 int len = atol(m_data["Len"].c_str());
00749 StringSource(msg.begin(), len/8, true, new HashFilter(*pHF, new ArraySink(tag, tag.size())));
00750 OutputData(output, "MD ", tag);
00751 AttachedTransformation()->Put((byte *)output.data(), output.size());
00752 output.resize(0);
00753 }
00754 return;
00755 }
00756
00757 SecByteBlock &key = m_data2[KEY_T];
00758
00759 if (m_algorithm == "TDES")
00760 {
00761 if (!m_data["KEY1"].empty())
00762 {
00763 const std::string keys[3] = {m_data["KEY1"], m_data["KEY2"], m_data["KEY3"]};
00764 key.resize(24);
00765 HexDecoder hexDec(new ArraySink(key, key.size()));
00766 for (int i=0; i<3; i++)
00767 hexDec.Put((byte *)keys[i].data(), keys[i].size());
00768
00769 if (keys[0] == keys[2])
00770 {
00771 if (keys[0] == keys[1])
00772 key.resize(8);
00773 else
00774 key.resize(16);
00775 }
00776 else
00777 key.resize(24);
00778 }
00779 }
00780
00781 if (m_algorithm == "RNG")
00782 {
00783 key.resize(16);
00784 HexDecoder hexDec(new ArraySink(key, key.size()));
00785 StringSource(m_data["Key1"], true, new Redirector(hexDec));
00786 StringSource(m_data["Key2"], true, new Redirector(hexDec));
00787
00788 SecByteBlock seed(m_data2[INPUT]), dt(m_data2[IV]), r(8);
00789 X917RNG rng(new DES_EDE2::Encryption(key), seed, dt);
00790
00791 if (m_test == "MCT")
00792 {
00793 for (int i=0; i<10000; i++)
00794 rng.GenerateBlock(r, r.size());
00795 }
00796 else
00797 {
00798 rng.GenerateBlock(r, r.size());
00799 }
00800
00801 OutputData(output, "R ", r);
00802 AttachedTransformation()->Put((byte *)output.data(), output.size());
00803 output.resize(0);
00804 return;
00805 }
00806
00807 if (m_algorithm == "HMAC")
00808 {
00809 member_ptr<MessageAuthenticationCode> pMAC;
00810
00811 if (m_bracketString == "L=20")
00812 pMAC.reset(new HMAC<SHA1>);
00813 else if (m_bracketString == "L=28")
00814 pMAC.reset(new HMAC<SHA224>);
00815 else if (m_bracketString == "L=32")
00816 pMAC.reset(new HMAC<SHA256>);
00817 else if (m_bracketString == "L=48")
00818 pMAC.reset(new HMAC<SHA384>);
00819 else if (m_bracketString == "L=64")
00820 pMAC.reset(new HMAC<SHA512>);
00821 else
00822 throw Exception(Exception::OTHER_ERROR, "TestDataParser: unexpected HMAC bracket string: " + m_bracketString);
00823
00824 pMAC->SetKey(key, key.size());
00825 int Tlen = atol(m_data["Tlen"].c_str());
00826 SecByteBlock tag(Tlen);
00827 StringSource(m_data["Msg"], true, new HexDecoder(new HashFilter(*pMAC, new ArraySink(tag, Tlen), false, Tlen)));
00828 OutputData(output, "Mac ", tag);
00829 AttachedTransformation()->Put((byte *)output.data(), output.size());
00830 output.resize(0);
00831 return;
00832 }
00833
00834 member_ptr<BlockCipher> pBT;
00835 if (m_algorithm == "DES")
00836 pBT.reset(NewBT((DES*)0));
00837 else if (m_algorithm == "TDES")
00838 {
00839 if (key.size() == 8)
00840 pBT.reset(NewBT((DES*)0));
00841 else if (key.size() == 16)
00842 pBT.reset(NewBT((DES_EDE2*)0));
00843 else
00844 pBT.reset(NewBT((DES_EDE3*)0));
00845 }
00846 else if (m_algorithm == "SKIPJACK")
00847 pBT.reset(NewBT((SKIPJACK*)0));
00848 else if (m_algorithm == "AES")
00849 pBT.reset(NewBT((AES*)0));
00850 else
00851 throw Exception(Exception::OTHER_ERROR, "TestDataParser: unexpected algorithm: " + m_algorithm);
00852
00853 if (!pBT->IsValidKeyLength(key.size()))
00854 key.CleanNew(pBT->DefaultKeyLength());
00855 pBT->SetKey(key.data(), key.size());
00856
00857 SecByteBlock &iv = m_data2[IV];
00858 if (iv.empty())
00859 iv.CleanNew(pBT->BlockSize());
00860
00861 member_ptr<SymmetricCipher> pCipher;
00862 unsigned int K = m_feedbackSize;
00863
00864 if (m_mode == "ECB")
00865 pCipher.reset(NewMode((ECB_Mode_ExternalCipher*)0, *pBT, iv));
00866 else if (m_mode == "CBC")
00867 pCipher.reset(NewMode((CBC_Mode_ExternalCipher*)0, *pBT, iv));
00868 else if (m_mode == "CFB")
00869 pCipher.reset(NewMode((CFB_Mode_ExternalCipher*)0, *pBT, iv));
00870 else if (m_mode == "OFB")
00871 pCipher.reset(NewMode((OFB_Mode_ExternalCipher*)0, *pBT, iv));
00872 else
00873 throw Exception(Exception::OTHER_ERROR, "TestDataParser: unexpected mode: " + m_mode);
00874
00875 bool encrypt = m_encrypt;
00876
00877 if (m_test == "MONTE")
00878 {
00879 SecByteBlock KEY[401];
00880 KEY[0] = key;
00881 int keySize = key.size();
00882 int blockSize = pBT->BlockSize();
00883
00884 SecByteBlock IB[10001], OB[10001], PT[10001], CT[10001], RESULT[10001], TXT[10001], CV[10001];
00885 PT[0] = GetData("PLAINTEXT");
00886 CT[0] = GetData("CIPHERTEXT");
00887 CV[0] = IB[0] = iv;
00888 TXT[0] = GetData("TEXT");
00889
00890 int outerCount = (m_algorithm == "AES") ? 100 : 400;
00891 int innerCount = (m_algorithm == "AES") ? 1000 : 10000;
00892
00893 for (int i=0; i<outerCount; i++)
00894 {
00895 pBT->SetKey(KEY[i], keySize);
00896
00897 for (int j=0; j<innerCount; j++)
00898 {
00899 if (m_mode == "ECB")
00900 {
00901 if (encrypt)
00902 {
00903 IB[j] = PT[j];
00904 CT[j].resize(blockSize);
00905 pBT->ProcessBlock(IB[j], CT[j]);
00906 PT[j+1] = CT[j];
00907 }
00908 else
00909 {
00910 IB[j] = CT[j];
00911 PT[j].resize(blockSize);
00912 pBT->ProcessBlock(IB[j], PT[j]);
00913 CT[j+1] = PT[j];
00914 }
00915 }
00916 else if (m_mode == "OFB")
00917 {
00918 OB[j].resize(blockSize);
00919 pBT->ProcessBlock(IB[j], OB[j]);
00920 Xor(RESULT[j], OB[j], TXT[j]);
00921 TXT[j+1] = IB[j];
00922 IB[j+1] = OB[j];
00923 }
00924 else if (m_mode == "CBC")
00925 {
00926 if (encrypt)
00927 {
00928 Xor(IB[j], PT[j], CV[j]);
00929 CT[j].resize(blockSize);
00930 pBT->ProcessBlock(IB[j], CT[j]);
00931 PT[j+1] = CV[j];
00932 CV[j+1] = CT[j];
00933 }
00934 else
00935 {
00936 IB[j] = CT[j];
00937 OB[j].resize(blockSize);
00938 pBT->ProcessBlock(IB[j], OB[j]);
00939 Xor(PT[j], OB[j], CV[j]);
00940 CV[j+1] = CT[j];
00941 CT[j+1] = PT[j];
00942 }
00943 }
00944 else if (m_mode == "CFB")
00945 {
00946 if (encrypt)
00947 {
00948 OB[j].resize(blockSize);
00949 pBT->ProcessBlock(IB[j], OB[j]);
00950 AssignLeftMostBits(CT[j], OB[j], K);
00951 Xor(CT[j], CT[j], PT[j]);
00952 AssignLeftMostBits(PT[j+1], IB[j], K);
00953 IB[j+1].resize(blockSize);
00954 memcpy(IB[j+1], IB[j]+K/8, blockSize-K/8);
00955 memcpy(IB[j+1]+blockSize-K/8, CT[j], K/8);
00956 }
00957 else
00958 {
00959 OB[j].resize(blockSize);
00960 pBT->ProcessBlock(IB[j], OB[j]);
00961 AssignLeftMostBits(PT[j], OB[j], K);
00962 Xor(PT[j], PT[j], CT[j]);
00963 IB[j+1].resize(blockSize);
00964 memcpy(IB[j+1], IB[j]+K/8, blockSize-K/8);
00965 memcpy(IB[j+1]+blockSize-K/8, CT[j], K/8);
00966 AssignLeftMostBits(CT[j+1], OB[j], K);
00967 }
00968 }
00969 else
00970 throw Exception(Exception::OTHER_ERROR, "TestDataParser: unexpected mode: " + m_mode);
00971 }
00972
00973 OutputData(output, "COUNT ", i);
00974 OutputData(output, KEY_T, KEY[i]);
00975 if (m_mode == "CBC")
00976 OutputData(output, IV, CV[0]);
00977 if (m_mode == "OFB" || m_mode == "CFB")
00978 OutputData(output, IV, IB[0]);
00979 if (m_mode == "ECB" || m_mode == "CBC" || m_mode == "CFB")
00980 {
00981 if (encrypt)
00982 {
00983 OutputData(output, INPUT, PT[0]);
00984 OutputData(output, OUTPUT, CT[innerCount-1]);
00985 KEY[i+1] = UpdateKey(KEY[i], CT);
00986 }
00987 else
00988 {
00989 OutputData(output, INPUT, CT[0]);
00990 OutputData(output, OUTPUT, PT[innerCount-1]);
00991 KEY[i+1] = UpdateKey(KEY[i], PT);
00992 }
00993 PT[0] = PT[innerCount];
00994 IB[0] = IB[innerCount];
00995 CV[0] = CV[innerCount];
00996 CT[0] = CT[innerCount];
00997 }
00998 else if (m_mode == "OFB")
00999 {
01000 OutputData(output, INPUT, TXT[0]);
01001 OutputData(output, OUTPUT, RESULT[innerCount-1]);
01002 KEY[i+1] = UpdateKey(KEY[i], RESULT);
01003 Xor(TXT[0], TXT[0], IB[innerCount-1]);
01004 IB[0] = OB[innerCount-1];
01005 }
01006 output += "\n";
01007 AttachedTransformation()->Put((byte *)output.data(), output.size());
01008 output.resize(0);
01009 }
01010 }
01011 else if (m_test == "MCT")
01012 {
01013 SecByteBlock KEY[101];
01014 KEY[0] = key;
01015 int keySize = key.size();
01016 int blockSize = pBT->BlockSize();
01017
01018 SecByteBlock ivs[101], inputs[1001], outputs[1001];
01019 ivs[0] = iv;
01020 inputs[0] = m_data2[INPUT];
01021
01022 for (int i=0; i<100; i++)
01023 {
01024 pCipher->SetKey(KEY[i], keySize, MakeParameters(Name::IV(), (const byte *)ivs[i])(Name::FeedbackSize(), (int)K/8, false));
01025
01026 for (int j=0; j<1000; j++)
01027 {
01028 outputs[j] = inputs[j];
01029 pCipher->ProcessString(outputs[j], outputs[j].size());
01030 if (K==8 && m_mode == "CFB")
01031 {
01032 if (j<16)
01033 inputs[j+1].Assign(ivs[i]+j, 1);
01034 else
01035 inputs[j+1] = outputs[j-16];
01036 }
01037 else if (m_mode == "ECB")
01038 inputs[j+1] = outputs[j];
01039 else if (j == 0)
01040 inputs[j+1] = ivs[i];
01041 else
01042 inputs[j+1] = outputs[j-1];
01043 }
01044
01045 if (m_algorithm == "AES")
01046 OutputData(output, COUNT, m_count++);
01047 OutputData(output, KEY_T, KEY[i]);
01048 if (m_mode != "ECB")
01049 OutputData(output, IV, ivs[i]);
01050 OutputData(output, INPUT, inputs[0]);
01051 OutputData(output, OUTPUT, outputs[999]);
01052 output += "\n";
01053 AttachedTransformation()->Put((byte *)output.data(), output.size());
01054 output.resize(0);
01055
01056 KEY[i+1] = UpdateKey(KEY[i], outputs);
01057 ivs[i+1].CleanNew(pCipher->IVSize());
01058 ivs[i+1] = UpdateKey(ivs[i+1], outputs);
01059 if (K==8 && m_mode == "CFB")
01060 inputs[0] = outputs[999-16];
01061 else if (m_mode == "ECB")
01062 inputs[0] = outputs[999];
01063 else
01064 inputs[0] = outputs[998];
01065 }
01066 }
01067 else
01068 {
01069 assert(m_test == "KAT");
01070
01071 SecByteBlock &input = m_data2[INPUT];
01072 SecByteBlock result(input.size());
01073 member_ptr<Filter> pFilter(new StreamTransformationFilter(*pCipher, new ArraySink(result, result.size()), StreamTransformationFilter::NO_PADDING));
01074 StringSource(input.data(), input.size(), true, pFilter.release());
01075
01076 OutputGivenData(output, COUNT, true);
01077 OutputData(output, KEY_T, key);
01078 OutputGivenData(output, IV, true);
01079 OutputGivenData(output, INPUT);
01080 OutputData(output, OUTPUT, result);
01081 output += "\n";
01082 AttachedTransformation()->Put((byte *)output.data(), output.size());
01083 }
01084 }
01085
01086 std::vector<std::string> Tokenize(const std::string &line)
01087 {
01088 std::vector<std::string> result;
01089 std::string s;
01090 for (unsigned int i=0; i<line.size(); i++)
01091 {
01092 if (isalnum(line[i]) || line[i] == '^')
01093 s += line[i];
01094 else if (!s.empty())
01095 {
01096 result.push_back(s);
01097 s = "";
01098 }
01099 if (line[i] == '=')
01100 result.push_back("=");
01101 }
01102 result.push_back(s);
01103 return result;
01104 }
01105
01106 bool IsolatedMessageEnd(bool blocking)
01107 {
01108 if (!blocking)
01109 throw BlockingInputOnly("TestDataParser");
01110
01111 m_line.resize(0);
01112 m_inQueue.TransferTo(StringSink(m_line).Ref());
01113
01114 if (m_line[0] == '#')
01115 return false;
01116
01117 bool copyLine = false;
01118
01119 if (m_line[0] == '[')
01120 {
01121 m_bracketString = m_line.substr(1, m_line.size()-2);
01122 if (m_bracketString == "ENCRYPT")
01123 SetEncrypt(true);
01124 if (m_bracketString == "DECRYPT")
01125 SetEncrypt(false);
01126 copyLine = true;
01127 }
01128
01129 if (m_line.substr(0, 2) == "H>")
01130 {
01131 assert(m_test == "sha");
01132 m_bracketString = m_line.substr(2, m_line.size()-4);
01133 m_line = m_line.substr(0, 13) + "Hashes<H";
01134 copyLine = true;
01135 }
01136
01137 if (m_line == "D>")
01138 copyLine = true;
01139
01140 if (m_line == "<D")
01141 {
01142 m_line += "\n";
01143 copyLine = true;
01144 }
01145
01146 if (copyLine)
01147 {
01148 m_line += '\n';
01149 AttachedTransformation()->Put((byte *)m_line.data(), m_line.size(), blocking);
01150 return false;
01151 }
01152
01153 std::vector<std::string> tokens = Tokenize(m_line);
01154
01155 if (m_algorithm == "DSS" && m_test == "sha")
01156 {
01157 for (unsigned int i = 0; i < tokens.size(); i++)
01158 {
01159 if (tokens[i] == "^")
01160 DoTest();
01161 else if (tokens[i] != "")
01162 m_compactString.push_back(atol(tokens[i].c_str()));
01163 }
01164 }
01165 else
01166 {
01167 if (!m_line.empty() && ((m_algorithm == "RSA" && m_test != "Gen") || m_algorithm == "RNG" || m_algorithm == "HMAC" || m_algorithm == "SHA2" || (m_algorithm == "ECDSA" && m_test != "KeyPair") || (m_algorithm == "DSS" && m_test != "pqg")))
01168 {
01169
01170 std::string output = m_line + '\n';
01171 AttachedTransformation()->Put((byte *)output.data(), output.size());
01172 }
01173
01174 for (unsigned int i = 0; i < tokens.size(); i++)
01175 {
01176 if (m_firstLine && m_algorithm != "DSS")
01177 {
01178 if (tokens[i] == "Encrypt" || tokens[i] == "OFB")
01179 SetEncrypt(true);
01180 else if (tokens[i] == "Decrypt")
01181 SetEncrypt(false);
01182 else if (tokens[i] == "Modes")
01183 m_test = "MONTE";
01184 }
01185 else
01186 {
01187 if (tokens[i] != "=")
01188 continue;
01189
01190 if (i == 0)
01191 throw Exception(Exception::OTHER_ERROR, "TestDataParser: unexpected data: " + m_line);
01192
01193 const std::string &key = tokens[i-1];
01194 std::string &data = m_data[key];
01195 data = tokens[i+1];
01196 DataType t = m_nameToType[key];
01197 m_typeToName[t] = key;
01198 m_data2[t] = DecodeHex(data);
01199
01200 if (key == m_trigger || (t == OUTPUT && !m_data2[INPUT].empty()))
01201 DoTest();
01202 }
01203 }
01204 }
01205
01206 m_firstLine = false;
01207
01208 return false;
01209 }
01210
01211 inline const SecByteBlock & GetData(const std::string &key)
01212 {
01213 return m_data2[m_nameToType[key]];
01214 }
01215
01216 static SecByteBlock DecodeHex(const std::string &data)
01217 {
01218 SecByteBlock data2(data.size() / 2);
01219 StringSource(data, true, new HexDecoder(new ArraySink(data2, data2.size())));
01220 return data2;
01221 }
01222
01223 std::string m_algorithm, m_test, m_mode, m_line, m_bracketString, m_trigger;
01224 unsigned int m_feedbackSize, m_blankLineTransition;
01225 bool m_encrypt, m_firstLine;
01226
01227 typedef std::map<std::string, DataType> NameToTypeMap;
01228 NameToTypeMap m_nameToType;
01229 typedef std::map<DataType, std::string> TypeToNameMap;
01230 TypeToNameMap m_typeToName;
01231
01232 typedef std::map<std::string, std::string> Map;
01233 Map m_data;
01234 typedef std::map<DataType, SecByteBlock> Map2;
01235 Map2 m_data2;
01236 int m_count;
01237
01238 AutoSeededX917RNG<DES_EDE3> m_rng;
01239 std::vector<unsigned int> m_compactString;
01240 };
01241
01242 int FIPS_140_AlgorithmTest(int argc, char **argv)
01243 {
01244 argc--;
01245 argv++;
01246
01247 std::string algorithm = argv[1];
01248 std::string pathname = argv[2];
01249 unsigned int i = pathname.find_last_of("\\/");
01250 std::string filename = pathname.substr(i == std::string::npos ? 0 : i+1);
01251 try
01252 {
01253 std::string mode;
01254 if (algorithm == "SHA2")
01255 mode = filename.substr(3, 3);
01256 else if (algorithm == "RSA")
01257 mode = filename.substr(6, 1);
01258 else if (filename[0] == 'S' || filename[0] == 'T')
01259 mode = filename.substr(1, 3);
01260 else
01261 mode = filename.substr(0, 3);
01262 for (i = 0; i<mode.size(); i++)
01263 mode[i] = toupper(mode[i]);
01264 unsigned int feedbackSize = mode == "CFB" ? atoi(filename.substr(filename.find_first_of("0123456789")).c_str()) : 0;
01265 std::string test;
01266 if (algorithm == "DSS" || algorithm == "ECDSA")
01267 test = filename.substr(0, filename.size() - 4);
01268 else if (algorithm == "RSA")
01269 test = filename.substr(3, 3);
01270 else if (filename.find("Monte") != std::string::npos)
01271 test = "MONTE";
01272 else if (filename.find("MCT") != std::string::npos)
01273 test = "MCT";
01274 else
01275 test = "KAT";
01276 bool encrypt = (filename.find("vrct") == std::string::npos);
01277
01278 BufferedTransformation *pSink = NULL;
01279
01280 if (argc > 3)
01281 {
01282 std::string outDir = argv[3];
01283 if (*outDir.rbegin() != '\\' && *outDir.rbegin() != '/')
01284 outDir += '/';
01285 std::string outPathname = outDir + filename.substr(0, filename.size() - 3) + "rsp";
01286 pSink = new FileSink(outPathname.c_str(), false);
01287 }
01288 else
01289 pSink = new FileSink(cout);
01290
01291 FileSource(pathname.c_str(), true, new LineBreakParser(new TestDataParser(algorithm, test, mode, feedbackSize, encrypt, pSink)), false);
01292 }
01293 catch (...)
01294 {
01295 cout << "file: " << filename << endl;
01296 throw;
01297 }
01298 return 0;
01299 }
01300
01301 extern int (*AdhocTest)(int argc, char *argv[]);
01302 static int s_i = (AdhocTest = &FIPS_140_AlgorithmTest, 0);
01303 #endif