GNUMessenger::CryptoManager Class Reference

The cryptography manager class. More...

#include <cryptography.h>

List of all members.

Public Member Functions

 CryptoManager (const string &pk)
 Default constructor.
CryptoSessioncreateSession ()
 The crypto factory.

Static Public Member Functions

byte * hash (const string &str, unsigned int &len, CryptDefines::Hashes type=CryptDefines::DefaultHash) throw (AlgoError)
 Generate a hash of the given std::string using the given hash type.
string encode (const SecByteBlock &array, CryptDefines::Encoding enc=CryptDefines::DefaultEncoder) throw (AlgoError)
 Encode a byte array.
string encode (const string &str, CryptDefines::Encoding enc=CryptDefines::DefaultEncoder)
byte * decode (const string &input, unsigned int &outLen, CryptDefines::Encoding enc) throw (AlgoError)
 Decode a string to byte array.
string hashEncode (const string &str, CryptDefines::Hashes type=CryptDefines::DefaultHash, CryptDefines::Encoding enc=CryptDefines::DefaultEncoder) throw (AlgoError)
 Hash and encode in one swoop.
byte * generateRandom (const unsigned int size) throw (RNGError)
 Generate a specified number of bytes using the OS supplied random number generator.
byte * encrypt (const SecByteBlock &data, const SecByteBlock &key, unsigned int &resultLen, const unsigned int blockSize=0, CryptDefines::BlockCipher cipher=CryptDefines::DefaultBC, CryptDefines::Mode mode=CryptDefines::DefaultMode) throw (RNGError, AlgoError, KeySizeError, BlockSizeError)
 Encrypt a data block with a key.
void encryptToFileWithHMAC (const string &filename, const SecByteBlock &data, const SecByteBlock &key, const unsigned int blockSize=0, CryptDefines::BlockCipher bc=CryptDefines::DefaultBC, CryptDefines::Mode mode=CryptDefines::DefaultMode, CryptDefines::Hashes hash=CryptDefines::DefaultHash) throw (RNGError, AlgoError, KeySizeError, BlockSizeError, IOError)
 Encrypt a data block with a key.
byte * compress (const SecByteBlock &data, unsigned int &resultLen, const unsigned int level=CryptDefines::DEFAULT_COMPRESS_LEVEL)
 Compress the data block with Zlib.
byte * decompress (const SecByteBlock &data, unsigned int &resultLen)
 Decompress the data block with Zlib.
byte * generateIV (const SecByteBlock &data, CryptDefines::Hashes hash=CryptDefines::DefaultHash)
 IV generation via hashing input data then XOR-ing it with itself.
unsigned int testRNG (const unsigned int insize) throw (RNGError)
bool encryptFile (const string &filename, const VBuffer &key, const string &data) throw (IOError)
string decryptFile (const string &filename, const VBuffer &key) throw (InvalidPassword, AuthFailed)
string hashEncode (const VBuffer &toHash, CryptDefines::Hashes hash=CryptDefines::DefaultHash, CryptDefines::Encoding enc=CryptDefines::DefaultEncoder)
VBuffer hash (const VBuffer &toHash, CryptDefines::Hashes hash=CryptDefines::DefaultHash)

Static Protected Member Functions

HashTransformation * getHash (CryptDefines::Hashes type) throw (AlgoError)
 This function is not a member function due to the problems with non-inline member templates.
SymmetricCipher * getEncryptor (CryptDefines::BlockCipher cipher, CryptDefines::Mode mode) throw (AlgoError)


Detailed Description

The cryptography manager class.

This class creates keys, encrypts, and decrypts data.

In other words, a dummied down interface to Crypto++.

This class is usually associated with an active Contact. The static hashing functions and disk i/o are used by the login/ contact loading class.

Author:
Jesse Lovelace

Definition at line 62 of file cryptography.h.


Member Function Documentation

byte * GNUMessenger::CryptoManager::compress const SecByteBlock &  data,
unsigned int &  resultLen,
const unsigned int  level = CryptDefines::DEFAULT_COMPRESS_LEVEL
[static]
 

Compress the data block with Zlib.

Parameters:
data Input data to compress.
resultLen A reference to the ending length.
level The compression level (higher takes longer and makes result smaller--hopefully).
Returns:
Byte array of resulting data.
Definition at line 230 of file cryptography.cpp.
00233 { 00234 ZlibCompressor z(NULL, level); 00235 z.Put(data, data.size()); 00236 z.MessageEnd(); 00237 00238 resultLen = z.MaxRetrievable(); 00239 byte * out = new byte[resultLen]; 00240 z.Get(out, z.MaxRetrievable()); 00241 00242 return out; 00243 }

