RSA是由MIT的三位数学家R.L.Rivest,A.Shamir和L.Adleman[Rivest等1978, 1979]提出的一种用数论构造双钥的方法,被称为MIT体制,后来被广泛称之为RSA体制。其既可以作为加密,又可以用于数字签字。RSA算法的安全性基于数论中大整数分解的困难性。

算法描述

1.独立的选取两个大素数p和q

2.计算\(n = p * q\),其欧拉函数值为\(\phi(n) = (p-1) * (q-1)\)

3.随机选一个整数\(e\),\(1\leq e\leq \phi(n) , gcd(\phi(n),e) = 1\) #gcd为最大公约数

4.在模\(\phi(n)\)下,计算e的逆元\(d = e^{-1} mod \phi(n)\) #意思是\((e * d) mod \phi(n) =1\)

5.以n,e为公钥,密钥为d

加密

将明文分组,每组的数要求小于n(字符串就想办法映射到整数)

计算\(c = m^e mod n\),其中m为明文,c为可以传输的密文

解密

计算\(m = c^d mod n\)

这个过程中只有算法描述中的第三步可能不是直接想到求解方法,对应这个问题,可以用扩展的欧几里得算法来求逆元。

以下算法内容来源自华中科技大学的PPT,在此注明。

问题:求A关于模N的逆元B

迭代计算

N = A × a0 + r0

A = r0 × a1 + r1

r0= r1 × a2 + r2

r1= r2 × a3 + r3

……

rn-2= rn-1 × an + rn

rn-1= rn-2× an+1+ 0

对上面的商数逆向排列(不含余数为0的商)



其中\(b_{-1} = 1\),\(b_0 = a_n\),\(b_i = a_{n-i} * b_{i-1} + b_{i-2}\)

如果商的个数为偶数,则\(b_n\)就是所求的B

如果商的个数为奇数,则\(N-b_n\)就是所求的B

例1:求61关于模105的逆元

105=61×1+44

61 =44×1+17

44 =17×2+10

17 =10×1+7

10 =7 ×1+3

7 =3 ×2+1

3 =3 ×1+0



由于商的个数为偶数(不包括余数为0的商),所以31就是61关于105的逆元

例二:求31关于模105的逆元

105=31×3+12

31 =12×2+7

12 =7 ×1+5

7 =5 ×1+2

5 =2 ×2+1

2 =1 ×2+0



商的个数是奇数,所以105-44 = 61为31关于模105的逆元

代码实现如下:

# coding=utf8
class RSA:
def encrypt(self, string, n, e):
'''
use RSA algorithm to encrypt string
:param string: the String need to be encrypt
:param n: p * q
:param e: encrypt code number
:return: encrypt number
这里是将字符先转换为ASCII值再加密
'''
s = []
for i in string:
s.append(str(ord(i)))
for i in range(len(s)):
s[i] = int(s[i]) ** e % n
return s def decrypt(self, p, q, e, encoding):
'''
:param p: prime number p
:param q: prime number q
:param e: encrypt code number
:param encoding: the string that need to be decrypted
:return: the string that decrypt the encoding number
这里相应的多了一步将ASCII转为字符后拼接的过程
'''
f_n = (p - 1) * (q - 1)
n = p * q
d = RSA.ext_euclid(e, f_n)
s = []
for i in range(len(encoding)):
s.append(chr(encoding[i] ** d % n))
return ''.join(s) @staticmethod
def ext_euclid(e, f_n):
'''
:param e: encrypt code number
:param f_n: p * q
:return: the number that multiply e mod n equals 1
'''
nc = f_n
if e > f_n or type(e) != int or type(f_n) != int:
return -1
quotient = [] #商的列表
remainder = -1 #余数
while remainder != 0:
quotient.append(f_n / e)
remainder = f_n - (f_n / e) * e
f_n = e
e = remainder
quotient = quotient[:-1][::-1] #对应上面写的将商逆序写出来
d_list = [1, quotient[0]]
for i in range(1, len(quotient)):
d_list.append(d_list[-1] * quotient[i] + d_list[-2])
return d_list[-1] if len(quotient) % 2 == 0 else nc - d_list[-1] #如果商的个数是偶数,直接返回bn,否则返回N - bn if __name__ == '__main__':
r = RSA()
p = int(raw_input("p = "))
q = int(raw_input("q = "))
e = int(raw_input("e = "))
string = raw_input("String: ")
en = r.encrypt(string, p * q, e)
print "encrypted code: ", ' '.join(map(str, en))
print "decrypted code: ", r.decrypt(p, q, e, en)

运行如图:



这里可以用小素数的原因是在代码中将明文简单的按字符分组了,但这样会收到频率分析的攻击,在此仅是实验用。

