Search code examples
c++encryptionopensslblowfish

How to encrypt a message to Blowfish using OpenSSL?


I need to get the Blowfish encryption with OpenSSL library. But something does not work.
What am I doing wrong? I'm trying to do it this way:

#include <iostream>
#include <openssl/blowfish.h>
#include "OpenSSL_Base64.h"
#include "Base64.h"

using namespace std;

int main()
{
    unsigned char ciphertext[BF_BLOCK];
    unsigned char plaintext[BF_BLOCK];

    // blowfish key
    const unsigned char *key = (const unsigned char*)"topsecret";
    //unsigned char key_data[10] = "topsecret";
    BF_KEY bfKey;
    BF_set_key(&bfKey, 10, key);

    /* Open SSL's Blowfish ECB encrypt/decrypt function only handles 8 bytes of data */
    char a_str[] = "8 Bytes";//{8, ,B,y,t,e,s,\0}
    char *arr_ptr = &a_str[0];

    //unsigned char* data_to_encrypt = (unsigned char*)"8 Bytes"; // 7 + \0

    BF_ecb_encrypt((unsigned char*)arr_ptr, ciphertext, &bfKey, BF_ENCRYPT);

    unsigned char* ret = new unsigned char[BF_BLOCK + 1];
    strcpy((char*)ret, (char*)ciphertext);
    ret[BF_BLOCK + 1] = '\0';

    char* base_enc = OpenSSL_Base64::Base64Encode((char*)ret, strlen((char*)ret));

    cout << base_enc << endl;

    cin.get();

    return 0;
}

But I get the wrong output:

fy7maf+FhmbM

I checked with it:

http://sladex.org/blowfish.js/

It should be: fEcC5/EKDVY=

Base64:

http://pastebin.com/wNLZQxQT


Solution

  • The problem is that ret may contain a null byte, encryption is 8-bit byte based, not character based and will contain values fromthe full range 0-255. strlen will terminate on the first null byte it finds giving a length that is smaller then the full length of the encrypted data.

    Note: When using encryption pay strice attention to providing the exact correct length parameters and data, do not rely on padding. (The exception is input data to encryption functions that support data padding such as PKCS#7 (née PKCS#5) padding.