模重复平方计算法(C语言版本)
\quad R S A RSA RSA算法是 1978 1978 1978年由 R . R i v e s t R.Rivest R.Rivest、 A . S h a m i r A.Shamir A.Shamir和 L . A d l e m a n L.Adleman L.Adleman提出的一种用数论构造的、也是迄今为止理论上最为成熟完善的公钥密码密码体制,该体制已得到广泛的应用。
算法描述
1.密钥的产生
(1)选两个保密的大素数 p p p和 q q q;
(2)计算 n = p ∗ q n=p*q n=p∗q, ψ ( n ) = ( p − 1 ) ( q − 1 ) \psi(n)=(p-1)(q-1) ψ(n)=(p−1)(q−1), 其中 ψ ( n ) \psi(n) ψ(n)是 n n n的欧拉函数;
(3)选一整数 e e e,满足 1 < e < ψ ( n ) 1<e<\psi(n) 1<e<ψ(n),且 g c d ( ψ ( n ) , e ) = 1 gcd(\psi(n),e)=1 gcd(ψ(n),e)=1;
(4)计算
d
d
d满足:
d
e
≡
1
m
o
d
ψ
(
n
)
de\equiv1mod\psi(n)
de≡1modψ(n)
即
d
d
d是在
e
e
e在模
ψ
(
n
)
\psi(n)
ψ(n)下的乘法逆元;
(5)以{
e
e
e,
n
n
n}为公钥,{
d
d
d,
n
n
n}为公钥.
2.加密
\quad
加密时首先将明文比特串分组,使得每个分组对应的十进制小数小于
n
n
n, 对每个明文分组
m
m
m做加密运算:
c
≡
m
e
m
o
d
ψ
(
n
)
c\equiv m^emod\psi(n)
c≡memodψ(n)
3.解密
对密文分组的解密运算为:
m
≡
c
d
m
o
d
ψ
(
n
)
m\equiv c^dmod\psi(n)
m≡cdmodψ(n)
算法中的优化
\quad
R
S
A
RSA
RSA的加密和解密过程得为求一个整数的整数次幂,在取模。在这个运算过程中如果简单的运用递归,那么中间结果非常大,有可能超出计算机所允许的整数取值范围。然而如果利用模的运算性质:
(
a
∗
b
)
m
o
d
(
n
)
≡
[
(
a
)
m
o
d
(
n
)
∗
b
m
o
d
(
n
)
]
m
o
d
n
.
(a*b)mod(n)\equiv [(a)mod(n)*bmod(n)]modn.
(a∗b)mod(n)≡[(a)mod(n)∗bmod(n)]modn.
我们就可以大大减小中间运算结果。
模重复平方计算法原理
\quad
考虑问题,对大整数m和大整数n计算:
b
n
(
m
o
d
m
)
b^n(modm)
bn(modm)
例如:
1299
6
227
m
o
d
37909
12996^{227}mod37909
12996227mod37909
不难看出若利用递归计算,那么这过程中的中间值将是惊人的,所以我们考虑使用模重复平方计算法。
1.现将n写成二进制,即:
n
=
n
0
+
n
1
2
+
…
+
n
k
−
1
2
k
−
1
,
n
i
∈
[
0
,
1
]
,
i
=
0
,
1
,
…
,
k
−
1
n=n_0+n_12+ \ldots +n_{k-1}2^{k-1},n_i\in[0,1],i=0,1,\ldots,k-1
n=n0+n12+…+nk−12k−1,ni∈[0,1],i=0,1,…,k−1
那么,式:
b
n
(
m
o
d
m
)
b^n(modm)
bn(modm)
的计算可以归纳为:
b
n
≡
b
n
0
⏟
a
0
(
b
2
⏟
b
1
)
n
1
⏟
a
1
…
(
b
2
k
−
2
⏟
b
k
−
2
)
n
k
−
2
⏟
a
k
−
2
(
b
2
k
−
1
⏟
b
k
−
1
)
n
k
−
1
⏟
a
k
−
1
(
m
o
d
m
)
b^n\equiv \underbrace{\underbrace{\underbrace{\underbrace {b^{n_0}} _ {a_0}(\underbrace {b^2}_ {b_1})^{n_1}}_{a_1} \ldots (\underbrace {b^{2^{k-2}}}_ {b_k-2})^{n_k-2}} _{a_k-2} (\underbrace {b^{2^{k-1}}}_ {b_k-1})^{n_k-1}}_{a_k-1}(modm)
bn≡ak−1
ak−2
a1
a0
bn0(b1
b2)n1…(bk−2
b2k−2)nk−2(bk−1
b2k−1)nk−1(modm)
这样我们就可以仅进行至多
2
[
l
o
g
2
n
]
2[log_2n]
2[log2n]次乘法便结束计算。
模重复平方计算法实现(C语言)
我们这里便展示上述的示例:
// 模重复平方计算法.cpp: 定义控制台应用程序的入口点。
//
#include "stdafx.h"
#include"conio.h"
#include"stdlib.h"
#include"string.h"
int MRSM(long long b, long long n,long long m)//模重复平方计算法,其中b为底数,n为指数,m为模数
{
long long M=1;
char str[1024];
_itoa_s(n, str, 2);//将指数n转化成二进制
int count = strlen(str);
for (int i = count-1; i >= 0; i--)//进入循环,利用模运算规律进行求解.
{
if (str[i] == '1')
M=((M *= b)%m);
else
M = M;
b = ((b * b)%m);
}
return M%m;
}
int main()
{
printf("%d\n", MRSM(12996, 227,37909));
_getch();
return 0;
}
运行结果展示:(注:经过仅不到2秒便得出结果,初步达到了简化计算的目的.)