The problem turned out to be in CryptStreamBuffer::GetNextChar() and was fixed by replacing:
// If there are no more bytes currently available then pump the source if (m_StreamTransformationFilter->MaxRetrievable() == 0) { m_Source->Pump(1024); } With the following which ewnsure that the last few bytes are processed: // If there are no more bytes currently available from the filter then // pump the source. if (m_StreamTransformationFilter->MaxRetrievable() == 0) { if (0 == m_Source->Pump(1024)) { // This seems to be required to ensure the final bytes are readable // from the filter. m_StreamTransformationFilter- >ChannelMessageEnd(CryptoPP::DEFAULT_CHANNEL); } } Tom On Jun 16, 6:46 pm, Don <donfai...@gmail.com> wrote: > here is your answer. > It has to do with the cipher that you picked. > > "ECB Mode is electronic codebook. ECB was originally specified by NIST > in FIPS 81. The standard, issued in 1981, only offers confidentiality. > Other modes, such as CCM and GCM, offer authenticated encryption which > places an integrity assurance over the encrpyted data. > > <B>ECB mode does not use an IV, and the plain text must be padded to > the block size of the cipher</B>. For additional information on this > mode, see Block Cipher Modes of Operation. " > > On Jun 16, 12:05 pm, Don <donfai...@gmail.com> wrote: > > > Hi > > I compiled your code and your stopping on the last BLOCKSIZE boundary. > > Bet your losing the remainder and only getting even BLOCKSIZE out put. > > > In other words your not losing 16 bytes your losing the last < 16 > > bytes. > > > don > > > I will see if I can find out why. > > > On Jun 11, 10:54 am, Tom <thw...@ntlworld.com> wrote: > > > > Hi, > > > > To answer my own previous question (http://groups.google.com/group/ > > > cryptopp-users/browse_thread/thread/721dbd6fa5992a57) I wrote the code > > > given at the end of this post. > > > > However it appears that DecryptFile() is not attempting to decrypt the > > > last 16 bytes (block size) of the encrypted file. Can anybody tell me > > > what I am doing wrong? > > > > Yours truly, > > > > Tom > > > > -------------------------------------------------------------------------------- > > > > // Runtime Includes > > > #include <iostream> > > > > // Crypto++ Includes > > > #include "aes.h" > > > #include "modes.h" // xxx_Mode< > > > > #include "filters.h" // StringSource and > > > // StreamTransformation > > > #include "files.h" > > > > using namespace std; > > > > class CryptStreamBuffer: public std::streambuf { > > > > public: > > > > CryptStreamBuffer(istream& encryptedInput, > > > CryptoPP::StreamTransformation& c); > > > > CryptStreamBuffer(ostream& encryptedOutput, > > > CryptoPP::StreamTransformation& c); > > > > protected: > > > virtual int_type overflow(int_type ch = traits_type::eof()); > > > > virtual int_type uflow(); > > > > virtual int_type underflow(); > > > > virtual int_type pbackfail(int_type ch); > > > > virtual int sync(); > > > > private: > > > int GetNextChar(); > > > > int m_NextChar; // Buffered character > > > > CryptoPP::StreamTransformationFilter* > > > m_StreamTransformationFilter; > > > > CryptoPP::FileSource* m_Source; > > > > CryptoPP::FileSink* m_Sink; > > > > }; // class CryptStreamBuffer > > > > CryptStreamBuffer::CryptStreamBuffer(istream& encryptedInput, > > > CryptoPP::StreamTransformation& c) : > > > m_NextChar(traits_type::eof()), > > > m_StreamTransformationFilter(0), > > > m_Source(0), > > > m_Sink(0) { > > > > m_StreamTransformationFilter = new > > > CryptoPP::StreamTransformationFilter(c); > > > m_Source = new CryptoPP::FileSource(encryptedInput, false, > > > m_StreamTransformationFilter); > > > > } > > > > CryptStreamBuffer::CryptStreamBuffer(ostream& encryptedOutput, > > > CryptoPP::StreamTransformation& c) : > > > m_NextChar(traits_type::eof()), > > > m_StreamTransformationFilter(0), > > > m_Source(0), > > > m_Sink(0) { > > > > m_Sink = new CryptoPP::FileSink(encryptedOutput); > > > m_StreamTransformationFilter = new > > > CryptoPP::StreamTransformationFilter(c, m_Sink); > > > > } > > > > CryptStreamBuffer::int_type CryptStreamBuffer::overflow(int_type ch) { > > > > return m_StreamTransformationFilter->Put((byte)ch); > > > > } > > > > CryptStreamBuffer::int_type CryptStreamBuffer::uflow() { > > > > int_type result = GetNextChar(); > > > > // Reset the buffered character > > > m_NextChar = traits_type::eof(); > > > > return result; > > > > } > > > > CryptStreamBuffer::int_type CryptStreamBuffer::underflow() { > > > > return GetNextChar(); > > > > } > > > > CryptStreamBuffer::int_type CryptStreamBuffer::pbackfail(int_type ch) > > > { > > > > return traits_type::eof(); > > > > } > > > > int CryptStreamBuffer::sync() { > > > > if (m_Sink) { > > > m_StreamTransformationFilter->MessageEnd(); > > > } > > > > } > > > > int CryptStreamBuffer::GetNextChar() { > > > > // If we have a buffered character do nothing > > > if (m_NextChar != traits_type::eof()) { > > > return m_NextChar; > > > } > > > > // If there are no more bytes currently available then pump the > > > source > > > if (m_StreamTransformationFilter->MaxRetrievable() == 0) { > > > m_Source->Pump(1024); > > > } > > > > // Retrieve the next byte > > > byte nextByte; > > > size_t noBytes = m_StreamTransformationFilter->Get(nextByte); > > > if (0 == noBytes) { > > > return traits_type::eof(); > > > } > > > > // Buffer up the next character > > > m_NextChar = nextByte; > > > > return m_NextChar; > > > > } > > > > void InitKey(byte key[]) { > > > > key[0] = -62; > > > key[1] = 102; > > > key[2] = 78; > > > key[3] = 75; > > > key[4] = -96; > > > key[5] = 125; > > > key[6] = 66; > > > key[7] = 125; > > > key[8] = -95; > > > key[9] = -66; > > > key[10] = 114; > > > key[11] = 22; > > > key[12] = 48; > > > key[13] = 111; > > > key[14] = -51; > > > key[15] = 112; > > > > } > > > > void DecryptFile(const char* sourceFileName, const char* destFileName) > > > { > > > > ifstream ifs(sourceFileName, ios::in | ios::binary); > > > ofstream ofs(destFileName, ios::out | ios::binary); > > > > byte key[CryptoPP::AES::DEFAULT_KEYLENGTH]; > > > InitKey(key); > > > CryptoPP::ECB_Mode<CryptoPP::AES>::Decryption decryptor(key, > > > sizeof(key)); > > > > if (ifs) { > > > if (ofs) { > > > CryptStreamBuffer cryptBuf(ifs, decryptor); > > > std::istream decrypt(&cryptBuf); > > > > int c; > > > while (EOF != (c = decrypt.get())) { > > > ofs << (char)c; > > > } > > > ofs.flush(); > > > } > > > else { > > > std::cerr << "Failed to open file '" << destFileName << > > > "'." << endl; > > > } > > > } > > > else { > > > std::cerr << "Failed to open file '" << sourceFileName << "'." > > > << endl; > > > } > > > > } > > > > void EncryptFile(const char* sourceFileName, const char* destFileName) > > > { > > > > ifstream ifs(sourceFileName, ios::in | ios::binary); > > > ofstream ofs(destFileName, ios::out | ios::binary); > > > > byte key[CryptoPP::AES::DEFAULT_KEYLENGTH]; > > > InitKey(key); > > > > CryptoPP::ECB_Mode<CryptoPP::AES>::Encryption encryptor(key, > > > sizeof(key)); > > > > if (ifs) { > > > if (ofs) { > > > CryptStreamBuffer cryptBuf(ofs, encryptor); > > > std::ostream encrypt(&cryptBuf); > > > > int c; > > > while (EOF != (c = ifs.get())) { > > > encrypt << (char)c; > > > } > > > encrypt.flush(); > > > } > > > else { > > > std::cerr << "Failed to open file '" << destFileName << > > > "'." << endl; > > > } > > > } > > > else { > > > std::cerr << "Failed to open file '" << sourceFileName << "'." > > > << endl; > > > } > > > > } > > > > int main(int argc, char* argv[]) > > > { > > > EncryptFile(argv[1], "encrypted.out"); > > > DecryptFile("encrypted.out", "decrypted.out"); > > > return 0; > > > > } > > > > --------------------------------------------------------------------------------- > > > Hide quoted text - > > > - Show quoted text - -- You received this message because you are subscribed to the "Crypto++ Users" Google Group. To unsubscribe, send an email to cryptopp-users-unsubscr...@googlegroups.com. More information about Crypto++ and this group is available at http://www.cryptopp.com.