RSA算法趣解及C实现(代码,实例,验证过程)
2014-07-21 19:46
459 查看
写在前面
RSA算法,在现代密码学中真的是算得上么么哒了。它是第一个既能用于数据加密也能用于数字签名的算法。它易于理解和操作,也很流行。算法的名字以发明者的名字命名:Ron Rivest, Adi Shamir 和Leonard Adleman。
一.算法简介(写得浅显易懂,基础理论请自己查询~)
1. 三个数, p, q, r,
其中 p, q 是两个相异的质数, r 是与 (p-1)(q-1) 互质的数
p, q, r 这三个数便是 private key
2. 找出 m, 使得 rm == 1 mod (p-1)(q-1)
这个 m 一定存在, 因为 r 与 (p-1)(q-1) 互质, 用辗转相除法就可以得到了
再来, 计算 n = pq
m, n 这两个数便是 public key
3. 加密过程是, 将a看成是一个大整数, 假设 a < n
如果 a >= n 的话, 就将 a 表成 s 进位 (s <= n, 通常取 s = 2^t), 即进行分组~
则每一位数均小於 n, 然後分段编码
接下来, 计算 b == a^m mod n, (0 <= b < n), b 就是编码後的数据。
4.解密过程呢,和加密算法一样,只是用到的密钥不同而已,若加密为公钥,这这一步就用私钥~
二、RSA 的安全性
RSA的安全性依赖于大数分解,但是否等同于大数分解一直未能得到理论上的证明,因为没有证明破解 RSA就一定需要作大数分解。假设存在一种无须分解大数的算法,那它肯定可以修改成为大数分解算法。目前, RSA 的一些变种算法已被证明等价于大数分解。不管怎样,分解n是最显然的攻击方法。现在,人们已能分解多个十进制位的大素数。因此,模数n 必须选大一些,因具体适用情况而定。
三、RSA的速度
由于进行的都是大数计算,使得RSA最快的情况也比DES慢上倍,无论是软件还是硬件实现。速度一直是RSA的缺陷。一般来说只用于少量数据加密。(这就是为什么要使用HASH,详情见我的文章——
HASH之于信息安全领域加解密算法)
四.C语言实现
#include <stdio.h>
#include <math.h>
//基于小 整数型的数据实例
//以 知道 p q e为基础,求d,从而实现plain to en
//判素数 p q,如果以前学过C的这儿就可以快乐的享用自己的成果了,不过再写一次也
//不麻烦,毕竟实现很简单
int Prime(int m){
int i,k;
if(m<2)
return 0;//1 是
k=(int)sqrt(m);
for(i=2;i<k;i++){
if(m%i==0)
return 1;//不是素数
}
return 0;//否则就是
}
//判断密钥与t是否互素
int judge_prime(int d,int t){
int a;
while(t){
a=d;
d=t;
t=a%t;
}
if(d==1)
return 0;// yes
else
return 1;//no
}
//求公玥
int get_publickey(int e,int t){
int d=1;
while(((d*e)%t)!=1){//笨方法,穷举
d++;
}
return d;
}
//加密过程:对明文求幂取余
int encrypt(int plain,int e,int n){
int r=1;
e+=1;
while(e!=1){
r*=plain;
r%=n;
e--;
}
return r;
}
int main (){
int p,q,n,t,e,d,plain,en,i,j;
printf("please input the p,q:\n");
for(i=1;i<5;i++){
scanf("%d%d",&p,&q);
if(Prime(p)||Prime(q))//其中有一个不成立,就重新输入
{
printf("p or q is not prime,please input again:\n");
}//if
else break;
}//for
if (i==5)
{printf("exiting...please try later~");
return 0;
}
n=p*q;
t=(p-1)*(q-1);
printf("please input the private key:\n");
for(j=0;j<5;j++){
scanf("%d",&d);
if(judge_prime(d,t)){
prntf("the key is not prime with the t,please input again:\n");
}//if
else break;
}//for
if (j==5)
{printf("exiting...please try later~");
return 0;
}
e=get_publickey(d,t);
printf("please input the plain you want to encrypt:");
scanf("%d",&plain);
en=encrypt(plain,e,n);
printf("%d is encrypted as %d\n",plain,en);
plain=encrypt(en,d,n);
printf("%d is decrypted as %d\n",en,plain);
return 1;
}
OK!
写在后面:
该算法不要只是过眼看看就走,要自己去亲自实现了才知道有没有,欢迎评论~
RSA算法,在现代密码学中真的是算得上么么哒了。它是第一个既能用于数据加密也能用于数字签名的算法。它易于理解和操作,也很流行。算法的名字以发明者的名字命名:Ron Rivest, Adi Shamir 和Leonard Adleman。
一.算法简介(写得浅显易懂,基础理论请自己查询~)
1. 三个数, p, q, r,
其中 p, q 是两个相异的质数, r 是与 (p-1)(q-1) 互质的数
p, q, r 这三个数便是 private key
2. 找出 m, 使得 rm == 1 mod (p-1)(q-1)
这个 m 一定存在, 因为 r 与 (p-1)(q-1) 互质, 用辗转相除法就可以得到了
再来, 计算 n = pq
m, n 这两个数便是 public key
3. 加密过程是, 将a看成是一个大整数, 假设 a < n
如果 a >= n 的话, 就将 a 表成 s 进位 (s <= n, 通常取 s = 2^t), 即进行分组~
则每一位数均小於 n, 然後分段编码
接下来, 计算 b == a^m mod n, (0 <= b < n), b 就是编码後的数据。
4.解密过程呢,和加密算法一样,只是用到的密钥不同而已,若加密为公钥,这这一步就用私钥~
二、RSA 的安全性
RSA的安全性依赖于大数分解,但是否等同于大数分解一直未能得到理论上的证明,因为没有证明破解 RSA就一定需要作大数分解。假设存在一种无须分解大数的算法,那它肯定可以修改成为大数分解算法。目前, RSA 的一些变种算法已被证明等价于大数分解。不管怎样,分解n是最显然的攻击方法。现在,人们已能分解多个十进制位的大素数。因此,模数n 必须选大一些,因具体适用情况而定。
三、RSA的速度
由于进行的都是大数计算,使得RSA最快的情况也比DES慢上倍,无论是软件还是硬件实现。速度一直是RSA的缺陷。一般来说只用于少量数据加密。(这就是为什么要使用HASH,详情见我的文章——
HASH之于信息安全领域加解密算法)
四.C语言实现
#include <stdio.h>
#include <math.h>
//基于小 整数型的数据实例
//以 知道 p q e为基础,求d,从而实现plain to en
//判素数 p q,如果以前学过C的这儿就可以快乐的享用自己的成果了,不过再写一次也
//不麻烦,毕竟实现很简单
int Prime(int m){
int i,k;
if(m<2)
return 0;//1 是
k=(int)sqrt(m);
for(i=2;i<k;i++){
if(m%i==0)
return 1;//不是素数
}
return 0;//否则就是
}
//判断密钥与t是否互素
int judge_prime(int d,int t){
int a;
while(t){
a=d;
d=t;
t=a%t;
}
if(d==1)
return 0;// yes
else
return 1;//no
}
//求公玥
int get_publickey(int e,int t){
int d=1;
while(((d*e)%t)!=1){//笨方法,穷举
d++;
}
return d;
}
//加密过程:对明文求幂取余
int encrypt(int plain,int e,int n){
int r=1;
e+=1;
while(e!=1){
r*=plain;
r%=n;
e--;
}
return r;
}
int main (){
int p,q,n,t,e,d,plain,en,i,j;
printf("please input the p,q:\n");
for(i=1;i<5;i++){
scanf("%d%d",&p,&q);
if(Prime(p)||Prime(q))//其中有一个不成立,就重新输入
{
printf("p or q is not prime,please input again:\n");
}//if
else break;
}//for
if (i==5)
{printf("exiting...please try later~");
return 0;
}
n=p*q;
t=(p-1)*(q-1);
printf("please input the private key:\n");
for(j=0;j<5;j++){
scanf("%d",&d);
if(judge_prime(d,t)){
prntf("the key is not prime with the t,please input again:\n");
}//if
else break;
}//for
if (j==5)
{printf("exiting...please try later~");
return 0;
}
e=get_publickey(d,t);
printf("please input the plain you want to encrypt:");
scanf("%d",&plain);
en=encrypt(plain,e,n);
printf("%d is encrypted as %d\n",plain,en);
plain=encrypt(en,d,n);
printf("%d is decrypted as %d\n",en,plain);
return 1;
}
OK!
写在后面:
该算法不要只是过眼看看就走,要自己去亲自实现了才知道有没有,欢迎评论~
相关文章推荐
- 使用Java实现的苹果IAP二次验证主要逻辑过程及原创代码
- Java实现多线程断点下载实例代码(下载过程中可以暂停)
- Ajax+Struts2实现验证码验证功能实例代码
- Struts2实现生成动态验证码并验证实例代码
- Ajax+Struts2实现验证码验证功能实例代码
- Js实现中国公民身份证号码有效性验证实例代码
- Qt连接数据库代码,按照工作要求实现数据库存储过程实例
- 基于jQuery实现的Ajax 验证用户名唯一性实例代码
- javascript实现文本框标签验证的实例代码
- angular实现form验证实例代码
- PHP实现阿里大鱼短信验证的实例代码
- 使用JS组件实现带ToolTip验证框的实例代码
- php实现验证码识别原理和程序代码实例
- php实现表单密码验证的代码实例
- 基于vue 实现token验证的实例代码
- 存储过程分页实例(含有分页代码asp)
- 简单SNMP管理程序的VC++代码实例实现
- 基于.Net平台应用程序唯一运行实例C#代码实现
- 代码实例之纯CSS代码实现翻页效果
- 简单SNMP管理程序的VC++代码实例实现