1a198e1ecc615e26a167d0f2dca9fa7e5fc62de10Brian Carlstrompackage org.bouncycastle.jcajce.provider.asymmetric.util; 28212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom 38212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstromimport java.math.BigInteger; 48212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstromimport java.security.spec.ECField; 58212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstromimport java.security.spec.ECFieldF2m; 68212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstromimport java.security.spec.ECFieldFp; 78212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstromimport java.security.spec.ECParameterSpec; 88212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstromimport java.security.spec.ECPoint; 98212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstromimport java.security.spec.EllipticCurve; 10d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Rootimport java.util.Enumeration; 11d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Rootimport java.util.HashMap; 12d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Rootimport java.util.Map; 138212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom 14d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Rootimport org.bouncycastle.asn1.x9.ECNamedCurveTable; 15d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Rootimport org.bouncycastle.asn1.x9.X9ECParameters; 16d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Rootimport org.bouncycastle.crypto.ec.CustomNamedCurves; 178212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstromimport org.bouncycastle.jce.spec.ECNamedCurveParameterSpec; 188212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstromimport org.bouncycastle.jce.spec.ECNamedCurveSpec; 19d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Rootimport org.bouncycastle.math.ec.ECAlgorithms; 208212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstromimport org.bouncycastle.math.ec.ECCurve; 218212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom 228212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrompublic class EC5Util 238212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom{ 24d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root private static Map customCurves = new HashMap(); 25d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root 26d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root static 27d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root { 28d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root Enumeration e = CustomNamedCurves.getNames(); 29d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root while (e.hasMoreElements()) 30d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root { 31d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root String name = (String)e.nextElement(); 32d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root 33d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root X9ECParameters curveParams = ECNamedCurveTable.getByName(name); 34d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root if (curveParams != null) // there may not be a regular curve, may just be a custom curve. 35d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root { 36d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root customCurves.put(curveParams.getCurve(), CustomNamedCurves.getByName(name).getCurve()); 37d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root } 38d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root } 39d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root } 40d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root 418212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom public static EllipticCurve convertCurve( 428212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom ECCurve curve, 438212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom byte[] seed) 448212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom { 458212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom // TODO: the Sun EC implementation doesn't currently handle the seed properly 468212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom // so at the moment it's set to null. Should probably look at making this configurable 47d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root if (ECAlgorithms.isFpCurve(curve)) 488212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom { 49d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root return new EllipticCurve(new ECFieldFp(curve.getField().getCharacteristic()), curve.getA().toBigInteger(), curve.getB().toBigInteger(), null); 508212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom } 518212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom else 528212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom { 538212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom ECCurve.F2m curveF2m = (ECCurve.F2m)curve; 548212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom int ks[]; 558212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom 568212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom if (curveF2m.isTrinomial()) 578212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom { 588212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom ks = new int[] { curveF2m.getK1() }; 598212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom 608212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom return new EllipticCurve(new ECFieldF2m(curveF2m.getM(), ks), curve.getA().toBigInteger(), curve.getB().toBigInteger(), null); 618212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom } 628212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom else 638212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom { 648212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom ks = new int[] { curveF2m.getK3(), curveF2m.getK2(), curveF2m.getK1() }; 658212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom 668212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom return new EllipticCurve(new ECFieldF2m(curveF2m.getM(), ks), curve.getA().toBigInteger(), curve.getB().toBigInteger(), null); 678212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom } 688212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom } 698212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom } 708212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom 718212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom public static ECCurve convertCurve( 728212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom EllipticCurve ec) 738212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom { 748212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom ECField field = ec.getField(); 758212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom BigInteger a = ec.getA(); 768212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom BigInteger b = ec.getB(); 778212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom 788212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom if (field instanceof ECFieldFp) 798212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom { 80d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root ECCurve.Fp curve = new ECCurve.Fp(((ECFieldFp)field).getP(), a, b); 81d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root 82d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root if (customCurves.containsKey(curve)) 83d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root { 84d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root return (ECCurve)customCurves.get(curve); 85d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root } 86d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root 87d001700a15b8bd733ae344c1fc315b97c43c6590Kenny Root return curve; 888212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom } 898212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom else 908212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom { 918212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom ECFieldF2m fieldF2m = (ECFieldF2m)field; 928212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom int m = fieldF2m.getM(); 938212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom int ks[] = ECUtil.convertMidTerms(fieldF2m.getMidTermsOfReductionPolynomial()); 948212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom return new ECCurve.F2m(m, ks[0], ks[1], ks[2], a, b); 958212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom } 968212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom } 978212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom 988212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom public static ECParameterSpec convertSpec( 998212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom EllipticCurve ellipticCurve, 1008212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom org.bouncycastle.jce.spec.ECParameterSpec spec) 1018212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom { 1028212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom if (spec instanceof ECNamedCurveParameterSpec) 1038212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom { 1048212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom return new ECNamedCurveSpec( 1058212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom ((ECNamedCurveParameterSpec)spec).getName(), 1068212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom ellipticCurve, 1078212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom new ECPoint( 1085db505e1f6a68c8d5dfdb0fed0b8607dea7bed96Kenny Root spec.getG().getAffineXCoord().toBigInteger(), 1095db505e1f6a68c8d5dfdb0fed0b8607dea7bed96Kenny Root spec.getG().getAffineYCoord().toBigInteger()), 1108212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom spec.getN(), 1118212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom spec.getH()); 1128212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom } 1138212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom else 1148212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom { 1158212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom return new ECParameterSpec( 1168212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom ellipticCurve, 1178212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom new ECPoint( 1185db505e1f6a68c8d5dfdb0fed0b8607dea7bed96Kenny Root spec.getG().getAffineXCoord().toBigInteger(), 1195db505e1f6a68c8d5dfdb0fed0b8607dea7bed96Kenny Root spec.getG().getAffineYCoord().toBigInteger()), 1208212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom spec.getN(), 1218212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom spec.getH().intValue()); 1228212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom } 1238212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom } 1248212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom 1258212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom public static org.bouncycastle.jce.spec.ECParameterSpec convertSpec( 1268212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom ECParameterSpec ecSpec, 1278212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom boolean withCompression) 1288212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom { 1298212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom ECCurve curve = convertCurve(ecSpec.getCurve()); 1308212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom 1318212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom return new org.bouncycastle.jce.spec.ECParameterSpec( 1328212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom curve, 1338212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom convertPoint(curve, ecSpec.getGenerator(), withCompression), 1348212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom ecSpec.getOrder(), 1358212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom BigInteger.valueOf(ecSpec.getCofactor()), 1368212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom ecSpec.getCurve().getSeed()); 1378212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom } 1388212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom 1398212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom public static org.bouncycastle.math.ec.ECPoint convertPoint( 1408212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom ECParameterSpec ecSpec, 1418212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom ECPoint point, 1428212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom boolean withCompression) 1438212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom { 1448212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom return convertPoint(convertCurve(ecSpec.getCurve()), point, withCompression); 1458212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom } 1468212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom 1478212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom public static org.bouncycastle.math.ec.ECPoint convertPoint( 1488212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom ECCurve curve, 1498212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom ECPoint point, 1508212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom boolean withCompression) 1518212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom { 1528212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom return curve.createPoint(point.getAffineX(), point.getAffineY(), withCompression); 1538212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom } 1548212855a312dc8ebe081a3e08b1d2d8f8757af02Brian Carlstrom} 155