RSA的算法优化加速-OPENSSL库-中国剩余定理和模平方运算

实验环境:Kali虚拟机,OPENSSL库

实验原理:

中国剩余定理

模重复平方运算

RSA算法:

RSA算法给予一个十分简单的数论事实:将两个大素数想成十分容易,但是想要对其乘积进行因式分解却极其困难,因此可以将乘积公开作为加密秘钥。RSA算法主要包括:秘钥生成,加密过程和解密过程。

(1)加密过程。在秘钥生成过程中,首先生成两个大的质数(素数)p和q,令n=p*q;m=(p-1)*(q-1),选取较小的数e,使e 和m互质,即e和m的最大公约数为1,然后生成d,使d*emod m=1,最后丢弃P,q,m,则公钥为e,n,私钥为d和n.

(2) 加密过程。将明文x加密成密文y的计算公式为:x=y^d mod n。从公式可见,加密牵涉到明文和公钥。因此,密文即使被截获,也无法被解读。

(3) 解密过程。将密文y解密成明文x的计算公式为:x=y^d mod n。从公式可见,解密至牵涉到私钥和密文。因此,只要保管好私钥,不泄密,就可以放心地把密文和公钥公开。

实验要求:

使用中国剩余定理和模重复平方运算简化RSA的计算量,加速RSA的实现,使用时间戳函数记录两次的运行时间,进行对比分析

明文为 姓名+学号

使用中国剩余定理和模重复平方运算简化RSA的计算量,加快加解密的速度

使用时间戳函数记录两次的运行时间,进行对比

RSA密钥生成算法具体如下:

(1)随机选取两个素数,作为p和q.

(2)计算n=q*p,m=(q-1)*(p-1);

(3)随机选取e,使e 与m互质.

(4)利用扩展欧几里得算法,计算d使d*e mod m=1.

(5)得到公钥(e,n)和私钥(d,n)。

RSA加密算法具体如下:

(1)输入明文x(数字)

(2)利用模运算的性质,计算密文y=x^e mod n。

RSA解密算法具体如下:

(1)输入密文y(数字)。

(2)利用模运算的性质,计算密文x=y^d mod n。

实验思路:

我们已知RSA算法的安全性是基于大整数分解难题的,那么这也会意味着n=p*q的位数会特别长,假设p,q长度都是1024比特,那么n的长度会变成2048比特

那么在进行

C=M^e(mod n)  以及 M=C^d(mod n) 时的计算量会非常大

我们已知中国剩余定理的基本思路如下

接下来我们来进行优化

以解密过程为例

M=C ^d(mod n)
对于n而言,他是一个2048比特的数,使用中国剩余定理,m1=p,m2=q,m=m1*m2
对于d而言,可以把d变成d1( 其中d1=d-k*fai(p) ),因为根据欧拉定理可以推到结论的成立,推理过程如下所示:

对于c而言,可以把c变成c1(其中C1=c mod p),推理过程如下:

观察上式,结合数学中的二项式定理可以发现

除了第一项不含有p之外,其余每一项都含有p

然后根据同余的知识,含有p的每一项mod p之后都会变成0

所以化简步骤正确,上式成立

综上所述

通过c d n 都进行了化简,RSA的加解密速度将会大大提升

源代码展示:

