RSA签名的PSS模式

本文由云+社区发表

作者:mariolu

一、什么是PSS模式?

1.1、两种签名方式之一RSA-PSS

PSS (Probabilistic Signature Scheme)私钥签名流程的一种填充模式。目前主流的RSA签名包括RSA-PSS和RSA-PKCS#1 v1.5。相对应PKCS(Public Key Cryptography Standards)是一种能够自我从签名,而PSS无法从签名中恢恢复原来的签名。openssl-1.1.x以后默认使用更安全的PSS的RSA签名模式。

1.2、填充的必要性

RSA算法比较慢,一般用于非对称加密的private key签名和public key验证。因RSA算法沒有加入乱数,当出现重复性的原始资料,攻击者会通过相同加密密文而猜测出原文,因此导入padding的机制來加強安全性。

TLS流程中的密钥材料若不进行填充而直接加密,那么显然相同的key,会得到相同的密文。这种在语义上来说,是不安全的。以下例子说明了无填充模式的安全漏洞。

  • m:明文
  • e,n:RSA参数(公钥)
  • d:RSA参数(私钥)
  • c:网络传输密文

加密方加密m:c = m^e mod n,传输c

解密方解密c:m = c^d mod n,还原m

  • c':篡改密文
  • k:篡改码

由于c在网络上传输,如果网络上有人对其进行c' = c*k^e mod n,这样的替换

那么解密方将得到的结果是

(c*k^e)^d mod n

= (c^d mod n)* (k^ed mod n)

= m*k

即中间人有办法控制m。

1.3、PSS的基本要素

使用PSS模式的RSA签名流程如下:

img图1、RSA-PSS的填充模式

相比较PKCS#1 v1.5的padding简单许多:

img图2、RSA-PKCS#v1.5的填充模式

PSS的一些概念:

  • hash算法,一般使用SHA-1
  • MGF函数(mask generation function)。默认是MGF1。
  • salt length,一般由hLen决定。当为0时,签名值变成了唯一确定的。
  • 截断符号,一般是0xbc

二、RSA签名实际操作

这节例子中所涉及到的文件说明:

/tmp/wildcard_domain.sports.qq.com.v2.key:私钥

/tmp/pub: 公钥

/tmp/data: 明文

/tmp/endata: 密文

/tmp/sign: 签名

/tmp/de_sign: 解签名

2.1、前期准备:公钥和私钥

  • 通过key文件提取出public key
openssl rsa -in /usr/local/services/ssl_agent/ca/wildcard_domain.sports.qq.com.v2.key -pubout -out /tmp/pub
  • 原始数据:

echo -n "1234567890" > /tmp/data

  • 这样就有一对公钥和私钥,用来测试RSA加密解密(encrypt、decrypt)和签名验证(sign,verify)
  • RSA加密的两种算法分别是RSAES-PKCS-v1_5 and RSAES-OAEP。

2.2、加密和解密(encrypt,decrypt)

  • 加密:
openssl rsautl -pubin -inkey /tmp/data -in /tmp/data -encrypt -out /tmp/endata
  • 解密,用private key解密,得到原本的值:
openssl rsautl -inkey /tmp/wildcard_domain.sports.qq.com.v2.key -in /tmp/en_data -decrypt

2.3、签名和验证(sign, verify)

签名过程包括hash和加密。hash函数一般使用sha1。这样输入明文,直接生成sign签名。

如果是私钥签名所做的事就是先hash再加密,选择一种hash算法把原始消息计算后成ASN1格式,再把这个资料用private key加密后送出,资料本身不加密,这种方式主要是用來验证资料来源是否可信任的,送出時把原始资料和签名一起送出。

  • 签名:
openssl sha1 -sign /tmp/wildcard_domain.sports.qq.com.v2.key  /tmp/data > /tmp/data/sign/tmp/data/sign
  • 解开签名:
openssl rsautl -pubin -inkey /tmp/pub -in sign -verify -out /tmp/de_sign 

用public key解开签名,并且保留padding

 openssl rsautl -pubin -inkey /tmp/pub -in /tmp/sign -encrypt -raw -hexdump

使用解开ASN1解开签名,或者签名后用ASN1工具解析

openssl rsautl -pubin -inkey /tmp/pub -in /tmp/sign -verify -asn1parse

或者:

openssl asn1parse -inform der -in /tmp/de_sign

和本地sha1对比

openssl sha1 /tmp/data

如果两者hash结果是一样,那么确定签名送过来是正确的。

2.4、openssl rsautl工具支持的填充模式

openssl rsautl --help,可以看到支持的padding模式有,在rsautl加上以下选项可以重复做2.2~2.3的实验。

 -ssl                     Use SSL v2 padding
 -raw                     Use no padding
 -pkcs                    Use PKCS#1 v1.5 padding (default)
 -oaep                    Use PKCS#1 OAEP

三、PSS填充模式的特点

PSS是RSA的填充模式中的一种。

完整的RSA的填充模式包括:

RSA_SSLV23_PADDING(SSLv23填充)
RSA_NO_PADDING(不填充)
RSA_PKCS1_OAEP_PADDING (RSAES-OAEP填充,强制使用SHA1,加密使用)
RSA_X931_PADDING(X9.31填充,签名使用)
RSA_PKCS1_PSS_PADDING(RSASSA-PSS填充,签名使用)
RSA_PKCS1_PADDING(RSAES-PKCS1-v1_5/RSASSA-PKCS1-v1_5填充,签名可使用)

其中主流的填充模式是PKCS1和PSS模式。

PSS的优缺点如下:

  • PKCS#1 v1.5比较简易实现,但是缺少security proof。
  • PSS更安全,所以新版的openssl-1.1.x优先使用PSS进行私钥签名(具体在ssl握手的server key exchange阶段)

