为什么openssl在生成私钥的时候会写入EC参数?

信息安全 openssl 电子抄送 asn1
2021-09-06 09:01:03

当我用 生成私钥时openssl,它会写入曲线的参数和实际的私钥:

❯ openssl ecparam  -name secp256k1 -genkey
-----BEGIN EC PARAMETERS-----
BgUrgQQACg==
-----END EC PARAMETERS-----
-----BEGIN EC PRIVATE KEY-----
MHQCAQEEIKYV1xoz6smkpdMksfgI8/3465V02UZdaKj4JSH30bBhoAcGBSuBBAAK
oUQDQgAEO1O+/xRGEVJgBEAOQorBveXPTQS3c7MA+9R+HEMP7TkscI9FONPclcRb
5sXZJjYHNYWhvxuXdGl8QrFVRIVBYg==
-----END EC PRIVATE KEY-----

注意参数不包含真实数据,仅参考使用的标准:

❯ openssl ecparam  -name secp256k1 | openssl asn1parse
    0:d=0  hl=2 l=   5 prim: OBJECT            :secp256k1

但是,当我查看私钥时,我可以看到它包含使用的曲线类型!查看以41:d开头的行

❯ openssl ecparam  -name secp256k1 -genkey -noout | openssl asn1parse
    0:d=0  hl=2 l= 116 cons: SEQUENCE          
    2:d=1  hl=2 l=   1 prim: INTEGER           :01
    5:d=1  hl=2 l=  32 prim: OCTET STRING      [HEX DUMP]:872F67D0B852C6FE9BD1F5B93AF54B7555D21267200DA2F8ED735729BF32730A
   39:d=1  hl=2 l=   7 cons: cont [ 0 ]        
   41:d=2  hl=2 l=   5 prim: OBJECT            :secp256k1
   48:d=1  hl=2 l=  68 cons: cont [ 1 ]        
   50:d=2  hl=2 l=  66 prim: BIT STRING

我有需要 EC 参数的原因吗?为什么它会默认生成它们?

(我能想到需要这些 EC 参数的唯一原因是在生成私钥时将它们用作输入,但是在命令行中给出它们的名称不是更好吗?)

1个回答

这是 OpenSSL 的一个怪癖。ecparam命令用于处理 EC 参数 - 即要播放的曲线的定义 - 并允许生成私钥作为辅助功能。您可以使用-noout命令行参数来抑制编码 EC 参数本身的生成:

$ openssl ecparam -name secp256k1 -genkey -noout
-----BEGIN EC PRIVATE KEY-----
MHQCAQEEIHyx/m9I6/ZbvqN5XJ/fZSM6P7PIuvNDnWdp8STjlGqQoAcGBSuBBAAK
oUQDQgAEVGRwTHlFRgxmhnJNO4Vfdojmg2pni44U4SMFEziNM8YVhd62UzwB5L0+
n8EXsvTIv5Uj7COQd/1cTsdL9kin4w==
-----END EC PRIVATE KEY-----

此外,“EC 参数”独立结构的存在是合理的,因为私钥编码可能缺少信息;请参阅RFC 5915,它给出了以下 ASN.1 类型:

ECPrivateKey ::= SEQUENCE {
  version        INTEGER { ecPrivkeyVer1(1) } (ecPrivkeyVer1),
  privateKey     OCTET STRING,
  parameters [0] ECParameters {{ NamedCurve }} OPTIONAL,
  publicKey  [1] BIT STRING OPTIONAL
}

其中parameterspublicKey字段被适当地标记为“可选”。

至于参数的内部表示(独立或作为私钥结构的一部分),使用简单的 OID 是相当正常的。生成自己的椭圆曲线比生成新的 DSA 参数要困难得多;此外,坚持一些标准曲线使 EC 密码学的实施更容易和更快。因此,大多数实施仅限于几条标准曲线,通常是 NIST 的 P-256 和 P-384 实际上来自 SEC,然后被 NIST “附件”)。支持所有 15 条标准 NIST 曲线的实现很少见。支持“任意”曲线的实现(其中完整的曲线值编码在参数结构中)是神话般的(我从来没有偶然发现一个,尽管我在某个时候接近写一个)。