/* IEEE1363 ECDSA Signature Verification. Signature C and D on F is verified using public key W */ public static int ECPVP_DSA(sbyte[] W, sbyte[] F, sbyte[] C, sbyte[] D) { BIG r, gx, gy, f, c, d, h2; int res = 0; ECP G, WP, P; HASH H = new HASH(); H.process_array(F); sbyte[] B = H.hash(); gx = new BIG(ROM.CURVE_Gx); gy = new BIG(ROM.CURVE_Gy); G = new ECP(gx, gy); r = new BIG(ROM.CURVE_Order); c = BIG.fromBytes(C); d = BIG.fromBytes(D); f = BIG.fromBytes(B); if (c.iszilch() || BIG.comp(c, r) >= 0 || d.iszilch() || BIG.comp(d, r) >= 0) { res = INVALID; } if (res == 0) { d.invmodp(r); f.copy(BIG.modmul(f, d, r)); h2 = BIG.modmul(c, d, r); WP = ECP.fromBytes(W); if (WP.is_infinity()) { res = ERROR; } else { P = new ECP(); P.copy(WP); P = P.mul2(h2, G, f); if (P.is_infinity()) { res = INVALID; } else { d = P.X; d.mod(r); if (BIG.comp(d, c) != 0) { res = INVALID; } } } } return(res); }
/* Multiply P by e in group G1 */ public static ECP G1mul(ECP P, BIG e) { ECP R; if (ROM.USE_GLV) { P.affine(); R = new ECP(); R.copy(P); int i, np, nn; ECP Q = new ECP(); Q.copy(P); BIG q = new BIG(ROM.CURVE_Order); FP cru = new FP(new BIG(ROM.CURVE_Cru)); BIG t = new BIG(0); BIG[] u = glv(e); Q.getx().mul(cru); np = u[0].nbits(); t.copy(BIG.modneg(u[0], q)); nn = t.nbits(); if (nn < np) { u[0].copy(t); R.neg(); } np = u[1].nbits(); t.copy(BIG.modneg(u[1], q)); nn = t.nbits(); if (nn < np) { u[1].copy(t); Q.neg(); } R = R.mul2(u[0], Q, u[1]); } else { R = P.mul(e); } return(R); }