gpt4 book ai didi

python - python-ecdsa 签名大小是否正确?

转载 作者:太空宇宙 更新时间:2023-11-03 14:44:56 25 4
gpt4 key购买 nike

在比特币维基上我发现比特币使用ECDSA算法和Secp256k1曲线。

相关链接:

在第一个链接上,它说私钥应该是 32 字节,公钥应该是 64 字节,签名通常在 71-73 字节之间。它说签名可以小概率小。

但是,当我运行以下 python3 代码时

>>> from ecdsa import SigningKey, SECP256k1
>>> private_key = SigningKey.generate(curve=SECP256k1)
>>> public_key = private_key.get_verifying_key()
>>> signature = private_key.sign(b'message')
>>> print((len(private_key.to_string()), len(public_key.to_string()), len(signature)))

我得到 (32, 64, 64) 作为输出。我希望得到类似 (32, 64, 72) 的结果。

我认为正在发生以下情况之一:

  • 我误解了维基文章。
  • 我错误地使用了 python-ecdsa
  • 比特币维基不正确
  • python-ecdsa 没有正确实现

前两个可能性较大。

谁能向我解释为什么我的期望与实际得到的不匹配?

最佳答案

ECDSA 签名由两个数字组成,r 和 s 是 [1..n-1] 范围内的数字,其中 n 是曲线的阶数。 n 是 [2^(k-1)..2^k-1] 范围内的(已知)数字,其中 k 是 key 大小。因此 r 和 s 的大小通常与 key 大小(以字节为单位)相同,有时略小。

现在r和s可以有多种编码方式,其中两种比较常见:

  1. r 和 s 在 ASN.1 SEQUENCE 中被 DER 编码为两个 ASN.1 签名的 INTEGER 类型。
  2. r 和 s 被编码为两个静态大小的无符号整数,其大小与 key 大小(或顺序)相同,以八位字节或字节为单位

所以大小的差异只是因为值 r 和 s 的编码不同。当然,在验证签名之前,你需要知道编码类型。

由于 r 和 s 完全相同,独立于编码,因此在两个版本之间进行转换相对简单(如果您可以将需要生成或解析 DER 编码的 ASN.1 结构的任何内容称为“简单”)。

类型 1 已在 ANSI X9.62 中标准化,类型 2 通常称为平面编码,通常用于嵌入式平台或智能卡。


r 和 s 非常可能与 n/ key 大小相同,但原则上,它们可以是例如数字 3。发生这种情况的可能性非常小。但是,您应该对 r 和 s 的大小执行任何测试。如果它们中的任何一个小于 8 个字节,那么您可能会开始抓耳挠腮,因为发生这种情况的可能性在 1/2^63 和 1/2^64 之间,即极不可能


所以:

  • 我误解了维基文章。

不,wiki 文章采用 ANSI X9.62 的标准化编码。

  • 我错误地使用了 python-ecdsa

不,python-ecdsa 包只是使用了不同的编码,你会感到惊讶。

  • 比特币维基不正确

不,比特币 wiki 假定为其协议(protocol)选择了特定的编码。

  • python-ecdsa 没有正确实现

绝对不是;至少在签名的大小方面不是。


现在是实现细节;以下内容在文档中:

There are also multiple ways to represent a signature. The default sk.sign() and vk.verify() methods present it as a short string, for simplicity and minimal overhead. To use a different scheme, use the sk.sign(sigencode=) and vk.verify(sigdecode=) arguments. There are helper functions in the "ecdsa.util" module that can be useful here.

因此尝试使用sigencode=sigencode_der 来获取wiki文章所期望的格式。 util.py源具有您可能需要的所有转换。它使用 number_to_string 创建静态大小的数字。此函数在 PKCS#1 (RSA) 中也称为 I2OSP 或整数到八位字节字符串原语。请注意,代码中的“字符串”指的是八位字节字符串,也称为字节数组 - 而不是文本字符串。

关于python - python-ecdsa 签名大小是否正确?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/50304509/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com