为什么我的OpenSSL C++代码会创建二进制加密输出
Why does my OpenSSL C++ code create binary encryption output?
我正在尝试使用OpenSSL中的AES加密文件,然后将输出写入文件。但我得到了混乱的输出,有时可以破译,有时无法破译。
主要代码基于以下内容:https://github.com/shanet/Crypto-Example/blob/master/crypto-example.cpp
这是代码:
int Crypt::__aesEncrypt(const unsigned char *msg, size_t msgLen, unsigned char **encMsg) {
EVP_CIPHER_CTX *aesEncryptCtx = (EVP_CIPHER_CTX*)malloc(sizeof(EVP_CIPHER_CTX));
EVP_CIPHER_CTX_init(aesEncryptCtx);
unsigned char *aesKey = (unsigned char*)malloc(AES_KEYLEN/8);
unsigned char *aesIV = (unsigned char*)malloc(AES_KEYLEN/8);
unsigned char *aesPass = (unsigned char*)malloc(AES_KEYLEN/8);
unsigned char *aesSalt = (unsigned char*)malloc(8);
if(RAND_bytes(aesPass, AES_KEYLEN/8) == 0) {
return FAILURE;
}
if(RAND_bytes(aesSalt, 8) == 0) {
return FAILURE;
}
if(EVP_BytesToKey(EVP_aes_256_cbc(), EVP_sha1(), aesSalt, aesPass, AES_KEYLEN/8, AES_ROUNDS, aesKey, aesIV) == 0) {
return FAILURE;
}
strncpy((char*)aesKey, (const char*)"B374A26A71490437AA024E4FADD5B4AA", AES_KEYLEN/8);
strncpy((char*)aesIV, (const char*)"7E892875A52C59A3B588306B13C31FBD", AES_KEYLEN/16);
size_t blockLen = 0;
size_t encMsgLen = 0;
*encMsg = (unsigned char*)malloc(msgLen + AES_BLOCK_SIZE);
if(encMsg == NULL) return FAILURE;
if(!EVP_EncryptInit_ex(aesEncryptCtx, EVP_aes_256_cbc(), NULL, aesKey, aesIV)) {
return FAILURE;
}
if(!EVP_EncryptUpdate(aesEncryptCtx, *encMsg, (int*)&blockLen, (unsigned char*)msg, msgLen)) {
return FAILURE;
}
encMsgLen += blockLen;
if(!EVP_EncryptFinal_ex(aesEncryptCtx, *encMsg + encMsgLen, (int*)&blockLen)) {
return FAILURE;
}
EVP_CIPHER_CTX_cleanup(aesEncryptCtx);
free(aesEncryptCtx);
free(aesKey);
free(aesIV);
return encMsgLen + blockLen;
}
我是这样打电话的:
unsigned char *encMsg = NULL;
__aesEncrypt((const unsigned char*)decrypted_string.c_str(), decrypted_string.size(), &encMsg);
std::stringstream ss;
ss << encMsg;
//write ss to file...
谢谢。
实际上,我是您的代码所基于的示例的作者。正如WhozCraig在上面的评论中指出的那样,您正在使用stringstream
将加密消息写入文件。问题是加密的消息不是常规的ASCII字符串。它们是二进制数据(值大于127,因此需要无符号字符数组),二进制数据不能像ASCII字符串一样处理。
我不太喜欢C++,所以我会用fwrite
以C的方式将数据写入文件,但如果你想用C++的方式,我认为你在寻找ifstream
而不是stringstream
。
附带说明,我打赌这只是为了调试,但无论如何我都会指出这一点,只是为了确保:对AES密钥和IV(strncpy((char*)aesKey, (const char*)"B374A26A71490437AA024E4FADD5B4AA", AES_KEYLEN/8)
)进行硬编码完全违背了加密的目的。如果你想避免PBKDF(EVP_BytesToKey
),你可以使用RAND_Bytes
来获得AES密钥的随机数据。
相关文章:
- 对在不同二进制文件中创建的对象文件的依赖关系
- 创建二进制文件时出现问题
- 如何创建一个新的二进制文件并用常量值填充它?
- 如何创建属性存储二进制文件
- 创建二进制树时意外的segfault
- C++正在创建二进制搜索树:EXC_BAD_ACCESS错误.算法错误还是编码错误
- 正在读取由另一组代码c++创建的二进制文件
- g++ - 虚拟方法在生成的二进制中创建符号,我无法隐藏
- 无法使用CPU后端使用TensorFlow AOT编译创建最终二进制文件
- 二进制树类创建随机节点,断裂
- Cmake:创建二进制Foo 库libfoo
- 如何用空节点创建完整的二进制树
- 在Qt中创建二进制外部资源文件
- 无法从我创建的 c 二进制程序中删除记录
- 如何在OpenCV中创建二进制非灰度图像
- 创建二进制搜索树时出现分段故障问题
- 需要使用初学者逻辑创建C++二进制计算器
- 如何为虚拟机创建二进制文件
- 为什么我的OpenSSL C++代码会创建二进制加密输出
- 如何在c++中创建二进制持久连接?