OpenSSL一共實(shí)現(xiàn)了4種非對(duì)稱(chēng)加密算法,包括DH算法,、RSA算法、DSA算法和橢圓曲線算法(EC),。DH算法一般用戶(hù)密鑰交換。RSA算法既可
以用于密鑰交換,,也可以用于數(shù)字簽名,,當(dāng)然,,如果你能夠忍受其緩慢的速度,那么也可以用于數(shù)據(jù)加密,。DSA算法則一般只用于數(shù)字簽名,。我想用RSA作為例
子來(lái)描述Openssl公鑰算法的實(shí)現(xiàn)過(guò)程。
/*****************RSA Code******************/
#include <stdio.h>
#include <string.h>
#include <openssl/evp.h>
#include <openssl/rsa.h>
void print(const char *promptStr,unsigned char *data,int len)
{
int i;
printf("\n===%s[長(zhǎng)度=%d字節(jié)]======\n",promptStr,len);
for(i = 0; i < len; i++) printf("%02x", data[i]);
printf("\n=======================\n");
}
//作為一條規(guī)則,,使用靜態(tài)調(diào)用,,
static void prime_generate_status(int code, int arg, void *cb_arg)
{
if( arg>0 && (arg%10) )
{
return;
}
if (code == 0)
printf("\n找到潛在素?cái)?shù): %d", (arg + 1));
else if (code != 1)
printf("\n成功獲取一個(gè)素?cái)?shù)!");
}
//如果成功返回包裝了RSA參數(shù)的EVP_PKEY,否則返回NULL
EVP_PKEY* getRSA()
{
EVP_PKEY* pkey=NULL;
RSA* rsa=RSA_generate_key(1024,//公鑰模長(zhǎng)
RSA_3, //第三個(gè)費(fèi)爾瑪數(shù)作為公鑰中的e
prime_generate_status, //素?cái)?shù)產(chǎn)生狀態(tài)的回調(diào)函數(shù)
NULL //傳給回調(diào)函數(shù)的參數(shù)
);
if(NULL==rsa)
{
printf("生成RSA密鑰對(duì)失敗\n");
return NULL;
}
//隱藏RSA密鑰抵御定時(shí)攻擊
RSA_blinding_on(rsa,NULL);
printf("\n成功生成RSA密鑰對(duì)\n");
pkey=EVP_PKEY_new();
if(NULL==pkey)
{
printf("EVP_PKEY_new failed\n");
RSA_free(rsa);
return NULL;
}
//將rsa對(duì)象賦給EVP_PKEY結(jié)構(gòu)
EVP_PKEY_assign_RSA(pkey,rsa);
return pkey;
}
void main(int argc, char *argv[])
{
RSA* rsa=NULL;
EVP_PKEY* pkey=NULL;
int len=-1;
//要加密的明文
char plainText[]="[For test to public/private key encryption/decryption]";
char encData[512];//加密后的數(shù)據(jù)
char decData[512];//解密后的數(shù)據(jù),,應(yīng)該和明文相同
OpenSSL_add_all_ciphers();
pkey=getRSA();
if(pkey==NULL)
{
return;
}
len=EVP_PKEY_encrypt(
encData, //加密后的數(shù)據(jù)
plainText, //明文
sizeof(plainText), //明文長(zhǎng)度
pkey //公鑰
);
if(len==-1)
{
printf("EVP_PKEY_encrypt加密失敗\n");
exit(-1);
}
print("加密后的數(shù)據(jù)",encData,len);
//解密
len=EVP_PKEY_decrypt(
decData, //解密后的數(shù)據(jù)
encData, //密文
len, //密文長(zhǎng)度
pkey //私鑰(事實(shí)上,,公私鑰都在此數(shù)據(jù)結(jié)構(gòu)中)
);
if(len==-1)
{
printf("EVP_PKEY_decrypt解密失敗\n");
return;
}
print("解密后的數(shù)據(jù)",decData,len);
printf("\n明文是:[長(zhǎng)度=%d字節(jié)]:%s\n",len,decData);
//釋放EVP_PKEY對(duì)象,其關(guān)聯(lián)的RSA對(duì)象也被同時(shí)釋放,。
EVP_PKEY_free(pkey);
getchar();
}
RSA 算法的一個(gè)重要環(huán)節(jié)是生成密鑰對(duì),。
在運(yùn)行程序之前你必須做好前期準(zhǔn)備,否則無(wú)法調(diào)試,,這里我們要用到Openssl的EVP,,我們需要在工程中引入要用到的鏈接庫(kù)文件
libeay32.lib,(創(chuàng)建好一個(gè)工程后Project->Settings->Link在Object/Library
Moduls:中添加libeay32.lib,并且要保證libeay32.dll已經(jīng)放在了System32目錄下了),這些都完成后你就可以直接運(yùn)
行程序了,。
|