此文已由腾讯云+社区在各渠道发布

获取更多新鲜技术干货,可以关注我们腾讯云技术社区-云加社区官方号及知乎机构号

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: RSA-PSS是一种RSA数字签名方案,它基于Probabilistic Signature Scheme(概率签名方案)。PSS是一种公认安全的签名方案,它在签名时引入了随机性,从而防止了针对固定签名方案的攻击。 在Python中,可以使用PyCryptodome库来实现RSA-PSS签名。首先,需要生成RSA密钥对: ```python from Crypto.PublicKey import RSA key = RSA.generate(2048) private_key = key.export_key() public_key = key.publickey().export_key() ``` 接下来,使用私钥对数据进行签名: ```python from Crypto.Signature import pkcs1_15 from Crypto.Hash import SHA256 message = b"Hello, world!" hash_obj = SHA256.new(message) from Crypto.Signature import pkcs1_15 from Crypto.Hash import SHA256 message = b"Hello, world!" hash_obj = SHA256.new(message) from Crypto.Signature import pkcs1_15 from Crypto.Hash import SHA256 message = b"Hello, world!" hash_obj = SHA256.new(message) from Crypto.Signature import pkcs1_15 from Crypto.Hash import SHA256 message = b"Hello, world!" hash_obj = SHA256.new(message) from Crypto.Signature import pkcs1_15 from Crypto.Hash import SHA256 message = b"Hello, world!" hash_obj = SHA256.new(message) from Crypto.Signature import pkcs1_15 from Crypto.Hash import SHA256 message = b"Hello, world!" hash_obj = SHA256.new(message) from Crypto.Signature import pkcs1_15 from Crypto.Hash import SHA256 message = b"Hello, world!" hash_obj = SHA256.new(message) from Crypto.Signature import pkcs1_15 from Crypto.Hash import SHA256 message = b"Hello, world!" hash_obj = SHA256.new(message) private_key = RSA.import_key(private_key) signature = pkcs1_15.new(private_key).sign(hash_obj) ``` 最后,使用公钥验证签名: ```python from Crypto.Signature import pkcs1_15 from Crypto.Hash import SHA256 public_key = RSA.import_key(public_key) try: pkcs1_15.new(public_key).verify(hash_obj, signature) print("Signature is valid.") except (ValueError, TypeError): print("Signature is invalid.") ``` 需要注意的是,在PSS模式中,可以使用不同的哈希算法和盐长度。在PyCryptodome中,可以使用`PSS.new()`来指定这些参数。例如,使用SHA-512哈希算法和20字节的盐长度: ```python from Crypto.Signature import pss from Crypto.Hash import SHA512 pss.new(private_key, salt_len=20, mgfunc=lambda x, y: pss.MGF1(x, y, SHA512)).sign(hash_obj) ``` ### 回答2: RSA-PSS是一种用于数字签名的加密算法,它在Python中是通过PyCryptodome库来实现的。PSS是Probabilistic Signature Scheme的缩写,它可以提供更高的安全性和更好的抵抗弱密钥之类的攻击。 Python中使用PSS模式来进行RSA签名的过程如下: 1. 导入必要的库和模块: ```python from Crypto.Signature import pkcs1_15 from Crypto.Hash import SHA256 from Crypto.PublicKey import RSA ``` 2. 加载私钥和公钥: ```python private_key = RSA.import_key(open('private.pem').read()) # 加载私钥 public_key = RSA.import_key(open('public.pem').read()) # 加载公钥 ``` 3. 对待签名的数据进行哈希处理: ```python message = b'Hello, world!' # 待签名的数据 hash_obj = SHA256.new(message) # 使用SHA-256算法哈希 ``` 4. 创建签名: ```python signer = pkcs1_15.new(private_key) # 创建一个用于签名的对象 signature = signer.sign(hash_obj) # 对哈希后的数据进行签名 ``` 5. 验证签名: ```python verifier = pkcs1_15.new(public_key) # 创建一个用于验证签名的对象 try: verifier.verify(hash_obj, signature) # 验证签名 print("数字签名有效!") except (ValueError, TypeError): print("数字签名无效!") ``` 通过以上步骤,就可以在Python中使用RSA-PSS模式进行数字签名的生成和验证。这种模式能够提供较高的安全性,并且可以用于确保数据的完整性和身份验证等领域。 ### 回答3: RSA-PSS(Probabilistic Signature Scheme)是一种用于密钥签名RSA加密算法的模式,其主要目的是提高安全性和防止哈希碰撞攻击。 在RSA-PSS中,首先需要选择合适的哈希函数,例如SHA-256。然后,消息需要通过哈希函数计算出摘要。接下来,通过使用一个称为盐(salt)的随机数来增加签名的随机性和安全性。盐的长度应与哈希输出长度相同。 在PSS模式中,需要定义一个填充方案来保持数据的完整性。常用的填充方案是OAEP(Optimal Asymmetric Encryption Padding)填充算法。OAEP填充算法包括两个随机数生成器,分别用于产生盐和掩码值。最后,使用私钥对填充后的数据进行加密,得到签名。 在验证签名时,首先需要对签名数据进行解密,使用公钥得到填充后的数据。然后,使用相同的哈希函数计算摘要,并与签名中的摘要进行比较。如果两者相同,则表示签名有效。 相比于传统的RSA签名模式RSA-PSS提供了更高的安全性,因为它能够抵御哈希碰撞和其他攻击。同时,使用PSS模式还能够提供更好的随机性和签名强度。 总之,RSA-PSS是一种基于RSA加密算法的高安全性签名模式,通过使用哈希函数,盐和填充方案来保证签名的安全性和完整性。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值