【发布时间】:2020-11-16 17:30:33
【问题描述】:
我正在向我的方法传递一个 byte[],并且我正在尝试生成一个 pubKey。看错误看起来好像我首先需要在生成 pubKey 之前解压缩。
如何解码压缩坐标?
private static PublicKey getPublicKeyFromBytes(byte[] pubKey) throws NoSuchAlgorithmException, InvalidKeySpecException
{
ECPoint point = new ECPoint(new BigInteger(pubKey), BigInteger.ZERO);
ECNamedCurveParameterSpec spec = ECNamedCurveTable.getParameterSpec("prime256v1");
KeyFactory kf = KeyFactory.getInstance("ECDSA", new BouncyCastleProvider());
ECNamedCurveSpec params = new ECNamedCurveSpec("prime256v1", spec.getCurve(), spec.getG(), spec.getN());
ECPublicKeySpec pubKeySpec = new ECPublicKeySpec(point, params);
ECPublicKey pk = (ECPublicKey) kf.generatePublic(pubKeySpec);
return pk;
}
错误信息:
Exception in thread "main" java.security.spec.InvalidKeySpecException: invalid KeySpec: x value invalid for SecP256R1FieldElement
at org.bouncycastle.jcajce.provider.asymmetric.ec.KeyFactorySpi.engineGeneratePublic(Unknown Source)
【问题讨论】:
-
处理方式取决于指定点是压缩的还是未压缩的,请参阅here。例如,如果指定为未压缩,则前导字节为 04,接下来的 32 个字节是 x 坐标,接下来的 32 个字节是 y 坐标(对于 prime256v1)。对于 x 和 y 无符号
BigIntegers 将被创建 (new BigInteger(1, ...)) 和ECPoint。 -
如果您可以包含您正在尝试读取的公钥,那么帮助您会更容易。只需包含
Base64.getEncoder().encodeToString(pubKey)的输出即可。 -
在我的机器上,
getPublicKeyFromBytes()触发未压缩和压缩 X9.62 密钥的已发布错误,即从错误无法断定您的数据代表未压缩或压缩密钥(甚至是另一种格式)。相比之下,loadPubKey()既适用于未压缩的 X9.62 密钥,也适用于压缩的 X9.62 密钥。由于您的数据使用后一种方法会触发错误,因此您的数据可能与 X9.62 格式不匹配。也许它是一个 X.509 密钥。如果你不想发布密钥,你可以检查这个,例如lapo.it/asn1js.
标签: java cryptography elliptic-curve