diff --git a/crypto/src/crypto/agreement/ECDHBasicAgreement.cs b/crypto/src/crypto/agreement/ECDHBasicAgreement.cs
index c33f16f78..ca7b3fa3f 100644
--- a/crypto/src/crypto/agreement/ECDHBasicAgreement.cs
+++ b/crypto/src/crypto/agreement/ECDHBasicAgreement.cs
@@ -46,6 +46,9 @@ namespace Org.BouncyCastle.Crypto.Agreement
ICipherParameters pubKey)
{
ECPublicKeyParameters pub = (ECPublicKeyParameters) pubKey;
+ if (!pub.Parameters.Equals(privKey.Parameters))
+ throw new InvalidOperationException("ECDH public key has wrong domain parameters");
+
ECPoint P = pub.Q.Multiply(privKey.D).Normalize();
if (P.IsInfinity)
diff --git a/crypto/src/crypto/agreement/ECDHCBasicAgreement.cs b/crypto/src/crypto/agreement/ECDHCBasicAgreement.cs
index 89be7061e..1c9ae45f9 100644
--- a/crypto/src/crypto/agreement/ECDHCBasicAgreement.cs
+++ b/crypto/src/crypto/agreement/ECDHCBasicAgreement.cs
@@ -29,7 +29,7 @@ namespace Org.BouncyCastle.Crypto.Agreement
public class ECDHCBasicAgreement
: IBasicAgreement
{
- private ECPrivateKeyParameters key;
+ private ECPrivateKeyParameters privKey;
public virtual void Init(
ICipherParameters parameters)
@@ -39,12 +39,12 @@ namespace Org.BouncyCastle.Crypto.Agreement
parameters = ((ParametersWithRandom) parameters).Parameters;
}
- this.key = (ECPrivateKeyParameters)parameters;
+ this.privKey = (ECPrivateKeyParameters)parameters;
}
public virtual int GetFieldSize()
{
- return (key.Parameters.Curve.FieldSize + 7) / 8;
+ return (privKey.Parameters.Curve.FieldSize + 7) / 8;
}
public virtual BigInteger CalculateAgreement(
@@ -52,8 +52,10 @@ namespace Org.BouncyCastle.Crypto.Agreement
{
ECPublicKeyParameters pub = (ECPublicKeyParameters) pubKey;
ECDomainParameters parameters = pub.Parameters;
+ if (!parameters.Equals(privKey.Parameters))
+ throw new InvalidOperationException("ECDHC public key has wrong domain parameters");
- BigInteger hd = parameters.H.Multiply(key.D).Mod(parameters.N);
+ BigInteger hd = parameters.H.Multiply(privKey.D).Mod(parameters.N);
ECPoint P = pub.Q.Multiply(hd).Normalize();
diff --git a/crypto/src/crypto/agreement/ECMqvBasicAgreement.cs b/crypto/src/crypto/agreement/ECMqvBasicAgreement.cs
index f55ae46af..8d5cebb13 100644
--- a/crypto/src/crypto/agreement/ECMqvBasicAgreement.cs
+++ b/crypto/src/crypto/agreement/ECMqvBasicAgreement.cs
@@ -34,8 +34,12 @@ namespace Org.BouncyCastle.Crypto.Agreement
MqvPublicParameters pubParams = (MqvPublicParameters)pubKey;
ECPrivateKeyParameters staticPrivateKey = privParams.StaticPrivateKey;
+ ECDomainParameters parameters = staticPrivateKey.Parameters;
- ECPoint agreement = CalculateMqvAgreement(staticPrivateKey.Parameters, staticPrivateKey,
+ if (!parameters.Equals(pubParams.StaticPublicKey.Parameters))
+ throw new InvalidOperationException("ECMQV public key components have wrong domain parameters");
+
+ ECPoint agreement = CalculateMqvAgreement(parameters, staticPrivateKey,
privParams.EphemeralPrivateKey, privParams.EphemeralPublicKey,
pubParams.StaticPublicKey, pubParams.EphemeralPublicKey).Normalize();
@@ -61,8 +65,8 @@ namespace Org.BouncyCastle.Crypto.Agreement
ECCurve curve = parameters.Curve;
ECPoint[] points = new ECPoint[]{
- // The Q2U public key is optional
- ECAlgorithms.ImportPoint(curve, Q2U == null ? parameters.G.Multiply(d2U.D) : Q2U.Q),
+ // The Q2U public key is optional - but will be calculated for us if it wasn't present
+ ECAlgorithms.ImportPoint(curve, Q2U.Q),
ECAlgorithms.ImportPoint(curve, Q1V.Q),
ECAlgorithms.ImportPoint(curve, Q2V.Q)
};
diff --git a/crypto/src/crypto/parameters/DHParameters.cs b/crypto/src/crypto/parameters/DHParameters.cs
index 4258df5c5..bdea12432 100644
--- a/crypto/src/crypto/parameters/DHParameters.cs
+++ b/crypto/src/crypto/parameters/DHParameters.cs
@@ -162,7 +162,7 @@ namespace Org.BouncyCastle.Crypto.Parameters
return Equals(other);
}
- protected bool Equals(
+ protected virtual bool Equals(
DHParameters other)
{
return p.Equals(other.p)
diff --git a/crypto/src/crypto/parameters/ECDomainParameters.cs b/crypto/src/crypto/parameters/ECDomainParameters.cs
index 619971a6c..9d1544771 100644
--- a/crypto/src/crypto/parameters/ECDomainParameters.cs
+++ b/crypto/src/crypto/parameters/ECDomainParameters.cs
@@ -93,14 +93,13 @@ namespace Org.BouncyCastle.Crypto.Parameters
return Equals(other);
}
- protected bool Equals(
+ protected virtual bool Equals(
ECDomainParameters other)
{
return curve.Equals(other.curve)
&& g.Equals(other.g)
&& n.Equals(other.n)
- && h.Equals(other.h)
- && Arrays.AreEqual(seed, other.seed);
+ && h.Equals(other.h);
}
public override int GetHashCode()
@@ -108,9 +107,7 @@ namespace Org.BouncyCastle.Crypto.Parameters
return curve.GetHashCode()
^ g.GetHashCode()
^ n.GetHashCode()
- ^ h.GetHashCode()
- ^ Arrays.GetHashCode(seed);
+ ^ h.GetHashCode();
}
}
-
}
diff --git a/crypto/src/crypto/parameters/MqvPrivateParameters.cs b/crypto/src/crypto/parameters/MqvPrivateParameters.cs
index 4bf33e347..9159cac12 100644
--- a/crypto/src/crypto/parameters/MqvPrivateParameters.cs
+++ b/crypto/src/crypto/parameters/MqvPrivateParameters.cs
@@ -21,22 +21,42 @@ namespace Org.BouncyCastle.Crypto.Parameters
ECPrivateKeyParameters ephemeralPrivateKey,
ECPublicKeyParameters ephemeralPublicKey)
{
- this.staticPrivateKey = staticPrivateKey;
- this.ephemeralPrivateKey = ephemeralPrivateKey;
- this.ephemeralPublicKey = ephemeralPublicKey;
+ if (staticPrivateKey == null)
+ throw new ArgumentNullException("staticPrivateKey");
+ if (ephemeralPrivateKey == null)
+ throw new ArgumentNullException("ephemeralPrivateKey");
+
+ ECDomainParameters parameters = staticPrivateKey.Parameters;
+ if (!parameters.Equals(ephemeralPrivateKey.Parameters))
+ throw new ArgumentException("Static and ephemeral private keys have different domain parameters");
+
+ if (ephemeralPublicKey == null)
+ {
+ ephemeralPublicKey = new ECPublicKeyParameters(
+ parameters.G.Multiply(ephemeralPrivateKey.D),
+ parameters);
+ }
+ else if (!parameters.Equals(ephemeralPublicKey.Parameters))
+ {
+ throw new ArgumentException("Ephemeral public key has different domain parameters");
+ }
+
+ this.staticPrivateKey = staticPrivateKey;
+ this.ephemeralPrivateKey = ephemeralPrivateKey;
+ this.ephemeralPublicKey = ephemeralPublicKey;
}
- public ECPrivateKeyParameters StaticPrivateKey
+ public virtual ECPrivateKeyParameters StaticPrivateKey
{
get { return staticPrivateKey; }
}
- public ECPrivateKeyParameters EphemeralPrivateKey
+ public virtual ECPrivateKeyParameters EphemeralPrivateKey
{
get { return ephemeralPrivateKey; }
}
- public ECPublicKeyParameters EphemeralPublicKey
+ public virtual ECPublicKeyParameters EphemeralPublicKey
{
get { return ephemeralPublicKey; }
}
diff --git a/crypto/src/crypto/parameters/MqvPublicParameters.cs b/crypto/src/crypto/parameters/MqvPublicParameters.cs
index a0e273ac4..239afa321 100644
--- a/crypto/src/crypto/parameters/MqvPublicParameters.cs
+++ b/crypto/src/crypto/parameters/MqvPublicParameters.cs
@@ -8,20 +8,27 @@ namespace Org.BouncyCastle.Crypto.Parameters
private readonly ECPublicKeyParameters staticPublicKey;
private readonly ECPublicKeyParameters ephemeralPublicKey;
- public MqvPublicParameters(
+ public MqvPublicParameters(
ECPublicKeyParameters staticPublicKey,
ECPublicKeyParameters ephemeralPublicKey)
{
- this.staticPublicKey = staticPublicKey;
+ if (staticPublicKey == null)
+ throw new ArgumentNullException("staticPublicKey");
+ if (ephemeralPublicKey == null)
+ throw new ArgumentNullException("ephemeralPublicKey");
+ if (!staticPublicKey.Parameters.Equals(ephemeralPublicKey.Parameters))
+ throw new ArgumentException("Static and ephemeral public keys have different domain parameters");
+
+ this.staticPublicKey = staticPublicKey;
this.ephemeralPublicKey = ephemeralPublicKey;
- }
+ }
- public ECPublicKeyParameters StaticPublicKey
+ public virtual ECPublicKeyParameters StaticPublicKey
{
get { return staticPublicKey; }
}
- public ECPublicKeyParameters EphemeralPublicKey
+ public virtual ECPublicKeyParameters EphemeralPublicKey
{
get { return ephemeralPublicKey; }
}
diff --git a/crypto/src/crypto/tls/TlsDHUtilities.cs b/crypto/src/crypto/tls/TlsDHUtilities.cs
index 019d084e3..7a44670fd 100644
--- a/crypto/src/crypto/tls/TlsDHUtilities.cs
+++ b/crypto/src/crypto/tls/TlsDHUtilities.cs
@@ -391,7 +391,8 @@ namespace Org.BouncyCastle.Crypto.Tls
public static bool AreCompatibleParameters(DHParameters a, DHParameters b)
{
- return a.P.Equals(b.P) && a.G.Equals(b.G);
+ return a.P.Equals(b.P) && a.G.Equals(b.G)
+ && (a.Q == null || b.Q == null || a.Q.Equals(b.Q));
}
public static byte[] CalculateDHBasicAgreement(DHPublicKeyParameters publicKey,
diff --git a/crypto/src/crypto/tls/TlsEccUtilities.cs b/crypto/src/crypto/tls/TlsEccUtilities.cs
index 706ebfd3c..a5c8fa910 100644
--- a/crypto/src/crypto/tls/TlsEccUtilities.cs
+++ b/crypto/src/crypto/tls/TlsEccUtilities.cs
@@ -279,8 +279,7 @@ namespace Org.BouncyCastle.Crypto.Tls
public static bool AreOnSameCurve(ECDomainParameters a, ECDomainParameters b)
{
- // TODO Move to ECDomainParameters.Equals() or other utility method?
- return a.Curve.Equals(b.Curve) && a.G.Equals(b.G) && a.N.Equals(b.N) && a.H.Equals(b.H);
+ return a != null && a.Equals(b);
}
public static bool IsSupportedNamedCurve(int namedCurve)
|