summary refs log tree commit diff
path: root/crypto/src/math/ec/endo
diff options
context:
space:
mode:
authorPeter Dettman <peter.dettman@bouncycastle.org>2014-03-13 22:54:23 +0700
committerPeter Dettman <peter.dettman@bouncycastle.org>2014-03-13 22:54:23 +0700
commit104b98cc2797c4613151b95dc87218eca7f32c98 (patch)
treef0e6d13b80c03fbcea305195071b63c85534249f /crypto/src/math/ec/endo
parentFix bug in DoFinal introduced by last change (diff)
downloadBouncyCastle.NET-ed25519-104b98cc2797c4613151b95dc87218eca7f32c98.tar.xz
Port GLV implementation from Java
Diffstat (limited to 'crypto/src/math/ec/endo')
-rw-r--r--crypto/src/math/ec/endo/ECEndomorphism.cs11
-rw-r--r--crypto/src/math/ec/endo/GlvEndomorphism.cs10
-rw-r--r--crypto/src/math/ec/endo/GlvTypeBEndomorphism.cs55
-rw-r--r--crypto/src/math/ec/endo/GlvTypeBParameters.cs60
4 files changed, 136 insertions, 0 deletions
diff --git a/crypto/src/math/ec/endo/ECEndomorphism.cs b/crypto/src/math/ec/endo/ECEndomorphism.cs
new file mode 100644

index 000000000..dfb321368 --- /dev/null +++ b/crypto/src/math/ec/endo/ECEndomorphism.cs
@@ -0,0 +1,11 @@ +using System; + +namespace Org.BouncyCastle.Math.EC.Endo +{ + public interface ECEndomorphism + { + ECPointMap PointMap { get; } + + bool HasEfficientPointMap { get; } + } +} diff --git a/crypto/src/math/ec/endo/GlvEndomorphism.cs b/crypto/src/math/ec/endo/GlvEndomorphism.cs new file mode 100644
index 000000000..f65bdd613 --- /dev/null +++ b/crypto/src/math/ec/endo/GlvEndomorphism.cs
@@ -0,0 +1,10 @@ +using System; + +namespace Org.BouncyCastle.Math.EC.Endo +{ + public interface GlvEndomorphism + : ECEndomorphism + { + BigInteger[] DecomposeScalar(BigInteger k); + } +} diff --git a/crypto/src/math/ec/endo/GlvTypeBEndomorphism.cs b/crypto/src/math/ec/endo/GlvTypeBEndomorphism.cs new file mode 100644
index 000000000..d234d88bf --- /dev/null +++ b/crypto/src/math/ec/endo/GlvTypeBEndomorphism.cs
@@ -0,0 +1,55 @@ +using System; + +namespace Org.BouncyCastle.Math.EC.Endo +{ + public class GlvTypeBEndomorphism + : GlvEndomorphism + { + protected readonly ECCurve m_curve; + protected readonly GlvTypeBParameters m_parameters; + protected readonly ECPointMap m_pointMap; + + public GlvTypeBEndomorphism(ECCurve curve, GlvTypeBParameters parameters) + { + this.m_curve = curve; + this.m_parameters = parameters; + this.m_pointMap = new ScaleXPointMap(curve.FromBigInteger(parameters.Beta)); + } + + public virtual BigInteger[] DecomposeScalar(BigInteger k) + { + int bits = m_parameters.Bits; + BigInteger b1 = CalculateB(k, m_parameters.G1, bits); + BigInteger b2 = CalculateB(k, m_parameters.G2, bits); + + BigInteger[] v1 = m_parameters.V1, v2 = m_parameters.V2; + BigInteger a = k.Subtract((b1.Multiply(v1[0])).Add(b2.Multiply(v2[0]))); + BigInteger b = (b1.Multiply(v1[1])).Add(b2.Multiply(v2[1])).Negate(); + + return new BigInteger[]{ a, b }; + } + + public virtual ECPointMap PointMap + { + get { return m_pointMap; } + } + + public virtual bool HasEfficientPointMap + { + get { return true; } + } + + protected virtual BigInteger CalculateB(BigInteger k, BigInteger g, int t) + { + bool negative = (g.SignValue < 0); + BigInteger b = k.Multiply(g.Abs()); + bool extra = b.TestBit(t - 1); + b = b.ShiftRight(t); + if (extra) + { + b = b.Add(BigInteger.One); + } + return negative ? b.Negate() : b; + } + } +} diff --git a/crypto/src/math/ec/endo/GlvTypeBParameters.cs b/crypto/src/math/ec/endo/GlvTypeBParameters.cs new file mode 100644
index 000000000..f93dfaf2b --- /dev/null +++ b/crypto/src/math/ec/endo/GlvTypeBParameters.cs
@@ -0,0 +1,60 @@ +using System; + +namespace Org.BouncyCastle.Math.EC.Endo +{ + public class GlvTypeBParameters + { + protected readonly BigInteger m_beta; + protected readonly BigInteger m_lambda; + protected readonly BigInteger[] m_v1, m_v2; + protected readonly BigInteger m_g1, m_g2; + protected readonly int m_bits; + + public GlvTypeBParameters(BigInteger beta, BigInteger lambda, BigInteger[] v1, BigInteger[] v2, + BigInteger g1, BigInteger g2, int bits) + { + this.m_beta = beta; + this.m_lambda = lambda; + this.m_v1 = v1; + this.m_v2 = v2; + this.m_g1 = g1; + this.m_g2 = g2; + this.m_bits = bits; + } + + public virtual BigInteger Beta + { + get { return m_beta; } + } + + public virtual BigInteger Lambda + { + get { return m_lambda; } + } + + public virtual BigInteger[] V1 + { + get { return m_v1; } + } + + public virtual BigInteger[] V2 + { + get { return m_v2; } + } + + public virtual BigInteger G1 + { + get { return m_g1; } + } + + public virtual BigInteger G2 + { + get { return m_g2; } + } + + public virtual int Bits + { + get { return m_bits; } + } + } +}