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