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

randpool.cpp

00001 // randpool.cpp - written and placed in the public domain by Wei Dai 00002 // The algorithm in this module comes from PGP's randpool.c 00003 00004 #include "pch.h" 00005 00006 #ifndef CRYPTOPP_IMPORTS 00007 00008 #include "randpool.h" 00009 #include "mdc.h" 00010 #include "sha.h" 00011 #include "modes.h" 00012 00013 NAMESPACE_BEGIN(CryptoPP) 00014 00015 typedef MDC<SHA> RandomPoolCipher; 00016 00017 RandomPool::RandomPool(unsigned int poolSize) 00018 : pool(poolSize), key(RandomPoolCipher::DEFAULT_KEYLENGTH) 00019 { 00020 assert(poolSize > key.size()); 00021 00022 addPos=0; 00023 getPos=poolSize; 00024 memset(pool, 0, poolSize); 00025 memset(key, 0, key.size()); 00026 } 00027 00028 void RandomPool::Stir() 00029 { 00030 CFB_Mode<RandomPoolCipher>::Encryption cipher; 00031 00032 for (int i=0; i<2; i++) 00033 { 00034 cipher.SetKeyWithIV(key, key.size(), pool.end()-cipher.IVSize()); 00035 cipher.ProcessString(pool, pool.size()); 00036 memcpy(key, pool, key.size()); 00037 } 00038 00039 addPos = 0; 00040 getPos = key.size(); 00041 } 00042 00043 unsigned int RandomPool::Put2(const byte *inString, unsigned int length, int messageEnd, bool blocking) 00044 { 00045 unsigned t; 00046 00047 while (length > (t = pool.size() - addPos)) 00048 { 00049 xorbuf(pool+addPos, inString, t); 00050 inString += t; 00051 length -= t; 00052 Stir(); 00053 } 00054 00055 if (length) 00056 { 00057 xorbuf(pool+addPos, inString, length); 00058 addPos += length; 00059 getPos = pool.size(); // Force stir on get 00060 } 00061 00062 return 0; 00063 } 00064 00065 unsigned int RandomPool::TransferTo2(BufferedTransformation &target, unsigned long &transferBytes, const std::string &channel, bool blocking) 00066 { 00067 if (!blocking) 00068 throw NotImplemented("RandomPool: nonblocking transfer is not implemented by this object"); 00069 00070 unsigned int t; 00071 unsigned long size = transferBytes; 00072 00073 while (size > (t = pool.size() - getPos)) 00074 { 00075 target.ChannelPut(channel, pool+getPos, t); 00076 size -= t; 00077 Stir(); 00078 } 00079 00080 if (size) 00081 { 00082 target.ChannelPut(channel, pool+getPos, size); 00083 getPos += size; 00084 } 00085 00086 return 0; 00087 } 00088 00089 byte RandomPool::GenerateByte() 00090 { 00091 if (getPos == pool.size()) 00092 Stir(); 00093 00094 return pool[getPos++]; 00095 } 00096 00097 void RandomPool::GenerateBlock(byte *outString, unsigned int size) 00098 { 00099 ArraySink sink(outString, size); 00100 TransferTo(sink, size); 00101 } 00102 00103 NAMESPACE_END 00104 00105 #endif

Generated on Wed Jul 21 19:15:32 2004 for Crypto++ by doxygen 1.3.7-20040704