github.com/consensys/gnark-crypto@v0.14.0/ecc/bls12-378/internal/fptower/e12_pairing.go (about) 1 package fptower 2 3 func (z *E12) nSquare(n int) { 4 for i := 0; i < n; i++ { 5 z.CyclotomicSquare(z) 6 } 7 } 8 9 func (z *E12) nSquareCompressed(n int) { 10 for i := 0; i < n; i++ { 11 z.CyclotomicSquareCompressed(z) 12 } 13 } 14 15 // Expt set z to x^t in E12 and return z 16 func (z *E12) Expt(x *E12) *E12 { 17 18 // Expt computation is derived from the addition chain: 19 // 20 // _1000 = 1 << 3 21 // _1001 = 1 + _1000 22 // _1001000 = _1001 << 3 23 // _1010001 = _1001 + _1001000 24 // _10011001 = _1001000 + _1010001 25 // i67 = ((_10011001 << 5 + _1001) << 10 + _1010001) << 41 26 // return 1 + i67 27 // 28 // Operations: 62 squares 6 multiplies 29 // 30 // Generated by github.com/mmcloughlin/addchain v0.4.0. 31 32 // Allocate Temporaries. 33 var result, t0, t1 E12 34 35 // Step 3: result = x^0x8 36 result.CyclotomicSquare(x) 37 result.nSquare(2) 38 39 // Step 4: t0 = x^0x9 40 t0.Mul(x, &result) 41 42 // Step 7: t1 = x^0x48 43 t1.CyclotomicSquare(&t0) 44 t1.nSquare(2) 45 46 // Step 8: result = x^0x51 47 result.Mul(&t0, &t1) 48 49 // Step 9: t1 = x^0x99 50 t1.Mul(&t1, &result) 51 52 // Step 14: t1 = x^0x1320 53 t1.nSquare(5) 54 55 // Step 15: t0 = x^0x1329 56 t0.Mul(&t0, &t1) 57 58 // Step 25: t0 = x^0x4ca400 59 t0.nSquare(10) 60 61 // Step 26: result = x^0x4ca451 62 result.Mul(&result, &t0) 63 64 // Step 67: result = x^0x9948a20000000000 65 result.nSquareCompressed(41) 66 result.DecompressKarabina(&result) 67 68 // Step 68: result = x^0x9948a20000000001 69 z.Mul(x, &result) 70 71 return z 72 } 73 74 // MulBy014 multiplication by sparse element (c0, c1, 0, 0, c4) 75 func (z *E12) MulBy014(c0, c1, c4 *E2) *E12 { 76 77 var a, b E6 78 var d E2 79 80 a.Set(&z.C0) 81 a.MulBy01(c0, c1) 82 83 b.Set(&z.C1) 84 b.MulBy1(c4) 85 d.Add(c1, c4) 86 87 z.C1.Add(&z.C1, &z.C0) 88 z.C1.MulBy01(c0, &d) 89 z.C1.Sub(&z.C1, &a) 90 z.C1.Sub(&z.C1, &b) 91 z.C0.MulByNonResidue(&b) 92 z.C0.Add(&z.C0, &a) 93 94 return z 95 } 96 97 // MulBy01 multiplication by sparse element (c0, c1, 0, 0, 1) 98 func (z *E12) MulBy01(c0, c1 *E2) *E12 { 99 100 var a, b E6 101 var d E2 102 103 a.Set(&z.C0) 104 a.MulBy01(c0, c1) 105 106 b.MulByNonResidue(&z.C1) 107 d.SetOne().Add(c1, &d) 108 109 z.C1.Add(&z.C1, &z.C0) 110 z.C1.MulBy01(c0, &d) 111 z.C1.Sub(&z.C1, &a) 112 z.C1.Sub(&z.C1, &b) 113 z.C0.MulByNonResidue(&b) 114 z.C0.Add(&z.C0, &a) 115 116 return z 117 } 118 119 // Mul014By014 multiplication of sparse element (c0,c1,0,0,c4,0) by sparse element (d0,d1,0,0,d4,0) 120 func Mul014By014(d0, d1, d4, c0, c1, c4 *E2) [5]E2 { 121 var z00, tmp, x0, x1, x4, x04, x01, x14 E2 122 x0.Mul(c0, d0) 123 x1.Mul(c1, d1) 124 x4.Mul(c4, d4) 125 tmp.Add(c0, c4) 126 x04.Add(d0, d4). 127 Mul(&x04, &tmp). 128 Sub(&x04, &x0). 129 Sub(&x04, &x4) 130 tmp.Add(c0, c1) 131 x01.Add(d0, d1). 132 Mul(&x01, &tmp). 133 Sub(&x01, &x0). 134 Sub(&x01, &x1) 135 tmp.Add(c1, c4) 136 x14.Add(d1, d4). 137 Mul(&x14, &tmp). 138 Sub(&x14, &x1). 139 Sub(&x14, &x4) 140 141 z00.MulByNonResidue(&x4). 142 Add(&z00, &x0) 143 144 return [5]E2{z00, x01, x1, x04, x14} 145 } 146 147 // Mul01By01 multiplication of sparse element (c0,c1,0,0,1,0) by sparse element (d0,d1,0,0,1,0) 148 func Mul01By01(d0, d1, c0, c1 *E2) [5]E2 { 149 var z00, tmp, x0, x1, x4, x04, x01, x14 E2 150 x0.Mul(c0, d0) 151 x1.Mul(c1, d1) 152 x4.SetOne() 153 x04.Add(d0, c0) 154 tmp.Add(c0, c1) 155 x01.Add(d0, d1). 156 Mul(&x01, &tmp). 157 Sub(&x01, &x0). 158 Sub(&x01, &x1) 159 x14.Add(d1, c1) 160 161 z00.MulByNonResidue(&x4). 162 Add(&z00, &x0) 163 164 return [5]E2{z00, x01, x1, x04, x14} 165 } 166 167 // MulBy01245 multiplies z by an E12 sparse element of the form (x0, x1, x2, 0, x4, x5) 168 func (z *E12) MulBy01245(x *[5]E2) *E12 { 169 var c1, a, b, c, z0, z1 E6 170 c0 := &E6{B0: x[0], B1: x[1], B2: x[2]} 171 c1.B1 = x[3] 172 c1.B2 = x[4] 173 a.Add(&z.C0, &z.C1) 174 b.Add(c0, &c1) 175 a.Mul(&a, &b) 176 b.Mul(&z.C0, c0) 177 c.Set(&z.C1).MulBy12(&x[3], &x[4]) 178 z1.Sub(&a, &b) 179 z1.Sub(&z1, &c) 180 z0.MulByNonResidue(&c) 181 z0.Add(&z0, &b) 182 183 z.C0 = z0 184 z.C1 = z1 185 186 return z 187 }