区块链公钥生成 区块链背后的信息安全(4)RSA加解密及签名算法技术原理及其Go语言实现)

入门知识 1周前 (08-06) 12次浏览 0个评论

# RSA加解密和签名算法的技术原理及其在Go语言中的实现

在对称加密中,加密和解密使用相同的密钥,所以必须将密钥分发给解密者,即密钥分发问题。

在非对称加密中,由于公钥和私钥分别用于加密和解密,而且公钥是公开的,所以可以避免密钥分配的问题。

非对称加密算法,又称公钥加密算法。

1977 年,Ron Rivest、Adi Shamir 和 Leonard Adleman 在美国发表了一种公钥加密算法,即 RSA 公钥加密算法。

RSA是目前最有影响力和最常用的公钥加密算法,可以说是公钥加密算法的事实标准。

### RSA加密原理

分别用M和C表示明文和密文,RSA加解密过程如下:

e和n(e,n)的组合是公钥,d和n(d,n)的组合是私钥。

当然,e、d、n不是任意值,需要满足一定的条件。下面是e、d、n的求解过程。

### 生成密钥对

e、d、n的求解过程就是生成密钥对的过程。涉及以下步骤:

* 1、取两个大素数(也叫素数)p,q,n = pq。

* 2、 取正整数e和d,使得ed mod (p-1)(q-1) = 1,即:ed ≡ 1 mod (p-1)@ > (q-1).

e 和 d 是模 (p-1)(q-1), 仅当 e 与 (p-1)(q-1), d 存在.

示例验证:

* 1、 取 p 和 q 为 13、17,n = pq = 221。

* 2、和 (p-1)(q-1) = 12×16 = 192, 取 e 和 d 为 13、133, 13×133 mod 192 = 1

取明文M=60,公钥加密私钥解密,加解密过程如下:

### RSA加密原理证明过程

### 手动求解密钥对中的d

ed mod (p-1)(q-1) = 1,给定e和(p-1)(q-1))求d,即求e模数 ( p-1)(q-1).

在上面的例子中,p和q是13、17,(p-1)(q-1)=192,取e=13,求d在13d mod 192 = 1.

13d ≡ 1 (mod 192), 将 192 的倍数加到右边使结果可以被 13 整除。

13d ≡ 1 + 192×9 ≡ 13×133 (mod 192), 所以 d = 133

其他计算方法有:费马小定律、扩展欧几里得算法、欧拉定理。

### RSA 安全性

由于公钥是公开的,即 e 和 n 是公开的。

所以破解RSA私钥就是在已知e和n的情况下求d。

由于 ed mod (p-1)(q-1) = 1, and n=pq, 问题演变为:求 p 和 q 进行 n 素数分解。

目前已经证明已知的e,n求d和n的素数分解求p,q是等价的。

在实际中,n的长度超过2048位,当n>200位时,n的分解是非常困难的,所以还是认为RSA算法是安全实用的。

### RSA定时攻击与预防

RSA解密的本质是模幂运算,即:

其中,C为密文,(d,n)为私钥,都是对1024位以上的大数的运算,直接计算是不可行的。因此,最经典的算法是蒙哥马利算法。

这种计算比较耗时,因此攻击者可以观察不同输入对应的解密时间,通过分析推断出私钥,称为定时攻击。

防止RSA定时攻击的方法是在解密时加入随机因素,使攻击者无法准确获取解密时间。

具体实施步骤如下:

### go标准库中的RSA加解密实现

go标准库中的解密实现了对定时攻击的防范。代码如下:

““去

//加密

//m是明文

//(pub.E, pub.N) 是公钥

//c是密文

func encrypt(c *big.Int, pub *, m *big.Int) *big.Int {

e := big.NewInt(int64(pub.E))

c.Exp(m, e, pub.N)

返回 c

}

//解密

//传入随机数支持防止定时攻击

func 解密(随机 io.Reader,priv *,c *big.Int)(m *big.Int,err 错误){

如果 c.Cmp(priv.N) > 0 {

错误 =

返回

}

如果 priv.N.Sign() == 0 {

返回零,

}

var ir *big.Int

如果随机!= nil {

var r *big.Int

为了 {

//第一步生成一个0到n-1之间的随机数r

r, err = rand.Int(random, priv.N)

如果错误!= nil {

返回

}

如果 r.Cmp(bigZero) == 0 {

r = bigOne

}

var ok 布尔值

//r 的乘法逆 ir 模 n区块链公钥生成,用于第 4 步

ir, ok = (r, priv.N)

如果可以{

休息

}

}

bigE := big.NewInt(int64(priv.E))

//计算第2步中的C’

rpowe := new(big.Int).Exp(r, bigE, priv.N) // N != 0

cCopy := new(big.Int).Set(c)

cCopy.Mul(cCopy, rpowe)

cCopy.Mod(cCopy, priv.N)

c = c复制

}

如果 priv..Dp == nil {

//第3步,用C’计算对应的M’

m = new(big.Int).Exp(c, priv.D, priv.N)

} 别的 {

//轻微地

用区块链监管区块链_区块链公链私链_区块链公钥生成

}

如果 ir != nil {

//第4步计算实际M

m.Mul(m, ir)

m.Mod(m, priv.N)

}

返回

}

