Search code examples
c#c++encryptionaes

C# AES Encryption in CFB Where Plaintext Length Equals Encrypted Length


I have an existing data format that has portions of it encrypted in what appears to be AES in CFB mode. The plaintext data length and the encrypted data length are the same.

In C#, pretty much every angle I've taken seems to expect the encrypted length to be a multiple of the block size... so I get an exception trying to decrypt the data.

In researching solutions, I've used Crypto++ and wrote a quick C++ app that successfully decrypts the data, so I'm pretty sure I'm using the right algorithm, key and IV. This works fine, but I'd like to keep everything inside C# if at all possible. Any suggestions?

Working C++ code below:

//define key
unsigned char key[16];
//populate key
//...


//define iv
unsigned char iv[16];
//populate iv
//...

std::ifstream inFile;

//open file
inFile.open("file.aes",ios::binary );

//get file size
inFile.seekg(0,ios::end);
int fileSize = (int) inFile.tellg();
inFile.seekg(offset, ios::beg);

//read/close file
char* inBytes = new char[fileSize];
inFile.read(inBytes,fileSize);
inFile.close();

//configure decryption
CFB_Mode<AES>::Decryption cfbDecryption(key, 16, iv);

//populate output bytes
char* outBytes = new char[fileSize];
cfbDecryption.ProcessData((byte*) outBytes,(byte*) inBytes,fileSize);

//open/write/close output file
std::ofstream outFile;
outFile.open("out.dec");
outFile.write(outBytes,fileSize);
outFile.close();

delete[] inBytes;

Solution

  • I revisited trying to use cryptlib and it solved my problem... code is below:

    using cryptlib;
    
    byte[] key = new byte[16] {...key bytes here...};
    
    byte[] iv =  new byte[16] {...iv bytes here...};
    
    byte[] enc;  //ciphertext bytes (i populated them from a filestream)
    
    crypt.Init();
    int cryptContext = crypt.CreateContext(crypt.UNUSED, crypt.ALGO_AES);
    crypt.SetAttribute(cryptContext, crypt.CTXINFO_MODE, crypt.MODE_CFB);
    crypt.SetAttributeString(cryptContext, crypt.CTXINFO_KEY, key, 0, 16);
    crypt.SetAttributeString(cryptContext, crypt.CTXINFO_IV, iv, 0, 16);
    crypt.Decrypt(cryptContext, enc);   //ciphertext bytes replaced with plaintext bytes
    crypt.DestroyContext(cryptContext);