diff options
author | Peter Dettman <peter.dettman@bouncycastle.org> | 2013-09-12 09:10:30 +0400 |
---|---|---|
committer | Peter Dettman <peter.dettman@bouncycastle.org> | 2013-09-12 09:10:30 +0400 |
commit | 17183de6da3770b187b5e588ea55a6bb0cf0253b (patch) | |
tree | 80c4583d4256ddf1efc44cda534f92f62fd6c8c1 /core/src | |
parent | ac21f62e490d66c4314ea36c3e63993d8b9dbfb5 (diff) |
Provide some extra methods on ECFieldElement to avoid full conversion to
BigInteger for common, simple tests
Diffstat (limited to 'core/src')
6 files changed, 71 insertions, 61 deletions
diff --git a/core/src/main/java/org/bouncycastle/asn1/ua/DSTU4145PointEncoder.java b/core/src/main/java/org/bouncycastle/asn1/ua/DSTU4145PointEncoder.java index 0227d2ad..41b50d04 100644 --- a/core/src/main/java/org/bouncycastle/asn1/ua/DSTU4145PointEncoder.java +++ b/core/src/main/java/org/bouncycastle/asn1/ua/DSTU4145PointEncoder.java @@ -38,26 +38,23 @@ public abstract class DSTU4145PointEncoder * @return the solution for <code>z<sup>2</sup> + z = beta</code> or * <code>null</code> if no solution exists. */ - private static ECFieldElement solveQuadradicEquation(ECFieldElement beta) + private static ECFieldElement solveQuadraticEquation(ECCurve curve, ECFieldElement beta) { - ECFieldElement.F2m b = (ECFieldElement.F2m)beta; - ECFieldElement zeroElement = new ECFieldElement.F2m( - b.getM(), b.getK1(), b.getK2(), b.getK3(), ECConstants.ZERO); - - if (beta.toBigInteger().equals(ECConstants.ZERO)) + if (beta.isZero()) { - return zeroElement; + return beta; } + ECFieldElement zeroElement = curve.fromBigInteger(ECConstants.ZERO); + ECFieldElement z = null; - ECFieldElement gamma = zeroElement; + ECFieldElement gamma = null; Random rand = new Random(); - int m = b.getM(); + int m = beta.getFieldSize(); do { - ECFieldElement t = new ECFieldElement.F2m(b.getM(), b.getK1(), - b.getK2(), b.getK3(), new BigInteger(m, rand)); + ECFieldElement t = curve.fromBigInteger(new BigInteger(m, rand)); z = zeroElement; ECFieldElement w = beta; for (int i = 1; i <= m - 1; i++) @@ -66,13 +63,13 @@ public abstract class DSTU4145PointEncoder z = z.square().add(w2.multiply(t)); w = w2.add(beta); } - if (!w.toBigInteger().equals(ECConstants.ZERO)) + if (!w.isZero()) { return null; } gamma = z.square().add(z); } - while (gamma.toBigInteger().equals(ECConstants.ZERO)); + while (gamma.isZero()); return z; } @@ -94,7 +91,7 @@ public abstract class DSTU4145PointEncoder int byteCount = converter.getByteLength(Q.getX()); byte[] bytes = converter.integerToBytes(Q.getX().toBigInteger(), byteCount); - if (!(Q.getX().toBigInteger().equals(ECConstants.ZERO))) + if (!Q.getX().isZero()) { ECFieldElement y = Q.getY().multiply(Q.getX().invert()); if (trace(y).equals(ECConstants.ONE)) @@ -129,13 +126,12 @@ public abstract class DSTU4145PointEncoder bytes = Arrays.clone(bytes); bytes[bytes.length - 1] ^= 0x01; } - ECCurve.F2m c = (ECCurve.F2m)curve; ECFieldElement xp = curve.fromBigInteger(new BigInteger(1, bytes)); ECFieldElement yp = null; - if (xp.toBigInteger().equals(ECConstants.ZERO)) + if (xp.isZero()) { yp = (ECFieldElement.F2m)curve.getB(); - for (int i = 0; i < c.getM() - 1; i++) + for (int i = 0; i < curve.getFieldSize() - 1; i++) { yp = yp.square(); } @@ -144,7 +140,7 @@ public abstract class DSTU4145PointEncoder { ECFieldElement beta = xp.add(curve.getA()).add( curve.getB().multiply(xp.square().invert())); - ECFieldElement z = solveQuadradicEquation(beta); + ECFieldElement z = solveQuadraticEquation(curve, beta); if (z == null) { throw new RuntimeException("Invalid point compression"); diff --git a/core/src/main/java/org/bouncycastle/crypto/signers/DSTU4145Signer.java b/core/src/main/java/org/bouncycastle/crypto/signers/DSTU4145Signer.java index a8fc194e..a12e4012 100644 --- a/core/src/main/java/org/bouncycastle/crypto/signers/DSTU4145Signer.java +++ b/core/src/main/java/org/bouncycastle/crypto/signers/DSTU4145Signer.java @@ -57,7 +57,7 @@ public class DSTU4145Signer public BigInteger[] generateSignature(byte[] message) { ECFieldElement h = hash2FieldElement(key.getParameters().getCurve(), message); - if (h.toBigInteger().signum() == 0) + if (h.isZero()) { h = key.getParameters().getCurve().fromBigInteger(ONE); } @@ -74,7 +74,7 @@ public class DSTU4145Signer e = generateRandomInteger(key.getParameters().getN(), random); Fe = key.getParameters().getG().multiply(e).getX(); } - while (Fe.toBigInteger().signum() == 0); + while (Fe.isZero()); y = h.multiply(Fe); r = fieldElement2Integer(key.getParameters().getN(), y); @@ -100,7 +100,7 @@ public class DSTU4145Signer } ECFieldElement h = hash2FieldElement(key.getParameters().getCurve(), message); - if (h.toBigInteger().signum() == 0) + if (h.isZero()) { h = key.getParameters().getCurve().fromBigInteger(ONE); } diff --git a/core/src/main/java/org/bouncycastle/math/ec/ECCurve.java b/core/src/main/java/org/bouncycastle/math/ec/ECCurve.java index 58281af7..63a5f19b 100644 --- a/core/src/main/java/org/bouncycastle/math/ec/ECCurve.java +++ b/core/src/main/java/org/bouncycastle/math/ec/ECCurve.java @@ -148,9 +148,7 @@ public abstract class ECCurve } BigInteger betaValue = beta.toBigInteger(); - int bit0 = betaValue.testBit(0) ? 1 : 0; - - if (bit0 != yTilde) + if (betaValue.testBit(0) != (yTilde == 1)) { // Use the other root beta = fromBigInteger(q.subtract(betaValue)); @@ -432,10 +430,7 @@ public abstract class ECCurve */ public boolean isKoblitz() { - return ((n != null) && (h != null) && - ((a.toBigInteger().equals(ECConstants.ZERO)) || - (a.toBigInteger().equals(ECConstants.ONE))) && - (b.toBigInteger().equals(ECConstants.ONE))); + return n != null && h != null && a.bitLength() <= 1 && b.bitLength() == 1; } /** @@ -480,7 +475,7 @@ public abstract class ECCurve { ECFieldElement xp = fromBigInteger(X1); ECFieldElement yp = null; - if (xp.toBigInteger().equals(ECConstants.ZERO)) + if (X1.signum() == 0) { yp = (ECFieldElement.F2m)b; for (int i = 0; i < m - 1; i++) @@ -491,13 +486,12 @@ public abstract class ECCurve else { ECFieldElement beta = xp.add(a).add(b.multiply(xp.square().invert())); - ECFieldElement z = solveQuadradicEquation(beta); + ECFieldElement z = solveQuadraticEquation(beta); if (z == null) { throw new IllegalArgumentException("Invalid point compression"); } - int zBit = z.toBigInteger().testBit(0) ? 1 : 0; - if (zBit != yTilde) + if (z.testBitZero() != (yTilde == 1)) { z = z.add(fromBigInteger(ECConstants.ONE)); } @@ -512,28 +506,26 @@ public abstract class ECCurve * D.1.6) The other solution is <code>z + 1</code>. * * @param beta - * The value to solve the qradratic equation for. + * The value to solve the quadratic equation for. * @return the solution for <code>z<sup>2</sup> + z = beta</code> or * <code>null</code> if no solution exists. */ - private ECFieldElement solveQuadradicEquation(ECFieldElement beta) + private ECFieldElement solveQuadraticEquation(ECFieldElement beta) { - ECFieldElement zeroElement = new ECFieldElement.F2m( - this.m, this.k1, this.k2, this.k3, ECConstants.ZERO); - - if (beta.toBigInteger().equals(ECConstants.ZERO)) + if (beta.isZero()) { - return zeroElement; + return beta; } + ECFieldElement zeroElement = fromBigInteger(ECConstants.ZERO); + ECFieldElement z = null; - ECFieldElement gamma = zeroElement; + ECFieldElement gamma = null; Random rand = new Random(); do { - ECFieldElement t = new ECFieldElement.F2m(this.m, this.k1, - this.k2, this.k3, new BigInteger(m, rand)); + ECFieldElement t = fromBigInteger(new BigInteger(m, rand)); z = zeroElement; ECFieldElement w = beta; for (int i = 1; i <= m - 1; i++) @@ -542,13 +534,13 @@ public abstract class ECCurve z = z.square().add(w2.multiply(t)); w = w2.add(beta); } - if (!w.toBigInteger().equals(ECConstants.ZERO)) + if (!w.isZero()) { return null; } gamma = z.square().add(z); } - while (gamma.toBigInteger().equals(ECConstants.ZERO)); + while (gamma.isZero()); return z; } diff --git a/core/src/main/java/org/bouncycastle/math/ec/ECFieldElement.java b/core/src/main/java/org/bouncycastle/math/ec/ECFieldElement.java index b5e9aa55..10a0fd35 100644 --- a/core/src/main/java/org/bouncycastle/math/ec/ECFieldElement.java +++ b/core/src/main/java/org/bouncycastle/math/ec/ECFieldElement.java @@ -19,6 +19,21 @@ public abstract class ECFieldElement public abstract ECFieldElement invert(); public abstract ECFieldElement sqrt(); + public int bitLength() + { + return toBigInteger().bitLength(); + } + + public boolean isZero() + { + return 0 == toBigInteger().signum(); + } + + public boolean testBitZero() + { + return toBigInteger().testBit(0); + } + public String toString() { return this.toBigInteger().toString(2); @@ -925,7 +940,21 @@ public abstract class ECFieldElement { this.representation = PPB; } + } + + public int bitLength() + { + return x.bitLength(); + } + public boolean isZero() + { + return x.isZero(); + } + + public boolean testBitZero() + { + return !x.isZero() && x.testBit(0); } public BigInteger toBigInteger() diff --git a/core/src/main/java/org/bouncycastle/math/ec/ECPoint.java b/core/src/main/java/org/bouncycastle/math/ec/ECPoint.java index cbc5aaf4..ff0dc33a 100644 --- a/core/src/main/java/org/bouncycastle/math/ec/ECPoint.java +++ b/core/src/main/java/org/bouncycastle/math/ec/ECPoint.java @@ -401,10 +401,9 @@ public abstract class ECPoint // bit of y * x^(-1) // if ypTilde = 0, then PC := 02, else PC := 03 // Note: PC === PO[0] - if (!(this.getX().toBigInteger().equals(ECConstants.ZERO))) + if (!this.getX().isZero()) { - if (this.getY().multiply(this.getX().invert()) - .toBigInteger().testBit(0)) + if (this.getY().multiply(this.getX().invert()).testBitZero()) { // ypTilde = 1, hence PC = 03 PO[0] = 0x03; @@ -545,7 +544,7 @@ public abstract class ECPoint return this; } - if (this.x.toBigInteger().signum() == 0) + if (this.x.isZero()) { // if x1 == 0, then (x1, y1) == (x1, x1 + y1) // and hence this = -this and thus 2(x1, y1) == infinity diff --git a/core/src/main/java/org/bouncycastle/math/ec/Tnaf.java b/core/src/main/java/org/bouncycastle/math/ec/Tnaf.java index af4355f3..03fc4da0 100644 --- a/core/src/main/java/org/bouncycastle/math/ec/Tnaf.java +++ b/core/src/main/java/org/bouncycastle/math/ec/Tnaf.java @@ -415,23 +415,17 @@ class Tnaf */ public static byte getMu(ECCurve.F2m curve) { - BigInteger a = curve.getA().toBigInteger(); - byte mu; - - if (a.equals(ECConstants.ZERO)) - { - mu = -1; - } - else if (a.equals(ECConstants.ONE)) + if (!curve.isKoblitz()) { - mu = 1; + throw new IllegalArgumentException("No Koblitz curve (ABC), TNAF multiplication not possible"); } - else + + if (curve.getA().isZero()) { - throw new IllegalArgumentException("No Koblitz curve (ABC), " + - "TNAF multiplication not possible"); + return -1; } - return mu; + + return 1; } /** |