summaryrefslogtreecommitdiffstats
path: root/bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/IESCipher.java
diff options
context:
space:
mode:
Diffstat (limited to 'bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/IESCipher.java')
-rw-r--r--bcprov/src/main/java/org/bouncycastle/jcajce/provider/asymmetric/ec/IESCipher.java74
1 files changed, 63 insertions, 11 deletions
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);
+ }
+ }
}