ecpoint.java

来自「内容:基于jdk1.4的加密算法的具体实现」· Java 代码 · 共 503 行 · 第 1/2 页

JAVA
503
字号
            for (int i = h.bitLength() - 2; i > 0; i--)            {                             R = R.twice();                       if (h.testBit(i) && !e.testBit(i))                {                                        //System.out.print("+");                    R = R.add(this);                }                else if (!h.testBit(i) && e.testBit(i))                {                    //System.out.print("-");                    R = R.subtract(this);                }                // else                // System.out.print(".");            }            // System.out.println();            return R;        }    }        /**     * Elliptic curve points over F2m     */    public static class F2m extends ECPoint    {        private boolean withCompression;                /**         * @param curve base curve         * @param x x point         * @param y y point         */        public F2m(ECCurve curve, ECFieldElement x, ECFieldElement y)        {            this(curve, x, y, false);        }                /**         * @param curve base curve         * @param x x point         * @param y y point         * @param withCompression true if encode with point compression.         */        public F2m(ECCurve curve, ECFieldElement x, ECFieldElement y, boolean withCompression)        {            super(curve, x, y);            if ((x != null && y == null) || (x == null && y != null))            {                throw new IllegalArgumentException("Exactly one of the field elements is null");            }                        if (x != null)            {                // Check if x and y are elements of the same field                ECFieldElement.F2m.checkFieldElements(this.x, this.y);                    // Check if x and a are elements of the same field                ECFieldElement.F2m.checkFieldElements(this.x, this.curve.getA());            }                        this.withCompression = withCompression;        }        /**         * Constructor for point at infinity         */        public F2m(ECCurve curve)        {            super(curve, null, null);        }        /* (non-Javadoc)         * @see org.bouncycastle.math.ec.ECPoint#getEncoded()         */        public byte[] getEncoded()        {            if (this.isInfinity())             {                throw new RuntimeException("Point at infinity cannot be encoded");            }            int byteCount = converter.getByteLength(this.x);            byte[] X = converter.integerToBytes(this.getX().toBigInteger(), byteCount);            byte[] PO;            if (withCompression)            {                // See X9.62 4.3.6 and 4.2.2                PO = new byte[byteCount + 1];                PO[0] = 0x02;                // X9.62 4.2.2 and 4.3.6:                // if x = 0 then ypTilde := 0, else ypTilde is the rightmost                // 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.getY().multiply(this.getX().invert())                            .toBigInteger().testBit(0))                    {                        // ypTilde = 1, hence PC = 03                        PO[0] = 0x03;                    }                }                System.arraycopy(X, 0, PO, 1, byteCount);            }            else            {                byte[] Y = converter.integerToBytes(this.getY().toBigInteger(), byteCount);                    PO = new byte[byteCount + byteCount + 1];                    PO[0] = 0x04;                System.arraycopy(X, 0, PO, 1, byteCount);                System.arraycopy(Y, 0, PO, byteCount + 1, byteCount);                }            return PO;        }        /* (non-Javadoc)         * @see org.bouncycastle.math.ec.ECPoint#add(org.bouncycastle.math.ec.ECPoint)         */        public ECPoint add(ECPoint b)        {            // Check, if points are on the same curve            if (!(this.curve.equals(b.getCurve())))            {                throw new IllegalArgumentException("Only points on the same "                        + "curve can be added");            }            if (this.isInfinity())            {                if (b.isInfinity())                {                    return new ECPoint.F2m(this.curve, null, null,                            this.withCompression);                }                return new ECPoint.F2m(b.getCurve(), b.getX(), b.getY(), withCompression);            }            if (b.isInfinity())            {                return new ECPoint.F2m(this.curve, this.x, this.y, withCompression);            }            ECFieldElement.F2m.checkFieldElements(this.x, b.getX());            ECFieldElement.F2m x2 = (ECFieldElement.F2m)b.getX();            ECFieldElement.F2m y2 = (ECFieldElement.F2m)b.getY();            // Check if b = this or b = -this            if (this.x.equals(x2))            {                if (this.y.equals(y2))                {                    // this = b, i.e. this must be doubled                    return this.twice();                }                else                {                    // this = -b, i.e. the result is the point at infinity                    return new ECPoint.F2m(this.curve, null, null,                            this.withCompression);                }            }            ECFieldElement.F2m lambda                = (ECFieldElement.F2m)(this.y.add(y2)).divide(this.x.add(x2));            ECFieldElement.F2m x3                = (ECFieldElement.F2m)lambda.square().add(lambda).add(this.x).add(x2).add(this.curve.getA());            ECFieldElement.F2m y3                = (ECFieldElement.F2m)lambda.multiply(this.x.add(x3)).add(x3).add(this.y);            return new ECPoint.F2m(curve, x3, y3, withCompression);        }        /* (non-Javadoc)         * @see org.bouncycastle.math.ec.ECPoint#subtract(org.bouncycastle.math.ec.ECPoint)         */        public ECPoint subtract(ECPoint b)        {            if (b.isInfinity())            {                return new ECPoint.F2m(this.curve, this.x, this.y,                        this.withCompression);            }            // Add -b            ECPoint.F2m minusB                = new ECPoint.F2m(this.curve, b.x, b.x.add(b.y),                        this.withCompression);            return add(minusB);        }        /* (non-Javadoc)         * @see org.bouncycastle.math.ec.ECPoint#twice()         */        public ECPoint twice()        {            if (this.isInfinity() || (this.x.toBigInteger().equals(ECConstants.ZERO)))             {                // Twice identity element (point at infinity) is identity                // element, and if x1 == 0, then (x1, y1) == (x1, x1 + y1)                // and hence this = -this and thus 2(x1, y1) == infinity                return new ECPoint.F2m(curve, null, null, this.withCompression);            }            ECFieldElement.F2m lambda                = (ECFieldElement.F2m)this.x.add(this.y.divide(this.x));            ECFieldElement.F2m x3                = (ECFieldElement.F2m)lambda.square().add(lambda).                    add(this.curve.getA());            ECFieldElement.F2m y3                = (ECFieldElement.F2m)this.x.square().add(lambda.multiply(x3)).                    add(x3);            return new ECPoint.F2m(this.curve, x3, y3, withCompression);        }        public ECPoint multiply(            BigInteger k)        {            ECPoint.F2m p = this;            ECPoint.F2m q = new ECPoint.F2m(this.curve, null, null,                    this.withCompression);            int t = k.bitLength();            for (int i = 0; i < t; i++)             {                if (k.testBit(i))                 {                    q = (ECPoint.F2m)q.add(p);                }                p = (ECPoint.F2m)p.twice();            }            return q;        }    }}

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?