#include<stdio.h>
#include <string.h>
#include<openssl/bn.h>
#define NBITS 256
void str_2_hex_str(char *dest, char *src)
{
    int size = strlen(src); 
    int i,j;

    for (i = 0, j = 0; i < size; i++) {
        sprintf(&dest[j], "%02X", src[i]);
        j+=2; 
    }
    dest[j] = '\0'; 
}
void printBN(char *msg,BIGNUM *a)
{
	char *number_str=BN_bn2hex(a);
	printf("%s %s\n",msg,number_str);
	OPENSSL_free(number_str); 
}
int main(){
char p1[33]="F7E75FDC469067FFDC4E847C51F452DF";
char res[32];
char data[64];
char p2[33]="F7E75FDC469067FFDC4E847C51F452DE";
char q1[33]="E85CED54AF57E53E092113E62F436F4F";
char q2[33]="E85CED54AF57E53E092113E62F436F4E";
char e1[33]="0D88C3";
char l[33]="00000000000000000000000000000001";
scanf("%s",data);
BN_hex2bn(&l,l);
str_2_hex_str(res,data);
BN_CTX *ctx =BN_CTX_new();
BIGNUM *p=BN_new();
BN_hex2bn(&p,p1);
BIGNUM *q=BN_new();
BN_hex2bn(&q,q1);
//p2=p1-1=fp
//q2=q2-1=fq
BIGNUM *P=BN_new();
BN_hex2bn(&P,p2);
BIGNUM *Q=BN_new();
BN_hex2bn(&Q,q2);
//mulity n =p*q
BIGNUM *n=BN_new();
BN_mul(n,p,q,ctx); 
//mulity fn=(p-1)*(q-1)
BIGNUM *fn=BN_new();
BN_mul(fn,P,Q,ctx);

BIGNUM *e=BN_new();
BN_hex2bn(&e,e1);
BIGNUM *d=BN_new();
//figure d which meet e*d=1 mod(fn)
BN_mod_inverse(d,e,fn,ctx);
//
BIGNUM *M=BN_new(); 
BN_hex2bn(&M,res); 
BIGNUM *c=BN_new();
//figure c which meet c=M^e mod n
//BN_mod_exp(c,M,e,n,ctx);
BIGNUM *m=BN_new();
//figure m which meet M=c^d mod n
//BN_mod_exp(m,c,d,n,ctx);
//定义可能用到的所有变量
BIGNUM *d1=BN_new();
BIGNUM *d2=BN_new();
BIGNUM *c1=BN_new();
BIGNUM *c2=BN_new();
BIGNUM *e11=BN_new();
BIGNUM *e12=BN_new();
BIGNUM *M1=BN_new();
BIGNUM *M2=BN_new();
BIGNUM *a1=BN_new();
BIGNUM *a2=BN_new();
BIGNUM *y1=BN_new();
BIGNUM *y2=BN_new();
//求出中国剩余定理所需要的所有变量
BN_mod_mul(d1,d,l,p,ctx);
BN_mod_mul(d2,d,l,q,ctx);
BN_mod_mul(c1,c,l,p,ctx);
BN_mod_mul(c2,c,l,q,ctx);
BN_mod_mul(e11,e,l,p,ctx);
BN_mod_mul(e12,e,l,q,ctx);
//this m means mingwen1
BN_mod_mul(M1,M,l,p,ctx);
BN_mod_mul(M2,M,l,q,ctx);

BN_mod_exp(a1,M1,e11,p,ctx);
BN_mod_exp(a2,M2,e12,q,ctx);
//figure out modular inverse 
//this process is about jiemi
BN_mod_inverse(y1,q,p,ctx);
BN_mod_inverse(y2,p,q,ctx);

BIGNUM *result=BN_new();
//result= a1*y1*q+a2*y2+p mod n根据中国剩余定理得出结果,并将结果存到result中
BIGNUM *result1=BN_new();
BIGNUM *result2=BN_new();
//result1=a1*y1*q;
//result2=a2*y2*p;
BIGNUM *result11=BN_new();
BIGNUM *result12=BN_new();
BN_mul(result11,a1,y1,ctx);
BN_mul(result12,a2,y2,ctx);

BN_mul(result1,result11,q,ctx);
BN_mul(result2,result12,p,ctx);

BN_add(result,result1,result2);

printBN("p:",p);
printBN("q:",q);
printBN("N:",n);
printBN("fai(n):",fn);
printBN("e:",e);
printBN("d:",d);
printBN("M:",M);
printBN("m^e mod n = \n",c);
printBN("c^d mod n = \n",m);
printf("result=",result);

}

运行结果:

运行结果和我那篇没有优化过的博客一样,这里因为隐私原因没有展示,那篇博客也没有展示最终的结果,大家自行运行就行了

中国剩余定理(CRT)在RSA中的应用:

快速乘法运算:在RSA算法中,明文和密文都是以大整数的形式存在。中国剩余定理允许我们把一个大整数分解成几个较小整数的乘积,然后分别对这些较小的数进行乘法运算,最后再将结果合并起来。这种方法可以显著提高乘法运算的速度。

模数分解:在RSA解密过程中,可以使用CRT将大模数n=p×q分解为两个较小的模数。这样,我们可以分别对其进行幂模运算,然后再利用CRT将结果合并回原始模数

减少计算量:由于分解之后的数通常比n小得多,使用CRT可以减少幂模运算的计算量,从而加快解密过程。

模重复平方运算(Modular Exponentiation)在RSA中的应用:

提高效率:模重复平方是一种高效的幂运算方法,特别是在模数很大的情况下。它通过将指数分解成二进制形式,并利用平方和减半的方式来减少必要的乘法次数。

简化实现:模重复平方提供了一种简单且高效的方式来实现幂模运算,这是RSA加密和解密过程中的核心步骤。

减少存储需求:由于模重复平方可以在每一步中只保存中间结果,它减少了在计算过程中对存储的需求。

防止溢出:在处理非常大的数时,模重复平方可以防止整数溢出的问题,因为每一步的计算都保持在模数的范围内。

优化作用:

加速运算:通过使用CRT和模重复平方,RSA算法的运算速度得到了显著提升,尤其是在解密过程中。

减少资源消耗:这两种方法减少了计算过程中所需的计算资源和存储资源。

提高安全性:优化算法的执行速度和效率,可以减少在实际应用中因性能问题而引入的潜在安全风险。

适应现代需求:随着数据量的增加和对加密速度要求的提高,这些优化方法使得RSA算法能够更好地适应现代加密需求。

实验中遇到的问题:

OPENSSL在编写程序时

1不允许一个大数和int类型的数做运算,就算不定义类型,比如直接拿大数减去一个数字,这个数字也会被系统默认为int类型,虽然在程序语法上可以通过,但是结果不对,会有语义错误

2不允许嵌套函数的出现,在编写程序时,为了减少变量的定义,我使用了嵌套函数,但是程序会报错,OPENSSL中不允许使用嵌套函数

实验感悟:

OPENSSL是一个功能很强大的库,但是在使用时会有点略显得不太容易上手

中国剩余定理和模重复平方运算对于RSA的加速作用很明显,尤其是当数据特别大的时候,计算量会大大的简化,比如中国剩余定理可以让1024bit的数变成512bit的数。

使用这两个定理可以实现对c d m e的优化,即最后的加解密过程都可以被优化。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值