https://aaron67.cc/2021/07/10/rabin-signatures/
本文将详细介绍 Rabin 数字签名的算法细节。在开始之前,你需要对模运算、同余和模逆元的概念有一些了解。
算法过程
质数 p p p 和 q q q,且有 p ≡ 3 ( m o d 4 ) p \equiv 3 \pmod{4} p≡3(mod4), q ≡ 3 ( m o d 4 ) q \equiv 3 \pmod{4} q≡3(mod4)。
组合 ( p , q ) (p, q) (p,q) 为私钥,两数的乘积 n = p q n = pq n=pq 为对应的公钥。
使用私钥 ( p , q ) (p, q) (p,q) 对消息 m m m 签名的结果为组合 ( S , U ) (S, U) (S,U),满足
S 2 ≡ H ( m ∣ ∣ U ) ( m o d n ) (1) S^2 \equiv H(m||U) \pmod{n} \tag{1} S2≡H(m∣∣U)(modn)(1)
其中的 U U U 被称为填充值, H ( m ∣ ∣ U ) H(m||U) H(m∣∣U) 的意思是将 m m m 和 U U U 的二进制流拼接在一起后再计算哈希,并将哈希结果(二进制流)看成一个整数。
令 H = H ( m ∣ ∣ U ) m o d n H = H(m||U) \bmod{n} H=H(m∣∣U)modn 来简化书写。当 U U U 确定后,可以用下式计算 S S S 的值。
S = [ q ⋅ ( H p + 1 4 m o d p ) ⋅ ( q p − 2 m o d p ) + p ⋅ ( H q + 1 4 m o d q ) ⋅ ( p q − 2 m o d q ) ] m o d n (2) S = \left[q \cdot (H^{\frac{p+1}{4}} \bmod{p}) \cdot (q^{p-2} \bmod{p}) + p \cdot (H^{\frac{q+1}{4}} \bmod{q}) \cdot (p^{q-2} \bmod{q})\right] \bmod{n} \tag{2} S=[q⋅(H4p+1modp)⋅(qp−2modp)+p⋅(H4q+1modq)⋅(pq−2modq)]modn(2)
这样便得到了一组 ( S , U ) (S, U) (S,U),将结果代入 (1) 式验算,若成立则返回这组结果,反之则改变 U U U 的值重新计算 S S S,直到找到一组满足 (1) 式的解。
请注意,当 p ≡ 3 ( m o d 4 ) p \equiv 3 \pmod{4} p≡3(mod4) 时, p + 1 4 \frac{p+1}{4} 4p+1 是一个整数,同理 q + 1 4 \frac{q+1}{4} 4q+1 也是一个整数。
完整代码请参考 rabin.py。签名时,通过循环在 m m m 后追加字节 0x00 来改变 H H H 的值,并在计算出 S S S 后验证 (1) 式是否成立,是则跳出循环返回,否则继续寻找。
def sign(p: int, q: int, digest: bytes) -> tuple:
"""
:param p: part of private key
:param q: part of private key
:param digest: message digest to sign
:return: rabin signature (S: int, U: bytes)
"""
n = p * q
i = 0
while True:
h = hash_to_int(digest + b'\x00' * i) % n
lp = q * pow(h, (p + 1) // 4, p) * pow(q, p - 2, p)
rp = p * pow(h, (q + 1) // 4, q) * pow(p, q - 2, q)
s = (lp + rp) % n
if (s * s) % n == h % n:
break
i += 1
return s, b'\x00' * i
验签时只需判断 (1) 式是否成立即可。
def verify(n: int, digest: bytes, s: int, u: bytes) -> bool:
"""
:param n: rabin public key
:param digest: digest of signed message
:param s: S of signature
:param u: padding U of signature
"""
return hash_to_int(digest + u) % n == (s * s) % n
通过上面的描述你能看到,Rabin 签名的计算过程相对复杂,但验证过程极其简单。这个特性使得它非常适合在链上直接验签,虽然我们也可以在比特币脚本中实现 ECDSA 的验签逻辑,但它的计算成本要比验证 Rabin 签名高出许多。
整个算法设计基于这样的数学难题:在模是大合数的情况下,求二次剩余平方根是困难的。使用 Rabin 签名时,为了获得足够的安全性,公钥 n n n 和哈希 H ( m ∣ ∣ U ) H(m||U) H(m∣∣U) 的结果至少需要 3072 位(bit)。
至此,我们介绍了如何计算和验证 Rabin 签名,并给出了完整代码,方便你直接使用。如果你还关心这些结论和公式背后的推导过程,可以继续阅读,我们留了一些问题没有解答:
- 问题一:当 p ≡ 3 ( m o d 4 ) p \equiv 3 \pmod{4} p≡3(mod4) 时,为什么 p + 1 4 \frac{p+1}{4} 4p+1 是一个整数?
- 问题二:公式 (1) 是如何推导出公式 (2) 的?
问题一
证明当 p ≡ 3 ( m o d 4 ) p \equiv 3 \pmod{4} p≡3(mod4) 时, p + 1 4 \frac{p+1}{4} 4p+1 是一个整数。
根据同余的定义,对 p ≡ 3 ( m o d 4 ) p \equiv 3 \pmod{4} p≡3(mod4),存在整数 m m m、 n n n 和 r r r 满足:
{ p = 4 m + r 3 = 4 n + r \begin{cases} p = 4m + r \\[0.5em] 3 = 4n + r \end{cases} ⎩⎨⎧p=4m+r3=4n+r
两式相减,有
p − 3 = 4 ( m − n ) (3) p - 3 = 4(m - n) \tag{3} p−3=4(m−n)(3)
因为 m m m 和 n n n 都是整数,所以 ( m − n ) (m - n) (m−n) 也是整数。也就是说,若两数在某个模数下同余,则两数的差是模数的整数倍,反之亦然。
等式 (3) 两边同时加 4,得到 p + 1 = 4 ( m − n + 1 ) p + 1 = 4(m - n + 1) p+1=4(m−n+1),即 p + 1 4 = m − n + 1 \frac{p+1}{4} = m - n + 1 4p+1=m−n+1。因为 m m m 和 n n n 都是整数,所以 ( m − n + 1 ) (m - n + 1) (m−n+1) 也是整数,证毕。
二次剩余
在数论特别是同余理论中,一个整数 X X X 对另一个整数 p p p 的二次剩余(quadratic residue),指的是 X X X 的平方 X 2 X^2 X2 除以 p p p 得到的余数。
若存在某个 X X X 使得 X 2 ≡ d ( m o d p ) X^2 \equiv d \pmod{p} X2≡d(modp) 成立,则称 d d d 是模 p p p 的二次剩余。若对任意的 X X X 式子 X 2 ≡ d ( m o d p ) X^2 \equiv d \pmod{p} X2≡d(modp) 均不成立,则称 d d d 是模 p p p 的非二次剩余。
例如,2 是模 7 的二次剩余,因为当 X = 3 X = 3 X=3 时 3 2 ≡ 2 ( m o d 7 ) 3^2 \equiv 2 \pmod{7} 32≡2(mod7) 成立。3 是模 7 的非二次剩余,因为你找不到整数 X X X 使式子 X 2 ≡ 3 ( m o d 7 ) X^2 \equiv 3 \pmod{7} X2≡3(mod7) 成立。
求二次剩余的平方根,即已知 d d d 和 p p p 求 X X X,可以使用 Tonelli–Shanks 算法。
当 p ≡ 3 ( m o d 4 ) p \equiv 3 \pmod{4} p≡3(mod4) 时,该算法有简化版本,即
X = { d p + 1 4 m o d p − d p + 1 4 m o d p X = \begin{cases} d^{\frac{p+1}{4}} \bmod{p} \\[0.5em] -d^{\frac{p+1}{4}} \bmod{p} \end{cases} X=⎩⎨⎧d4p+1modp−d4p+1modp
例如,当 p = 7 p = 7 p=7 时,若 X 2 ≡ 2 ( m o d 7 ) X^2 \equiv 2 \pmod{7} X2≡2(mod7),则
X = { 2 7 + 1 4 m o d 7 = 4 m o d 7 = 4 − 2 7 + 1 4 m o d 7 = − 4 m o d 7 = 3 X = \begin{cases} 2^{\frac{7+1}{4}} \bmod{7} = 4 \bmod{7} = 4 \\[0.5em] -2^{\frac{7+1}{4}} \bmod{7} = -4 \bmod{7} = 3 \end{cases} X=⎩⎨⎧247+1mod7=4mod7=4−247+1mod7=−4mod

最低0.47元/天 解锁文章
2483

被折叠的 条评论
为什么被折叠?



