我可以从openssh公钥和ECParameterSpec的Q值创建JCE ECPublicKey吗? [英] Can I create a JCE ECPublicKey from a Q value from an openssh public key and ECParameterSpec
问题描述
我正在阅读openssh格式的椭圆曲线公共密钥( RFC 5656第3.1节,),并希望使用JCE从BigInteger Q值获取到ECPublicKey
实例(而不是说BouncyCastle).我要执行此操作以验证 JWT 签名.
I'm reading openssh format elliptic curve public keys (RFC 5656, section 3.1) and would like to get from a BigInteger Q value to an ECPublicKey
instance using JCE (rather than say BouncyCastle). I want to do this to verify JWT signatures.
例如 https://api.github.com/users/davidcarboni/keys :>
ecdsa-sha2-nistp256 AAAAE2VjZHNhLXNoYTItbmlzdHAyNTYAAAAIbmlzdHAyNTYAAABBBK8hPtB72/sfYgNw1WTska2DNOJFx+QhUxuV6OLINSD2ty+6gxcM8yZrvMqWdMePGRb2cGh8L/0bGOk+64IQ/pM=
看起来我可以使用ECPublicKeySpec
.这需要两个参数. ECPoint
和ECParameterSpec
.我可以使用以下JCE代码(以及密钥数据中的openssh标识符,例如"nistp256")来获取参数规范:
It looks like I can use ECPublicKeySpec
. This takes two parameters. An ECPoint
and an ECParameterSpec
. I'm able to get the parameter spec using the following JCE code (and the openssh identifier from the key data, say "nistp256"):
ECParameterSpec getECParameterSpec(String identifier) {
try {
AlgorithmParameters parameters = AlgorithmParameters.getInstance("EC");
String name = identifier.replace("nist", "sec") + "r1";
parameters.init(new ECGenParameterSpec(name));
return parameters.getParameterSpec(ECParameterSpec.class);
} catch (InvalidParameterSpecException | NoSuchAlgorithmException e) {
throw new IllegalArgumentException("Unable to get parameter spec for identifier " + identifier, e);
}
}
我已经成功地从关键数据中解析了Q值. RFC 5656告诉我"Q是从椭圆曲线点编码为八位字节串的公共密钥"),但是JCE的ECPoint
类的构造函数采用两个参数X和Y.
I've successfully parsed the Q value from the key data. RFC 5656 tells me that "Q is the public key encoded from an elliptic curve point into an octet string") however the constructor of JCE's ECPoint
class takes two parameters, X and Y.
我可以从Q转到X和Y,还是需要采用其他方法?
Can I get to X and Y from Q, or do I need to take a different approach?
(请注意,我完全无权使用私钥)
(NB I quite rightly don't have access to the private key)
推荐答案
您输入的base64部分具有等价的
The base64 portion of your input has the equivalent hex of
00 00 00 13 65 63 64 73 61 2D 73 68 61 32 2D 6E
69 73 74 70 32 35 36 00 00 00 08 6E 69 73 74 70
32 35 36 00 00 00 41 04 AF 21 3E D0 7B DB FB 1F
62 03 70 D5 64 EC 91 AD 83 34 E2 45 C7 E4 21 53
1B 95 E8 E2 C8 35 20 F6 B7 2F BA 83 17 0C F3 26
6B BC CA 96 74 C7 8F 19 16 F6 70 68 7C 2F FD 1B
18 E9 3E EB 82 10 FE 93
65 63 64以"ecd"的身份跳到我身上(肯定是"ecdsa-sha2-nistp256").
65 63 64 jumped out to me as "ecd" (sure enough, "ecdsa-sha2-nistp256").
所以斑点看起来是
- 字符串/有效载荷的大尾数长度(19)
- 字符串"ecdsa-sha2-nistp256"
- 字符串/有效载荷的大尾数长度(8)
- 字符串"nistp256"
- 有效载荷的大尾数长度(0x41 == 65)
- 编码的ECPoint Q(
04 AF 21 ... 10 FE 93
)
- Big Endian length of a string/payload (19)
- The string "ecdsa-sha2-nistp256"
- Big Endian length of a string/payload (8)
- The string "nistp256"
- Big Endian length of a payload (0x41 == 65)
- The encoded ECPoint Q (
04 AF 21 ... 10 FE 93
)
编码的ECPoint以04
开头,指示它是未压缩的点(最常见的编码). 04
编码规则(来自 http://www.secg.org/sec1-v2. pdf ,第2.3.5节,第3步)说,剩余有效载荷是X和Y,每个有效载荷都用零填充到曲线字段的编码大小.
The encoded ECPoint starts with 04
indicating it is an uncompressed point (the most common encoding). The 04
encoding rules (from http://www.secg.org/sec1-v2.pdf, 2.3.5, step 3) say that the remaining payload is X and Y, each left-padded with zeros to the encoding size of the curve field.
所以您的ECPoint看起来像
So your ECPoint looks like
04
Qx:
AF 21 3E D0 7B DB FB 1F 62 03 70 D5 64 EC 91 AD
83 34 E2 45 C7 E4 21 53 1B 95 E8 E2 C8 35 20 F6
Qy:
B7 2F BA 83 17 0C F3 26 6B BC CA 96 74 C7 8F 19
16 F6 70 68 7C 2F FD 1B 18 E9 3E EB 82 10 FE 93
在C#中,您需要a)反转Qx和Qy的每个字节(因为.NET BigInteger期望使用Little Endian,而这些是Big Endian),并且b)将填充0x00字节的重要性大于0xAF和0xB7字节,因为它们设置了高位(将被解释为负数).不知道Java是否有这些古怪之处.
In C# you'd need to a) reverse the bytes of each of Qx and Qy (because the .NET BigInteger expects Little Endian, and these are Big Endian) and b) put a padding 0x00 byte as more significant than the 0xAF and 0xB7 bytes, since they have their high bits set (and would be interpreted as negative numbers). Don't know if Java has either of those quirks.
这篇关于我可以从openssh公钥和ECParameterSpec的Q值创建JCE ECPublicKey吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!