/
githubmirror
/
jdk22
Обзор
Документация
Войти
/
githubmirror
/
jdk22
Код
Запросы
0
Пакеты
0
Релизы
0
Аналитика
Безопасность
master
src/java.base/share/classes/sun/security/ec/ed/Ed25519Operations.java
214 строк
8 KB
Anthony Scarpino
8308398: Move SunEC crypto provider into java.base
17 июл 2023, 20:38
17 июл 2023, 20:38
e737968
Код
Авторство
О чём код?
/* * Copyright (c) 2020, 2022, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License version 2 only, as * published by the Free Software Foundation. Oracle designates this * particular file as subject to the "Classpath" exception as provided * by Oracle in the LICENSE file that accompanied this code. * * This code is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * version 2 for more details (a copy is included in the LICENSE file that * accompanied this code). * * You should have received a copy of the GNU General Public License version * 2 along with this work; if not, write to the Free Software Foundation, * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. * * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA * or visit www.oracle.com if you need additional information or have any * questions. */ package sun.security.ec.ed; import sun.security.ec.point.*; import sun.security.util.math.*; import java.math.BigInteger; import java.util.function.Function; /* * Elliptic curve point arithmetic, decoding, and other operations for the * family of curves including edwards25519 and its related group. Though the * operations in this class are optimized for edwards25519, they are correct * for any twisted Edwards curve ax^2 + y^2 = 1 + dx^2y^2 (mod p) with the * following properties: * 1) a = -1 (mod p) * 2) a is square (mod p) * 3) d is not square (mod p) */ public class Ed25519Operations extends EdECOperations { private final SmallValue two; private final ImmutableIntegerModuloP d; private final ExtendedHomogeneousPoint.Immutable basePoint; private static final BigInteger TWO = BigInteger.valueOf(2); private static final BigInteger SEVEN = BigInteger.valueOf(7); private final BigInteger sizeMinus5; public Ed25519Operations(ImmutableIntegerModuloP d, BigInteger baseX, BigInteger baseY) { this.two = d.getField().getSmallValue(2); this.d = d; this.basePoint = of(new AffinePoint( d.getField().getElement(baseX), d.getField().getElement(baseY) )); this.sizeMinus5 = d.getField().getSize().subtract(BigInteger.valueOf(5)); } @Override public Point basePointMultiply(byte[] scalar) { return setProduct(basePoint.mutable(), scalar); } @Override protected ExtendedHomogeneousPoint.Immutable getNeutral() { IntegerFieldModuloP field = d.getField(); return new ExtendedHomogeneousPoint.Immutable(field.get0(), field.get1(), field.get0(), field.get1()); } @Override protected MutablePoint setSum(MutablePoint p1, MutablePoint p2, MutableIntegerModuloP t1, MutableIntegerModuloP t2, MutableIntegerModuloP t3) { ExtendedHomogeneousPoint.Mutable ehp1 = (ExtendedHomogeneousPoint.Mutable) p1; ExtendedHomogeneousPoint.Mutable ehp2 = (ExtendedHomogeneousPoint.Mutable) p2; return setSum(ehp1, ehp2, t1, t2, t3); } @Override protected MutablePoint setDouble(MutablePoint p, MutableIntegerModuloP t1, MutableIntegerModuloP t2) { ExtendedHomogeneousPoint.Mutable ehp = (ExtendedHomogeneousPoint.Mutable) p; return setDouble(ehp, t1, t2); } @Override public ExtendedHomogeneousPoint.Immutable of(AffinePoint p) { return new ExtendedHomogeneousPoint.Immutable(p.getX(), p.getY(), p.getX().multiply(p.getY()), p.getX().getField().get1()); } @Override public <T extends Throwable> AffinePoint decodeAffinePoint(Function<String, T> exception, int xLSB, IntegerModuloP y) throws T { IntegerFieldModuloP field = d.getField(); BigInteger p = field.getSize(); ImmutableIntegerModuloP y2 = y.square(); ImmutableIntegerModuloP u = y2.subtract(field.get1()); MutableIntegerModuloP v = d.mutable().setProduct(y2) .setSum(field.get1()); MutableIntegerModuloP x = u.mutable().setProduct(v.pow(BigInteger.valueOf(3))); ImmutableIntegerModuloP uv7pow = u.multiply(v.pow(SEVEN)).pow(sizeMinus5.shiftRight(3)); x.setProduct(uv7pow); v.setProduct(x).setProduct(x); // v now holds vx^2 BigInteger bigVX2 = v.asBigInteger(); if (bigVX2.equals(u.asBigInteger())) { // do nothing---x is correct } else if (bigVX2.equals(u.additiveInverse().asBigInteger())) { BigInteger exp = p.subtract(BigInteger.ONE).shiftRight(2); IntegerModuloP twoPow = field.getElement(TWO.modPow(exp, p)); x.setProduct(twoPow); } else { throw exception.apply("Invalid point"); } if (x.asBigInteger().equals(BigInteger.ZERO) && xLSB == 1) { throw exception.apply("Invalid point"); } if (xLSB != (x.asBigInteger().intValue() & 1)) { x.setAdditiveInverse(); } return new AffinePoint(x.fixed(), y.fixed()); } ExtendedHomogeneousPoint.Mutable setSum( ExtendedHomogeneousPoint.Mutable p1, ExtendedHomogeneousPoint.Mutable p2, MutableIntegerModuloP t1, MutableIntegerModuloP t2, MutableIntegerModuloP t3) { t1.setValue(p2.getY()).setDifference(p2.getX()); // t1 holds y2 - x2 t2.setValue(p1.getY()).setDifference(p1.getX()).setProduct(t1); // t2 holds A = (y1 - x1) * (y2 - x2) t1.setValue(p2.getY()).setSum(p2.getX()); // t1 holds y2 + x2 t3.setValue(p1.getY()).setSum(p1.getX()).setProduct(t1); // t3 holds B = (y1 + x1) * (y2 + x2) p1.getX().setValue(t3).setDifference(t2); // x holds E = B - A t3.setSum(t2); // t3 holds H = B + A, t2 is unused t2.setValue(d).setSum(d).setProduct(p1.getT()).setProduct(p2.getT()); // t2 holds C t1.setValue(p1.getZ()).setProduct(p2.getZ()).setProduct(two); // t1 holds D p1.getY().setValue(t1).setSum(t2); // y holds G p1.getZ().setValue(t1).setDifference(t2); // z holds F p1.getT().setValue(p1.getX()).setProduct(t3); p1.getX().setProduct(p1.getZ()); p1.getZ().setProduct(p1.getY()); p1.getY().setProduct(t3); return p1; } protected ExtendedHomogeneousPoint.Mutable setDouble( ExtendedHomogeneousPoint.Mutable p, MutableIntegerModuloP t1, MutableIntegerModuloP t2) { t1.setValue(p.getX()).setSum(p.getY()).setSquare(); // t1 holds (x + y)^2 p.getX().setSquare(); // x = A = x^2 p.getY().setSquare(); // y = B = y^2 t2.setValue(p.getX()).setSum(p.getY()); // t2 holds H p.getZ().setSquare().setProduct(two); // z holds C p.getT().setValue(t2).setDifference(t1); // t holds E t1.setValue(p.getX()).setDifference(p.getY()); // t1 holds G p.getZ().setSum(t1); // z holds F p.getX().setValue(p.getT()).setProduct(p.getZ()); p.getY().setValue(t1).setProduct(t2); p.getT().setProduct(t2); p.getZ().setProduct(t1); return p; } }