如何使用AES(openssl)加密数据
How to encrypt data using AES(openssl)?
我需要加密我的数据,所以我使用AES加密它们。我可以加密短数据。但我需要加密长数据,这行不通。我能做些什么来解决这个问题?这是我的代码。
#include "cooloi_aes.h"
CooloiAES::CooloiAES()
: MSG_LEN(0)
{
for(int i = 0; i < AES_BLOCK_SIZE; i++)
{
key[i] = 32 + i;
}
}
CooloiAES::~CooloiAES()
{
}
std::string CooloiAES::aes_encrypt(std::string msg)
{
int i = msg.size() / 1024;
MSG_LEN = ( i + 1 ) * 1024;
char in[MSG_LEN];
char out[MSG_LEN];
memset((char*)in,0,MSG_LEN);
memset((char*)out,0,MSG_LEN);
strncpy((char*)in,msg.c_str(),msg.size());
unsigned char iv[AES_BLOCK_SIZE];
for(int j = 0; j < AES_BLOCK_SIZE; ++j)
{
iv[j] = 0;
}
AES_KEY aes;
if(AES_set_encrypt_key((unsigned char*)key, 128, &aes) < 0)
{
return NULL;
}
int len = msg.size();
AES_cbc_encrypt((unsigned char*)in,(unsigned char*)out,len,&aes,iv,AES_ENCRYPT);
std::string encrypt_msg(&out[0],&out[MSG_LEN+16]);
std::cout << std::endl;
return encrypt_msg;
}
std::string CooloiAES::aes_decrypt(std::string msg)
{
MSG_LEN = msg.size();
char in[MSG_LEN];
char out[MSG_LEN+16];
memset((char*)in,0,MSG_LEN);
memset((char*)out,0,MSG_LEN+16);
strncpy((char*)in,msg.c_str(),msg.size());
std::cout << std::endl;
unsigned char iv[AES_BLOCK_SIZE];
for(int j = 0; j < AES_BLOCK_SIZE; ++j)
{
iv[j] = 0;
}
AES_KEY aes;
if(AES_set_decrypt_key((unsigned char*)key, 128, &aes) < 0)
{
return NULL;
}
int len = msg.size();
AES_cbc_encrypt((unsigned char*)in,(unsigned char*)out,len,&aes,iv,AES_DECRYPT);
std::string decrypt_msg = out;
return decrypt_msg;
}
当我加密96字节的数据时,它将失败。我得到这个错误"在抛出'std::length_error'实例后调用终止"(): basic_string: _S_create".但我不认为这个字符串超过最大长度。我不知道哪里错了
除了填充问题和处理二进制时strncpy和(char *)构造函数的使用之外,您的加密/解密没有任何错误。如果最后一个数据块不适合所有16字节,则不应该加密。因此,您应该实现自己的填充或不加密最后一小块,您的代码将简化为:
string aes_encrypt/decrypt(string msg)
{
unsigned char out[msg.size()];
memcpy((char*)out,msg.data(),msg.size());
AES_cbc_encrypt((unsigned char *)msg.data(),out,msg.size()/16*16,&aes,iv,AES_ENCRYPT **or** AES_DECRYPT);
return string((char *)out, msg.size());
}
总结:
- 不要在binary 中使用strncpy()
- 不要使用
string s = binary_char_massive;
构造器 - 不加密数据的最后一部分,如果它不适合块大小或自己填充它
- 使用EVP_* openssl API,如果有可能在未来的算法改变
AES通常通过将数据分解为16字节块来加密数据。如果最后一个块不是16字节长,则填充为16字节。Wiki文章:
http://en.wikipedia.org/wiki/Advanced_Encryption_Standard http://en.wikipedia.org/wiki/AES_implementations相关文章:
- 加密在 Windows、C++ 和 Java 中传输中的数据
- 在 EAX 模式下加密数据时"program has stopped working"
- 我们是否可以使用 SEAL / PySEAL 库对加密数据执行除法操作Microsoft?
- 如何将加密数据从C 传输到Java
- 在一个应用中使用 AES 加密数据,并在另一个 C++ WinCrypt 中解密
- 使用Windows AES加密提供商在C 中解密C#加密数据
- 使用 libconfig 存储加密数据
- 如何在C++中加密数据并在PHP中解密
- 在libgcrypt的Crypto++中解密加密数据的步骤
- 使用 Boost::asio::async_send_to 发送加密数据时出错
- 使用 Win32/MFC 加密数据
- 将加密数据存储在控制台应用程序中
- 如何在C++中加密数据文件
- 在Java中使用RSA公钥加密数据,在Crypto++中解密
- Python的M2Crypto.EVP.Cipher无法使用C++加密数据
- 如何使用AES(openssl)加密数据
- OpenSSL:尝试使用通过握手获得的密钥材料来本地加密数据
- c++ AES如何逐块加密数据
- 生成大小不是16的倍数的加密数据
- 加密数据中的Null字符