byte* GNUMessenger::CryptoManager::decode const string &  input,
unsigned int &  outLen,
CryptDefines::Encoding  enc
throw (AlgoError) [static]
 

Decode a string to byte array.

Parameters:
input The input string to decode.
outLen The final length of the byte array. See decodeLength()
enc The decoder to use.
Returns:
A byte array of the decoded data, owned by the caller.

byte * GNUMessenger::CryptoManager::decompress const SecByteBlock &  data,
unsigned int &  resultLen
[static]
 

Decompress the data block with Zlib.

Parameters:
data Input data to compress.
resultLen A reference to the ending length.
Returns:
Byte array of resulting data.
Definition at line 245 of file cryptography.cpp.
00247 { 00248 ZlibDecompressor inflate; 00249 inflate.Put(data, data.size()); 00250 inflate.MessageEnd(); 00251 00252 resultLen = inflate.MaxRetrievable(); 00253 byte * out = new byte[resultLen]; 00254 inflate.Get(out, inflate.MaxRetrievable()); 00255 00256 return out; 00257 }

string GNUMessenger::CryptoManager::encode const SecByteBlock &  array,
CryptDefines::Encoding  enc = CryptDefines::DefaultEncoder
throw (AlgoError) [static]
 

Encode a byte array.

Parameters:
array The byte array to encode.
enc The encoder to use.
Returns:
A std::string object of the encoded data.
Exceptions:
AlgoError is the specified encoder is invalid.
Definition at line 298 of file cryptography.cpp.
00300 { 00301 string result; 00302 auto_ptr<SimpleProxyFilter> encoder; 00303 00304 switch (type) { // @todo This isn't optimal 00305 case(CryptDefines::Base64): 00306 encoder.reset(new Base64Encoder(new StringSink(result))); 00307 break; 00308 case(CryptDefines::Base32): 00309 encoder.reset(new Base32Encoder(new StringSink(result))); 00310 break; 00311 case(CryptDefines::Hex): 00312 encoder.reset(new HexEncoder(new StringSink(result))); 00313 break; 00314 default: throw AlgoError("No such encoding system."); 00315 } 00316 00317 encoder->Put(data, data.size()); 00318 encoder->MessageEnd(); 00319 return result; 00320 }

byte * GNUMessenger::CryptoManager::encrypt const SecByteBlock &  data,
const SecByteBlock &  key,
unsigned int &  resultLen,
const unsigned int  blockSize = 0,
CryptDefines::BlockCipher  cipher = CryptDefines::DefaultBC,
CryptDefines::Mode  mode = CryptDefines::DefaultMode
throw (RNGError, AlgoError, KeySizeError, BlockSizeError) [static]
 

Encrypt a data block with a key.

Generates a random IV for the block cipher.

Parameters:
data The data to encrypt.
key The key to encrypt with.
blockSize The size, in bytes, of a block for the ciper. 0 means default.
resultLen The length of the resulting byte array.
Exceptions:
RNGError The OS RNG failed to allocate the requested number of bytes.
AlgoError The specified algorithm is invalid.
KeySizeError The key size is invalid for the ciper.
BlockSizeError The block size is invalid for this ciper
Definition at line 259 of file cryptography.cpp.
00266 { 00267 00268 auto_ptr<SymmetricCipher> theCipher(getEncryptor(cipher,mode)); 00269 00270 if (!theCipher->IsValidKeyLength(key.size())) 00271 throw KeySizeError("Invalid key size for this cipher", 00272 theCipher->MinKeyLength(), 00273 theCipher->MaxKeyLength()); 00274 00275 if (theCipher->IVRequirement() == theCipher->RANDOM_IV) 00276 LOG_DEBUG("Requires random IV"); 00277 00278 SecByteBlock iv( 00279 generateIV( 00280 SecByteBlock( 00281 generateRandom(theCipher->MandatoryBlockSize()), 00282 theCipher->MandatoryBlockSize() 00283 ) 00284 ), 00285 theCipher->MandatoryBlockSize() 00286 ); 00287 00288 theCipher->SetKeyWithIV(key, key.size(), iv); 00289 ArraySink cipherText; 00290 00291 StreamTransformationFilter encryptor(*theCipher, &cipherText); 00292 encryptor.Put(data, data.size()); 00293 // input more plaintext here if needed 00294 encryptor.MessageEnd(); 00295 return NULL; 00296 }

bool GNUMessenger::CryptoManager::encryptFile const string &  filename,
const VBuffer key,
const string &  data
throw (IOError) [static]
 

Grow container to ciphertext size Definition at line 333 of file cryptography.cpp.

00335 { 00336 00337 // generating random seed for iv 00338 SecByteBlock ivSeed(CryptDefines::IV_SEED_LENGTH); 00339 SecByteBlock realIv(CryptDefines::IV_LENGTH); 00340 00341 AutoSeededRandomPool rng; 00342 rng.GenerateBlock(ivSeed, CryptDefines::IV_SEED_LENGTH); 00343 00344 //creating actual iv, thanks to denis bider for this method 00345 SecByteBlock ivHash(SHA256::DIGESTSIZE); 00346 SHA256().CalculateDigest(ivHash, ivSeed, CryptDefines::IV_SEED_LENGTH); 00347 00348 for (unsigned int i = 0; i != CryptDefines::IV_LENGTH; ++i) 00349 realIv[i] = ivHash[i] ^ ivHash[i+16]; 00350 00351 //compress 00352 ZlibCompressor z(NULL,9); 00353 z.Put((const unsigned char *)data.c_str(), 00354 static_cast<unsigned int>(data.length())); 00355 z.MessageEnd(); 00356 00357 SecByteBlock compressedPlainText(z.MaxRetrievable()); 00358 z.Get(compressedPlainText, compressedPlainText.size()); 00359 00360 //encrypting 00361 SecByteBlock cipherText(compressedPlainText.size()); 00362 00363 CBC_Mode<MARS>::Encryption enc(key.data(), key.size(), realIv.data()); 00364 StreamTransformationFilter encryptor(enc); 00365 encryptor.Put(compressedPlainText, compressedPlainText.size()); 00366 encryptor.MessageEnd(); 00367 00369 cipherText.CleanGrow(encryptor.MaxRetrievable()); 00370 encryptor.Get(cipherText, cipherText.size()); 00371 00372 // create HMAC 00373 SecByteBlock myMac(HMAC<SHA>::DIGESTSIZE); 00374 HMAC<SHA> themac(key.data(), key.size()); 00375 themac.Update(cipherText, cipherText.size()); 00376 themac.Final(myMac); 00377 00378 // setup output file and encode the file as base64 00379 try { 00380 Base64Encoder encoder(new FileSink(filename.c_str(), false)); 00381 encoder.Put(realIv, CryptDefines::IV_LENGTH); 00382 encoder.Put(cipherText, cipherText.size()); 00383 encoder.Put(myMac, HMAC<SHA>::DIGESTSIZE); 00384 encoder.MessageEnd(); 00385 00386 } catch(CryptoPP::Exception &e) { 00387 throw IOError(e.what()); 00388 } 00389 00390 return true; 00391 00392 }

void GNUMessenger::CryptoManager::encryptToFileWithHMAC const string &  filename,
const SecByteBlock &  data,
const SecByteBlock &  key,
const unsigned int  blockSize = 0,
CryptDefines::BlockCipher  bc = CryptDefines::DefaultBC,
CryptDefines::Mode  mode = CryptDefines::DefaultMode,
CryptDefines::Hashes  hash = CryptDefines::DefaultHash
throw (RNGError, AlgoError, KeySizeError, BlockSizeError, IOError) [static]
 

Encrypt a data block with a key.

Generates a random IV for the block cipher; a SHA.

Parameters:
data The data to encrypt.
key The key to encrypt with.
blockSize The size, in bytes, of a block for the ciper. 0 means default.
resultLen The length of the resulting byte array.
bc The block cipher algorithm to use.
mode The mode encryption mode to use.
hash The type of hash to use in the HMAC.
Exceptions:
RNGError The OS RNG failed to allocate the requested number of bytes.
AlgoError The specified algorithm is invalid.
KeySizeError The key size is invalid for the ciper.
BlockSizeError The block size is invalid for this ciper
IOError There was an error with the filesystem.

byte * GNUMessenger::CryptoManager::generateIV const SecByteBlock &  data,
CryptDefines::Hashes  hash = CryptDefines::DefaultHash
[static]
 

IV generation via hashing input data then XOR-ing it with itself.

This algorithm was sugguested by Denis Bider from the Crypto++ list.

Parameters:
data The data to be worked on.
type The type of hash algorithm to use.
Returns:
Byte array of the same size as initial data.
Definition at line 181 of file cryptography.cpp.

References getHash().

00183 { 00184 auto_ptr<HashTransformation> theHash(getHash(hash)); 00185 00186 byte * result = new byte[theHash->DigestSize()]; 00187 00188 SecByteBlock hashed(theHash->DigestSize()); 00189 theHash->CalculateDigest(hashed, data, data.size()); 00190 00191 // digestsize should always be 2a = b 00192 for (unsigned int i = 0; i < theHash->DigestSize() / 2; i++) 00193 result[i] = hashed[i] ^ hashed[i+ (theHash->DigestSize() / 2)]; 00194 00195 return result; 00196 }

Here is the call graph for this function:

byte * GNUMessenger::CryptoManager::generateRandom const unsigned int  size  )  throw (RNGError) [static]
 

Generate a specified number of bytes using the OS supplied random number generator.

Returns:
A byte array.
Exceptions:
RNGError The OS RNG can't get the required number of bytes.
Definition at line 213 of file cryptography.cpp.
00215 { 00216 00217 byte * result = new byte[size]; 00218 00219 AutoSeededRandomPool rng; 00220 try { 00221 rng.GenerateBlock(result, size); 00222 } catch (OS_RNG_Err &e) { 00223 delete [] result; 00224 throw RNGError(e.what()); 00225 } 00226 return result; 00227 00228 }

HashTransformation * GNUMessenger::CryptoManager::getHash CryptDefines::Hashes  type  )  throw (AlgoError) [static, protected]
 

This function is not a member function due to the problems with non-inline member templates.

Parameters:
The type of hash.
Returns:
HashTransformation pointer.
Exceptions:
AlgoError if algo is invalid.
Definition at line 143 of file cryptography.cpp.

Referenced by generateIV().

00145 { 00146 switch (type) 00147 { 00148 case(CryptDefines::SHA1): return new SHA(); 00149 case(CryptDefines::SHA_256): return new SHA256(); 00150 case(CryptDefines::SHA_384): return new SHA384(); 00151 case(CryptDefines::SHA_512): return new SHA512(); 00152 case(CryptDefines::MD_2): return new MD2(); 00153 case(CryptDefines::MD_5): return new MD5(); 00154 case(CryptDefines::HAVAL_3): return new HAVAL3(); 00155 case(CryptDefines::HAVAL_4): return new HAVAL4(); 00156 case(CryptDefines::HAVAL_5): return new HAVAL5(); 00157 case(CryptDefines::RIPEMD_160): return new RIPEMD160(); 00158 case(CryptDefines::_TIGER): return new Tiger(); 00159 #ifdef IS_LITTLE_ENDIAN 00160 case(CryptDefines::PANAMA_HASH): 00161 return new PanamaHash<LittleEndian>(); 00162 #else 00163 case(CryptDefines::PANAMA_HASH): 00164 return new PanamaHash<BigEndian>(); 00165 #endif 00166 default: throw AlgoError("Invalid Hash Algorithm."); 00167 } 00168 }

byte * GNUMessenger::CryptoManager::hash const string &  str,
unsigned int &  len,
CryptDefines::Hashes  type = CryptDefines::DefaultHash
throw (AlgoError) [static]
 

Generate a hash of the given std::string using the given hash type.

Parameters:
str The std::string to hash
type The hash algo to use.
len The length of the byte array generated.
Returns:
The byte array.
Exceptions:
AlgoError There was an error with the algorithm.
Definition at line 170 of file cryptography.cpp.
00172 { 00173 auto_ptr<HashTransformation> theHash(getHash(hashType)); 00174 00175 byte * result = new byte[theHash->DigestSize()]; 00176 theHash->CalculateDigest(result, (byte *)data.c_str(), data.length()); 00177 00178 return result; 00179 }

string GNUMessenger::CryptoManager::hashEncode const string &  str,
CryptDefines::Hashes  type = CryptDefines::DefaultHash,
CryptDefines::Encoding  enc = CryptDefines::DefaultEncoder
throw (AlgoError) [static]
 

Hash and encode in one swoop.


The documentation for this class was generated from the following files:
Generated on Tue Oct 5 14:41:51 2004 for GNU Messenger by doxygen 1.3.8