Main Page | Namespace List | Class Hierarchy | Alphabetical List | Class List | File List | Namespace Members | Class Members | File Members

cryptlib.cpp

00001 // cryptlib.cpp - written and placed in the public domain by Wei Dai
00002 
00003 #include "pch.h"
00004 #include "cryptlib.h"
00005 #include "misc.h"
00006 #include "filters.h"
00007 #include "algparam.h"
00008 #include "fips140.h"
00009 #include "argnames.h"
00010 
00011 #include <memory>
00012 
00013 NAMESPACE_BEGIN(CryptoPP)
00014 
00015 CRYPTOPP_COMPILE_ASSERT(sizeof(byte) == 1);
00016 CRYPTOPP_COMPILE_ASSERT(sizeof(word16) == 2);
00017 CRYPTOPP_COMPILE_ASSERT(sizeof(word32) == 4);
00018 #ifdef WORD64_AVAILABLE
00019 CRYPTOPP_COMPILE_ASSERT(sizeof(word64) == 8);
00020 #endif
00021 CRYPTOPP_COMPILE_ASSERT(sizeof(dword) == 2*sizeof(word));
00022 
00023 const std::string BufferedTransformation::NULL_CHANNEL;
00024 const NullNameValuePairs g_nullNameValuePairs;
00025 
00026 BufferedTransformation & TheBitBucket()
00027 {
00028         static BitBucket bitBucket;
00029         return bitBucket;
00030 }
00031 
00032 Algorithm::Algorithm(bool checkSelfTestStatus)
00033 {
00034         if (checkSelfTestStatus && FIPS_140_2_ComplianceEnabled())
00035         {
00036                 if (GetPowerUpSelfTestStatus() == POWER_UP_SELF_TEST_NOT_DONE && !PowerUpSelfTestInProgressOnThisThread())
00037                         throw SelfTestFailure("Cryptographic algorithms are disabled before the power-up self tests are performed.");
00038 
00039                 if (GetPowerUpSelfTestStatus() == POWER_UP_SELF_TEST_FAILED)
00040                         throw SelfTestFailure("Cryptographic algorithms are disabled after power-up a self test failed.");
00041         }
00042 }
00043 
00044 void SimpleKeyingInterface::SetKeyWithRounds(const byte *key, unsigned int length, int rounds)
00045 {
00046         SetKey(key, length, MakeParameters(Name::Rounds(), rounds));
00047 }
00048 
00049 void SimpleKeyingInterface::SetKeyWithIV(const byte *key, unsigned int length, const byte *iv)
00050 {
00051         SetKey(key, length, MakeParameters(Name::IV(), iv));
00052 }
00053 
00054 void SimpleKeyingInterface::ThrowIfInvalidKeyLength(const Algorithm &algorithm, unsigned int length)
00055 {
00056         if (!IsValidKeyLength(length))
00057                 throw InvalidKeyLength(algorithm.AlgorithmName(), length);
00058 }
00059 
00060 void BlockTransformation::ProcessAndXorMultipleBlocks(const byte *inBlocks, const byte *xorBlocks, byte *outBlocks, unsigned int numberOfBlocks) const
00061 {
00062         unsigned int blockSize = BlockSize();
00063         while (numberOfBlocks--)
00064         {
00065                 ProcessAndXorBlock(inBlocks, xorBlocks, outBlocks);
00066                 inBlocks += blockSize;
00067                 outBlocks += blockSize;
00068                 if (xorBlocks)
00069                         xorBlocks += blockSize;
00070         }
00071 }
00072 
00073 void StreamTransformation::ProcessLastBlock(byte *outString, const byte *inString, unsigned int length)
00074 {
00075         assert(MinLastBlockSize() == 0);        // this function should be overriden otherwise
00076 
00077         if (length == MandatoryBlockSize())
00078                 ProcessData(outString, inString, length);
00079         else if (length != 0)
00080                 throw NotImplemented("StreamTransformation: this object does't support a special last block");
00081 }
00082 
00083 unsigned int RandomNumberGenerator::GenerateBit()
00084 {
00085         return Parity(GenerateByte());
00086 }
00087 
00088 void RandomNumberGenerator::GenerateBlock(byte *output, unsigned int size)
00089 {
00090         while (size--)
00091                 *output++ = GenerateByte();
00092 }
00093 
00094 word32 RandomNumberGenerator::GenerateWord32(word32 min, word32 max)
00095 {
00096         word32 range = max-min;
00097         const int maxBytes = BytePrecision(range);
00098         const int maxBits = BitPrecision(range);
00099 
00100         word32 value;
00101 
00102         do
00103         {
00104                 value = 0;
00105                 for (int i=0; i<maxBytes; i++)
00106                         value = (value << 8) | GenerateByte();
00107 
00108                 value = Crop(value, maxBits);
00109         } while (value > range);
00110 
00111         return value+min;
00112 }
00113 
00114 void RandomNumberGenerator::DiscardBytes(unsigned int n)
00115 {
00116         while (n--)
00117                 GenerateByte();
00118 }
00119 
00120 RandomNumberGenerator & NullRNG()
00121 {
00122         class NullRNG : public RandomNumberGenerator
00123         {
00124         public:
00125                 std::string AlgorithmName() const {return "NullRNG";}
00126                 byte GenerateByte() {throw NotImplemented("NullRNG: NullRNG should only be passed to functions that don't need to generate random bytes");}
00127         };
00128 
00129         static NullRNG s_nullRNG;
00130         return s_nullRNG;
00131 }
00132 
00133 bool HashTransformation::TruncatedVerify(const byte *digestIn, unsigned int digestLength)
00134 {
00135         ThrowIfInvalidTruncatedSize(digestLength);
00136         SecByteBlock digest(digestLength);
00137         TruncatedFinal(digest, digestLength);
00138         return memcmp(digest, digestIn, digestLength) == 0;
00139 }
00140 
00141 void HashTransformation::ThrowIfInvalidTruncatedSize(unsigned int size) const
00142 {
00143         if (size > DigestSize())
00144                 throw InvalidArgument("HashTransformation: can't truncate a " + IntToString(DigestSize()) + " byte digest to " + IntToString(size) + " bytes");
00145 }
00146 
00147 unsigned int BufferedTransformation::GetMaxWaitObjectCount() const
00148 {
00149         const BufferedTransformation *t = AttachedTransformation();
00150         return t ? t->GetMaxWaitObjectCount() : 0;
00151 }
00152 
00153 void BufferedTransformation::GetWaitObjects(WaitObjectContainer &container)
00154 {
00155         BufferedTransformation *t = AttachedTransformation();
00156         if (t)
00157                 t->GetWaitObjects(container);
00158 }
00159 
00160 void BufferedTransformation::Initialize(const NameValuePairs &parameters, int propagation)
00161 {
00162         assert(!AttachedTransformation());
00163         IsolatedInitialize(parameters);
00164 }
00165 
00166 bool BufferedTransformation::Flush(bool hardFlush, int propagation, bool blocking)
00167 {
00168         assert(!AttachedTransformation());
00169         return IsolatedFlush(hardFlush, blocking);
00170 }
00171 
00172 bool BufferedTransformation::MessageSeriesEnd(int propagation, bool blocking)
00173 {
00174         assert(!AttachedTransformation());
00175         return IsolatedMessageSeriesEnd(blocking);
00176 }
00177 
00178 byte * BufferedTransformation::ChannelCreatePutSpace(const std::string &channel, unsigned int &size)
00179 {
00180         if (channel.empty())
00181                 return CreatePutSpace(size);
00182         else
00183                 throw NoChannelSupport();
00184 }
00185 
00186 unsigned int BufferedTransformation::ChannelPut2(const std::string &channel, const byte *begin, unsigned int length, int messageEnd, bool blocking)
00187 {
00188         if (channel.empty())
00189                 return Put2(begin, length, messageEnd, blocking);
00190         else
00191                 throw NoChannelSupport();
00192 }
00193 
00194 unsigned int BufferedTransformation::ChannelPutModifiable2(const std::string &channel, byte *begin, unsigned int length, int messageEnd, bool blocking)
00195 {
00196         if (channel.empty())
00197                 return PutModifiable2(begin, length, messageEnd, blocking);
00198         else
00199                 return ChannelPut2(channel, begin, length, messageEnd, blocking);
00200 }
00201 
00202 void BufferedTransformation::ChannelInitialize(const std::string &channel, const NameValuePairs &parameters, int propagation)
00203 {
00204         if (channel.empty())
00205                 Initialize(parameters, propagation);
00206         else
00207                 throw NoChannelSupport();
00208 }
00209 
00210 bool BufferedTransformation::ChannelFlush(const std::string &channel, bool completeFlush, int propagation, bool blocking)
00211 {
00212         if (channel.empty())
00213                 return Flush(completeFlush, propagation, blocking);
00214         else
00215                 throw NoChannelSupport();
00216 }
00217 
00218 bool BufferedTransformation::ChannelMessageSeriesEnd(const std::string &channel, int propagation, bool blocking)
00219 {
00220         if (channel.empty())
00221                 return MessageSeriesEnd(propagation, blocking);
00222         else
00223                 throw NoChannelSupport();
00224 }
00225 
00226 unsigned long BufferedTransformation::MaxRetrievable() const
00227 {
00228         if (AttachedTransformation())
00229                 return AttachedTransformation()->MaxRetrievable();
00230         else
00231                 return CopyTo(TheBitBucket());
00232 }
00233 
00234 bool BufferedTransformation::AnyRetrievable() const
00235 {
00236         if (AttachedTransformation())
00237                 return AttachedTransformation()->AnyRetrievable();
00238         else
00239         {
00240                 byte b;
00241                 return Peek(b) != 0;
00242         }
00243 }
00244 
00245 unsigned int BufferedTransformation::Get(byte &outByte)
00246 {
00247         if (AttachedTransformation())
00248                 return AttachedTransformation()->Get(outByte);
00249         else
00250                 return Get(&outByte, 1);
00251 }
00252 
00253 unsigned int BufferedTransformation::Get(byte *outString, unsigned int getMax)
00254 {
00255         if (AttachedTransformation())
00256                 return AttachedTransformation()->Get(outString, getMax);
00257         else
00258         {
00259                 ArraySink arraySink(outString, getMax);
00260                 return TransferTo(arraySink, getMax);
00261         }
00262 }
00263 
00264 unsigned int BufferedTransformation::Peek(byte &outByte) const
00265 {
00266         if (AttachedTransformation())
00267                 return AttachedTransformation()->Peek(outByte);
00268         else
00269                 return Peek(&outByte, 1);
00270 }
00271 
00272 unsigned int BufferedTransformation::Peek(byte *outString, unsigned int peekMax) const
00273 {
00274         if (AttachedTransformation())
00275                 return AttachedTransformation()->Peek(outString, peekMax);
00276         else
00277         {
00278                 ArraySink arraySink(outString, peekMax);
00279                 return CopyTo(arraySink, peekMax);
00280         }
00281 }
00282 
00283 unsigned long BufferedTransformation::Skip(unsigned long skipMax)
00284 {
00285         if (AttachedTransformation())
00286                 return AttachedTransformation()->Skip(skipMax);
00287         else
00288                 return TransferTo(TheBitBucket(), skipMax);
00289 }
00290 
00291 unsigned long BufferedTransformation::TotalBytesRetrievable() const
00292 {
00293         if (AttachedTransformation())
00294                 return AttachedTransformation()->TotalBytesRetrievable();
00295         else
00296                 return MaxRetrievable();
00297 }
00298 
00299 unsigned int BufferedTransformation::NumberOfMessages() const
00300 {
00301         if (AttachedTransformation())
00302                 return AttachedTransformation()->NumberOfMessages();
00303         else
00304                 return CopyMessagesTo(TheBitBucket());
00305 }
00306 
00307 bool BufferedTransformation::AnyMessages() const
00308 {
00309         if (AttachedTransformation())
00310                 return AttachedTransformation()->AnyMessages();
00311         else
00312                 return NumberOfMessages() != 0;
00313 }
00314 
00315 bool BufferedTransformation::GetNextMessage()
00316 {
00317         if (AttachedTransformation())
00318                 return AttachedTransformation()->GetNextMessage();
00319         else
00320         {
00321                 assert(!AnyMessages());
00322                 return false;
00323         }
00324 }
00325 
00326 unsigned int BufferedTransformation::SkipMessages(unsigned int count)
00327 {
00328         if (AttachedTransformation())
00329                 return AttachedTransformation()->SkipMessages(count);
00330         else
00331                 return TransferMessagesTo(TheBitBucket(), count);
00332 }
00333 
00334 unsigned int BufferedTransformation::TransferMessagesTo2(BufferedTransformation &target, unsigned int &messageCount, const std::string &channel, bool blocking)
00335 {
00336         if (AttachedTransformation())
00337                 return AttachedTransformation()->TransferMessagesTo2(target, messageCount, channel, blocking);
00338         else
00339         {
00340                 unsigned int maxMessages = messageCount;
00341                 for (messageCount=0; messageCount < maxMessages && AnyMessages(); messageCount++)
00342                 {
00343                         unsigned int blockedBytes;
00344                         unsigned long transferedBytes;
00345 
00346                         while (AnyRetrievable())
00347                         {
00348                                 transferedBytes = ULONG_MAX;
00349                                 blockedBytes = TransferTo2(target, transferedBytes, channel, blocking);
00350                                 if (blockedBytes > 0)
00351                                         return blockedBytes;
00352                         }
00353 
00354                         if (target.ChannelMessageEnd(channel, GetAutoSignalPropagation(), blocking))
00355                                 return 1;
00356 
00357                         bool result = GetNextMessage();
00358                         assert(result);
00359                 }
00360                 return 0;
00361         }
00362 }
00363 
00364 unsigned int BufferedTransformation::CopyMessagesTo(BufferedTransformation &target, unsigned int count, const std::string &channel) const
00365 {
00366         if (AttachedTransformation())
00367                 return AttachedTransformation()->CopyMessagesTo(target, count, channel);
00368         else
00369                 return 0;
00370 }
00371 
00372 void BufferedTransformation::SkipAll()
00373 {
00374         if (AttachedTransformation())
00375                 AttachedTransformation()->SkipAll();
00376         else
00377         {
00378                 while (SkipMessages()) {}
00379                 while (Skip()) {}
00380         }
00381 }
00382 
00383 unsigned int BufferedTransformation::TransferAllTo2(BufferedTransformation &target, const std::string &channel, bool blocking)
00384 {
00385         if (AttachedTransformation())
00386                 return AttachedTransformation()->TransferAllTo2(target, channel, blocking);
00387         else
00388         {
00389                 assert(!NumberOfMessageSeries());
00390 
00391                 unsigned int messageCount;
00392                 do
00393                 {
00394                         messageCount = UINT_MAX;
00395                         unsigned int blockedBytes = TransferMessagesTo2(target, messageCount, channel, blocking);
00396                         if (blockedBytes)
00397                                 return blockedBytes;
00398                 }
00399                 while (messageCount != 0);
00400 
00401                 unsigned long byteCount;
00402                 do
00403                 {
00404                         byteCount = ULONG_MAX;
00405                         unsigned int blockedBytes = TransferTo2(target, byteCount, channel, blocking);
00406                         if (blockedBytes)
00407                                 return blockedBytes;
00408                 }
00409                 while (byteCount != 0);
00410 
00411                 return 0;
00412         }
00413 }
00414 
00415 void BufferedTransformation::CopyAllTo(BufferedTransformation &target, const std::string &channel) const
00416 {
00417         if (AttachedTransformation())
00418                 AttachedTransformation()->CopyAllTo(target, channel);
00419         else
00420         {
00421                 assert(!NumberOfMessageSeries());
00422                 while (CopyMessagesTo(target, UINT_MAX, channel)) {}
00423         }
00424 }
00425 
00426 void BufferedTransformation::SetRetrievalChannel(const std::string &channel)
00427 {
00428         if (AttachedTransformation())
00429                 AttachedTransformation()->SetRetrievalChannel(channel);
00430 }
00431 
00432 unsigned int BufferedTransformation::ChannelPutWord16(const std::string &channel, word16 value, ByteOrder order, bool blocking)
00433 {
00434         FixedSizeSecBlock<byte, 2> buf;
00435         PutWord(false, order, buf, value);
00436         return ChannelPut(channel, buf, 2, blocking);
00437 }
00438 
00439 unsigned int BufferedTransformation::ChannelPutWord32(const std::string &channel, word32 value, ByteOrder order, bool blocking)
00440 {
00441         FixedSizeSecBlock<byte, 4> buf;
00442         PutWord(false, order, buf, value);
00443         return ChannelPut(channel, buf, 4, blocking);
00444 }
00445 
00446 unsigned int BufferedTransformation::PutWord16(word16 value, ByteOrder order, bool blocking)
00447 {
00448         return ChannelPutWord16(NULL_CHANNEL, value, order, blocking);
00449 }
00450 
00451 unsigned int BufferedTransformation::PutWord32(word32 value, ByteOrder order, bool blocking)
00452 {
00453         return ChannelPutWord32(NULL_CHANNEL, value, order, blocking);
00454 }
00455 
00456 unsigned int BufferedTransformation::PeekWord16(word16 &value, ByteOrder order)
00457 {
00458         byte buf[2] = {0, 0};
00459         unsigned int len = Peek(buf, 2);
00460 
00461         if (order)
00462                 value = (buf[0] << 8) | buf[1];
00463         else
00464                 value = (buf[1] << 8) | buf[0];
00465 
00466         return len;
00467 }
00468 
00469 unsigned int BufferedTransformation::PeekWord32(word32 &value, ByteOrder order)
00470 {
00471         byte buf[4] = {0, 0, 0, 0};
00472         unsigned int len = Peek(buf, 4);
00473 
00474         if (order)
00475                 value = (buf[0] << 24) | (buf[1] << 16) | (buf[2] << 8) | buf [3];
00476         else
00477                 value = (buf[3] << 24) | (buf[2] << 16) | (buf[1] << 8) | buf [0];
00478 
00479         return len;
00480 }
00481 
00482 unsigned int BufferedTransformation::GetWord16(word16 &value, ByteOrder order)
00483 {
00484         return Skip(PeekWord16(value, order));
00485 }
00486 
00487 unsigned int BufferedTransformation::GetWord32(word32 &value, ByteOrder order)
00488 {
00489         return Skip(PeekWord32(value, order));
00490 }
00491 
00492 void BufferedTransformation::Attach(BufferedTransformation *newOut)
00493 {
00494         if (AttachedTransformation() && AttachedTransformation()->Attachable())
00495                 AttachedTransformation()->Attach(newOut);
00496         else
00497                 Detach(newOut);
00498 }
00499 
00500 void GeneratableCryptoMaterial::GenerateRandomWithKeySize(RandomNumberGenerator &rng, unsigned int keySize)
00501 {
00502         GenerateRandom(rng, MakeParameters("KeySize", (int)keySize));
00503 }
00504 
00505 BufferedTransformation * PK_Encryptor::CreateEncryptionFilter(RandomNumberGenerator &rng, BufferedTransformation *attachment) const
00506 {
00507         struct EncryptionFilter : public Unflushable<FilterWithInputQueue>
00508         {
00509                 // VC60 complains if this function is missing
00510                 EncryptionFilter(const EncryptionFilter &x) : Unflushable<FilterWithInputQueue>(NULL), m_rng(x.m_rng), m_encryptor(x.m_encryptor) {}
00511 
00512                 EncryptionFilter(RandomNumberGenerator &rng, const PK_Encryptor &encryptor, BufferedTransformation *attachment)
00513                         : Unflushable<FilterWithInputQueue>(attachment), m_rng(rng), m_encryptor(encryptor)
00514                 {
00515                 }
00516 
00517                 bool IsolatedMessageEnd(bool blocking)
00518                 {
00519                         switch (m_continueAt)
00520                         {
00521                         case 0:
00522                                 {
00523                                 unsigned int plaintextLength = m_inQueue.CurrentSize();
00524                                 m_ciphertextLength = m_encryptor.CiphertextLength(plaintextLength);
00525 
00526                                 SecByteBlock plaintext(plaintextLength);
00527                                 m_inQueue.Get(plaintext, plaintextLength);
00528                                 m_ciphertext.resize(m_ciphertextLength);
00529                                 m_encryptor.Encrypt(m_rng, plaintext, plaintextLength, m_ciphertext);
00530                                 }
00531 
00532                         case 1:
00533                                 if (!Output(1, m_ciphertext, m_ciphertextLength, 0, blocking))
00534                                         return false;
00535                         };
00536                         return true;
00537                 }
00538 
00539                 RandomNumberGenerator &m_rng;
00540                 const PK_Encryptor &m_encryptor;
00541                 unsigned int m_ciphertextLength;
00542                 SecByteBlock m_ciphertext;
00543         };
00544 
00545         return new EncryptionFilter(rng, *this, attachment);
00546 }
00547 
00548 BufferedTransformation * PK_Decryptor::CreateDecryptionFilter(RandomNumberGenerator &rng, BufferedTransformation *attachment) const
00549 {
00550         struct DecryptionFilter : public Unflushable<FilterWithInputQueue>
00551         {
00552                 // VC60 complains if this function is missing
00553                 DecryptionFilter(const DecryptionFilter &x) : Unflushable<FilterWithInputQueue>(NULL), m_rng(x.m_rng), m_decryptor(x.m_decryptor) {}
00554 
00555                 DecryptionFilter(RandomNumberGenerator &rng, const PK_Decryptor &decryptor, BufferedTransformation *attachment)
00556                         : Unflushable<FilterWithInputQueue>(attachment), m_rng(rng), m_decryptor(decryptor)
00557                 {
00558                 }
00559 
00560                 bool IsolatedMessageEnd(bool blocking)
00561                 {
00562                         switch (m_continueAt)
00563                         {
00564                         case 0:
00565                                 {
00566                                 unsigned int ciphertextLength = m_inQueue.CurrentSize();
00567                                 unsigned int maxPlaintextLength = m_decryptor.MaxPlaintextLength(ciphertextLength);
00568 
00569                                 SecByteBlock ciphertext(ciphertextLength);
00570                                 m_inQueue.Get(ciphertext, ciphertextLength);
00571                                 m_plaintext.resize(maxPlaintextLength);
00572                                 m_result = m_decryptor.Decrypt(m_rng, ciphertext, ciphertextLength, m_plaintext);
00573                                 if (!m_result.isValidCoding)
00574                                         throw InvalidCiphertext(m_decryptor.AlgorithmName() + ": invalid ciphertext");
00575                                 }
00576 
00577                         case 1:
00578                                 if (!Output(1, m_plaintext, m_result.messageLength, 0, blocking))
00579                                         return false;
00580                         }
00581                         return true;
00582                 }
00583 
00584                 RandomNumberGenerator &m_rng;
00585                 const PK_Decryptor &m_decryptor;
00586                 SecByteBlock m_plaintext;
00587                 DecodingResult m_result;
00588         };
00589 
00590         return new DecryptionFilter(rng, *this, attachment);
00591 }
00592 
00593 unsigned int PK_FixedLengthCryptoSystem::MaxPlaintextLength(unsigned int cipherTextLength) const
00594 {
00595         if (cipherTextLength == FixedCiphertextLength())
00596                 return FixedMaxPlaintextLength();
00597         else
00598                 return 0;
00599 }
00600 
00601 unsigned int PK_FixedLengthCryptoSystem::CiphertextLength(unsigned int plainTextLength) const
00602 {
00603         if (plainTextLength <= FixedMaxPlaintextLength())
00604                 return FixedCiphertextLength();
00605         else
00606                 return 0;
00607 }
00608 
00609 DecodingResult PK_FixedLengthDecryptor::Decrypt(RandomNumberGenerator &rng, const byte *cipherText, unsigned int cipherTextLength, byte *plainText) const
00610 {
00611         if (cipherTextLength != FixedCiphertextLength())
00612                 return DecodingResult();
00613 
00614         return FixedLengthDecrypt(rng, cipherText, plainText);
00615 }
00616 
00617 unsigned int PK_Signer::Sign(RandomNumberGenerator &rng, PK_MessageAccumulator *messageAccumulator, byte *signature) const
00618 {
00619         std::auto_ptr<PK_MessageAccumulator> m(messageAccumulator);
00620         return SignAndRestart(rng, *m, signature, false);
00621 }
00622 
00623 unsigned int PK_Signer::SignMessage(RandomNumberGenerator &rng, const byte *message, unsigned int messageLen, byte *signature) const
00624 {
00625         std::auto_ptr<PK_MessageAccumulator> m(NewSignatureAccumulator(rng));
00626         m->Update(message, messageLen);
00627         return SignAndRestart(rng, *m, signature, false);
00628 }
00629 
00630 unsigned int PK_Signer::SignMessageWithRecovery(RandomNumberGenerator &rng, const byte *recoverableMessage, unsigned int recoverableMessageLength, 
00631         const byte *nonrecoverableMessage, unsigned int nonrecoverableMessageLength, byte *signature) const
00632 {
00633         std::auto_ptr<PK_MessageAccumulator> m(NewSignatureAccumulator(rng));
00634         InputRecoverableMessage(*m, recoverableMessage, recoverableMessageLength);
00635         m->Update(nonrecoverableMessage, nonrecoverableMessageLength);
00636         return SignAndRestart(rng, *m, signature, false);
00637 }
00638 
00639 bool PK_Verifier::Verify(PK_MessageAccumulator *messageAccumulator) const
00640 {
00641         std::auto_ptr<PK_MessageAccumulator> m(messageAccumulator);
00642         return VerifyAndRestart(*m);
00643 }
00644 
00645 bool PK_Verifier::VerifyMessage(const byte *message, unsigned int messageLen, const byte *signature, unsigned int signatureLength) const
00646 {
00647         std::auto_ptr<PK_MessageAccumulator> m(NewVerificationAccumulator());
00648         InputSignature(*m, signature, signatureLength);
00649         m->Update(message, messageLen);
00650         return VerifyAndRestart(*m);
00651 }
00652 
00653 DecodingResult PK_Verifier::Recover(byte *recoveredMessage, PK_MessageAccumulator *messageAccumulator) const
00654 {
00655         std::auto_ptr<PK_MessageAccumulator> m(messageAccumulator);
00656         return RecoverAndRestart(recoveredMessage, *m);
00657 }
00658 
00659 DecodingResult PK_Verifier::RecoverMessage(byte *recoveredMessage, 
00660         const byte *nonrecoverableMessage, unsigned int nonrecoverableMessageLength, 
00661         const byte *signature, unsigned int signatureLength) const
00662 {
00663         std::auto_ptr<PK_MessageAccumulator> m(NewVerificationAccumulator());
00664         InputSignature(*m, signature, signatureLength);
00665         m->Update(nonrecoverableMessage, nonrecoverableMessageLength);
00666         return RecoverAndRestart(recoveredMessage, *m);
00667 }
00668 
00669 void SimpleKeyAgreementDomain::GenerateKeyPair(RandomNumberGenerator &rng, byte *privateKey, byte *publicKey) const
00670 {
00671         GeneratePrivateKey(rng, privateKey);
00672         GeneratePublicKey(rng, privateKey, publicKey);
00673 }
00674 
00675 void AuthenticatedKeyAgreementDomain::GenerateStaticKeyPair(RandomNumberGenerator &rng, byte *privateKey, byte *publicKey) const
00676 {
00677         GenerateStaticPrivateKey(rng, privateKey);
00678         GenerateStaticPublicKey(rng, privateKey, publicKey);
00679 }
00680 
00681 void AuthenticatedKeyAgreementDomain::GenerateEphemeralKeyPair(RandomNumberGenerator &rng, byte *privateKey, byte *publicKey) const
00682 {
00683         GenerateEphemeralPrivateKey(rng, privateKey);
00684         GenerateEphemeralPublicKey(rng, privateKey, publicKey);
00685 }
00686 
00687 NAMESPACE_END

Generated on Mon Apr 19 18:12:29 2004 for Crypto++ by doxygen 1.3.6-20040222