调用openssl中的evp.h加密解密中出的问题
就是我先把原文读到一个数组in中,再使用EVP_EncryptUpdate()加密,使用的是EVP_aes_128_ecb加密算法,将加密后文件读入密文文件,再调用EVP...
就是我先把原文读到一个数组in中,再使用EVP_EncryptUpdate()加密,使用的是EVP_aes_128_ecb加密算法,将加密后文件读入密文文件,再调用EVP_EncryptFinal()将剩余密文读入密文文件。当原文文件大小不是16的整数倍时,更够加密解密成功。但当原文大小为16的整数倍时,保存后的密文大小不是16的整数倍,更不能解密了。我调查很久不知道哪出问题了,猜测是EVP_EncryptUpdate()或EVP_EncryptFinal()中有问题。 下面附上我的代码:
#include<stdio.h>
#include<openssl/evp.h>
#define IN
#define OUT
////////////////////////////////////////////////////////////////////////////////////////
int AesEncryptFile (IN char * szSrc,
IN char * szTarget ,
IN unsigned char * key,
IN int iType)
{
FILE *p = fopen(szSrc,"rb");
if(p==NULL)
{
printf("Open file failed!");
fclose(p);
return 0;
}
fseek(p,0,SEEK_END);
long position;
position=ftell(p); //获取文件大小
if(position==-1L)
{
printf("ftell failed");
fclose(p);
return 0;
}
fseek(p,0,SEEK_SET); //将文件指针指向开头
////////////////////////////////////////////////////////////////////
printf("%ld\n",position);
FILE *q = fopen(szTarget,"w+");
if(q==NULL)
{
printf("Open file failed!");
fclose(p);
fclose(q);
return 0;
}
///////////////////////////////////////////////////////////////////
//// 将src中原文读入数组in中
long isSuccess;
unsigned char *in;
in = new unsigned char [position];
isSuccess = fread(in,1,position,p);
if(isSuccess!=position)
{
printf("fread failed");
delete in;
return 0;
}
//////////////////////////////////////////////////////////////////
//初始化EVP_CIPHER_CTX,密码上下文关系句柄
EVP_CIPHER_CTX ctx;
EVP_CIPHER_CTX_init(&ctx);
//////////////////////////////////////////////////////////////////
unsigned char *out;
out = new unsigned char [100000];
int outl;
int outltmp;
int i=0;
for(i=0;i<16;i++)
{
keyA[i]=0;
}
i=0;
while(key!=NULL)
{
keyA[i++] = *key++;
}*/
isSuccess=EVP_EncryptInit_ex(&ctx,EVP_aes_128_ecb(),NULL,key,NULL); //key为16字节
if(!isSuccess)
{
printf("EVP_EncryptInit_ex() failed!");
fclose(p);
fclose(q);
EVP_CIPHER_CTX_cleanup(&ctx);
delete out;
delete in;
return 0;
}
isSuccess = EVP_EncryptUpdate(&ctx,out,&outl,in,position);
if(!isSuccess)
{
printf("EVP_EncryptUpdate() failed!");
fclose(p);
fclose(q);
EVP_CIPHER_CTX_cleanup(&ctx);
delete out;
delete in;
return 0;
}
isSuccess = EVP_EncryptFinal(&ctx,out+outl,&outltmp);
if(!isSuccess)
{
printf("EVP_EncryptFinal() failed!");
fclose(p);
fclose(q);
EVP_CIPHER_CTX_cleanup(&ctx);
delete out;
delete in;
return 0;
}
outl = outl + outltmp;
fwrite(out,1,outl,q);
//加密结束
printf("加密结束");
fclose(p);
fclose(q);
delete out;
delete in;
EVP_CIPHER_CTX_cleanup(&ctx);
return 0;
}
解密函数的代码贴不上了。。加密函数里的错误应该是在开始加密到写入密文文件之间发生的。。。请大家帮忙看看。。谢谢 展开
#include<stdio.h>
#include<openssl/evp.h>
#define IN
#define OUT
////////////////////////////////////////////////////////////////////////////////////////
int AesEncryptFile (IN char * szSrc,
IN char * szTarget ,
IN unsigned char * key,
IN int iType)
{
FILE *p = fopen(szSrc,"rb");
if(p==NULL)
{
printf("Open file failed!");
fclose(p);
return 0;
}
fseek(p,0,SEEK_END);
long position;
position=ftell(p); //获取文件大小
if(position==-1L)
{
printf("ftell failed");
fclose(p);
return 0;
}
fseek(p,0,SEEK_SET); //将文件指针指向开头
////////////////////////////////////////////////////////////////////
printf("%ld\n",position);
FILE *q = fopen(szTarget,"w+");
if(q==NULL)
{
printf("Open file failed!");
fclose(p);
fclose(q);
return 0;
}
///////////////////////////////////////////////////////////////////
//// 将src中原文读入数组in中
long isSuccess;
unsigned char *in;
in = new unsigned char [position];
isSuccess = fread(in,1,position,p);
if(isSuccess!=position)
{
printf("fread failed");
delete in;
return 0;
}
//////////////////////////////////////////////////////////////////
//初始化EVP_CIPHER_CTX,密码上下文关系句柄
EVP_CIPHER_CTX ctx;
EVP_CIPHER_CTX_init(&ctx);
//////////////////////////////////////////////////////////////////
unsigned char *out;
out = new unsigned char [100000];
int outl;
int outltmp;
int i=0;
for(i=0;i<16;i++)
{
keyA[i]=0;
}
i=0;
while(key!=NULL)
{
keyA[i++] = *key++;
}*/
isSuccess=EVP_EncryptInit_ex(&ctx,EVP_aes_128_ecb(),NULL,key,NULL); //key为16字节
if(!isSuccess)
{
printf("EVP_EncryptInit_ex() failed!");
fclose(p);
fclose(q);
EVP_CIPHER_CTX_cleanup(&ctx);
delete out;
delete in;
return 0;
}
isSuccess = EVP_EncryptUpdate(&ctx,out,&outl,in,position);
if(!isSuccess)
{
printf("EVP_EncryptUpdate() failed!");
fclose(p);
fclose(q);
EVP_CIPHER_CTX_cleanup(&ctx);
delete out;
delete in;
return 0;
}
isSuccess = EVP_EncryptFinal(&ctx,out+outl,&outltmp);
if(!isSuccess)
{
printf("EVP_EncryptFinal() failed!");
fclose(p);
fclose(q);
EVP_CIPHER_CTX_cleanup(&ctx);
delete out;
delete in;
return 0;
}
outl = outl + outltmp;
fwrite(out,1,outl,q);
//加密结束
printf("加密结束");
fclose(p);
fclose(q);
delete out;
delete in;
EVP_CIPHER_CTX_cleanup(&ctx);
return 0;
}
解密函数的代码贴不上了。。加密函数里的错误应该是在开始加密到写入密文文件之间发生的。。。请大家帮忙看看。。谢谢 展开
1个回答
2011-05-04
展开全部
我没用过这个语言,所以解答的可能不太正确。以下我只是建议
(以下是基于我编程时的经验说的,有可能由于语言上的差异造成疑问。)
首先问几个问题:"将src中原文读入数组in中"文件应该是字节集吧你用数组做什么呢?
这些是你的代码中的一些涉及到16的代码:
1、//key为16字节
2、for(i=0;i<16;i++)
这个可能是算法上的问题。至于写入代码,没看到什么引起异常的东西。
解决:(假设以上判断正确,因为你的程序只要不加密16的整数倍大小文件就没错。)你可以试试一个双向判断加密时如果正好是16的整数倍在文件头或文件尾加入某些多余数据。解密时分析是否曾经加入过数据并在解密前将文件还原[请注意很可能解密时也会出错,所以建议你想办法在解密后再还原文件。(如果可以的话。)]
这只代表我个人观点 我不是专家我也只是建议……
(以下是基于我编程时的经验说的,有可能由于语言上的差异造成疑问。)
首先问几个问题:"将src中原文读入数组in中"文件应该是字节集吧你用数组做什么呢?
这些是你的代码中的一些涉及到16的代码:
1、//key为16字节
2、for(i=0;i<16;i++)
这个可能是算法上的问题。至于写入代码,没看到什么引起异常的东西。
解决:(假设以上判断正确,因为你的程序只要不加密16的整数倍大小文件就没错。)你可以试试一个双向判断加密时如果正好是16的整数倍在文件头或文件尾加入某些多余数据。解密时分析是否曾经加入过数据并在解密前将文件还原[请注意很可能解密时也会出错,所以建议你想办法在解密后再还原文件。(如果可以的话。)]
这只代表我个人观点 我不是专家我也只是建议……
参考资料: 我自己猜出来的
推荐律师服务:
若未解决您的问题,请您详细描述您的问题,通过百度律临进行免费专业咨询