diff options
Diffstat (limited to 'bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric')
48 files changed, 761 insertions, 310 deletions
diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/DH.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/DH.java index 0f7d202..5b6b8c4 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/DH.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/DH.java @@ -1,5 +1,8 @@ package org.bouncycastle.jcajce.provider.asymmetric; +import org.bouncycastle.asn1.pkcs.PKCSObjectIdentifiers; +import org.bouncycastle.asn1.x9.X9ObjectIdentifiers; +import org.bouncycastle.jcajce.provider.asymmetric.dh.KeyFactorySpi; import org.bouncycastle.jcajce.provider.config.ConfigurableProvider; import org.bouncycastle.jcajce.provider.util.AsymmetricAlgorithmProvider; @@ -36,6 +39,9 @@ public class DH provider.addAlgorithm("Cipher.DHIESwithAES", PREFIX + "IESCipher$IESwithAES"); provider.addAlgorithm("Cipher.DHIESWITHAES", PREFIX + "IESCipher$IESwithAES"); provider.addAlgorithm("Cipher.DHIESWITHDESEDE", PREFIX + "IESCipher$IESwithDESede"); + + registerOid(provider, PKCSObjectIdentifiers.dhKeyAgreement, "DH", new KeyFactorySpi()); + registerOid(provider, X9ObjectIdentifiers.dhpublicnumber, "DH", new KeyFactorySpi()); } } } diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/EC.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/EC.java index d06e05c..d7b437c 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/EC.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/EC.java @@ -1,5 +1,6 @@ package org.bouncycastle.jcajce.provider.asymmetric; +import org.bouncycastle.asn1.bsi.BSIObjectIdentifiers; import org.bouncycastle.asn1.eac.EACObjectIdentifiers; import org.bouncycastle.asn1.teletrust.TeleTrusTObjectIdentifiers; import org.bouncycastle.asn1.x9.X9ObjectIdentifiers; @@ -25,6 +26,7 @@ public class EC provider.addAlgorithm("KeyAgreement.ECMQV", PREFIX + "KeyAgreementSpi$MQV"); provider.addAlgorithm("KeyAgreement." + X9ObjectIdentifiers.dhSinglePass_stdDH_sha1kdf_scheme, PREFIX + "KeyAgreementSpi$DHwithSHA1KDF"); provider.addAlgorithm("KeyAgreement." + X9ObjectIdentifiers.mqvSinglePass_sha1kdf_scheme, PREFIX + "KeyAgreementSpi$MQVwithSHA1KDF"); + provider.addAlgorithm("KeyAgreement.ECDHWITHSHA1KDF", PREFIX + "KeyAgreementSpi$DHwithSHA1KDF"); registerOid(provider, X9ObjectIdentifiers.id_ecPublicKey, "EC", new KeyFactorySpi.EC()); // TODO Should this be an alias for ECDH? @@ -45,6 +47,7 @@ public class EC provider.addAlgorithm("KeyPairGenerator.EC", PREFIX + "KeyPairGeneratorSpi$EC"); provider.addAlgorithm("KeyPairGenerator.ECDSA", PREFIX + "KeyPairGeneratorSpi$ECDSA"); provider.addAlgorithm("KeyPairGenerator.ECDH", PREFIX + "KeyPairGeneratorSpi$ECDH"); + provider.addAlgorithm("KeyPairGenerator.ECDHWITHSHA1KDF", PREFIX + "KeyPairGeneratorSpi$ECDH"); provider.addAlgorithm("KeyPairGenerator.ECDHC", PREFIX + "KeyPairGeneratorSpi$ECDHC"); provider.addAlgorithm("KeyPairGenerator.ECIES", PREFIX + "KeyPairGeneratorSpi$ECDH"); provider.addAlgorithm("KeyPairGenerator.ECMQV", PREFIX + "KeyPairGeneratorSpi$ECMQV"); @@ -54,6 +57,10 @@ public class EC provider.addAlgorithm("Cipher.ECIESWITHAES", PREFIX + "IESCipher$ECIESwithAES"); provider.addAlgorithm("Cipher.ECIESwithDESEDE", PREFIX + "IESCipher$ECIESwithDESede"); provider.addAlgorithm("Cipher.ECIESWITHDESEDE", PREFIX + "IESCipher$ECIESwithDESede"); + provider.addAlgorithm("Cipher.ECIESwithAES-CBC", PREFIX + "IESCipher$ECIESwithAESCBC"); + provider.addAlgorithm("Cipher.ECIESWITHAES-CBC", PREFIX + "IESCipher$ECIESwithAESCBC"); + provider.addAlgorithm("Cipher.ECIESwithDESEDE-CBC", PREFIX + "IESCipher$ECIESwithDESedeCBC"); + provider.addAlgorithm("Cipher.ECIESWITHDESEDE-CBC", PREFIX + "IESCipher$ECIESwithDESedeCBC"); provider.addAlgorithm("Signature.ECDSA", PREFIX + "SignatureSpi$ecDSA"); provider.addAlgorithm("Signature.NONEwithECDSA", PREFIX + "SignatureSpi$ecDSAnone"); @@ -91,6 +98,13 @@ public class EC addSignatureAlgorithm(provider, "SHA256", "CVC-ECDSA", PREFIX + "SignatureSpi$ecCVCDSA256", EACObjectIdentifiers.id_TA_ECDSA_SHA_256); addSignatureAlgorithm(provider, "SHA384", "CVC-ECDSA", PREFIX + "SignatureSpi$ecCVCDSA384", EACObjectIdentifiers.id_TA_ECDSA_SHA_384); addSignatureAlgorithm(provider, "SHA512", "CVC-ECDSA", PREFIX + "SignatureSpi$ecCVCDSA512", EACObjectIdentifiers.id_TA_ECDSA_SHA_512); + + addSignatureAlgorithm(provider, "SHA1", "PLAIN-ECDSA", PREFIX + "SignatureSpi$ecCVCDSA", BSIObjectIdentifiers.ecdsa_plain_SHA1); + addSignatureAlgorithm(provider, "SHA224", "PLAIN-ECDSA", PREFIX + "SignatureSpi$ecCVCDSA224", BSIObjectIdentifiers.ecdsa_plain_SHA224); + addSignatureAlgorithm(provider, "SHA256", "PLAIN-ECDSA", PREFIX + "SignatureSpi$ecCVCDSA256", BSIObjectIdentifiers.ecdsa_plain_SHA256); + addSignatureAlgorithm(provider, "SHA384", "PLAIN-ECDSA", PREFIX + "SignatureSpi$ecCVCDSA384", BSIObjectIdentifiers.ecdsa_plain_SHA384); + addSignatureAlgorithm(provider, "SHA512", "PLAIN-ECDSA", PREFIX + "SignatureSpi$ecCVCDSA512", BSIObjectIdentifiers.ecdsa_plain_SHA512); + addSignatureAlgorithm(provider, "RIPEMD160", "PLAIN-ECDSA", PREFIX + "SignatureSpi$ecPlainDSARP160", BSIObjectIdentifiers.ecdsa_plain_RIPEMD160); } } } diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/RSA.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/RSA.java index 70fe386..b65b859 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/RSA.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/RSA.java @@ -80,6 +80,10 @@ public class RSA provider.addAlgorithm("Signature." + PKCSObjectIdentifiers.id_RSASSA_PSS, PREFIX + "PSSSignatureSpi$PSSwithRSA"); provider.addAlgorithm("Signature.OID." + PKCSObjectIdentifiers.id_RSASSA_PSS, PREFIX + "PSSSignatureSpi$PSSwithRSA"); + provider.addAlgorithm("Signature.SHA224WITHRSAANDMGF1", PREFIX + "PSSSignatureSpi$SHA224withRSA"); + provider.addAlgorithm("Signature.SHA256WITHRSAANDMGF1", PREFIX + "PSSSignatureSpi$SHA256withRSA"); + provider.addAlgorithm("Signature.SHA384WITHRSAANDMGF1", PREFIX + "PSSSignatureSpi$SHA384withRSA"); + provider.addAlgorithm("Signature.SHA512WITHRSAANDMGF1", PREFIX + "PSSSignatureSpi$SHA512withRSA"); provider.addAlgorithm("Signature.SHA224withRSA/PSS", PREFIX + "PSSSignatureSpi$SHA224withRSA"); provider.addAlgorithm("Signature.SHA256withRSA/PSS", PREFIX + "PSSSignatureSpi$SHA256withRSA"); provider.addAlgorithm("Signature.SHA384withRSA/PSS", PREFIX + "PSSSignatureSpi$SHA384withRSA"); @@ -101,10 +105,6 @@ public class RSA provider.addAlgorithm("Alg.Alias.Signature.SHA256withRSAandMGF1", "SHA256withRSA/PSS"); provider.addAlgorithm("Alg.Alias.Signature.SHA384withRSAandMGF1", "SHA384withRSA/PSS"); provider.addAlgorithm("Alg.Alias.Signature.SHA512withRSAandMGF1", "SHA512withRSA/PSS"); - provider.addAlgorithm("Alg.Alias.Signature.SHA224WITHRSAANDMGF1", "SHA224withRSA/PSS"); - provider.addAlgorithm("Alg.Alias.Signature.SHA256WITHRSAANDMGF1", "SHA256withRSA/PSS"); - provider.addAlgorithm("Alg.Alias.Signature.SHA384WITHRSAANDMGF1", "SHA384withRSA/PSS"); - provider.addAlgorithm("Alg.Alias.Signature.SHA512WITHRSAANDMGF1", "SHA512withRSA/PSS"); if (provider.hasAlgorithm("MessageDigest", "MD2")) { @@ -137,6 +137,10 @@ public class RSA provider.addAlgorithm("Signature.SHA1withRSA/ISO9796-2", PREFIX + "ISOSignatureSpi$SHA1WithRSAEncryption"); provider.addAlgorithm("Alg.Alias.Signature." + OIWObjectIdentifiers.sha1WithRSA, "SHA1WITHRSA"); provider.addAlgorithm("Alg.Alias.Signature.OID." + OIWObjectIdentifiers.sha1WithRSA, "SHA1WITHRSA"); + + provider.addAlgorithm("Alg.Alias.Signature.SHA1withRSA/X9.31", "SHA1WITHRSA/X9.31"); + provider.addAlgorithm("Alg.Alias.Signature.SHA1WithRSA/X9.31", "SHA1WITHRSA/X9.31"); + provider.addAlgorithm("Signature.SHA1WITHRSA/X9.31", PREFIX + "X931SignatureSpi$SHA1WithRSAEncryption"); } addDigestSignature(provider, "SHA224", PREFIX + "DigestSignatureSpi$SHA224", PKCSObjectIdentifiers.sha224WithRSAEncryption); @@ -144,10 +148,26 @@ public class RSA addDigestSignature(provider, "SHA384", PREFIX + "DigestSignatureSpi$SHA384", PKCSObjectIdentifiers.sha384WithRSAEncryption); addDigestSignature(provider, "SHA512", PREFIX + "DigestSignatureSpi$SHA512", PKCSObjectIdentifiers.sha512WithRSAEncryption); + provider.addAlgorithm("Alg.Alias.Signature.SHA224withRSA/X9.31", "SHA224WITHRSA/X9.31"); + provider.addAlgorithm("Alg.Alias.Signature.SHA224WithRSA/X9.31", "SHA224WITHRSA/X9.31"); + provider.addAlgorithm("Signature.SHA224WITHRSA/X9.31", PREFIX + "X931SignatureSpi$SHA224WithRSAEncryption"); + provider.addAlgorithm("Alg.Alias.Signature.SHA256withRSA/X9.31", "SHA256WITHRSA/X9.31"); + provider.addAlgorithm("Alg.Alias.Signature.SHA256WithRSA/X9.31", "SHA256WITHRSA/X9.31"); + provider.addAlgorithm("Signature.SHA256WITHRSA/X9.31", PREFIX + "X931SignatureSpi$SHA256WithRSAEncryption"); + provider.addAlgorithm("Alg.Alias.Signature.SHA384withRSA/X9.31", "SHA384WITHRSA/X9.31"); + provider.addAlgorithm("Alg.Alias.Signature.SHA384WithRSA/X9.31", "SHA384WITHRSA/X9.31"); + provider.addAlgorithm("Signature.SHA384WITHRSA/X9.31", PREFIX + "X931SignatureSpi$SHA384WithRSAEncryption"); + provider.addAlgorithm("Alg.Alias.Signature.SHA512withRSA/X9.31", "SHA512WITHRSA/X9.31"); + provider.addAlgorithm("Alg.Alias.Signature.SHA512WithRSA/X9.31", "SHA512WITHRSA/X9.31"); + provider.addAlgorithm("Signature.SHA512WITHRSA/X9.31", PREFIX + "X931SignatureSpi$SHA512WithRSAEncryption"); + if (provider.hasAlgorithm("MessageDigest", "RIPEMD128")) { addDigestSignature(provider, "RIPEMD128", PREFIX + "DigestSignatureSpi$RIPEMD128", TeleTrusTObjectIdentifiers.rsaSignatureWithripemd128); addDigestSignature(provider, "RMD128", PREFIX + "DigestSignatureSpi$RIPEMD128", null); + provider.addAlgorithm("Alg.Alias.Signature.RIPEMD128withRSA/X9.31", "RIPEMD128WITHRSA/X9.31"); + provider.addAlgorithm("Alg.Alias.Signature.RIPEMD128WithRSA/X9.31", "RIPEMD128WITHRSA/X9.31"); + provider.addAlgorithm("Signature.RIPEMD128WITHRSA/X9.31", PREFIX + "X931SignatureSpi$RIPEMD128WithRSAEncryption"); } if (provider.hasAlgorithm("MessageDigest", "RIPEMD160")) @@ -156,6 +176,9 @@ public class RSA addDigestSignature(provider, "RMD160", PREFIX + "DigestSignatureSpi$RIPEMD160", null); provider.addAlgorithm("Alg.Alias.Signature.RIPEMD160WithRSA/ISO9796-2", "RIPEMD160withRSA/ISO9796-2"); provider.addAlgorithm("Signature.RIPEMD160withRSA/ISO9796-2", PREFIX + "ISOSignatureSpi$RIPEMD160WithRSAEncryption"); + provider.addAlgorithm("Alg.Alias.Signature.RIPEMD160withRSA/X9.31", "RIPEMD160WITHRSA/X9.31"); + provider.addAlgorithm("Alg.Alias.Signature.RIPEMD160WithRSA/X9.31", "RIPEMD160WITHRSA/X9.31"); + provider.addAlgorithm("Signature.RIPEMD160WITHRSA/X9.31", PREFIX + "X931SignatureSpi$RIPEMD160WithRSAEncryption"); } if (provider.hasAlgorithm("MessageDigest", "RIPEMD256")) @@ -163,6 +186,14 @@ public class RSA addDigestSignature(provider, "RIPEMD256", PREFIX + "DigestSignatureSpi$RIPEMD256", TeleTrusTObjectIdentifiers.rsaSignatureWithripemd256); addDigestSignature(provider, "RMD256", PREFIX + "DigestSignatureSpi$RIPEMD256", null); } + + if (provider.hasAlgorithm("MessageDigest", "WHIRLPOOL")) + { + provider.addAlgorithm("Alg.Alias.Signature.WhirlpoolWithRSA/X9.31", "WHIRLPOOLWITHRSA/X9.31"); + provider.addAlgorithm("Alg.Alias.Signature.WHIRLPOOLwithRSA/X9.31", "WHIRLPOOLWITHRSA/X9.31"); + provider.addAlgorithm("Alg.Alias.Signature.WHIRLPOOLWithRSA/X9.31", "WHIRLPOOLWITHRSA/X9.31"); + provider.addAlgorithm("Signature.WHIRLPOOLWITHRSA/X9.31", PREFIX + "X931SignatureSpi$WhirlpoolWithRSAEncryption"); + } } private void addDigestSignature( diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dh/AlgorithmParameterGeneratorSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dh/AlgorithmParameterGeneratorSpi.java index 8bdcc55..e4c8172 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dh/AlgorithmParameterGeneratorSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dh/AlgorithmParameterGeneratorSpi.java @@ -10,10 +10,10 @@ import javax.crypto.spec.DHParameterSpec; import org.bouncycastle.crypto.generators.DHParametersGenerator; import org.bouncycastle.crypto.params.DHParameters; -import org.bouncycastle.jce.provider.BouncyCastleProvider; +import org.bouncycastle.jcajce.provider.asymmetric.util.BaseAlgorithmParameterGeneratorSpi; public class AlgorithmParameterGeneratorSpi - extends java.security.AlgorithmParameterGeneratorSpi + extends BaseAlgorithmParameterGeneratorSpi { protected SecureRandom random; protected int strength = 1024; @@ -63,7 +63,7 @@ public class AlgorithmParameterGeneratorSpi try { - params = AlgorithmParameters.getInstance("DH", BouncyCastleProvider.PROVIDER_NAME); + params = createParametersInstance("DH"); params.init(new DHParameterSpec(p.getP(), p.getG(), l)); } catch (Exception e) diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dh/IESCipher.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dh/IESCipher.java index c29ff2d..df6b6f9 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dh/IESCipher.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dh/IESCipher.java @@ -7,8 +7,10 @@ import java.security.InvalidKeyException; import java.security.Key; import java.security.NoSuchAlgorithmException; import java.security.PrivateKey; +import java.security.Provider; import java.security.PublicKey; import java.security.SecureRandom; +import java.security.Security; import java.security.spec.AlgorithmParameterSpec; import javax.crypto.BadPaddingException; @@ -43,6 +45,8 @@ import org.bouncycastle.crypto.params.IESWithCipherParameters; import org.bouncycastle.crypto.parsers.DHIESPublicKeyParser; import org.bouncycastle.jcajce.provider.asymmetric.util.DHUtil; import org.bouncycastle.jcajce.provider.asymmetric.util.IESUtil; +import org.bouncycastle.jcajce.util.BCJcaJceHelper; +import org.bouncycastle.jcajce.util.JcaJceHelper; import org.bouncycastle.jce.interfaces.IESKey; import org.bouncycastle.jce.provider.BouncyCastleProvider; import org.bouncycastle.jce.spec.IESParameterSpec; @@ -53,6 +57,8 @@ import org.bouncycastle.util.Strings; public class IESCipher extends CipherSpi { + private final JcaJceHelper helper = new BCJcaJceHelper(); + private IESEngine engine; private int state = -1; private ByteArrayOutputStream buffer = new ByteArrayOutputStream(); @@ -106,7 +112,7 @@ public class IESCipher { try { - engineParam = AlgorithmParameters.getInstance("IES", BouncyCastleProvider.PROVIDER_NAME); + engineParam = helper.createAlgorithmParameters("IES"); engineParam.init(engineSpec); } catch (Exception e) @@ -465,7 +471,6 @@ public class IESCipher } - /** * Classes that inherit from us */ diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dsa/AlgorithmParameterGeneratorSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dsa/AlgorithmParameterGeneratorSpi.java index d850e5d..2d7c4c5 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dsa/AlgorithmParameterGeneratorSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dsa/AlgorithmParameterGeneratorSpi.java @@ -11,10 +11,10 @@ import org.bouncycastle.crypto.digests.SHA256Digest; import org.bouncycastle.crypto.generators.DSAParametersGenerator; import org.bouncycastle.crypto.params.DSAParameterGenerationParameters; import org.bouncycastle.crypto.params.DSAParameters; -import org.bouncycastle.jce.provider.BouncyCastleProvider; +import org.bouncycastle.jcajce.provider.asymmetric.util.BaseAlgorithmParameterGeneratorSpi; public class AlgorithmParameterGeneratorSpi - extends java.security.AlgorithmParameterGeneratorSpi + extends BaseAlgorithmParameterGeneratorSpi { protected SecureRandom random; protected int strength = 1024; @@ -90,7 +90,7 @@ public class AlgorithmParameterGeneratorSpi try { - params = AlgorithmParameters.getInstance("DSA", BouncyCastleProvider.PROVIDER_NAME); + params = createParametersInstance("DSA"); params.init(new DSAParameterSpec(p.getP(), p.getQ(), p.getG())); } catch (Exception e) diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dsa/AlgorithmParametersSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dsa/AlgorithmParametersSpi.java index 61fa33c..5722479 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dsa/AlgorithmParametersSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dsa/AlgorithmParametersSpi.java @@ -33,7 +33,6 @@ public class AlgorithmParametersSpi /** * Return the X.509 ASN.1 structure DSAParameter. - * <p/> * <pre> * DSAParameter ::= SEQUENCE { * prime INTEGER, -- p diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dsa/KeyPairGeneratorSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dsa/KeyPairGeneratorSpi.java index c6ddf9b..d2c2c71 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dsa/KeyPairGeneratorSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dsa/KeyPairGeneratorSpi.java @@ -34,9 +34,9 @@ public class KeyPairGeneratorSpi int strength, SecureRandom random) { - if (strength < 512 || strength > 1024 || strength % 64 != 0) + if (strength < 512 || strength > 4096 || ((strength < 1024) && strength % 64 != 0) || (strength >= 1024 && strength % 1024 != 0)) { - throw new InvalidParameterException("strength must be from 512 - 1024 and a multiple of 64"); + throw new InvalidParameterException("strength must be from 512 - 4096 and a multiple of 1024 above 1024"); } this.strength = strength; diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dstu/BCDSTU4145PrivateKey.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dstu/BCDSTU4145PrivateKey.java index 9b7e797..27d4b45 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dstu/BCDSTU4145PrivateKey.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dstu/BCDSTU4145PrivateKey.java @@ -13,12 +13,11 @@ import java.util.Enumeration; import org.bouncycastle.asn1.ASN1Encodable; import org.bouncycastle.asn1.ASN1Encoding; +import org.bouncycastle.asn1.ASN1Integer; import org.bouncycastle.asn1.ASN1ObjectIdentifier; import org.bouncycastle.asn1.ASN1Primitive; import org.bouncycastle.asn1.DERBitString; -import org.bouncycastle.asn1.DERInteger; import org.bouncycastle.asn1.DERNull; -import org.bouncycastle.asn1.DERObjectIdentifier; import org.bouncycastle.asn1.pkcs.PrivateKeyInfo; import org.bouncycastle.asn1.ua.DSTU4145NamedCurves; import org.bouncycastle.asn1.ua.UAObjectIdentifiers; @@ -244,9 +243,9 @@ public class BCDSTU4145PrivateKey } ASN1Encodable privKey = info.parsePrivateKey(); - if (privKey instanceof DERInteger) + if (privKey instanceof ASN1Integer) { - DERInteger derD = DERInteger.getInstance(privKey); + ASN1Integer derD = ASN1Integer.getInstance(privKey); this.d = derD.getValue(); } @@ -283,19 +282,22 @@ public class BCDSTU4145PrivateKey public byte[] getEncoded() { X962Parameters params; + int orderBitLength; if (ecSpec instanceof ECNamedCurveSpec) { - DERObjectIdentifier curveOid = ECUtil.getNamedCurveOid(((ECNamedCurveSpec)ecSpec).getName()); + ASN1ObjectIdentifier curveOid = ECUtil.getNamedCurveOid(((ECNamedCurveSpec)ecSpec).getName()); if (curveOid == null) // guess it's the OID { - curveOid = new DERObjectIdentifier(((ECNamedCurveSpec)ecSpec).getName()); + curveOid = new ASN1ObjectIdentifier(((ECNamedCurveSpec)ecSpec).getName()); } params = new X962Parameters(curveOid); + orderBitLength = ECUtil.getOrderBitLength(ecSpec.getOrder(), this.getS()); } else if (ecSpec == null) { params = new X962Parameters(DERNull.INSTANCE); + orderBitLength = ECUtil.getOrderBitLength(null, this.getS()); } else { @@ -309,6 +311,7 @@ public class BCDSTU4145PrivateKey ecSpec.getCurve().getSeed()); params = new X962Parameters(ecP); + orderBitLength = ECUtil.getOrderBitLength(ecSpec.getOrder(), this.getS()); } PrivateKeyInfo info; @@ -316,11 +319,11 @@ public class BCDSTU4145PrivateKey if (publicKey != null) { - keyStructure = new org.bouncycastle.asn1.sec.ECPrivateKey(this.getS(), publicKey, params); + keyStructure = new org.bouncycastle.asn1.sec.ECPrivateKey(orderBitLength, this.getS(), publicKey, params); } else { - keyStructure = new org.bouncycastle.asn1.sec.ECPrivateKey(this.getS(), params); + keyStructure = new org.bouncycastle.asn1.sec.ECPrivateKey(orderBitLength, this.getS(), params); } try diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dstu/BCDSTU4145PublicKey.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dstu/BCDSTU4145PublicKey.java index c641ee9..11c52a7 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dstu/BCDSTU4145PublicKey.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/dstu/BCDSTU4145PublicKey.java @@ -36,6 +36,8 @@ import org.bouncycastle.jce.provider.BouncyCastleProvider; import org.bouncycastle.jce.spec.ECNamedCurveParameterSpec; import org.bouncycastle.jce.spec.ECNamedCurveSpec; import org.bouncycastle.math.ec.ECCurve; +import org.bouncycastle.math.ec.custom.sec.SecP256K1Point; +import org.bouncycastle.math.ec.custom.sec.SecP256R1Point; public class BCDSTU4145PublicKey implements ECPublicKey, org.bouncycastle.jce.interfaces.ECPublicKey, ECPointEncoder @@ -352,14 +354,7 @@ public class BCDSTU4145PublicKey { if (ecSpec == null) { - if (q instanceof org.bouncycastle.math.ec.ECPoint.Fp) - { - return new org.bouncycastle.math.ec.ECPoint.Fp(null, q.getAffineXCoord(), q.getAffineYCoord()); - } - else - { - return new org.bouncycastle.math.ec.ECPoint.F2m(null, q.getAffineXCoord(), q.getAffineYCoord()); - } + return q.getDetachedPoint(); } return q; diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/BCECPrivateKey.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/BCECPrivateKey.java index 45d5b08..c9ad445 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/BCECPrivateKey.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/BCECPrivateKey.java @@ -282,7 +282,8 @@ public class BCECPrivateKey */ public byte[] getEncoded() { - X962Parameters params; + X962Parameters params; + int orderBitLength; if (ecSpec instanceof ECNamedCurveSpec) { @@ -293,10 +294,12 @@ public class BCECPrivateKey } params = new X962Parameters(curveOid); + orderBitLength = ECUtil.getOrderBitLength(ecSpec.getOrder(), this.getS()); } else if (ecSpec == null) { params = new X962Parameters(DERNull.INSTANCE); + orderBitLength = ECUtil.getOrderBitLength(null, this.getS()); } else { @@ -310,6 +313,7 @@ public class BCECPrivateKey ecSpec.getCurve().getSeed()); params = new X962Parameters(ecP); + orderBitLength = ECUtil.getOrderBitLength(ecSpec.getOrder(), this.getS()); } PrivateKeyInfo info; @@ -317,11 +321,11 @@ public class BCECPrivateKey if (publicKey != null) { - keyStructure = new org.bouncycastle.asn1.sec.ECPrivateKey(this.getS(), publicKey, params); + keyStructure = new org.bouncycastle.asn1.sec.ECPrivateKey(orderBitLength, this.getS(), publicKey, params); } else { - keyStructure = new org.bouncycastle.asn1.sec.ECPrivateKey(this.getS(), params); + keyStructure = new org.bouncycastle.asn1.sec.ECPrivateKey(orderBitLength, this.getS(), params); } try diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/BCECPublicKey.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/BCECPublicKey.java index 0eaae1d..ac0ddf5 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/BCECPublicKey.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/BCECPublicKey.java @@ -34,6 +34,8 @@ import org.bouncycastle.jce.interfaces.ECPointEncoder; import org.bouncycastle.jce.provider.BouncyCastleProvider; import org.bouncycastle.jce.spec.ECNamedCurveSpec; import org.bouncycastle.math.ec.ECCurve; +import org.bouncycastle.math.ec.custom.sec.SecP256K1Point; +import org.bouncycastle.math.ec.custom.sec.SecP256R1Point; public class BCECPublicKey implements ECPublicKey, org.bouncycastle.jce.interfaces.ECPublicKey, ECPointEncoder @@ -82,6 +84,8 @@ public class BCECPublicKey ECCurve curve = spec.getParams().getCurve(); EllipticCurve ellipticCurve = EC5Util.convertCurve(curve, spec.getParams().getSeed()); + // this may seem a little long-winded but it's how we pick up the custom curve. + this.q = EC5Util.convertCurve(ellipticCurve).createPoint(spec.getQ().getAffineXCoord().toBigInteger(), spec.getQ().getAffineYCoord().toBigInteger()); this.ecSpec = EC5Util.convertSpec(ellipticCurve, spec.getParams()); } else @@ -132,7 +136,6 @@ public class BCECPublicKey ECDomainParameters dp = params.getParameters(); this.algorithm = algorithm; - this.q = params.getQ(); if (spec == null) { @@ -147,6 +150,8 @@ public class BCECPublicKey this.ecSpec = EC5Util.convertSpec(ellipticCurve, spec); } + this.q = EC5Util.convertCurve(ecSpec.getCurve()).createPoint(params.getQ().getAffineXCoord().toBigInteger(), params.getQ().getAffineYCoord().toBigInteger()); + this.configuration = configuration; } @@ -369,14 +374,7 @@ public class BCECPublicKey { if (ecSpec == null) { - if (q instanceof org.bouncycastle.math.ec.ECPoint.Fp) - { - return new org.bouncycastle.math.ec.ECPoint.Fp(null, q.getAffineXCoord(), q.getAffineYCoord()); - } - else - { - return new org.bouncycastle.math.ec.ECPoint.F2m(null, q.getAffineXCoord(), q.getAffineYCoord()); - } + return q.getDetachedPoint(); } return q; diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/IESCipher.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/IESCipher.java index 4ad0512..fbeb8f0 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/IESCipher.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/IESCipher.java @@ -18,6 +18,7 @@ import javax.crypto.IllegalBlockSizeException; import javax.crypto.NoSuchPaddingException; import javax.crypto.ShortBufferException; +import org.bouncycastle.crypto.CipherParameters; import org.bouncycastle.crypto.InvalidCipherTextException; import org.bouncycastle.crypto.KeyEncoder; import org.bouncycastle.crypto.agreement.ECDHBasicAgreement; @@ -29,22 +30,22 @@ import org.bouncycastle.crypto.generators.ECKeyPairGenerator; import org.bouncycastle.crypto.generators.EphemeralKeyPairGenerator; import org.bouncycastle.crypto.generators.KDF2BytesGenerator; import org.bouncycastle.crypto.macs.HMac; +import org.bouncycastle.crypto.modes.CBCBlockCipher; import org.bouncycastle.crypto.paddings.PaddedBufferedBlockCipher; import org.bouncycastle.crypto.params.AsymmetricKeyParameter; import org.bouncycastle.crypto.params.ECDomainParameters; import org.bouncycastle.crypto.params.ECKeyGenerationParameters; import org.bouncycastle.crypto.params.ECKeyParameters; import org.bouncycastle.crypto.params.ECPublicKeyParameters; -import org.bouncycastle.crypto.params.IESParameters; import org.bouncycastle.crypto.params.IESWithCipherParameters; +import org.bouncycastle.crypto.params.ParametersWithIV; import org.bouncycastle.crypto.parsers.ECIESPublicKeyParser; import org.bouncycastle.jcajce.provider.asymmetric.util.ECUtil; import org.bouncycastle.jcajce.provider.asymmetric.util.IESUtil; +import org.bouncycastle.jcajce.util.BCJcaJceHelper; +import org.bouncycastle.jcajce.util.JcaJceHelper; import org.bouncycastle.jce.interfaces.ECKey; -import org.bouncycastle.jce.interfaces.ECPrivateKey; -import org.bouncycastle.jce.interfaces.ECPublicKey; import org.bouncycastle.jce.interfaces.IESKey; -import org.bouncycastle.jce.provider.BouncyCastleProvider; import org.bouncycastle.jce.spec.IESParameterSpec; import org.bouncycastle.util.Strings; @@ -52,6 +53,9 @@ import org.bouncycastle.util.Strings; public class IESCipher extends CipherSpi { + private final JcaJceHelper helper = new BCJcaJceHelper(); + + private int ivLength; private IESEngine engine; private int state = -1; private ByteArrayOutputStream buffer = new ByteArrayOutputStream(); @@ -65,8 +69,14 @@ public class IESCipher public IESCipher(IESEngine engine) { this.engine = engine; + this.ivLength = 0; } + public IESCipher(IESEngine engine, int ivLength) + { + this.engine = engine; + this.ivLength = ivLength; + } public int engineGetBlockSize() { @@ -99,14 +109,13 @@ public class IESCipher return null; } - public AlgorithmParameters engineGetParameters() { if (engineParam == null && engineSpec != null) { try { - engineParam = AlgorithmParameters.getInstance("IES", BouncyCastleProvider.PROVIDER_NAME); + engineParam = helper.createAlgorithmParameters("IES"); engineParam.init(engineSpec); } catch (Exception e) @@ -259,10 +268,24 @@ public class IESCipher throw new InvalidAlgorithmParameterException("must be passed IES parameters"); } + byte[] nonce = this.engineSpec.getNonce(); + + if (nonce != null) + { + if (ivLength == 0) + { + throw new InvalidAlgorithmParameterException("NONCE present in IES Parameters when none required"); + } + else if (nonce.length != ivLength) + { + throw new InvalidAlgorithmParameterException("NONCE in IES Parameters needs to be " + ivLength + " bytes long"); + } + } + // Parse the recipient's key if (opmode == Cipher.ENCRYPT_MODE || opmode == Cipher.WRAP_MODE) { - if (key instanceof ECPublicKey) + if (key instanceof PublicKey) { this.key = ECUtil.generatePublicKeyParameter((PublicKey)key); } @@ -280,7 +303,7 @@ public class IESCipher } else if (opmode == Cipher.DECRYPT_MODE || opmode == Cipher.UNWRAP_MODE) { - if (key instanceof ECPrivateKey) + if (key instanceof PrivateKey) { this.key = ECUtil.generatePrivateKeyParameter((PrivateKey)key); } @@ -368,11 +391,16 @@ public class IESCipher buffer.reset(); // Convert parameters for use in IESEngine - IESParameters params = new IESWithCipherParameters(engineSpec.getDerivationV(), + CipherParameters params = new IESWithCipherParameters(engineSpec.getDerivationV(), engineSpec.getEncodingV(), engineSpec.getMacKeySize(), engineSpec.getCipherKeySize()); + if (engineSpec.getNonce() != null) + { + params = new ParametersWithIV(params, engineSpec.getNonce()); + } + final ECDomainParameters ecParams = ((ECKeyParameters)key).getParameters(); final byte[] V; @@ -403,11 +431,12 @@ public class IESCipher ECKeyPairGenerator gen = new ECKeyPairGenerator(); gen.init(new ECKeyGenerationParameters(ecParams, random)); + final boolean usePointCompression = engineSpec.getPointCompression(); EphemeralKeyPairGenerator kGen = new EphemeralKeyPairGenerator(gen, new KeyEncoder() { public byte[] getEncoded(AsymmetricKeyParameter keyParameter) { - return ((ECPublicKeyParameters)keyParameter).getQ().getEncoded(); + return ((ECPublicKeyParameters)keyParameter).getQ().getEncoded(usePointCompression); } }); @@ -459,7 +488,6 @@ public class IESCipher return buf.length; } - /** * Classes that inherit from us */ @@ -498,4 +526,28 @@ public class IESCipher new PaddedBufferedBlockCipher(new AESEngine()))); } } + + static public class ECIESwithDESedeCBC + extends IESCipher + { + public ECIESwithDESedeCBC() + { + super(new IESEngine(new ECDHBasicAgreement(), + new KDF2BytesGenerator(new SHA1Digest()), + new HMac(new SHA1Digest()), + new PaddedBufferedBlockCipher(new CBCBlockCipher(new DESedeEngine()))), 8); + } + } + + static public class ECIESwithAESCBC + extends IESCipher + { + public ECIESwithAESCBC() + { + super(new IESEngine(new ECDHBasicAgreement(), + new KDF2BytesGenerator(new SHA1Digest()), + new HMac(new SHA1Digest()), + new PaddedBufferedBlockCipher(new CBCBlockCipher(new AESEngine()))), 16); + } + } } diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/KeyAgreementSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/KeyAgreementSpi.java index 0556378..4ea57fe 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/KeyAgreementSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/KeyAgreementSpi.java @@ -17,6 +17,7 @@ import javax.crypto.spec.SecretKeySpec; import org.bouncycastle.asn1.ASN1ObjectIdentifier; import org.bouncycastle.asn1.nist.NISTObjectIdentifiers; +import org.bouncycastle.asn1.oiw.OIWObjectIdentifiers; import org.bouncycastle.asn1.pkcs.PKCSObjectIdentifiers; import org.bouncycastle.asn1.x9.X9IntegerConverter; import org.bouncycastle.crypto.BasicAgreement; @@ -28,6 +29,7 @@ import org.bouncycastle.crypto.agreement.ECMQVBasicAgreement; import org.bouncycastle.crypto.agreement.kdf.DHKDFParameters; import org.bouncycastle.crypto.agreement.kdf.ECDHKEKGenerator; import org.bouncycastle.crypto.digests.SHA1Digest; +import org.bouncycastle.crypto.params.DESParameters; import org.bouncycastle.crypto.params.ECDomainParameters; import org.bouncycastle.crypto.params.ECPrivateKeyParameters; import org.bouncycastle.crypto.params.ECPublicKeyParameters; @@ -39,6 +41,7 @@ import org.bouncycastle.jce.interfaces.ECPublicKey; import org.bouncycastle.jce.interfaces.MQVPrivateKey; import org.bouncycastle.jce.interfaces.MQVPublicKey; import org.bouncycastle.util.Integers; +import org.bouncycastle.util.Strings; /** * Diffie-Hellman key agreement using elliptic curve keys, ala IEEE P1363 @@ -51,9 +54,12 @@ public class KeyAgreementSpi { private static final X9IntegerConverter converter = new X9IntegerConverter(); private static final Hashtable algorithms = new Hashtable(); + private static final Hashtable oids = new Hashtable(); + private static final Hashtable des = new Hashtable(); static { + Integer i64 = Integers.valueOf(64); Integer i128 = Integers.valueOf(128); Integer i192 = Integers.valueOf(192); Integer i256 = Integers.valueOf(256); @@ -65,6 +71,18 @@ public class KeyAgreementSpi algorithms.put(NISTObjectIdentifiers.id_aes192_wrap.getId(), i192); algorithms.put(NISTObjectIdentifiers.id_aes256_wrap.getId(), i256); algorithms.put(PKCSObjectIdentifiers.id_alg_CMS3DESwrap.getId(), i192); + algorithms.put(PKCSObjectIdentifiers.des_EDE3_CBC.getId(), i192); + algorithms.put(OIWObjectIdentifiers.desCBC.getId(), i64); + + oids.put("DESEDE", PKCSObjectIdentifiers.des_EDE3_CBC); + oids.put("AES", NISTObjectIdentifiers.id_aes256_CBC); + oids.put("DES", OIWObjectIdentifiers.desCBC); + + des.put("DES", "DES"); + des.put("DESEDE", "DES"); + des.put(OIWObjectIdentifiers.desCBC.getId(), "DES"); + des.put(PKCSObjectIdentifiers.des_EDE3_CBC.getId(), "DES"); + des.put(PKCSObjectIdentifiers.id_alg_CMS3DESwrap.getId(), "DES"); } private String kaAlgorithm; @@ -76,7 +94,7 @@ public class KeyAgreementSpi private byte[] bigIntToBytes( BigInteger r) { - return converter.integerToBytes(r, converter.getByteLength(parameters.getG().getAffineXCoord())); + return converter.integerToBytes(r, converter.getByteLength(parameters.getCurve())); } protected KeyAgreementSpi( @@ -175,17 +193,24 @@ public class KeyAgreementSpi throws NoSuchAlgorithmException { byte[] secret = bigIntToBytes(result); + String algKey = Strings.toUpperCase(algorithm); + String oidAlgorithm = algorithm; + + if (oids.containsKey(algKey)) + { + oidAlgorithm = ((ASN1ObjectIdentifier)oids.get(algKey)).getId(); + } if (kdf != null) { - if (!algorithms.containsKey(algorithm)) + if (!algorithms.containsKey(oidAlgorithm)) { throw new NoSuchAlgorithmException("unknown algorithm encountered: " + algorithm); } - int keySize = ((Integer)algorithms.get(algorithm)).intValue(); + int keySize = ((Integer)algorithms.get(oidAlgorithm)).intValue(); - DHKDFParameters params = new DHKDFParameters(new ASN1ObjectIdentifier(algorithm), keySize, secret); + DHKDFParameters params = new DHKDFParameters(new ASN1ObjectIdentifier(oidAlgorithm), keySize, secret); byte[] keyBytes = new byte[keySize / 8]; kdf.init(params); @@ -194,7 +219,21 @@ public class KeyAgreementSpi } else { - // TODO Should we be ensuring the key is the right length? + if (algorithms.containsKey(oidAlgorithm)) + { + Integer length = (Integer)algorithms.get(oidAlgorithm); + + byte[] key = new byte[length.intValue() / 8]; + + System.arraycopy(secret, 0, key, 0, key.length); + + secret = key; + } + } + + if (des.containsKey(oidAlgorithm)) + { + DESParameters.setOddParity(secret); } return new SecretKeySpec(secret, algorithm); @@ -206,6 +245,11 @@ public class KeyAgreementSpi SecureRandom random) throws InvalidKeyException, InvalidAlgorithmParameterException { + if (params != null) + { + throw new InvalidAlgorithmParameterException("No algorithm parameters supported"); + } + initFromKey(key); } diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/KeyPairGeneratorSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/KeyPairGeneratorSpi.java index f47f8a2..ae9be26 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/KeyPairGeneratorSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/KeyPairGeneratorSpi.java @@ -85,22 +85,20 @@ public abstract class KeyPairGeneratorSpi { this.strength = strength; this.random = random; + ECGenParameterSpec ecParams = (ECGenParameterSpec)ecParameters.get(Integers.valueOf(strength)); + if (ecParams == null) + { + throw new InvalidParameterException("unknown key size."); + } - if (ecParams != null) + try { - try - { - initialize(ecParams, random); - } - catch (InvalidAlgorithmParameterException e) - { - throw new InvalidParameterException("key size not configurable."); - } + initialize(ecParams, random); } - else + catch (InvalidAlgorithmParameterException e) { - throw new InvalidParameterException("unknown key size."); + throw new InvalidParameterException("key size not configurable."); } } @@ -109,97 +107,42 @@ public abstract class KeyPairGeneratorSpi SecureRandom random) throws InvalidAlgorithmParameterException { - if (params instanceof ECParameterSpec) + if (params == null) { - ECParameterSpec p = (ECParameterSpec)params; - this.ecParams = params; - - param = new ECKeyGenerationParameters(new ECDomainParameters(p.getCurve(), p.getG(), p.getN()), random); + ECParameterSpec implicitCA = configuration.getEcImplicitlyCa(); + if (implicitCA == null) + { + throw new InvalidAlgorithmParameterException("null parameter passed but no implicitCA set"); + } - engine.init(param); - initialised = true; + this.ecParams = null; + this.param = createKeyGenParamsBC(implicitCA, random); } - else if (params instanceof java.security.spec.ECParameterSpec) + else if (params instanceof ECParameterSpec) { - java.security.spec.ECParameterSpec p = (java.security.spec.ECParameterSpec)params; this.ecParams = params; - - ECCurve curve = EC5Util.convertCurve(p.getCurve()); - ECPoint g = EC5Util.convertPoint(curve, p.getGenerator(), false); - - param = new ECKeyGenerationParameters(new ECDomainParameters(curve, g, p.getOrder(), BigInteger.valueOf(p.getCofactor())), random); - - engine.init(param); - initialised = true; + this.param = createKeyGenParamsBC((ECParameterSpec)params, random); } - else if (params instanceof ECGenParameterSpec || params instanceof ECNamedCurveGenParameterSpec) + else if (params instanceof java.security.spec.ECParameterSpec) { - String curveName; - - if (params instanceof ECGenParameterSpec) - { - curveName = ((ECGenParameterSpec)params).getName(); - } - else - { - curveName = ((ECNamedCurveGenParameterSpec)params).getName(); - } - - X9ECParameters ecP = ECNamedCurveTable.getByName(curveName); - if (ecP == null) - { - // See if it's actually an OID string (SunJSSE ServerHandshaker setupEphemeralECDHKeys bug) - try - { - ASN1ObjectIdentifier oid = new ASN1ObjectIdentifier(curveName); - ecP = ECNamedCurveTable.getByOID(oid); - if (ecP == null) - { - throw new InvalidAlgorithmParameterException("unknown curve OID: " + curveName); - } - } - catch (IllegalArgumentException ex) - { - throw new InvalidAlgorithmParameterException("unknown curve name: " + curveName); - } - } - - this.ecParams = new ECNamedCurveSpec( - curveName, - ecP.getCurve(), - ecP.getG(), - ecP.getN(), - ecP.getH(), - null); // ecP.getSeed()); Work-around JDK bug -- it won't look up named curves properly if seed is present - - java.security.spec.ECParameterSpec p = (java.security.spec.ECParameterSpec)ecParams; - - ECCurve curve = EC5Util.convertCurve(p.getCurve()); - ECPoint g = EC5Util.convertPoint(curve, p.getGenerator(), false); - - param = new ECKeyGenerationParameters(new ECDomainParameters(curve, g, p.getOrder(), BigInteger.valueOf(p.getCofactor())), random); - - engine.init(param); - initialised = true; + this.ecParams = params; + this.param = createKeyGenParamsJCE((java.security.spec.ECParameterSpec)params, random); } - else if (params == null && configuration.getEcImplicitlyCa() != null) + else if (params instanceof ECGenParameterSpec) { - ECParameterSpec p = configuration.getEcImplicitlyCa(); - this.ecParams = params; - - param = new ECKeyGenerationParameters(new ECDomainParameters(p.getCurve(), p.getG(), p.getN()), random); - - engine.init(param); - initialised = true; + initializeNamedCurve(((ECGenParameterSpec)params).getName(), random); } - else if (params == null && configuration.getEcImplicitlyCa() == null) + else if (params instanceof ECNamedCurveGenParameterSpec) { - throw new InvalidAlgorithmParameterException("null parameter passed but no implicitCA set"); + initializeNamedCurve(((ECNamedCurveGenParameterSpec)params).getName(), random); } else { throw new InvalidAlgorithmParameterException("parameter object not a ECParameterSpec"); } + + engine.init(param); + initialised = true; } public KeyPair generateKeyPair() @@ -235,6 +178,58 @@ public abstract class KeyPairGeneratorSpi return new KeyPair(pubKey, new BCECPrivateKey(algorithm, priv, pubKey, p, configuration)); } } + + protected ECKeyGenerationParameters createKeyGenParamsBC(ECParameterSpec p, SecureRandom r) + { + return new ECKeyGenerationParameters(new ECDomainParameters(p.getCurve(), p.getG(), p.getN()), r); + } + + protected ECKeyGenerationParameters createKeyGenParamsJCE(java.security.spec.ECParameterSpec p, SecureRandom r) + { + ECCurve curve = EC5Util.convertCurve(p.getCurve()); + ECPoint g = EC5Util.convertPoint(curve, p.getGenerator(), false); + BigInteger n = p.getOrder(); + BigInteger h = BigInteger.valueOf(p.getCofactor()); + ECDomainParameters dp = new ECDomainParameters(curve, g, n, h); + return new ECKeyGenerationParameters(dp, r); + } + + protected ECNamedCurveSpec createNamedCurveSpec(String curveName) + throws InvalidAlgorithmParameterException + { + // NOTE: Don't bother with custom curves here as the curve will be converted to JCE type shortly + + X9ECParameters p = ECNamedCurveTable.getByName(curveName); + if (p == null) + { + try + { + // Check whether it's actually an OID string (SunJSSE ServerHandshaker setupEphemeralECDHKeys bug) + p = ECNamedCurveTable.getByOID(new ASN1ObjectIdentifier(curveName)); + if (p == null) + { + throw new InvalidAlgorithmParameterException("unknown curve OID: " + curveName); + } + } + catch (IllegalArgumentException ex) + { + throw new InvalidAlgorithmParameterException("unknown curve name: " + curveName); + } + } + + // Work-around for JDK bug -- it won't look up named curves properly if seed is present + byte[] seed = null; //p.getSeed(); + + return new ECNamedCurveSpec(curveName, p.getCurve(), p.getG(), p.getN(), p.getH(), seed); + } + + protected void initializeNamedCurve(String curveName, SecureRandom random) + throws InvalidAlgorithmParameterException + { + ECNamedCurveSpec namedCurve = createNamedCurveSpec(curveName); + this.ecParams = namedCurve; + this.param = createKeyGenParamsJCE(namedCurve, random); + } } public static class ECDSA diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/SignatureSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/SignatureSpi.java index e94746c..5e2bb4e 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/SignatureSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/SignatureSpi.java @@ -223,7 +223,7 @@ public class SignatureSpi { public ecCVCDSA() { - super(new SHA1Digest(), new ECDSASigner(), new CVCDSAEncoder()); + super(new SHA1Digest(), new ECDSASigner(), new PlainDSAEncoder()); } } @@ -232,7 +232,7 @@ public class SignatureSpi { public ecCVCDSA224() { - super(new SHA224Digest(), new ECDSASigner(), new CVCDSAEncoder()); + super(new SHA224Digest(), new ECDSASigner(), new PlainDSAEncoder()); } } @@ -241,7 +241,7 @@ public class SignatureSpi { public ecCVCDSA256() { - super(new SHA256Digest(), new ECDSASigner(), new CVCDSAEncoder()); + super(new SHA256Digest(), new ECDSASigner(), new PlainDSAEncoder()); } } @@ -250,7 +250,7 @@ public class SignatureSpi { public ecCVCDSA384() { - super(new SHA384Digest(), new ECDSASigner(), new CVCDSAEncoder()); + super(new SHA384Digest(), new ECDSASigner(), new PlainDSAEncoder()); } } @@ -259,7 +259,16 @@ public class SignatureSpi { public ecCVCDSA512() { - super(new SHA512Digest(), new ECDSASigner(), new CVCDSAEncoder()); + super(new SHA512Digest(), new ECDSASigner(), new PlainDSAEncoder()); + } + } + + static public class ecPlainDSARP160 + extends SignatureSpi + { + public ecPlainDSARP160() + { + super(new RIPEMD160Digest(), new ECDSASigner(), new PlainDSAEncoder()); } } @@ -293,7 +302,7 @@ public class SignatureSpi } } - private static class CVCDSAEncoder + private static class PlainDSAEncoder implements DSAEncoder { public byte[] encode( diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ecgost/BCECGOST3410PrivateKey.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ecgost/BCECGOST3410PrivateKey.java index 2b1c3fa..4c046fe 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ecgost/BCECGOST3410PrivateKey.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ecgost/BCECGOST3410PrivateKey.java @@ -13,14 +13,13 @@ import java.util.Enumeration; import org.bouncycastle.asn1.ASN1Encodable; import org.bouncycastle.asn1.ASN1Encoding; +import org.bouncycastle.asn1.ASN1Integer; import org.bouncycastle.asn1.ASN1ObjectIdentifier; import org.bouncycastle.asn1.ASN1OctetString; import org.bouncycastle.asn1.ASN1Primitive; import org.bouncycastle.asn1.ASN1Sequence; import org.bouncycastle.asn1.DERBitString; -import org.bouncycastle.asn1.DERInteger; import org.bouncycastle.asn1.DERNull; -import org.bouncycastle.asn1.DERObjectIdentifier; import org.bouncycastle.asn1.DEROctetString; import org.bouncycastle.asn1.cryptopro.CryptoProObjectIdentifiers; import org.bouncycastle.asn1.cryptopro.ECGOST3410NamedCurves; @@ -289,9 +288,9 @@ public class BCECGOST3410PrivateKey } ASN1Encodable privKey = info.parsePrivateKey(); - if (privKey instanceof DERInteger) + if (privKey instanceof ASN1Integer) { - DERInteger derD = DERInteger.getInstance(privKey); + ASN1Integer derD = ASN1Integer.getInstance(privKey); this.d = derD.getValue(); } @@ -348,19 +347,22 @@ public class BCECGOST3410PrivateKey else { X962Parameters params; + int orderBitLength; if (ecSpec instanceof ECNamedCurveSpec) { - DERObjectIdentifier curveOid = ECUtil.getNamedCurveOid(((ECNamedCurveSpec)ecSpec).getName()); + ASN1ObjectIdentifier curveOid = ECUtil.getNamedCurveOid(((ECNamedCurveSpec)ecSpec).getName()); if (curveOid == null) // guess it's the OID { curveOid = new ASN1ObjectIdentifier(((ECNamedCurveSpec)ecSpec).getName()); } params = new X962Parameters(curveOid); + orderBitLength = ECUtil.getOrderBitLength(ecSpec.getOrder(), this.getS()); } else if (ecSpec == null) { params = new X962Parameters(DERNull.INSTANCE); + orderBitLength = ECUtil.getOrderBitLength(null, this.getS()); } else { @@ -374,6 +376,7 @@ public class BCECGOST3410PrivateKey ecSpec.getCurve().getSeed()); params = new X962Parameters(ecP); + orderBitLength = ECUtil.getOrderBitLength(ecSpec.getOrder(), this.getS()); } PrivateKeyInfo info; @@ -381,11 +384,11 @@ public class BCECGOST3410PrivateKey if (publicKey != null) { - keyStructure = new org.bouncycastle.asn1.sec.ECPrivateKey(this.getS(), publicKey, params); + keyStructure = new org.bouncycastle.asn1.sec.ECPrivateKey(orderBitLength, this.getS(), publicKey, params); } else { - keyStructure = new org.bouncycastle.asn1.sec.ECPrivateKey(this.getS(), params); + keyStructure = new org.bouncycastle.asn1.sec.ECPrivateKey(orderBitLength, this.getS(), params); } try diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ecgost/BCECGOST3410PublicKey.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ecgost/BCECGOST3410PublicKey.java index 650855e..1240a0f 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ecgost/BCECGOST3410PublicKey.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ecgost/BCECGOST3410PublicKey.java @@ -32,6 +32,8 @@ import org.bouncycastle.jce.provider.BouncyCastleProvider; import org.bouncycastle.jce.spec.ECNamedCurveParameterSpec; import org.bouncycastle.jce.spec.ECNamedCurveSpec; import org.bouncycastle.math.ec.ECCurve; +import org.bouncycastle.math.ec.custom.sec.SecP256K1Point; +import org.bouncycastle.math.ec.custom.sec.SecP256R1Point; public class BCECGOST3410PublicKey implements ECPublicKey, org.bouncycastle.jce.interfaces.ECPublicKey, ECPointEncoder @@ -316,14 +318,7 @@ public class BCECGOST3410PublicKey { if (ecSpec == null) { - if (q instanceof org.bouncycastle.math.ec.ECPoint.Fp) - { - return new org.bouncycastle.math.ec.ECPoint.Fp(null, q.getAffineXCoord(), q.getAffineYCoord()); - } - else - { - return new org.bouncycastle.math.ec.ECPoint.F2m(null, q.getAffineXCoord(), q.getAffineYCoord()); - } + return q.getDetachedPoint(); } return q; diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ecgost/SignatureSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ecgost/SignatureSpi.java index b59db8f..407dda5 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ecgost/SignatureSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ecgost/SignatureSpi.java @@ -58,14 +58,7 @@ public class SignatureSpi publicKey = BouncyCastleProvider.getPublicKey(SubjectPublicKeyInfo.getInstance(bytes)); - if (publicKey instanceof ECPublicKey) - { - param = ECUtil.generatePublicKeyParameter(publicKey); - } - else - { - throw new InvalidKeyException("can't recognise key type in DSA based signer"); - } + param = ECUtil.generatePublicKeyParameter(publicKey); } catch (Exception e) { diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/AlgorithmParameterGeneratorSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/AlgorithmParameterGeneratorSpi.java index 9cb9c87..6097c3c 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/AlgorithmParameterGeneratorSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/AlgorithmParameterGeneratorSpi.java @@ -10,10 +10,10 @@ import javax.crypto.spec.DHParameterSpec; import org.bouncycastle.crypto.generators.ElGamalParametersGenerator; import org.bouncycastle.crypto.params.ElGamalParameters; -import org.bouncycastle.jce.provider.BouncyCastleProvider; +import org.bouncycastle.jcajce.provider.asymmetric.util.BaseAlgorithmParameterGeneratorSpi; public class AlgorithmParameterGeneratorSpi - extends java.security.AlgorithmParameterGeneratorSpi + extends BaseAlgorithmParameterGeneratorSpi { protected SecureRandom random; protected int strength = 1024; @@ -63,7 +63,7 @@ public class AlgorithmParameterGeneratorSpi try { - params = AlgorithmParameters.getInstance("ElGamal", BouncyCastleProvider.PROVIDER_NAME); + params = createParametersInstance("ElGamal"); params.init(new DHParameterSpec(p.getP(), p.getG(), l)); } catch (Exception e) diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/AlgorithmParametersSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/AlgorithmParametersSpi.java index 2c56ee3..3253fbb 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/AlgorithmParametersSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/AlgorithmParametersSpi.java @@ -8,7 +8,6 @@ import javax.crypto.spec.DHParameterSpec; import org.bouncycastle.asn1.ASN1Encoding; import org.bouncycastle.asn1.ASN1Primitive; -import org.bouncycastle.asn1.ASN1Sequence; import org.bouncycastle.asn1.oiw.ElGamalParameter; import org.bouncycastle.jcajce.provider.symmetric.util.BaseAlgorithmParameters; import org.bouncycastle.jce.spec.ElGamalParameterSpec; @@ -20,7 +19,6 @@ public class AlgorithmParametersSpi /** * Return the X.509 ASN.1 structure ElGamalParameter. - * <p/> * <pre> * ElGamalParameter ::= SEQUENCE { * prime INTEGER, -- p @@ -95,7 +93,7 @@ public class AlgorithmParametersSpi { try { - ElGamalParameter elP = new ElGamalParameter((ASN1Sequence)ASN1Primitive.fromByteArray(params)); + ElGamalParameter elP = ElGamalParameter.getInstance(ASN1Primitive.fromByteArray(params)); currentSpec = new ElGamalParameterSpec(elP.getP(), elP.getG()); } diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/BCElGamalPrivateKey.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/BCElGamalPrivateKey.java index 0806b43..f0f83fa 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/BCElGamalPrivateKey.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/BCElGamalPrivateKey.java @@ -14,8 +14,6 @@ import org.bouncycastle.asn1.ASN1Encodable; import org.bouncycastle.asn1.ASN1Encoding; import org.bouncycastle.asn1.ASN1Integer; import org.bouncycastle.asn1.ASN1ObjectIdentifier; -import org.bouncycastle.asn1.ASN1Sequence; -import org.bouncycastle.asn1.DERInteger; import org.bouncycastle.asn1.oiw.ElGamalParameter; import org.bouncycastle.asn1.oiw.OIWObjectIdentifiers; import org.bouncycastle.asn1.pkcs.PrivateKeyInfo; @@ -73,8 +71,8 @@ public class BCElGamalPrivateKey PrivateKeyInfo info) throws IOException { - ElGamalParameter params = new ElGamalParameter((ASN1Sequence)info.getAlgorithmId().getParameters()); - DERInteger derX = ASN1Integer.getInstance(info.parsePrivateKey()); + ElGamalParameter params = ElGamalParameter.getInstance(info.getPrivateKeyAlgorithm().getParameters()); + ASN1Integer derX = ASN1Integer.getInstance(info.parsePrivateKey()); this.x = derX.getValue(); this.elSpec = new ElGamalParameterSpec(params.getP(), params.getG()); @@ -112,7 +110,7 @@ public class BCElGamalPrivateKey { try { - PrivateKeyInfo info = new PrivateKeyInfo(new AlgorithmIdentifier(OIWObjectIdentifiers.elGamalAlgorithm, new ElGamalParameter(elSpec.getP(), elSpec.getG())), new DERInteger(getX())); + PrivateKeyInfo info = new PrivateKeyInfo(new AlgorithmIdentifier(OIWObjectIdentifiers.elGamalAlgorithm, new ElGamalParameter(elSpec.getP(), elSpec.getG())), new ASN1Integer(getX())); return info.getEncoded(ASN1Encoding.DER); } diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/BCElGamalPublicKey.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/BCElGamalPublicKey.java index e0f7298..cd31cc5 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/BCElGamalPublicKey.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/BCElGamalPublicKey.java @@ -10,8 +10,7 @@ import javax.crypto.spec.DHParameterSpec; import javax.crypto.spec.DHPublicKeySpec; import org.bouncycastle.asn1.ASN1Encoding; -import org.bouncycastle.asn1.ASN1Sequence; -import org.bouncycastle.asn1.DERInteger; +import org.bouncycastle.asn1.ASN1Integer; import org.bouncycastle.asn1.oiw.ElGamalParameter; import org.bouncycastle.asn1.oiw.OIWObjectIdentifiers; import org.bouncycastle.asn1.x509.AlgorithmIdentifier; @@ -75,12 +74,12 @@ public class BCElGamalPublicKey BCElGamalPublicKey( SubjectPublicKeyInfo info) { - ElGamalParameter params = new ElGamalParameter((ASN1Sequence)info.getAlgorithmId().getParameters()); - DERInteger derY = null; + ElGamalParameter params = ElGamalParameter.getInstance(info.getAlgorithm().getParameters()); + ASN1Integer derY = null; try { - derY = (DERInteger)info.parsePublicKey(); + derY = (ASN1Integer)info.parsePublicKey(); } catch (IOException e) { @@ -105,7 +104,7 @@ public class BCElGamalPublicKey { try { - SubjectPublicKeyInfo info = new SubjectPublicKeyInfo(new AlgorithmIdentifier(OIWObjectIdentifiers.elGamalAlgorithm, new ElGamalParameter(elSpec.getP(), elSpec.getG())), new DERInteger(y)); + SubjectPublicKeyInfo info = new SubjectPublicKeyInfo(new AlgorithmIdentifier(OIWObjectIdentifiers.elGamalAlgorithm, new ElGamalParameter(elSpec.getP(), elSpec.getG())), new ASN1Integer(y)); return info.getEncoded(ASN1Encoding.DER); } diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/CipherSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/CipherSpi.java index fbf4f75..9c28670 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/CipherSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/elgamal/CipherSpi.java @@ -34,7 +34,6 @@ import org.bouncycastle.jcajce.provider.util.DigestFactory; import org.bouncycastle.jce.interfaces.ElGamalKey; import org.bouncycastle.jce.interfaces.ElGamalPrivateKey; import org.bouncycastle.jce.interfaces.ElGamalPublicKey; -import org.bouncycastle.jce.provider.BouncyCastleProvider; import org.bouncycastle.util.Strings; public class CipherSpi @@ -104,7 +103,7 @@ public class CipherSpi { try { - engineParams = AlgorithmParameters.getInstance("OAEP", BouncyCastleProvider.PROVIDER_NAME); + engineParams = createParametersInstance("OAEP"); engineParams.init(paramSpec); } catch (Exception e) diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/gost/AlgorithmParameterGeneratorSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/gost/AlgorithmParameterGeneratorSpi.java index 7019b81..2e7ee7c 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/gost/AlgorithmParameterGeneratorSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/gost/AlgorithmParameterGeneratorSpi.java @@ -7,12 +7,12 @@ import java.security.spec.AlgorithmParameterSpec; import org.bouncycastle.crypto.generators.GOST3410ParametersGenerator; import org.bouncycastle.crypto.params.GOST3410Parameters; -import org.bouncycastle.jce.provider.BouncyCastleProvider; +import org.bouncycastle.jcajce.provider.asymmetric.util.BaseAlgorithmParameterGeneratorSpi; import org.bouncycastle.jce.spec.GOST3410ParameterSpec; import org.bouncycastle.jce.spec.GOST3410PublicKeyParameterSetSpec; public abstract class AlgorithmParameterGeneratorSpi - extends java.security.AlgorithmParameterGeneratorSpi + extends BaseAlgorithmParameterGeneratorSpi { protected SecureRandom random; protected int strength = 1024; @@ -52,7 +52,7 @@ public abstract class AlgorithmParameterGeneratorSpi try { - params = AlgorithmParameters.getInstance("GOST3410", BouncyCastleProvider.PROVIDER_NAME); + params = createParametersInstance("GOST3410"); params.init(new GOST3410ParameterSpec(new GOST3410PublicKeyParameterSetSpec(p.getP(), p.getQ(), p.getA()))); } catch (Exception e) diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/gost/AlgorithmParametersSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/gost/AlgorithmParametersSpi.java index 0af98e0..88f78bd 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/gost/AlgorithmParametersSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/gost/AlgorithmParametersSpi.java @@ -37,7 +37,6 @@ public class AlgorithmParametersSpi /** * Return the X.509 ASN.1 structure GOST3410Parameter. - * <p/> * <pre> * GOST3410Parameter ::= SEQUENCE { * prime INTEGER, -- p diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ies/AlgorithmParametersSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ies/AlgorithmParametersSpi.java index 2f39c4a..61f1e37 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ies/AlgorithmParametersSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ies/AlgorithmParametersSpi.java @@ -6,10 +6,10 @@ import java.security.spec.InvalidParameterSpecException; import org.bouncycastle.asn1.ASN1EncodableVector; import org.bouncycastle.asn1.ASN1Encoding; +import org.bouncycastle.asn1.ASN1Integer; import org.bouncycastle.asn1.ASN1OctetString; import org.bouncycastle.asn1.ASN1Primitive; import org.bouncycastle.asn1.ASN1Sequence; -import org.bouncycastle.asn1.DERInteger; import org.bouncycastle.asn1.DEROctetString; import org.bouncycastle.asn1.DERSequence; import org.bouncycastle.jce.spec.IESParameterSpec; @@ -48,7 +48,7 @@ public class AlgorithmParametersSpi v.add(new DEROctetString(currentSpec.getDerivationV())); v.add(new DEROctetString(currentSpec.getEncodingV())); - v.add(new DERInteger(currentSpec.getMacKeySize())); + v.add(new ASN1Integer(currentSpec.getMacKeySize())); return new DERSequence(v).getEncoded(ASN1Encoding.DER); } @@ -104,7 +104,7 @@ public class AlgorithmParametersSpi this.currentSpec = new IESParameterSpec( ((ASN1OctetString)s.getObjectAt(0)).getOctets(), ((ASN1OctetString)s.getObjectAt(0)).getOctets(), - ((DERInteger)s.getObjectAt(0)).getValue().intValue()); + ((ASN1Integer)s.getObjectAt(0)).getValue().intValue()); } catch (ClassCastException e) { diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ies/CipherSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ies/CipherSpi.java index 8cfaf2a..430f6b1 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ies/CipherSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ies/CipherSpi.java @@ -13,6 +13,7 @@ import javax.crypto.Cipher; import javax.crypto.IllegalBlockSizeException; import javax.crypto.NoSuchPaddingException; import javax.crypto.interfaces.DHPrivateKey; +import javax.crypto.interfaces.DHPublicKey; import org.bouncycastle.crypto.CipherParameters; import org.bouncycastle.crypto.InvalidCipherTextException; @@ -22,17 +23,19 @@ import org.bouncycastle.crypto.engines.IESEngine; import org.bouncycastle.crypto.generators.KDF2BytesGenerator; import org.bouncycastle.crypto.macs.HMac; import org.bouncycastle.crypto.params.IESParameters; -import org.bouncycastle.jce.provider.BouncyCastleProvider; import org.bouncycastle.jcajce.provider.asymmetric.util.DHUtil; import org.bouncycastle.jcajce.provider.asymmetric.util.ECUtil; +import org.bouncycastle.jcajce.util.BCJcaJceHelper; +import org.bouncycastle.jcajce.util.JcaJceHelper; import org.bouncycastle.jce.interfaces.ECPrivateKey; -import org.bouncycastle.jce.interfaces.ECPublicKey; import org.bouncycastle.jce.interfaces.IESKey; import org.bouncycastle.jce.spec.IESParameterSpec; public class CipherSpi extends javax.crypto.CipherSpi { + private final JcaJceHelper helper = new BCJcaJceHelper(); + private IESEngine cipher; private int state = -1; private ByteArrayOutputStream buffer = new ByteArrayOutputStream(); @@ -116,7 +119,7 @@ public class CipherSpi try { - engineParam = AlgorithmParameters.getInstance(name, BouncyCastleProvider.PROVIDER_NAME); + engineParam = helper.createAlgorithmParameters(name); engineParam.init(engineParams); } catch (Exception e) @@ -183,15 +186,16 @@ public class CipherSpi CipherParameters pubKey; CipherParameters privKey; - if (ieKey.getPublic() instanceof ECPublicKey) + if (ieKey.getPublic() instanceof DHPublicKey) { - pubKey = ECUtil.generatePublicKeyParameter(ieKey.getPublic()); - privKey = ECUtil.generatePrivateKeyParameter(ieKey.getPrivate()); + pubKey = DHUtil.generatePublicKeyParameter(ieKey.getPublic()); + privKey = DHUtil.generatePrivateKeyParameter(ieKey.getPrivate()); + } else { - pubKey = DHUtil.generatePublicKeyParameter(ieKey.getPublic()); - privKey = DHUtil.generatePrivateKeyParameter(ieKey.getPrivate()); + pubKey = ECUtil.generatePublicKeyParameter(ieKey.getPublic()); + privKey = ECUtil.generatePrivateKeyParameter(ieKey.getPrivate()); } this.engineParams = (IESParameterSpec)params; diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/BCRSAPrivateKey.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/BCRSAPrivateKey.java index 0aa81b4..b82c5f8 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/BCRSAPrivateKey.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/BCRSAPrivateKey.java @@ -55,6 +55,12 @@ public class BCRSAPrivateKey this.privateExponent = key.getPrivateExponent(); } + BCRSAPrivateKey(org.bouncycastle.asn1.pkcs.RSAPrivateKey key) + { + this.modulus = key.getModulus(); + this.privateExponent = key.getPrivateExponent(); + } + public BigInteger getModulus() { return modulus; diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/BCRSAPublicKey.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/BCRSAPublicKey.java index a2114fa..6f5292c 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/BCRSAPublicKey.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/BCRSAPublicKey.java @@ -1,5 +1,6 @@ package org.bouncycastle.jcajce.provider.asymmetric.rsa; +import java.io.EOFException; import java.io.IOException; import java.io.ObjectInputStream; import java.io.ObjectOutputStream; @@ -156,6 +157,10 @@ public class BCRSAPublicKey { algorithmIdentifier = DEFAULT_ALGORITHM_IDENTIFIER; } + catch (EOFException e) + { + algorithmIdentifier = DEFAULT_ALGORITHM_IDENTIFIER; + } } private void writeObject( diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/CipherSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/CipherSpi.java index dc8dcb2..239e511 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/CipherSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/CipherSpi.java @@ -33,12 +33,16 @@ import org.bouncycastle.crypto.engines.RSABlindedEngine; import org.bouncycastle.crypto.params.ParametersWithRandom; import org.bouncycastle.jcajce.provider.asymmetric.util.BaseCipherSpi; import org.bouncycastle.jcajce.provider.util.DigestFactory; +import org.bouncycastle.jcajce.util.BCJcaJceHelper; +import org.bouncycastle.jcajce.util.JcaJceHelper; import org.bouncycastle.jce.provider.BouncyCastleProvider; import org.bouncycastle.util.Strings; public class CipherSpi extends BaseCipherSpi { + private final JcaJceHelper helper = new BCJcaJceHelper(); + private AsymmetricBlockCipher cipher; private AlgorithmParameterSpec paramSpec; private AlgorithmParameters engineParams; @@ -143,7 +147,7 @@ public class CipherSpi { try { - engineParams = AlgorithmParameters.getInstance("OAEP", BouncyCastleProvider.PROVIDER_NAME); + engineParams = helper.createAlgorithmParameters("OAEP"); engineParams.init(paramSpec); } catch (Exception e) @@ -307,7 +311,7 @@ public class CipherSpi } else { - throw new IllegalArgumentException("unknown parameter type."); + throw new InvalidAlgorithmParameterException("unknown parameter type: " + params.getClass().getName()); } if (!(cipher instanceof RSABlindedEngine)) diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/DigestSignatureSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/DigestSignatureSpi.java index 4462548..c04bec9 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/DigestSignatureSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/DigestSignatureSpi.java @@ -37,6 +37,7 @@ import org.bouncycastle.crypto.digests.SHA384Digest; import org.bouncycastle.crypto.digests.SHA512Digest; import org.bouncycastle.crypto.encodings.PKCS1Encoding; import org.bouncycastle.crypto.engines.RSABlindedEngine; +import org.bouncycastle.util.Arrays; public class DigestSignatureSpi extends SignatureSpi @@ -171,13 +172,7 @@ public class DigestSignatureSpi if (sig.length == expected.length) { - for (int i = 0; i < sig.length; i++) - { - if (sig[i] != expected[i]) - { - return false; - } - } + return Arrays.constantTimeAreEqual(sig, expected); } else if (sig.length == expected.length - 2) // NULL left out { @@ -187,28 +182,26 @@ public class DigestSignatureSpi expected[1] -= 2; // adjust lengths expected[3] -= 2; + int nonEqual = 0; + for (int i = 0; i < hash.length; i++) { - if (sig[sigOffset + i] != expected[expectedOffset + i]) // check hash - { - return false; - } + nonEqual |= (sig[sigOffset + i] ^ expected[expectedOffset + i]); } for (int i = 0; i < sigOffset; i++) { - if (sig[i] != expected[i]) // check header less NULL - { - return false; - } + nonEqual |= (sig[i] ^ expected[i]); // check header less NULL } + + return nonEqual == 0; } else { + Arrays.constantTimeAreEqual(expected, expected); // keep time "steady". + return false; } - - return true; } protected void engineSetParameter( diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/KeyFactorySpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/KeyFactorySpi.java index d8eb539..80690f7 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/KeyFactorySpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/KeyFactorySpi.java @@ -137,7 +137,16 @@ public class KeyFactorySpi if (RSAUtil.isRsaOid(algOid)) { - return new BCRSAPrivateCrtKey(keyInfo); + RSAPrivateKey rsaPrivKey = RSAPrivateKey.getInstance(keyInfo.parsePrivateKey()); + + if (rsaPrivKey.getCoefficient().intValue() == 0) + { + return new BCRSAPrivateKey(rsaPrivKey); + } + else + { + return new BCRSAPrivateCrtKey(keyInfo); + } } else { diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/KeyPairGeneratorSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/KeyPairGeneratorSpi.java index c61e7cb..f779a66 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/KeyPairGeneratorSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/KeyPairGeneratorSpi.java @@ -23,7 +23,7 @@ public class KeyPairGeneratorSpi } final static BigInteger defaultPublicExponent = BigInteger.valueOf(0x10001); - final static int defaultTests = 12; + final static int defaultTests = 112; RSAKeyGenerationParameters param; RSAKeyPairGenerator engine; diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/PSSSignatureSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/PSSSignatureSpi.java index c0a2fc9..ea632fc 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/PSSSignatureSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/PSSSignatureSpi.java @@ -22,11 +22,15 @@ import org.bouncycastle.crypto.Digest; import org.bouncycastle.crypto.engines.RSABlindedEngine; import org.bouncycastle.crypto.params.ParametersWithRandom; import org.bouncycastle.jcajce.provider.util.DigestFactory; +import org.bouncycastle.jcajce.util.BCJcaJceHelper; +import org.bouncycastle.jcajce.util.JcaJceHelper; import org.bouncycastle.jce.provider.BouncyCastleProvider; public class PSSSignatureSpi extends SignatureSpi { + private final JcaJceHelper helper = new BCJcaJceHelper(); + private AlgorithmParameters engineParams; private PSSParameterSpec paramSpec; private PSSParameterSpec originalSpec; @@ -234,7 +238,7 @@ public class PSSSignatureSpi { try { - engineParams = AlgorithmParameters.getInstance("PSS", BouncyCastleProvider.PROVIDER_NAME); + engineParams = helper.createAlgorithmParameters("PSS"); engineParams.init(paramSpec); } catch (Exception e) diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/X931SignatureSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/X931SignatureSpi.java new file mode 100644 index 0000000..727f685 --- /dev/null +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/rsa/X931SignatureSpi.java @@ -0,0 +1,194 @@ +package org.bouncycastle.jcajce.provider.asymmetric.rsa; + +import java.security.InvalidKeyException; +import java.security.PrivateKey; +import java.security.PublicKey; +import java.security.SignatureException; +import java.security.SignatureSpi; +import java.security.interfaces.RSAPrivateKey; +import java.security.interfaces.RSAPublicKey; +import java.security.spec.AlgorithmParameterSpec; + +import org.bouncycastle.crypto.AsymmetricBlockCipher; +import org.bouncycastle.crypto.CipherParameters; +import org.bouncycastle.crypto.Digest; +import org.bouncycastle.crypto.digests.MD5Digest; +import org.bouncycastle.crypto.digests.RIPEMD128Digest; +import org.bouncycastle.crypto.digests.RIPEMD160Digest; +import org.bouncycastle.crypto.digests.SHA1Digest; +import org.bouncycastle.crypto.digests.SHA224Digest; +import org.bouncycastle.crypto.digests.SHA256Digest; +import org.bouncycastle.crypto.digests.SHA384Digest; +import org.bouncycastle.crypto.digests.SHA512Digest; +import org.bouncycastle.crypto.digests.WhirlpoolDigest; +import org.bouncycastle.crypto.engines.RSABlindedEngine; +import org.bouncycastle.crypto.signers.ISO9796d2Signer; +import org.bouncycastle.crypto.signers.X931Signer; + +public class X931SignatureSpi + extends SignatureSpi +{ + private X931Signer signer; + + protected X931SignatureSpi( + Digest digest, + AsymmetricBlockCipher cipher) + { + signer = new X931Signer(cipher, digest); + } + + protected void engineInitVerify( + PublicKey publicKey) + throws InvalidKeyException + { + CipherParameters param = RSAUtil.generatePublicKeyParameter((RSAPublicKey)publicKey); + + signer.init(false, param); + } + + protected void engineInitSign( + PrivateKey privateKey) + throws InvalidKeyException + { + CipherParameters param = RSAUtil.generatePrivateKeyParameter((RSAPrivateKey)privateKey); + + signer.init(true, param); + } + + protected void engineUpdate( + byte b) + throws SignatureException + { + signer.update(b); + } + + protected void engineUpdate( + byte[] b, + int off, + int len) + throws SignatureException + { + signer.update(b, off, len); + } + + protected byte[] engineSign() + throws SignatureException + { + try + { + byte[] sig = signer.generateSignature(); + + return sig; + } + catch (Exception e) + { + throw new SignatureException(e.toString()); + } + } + + protected boolean engineVerify( + byte[] sigBytes) + throws SignatureException + { + boolean yes = signer.verifySignature(sigBytes); + + return yes; + } + + protected void engineSetParameter( + AlgorithmParameterSpec params) + { + throw new UnsupportedOperationException("engineSetParameter unsupported"); + } + + /** + * @deprecated replaced with <a href = "#engineSetParameter(java.security.spec.AlgorithmParameterSpec)"> + */ + protected void engineSetParameter( + String param, + Object value) + { + throw new UnsupportedOperationException("engineSetParameter unsupported"); + } + + /** + * @deprecated + */ + protected Object engineGetParameter( + String param) + { + throw new UnsupportedOperationException("engineSetParameter unsupported"); + } + + static public class RIPEMD128WithRSAEncryption + extends X931SignatureSpi + { + public RIPEMD128WithRSAEncryption() + { + super(new RIPEMD128Digest(), new RSABlindedEngine()); + } + } + + static public class RIPEMD160WithRSAEncryption + extends X931SignatureSpi + { + public RIPEMD160WithRSAEncryption() + { + super(new RIPEMD160Digest(), new RSABlindedEngine()); + } + } + + static public class SHA1WithRSAEncryption + extends X931SignatureSpi + { + public SHA1WithRSAEncryption() + { + super(new SHA1Digest(), new RSABlindedEngine()); + } + } + + static public class SHA224WithRSAEncryption + extends X931SignatureSpi + { + public SHA224WithRSAEncryption() + { + super(new SHA224Digest(), new RSABlindedEngine()); + } + } + + static public class SHA256WithRSAEncryption + extends X931SignatureSpi + { + public SHA256WithRSAEncryption() + { + super(new SHA256Digest(), new RSABlindedEngine()); + } + } + + static public class SHA384WithRSAEncryption + extends X931SignatureSpi + { + public SHA384WithRSAEncryption() + { + super(new SHA384Digest(), new RSABlindedEngine()); + } + } + + static public class SHA512WithRSAEncryption + extends X931SignatureSpi + { + public SHA512WithRSAEncryption() + { + super(new SHA512Digest(), new RSABlindedEngine()); + } + } + + static public class WhirlpoolWithRSAEncryption + extends X931SignatureSpi + { + public WhirlpoolWithRSAEncryption() + { + super(new WhirlpoolDigest(), new RSABlindedEngine()); + } + } +} diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/BaseAlgorithmParameterGeneratorSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/BaseAlgorithmParameterGeneratorSpi.java new file mode 100644 index 0000000..d9fb3fb --- /dev/null +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/BaseAlgorithmParameterGeneratorSpi.java @@ -0,0 +1,25 @@ +package org.bouncycastle.jcajce.provider.asymmetric.util; + +import java.security.AlgorithmParameterGeneratorSpi; +import java.security.AlgorithmParameters; +import java.security.NoSuchAlgorithmException; +import java.security.NoSuchProviderException; + +import org.bouncycastle.jcajce.util.BCJcaJceHelper; +import org.bouncycastle.jcajce.util.JcaJceHelper; + +public abstract class BaseAlgorithmParameterGeneratorSpi + extends AlgorithmParameterGeneratorSpi +{ + private final JcaJceHelper helper = new BCJcaJceHelper(); + + public BaseAlgorithmParameterGeneratorSpi() + { + } + + protected final AlgorithmParameters createParametersInstance(String algorithm) + throws NoSuchAlgorithmException, NoSuchProviderException + { + return helper.createAlgorithmParameters(algorithm); + } +} diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/BaseCipherSpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/BaseCipherSpi.java index 722a5ca..482329c 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/BaseCipherSpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/BaseCipherSpi.java @@ -25,6 +25,8 @@ import javax.crypto.spec.SecretKeySpec; import org.bouncycastle.asn1.pkcs.PrivateKeyInfo; import org.bouncycastle.crypto.InvalidCipherTextException; import org.bouncycastle.crypto.Wrapper; +import org.bouncycastle.jcajce.util.BCJcaJceHelper; +import org.bouncycastle.jcajce.util.JcaJceHelper; import org.bouncycastle.jce.provider.BouncyCastleProvider; public abstract class BaseCipherSpi @@ -41,6 +43,7 @@ public abstract class BaseCipherSpi RC5ParameterSpec.class }; + private final JcaJceHelper helper = new BCJcaJceHelper(); protected AlgorithmParameters engineParams = null; @@ -80,6 +83,12 @@ public abstract class BaseCipherSpi return null; } + protected final AlgorithmParameters createParametersInstance(String algorithm) + throws NoSuchAlgorithmException, NoSuchProviderException + { + return helper.createAlgorithmParameters(algorithm); + } + protected void engineSetMode( String mode) throws NoSuchAlgorithmException @@ -186,7 +195,7 @@ public abstract class BaseCipherSpi { try { - KeyFactory kf = KeyFactory.getInstance(wrappedKeyAlgorithm, BouncyCastleProvider.PROVIDER_NAME); + KeyFactory kf = helper.createKeyFactory(wrappedKeyAlgorithm); if (wrappedKeyType == Cipher.PUBLIC_KEY) { @@ -197,17 +206,17 @@ public abstract class BaseCipherSpi return kf.generatePrivate(new PKCS8EncodedKeySpec(encoded)); } } - catch (NoSuchProviderException e) + catch (NoSuchAlgorithmException e) { throw new InvalidKeyException("Unknown key type " + e.getMessage()); } - catch (NoSuchAlgorithmException e) + catch (InvalidKeySpecException e) { throw new InvalidKeyException("Unknown key type " + e.getMessage()); } - catch (InvalidKeySpecException e2) + catch (NoSuchProviderException e) { - throw new InvalidKeyException("Unknown key type " + e2.getMessage()); + throw new InvalidKeyException("Unknown key type " + e.getMessage()); } throw new InvalidKeyException("Unknown key type " + wrappedKeyType); diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/BaseKeyFactorySpi.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/BaseKeyFactorySpi.java index 490bf4e..cb34f44 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/BaseKeyFactorySpi.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/BaseKeyFactorySpi.java @@ -1,6 +1,5 @@ package org.bouncycastle.jcajce.provider.asymmetric.util; -import java.io.IOException; import java.security.Key; import java.security.PrivateKey; import java.security.PublicKey; diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/EC5Util.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/EC5Util.java index 5eea1b9..d5b62fe 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/EC5Util.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/EC5Util.java @@ -7,22 +7,46 @@ import java.security.spec.ECFieldFp; import java.security.spec.ECParameterSpec; import java.security.spec.ECPoint; import java.security.spec.EllipticCurve; +import java.util.Enumeration; +import java.util.HashMap; +import java.util.Map; +import org.bouncycastle.asn1.x9.ECNamedCurveTable; +import org.bouncycastle.asn1.x9.X9ECParameters; +import org.bouncycastle.crypto.ec.CustomNamedCurves; import org.bouncycastle.jce.spec.ECNamedCurveParameterSpec; import org.bouncycastle.jce.spec.ECNamedCurveSpec; +import org.bouncycastle.math.ec.ECAlgorithms; import org.bouncycastle.math.ec.ECCurve; public class EC5Util { + private static Map customCurves = new HashMap(); + + static + { + Enumeration e = CustomNamedCurves.getNames(); + while (e.hasMoreElements()) + { + String name = (String)e.nextElement(); + + X9ECParameters curveParams = ECNamedCurveTable.getByName(name); + if (curveParams != null) // there may not be a regular curve, may just be a custom curve. + { + customCurves.put(curveParams.getCurve(), CustomNamedCurves.getByName(name).getCurve()); + } + } + } + public static EllipticCurve convertCurve( ECCurve curve, byte[] seed) { // TODO: the Sun EC implementation doesn't currently handle the seed properly // so at the moment it's set to null. Should probably look at making this configurable - if (curve instanceof ECCurve.Fp) + if (ECAlgorithms.isFpCurve(curve)) { - return new EllipticCurve(new ECFieldFp(((ECCurve.Fp)curve).getQ()), curve.getA().toBigInteger(), curve.getB().toBigInteger(), null); + return new EllipticCurve(new ECFieldFp(curve.getField().getCharacteristic()), curve.getA().toBigInteger(), curve.getB().toBigInteger(), null); } else { @@ -53,7 +77,14 @@ public class EC5Util if (field instanceof ECFieldFp) { - return new ECCurve.Fp(((ECFieldFp)field).getP(), a, b); + ECCurve.Fp curve = new ECCurve.Fp(((ECFieldFp)field).getP(), a, b); + + if (customCurves.containsKey(curve)) + { + return (ECCurve)customCurves.get(curve); + } + + return curve; } else { diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/ECUtil.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/ECUtil.java index 97ade38..b1805f6 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/ECUtil.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/ECUtil.java @@ -1,5 +1,6 @@ package org.bouncycastle.jcajce.provider.asymmetric.util; +import java.math.BigInteger; import java.security.InvalidKeyException; import java.security.PrivateKey; import java.security.PublicKey; @@ -12,7 +13,9 @@ import org.bouncycastle.asn1.sec.SECNamedCurves; import org.bouncycastle.asn1.teletrust.TeleTrusTNamedCurves; import org.bouncycastle.asn1.x509.SubjectPublicKeyInfo; import org.bouncycastle.asn1.x9.X962NamedCurves; +import org.bouncycastle.asn1.x9.X962Parameters; import org.bouncycastle.asn1.x9.X9ECParameters; +import org.bouncycastle.crypto.ec.CustomNamedCurves; import org.bouncycastle.crypto.params.AsymmetricKeyParameter; import org.bouncycastle.crypto.params.ECDomainParameters; import org.bouncycastle.crypto.params.ECPrivateKeyParameters; @@ -213,6 +216,25 @@ public class ECUtil throw new InvalidKeyException("can't identify EC private key."); } + public static int getOrderBitLength(BigInteger order, BigInteger privateValue) + { + if (order == null) // implicitly CA + { + ECParameterSpec implicitCA = BouncyCastleProvider.CONFIGURATION.getEcImplicitlyCa(); + + if (implicitCA == null) + { + return privateValue.bitLength(); // a guess but better than an exception! + } + + return implicitCA.getN().bitLength(); + } + else + { + return order.bitLength(); + } + } + public static ASN1ObjectIdentifier getNamedCurveOid( String name) { @@ -241,11 +263,15 @@ public class ECUtil public static X9ECParameters getNamedCurveByOid( ASN1ObjectIdentifier oid) { - X9ECParameters params = X962NamedCurves.getByOID(oid); - + X9ECParameters params = CustomNamedCurves.getByOID(oid); + if (params == null) { - params = SECNamedCurves.getByOID(oid); + params = X962NamedCurves.getByOID(oid); + if (params == null) + { + params = SECNamedCurves.getByOID(oid); + } if (params == null) { params = NISTNamedCurves.getByOID(oid); diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/PKCS12BagAttributeCarrierImpl.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/PKCS12BagAttributeCarrierImpl.java index 532554d..3e328da 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/PKCS12BagAttributeCarrierImpl.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/util/PKCS12BagAttributeCarrierImpl.java @@ -12,7 +12,6 @@ import org.bouncycastle.asn1.ASN1Encodable; import org.bouncycastle.asn1.ASN1InputStream; import org.bouncycastle.asn1.ASN1ObjectIdentifier; import org.bouncycastle.asn1.ASN1OutputStream; -import org.bouncycastle.asn1.DERObjectIdentifier; import org.bouncycastle.jce.interfaces.PKCS12BagAttributeCarrier; public class PKCS12BagAttributeCarrierImpl @@ -90,7 +89,7 @@ public class PKCS12BagAttributeCarrierImpl while (e.hasMoreElements()) { - DERObjectIdentifier oid = (DERObjectIdentifier)e.nextElement(); + ASN1ObjectIdentifier oid = (ASN1ObjectIdentifier)e.nextElement(); aOut.writeObject(oid); aOut.writeObject((ASN1Encodable)pkcs12Attributes.get(oid)); diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/PEMUtil.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/PEMUtil.java index 8699c3c..8116f29 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/PEMUtil.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/PEMUtil.java @@ -6,7 +6,7 @@ import java.io.InputStream; import org.bouncycastle.asn1.ASN1Sequence; import org.bouncycastle.util.encoders.Base64; -public class PEMUtil +class PEMUtil { private final String _header1; private final String _header2; @@ -33,11 +33,6 @@ public class PEMUtil { while (((c = in.read()) != '\r') && c != '\n' && (c >= 0)) { - if (c == '\r') - { - continue; - } - l.append((char)c); } } diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/PKIXCertPath.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/PKIXCertPath.java index 91d4829..b82d091 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/PKIXCertPath.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/PKIXCertPath.java @@ -34,7 +34,8 @@ import org.bouncycastle.asn1.DERSet; import org.bouncycastle.asn1.pkcs.ContentInfo; import org.bouncycastle.asn1.pkcs.PKCSObjectIdentifiers; import org.bouncycastle.asn1.pkcs.SignedData; -import org.bouncycastle.jce.provider.BouncyCastleProvider; +import org.bouncycastle.jcajce.util.BCJcaJceHelper; +import org.bouncycastle.jcajce.util.JcaJceHelper; import org.bouncycastle.util.io.pem.PemObject; import org.bouncycastle.util.io.pem.PemWriter; @@ -45,6 +46,8 @@ import org.bouncycastle.util.io.pem.PemWriter; public class PKIXCertPath extends CertPath { + private final JcaJceHelper helper = new BCJcaJceHelper(); + static final List certPathEncodings; static @@ -180,7 +183,7 @@ public class PKIXCertPath } Enumeration e = ((ASN1Sequence)derObject).getObjects(); certificates = new ArrayList(); - CertificateFactory certFactory = CertificateFactory.getInstance("X.509", BouncyCastleProvider.PROVIDER_NAME); + CertificateFactory certFactory = helper.createCertificateFactory("X.509"); while (e.hasMoreElements()) { ASN1Encodable element = (ASN1Encodable)e.nextElement(); @@ -193,7 +196,7 @@ public class PKIXCertPath { inStream = new BufferedInputStream(inStream); certificates = new ArrayList(); - CertificateFactory certFactory= CertificateFactory.getInstance("X.509", BouncyCastleProvider.PROVIDER_NAME); + CertificateFactory certFactory= helper.createCertificateFactory("X.509"); Certificate cert; while ((cert = certFactory.generateCertificate(inStream)) != null) { @@ -213,7 +216,7 @@ public class PKIXCertPath { throw new CertificateException("BouncyCastle provider not found while trying to get a CertificateFactory:\n" + ex.toString()); } - + this.certificates = sortCerts(certificates); } diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/X509CRLEntryObject.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/X509CRLEntryObject.java index 32e595c..0b53bd3 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/X509CRLEntryObject.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/X509CRLEntryObject.java @@ -23,7 +23,6 @@ import org.bouncycastle.asn1.x509.Extensions; import org.bouncycastle.asn1.x509.GeneralName; import org.bouncycastle.asn1.x509.GeneralNames; import org.bouncycastle.asn1.x509.TBSCertList; -import org.bouncycastle.asn1.x509.X509Extension; /** * The following extensions are listed in RFC 2459 as relevant to CRL Entries @@ -31,7 +30,7 @@ import org.bouncycastle.asn1.x509.X509Extension; * ReasonCode Hode Instruction Code Invalidity Date Certificate Issuer * (critical) */ -public class X509CRLEntryObject extends X509CRLEntry +class X509CRLEntryObject extends X509CRLEntry { private TBSCertList.CRLEntry c; @@ -285,11 +284,11 @@ public class X509CRLEntryObject extends X509CRLEntry buf.append(" critical(").append(ext.isCritical()).append(") "); try { - if (oid.equals(X509Extension.reasonCode)) + if (oid.equals(Extension.reasonCode)) { buf.append(CRLReason.getInstance(ASN1Enumerated.getInstance(dIn.readObject()))).append(nl); } - else if (oid.equals(X509Extension.certificateIssuer)) + else if (oid.equals(Extension.certificateIssuer)) { buf.append("Certificate issuer: ").append(GeneralNames.getInstance(dIn.readObject())).append(nl); } diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/X509CRLObject.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/X509CRLObject.java index c7d0402..cd877d0 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/X509CRLObject.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/X509CRLObject.java @@ -42,7 +42,6 @@ import org.bouncycastle.asn1.x509.IssuingDistributionPoint; import org.bouncycastle.asn1.x509.TBSCertList; import org.bouncycastle.jce.X509Principal; import org.bouncycastle.jce.provider.BouncyCastleProvider; -import org.bouncycastle.jce.provider.RFC3280CertPathUtilities; import org.bouncycastle.util.encoders.Hex; /** @@ -54,7 +53,7 @@ import org.bouncycastle.util.encoders.Hex; * Delta CRL Indicator (critical) * Issuing Distribution Point (critical) */ -public class X509CRLObject +class X509CRLObject extends X509CRL { private CertificateList c; @@ -120,8 +119,8 @@ public class X509CRLObject return false; } - extns.remove(RFC3280CertPathUtilities.ISSUING_DISTRIBUTION_POINT); - extns.remove(RFC3280CertPathUtilities.DELTA_CRL_INDICATOR); + extns.remove(Extension.issuingDistributionPoint.getId()); + extns.remove(Extension.deltaCRLIndicator.getId()); return !extns.isEmpty(); } diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/X509CertificateObject.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/X509CertificateObject.java index 4422062..56df634 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/X509CertificateObject.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/X509CertificateObject.java @@ -9,9 +9,7 @@ import java.security.InvalidKeyException; import java.security.NoSuchAlgorithmException; import java.security.NoSuchProviderException; import java.security.Principal; -import java.security.Provider; import java.security.PublicKey; -import java.security.Security; import java.security.Signature; import java.security.SignatureException; import java.security.cert.Certificate; @@ -61,7 +59,6 @@ import org.bouncycastle.jcajce.provider.asymmetric.util.PKCS12BagAttributeCarrie import org.bouncycastle.jce.X509Principal; import org.bouncycastle.jce.interfaces.PKCS12BagAttributeCarrier; import org.bouncycastle.jce.provider.BouncyCastleProvider; -import org.bouncycastle.jce.provider.RFC3280CertPathUtilities; import org.bouncycastle.util.Arrays; import org.bouncycastle.util.Integers; import org.bouncycastle.util.encoders.Hex; @@ -238,37 +235,11 @@ class X509CertificateObject /** * return a more "meaningful" representation for the signature algorithm used in - * the certficate. + * the certificate. */ public String getSigAlgName() { - Provider prov = Security.getProvider(BouncyCastleProvider.PROVIDER_NAME); - - if (prov != null) - { - String algName = prov.getProperty("Alg.Alias.Signature." + this.getSigAlgOID()); - - if (algName != null) - { - return algName; - } - } - - Provider[] provs = Security.getProviders(); - - // - // search every provider looking for a real algorithm - // - for (int i = 0; i != provs.length; i++) - { - String algName = provs[i].getProperty("Alg.Alias.Signature." + this.getSigAlgOID()); - if (algName != null) - { - return algName; - } - } - - return this.getSigAlgOID(); + return X509SignatureUtil.getSignatureName(c.getSignatureAlgorithm()); } /** @@ -522,19 +493,18 @@ class X509CertificateObject while (e.hasMoreElements()) { ASN1ObjectIdentifier oid = (ASN1ObjectIdentifier)e.nextElement(); - String oidId = oid.getId(); - - if (oidId.equals(RFC3280CertPathUtilities.KEY_USAGE) - || oidId.equals(RFC3280CertPathUtilities.CERTIFICATE_POLICIES) - || oidId.equals(RFC3280CertPathUtilities.POLICY_MAPPINGS) - || oidId.equals(RFC3280CertPathUtilities.INHIBIT_ANY_POLICY) - || oidId.equals(RFC3280CertPathUtilities.CRL_DISTRIBUTION_POINTS) - || oidId.equals(RFC3280CertPathUtilities.ISSUING_DISTRIBUTION_POINT) - || oidId.equals(RFC3280CertPathUtilities.DELTA_CRL_INDICATOR) - || oidId.equals(RFC3280CertPathUtilities.POLICY_CONSTRAINTS) - || oidId.equals(RFC3280CertPathUtilities.BASIC_CONSTRAINTS) - || oidId.equals(RFC3280CertPathUtilities.SUBJECT_ALTERNATIVE_NAME) - || oidId.equals(RFC3280CertPathUtilities.NAME_CONSTRAINTS)) + + if (oid.equals(Extension.keyUsage) + || oid.equals(Extension.certificatePolicies) + || oid.equals(Extension.policyMappings) + || oid.equals(Extension.inhibitAnyPolicy) + || oid.equals(Extension.cRLDistributionPoints) + || oid.equals(Extension.issuingDistributionPoint) + || oid.equals(Extension.deltaCRLIndicator) + || oid.equals(Extension.policyConstraints) + || oid.equals(Extension.basicConstraints) + || oid.equals(Extension.subjectAlternativeName) + || oid.equals(Extension.nameConstraints)) { continue; } @@ -775,7 +745,16 @@ class X509CertificateObject InvalidKeyException, NoSuchProviderException, SignatureException { String sigName = X509SignatureUtil.getSignatureName(c.getSignatureAlgorithm()); - Signature signature = Signature.getInstance(sigName, sigProvider); + Signature signature; + + if (sigProvider != null) + { + signature = Signature.getInstance(sigName, sigProvider); + } + else + { + signature = Signature.getInstance(sigName); + } checkSignature(key, signature); } diff --git a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/X509SignatureUtil.java b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/X509SignatureUtil.java index 127b534..8488f80 100644 --- a/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/X509SignatureUtil.java +++ b/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/x509/X509SignatureUtil.java @@ -5,15 +5,17 @@ import java.security.AlgorithmParameters; import java.security.GeneralSecurityException; import java.security.InvalidKeyException; import java.security.NoSuchAlgorithmException; +import java.security.Provider; +import java.security.Security; import java.security.Signature; import java.security.SignatureException; import java.security.spec.PSSParameterSpec; import org.bouncycastle.asn1.ASN1Encodable; import org.bouncycastle.asn1.ASN1Null; +import org.bouncycastle.asn1.ASN1ObjectIdentifier; import org.bouncycastle.asn1.ASN1Sequence; import org.bouncycastle.asn1.DERNull; -import org.bouncycastle.asn1.DERObjectIdentifier; import org.bouncycastle.asn1.cryptopro.CryptoProObjectIdentifiers; import org.bouncycastle.asn1.nist.NISTObjectIdentifiers; import org.bouncycastle.asn1.oiw.OIWObjectIdentifiers; @@ -22,6 +24,7 @@ import org.bouncycastle.asn1.pkcs.RSASSAPSSparams; import org.bouncycastle.asn1.teletrust.TeleTrusTObjectIdentifiers; import org.bouncycastle.asn1.x509.AlgorithmIdentifier; import org.bouncycastle.asn1.x9.X9ObjectIdentifiers; +import org.bouncycastle.jce.provider.BouncyCastleProvider; class X509SignatureUtil { @@ -76,7 +79,33 @@ class X509SignatureUtil { ASN1Sequence ecDsaParams = ASN1Sequence.getInstance(params); - return getDigestAlgName((DERObjectIdentifier)ecDsaParams.getObjectAt(0)) + "withECDSA"; + return getDigestAlgName((ASN1ObjectIdentifier)ecDsaParams.getObjectAt(0)) + "withECDSA"; + } + } + + Provider prov = Security.getProvider(BouncyCastleProvider.PROVIDER_NAME); + + if (prov != null) + { + String algName = prov.getProperty("Alg.Alias.Signature." + sigAlgId.getAlgorithm().getId()); + + if (algName != null) + { + return algName; + } + } + + Provider[] provs = Security.getProviders(); + + // + // search every provider looking for a real algorithm + // + for (int i = 0; i != provs.length; i++) + { + String algName = provs[i].getProperty("Alg.Alias.Signature." + sigAlgId.getAlgorithm().getId()); + if (algName != null) + { + return algName; } } @@ -88,7 +117,7 @@ class X509SignatureUtil * representations rather the the algorithm identifier (if possible). */ private static String getDigestAlgName( - DERObjectIdentifier digestAlgOID) + ASN1ObjectIdentifier digestAlgOID) { if (PKCSObjectIdentifiers.md5.equals(digestAlgOID)) { |