密码学系列 - 椭圆曲线 ECDSA - 签名与验签

数字签名的生成

假设Alice要给Bob发一个经过数字签名的消息,他们首先需要定义一组共同接受的椭圆曲线加密用参数,简单的,这组参数可表示为 (CURVE, G, n)
其中,CURVE表示椭圆曲线点域和几何方程;G是所有点倍积运算的基点;n是该椭圆曲线的可倍积阶数(multiplicative order),作为一个很大的质数,n的几何意义在于,nG = 0,即点倍积nG的结果不存在,而对于小于n的任何一个正整数 m = [1,n-1],点倍积mG都可以得到一个合理的处于该椭圆曲线上的点。

其次,Alice要创建一对钥,即一个私钥和一个公钥。私钥来自于[1, n-1]范围内一个随机数: d A = r a n d ( 1 , n − 1 ) d_A = rand(1, n-1) dA=rand(1,n1)
公钥如下,它来自私钥和基点的椭圆曲线点倍积: Q A = d A × G Q_A = d_A \times G QA=dA×G

Alice想要对消息m作数字签名,有以下步骤:

  1. 计算 e = HASH(m),HASH是一个哈希加密函数,比如SHA-2,或SHA-3。
  2. 计算 z,来自e的二进制形式下最左边(即最高位)L_n个bits,而L_n是上述椭圆曲线参数中的可倍积阶数n的二进制长度。注意z 可能大于n,但长度绝对不会比 n 更长。
  3. 从 [1, n-1] 内,随机选择一个符合加密学随机安全性的整数k
  4. 计算一个椭圆曲线上点: ( x 1 , y 1 ) = k × G (x_1, y_1) = k \times G (x1,y1)=k×G
  5. 以下式计算 r 值, 如果r == 0, 则返回步骤3重新计算 r = x 1   m o d   n r = x_1 \bmod n r=x1modn
  6. 以下式计算 s 值,如果 s == 0,则返回步骤3重新计算 s = k − 1 ( z + r d A )   m o d   n s=k^{-1}(z+rd_A) \bmod n s=k1(z+rdA)modn
  7. 生成的数字签名就是 (r, s)

在这里插入图片描述
Alice 用自己的私钥和随机数 k 签名了哈希值 z。Bob 用 Alice 的公钥来验证签名的正确性

特别需要注意的是步骤3中 k 的选择,它不仅要满足加密学的随机安全性要求,要像私钥一样保护起来,更重要的是,在每次生成一个新的数字签名时,这个 k 必须每次都要更新。否则,通过上述数字签名过程中的算式相互换算,很容易从中破译出私钥!具体换算过程可见wiki_ECDSA。
ECDSA签名可能泄漏私钥的另一种方式是 k是由错误的随机数发生器产生的。这样的随机数生成失败导致Android比特币钱包的用户在2013年8月损失了资金

数字签名的验证

对于消息的接收方Bob来说,他除了收到数字签名文件外,还会有一份公钥。所以Bob的验证分两部分,首先验证公钥,然后验证签名文件(r, s)。

公钥的验证

  1. 公钥 Q A Q_A QA的坐标应是有效的,不会等于一个极限值空点 O O O
  2. 通过公钥 Q A Q_A QA的坐标验证它必须是处于该椭圆曲线上的点。
  3. 应有下式成立,即曲线的可倍积阶数 n 与公钥的点倍积不存在 n × Q A = O n \times Q_A = O n×QA=O

签名文件的验证

  1. 验证 r 和 s 均是处于[1, n-1]范围内的整型数;否则验证失败
  2. 计算 e = HASH(m),HASH()即签名生成过程步骤1中使用的哈希函数。
  3. 计算 z,来自 e的最左边L_n个bits
  4. 计算两个参数 u 1 u_1 u1 u 2 u_2 u2 u 1 = z s − 1   m o d   n u_1 = zs^{-1} \bmod n u1=zs1modn u 2 = r s − 1   m o d   n u_2 = rs^{-1} \bmod n u2=rs1modn
  1. 计算 ( x 1 , y 1 ) (x_1, y_1) (x1,y1),如果 ( x 1 , y 1 ) (x_1, y_1) (x1,y1)不是一个椭圆曲线上的点,则验证失败: ( x 1 , y 1 ) = u 1 × G + u 2 × Q A (x_1, y_1) = u_1 \times G + u_2 \times Q_A (x1,y1)=u1×G+u2×QA
  2. 如果下面等式成立, 则签名有效 r ≡ x 1 ( m o d n ) r \equiv x_1 \pmod n rx1(modn)