//代码位置 src/crypto/rsa/rsa.go

““

### RSA签名和验证的原理

非对称加密算法,除了支持加密外,还可以实现签名。原理如下:

符号:

* 1、 提取消息摘要,用发送者的私钥加密消息摘要,生成消息签名。

* 2、消息签名和消息与接收者的公钥一起加密区块链公钥生成,得到密文。

签名验证:

* 1、使用接收者的私钥对密文进行解密,得到消息和消息签名。

* 2、使用发送者的公钥解密消息签名,得到消息摘要。

* 3、用同样的方法再次提取消息摘要,并与上一步的消息摘要进行比较。如果相同,则签名验证成功。

附图如下:

1)0@>

### Go 标准库中的 RSA 签名和验证实现

代码显示如下:

““去

//符号

func (rand io.Reader, priv *, hash crypto.Hash, hashed []byte) ([]byte, error) {

//哈希提取消息摘要

hashLen, 前缀, err := (hash, len(hashed))

如果错误!= nil {

返回零,错误

}

tLen := len(前缀) + hashLen

区块链公链私链_用区块链监管区块链_区块链公钥生成

k := (priv.N.BitLen() + 1)1@> / 8

如果 k < tLen+11 {

返回零,

}

// EM = 0x00 || 0x01 || PS || 0x00 || 吨

em := make([]byte, k)

em[1] = 1

对于 i := 2; 我 < k-tLen-1; 我++ {

em[i] = 0xff

}

//整合消息摘要和消息正文

复制(em[k-tLen:k-hashLen],前缀)

复制(em[k-hashLen:k],散列)

m := new(big.Int).(em)

//使用发送者的私钥对消息摘要和消息体进行加密,即签名

c, err := (rand, priv, m)

如果错误!= nil {

返回零,错误

}

(em, c.Bytes())

返回 em,无

}

//验证签名

func (pub *, hash crypto.Hash, hashed []byte, sig []byte) 错误 {

//哈希提取消息摘要

hashLen, 前缀, err := (hash, len(hashed))

如果错误!= nil {

返回错误

}

tLen := len(前缀) + hashLen

k := (pub.N.BitLen() + 1)1@> / 8

如果 k < tLen+11 {

区块链公链私链_区块链公钥生成_用区块链监管区块链

返回

}

c := new(big.Int).(sig)

//使用发送者的公钥解密,提取消息体和消息签名

m := 加密(new(big.Int), pub, c)

em := leftPad(m.Bytes(), k)

// EM = 0x00 || 0x01 || PS || 0x00 || 吨

//比较发送者和接收者的消息体,以及消息签名

好的 := 微妙的。(em[0], 1)3@>

好的 &= 微妙的。(em[1], 1)

好的 &= 微妙的。(em[k-hashLen:k],散列)

好的 &= 微妙的。(em[k-tLen:k-hashLen],前缀)

好的 &= 微妙的。(em[k-tLen-1], 1)3@>

对于 i := 2; 我 < k-tLen-1; 我++ {

好的 &= 微妙的。(em[i], 0xff)

}

如果没问题!= 1 {

返回

}

返回零

}

//代码位置 src/crypto/rsa/.go

““

### 后记

RSA算法中用到了很多数论知识,而数论方面的知识还有待学习。

未完待续。

1)6@>

1)7@>

1)8@>

网址:

1)9@>

领取造币技术及全套虚拟机资料

区块链技术交流QQ群: 备注:CSDN

挖矿网Ethos中文站简单易用的挖矿系统,为挖矿产业提供教程软件以及矿机测评交易信息等,挖矿网各种数字货币挖矿收益对比计算,挖矿网介绍挖矿的工具,以及矿场的最新消息等。http://www.ethospool.com/

喜欢 (0)
发表我的评论
取消评论
表情 贴图 加粗 删除线 居中 斜体 签到

Hi,您需要填写昵称和邮箱!

  • 昵称 (必填)
  • 邮箱 (必填)
  • 网址