My implementation looks like this (at least part of it does):
OpenSSL_add_all_ciphers();
EVP_CIPHER_CTX ctx;
EVP_CIPHER_CTX_init(&ctx);
const EVP_CIPHER *cipher = EVP_get_cipherbyname(qPrintable(algorithm));
if (!cipher) {
EVP_cleanup();
}
EVP_EncryptInit_ex(&ctx, cipher, NULL, (const unsigned char*)key.constData(), (const unsigned char*)iv.constData());
int outlen, inlen, tmplen;
inlen = inba.count();
// outbuf = inlen+cipher_block-1
if (!EVP_EncryptUpdate(&ctx, (unsigned char*)outbuf.data(), &outlen, (const unsigned char*)inba.constData(), inlen)) {
}
if (!EVP_EncryptFinal_ex(&ctx, ((unsigned char*)outbuf.data())+outlen, &tmplen)) {
}
outlen += tmplen;
EVP_CIPHER_CTX_cleanup(&ctx);
EVP_cleanup();
outbuf.resize(outlen);
return outbuf;
}
QByteArray qEncrypt(const QString &algorithm, const QByteArray &inba, const QByteArray &key, const QByteArray &iv) {
OpenSSL_add_all_ciphers();
EVP_CIPHER_CTX ctx;
EVP_CIPHER_CTX_init(&ctx);
const EVP_CIPHER *cipher = EVP_get_cipherbyname(qPrintable(algorithm));
if (!cipher) {
EVP_cleanup();
return QByteArray();
}
EVP_EncryptInit_ex(&ctx, cipher, NULL, (const unsigned char*)key.constData(), (const unsigned char*)iv.constData());
int outlen, inlen, tmplen;
inlen = inba.count();
QByteArray outbuf(inlen+EVP_MAX_BLOCK_LENGTH, 0);
// outbuf = inlen+cipher_block-1
if (!EVP_EncryptUpdate(&ctx, (unsigned char*)outbuf.data(), &outlen, (const unsigned char*)inba.constData(), inlen)) {
return QByteArray();
}
if (!EVP_EncryptFinal_ex(&ctx, ((unsigned char*)outbuf.data())+outlen, &tmplen)) {
return QByteArray();
}
outlen += tmplen;
EVP_CIPHER_CTX_cleanup(&ctx);
EVP_cleanup();
outbuf.resize(outlen);
return outbuf;
}
To copy to clipboard, switch view to plain text mode
I also have a class that does the encryption that can be called like so:
QwwCipher ciph("aes-128-cbc");
ciph.setKey("0123456789ABCDEF");
ciph.setIv("12345678");
ciph.setInput(&inba);
ciph.setOutput(&outba);
ciph.encryptAll();
qDebug() << outba.toBase64().constData();
QwwCipher ciph("aes-128-cbc");
ciph.setKey("0123456789ABCDEF");
ciph.setIv("12345678");
QByteArray inba("text to be encrypted");
QByteArray outba;
ciph.setInput(&inba);
ciph.setOutput(&outba);
ciph.encryptAll();
qDebug() << outba.toBase64().constData();
To copy to clipboard, switch view to plain text mode
or so (asynchronous encryption):
...
QwwCipher ciph("des-ofb");
ciph.setKey("01234567");
ciph.setIv("12345678");
ciph.setInput(&inba);
QFile file("cipher.bin");
ciph.setOutput(&file);
ciph.encrypt();
QObject::connect(&ciph,
SIGNAL(done
()),
&app,
SLOT(quit
()));
return app.exec();
QCoreApplication app(argc, argv);
...
QwwCipher ciph("des-ofb");
ciph.setKey("01234567");
ciph.setIv("12345678");
QByteArray inba("text to be encrypted");
ciph.setInput(&inba);
QFile file("cipher.bin");
ciph.setOutput(&file);
ciph.encrypt();
QObject::connect(&ciph, SIGNAL(done()), &app, SLOT(quit()));
return app.exec();
To copy to clipboard, switch view to plain text mode
Your implementation is incorrectly assuming that the ciphertext is readable. You can't just dump it to stderr, first \0 byte will terminate the printout and a lack of \0 at the end will append garbage to printout. Also you are returning a pointer to a local stack based variable.
Bookmarks