c - 在 C 中使用 openssl 解密时出现分段错误
问题描述
我正在尝试解密使用 AES 192 ECB 加密的消息并遇到分段错误,并且不知道该往哪里看。我知道 ECB 是不安全的,但它不适用于生产应用程序。
- 我已经检查了我的 readFile 方法,它可以工作(我将密码写回文件并使用 diff 工具检查)
- 密钥长度为 24 字节(使用 ls 和 hexdump 检查)
- 据我所知,ECB 没有 IV-Vector,所以我将其设置为 NULL
- 对于解密部分,我使用https://wiki.openssl.org/index.php/EVP_Symmetric_Encryption_and_Decryption上的示例开始
- 我认为问题出在 EVP_DecryptUpdate
- 我试图用 gdb 进一步追踪它,但我没有这方面的经验,只得到了
0x00007ffff798089d 在?? () 来自 /usr/lib64/libcrypto.so.1.1
感谢您的时间。
#include <stdio.h>
#include <stdlib.h>
#include <openssl/err.h>
#include <openssl/evp.h>
#include <openssl/conf.h>
#include <openssl/sha.h>
int readFile(char* filename, unsigned char** data){
FILE *fp;
unsigned char* tmp;
long fsize = 0;
if ((fp = fopen(filename, "rb")) == NULL){
perror(filename);
exit(EXIT_FAILURE);
}
// get length by going to end of the file and checking the position.
// Rewinding to start afterwards
fseek(fp, 0, SEEK_END);
fsize = ftell(fp);
rewind(fp);
if((tmp = malloc(fsize))){
fread(tmp, fsize, 1, fp);
fclose(fp);
} else {
fclose(fp);
perror(filename);
exit(EXIT_FAILURE);
}
*data = tmp;
return fsize;
}
int decryptAES192ECB(unsigned char *ciphertext, int ciphertext_len, unsigned char *key, unsigned char *plaintext){
EVP_CIPHER_CTX *ctx;
int len;
int plaintext_len;
/* Create and initialise the context */
if(!(ctx = EVP_CIPHER_CTX_new()))
handleErrors();
/*
* Initialise the decryption operation. IMPORTANT - ensure you use a key
* and IV size appropriate for your cipher
*/
if(1 != EVP_DecryptInit_ex(ctx, EVP_aes_192_ecb(), NULL, key, NULL))
handleErrors();
/*
* Provide the message to be decrypted, and obtain the plaintext output.
* EVP_DecryptUpdate can be called multiple times if necessary.
*/
if(1 != EVP_DecryptUpdate(ctx, plaintext, &len, ciphertext, ciphertext_len))
handleErrors();
plaintext_len = len;
/*
* Finalise the decryption. Further plaintext bytes may be written at
* this stage.
*/
if(1 != EVP_DecryptFinal_ex(ctx, plaintext + len, &len))
handleErrors();
plaintext_len += len;
/* Clean up */
EVP_CIPHER_CTX_free(ctx);
return plaintext_len;
}
int main(int argc, char **argv){
unsigned char *source_cipher, *source_key;
long source_cipher_len = readFile("source-cipher.bin", &source_cipher);
long source_key_len = readFile("source-key.bin", &source_key);
unsigned char* plaintext;
decryptAES192ECB(source_cipher, source_cipher_len, source_key, plaintext);
return 0;
}
编辑:解决方案是添加
unsigned char* plaintext = malloc(source_cipher_len);
在decryptAES192ECB调用之前到main方法并删除
handleErrors();
在 EVP_DecryptFinal_ex 调用后,解密AES192ECB。
解决方案
这是由热门评论开始的。
你的回答解决了它。EVP_DecryptFinal_ex 上的错误是因为密钥错误 随意发表您的评论作为答案!– 阿克雷特
plaintext
在 中未初始化main
。
我试过:
unsigned char *plaintext = "abcdef";
这效果不太好,我怀疑这plaintext
是一个输出缓冲区,所以:
unsigned char *plaintext = malloc(1000000);
让你过去的段错误。
但是,它会为 生成一个错误返回EVP_DecryptFinal_ex
,即进度 [某种 ;-)]。
请注意,我只是将 [dummy] ascii 文本放入两个.bin
文件中,因此了解这两个输入文件中实际应该包含的内容可能会有所帮助。有了正确/真实的数据,我认为事情会奏效[如上所述]。
推荐阅读
- javascript - 如何在数组[]中显示对象
- arrays - 最小化 (A[i]*B[i]) 的最大值
- sql-server - SQL:遍历文件夹并发送带有附件和存档文件的电子邮件。执行 sp_send_dbmail
- python - AttributeError:“NoneType”对象没有属性“通道”
- laravel - Laravel 身份验证中间件
- r - 如何在 R 中以有组织的方式读取 csv 列
- wordpress - 如何从插件和其他来源捆绑 WordPress JS 和 CSS 文件
- javascript - 为什么我不能在 numbro.js 中设置语言?
- python - Python 3.4.2,从文本文件中读取并相应打印
- android - 如何获取我的应用程序 APK 的 URL?(Google Play 保护申诉)