公钥恢复

收到消息m 和爱丽丝的签名r,s,在该消息上,Bob可以(可能)恢复Alice的公钥:

  1. 验证 rs 是整数 [1,n-1] 。如果不是,则签名无效。
  2. 计算曲线点 R = ( x 1 , y 1 ) R=(x_1, y_1) R=(x1,y1) , x 1 x_1 x1是r, r+n, r+2n等其中之一(提供的 x 1 x_1 x1对于字段元素来说不是太大), y 1 y_1 y1是满足曲线方程式的值。
    请注意,可能有几个满足这些条件的曲线点,每个曲线点都不同 R 值将产生一个不同的已恢复密钥。
  3. 计算 e = HASH(m),HASH()即签名生成过程步骤1中使用的哈希函数。
  4. 计算 z,来自 e的最左边L_n个bits
  5. 计算两个参数 u 1 u_1 u1 u 2 u_2 u2 u 1 = − z r − 1   m o d   n u_1 = -zr^{-1} \bmod n u1=zr1modn u 2 = s r − 1   m o d   n u_2 = sr^{-1} \bmod n u2=sr1modn
  1. 计算曲线点 Q A = ( x A , y A ) = u 1 × G + u 2 × R Q_A = (x_A, y_A) = u_1 \times G + u_2 \times R QA=(xA,yA)=u1×G+u2×R
  2. 如果 Q A Q_A QA匹配Alice的公钥, 则签名有效
  3. 如果尝试了所有可能的R点且没有匹配Alice的公钥,则签名无效。

请注意,无效的签名或来自其他消息的签名将导致恢复不正确的公钥。如果事先知道签名者的公钥(或其哈希),则恢复算法只能用于检查签名的有效性。

公式推导请参考: wiki_ECDSA

公链签名与验签算法

摘要生成签名算法签名数据格式验签算法
BTCSHA256ECDSA-secp256k1BIP66之后采用DER编码.
0x30 [total-length]
0x02 [R-length] [R]
0x02 [S-length] [S]
verify模式 OP_CHECKSIG
ECDSA_CheckSignature
(pubKeyStr,sigStr,
sha256(sha256(verifyThisStr)))
ETHSHA3-KeccackECDSA-secp256k1(R,S,V)
V是recid, 为0或者1,
v := sig[0] - 27
recove模式
pub, err := crypto.Ecrecover(sighash[:], sig)
EOSSHA256ECDSA-secp256k1|r1(V,R,S)
V中带了recid
v: 27 + 4 + recid,
从签名中提取出recove id: V - 4 - 27
recove模式
recov = public_key_type( sig, digest )

公链 ECDSA 验签方式

用公钥去verify的方式:

  1. BTC :

    ECDSA_CheckSignature(pubKeyStr,sigStr,sha256(sha256(verifyThisStr)))

    (参考资料: https://en.bitcoin.it/wiki/File:Bitcoin_OpCheckSig_InDetail.png )

  2. Hyperledger Fabric

    valid, err := id.msp.bccsp.Verify([id.pk](http://id.pk/), sig, digest, nil)

    (参考资料: https://blog.csdn.net/idsuf698987/article/details/81677133 )

recove出公钥的方式:

  1. ETH
    pub, err := crypto.Ecrecover(sighash[:], sig) //摘自源码
  2. EOS
    recov = public_key_type( sig, digest ) //摘自源码

参考: Elliptic Curve Cryptography: ECDH and ECDSA


往期精彩回顾:
区块链知识系列
密码学系列
共识系列
公链调研系列
以太坊系列
EOS系列
智能合约系列
Token系列
  • 7
    点赞
  • 25
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 5
    评论
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

搬砖魁首

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值