RSA非对称加密解密详解
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
非对称算法之RSA的签名剖析
前言
数字签名,就是只有信息的发送者才能产生的别人无法伪造的一段数字串,这段数字串同时也是对信息的发送者发送信息真实性的一个有效证明。
不清楚的请自行科普数字签名。
本篇主要来讲签名值具体是怎么计算出来的~
一、动手解密签名值
1、测试密钥
2、编写代码解密
众所周知:
RSA加密解密:私钥解密,公钥加密。
RSA数字签名-俗称加签验签:私钥加签,公钥验签。
其实:
也是有私钥加密,公钥解密的。
只是因为公钥是公开的,私钥加密后所有人都可以解密,没有意义,所以常用签名,而不是加密。
私钥加签的本质也是私钥加密数据的Hash值。
这里有个小技巧:我们用公钥对签名值解密,使用RSA_NO_PADDING,这样就能得到签名时私钥加密的数据。
鉴于篇幅长度,代码只贴出关键部分。
代码之PHP:
其他语言代码整理ing…
本次测试java、js、C#、PHP。
结果均一致,如下:
简单分析
1. 字符串”hello world”进行sha256运算得到hash:
b94d27b9934d3e08a52e52d7da7dabfac484efe37a5380ee9088f7ace2efcde 9
2. 在Hash结果前数据填充:3031300d060960864801650304020105000420
3. PKCS1 在上一步结果前填充:
二、结合资料分析RSA的补位
1、签名时,对Hash值的数据填充方式
对hash算法id和hash值进行ASN.1的DER编码。
如下:
为方便理解,我们使用ASN1dump对示例中的数据做解析:
直接上图:
可以看到sha256的算法id,2.16.840.1.101.3.4.2.1:
数据也在其中,另附上部分算法id:
另因为各个hash算法id是固定的,计算的结果也是固定的。
所以不同的hash算法的填充也是固定的。
如下:
2、pkcs1padding V1.5的填充模式参考rfc2312
以下描述均以十六进制字符串来描述。
pkcs1padding V1.5的填充模式方式如下:
即:加密块=00+块类型+填充字符+00+数据
1. 开头00是为了确保块转换为整数的时候小于模数
2. BT(Block Type):当使用私钥操作,块类型为00或01,公钥操作,块类型为02。
块类型为00,数据开头必须不能是00,因为填充的也是00,将无法解析。
块类型为01或02,块可以被准确解析,因为不会是00来填充。
3. PS(Padding String):k-3-||D|| 个字节组组成,k表示密钥的字节长度, D表示明文数据D的字节长度。
当BT为01时,填充字节值为FF,BT为00时,填充字节值为00,BT为02时填充随机数(非00)。
填充长度至少为8个字节
4. 00,用于分开PS和D
5. D,数据原文(HEX)
注意:2048位的RSA密钥,加密块长度也必须是2048位,也就是256个字节。
所以示例中的加密块需要填充202个FF才够256个字节。
故签名的时候,加密的块:00+01+FF(202个) +00 +
">3031300d060960864801650304020105000420b94d27b9934d3e08a52e52d7da7dabfac48 4efe37a5380ee9088f7ace2efcde9
三、测试题
最后抛了两个问题,看看大家有没有理解上面所介绍的内容。
1、RSA签名的时候值是固定,公钥加密的结果确实随机的,为什么?
2、分析如下代码,是否有问题?。