【发布时间】:2020-02-12 22:32:54
【问题描述】:
我有一个未压缩的prime256v1 曲线的 EC 点,我正在尝试使用 BouncyCastle 提供程序使用以下代码(引用自 here)从中构造一个 PublicKey 对象:
public static void main(String[] args) throws Exception
{
// Using BC as SunEC (java8) doesn't support prime256v1.
Security.addProvider(new BouncyCastleProvider());
// Input values -----------------
// Complete EC Point (with uncompressed prefix 04 and the length [41])
// 0441044ef454741576ed945005ea87f114bf8045bcff84155914246aaef43bc35804c9537201ea2387f7edabf76e85b9a7fc341001ddda3272a9685d9aa36ff96526d9
// EC Point value w/o the tag and length
final String ecPointHex = "044ef454741576ed945005ea87f114bf8045bcff84155914246aaef43bc35804c9537201ea2387f7edabf76e85b9a7fc341001ddda3272a9685d9aa36ff96526d9";
// final String ecParamsHex = "06082a8648ce3d030107"; // prime256v1; OID: 1.2.840.10045.3.1.7
final String curveName = "prime256v1";
// ------------------------------
// EC Parameter Spec ------------
AlgorithmParameters params = AlgorithmParameters.getInstance("EC", "BC");
params.init(new ECGenParameterSpec(curveName));
ECParameterSpec ecParameterSpec = params.getParameterSpec(ECParameterSpec.class);
// ------------------------------
// EC Point ---------------------
byte[] ecPointBinary = Hex.decode(ecPointHex);
byte[] x = Arrays.copyOfRange(ecPointBinary, 0, ecPointBinary.length / 2);
byte[] y = Arrays.copyOfRange(ecPointBinary, ecPointBinary.length / 2, ecPointBinary.length);
ECPoint ecPoint = new ECPoint(new BigInteger(1, x), new BigInteger(1, y));
// ------------------------------
// Construct Public Key ---------
KeyFactory keyFactory = KeyFactory.getInstance("EC", "BC"); // Tried ECDSA as well
ECPublicKey ecPublicKey = (ECPublicKey) keyFactory.generatePublic(new ECPublicKeySpec(ecPoint, ecParameterSpec)); // <-- exception here
System.out.println(ecPublicKey);
// ------------------------------
}
但我得到了这个例外:
Exception in thread "main" java.lang.IllegalArgumentException: x value invalid for SecP256R1FieldElement
at org.bouncycastle.math.ec.custom.sec.SecP256R1FieldElement.<init>(Unknown Source)
at org.bouncycastle.math.ec.custom.sec.SecP256R1Curve.fromBigInteger(Unknown Source)
at org.bouncycastle.math.ec.ECCurve.createPoint(Unknown Source)
at org.bouncycastle.math.ec.ECCurve.createPoint(Unknown Source)
at org.bouncycastle.jcajce.provider.asymmetric.util.EC5Util.convertPoint(Unknown Source)
at org.bouncycastle.jcajce.provider.asymmetric.util.EC5Util.convertPoint(Unknown Source)
at org.bouncycastle.jcajce.provider.asymmetric.ec.BCECPublicKey.<init>(Unknown Source)
at org.bouncycastle.jcajce.provider.asymmetric.ec.KeyFactorySpi.engineGeneratePublic(Unknown Source)
at java.security.KeyFactory.generatePublic(KeyFactory.java:328)
at com.test.ECStackOverflow.main(ECStackOverflow.java:70)
我做错了什么?
P.S:此 PublicKey 是在 SafeNet HSM 中生成的,EC Point 和 Params 值是从 PublicKey 对象中检索的。
【问题讨论】:
标签: java cryptography bouncycastle elliptic-curve hsm