RSA加解密实现的更多相关文章

  1. Rsa加解密Java、C#、php通用代码 密钥转换工具

    之前发了一篇"TripleDes的加解密Java.C#.php通用代码",后面又有项目用到了Rsa加解密,还是在不同系统之间进行交互,Rsa在不同语言的密钥格式不一样,所以过程中主 ...

  2. 【go语言】RSA加解密

    关于go语言的RSA加解密的介绍,这里有一篇文章,已经介绍的很完整了. 对应的go语言的加解密代码,参考git. 因为原文跨语言是跟php,我这里要跟c语言进行交互,所以,这里贴上c语言的例子. 参考 ...

  3. java RSA加解密以及用途

    在公司当前版本的中间件通信框架中,为了防止非授权第三方和到期客户端的连接,我们通过AES和RSA两种方式的加解密策略进行认证.对于非对称RSA加解密,因为其性能耗费较大,一般仅用于认证连接,不会用于每 ...

  4. openssl - rsa加解密例程

    原文链接: http://www.cnblogs.com/cswuyg/p/3187462.html openssl是可以很方便加密解密的库,可以使用它来对需要在网络中传输的数据加密.可以使用非对称加 ...

  5. RSA加解密工具类RSAUtils.java,实现公钥加密私钥解密和私钥解密公钥解密

    package com.geostar.gfstack.cas.util; import org.apache.commons.codec.binary.Base64; import javax.cr ...

  6. PHP RSA加解密详解(附代码)

    前言:RSA加密一般用在涉及到重要数据时所使用的加密算法,比如用户的账户密码传输,订单的相关数据传输等. 加密方式说明:公钥加密,私钥解密.也可以  私钥加密,公钥解密 一.RSA简介 RSA公钥加密 ...

  7. RSA算法原理——(3)RSA加解密过程及公式论证

    上期(RSA简介及基础数论知识)为大家介绍了:互质.欧拉函数.欧拉定理.模反元素 这四个数论的知识点,而这四个知识点是理解RSA加密算法的基石,忘了的同学可以快速的回顾一遍. 一.目前常见加密算法简介 ...

  8. 与非java语言使用RSA加解密遇到的问题:algid parse error, not a sequence

    遇到的问题 在一个与Ruby语言对接的项目中,决定使用RSA算法来作为数据传输的加密与签名算法.但是,在使用Ruby生成后给我的私钥时,却发生了异常:IOException: algid parse ...

  9. JavaScript实现RSA加解密

    在GitHub上找到jsencrypt.js对RSA加解密的工具文件,地址分别是:https://github.com/travist/jsencrypt和https://github.com/ope ...

  10. RSA加解密算法以及密钥格式

    RSA算法: 有个文章关于RSA原理讲的不错: https://blog.csdn.net/dbs1215/article/details/48953589 http://www.ruanyifeng ...

随机推荐

  1. KMP算法求next数组

    next数组的求解方法是:第一位的next值为0,第二位的next值为1.后面求解每一位的next值时,根据前一位进行比较.首先将前一位与其next值对应的内容进行比较,如果相等,则该位的next值就 ...

  2. 简单使用Unity导航系统(小白之路)

    1.介绍 NavMesh:是一种根据场景中几何图像创建出来的3D网格.它会使导航和寻路变得很容易. 简单来说,NavMesh是一种我们在游戏世界中,可以让游戏角色在其表面行走并且导航的平面. 2.注意 ...

  3. mysql 各数据类型的 大小及长度

    数字型 类型 大小 范围(有符号) 范围(无符号) 用途 TINYINT 1 字节 (-128,127) (0,255) 小整数值 SMALLINT 2 字节 (-32 768,32 767) (0, ...

  4. PPPOE拨号上网流程及密码窃取具体实现

    楼主学生党一枚,最近研究netkeeper有些许心得. 关于netkeeper是调用windows的rasdial来进行上网的东西,网上已经有一大堆,我就不赘述了. 本文主要讲解rasdial的部分核 ...

  5. C#换行 System.Environment.NewLine。

    为保持平台的通用性,可以用系统默认换行符 System.Environment.NewLine.

  6. labview生成可执行文件

    labview生成可执行文件可以分为两种情况. 第一种,是电脑中有labview软件开发环境的情况 第二种,是电脑中没有安装labview软件开发环境 下面是一个简单的labview代码: 程序解释: ...

  7. 是否是有效的dom节点--轮子代码

    <!DOCTYPE html> <html> <head> <meta charset="utf-8"/> <title> ...

  8. ettercap的中间人欺骗+sslstrip过滤掉https协议

    环境准备:kali系统 因为kali系统自带ettercap,比较方便, 不需要安装 ifcofing命令查看当前网关 ,当前的IP是: 172.16.42.1 查找局域网所有主机 通过netdisc ...

  9. 改动hosts权限

    在屏蔽网页.訪问一些特定局域网的时候,都可能须要改动Hosts文件. 只是在改动Hosts文件后.会遇到无法保存的情况,提示"您没有权限在此位置中保存文件,请与管理员联系以获取对应权限&qu ...

  10. overridePendingTransition介绍

    Activity的切换动画指的是从一个activity跳转到另外一个activity时的动画 它包含两个部分: 一部分是第一个activity退出时的动画: 另外一部分时第二个activity进入时的 ...