GLV method for BLS12

dev
MITSUNARI Shigeo 7 years ago
parent d5de0e304a
commit 6262d99736
  1. 40
      include/mcl/bn.hpp
  2. 28
      test/glv_test.cpp

@ -502,23 +502,44 @@ struct GLV1 {
mpz_class v0, v1;
mpz_class B[2][2];
mpz_class r;
void init(const mpz_class& r, const mpz_class& z)
void init(const mpz_class& r, const mpz_class& z, bool isBLS12 = false)
{
if (!Fp::squareRoot(rw, -3)) throw cybozu::Exception("GLV1:init");
rw = -(rw + 1) / 2;
this->r = r;
m = gmp::getBitSize(r);
m = (m + fp::UnitBitSize - 1) & ~(fp::UnitBitSize - 1);// a little better size
v0 = ((6 * z * z + 4 * z + 1) << m) / r;
v1 = ((-2 * z - 1) << m) / r;
B[0][0] = 6 * z * z + 2 * z;
B[0][1] = -2 * z - 1;
B[1][0] = -2 * z - 1;
B[1][1] = -6 * z * z - 4 * z - 1;
if (isBLS12) {
/*
BLS12
L = z^4
(-z^2+1) + L = 0
1 + z^2 L = 0
*/
B[0][0] = -z * z + 1;
B[0][1] = 1;
B[1][0] = 1;
B[1][1] = z * z;
v0 = ((-B[1][1]) << m) / r;
v1 = ((B[1][0]) << m) / r;
} else {
/*
BN
L = 36z^4 - 1
(6z^2+2z) - (2z+1) L = 0
(-2z-1) - (6z^2+4z+1)L = 0
*/
B[0][0] = 6 * z * z + 2 * z;
B[0][1] = -2 * z - 1;
B[1][0] = -2 * z - 1;
B[1][1] = -6 * z * z - 4 * z - 1;
v0 = ((-B[1][1]) << m) / r;
v1 = ((B[1][0]) << m) / r;
}
}
/*
lambda = 36z^4 - 1
lambda (x, y) = (rw x, y)
L = p^4
L (x, y) = (rw x, y)
*/
void mulLambda(G1& Q, const G1& P) const
{
@ -527,7 +548,6 @@ struct GLV1 {
Q.z = P.z;
}
/*
lambda = 36 z^4 - 1
x = a + b * lambda mod r
*/
void split(mpz_class& a, mpz_class& b, const mpz_class& x) const

@ -80,9 +80,9 @@ template<class GLV1, class GLV2>
void compareLength(const GLV1& rhs, const GLV2& lhs)
{
cybozu::XorShift rg;
int Rc = 0;
int Lc = 0;
int lt = 0;
int eq = 0;
int gt = 0;
mpz_class R0, R1, L0, L1, x;
Fr r;
for (int i = 1; i < 1000; i++) {
@ -101,13 +101,13 @@ void compareLength(const GLV1& rhs, const GLV2& lhs)
eq++;
}
if (Rn > Ln) {
Rc++;
gt++;
}
if (Rn < Ln) {
Lc++;
lt++;
}
}
printf("eq=%d small is better rhs=%d, lhs=%d\n", eq, Rc, Lc);
printf("#of{<} = %d, #of{=} = %d #of{>} = %d\n", lt, eq, gt);
}
void testGLV1()
@ -117,11 +117,15 @@ void testGLV1()
cybozu::XorShift rg;
oldGLV oldGlv;
oldGlv.init(BN::param.r, BN::param.z);
if (!BN::param.isBLS12) {
oldGlv.init(BN::param.r, BN::param.z);
}
mcl::bn::local::GLV1 glv;
glv.init(BN::param.r, BN::param.z);
compareLength(glv, oldGlv);
glv.init(BN::param.r, BN::param.z, BN::param.isBLS12);
if (!BN::param.isBLS12) {
compareLength(glv, oldGlv);
}
for (int i = 1; i < 100; i++) {
mapToG1(P0, i);
@ -133,8 +137,10 @@ void testGLV1()
CYBOZU_TEST_EQUAL(P1, P2);
glv.mul(P2, P0, ss, true);
CYBOZU_TEST_EQUAL(P1, P2);
oldGlv.mul(P2, P0, ss);
CYBOZU_TEST_EQUAL(P1, P2);
if (!BN::param.isBLS12) {
oldGlv.mul(P2, P0, ss);
CYBOZU_TEST_EQUAL(P1, P2);
}
}
for (int i = -100; i < 100; i++) {
mpz_class ss = i;
@ -191,11 +197,13 @@ CYBOZU_TEST_AUTO(glv)
mcl::BN254,
mcl::BN381_1,
mcl::BN381_2,
mcl::BLS12_381,
};
for (size_t i = 0; i < CYBOZU_NUM_OF_ARRAY(tbl); i++) {
const mcl::CurveParam& cp = tbl[i];
initPairing(cp);
testGLV1();
if (BN::param.isBLS12) break;
testGLV2();
}
}

Loading…
Cancel
Save