This is intresting, it seems to me that this should not work that way. I will try to explain how to reproduce this. Consider the following sample:

#include <stdio.h>
#include <cryptopp/dll.h>
using namespace CryptoPP;
#define EXTERN_CIPHERS
int main()
{
   AutoSeededRandomPool rng;
   unsigned char m_Key[DES::DEFAULT_KEYLENGTH];
   rng.GenerateBlock(m_Key,sizeof(m_Key));

   unsigned char m_iv[DES::BLOCKSIZE];
   rng.GenerateBlock(m_iv,sizeof(m_iv));

#ifdef EXTERN_CIPHERS
DES::Encryption cipher(m_Key,DES::DEFAULT_KEYLENGTH);
StreamTransformation* cipherEncrypt = new ECB_Mode_ExternalCipher::Encryption(cipher,m_iv);
StreamTransformation* cipherDecrypt = new ECB_Mode_ExternalCipher::Decryption(cipher,m_iv);
#else
StreamTransformation* cipherEncrypt = new ECB_Mode<DES>::Encryption(m_Key,DES::DEFAULT_KEYLENGTH,m_iv);
StreamTransformation* cipherDecrypt = new ECB_Mode<DES>::Decryption(m_Key,DES::DEFAULT_KEYLENGTH,m_iv);
#endif


StreamTransformationFilter STFilterEncrypt(*cipherEncrypt,NULL);
StreamTransformationFilter STFilterDecrypt(*cipherDecrypt,NULL);
unsigned char plaintext[] = "1234567";
unsigned char ciphertext[sizeof(plaintext)+DES::BLOCKSIZE]={0};
unsigned char out_plaintext[sizeof(ciphertext)*3]={0};



STFilterEncrypt.PutMessageEnd(plaintext,sizeof(plaintext)); int ciphersize = STFilterEncrypt.MaxRetrievable(); if(ciphersize>sizeof(ciphertext))printf("ERROR: buffer overrun\n"); STFilterEncrypt.Get(ciphertext,ciphersize);

STFilterDecrypt.PutMessageEnd(ciphertext,ciphersize);
int out_plainsize = STFilterDecrypt.MaxRetrievable();
if(out_plainsize>sizeof(out_plaintext))printf("ERROR: buffer overrun\n");
STFilterDecrypt.Get(out_plaintext,out_plainsize);
if(!memcmp(plaintext,out_plaintext,sizeof(plaintext)))
printf("Decryption OK\n");
else printf("Decryption FAILED\n");



delete cipherEncrypt; delete cipherDecrypt;

   return 0;
}

------------------------------------------------------------------------------------------------------------------------------------------------------------

Here I used a macro to switch beetween externals/internal chipers, just undef the EXTERN_CIPHERS macro to switch.
When working with internal chiper all is correct.
External chipers by definition should work too, but when the encryption mode is: ECB or CBC (chipertext size multiple to block length) the result is not correct.
For the code to work in ECB or CBC mode the following must be done:


DES::Encryption cipher(m_Key,DES::DEFAULT_KEYLENGTH);
here ---> DES::Decryption cipher_dec(m_Key,DES::DEFAULT_KEYLENGTH);
StreamTransformation* cipherEncrypt = new ECB_Mode_ExternalCipher::Encryption(cipher,m_iv);
StreamTransformation* cipherDecrypt = new ECB_Mode_ExternalCipher::Decryption(cipher_dec,m_iv);


While for other modes no changes is required.



Reply via email to