github.com/consensys/gnark-crypto@v0.14.0/ecc/bls12-378/fp/element.go (about)

     1  // Copyright 2020 ConsenSys Software Inc.
     2  //
     3  // Licensed under the Apache License, Version 2.0 (the "License");
     4  // you may not use this file except in compliance with the License.
     5  // You may obtain a copy of the License at
     6  //
     7  //     http://www.apache.org/licenses/LICENSE-2.0
     8  //
     9  // Unless required by applicable law or agreed to in writing, software
    10  // distributed under the License is distributed on an "AS IS" BASIS,
    11  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    12  // See the License for the specific language governing permissions and
    13  // limitations under the License.
    14  
    15  // Code generated by consensys/gnark-crypto DO NOT EDIT
    16  
    17  package fp
    18  
    19  import (
    20  	"crypto/rand"
    21  	"encoding/binary"
    22  	"errors"
    23  	"io"
    24  	"math/big"
    25  	"math/bits"
    26  	"reflect"
    27  	"strconv"
    28  	"strings"
    29  
    30  	"github.com/bits-and-blooms/bitset"
    31  	"github.com/consensys/gnark-crypto/field/hash"
    32  	"github.com/consensys/gnark-crypto/field/pool"
    33  )
    34  
    35  // Element represents a field element stored on 6 words (uint64)
    36  //
    37  // Element are assumed to be in Montgomery form in all methods.
    38  //
    39  // Modulus q =
    40  //
    41  //	q[base10] = 605248206075306171733248481581800960739847691770924913753520744034740935903401304776283802348837311170974282940417
    42  //	q[base16] = 0x3eeb0416684d19053cb5d240ed107a284059eb647102326980dc360d0a49d7fce97f76a822c00009948a20000000001
    43  //
    44  // # Warning
    45  //
    46  // This code has not been audited and is provided as-is. In particular, there is no security guarantees such as constant time implementation or side-channel attack resistance.
    47  type Element [6]uint64
    48  
    49  const (
    50  	Limbs = 6   // number of 64 bits words needed to represent a Element
    51  	Bits  = 378 // number of bits needed to represent a Element
    52  	Bytes = 48  // number of bytes needed to represent a Element
    53  )
    54  
    55  // Field modulus q
    56  const (
    57  	q0 uint64 = 11045256207009841153
    58  	q1 uint64 = 14886639130118979584
    59  	q2 uint64 = 10956628289047010687
    60  	q3 uint64 = 9513184293603517222
    61  	q4 uint64 = 6038022134869067682
    62  	q5 uint64 = 283357621510263184
    63  )
    64  
    65  var qElement = Element{
    66  	q0,
    67  	q1,
    68  	q2,
    69  	q3,
    70  	q4,
    71  	q5,
    72  }
    73  
    74  var _modulus big.Int // q stored as big.Int
    75  
    76  // Modulus returns q as a big.Int
    77  //
    78  //	q[base10] = 605248206075306171733248481581800960739847691770924913753520744034740935903401304776283802348837311170974282940417
    79  //	q[base16] = 0x3eeb0416684d19053cb5d240ed107a284059eb647102326980dc360d0a49d7fce97f76a822c00009948a20000000001
    80  func Modulus() *big.Int {
    81  	return new(big.Int).Set(&_modulus)
    82  }
    83  
    84  // q + r'.r = 1, i.e., qInvNeg = - q⁻¹ mod r
    85  // used for Montgomery reduction
    86  const qInvNeg uint64 = 11045256207009841151
    87  
    88  func init() {
    89  	_modulus.SetString("3eeb0416684d19053cb5d240ed107a284059eb647102326980dc360d0a49d7fce97f76a822c00009948a20000000001", 16)
    90  }
    91  
    92  // NewElement returns a new Element from a uint64 value
    93  //
    94  // it is equivalent to
    95  //
    96  //	var v Element
    97  //	v.SetUint64(...)
    98  func NewElement(v uint64) Element {
    99  	z := Element{v}
   100  	z.Mul(&z, &rSquare)
   101  	return z
   102  }
   103  
   104  // SetUint64 sets z to v and returns z
   105  func (z *Element) SetUint64(v uint64) *Element {
   106  	//  sets z LSB to v (non-Montgomery form) and convert z to Montgomery form
   107  	*z = Element{v}
   108  	return z.Mul(z, &rSquare) // z.toMont()
   109  }
   110  
   111  // SetInt64 sets z to v and returns z
   112  func (z *Element) SetInt64(v int64) *Element {
   113  
   114  	// absolute value of v
   115  	m := v >> 63
   116  	z.SetUint64(uint64((v ^ m) - m))
   117  
   118  	if m != 0 {
   119  		// v is negative
   120  		z.Neg(z)
   121  	}
   122  
   123  	return z
   124  }
   125  
   126  // Set z = x and returns z
   127  func (z *Element) Set(x *Element) *Element {
   128  	z[0] = x[0]
   129  	z[1] = x[1]
   130  	z[2] = x[2]
   131  	z[3] = x[3]
   132  	z[4] = x[4]
   133  	z[5] = x[5]
   134  	return z
   135  }
   136  
   137  // SetInterface converts provided interface into Element
   138  // returns an error if provided type is not supported
   139  // supported types:
   140  //
   141  //	Element
   142  //	*Element
   143  //	uint64
   144  //	int
   145  //	string (see SetString for valid formats)
   146  //	*big.Int
   147  //	big.Int
   148  //	[]byte
   149  func (z *Element) SetInterface(i1 interface{}) (*Element, error) {
   150  	if i1 == nil {
   151  		return nil, errors.New("can't set fp.Element with <nil>")
   152  	}
   153  
   154  	switch c1 := i1.(type) {
   155  	case Element:
   156  		return z.Set(&c1), nil
   157  	case *Element:
   158  		if c1 == nil {
   159  			return nil, errors.New("can't set fp.Element with <nil>")
   160  		}
   161  		return z.Set(c1), nil
   162  	case uint8:
   163  		return z.SetUint64(uint64(c1)), nil
   164  	case uint16:
   165  		return z.SetUint64(uint64(c1)), nil
   166  	case uint32:
   167  		return z.SetUint64(uint64(c1)), nil
   168  	case uint:
   169  		return z.SetUint64(uint64(c1)), nil
   170  	case uint64:
   171  		return z.SetUint64(c1), nil
   172  	case int8:
   173  		return z.SetInt64(int64(c1)), nil
   174  	case int16:
   175  		return z.SetInt64(int64(c1)), nil
   176  	case int32:
   177  		return z.SetInt64(int64(c1)), nil
   178  	case int64:
   179  		return z.SetInt64(c1), nil
   180  	case int:
   181  		return z.SetInt64(int64(c1)), nil
   182  	case string:
   183  		return z.SetString(c1)
   184  	case *big.Int:
   185  		if c1 == nil {
   186  			return nil, errors.New("can't set fp.Element with <nil>")
   187  		}
   188  		return z.SetBigInt(c1), nil
   189  	case big.Int:
   190  		return z.SetBigInt(&c1), nil
   191  	case []byte:
   192  		return z.SetBytes(c1), nil
   193  	default:
   194  		return nil, errors.New("can't set fp.Element from type " + reflect.TypeOf(i1).String())
   195  	}
   196  }
   197  
   198  // SetZero z = 0
   199  func (z *Element) SetZero() *Element {
   200  	z[0] = 0
   201  	z[1] = 0
   202  	z[2] = 0
   203  	z[3] = 0
   204  	z[4] = 0
   205  	z[5] = 0
   206  	return z
   207  }
   208  
   209  // SetOne z = 1 (in Montgomery form)
   210  func (z *Element) SetOne() *Element {
   211  	z[0] = 1481365419032838079
   212  	z[1] = 10045892448872562649
   213  	z[2] = 7242180086616818316
   214  	z[3] = 8832319421896135475
   215  	z[4] = 13356930855120736188
   216  	z[5] = 28498675542444634
   217  	return z
   218  }
   219  
   220  // Div z = x*y⁻¹ (mod q)
   221  func (z *Element) Div(x, y *Element) *Element {
   222  	var yInv Element
   223  	yInv.Inverse(y)
   224  	z.Mul(x, &yInv)
   225  	return z
   226  }
   227  
   228  // Equal returns z == x; constant-time
   229  func (z *Element) Equal(x *Element) bool {
   230  	return z.NotEqual(x) == 0
   231  }
   232  
   233  // NotEqual returns 0 if and only if z == x; constant-time
   234  func (z *Element) NotEqual(x *Element) uint64 {
   235  	return (z[5] ^ x[5]) | (z[4] ^ x[4]) | (z[3] ^ x[3]) | (z[2] ^ x[2]) | (z[1] ^ x[1]) | (z[0] ^ x[0])
   236  }
   237  
   238  // IsZero returns z == 0
   239  func (z *Element) IsZero() bool {
   240  	return (z[5] | z[4] | z[3] | z[2] | z[1] | z[0]) == 0
   241  }
   242  
   243  // IsOne returns z == 1
   244  func (z *Element) IsOne() bool {
   245  	return ((z[5] ^ 28498675542444634) | (z[4] ^ 13356930855120736188) | (z[3] ^ 8832319421896135475) | (z[2] ^ 7242180086616818316) | (z[1] ^ 10045892448872562649) | (z[0] ^ 1481365419032838079)) == 0
   246  }
   247  
   248  // IsUint64 reports whether z can be represented as an uint64.
   249  func (z *Element) IsUint64() bool {
   250  	zz := *z
   251  	zz.fromMont()
   252  	return zz.FitsOnOneWord()
   253  }
   254  
   255  // Uint64 returns the uint64 representation of x. If x cannot be represented in a uint64, the result is undefined.
   256  func (z *Element) Uint64() uint64 {
   257  	return z.Bits()[0]
   258  }
   259  
   260  // FitsOnOneWord reports whether z words (except the least significant word) are 0
   261  //
   262  // It is the responsibility of the caller to convert from Montgomery to Regular form if needed.
   263  func (z *Element) FitsOnOneWord() bool {
   264  	return (z[5] | z[4] | z[3] | z[2] | z[1]) == 0
   265  }
   266  
   267  // Cmp compares (lexicographic order) z and x and returns:
   268  //
   269  //	-1 if z <  x
   270  //	 0 if z == x
   271  //	+1 if z >  x
   272  func (z *Element) Cmp(x *Element) int {
   273  	_z := z.Bits()
   274  	_x := x.Bits()
   275  	if _z[5] > _x[5] {
   276  		return 1
   277  	} else if _z[5] < _x[5] {
   278  		return -1
   279  	}
   280  	if _z[4] > _x[4] {
   281  		return 1
   282  	} else if _z[4] < _x[4] {
   283  		return -1
   284  	}
   285  	if _z[3] > _x[3] {
   286  		return 1
   287  	} else if _z[3] < _x[3] {
   288  		return -1
   289  	}
   290  	if _z[2] > _x[2] {
   291  		return 1
   292  	} else if _z[2] < _x[2] {
   293  		return -1
   294  	}
   295  	if _z[1] > _x[1] {
   296  		return 1
   297  	} else if _z[1] < _x[1] {
   298  		return -1
   299  	}
   300  	if _z[0] > _x[0] {
   301  		return 1
   302  	} else if _z[0] < _x[0] {
   303  		return -1
   304  	}
   305  	return 0
   306  }
   307  
   308  // LexicographicallyLargest returns true if this element is strictly lexicographically
   309  // larger than its negation, false otherwise
   310  func (z *Element) LexicographicallyLargest() bool {
   311  	// adapted from github.com/zkcrypto/bls12_381
   312  	// we check if the element is larger than (q-1) / 2
   313  	// if z - (((q -1) / 2) + 1) have no underflow, then z > (q-1) / 2
   314  
   315  	_z := z.Bits()
   316  
   317  	var b uint64
   318  	_, b = bits.Sub64(_z[0], 5522628103504920577, 0)
   319  	_, b = bits.Sub64(_z[1], 16666691601914265600, b)
   320  	_, b = bits.Sub64(_z[2], 5478314144523505343, b)
   321  	_, b = bits.Sub64(_z[3], 4756592146801758611, b)
   322  	_, b = bits.Sub64(_z[4], 3019011067434533841, b)
   323  	_, b = bits.Sub64(_z[5], 141678810755131592, b)
   324  
   325  	return b == 0
   326  }
   327  
   328  // SetRandom sets z to a uniform random value in [0, q).
   329  //
   330  // This might error only if reading from crypto/rand.Reader errors,
   331  // in which case, value of z is undefined.
   332  func (z *Element) SetRandom() (*Element, error) {
   333  	// this code is generated for all modulus
   334  	// and derived from go/src/crypto/rand/util.go
   335  
   336  	// l is number of limbs * 8; the number of bytes needed to reconstruct 6 uint64
   337  	const l = 48
   338  
   339  	// bitLen is the maximum bit length needed to encode a value < q.
   340  	const bitLen = 378
   341  
   342  	// k is the maximum byte length needed to encode a value < q.
   343  	const k = (bitLen + 7) / 8
   344  
   345  	// b is the number of bits in the most significant byte of q-1.
   346  	b := uint(bitLen % 8)
   347  	if b == 0 {
   348  		b = 8
   349  	}
   350  
   351  	var bytes [l]byte
   352  
   353  	for {
   354  		// note that bytes[k:l] is always 0
   355  		if _, err := io.ReadFull(rand.Reader, bytes[:k]); err != nil {
   356  			return nil, err
   357  		}
   358  
   359  		// Clear unused bits in in the most significant byte to increase probability
   360  		// that the candidate is < q.
   361  		bytes[k-1] &= uint8(int(1<<b) - 1)
   362  		z[0] = binary.LittleEndian.Uint64(bytes[0:8])
   363  		z[1] = binary.LittleEndian.Uint64(bytes[8:16])
   364  		z[2] = binary.LittleEndian.Uint64(bytes[16:24])
   365  		z[3] = binary.LittleEndian.Uint64(bytes[24:32])
   366  		z[4] = binary.LittleEndian.Uint64(bytes[32:40])
   367  		z[5] = binary.LittleEndian.Uint64(bytes[40:48])
   368  
   369  		if !z.smallerThanModulus() {
   370  			continue // ignore the candidate and re-sample
   371  		}
   372  
   373  		return z, nil
   374  	}
   375  }
   376  
   377  // smallerThanModulus returns true if z < q
   378  // This is not constant time
   379  func (z *Element) smallerThanModulus() bool {
   380  	return (z[5] < q5 || (z[5] == q5 && (z[4] < q4 || (z[4] == q4 && (z[3] < q3 || (z[3] == q3 && (z[2] < q2 || (z[2] == q2 && (z[1] < q1 || (z[1] == q1 && (z[0] < q0)))))))))))
   381  }
   382  
   383  // One returns 1
   384  func One() Element {
   385  	var one Element
   386  	one.SetOne()
   387  	return one
   388  }
   389  
   390  // Halve sets z to z / 2 (mod q)
   391  func (z *Element) Halve() {
   392  	var carry uint64
   393  
   394  	if z[0]&1 == 1 {
   395  		// z = z + q
   396  		z[0], carry = bits.Add64(z[0], q0, 0)
   397  		z[1], carry = bits.Add64(z[1], q1, carry)
   398  		z[2], carry = bits.Add64(z[2], q2, carry)
   399  		z[3], carry = bits.Add64(z[3], q3, carry)
   400  		z[4], carry = bits.Add64(z[4], q4, carry)
   401  		z[5], _ = bits.Add64(z[5], q5, carry)
   402  
   403  	}
   404  	// z = z >> 1
   405  	z[0] = z[0]>>1 | z[1]<<63
   406  	z[1] = z[1]>>1 | z[2]<<63
   407  	z[2] = z[2]>>1 | z[3]<<63
   408  	z[3] = z[3]>>1 | z[4]<<63
   409  	z[4] = z[4]>>1 | z[5]<<63
   410  	z[5] >>= 1
   411  
   412  }
   413  
   414  // fromMont converts z in place (i.e. mutates) from Montgomery to regular representation
   415  // sets and returns z = z * 1
   416  func (z *Element) fromMont() *Element {
   417  	fromMont(z)
   418  	return z
   419  }
   420  
   421  // Add z = x + y (mod q)
   422  func (z *Element) Add(x, y *Element) *Element {
   423  
   424  	var carry uint64
   425  	z[0], carry = bits.Add64(x[0], y[0], 0)
   426  	z[1], carry = bits.Add64(x[1], y[1], carry)
   427  	z[2], carry = bits.Add64(x[2], y[2], carry)
   428  	z[3], carry = bits.Add64(x[3], y[3], carry)
   429  	z[4], carry = bits.Add64(x[4], y[4], carry)
   430  	z[5], _ = bits.Add64(x[5], y[5], carry)
   431  
   432  	// if z ⩾ q → z -= q
   433  	if !z.smallerThanModulus() {
   434  		var b uint64
   435  		z[0], b = bits.Sub64(z[0], q0, 0)
   436  		z[1], b = bits.Sub64(z[1], q1, b)
   437  		z[2], b = bits.Sub64(z[2], q2, b)
   438  		z[3], b = bits.Sub64(z[3], q3, b)
   439  		z[4], b = bits.Sub64(z[4], q4, b)
   440  		z[5], _ = bits.Sub64(z[5], q5, b)
   441  	}
   442  	return z
   443  }
   444  
   445  // Double z = x + x (mod q), aka Lsh 1
   446  func (z *Element) Double(x *Element) *Element {
   447  
   448  	var carry uint64
   449  	z[0], carry = bits.Add64(x[0], x[0], 0)
   450  	z[1], carry = bits.Add64(x[1], x[1], carry)
   451  	z[2], carry = bits.Add64(x[2], x[2], carry)
   452  	z[3], carry = bits.Add64(x[3], x[3], carry)
   453  	z[4], carry = bits.Add64(x[4], x[4], carry)
   454  	z[5], _ = bits.Add64(x[5], x[5], carry)
   455  
   456  	// if z ⩾ q → z -= q
   457  	if !z.smallerThanModulus() {
   458  		var b uint64
   459  		z[0], b = bits.Sub64(z[0], q0, 0)
   460  		z[1], b = bits.Sub64(z[1], q1, b)
   461  		z[2], b = bits.Sub64(z[2], q2, b)
   462  		z[3], b = bits.Sub64(z[3], q3, b)
   463  		z[4], b = bits.Sub64(z[4], q4, b)
   464  		z[5], _ = bits.Sub64(z[5], q5, b)
   465  	}
   466  	return z
   467  }
   468  
   469  // Sub z = x - y (mod q)
   470  func (z *Element) Sub(x, y *Element) *Element {
   471  	var b uint64
   472  	z[0], b = bits.Sub64(x[0], y[0], 0)
   473  	z[1], b = bits.Sub64(x[1], y[1], b)
   474  	z[2], b = bits.Sub64(x[2], y[2], b)
   475  	z[3], b = bits.Sub64(x[3], y[3], b)
   476  	z[4], b = bits.Sub64(x[4], y[4], b)
   477  	z[5], b = bits.Sub64(x[5], y[5], b)
   478  	if b != 0 {
   479  		var c uint64
   480  		z[0], c = bits.Add64(z[0], q0, 0)
   481  		z[1], c = bits.Add64(z[1], q1, c)
   482  		z[2], c = bits.Add64(z[2], q2, c)
   483  		z[3], c = bits.Add64(z[3], q3, c)
   484  		z[4], c = bits.Add64(z[4], q4, c)
   485  		z[5], _ = bits.Add64(z[5], q5, c)
   486  	}
   487  	return z
   488  }
   489  
   490  // Neg z = q - x
   491  func (z *Element) Neg(x *Element) *Element {
   492  	if x.IsZero() {
   493  		z.SetZero()
   494  		return z
   495  	}
   496  	var borrow uint64
   497  	z[0], borrow = bits.Sub64(q0, x[0], 0)
   498  	z[1], borrow = bits.Sub64(q1, x[1], borrow)
   499  	z[2], borrow = bits.Sub64(q2, x[2], borrow)
   500  	z[3], borrow = bits.Sub64(q3, x[3], borrow)
   501  	z[4], borrow = bits.Sub64(q4, x[4], borrow)
   502  	z[5], _ = bits.Sub64(q5, x[5], borrow)
   503  	return z
   504  }
   505  
   506  // Select is a constant-time conditional move.
   507  // If c=0, z = x0. Else z = x1
   508  func (z *Element) Select(c int, x0 *Element, x1 *Element) *Element {
   509  	cC := uint64((int64(c) | -int64(c)) >> 63) // "canonicized" into: 0 if c=0, -1 otherwise
   510  	z[0] = x0[0] ^ cC&(x0[0]^x1[0])
   511  	z[1] = x0[1] ^ cC&(x0[1]^x1[1])
   512  	z[2] = x0[2] ^ cC&(x0[2]^x1[2])
   513  	z[3] = x0[3] ^ cC&(x0[3]^x1[3])
   514  	z[4] = x0[4] ^ cC&(x0[4]^x1[4])
   515  	z[5] = x0[5] ^ cC&(x0[5]^x1[5])
   516  	return z
   517  }
   518  
   519  // _mulGeneric is unoptimized textbook CIOS
   520  // it is a fallback solution on x86 when ADX instruction set is not available
   521  // and is used for testing purposes.
   522  func _mulGeneric(z, x, y *Element) {
   523  
   524  	// Implements CIOS multiplication -- section 2.3.2 of Tolga Acar's thesis
   525  	// https://www.microsoft.com/en-us/research/wp-content/uploads/1998/06/97Acar.pdf
   526  	//
   527  	// The algorithm:
   528  	//
   529  	// for i=0 to N-1
   530  	// 		C := 0
   531  	// 		for j=0 to N-1
   532  	// 			(C,t[j]) := t[j] + x[j]*y[i] + C
   533  	// 		(t[N+1],t[N]) := t[N] + C
   534  	//
   535  	// 		C := 0
   536  	// 		m := t[0]*q'[0] mod D
   537  	// 		(C,_) := t[0] + m*q[0]
   538  	// 		for j=1 to N-1
   539  	// 			(C,t[j-1]) := t[j] + m*q[j] + C
   540  	//
   541  	// 		(C,t[N-1]) := t[N] + C
   542  	// 		t[N] := t[N+1] + C
   543  	//
   544  	// → N is the number of machine words needed to store the modulus q
   545  	// → D is the word size. For example, on a 64-bit architecture D is 2	64
   546  	// → x[i], y[i], q[i] is the ith word of the numbers x,y,q
   547  	// → q'[0] is the lowest word of the number -q⁻¹ mod r. This quantity is pre-computed, as it does not depend on the inputs.
   548  	// → t is a temporary array of size N+2
   549  	// → C, S are machine words. A pair (C,S) refers to (hi-bits, lo-bits) of a two-word number
   550  
   551  	var t [7]uint64
   552  	var D uint64
   553  	var m, C uint64
   554  	// -----------------------------------
   555  	// First loop
   556  
   557  	C, t[0] = bits.Mul64(y[0], x[0])
   558  	C, t[1] = madd1(y[0], x[1], C)
   559  	C, t[2] = madd1(y[0], x[2], C)
   560  	C, t[3] = madd1(y[0], x[3], C)
   561  	C, t[4] = madd1(y[0], x[4], C)
   562  	C, t[5] = madd1(y[0], x[5], C)
   563  
   564  	t[6], D = bits.Add64(t[6], C, 0)
   565  
   566  	// m = t[0]n'[0] mod W
   567  	m = t[0] * qInvNeg
   568  
   569  	// -----------------------------------
   570  	// Second loop
   571  	C = madd0(m, q0, t[0])
   572  	C, t[0] = madd2(m, q1, t[1], C)
   573  	C, t[1] = madd2(m, q2, t[2], C)
   574  	C, t[2] = madd2(m, q3, t[3], C)
   575  	C, t[3] = madd2(m, q4, t[4], C)
   576  	C, t[4] = madd2(m, q5, t[5], C)
   577  
   578  	t[5], C = bits.Add64(t[6], C, 0)
   579  	t[6], _ = bits.Add64(0, D, C)
   580  	// -----------------------------------
   581  	// First loop
   582  
   583  	C, t[0] = madd1(y[1], x[0], t[0])
   584  	C, t[1] = madd2(y[1], x[1], t[1], C)
   585  	C, t[2] = madd2(y[1], x[2], t[2], C)
   586  	C, t[3] = madd2(y[1], x[3], t[3], C)
   587  	C, t[4] = madd2(y[1], x[4], t[4], C)
   588  	C, t[5] = madd2(y[1], x[5], t[5], C)
   589  
   590  	t[6], D = bits.Add64(t[6], C, 0)
   591  
   592  	// m = t[0]n'[0] mod W
   593  	m = t[0] * qInvNeg
   594  
   595  	// -----------------------------------
   596  	// Second loop
   597  	C = madd0(m, q0, t[0])
   598  	C, t[0] = madd2(m, q1, t[1], C)
   599  	C, t[1] = madd2(m, q2, t[2], C)
   600  	C, t[2] = madd2(m, q3, t[3], C)
   601  	C, t[3] = madd2(m, q4, t[4], C)
   602  	C, t[4] = madd2(m, q5, t[5], C)
   603  
   604  	t[5], C = bits.Add64(t[6], C, 0)
   605  	t[6], _ = bits.Add64(0, D, C)
   606  	// -----------------------------------
   607  	// First loop
   608  
   609  	C, t[0] = madd1(y[2], x[0], t[0])
   610  	C, t[1] = madd2(y[2], x[1], t[1], C)
   611  	C, t[2] = madd2(y[2], x[2], t[2], C)
   612  	C, t[3] = madd2(y[2], x[3], t[3], C)
   613  	C, t[4] = madd2(y[2], x[4], t[4], C)
   614  	C, t[5] = madd2(y[2], x[5], t[5], C)
   615  
   616  	t[6], D = bits.Add64(t[6], C, 0)
   617  
   618  	// m = t[0]n'[0] mod W
   619  	m = t[0] * qInvNeg
   620  
   621  	// -----------------------------------
   622  	// Second loop
   623  	C = madd0(m, q0, t[0])
   624  	C, t[0] = madd2(m, q1, t[1], C)
   625  	C, t[1] = madd2(m, q2, t[2], C)
   626  	C, t[2] = madd2(m, q3, t[3], C)
   627  	C, t[3] = madd2(m, q4, t[4], C)
   628  	C, t[4] = madd2(m, q5, t[5], C)
   629  
   630  	t[5], C = bits.Add64(t[6], C, 0)
   631  	t[6], _ = bits.Add64(0, D, C)
   632  	// -----------------------------------
   633  	// First loop
   634  
   635  	C, t[0] = madd1(y[3], x[0], t[0])
   636  	C, t[1] = madd2(y[3], x[1], t[1], C)
   637  	C, t[2] = madd2(y[3], x[2], t[2], C)
   638  	C, t[3] = madd2(y[3], x[3], t[3], C)
   639  	C, t[4] = madd2(y[3], x[4], t[4], C)
   640  	C, t[5] = madd2(y[3], x[5], t[5], C)
   641  
   642  	t[6], D = bits.Add64(t[6], C, 0)
   643  
   644  	// m = t[0]n'[0] mod W
   645  	m = t[0] * qInvNeg
   646  
   647  	// -----------------------------------
   648  	// Second loop
   649  	C = madd0(m, q0, t[0])
   650  	C, t[0] = madd2(m, q1, t[1], C)
   651  	C, t[1] = madd2(m, q2, t[2], C)
   652  	C, t[2] = madd2(m, q3, t[3], C)
   653  	C, t[3] = madd2(m, q4, t[4], C)
   654  	C, t[4] = madd2(m, q5, t[5], C)
   655  
   656  	t[5], C = bits.Add64(t[6], C, 0)
   657  	t[6], _ = bits.Add64(0, D, C)
   658  	// -----------------------------------
   659  	// First loop
   660  
   661  	C, t[0] = madd1(y[4], x[0], t[0])
   662  	C, t[1] = madd2(y[4], x[1], t[1], C)
   663  	C, t[2] = madd2(y[4], x[2], t[2], C)
   664  	C, t[3] = madd2(y[4], x[3], t[3], C)
   665  	C, t[4] = madd2(y[4], x[4], t[4], C)
   666  	C, t[5] = madd2(y[4], x[5], t[5], C)
   667  
   668  	t[6], D = bits.Add64(t[6], C, 0)
   669  
   670  	// m = t[0]n'[0] mod W
   671  	m = t[0] * qInvNeg
   672  
   673  	// -----------------------------------
   674  	// Second loop
   675  	C = madd0(m, q0, t[0])
   676  	C, t[0] = madd2(m, q1, t[1], C)
   677  	C, t[1] = madd2(m, q2, t[2], C)
   678  	C, t[2] = madd2(m, q3, t[3], C)
   679  	C, t[3] = madd2(m, q4, t[4], C)
   680  	C, t[4] = madd2(m, q5, t[5], C)
   681  
   682  	t[5], C = bits.Add64(t[6], C, 0)
   683  	t[6], _ = bits.Add64(0, D, C)
   684  	// -----------------------------------
   685  	// First loop
   686  
   687  	C, t[0] = madd1(y[5], x[0], t[0])
   688  	C, t[1] = madd2(y[5], x[1], t[1], C)
   689  	C, t[2] = madd2(y[5], x[2], t[2], C)
   690  	C, t[3] = madd2(y[5], x[3], t[3], C)
   691  	C, t[4] = madd2(y[5], x[4], t[4], C)
   692  	C, t[5] = madd2(y[5], x[5], t[5], C)
   693  
   694  	t[6], D = bits.Add64(t[6], C, 0)
   695  
   696  	// m = t[0]n'[0] mod W
   697  	m = t[0] * qInvNeg
   698  
   699  	// -----------------------------------
   700  	// Second loop
   701  	C = madd0(m, q0, t[0])
   702  	C, t[0] = madd2(m, q1, t[1], C)
   703  	C, t[1] = madd2(m, q2, t[2], C)
   704  	C, t[2] = madd2(m, q3, t[3], C)
   705  	C, t[3] = madd2(m, q4, t[4], C)
   706  	C, t[4] = madd2(m, q5, t[5], C)
   707  
   708  	t[5], C = bits.Add64(t[6], C, 0)
   709  	t[6], _ = bits.Add64(0, D, C)
   710  
   711  	if t[6] != 0 {
   712  		// we need to reduce, we have a result on 7 words
   713  		var b uint64
   714  		z[0], b = bits.Sub64(t[0], q0, 0)
   715  		z[1], b = bits.Sub64(t[1], q1, b)
   716  		z[2], b = bits.Sub64(t[2], q2, b)
   717  		z[3], b = bits.Sub64(t[3], q3, b)
   718  		z[4], b = bits.Sub64(t[4], q4, b)
   719  		z[5], _ = bits.Sub64(t[5], q5, b)
   720  		return
   721  	}
   722  
   723  	// copy t into z
   724  	z[0] = t[0]
   725  	z[1] = t[1]
   726  	z[2] = t[2]
   727  	z[3] = t[3]
   728  	z[4] = t[4]
   729  	z[5] = t[5]
   730  
   731  	// if z ⩾ q → z -= q
   732  	if !z.smallerThanModulus() {
   733  		var b uint64
   734  		z[0], b = bits.Sub64(z[0], q0, 0)
   735  		z[1], b = bits.Sub64(z[1], q1, b)
   736  		z[2], b = bits.Sub64(z[2], q2, b)
   737  		z[3], b = bits.Sub64(z[3], q3, b)
   738  		z[4], b = bits.Sub64(z[4], q4, b)
   739  		z[5], _ = bits.Sub64(z[5], q5, b)
   740  	}
   741  }
   742  
   743  func _fromMontGeneric(z *Element) {
   744  	// the following lines implement z = z * 1
   745  	// with a modified CIOS montgomery multiplication
   746  	// see Mul for algorithm documentation
   747  	{
   748  		// m = z[0]n'[0] mod W
   749  		m := z[0] * qInvNeg
   750  		C := madd0(m, q0, z[0])
   751  		C, z[0] = madd2(m, q1, z[1], C)
   752  		C, z[1] = madd2(m, q2, z[2], C)
   753  		C, z[2] = madd2(m, q3, z[3], C)
   754  		C, z[3] = madd2(m, q4, z[4], C)
   755  		C, z[4] = madd2(m, q5, z[5], C)
   756  		z[5] = C
   757  	}
   758  	{
   759  		// m = z[0]n'[0] mod W
   760  		m := z[0] * qInvNeg
   761  		C := madd0(m, q0, z[0])
   762  		C, z[0] = madd2(m, q1, z[1], C)
   763  		C, z[1] = madd2(m, q2, z[2], C)
   764  		C, z[2] = madd2(m, q3, z[3], C)
   765  		C, z[3] = madd2(m, q4, z[4], C)
   766  		C, z[4] = madd2(m, q5, z[5], C)
   767  		z[5] = C
   768  	}
   769  	{
   770  		// m = z[0]n'[0] mod W
   771  		m := z[0] * qInvNeg
   772  		C := madd0(m, q0, z[0])
   773  		C, z[0] = madd2(m, q1, z[1], C)
   774  		C, z[1] = madd2(m, q2, z[2], C)
   775  		C, z[2] = madd2(m, q3, z[3], C)
   776  		C, z[3] = madd2(m, q4, z[4], C)
   777  		C, z[4] = madd2(m, q5, z[5], C)
   778  		z[5] = C
   779  	}
   780  	{
   781  		// m = z[0]n'[0] mod W
   782  		m := z[0] * qInvNeg
   783  		C := madd0(m, q0, z[0])
   784  		C, z[0] = madd2(m, q1, z[1], C)
   785  		C, z[1] = madd2(m, q2, z[2], C)
   786  		C, z[2] = madd2(m, q3, z[3], C)
   787  		C, z[3] = madd2(m, q4, z[4], C)
   788  		C, z[4] = madd2(m, q5, z[5], C)
   789  		z[5] = C
   790  	}
   791  	{
   792  		// m = z[0]n'[0] mod W
   793  		m := z[0] * qInvNeg
   794  		C := madd0(m, q0, z[0])
   795  		C, z[0] = madd2(m, q1, z[1], C)
   796  		C, z[1] = madd2(m, q2, z[2], C)
   797  		C, z[2] = madd2(m, q3, z[3], C)
   798  		C, z[3] = madd2(m, q4, z[4], C)
   799  		C, z[4] = madd2(m, q5, z[5], C)
   800  		z[5] = C
   801  	}
   802  	{
   803  		// m = z[0]n'[0] mod W
   804  		m := z[0] * qInvNeg
   805  		C := madd0(m, q0, z[0])
   806  		C, z[0] = madd2(m, q1, z[1], C)
   807  		C, z[1] = madd2(m, q2, z[2], C)
   808  		C, z[2] = madd2(m, q3, z[3], C)
   809  		C, z[3] = madd2(m, q4, z[4], C)
   810  		C, z[4] = madd2(m, q5, z[5], C)
   811  		z[5] = C
   812  	}
   813  
   814  	// if z ⩾ q → z -= q
   815  	if !z.smallerThanModulus() {
   816  		var b uint64
   817  		z[0], b = bits.Sub64(z[0], q0, 0)
   818  		z[1], b = bits.Sub64(z[1], q1, b)
   819  		z[2], b = bits.Sub64(z[2], q2, b)
   820  		z[3], b = bits.Sub64(z[3], q3, b)
   821  		z[4], b = bits.Sub64(z[4], q4, b)
   822  		z[5], _ = bits.Sub64(z[5], q5, b)
   823  	}
   824  }
   825  
   826  func _reduceGeneric(z *Element) {
   827  
   828  	// if z ⩾ q → z -= q
   829  	if !z.smallerThanModulus() {
   830  		var b uint64
   831  		z[0], b = bits.Sub64(z[0], q0, 0)
   832  		z[1], b = bits.Sub64(z[1], q1, b)
   833  		z[2], b = bits.Sub64(z[2], q2, b)
   834  		z[3], b = bits.Sub64(z[3], q3, b)
   835  		z[4], b = bits.Sub64(z[4], q4, b)
   836  		z[5], _ = bits.Sub64(z[5], q5, b)
   837  	}
   838  }
   839  
   840  // BatchInvert returns a new slice with every element inverted.
   841  // Uses Montgomery batch inversion trick
   842  func BatchInvert(a []Element) []Element {
   843  	res := make([]Element, len(a))
   844  	if len(a) == 0 {
   845  		return res
   846  	}
   847  
   848  	zeroes := bitset.New(uint(len(a)))
   849  	accumulator := One()
   850  
   851  	for i := 0; i < len(a); i++ {
   852  		if a[i].IsZero() {
   853  			zeroes.Set(uint(i))
   854  			continue
   855  		}
   856  		res[i] = accumulator
   857  		accumulator.Mul(&accumulator, &a[i])
   858  	}
   859  
   860  	accumulator.Inverse(&accumulator)
   861  
   862  	for i := len(a) - 1; i >= 0; i-- {
   863  		if zeroes.Test(uint(i)) {
   864  			continue
   865  		}
   866  		res[i].Mul(&res[i], &accumulator)
   867  		accumulator.Mul(&accumulator, &a[i])
   868  	}
   869  
   870  	return res
   871  }
   872  
   873  func _butterflyGeneric(a, b *Element) {
   874  	t := *a
   875  	a.Add(a, b)
   876  	b.Sub(&t, b)
   877  }
   878  
   879  // BitLen returns the minimum number of bits needed to represent z
   880  // returns 0 if z == 0
   881  func (z *Element) BitLen() int {
   882  	if z[5] != 0 {
   883  		return 320 + bits.Len64(z[5])
   884  	}
   885  	if z[4] != 0 {
   886  		return 256 + bits.Len64(z[4])
   887  	}
   888  	if z[3] != 0 {
   889  		return 192 + bits.Len64(z[3])
   890  	}
   891  	if z[2] != 0 {
   892  		return 128 + bits.Len64(z[2])
   893  	}
   894  	if z[1] != 0 {
   895  		return 64 + bits.Len64(z[1])
   896  	}
   897  	return bits.Len64(z[0])
   898  }
   899  
   900  // Hash msg to count prime field elements.
   901  // https://tools.ietf.org/html/draft-irtf-cfrg-hash-to-curve-06#section-5.2
   902  func Hash(msg, dst []byte, count int) ([]Element, error) {
   903  	// 128 bits of security
   904  	// L = ceil((ceil(log2(p)) + k) / 8), where k is the security parameter = 128
   905  	const Bytes = 1 + (Bits-1)/8
   906  	const L = 16 + Bytes
   907  
   908  	lenInBytes := count * L
   909  	pseudoRandomBytes, err := hash.ExpandMsgXmd(msg, dst, lenInBytes)
   910  	if err != nil {
   911  		return nil, err
   912  	}
   913  
   914  	// get temporary big int from the pool
   915  	vv := pool.BigInt.Get()
   916  
   917  	res := make([]Element, count)
   918  	for i := 0; i < count; i++ {
   919  		vv.SetBytes(pseudoRandomBytes[i*L : (i+1)*L])
   920  		res[i].SetBigInt(vv)
   921  	}
   922  
   923  	// release object into pool
   924  	pool.BigInt.Put(vv)
   925  
   926  	return res, nil
   927  }
   928  
   929  // Exp z = xᵏ (mod q)
   930  func (z *Element) Exp(x Element, k *big.Int) *Element {
   931  	if k.IsUint64() && k.Uint64() == 0 {
   932  		return z.SetOne()
   933  	}
   934  
   935  	e := k
   936  	if k.Sign() == -1 {
   937  		// negative k, we invert
   938  		// if k < 0: xᵏ (mod q) == (x⁻¹)ᵏ (mod q)
   939  		x.Inverse(&x)
   940  
   941  		// we negate k in a temp big.Int since
   942  		// Int.Bit(_) of k and -k is different
   943  		e = pool.BigInt.Get()
   944  		defer pool.BigInt.Put(e)
   945  		e.Neg(k)
   946  	}
   947  
   948  	z.Set(&x)
   949  
   950  	for i := e.BitLen() - 2; i >= 0; i-- {
   951  		z.Square(z)
   952  		if e.Bit(i) == 1 {
   953  			z.Mul(z, &x)
   954  		}
   955  	}
   956  
   957  	return z
   958  }
   959  
   960  // rSquare where r is the Montgommery constant
   961  // see section 2.3.2 of Tolga Acar's thesis
   962  // https://www.microsoft.com/en-us/research/wp-content/uploads/1998/06/97Acar.pdf
   963  var rSquare = Element{
   964  	13541478318970833666,
   965  	5510290684934426267,
   966  	8467587974331926354,
   967  	13931463632695577534,
   968  	3531303697457869800,
   969  	51529254522778566,
   970  }
   971  
   972  // toMont converts z to Montgomery form
   973  // sets and returns z = z * r²
   974  func (z *Element) toMont() *Element {
   975  	return z.Mul(z, &rSquare)
   976  }
   977  
   978  // String returns the decimal representation of z as generated by
   979  // z.Text(10).
   980  func (z *Element) String() string {
   981  	return z.Text(10)
   982  }
   983  
   984  // toBigInt returns z as a big.Int in Montgomery form
   985  func (z *Element) toBigInt(res *big.Int) *big.Int {
   986  	var b [Bytes]byte
   987  	binary.BigEndian.PutUint64(b[40:48], z[0])
   988  	binary.BigEndian.PutUint64(b[32:40], z[1])
   989  	binary.BigEndian.PutUint64(b[24:32], z[2])
   990  	binary.BigEndian.PutUint64(b[16:24], z[3])
   991  	binary.BigEndian.PutUint64(b[8:16], z[4])
   992  	binary.BigEndian.PutUint64(b[0:8], z[5])
   993  
   994  	return res.SetBytes(b[:])
   995  }
   996  
   997  // Text returns the string representation of z in the given base.
   998  // Base must be between 2 and 36, inclusive. The result uses the
   999  // lower-case letters 'a' to 'z' for digit values 10 to 35.
  1000  // No prefix (such as "0x") is added to the string. If z is a nil
  1001  // pointer it returns "<nil>".
  1002  // If base == 10 and -z fits in a uint16 prefix "-" is added to the string.
  1003  func (z *Element) Text(base int) string {
  1004  	if base < 2 || base > 36 {
  1005  		panic("invalid base")
  1006  	}
  1007  	if z == nil {
  1008  		return "<nil>"
  1009  	}
  1010  
  1011  	const maxUint16 = 65535
  1012  	if base == 10 {
  1013  		var zzNeg Element
  1014  		zzNeg.Neg(z)
  1015  		zzNeg.fromMont()
  1016  		if zzNeg.FitsOnOneWord() && zzNeg[0] <= maxUint16 && zzNeg[0] != 0 {
  1017  			return "-" + strconv.FormatUint(zzNeg[0], base)
  1018  		}
  1019  	}
  1020  	zz := *z
  1021  	zz.fromMont()
  1022  	if zz.FitsOnOneWord() {
  1023  		return strconv.FormatUint(zz[0], base)
  1024  	}
  1025  	vv := pool.BigInt.Get()
  1026  	r := zz.toBigInt(vv).Text(base)
  1027  	pool.BigInt.Put(vv)
  1028  	return r
  1029  }
  1030  
  1031  // BigInt sets and return z as a *big.Int
  1032  func (z *Element) BigInt(res *big.Int) *big.Int {
  1033  	_z := *z
  1034  	_z.fromMont()
  1035  	return _z.toBigInt(res)
  1036  }
  1037  
  1038  // ToBigIntRegular returns z as a big.Int in regular form
  1039  //
  1040  // Deprecated: use BigInt(*big.Int) instead
  1041  func (z Element) ToBigIntRegular(res *big.Int) *big.Int {
  1042  	z.fromMont()
  1043  	return z.toBigInt(res)
  1044  }
  1045  
  1046  // Bits provides access to z by returning its value as a little-endian [6]uint64 array.
  1047  // Bits is intended to support implementation of missing low-level Element
  1048  // functionality outside this package; it should be avoided otherwise.
  1049  func (z *Element) Bits() [6]uint64 {
  1050  	_z := *z
  1051  	fromMont(&_z)
  1052  	return _z
  1053  }
  1054  
  1055  // Bytes returns the value of z as a big-endian byte array
  1056  func (z *Element) Bytes() (res [Bytes]byte) {
  1057  	BigEndian.PutElement(&res, *z)
  1058  	return
  1059  }
  1060  
  1061  // Marshal returns the value of z as a big-endian byte slice
  1062  func (z *Element) Marshal() []byte {
  1063  	b := z.Bytes()
  1064  	return b[:]
  1065  }
  1066  
  1067  // Unmarshal is an alias for SetBytes, it sets z to the value of e.
  1068  func (z *Element) Unmarshal(e []byte) {
  1069  	z.SetBytes(e)
  1070  }
  1071  
  1072  // SetBytes interprets e as the bytes of a big-endian unsigned integer,
  1073  // sets z to that value, and returns z.
  1074  func (z *Element) SetBytes(e []byte) *Element {
  1075  	if len(e) == Bytes {
  1076  		// fast path
  1077  		v, err := BigEndian.Element((*[Bytes]byte)(e))
  1078  		if err == nil {
  1079  			*z = v
  1080  			return z
  1081  		}
  1082  	}
  1083  
  1084  	// slow path.
  1085  	// get a big int from our pool
  1086  	vv := pool.BigInt.Get()
  1087  	vv.SetBytes(e)
  1088  
  1089  	// set big int
  1090  	z.SetBigInt(vv)
  1091  
  1092  	// put temporary object back in pool
  1093  	pool.BigInt.Put(vv)
  1094  
  1095  	return z
  1096  }
  1097  
  1098  // SetBytesCanonical interprets e as the bytes of a big-endian 48-byte integer.
  1099  // If e is not a 48-byte slice or encodes a value higher than q,
  1100  // SetBytesCanonical returns an error.
  1101  func (z *Element) SetBytesCanonical(e []byte) error {
  1102  	if len(e) != Bytes {
  1103  		return errors.New("invalid fp.Element encoding")
  1104  	}
  1105  	v, err := BigEndian.Element((*[Bytes]byte)(e))
  1106  	if err != nil {
  1107  		return err
  1108  	}
  1109  	*z = v
  1110  	return nil
  1111  }
  1112  
  1113  // SetBigInt sets z to v and returns z
  1114  func (z *Element) SetBigInt(v *big.Int) *Element {
  1115  	z.SetZero()
  1116  
  1117  	var zero big.Int
  1118  
  1119  	// fast path
  1120  	c := v.Cmp(&_modulus)
  1121  	if c == 0 {
  1122  		// v == 0
  1123  		return z
  1124  	} else if c != 1 && v.Cmp(&zero) != -1 {
  1125  		// 0 < v < q
  1126  		return z.setBigInt(v)
  1127  	}
  1128  
  1129  	// get temporary big int from the pool
  1130  	vv := pool.BigInt.Get()
  1131  
  1132  	// copy input + modular reduction
  1133  	vv.Mod(v, &_modulus)
  1134  
  1135  	// set big int byte value
  1136  	z.setBigInt(vv)
  1137  
  1138  	// release object into pool
  1139  	pool.BigInt.Put(vv)
  1140  	return z
  1141  }
  1142  
  1143  // setBigInt assumes 0 ⩽ v < q
  1144  func (z *Element) setBigInt(v *big.Int) *Element {
  1145  	vBits := v.Bits()
  1146  
  1147  	if bits.UintSize == 64 {
  1148  		for i := 0; i < len(vBits); i++ {
  1149  			z[i] = uint64(vBits[i])
  1150  		}
  1151  	} else {
  1152  		for i := 0; i < len(vBits); i++ {
  1153  			if i%2 == 0 {
  1154  				z[i/2] = uint64(vBits[i])
  1155  			} else {
  1156  				z[i/2] |= uint64(vBits[i]) << 32
  1157  			}
  1158  		}
  1159  	}
  1160  
  1161  	return z.toMont()
  1162  }
  1163  
  1164  // SetString creates a big.Int with number and calls SetBigInt on z
  1165  //
  1166  // The number prefix determines the actual base: A prefix of
  1167  // ”0b” or ”0B” selects base 2, ”0”, ”0o” or ”0O” selects base 8,
  1168  // and ”0x” or ”0X” selects base 16. Otherwise, the selected base is 10
  1169  // and no prefix is accepted.
  1170  //
  1171  // For base 16, lower and upper case letters are considered the same:
  1172  // The letters 'a' to 'f' and 'A' to 'F' represent digit values 10 to 15.
  1173  //
  1174  // An underscore character ”_” may appear between a base
  1175  // prefix and an adjacent digit, and between successive digits; such
  1176  // underscores do not change the value of the number.
  1177  // Incorrect placement of underscores is reported as a panic if there
  1178  // are no other errors.
  1179  //
  1180  // If the number is invalid this method leaves z unchanged and returns nil, error.
  1181  func (z *Element) SetString(number string) (*Element, error) {
  1182  	// get temporary big int from the pool
  1183  	vv := pool.BigInt.Get()
  1184  
  1185  	if _, ok := vv.SetString(number, 0); !ok {
  1186  		return nil, errors.New("Element.SetString failed -> can't parse number into a big.Int " + number)
  1187  	}
  1188  
  1189  	z.SetBigInt(vv)
  1190  
  1191  	// release object into pool
  1192  	pool.BigInt.Put(vv)
  1193  
  1194  	return z, nil
  1195  }
  1196  
  1197  // MarshalJSON returns json encoding of z (z.Text(10))
  1198  // If z == nil, returns null
  1199  func (z *Element) MarshalJSON() ([]byte, error) {
  1200  	if z == nil {
  1201  		return []byte("null"), nil
  1202  	}
  1203  	const maxSafeBound = 15 // we encode it as number if it's small
  1204  	s := z.Text(10)
  1205  	if len(s) <= maxSafeBound {
  1206  		return []byte(s), nil
  1207  	}
  1208  	var sbb strings.Builder
  1209  	sbb.WriteByte('"')
  1210  	sbb.WriteString(s)
  1211  	sbb.WriteByte('"')
  1212  	return []byte(sbb.String()), nil
  1213  }
  1214  
  1215  // UnmarshalJSON accepts numbers and strings as input
  1216  // See Element.SetString for valid prefixes (0x, 0b, ...)
  1217  func (z *Element) UnmarshalJSON(data []byte) error {
  1218  	s := string(data)
  1219  	if len(s) > Bits*3 {
  1220  		return errors.New("value too large (max = Element.Bits * 3)")
  1221  	}
  1222  
  1223  	// we accept numbers and strings, remove leading and trailing quotes if any
  1224  	if len(s) > 0 && s[0] == '"' {
  1225  		s = s[1:]
  1226  	}
  1227  	if len(s) > 0 && s[len(s)-1] == '"' {
  1228  		s = s[:len(s)-1]
  1229  	}
  1230  
  1231  	// get temporary big int from the pool
  1232  	vv := pool.BigInt.Get()
  1233  
  1234  	if _, ok := vv.SetString(s, 0); !ok {
  1235  		return errors.New("can't parse into a big.Int: " + s)
  1236  	}
  1237  
  1238  	z.SetBigInt(vv)
  1239  
  1240  	// release object into pool
  1241  	pool.BigInt.Put(vv)
  1242  	return nil
  1243  }
  1244  
  1245  // A ByteOrder specifies how to convert byte slices into a Element
  1246  type ByteOrder interface {
  1247  	Element(*[Bytes]byte) (Element, error)
  1248  	PutElement(*[Bytes]byte, Element)
  1249  	String() string
  1250  }
  1251  
  1252  // BigEndian is the big-endian implementation of ByteOrder and AppendByteOrder.
  1253  var BigEndian bigEndian
  1254  
  1255  type bigEndian struct{}
  1256  
  1257  // Element interpret b is a big-endian 48-byte slice.
  1258  // If b encodes a value higher than q, Element returns error.
  1259  func (bigEndian) Element(b *[Bytes]byte) (Element, error) {
  1260  	var z Element
  1261  	z[0] = binary.BigEndian.Uint64((*b)[40:48])
  1262  	z[1] = binary.BigEndian.Uint64((*b)[32:40])
  1263  	z[2] = binary.BigEndian.Uint64((*b)[24:32])
  1264  	z[3] = binary.BigEndian.Uint64((*b)[16:24])
  1265  	z[4] = binary.BigEndian.Uint64((*b)[8:16])
  1266  	z[5] = binary.BigEndian.Uint64((*b)[0:8])
  1267  
  1268  	if !z.smallerThanModulus() {
  1269  		return Element{}, errors.New("invalid fp.Element encoding")
  1270  	}
  1271  
  1272  	z.toMont()
  1273  	return z, nil
  1274  }
  1275  
  1276  func (bigEndian) PutElement(b *[Bytes]byte, e Element) {
  1277  	e.fromMont()
  1278  	binary.BigEndian.PutUint64((*b)[40:48], e[0])
  1279  	binary.BigEndian.PutUint64((*b)[32:40], e[1])
  1280  	binary.BigEndian.PutUint64((*b)[24:32], e[2])
  1281  	binary.BigEndian.PutUint64((*b)[16:24], e[3])
  1282  	binary.BigEndian.PutUint64((*b)[8:16], e[4])
  1283  	binary.BigEndian.PutUint64((*b)[0:8], e[5])
  1284  }
  1285  
  1286  func (bigEndian) String() string { return "BigEndian" }
  1287  
  1288  // LittleEndian is the little-endian implementation of ByteOrder and AppendByteOrder.
  1289  var LittleEndian littleEndian
  1290  
  1291  type littleEndian struct{}
  1292  
  1293  func (littleEndian) Element(b *[Bytes]byte) (Element, error) {
  1294  	var z Element
  1295  	z[0] = binary.LittleEndian.Uint64((*b)[0:8])
  1296  	z[1] = binary.LittleEndian.Uint64((*b)[8:16])
  1297  	z[2] = binary.LittleEndian.Uint64((*b)[16:24])
  1298  	z[3] = binary.LittleEndian.Uint64((*b)[24:32])
  1299  	z[4] = binary.LittleEndian.Uint64((*b)[32:40])
  1300  	z[5] = binary.LittleEndian.Uint64((*b)[40:48])
  1301  
  1302  	if !z.smallerThanModulus() {
  1303  		return Element{}, errors.New("invalid fp.Element encoding")
  1304  	}
  1305  
  1306  	z.toMont()
  1307  	return z, nil
  1308  }
  1309  
  1310  func (littleEndian) PutElement(b *[Bytes]byte, e Element) {
  1311  	e.fromMont()
  1312  	binary.LittleEndian.PutUint64((*b)[0:8], e[0])
  1313  	binary.LittleEndian.PutUint64((*b)[8:16], e[1])
  1314  	binary.LittleEndian.PutUint64((*b)[16:24], e[2])
  1315  	binary.LittleEndian.PutUint64((*b)[24:32], e[3])
  1316  	binary.LittleEndian.PutUint64((*b)[32:40], e[4])
  1317  	binary.LittleEndian.PutUint64((*b)[40:48], e[5])
  1318  }
  1319  
  1320  func (littleEndian) String() string { return "LittleEndian" }
  1321  
  1322  // Legendre returns the Legendre symbol of z (either +1, -1, or 0.)
  1323  func (z *Element) Legendre() int {
  1324  	var l Element
  1325  	// z^((q-1)/2)
  1326  	l.expByLegendreExp(*z)
  1327  
  1328  	if l.IsZero() {
  1329  		return 0
  1330  	}
  1331  
  1332  	// if l == 1
  1333  	if l.IsOne() {
  1334  		return 1
  1335  	}
  1336  	return -1
  1337  }
  1338  
  1339  // Sqrt z = √x (mod q)
  1340  // if the square root doesn't exist (x is not a square mod q)
  1341  // Sqrt leaves z unchanged and returns nil
  1342  func (z *Element) Sqrt(x *Element) *Element {
  1343  	// q ≡ 1 (mod 4)
  1344  	// see modSqrtTonelliShanks in math/big/int.go
  1345  	// using https://www.maa.org/sites/default/files/pdf/upload_library/22/Polya/07468342.di020786.02p0470a.pdf
  1346  
  1347  	var y, b, t, w Element
  1348  	// w = x^((s-1)/2))
  1349  	w.expBySqrtExp(*x)
  1350  
  1351  	// y = x^((s+1)/2)) = w * x
  1352  	y.Mul(x, &w)
  1353  
  1354  	// b = xˢ = w * w * x = y * x
  1355  	b.Mul(&w, &y)
  1356  
  1357  	// g = nonResidue ^ s
  1358  	var g = Element{
  1359  		15655215628902554004,
  1360  		15894127656167592378,
  1361  		9702012166408397168,
  1362  		12335982559306940759,
  1363  		1313802173610541430,
  1364  		81629743607937133,
  1365  	}
  1366  	r := uint64(41)
  1367  
  1368  	// compute legendre symbol
  1369  	// t = x^((q-1)/2) = r-1 squaring of xˢ
  1370  	t = b
  1371  	for i := uint64(0); i < r-1; i++ {
  1372  		t.Square(&t)
  1373  	}
  1374  	if t.IsZero() {
  1375  		return z.SetZero()
  1376  	}
  1377  	if !t.IsOne() {
  1378  		// t != 1, we don't have a square root
  1379  		return nil
  1380  	}
  1381  	for {
  1382  		var m uint64
  1383  		t = b
  1384  
  1385  		// for t != 1
  1386  		for !t.IsOne() {
  1387  			t.Square(&t)
  1388  			m++
  1389  		}
  1390  
  1391  		if m == 0 {
  1392  			return z.Set(&y)
  1393  		}
  1394  		// t = g^(2^(r-m-1)) (mod q)
  1395  		ge := int(r - m - 1)
  1396  		t = g
  1397  		for ge > 0 {
  1398  			t.Square(&t)
  1399  			ge--
  1400  		}
  1401  
  1402  		g.Square(&t)
  1403  		y.Mul(&y, &t)
  1404  		b.Mul(&b, &g)
  1405  		r = m
  1406  	}
  1407  }
  1408  
  1409  const (
  1410  	k               = 32 // word size / 2
  1411  	signBitSelector = uint64(1) << 63
  1412  	approxLowBitsN  = k - 1
  1413  	approxHighBitsN = k + 1
  1414  )
  1415  
  1416  const (
  1417  	inversionCorrectionFactorWord0 = 851295657643717122
  1418  	inversionCorrectionFactorWord1 = 10857859049187504913
  1419  	inversionCorrectionFactorWord2 = 7148604188520083019
  1420  	inversionCorrectionFactorWord3 = 1138623559447261654
  1421  	inversionCorrectionFactorWord4 = 1203095380280779597
  1422  	inversionCorrectionFactorWord5 = 148579538565968037
  1423  	invIterationsN                 = 26
  1424  )
  1425  
  1426  // Inverse z = x⁻¹ (mod q)
  1427  //
  1428  // if x == 0, sets and returns z = x
  1429  func (z *Element) Inverse(x *Element) *Element {
  1430  	// Implements "Optimized Binary GCD for Modular Inversion"
  1431  	// https://github.com/pornin/bingcd/blob/main/doc/bingcd.pdf
  1432  
  1433  	a := *x
  1434  	b := Element{
  1435  		q0,
  1436  		q1,
  1437  		q2,
  1438  		q3,
  1439  		q4,
  1440  		q5,
  1441  	} // b := q
  1442  
  1443  	u := Element{1}
  1444  
  1445  	// Update factors: we get [u; v] ← [f₀ g₀; f₁ g₁] [u; v]
  1446  	// cᵢ = fᵢ + 2³¹ - 1 + 2³² * (gᵢ + 2³¹ - 1)
  1447  	var c0, c1 int64
  1448  
  1449  	// Saved update factors to reduce the number of field multiplications
  1450  	var pf0, pf1, pg0, pg1 int64
  1451  
  1452  	var i uint
  1453  
  1454  	var v, s Element
  1455  
  1456  	// Since u,v are updated every other iteration, we must make sure we terminate after evenly many iterations
  1457  	// This also lets us get away with half as many updates to u,v
  1458  	// To make this constant-time-ish, replace the condition with i < invIterationsN
  1459  	for i = 0; i&1 == 1 || !a.IsZero(); i++ {
  1460  		n := max(a.BitLen(), b.BitLen())
  1461  		aApprox, bApprox := approximate(&a, n), approximate(&b, n)
  1462  
  1463  		// f₀, g₀, f₁, g₁ = 1, 0, 0, 1
  1464  		c0, c1 = updateFactorIdentityMatrixRow0, updateFactorIdentityMatrixRow1
  1465  
  1466  		for j := 0; j < approxLowBitsN; j++ {
  1467  
  1468  			// -2ʲ < f₀, f₁ ≤ 2ʲ
  1469  			// |f₀| + |f₁| < 2ʲ⁺¹
  1470  
  1471  			if aApprox&1 == 0 {
  1472  				aApprox /= 2
  1473  			} else {
  1474  				s, borrow := bits.Sub64(aApprox, bApprox, 0)
  1475  				if borrow == 1 {
  1476  					s = bApprox - aApprox
  1477  					bApprox = aApprox
  1478  					c0, c1 = c1, c0
  1479  					// invariants unchanged
  1480  				}
  1481  
  1482  				aApprox = s / 2
  1483  				c0 = c0 - c1
  1484  
  1485  				// Now |f₀| < 2ʲ⁺¹ ≤ 2ʲ⁺¹ (only the weaker inequality is needed, strictly speaking)
  1486  				// Started with f₀ > -2ʲ and f₁ ≤ 2ʲ, so f₀ - f₁ > -2ʲ⁺¹
  1487  				// Invariants unchanged for f₁
  1488  			}
  1489  
  1490  			c1 *= 2
  1491  			// -2ʲ⁺¹ < f₁ ≤ 2ʲ⁺¹
  1492  			// So now |f₀| + |f₁| < 2ʲ⁺²
  1493  		}
  1494  
  1495  		s = a
  1496  
  1497  		var g0 int64
  1498  		// from this point on c0 aliases for f0
  1499  		c0, g0 = updateFactorsDecompose(c0)
  1500  		aHi := a.linearCombNonModular(&s, c0, &b, g0)
  1501  		if aHi&signBitSelector != 0 {
  1502  			// if aHi < 0
  1503  			c0, g0 = -c0, -g0
  1504  			aHi = negL(&a, aHi)
  1505  		}
  1506  		// right-shift a by k-1 bits
  1507  		a[0] = (a[0] >> approxLowBitsN) | ((a[1]) << approxHighBitsN)
  1508  		a[1] = (a[1] >> approxLowBitsN) | ((a[2]) << approxHighBitsN)
  1509  		a[2] = (a[2] >> approxLowBitsN) | ((a[3]) << approxHighBitsN)
  1510  		a[3] = (a[3] >> approxLowBitsN) | ((a[4]) << approxHighBitsN)
  1511  		a[4] = (a[4] >> approxLowBitsN) | ((a[5]) << approxHighBitsN)
  1512  		a[5] = (a[5] >> approxLowBitsN) | (aHi << approxHighBitsN)
  1513  
  1514  		var f1 int64
  1515  		// from this point on c1 aliases for g0
  1516  		f1, c1 = updateFactorsDecompose(c1)
  1517  		bHi := b.linearCombNonModular(&s, f1, &b, c1)
  1518  		if bHi&signBitSelector != 0 {
  1519  			// if bHi < 0
  1520  			f1, c1 = -f1, -c1
  1521  			bHi = negL(&b, bHi)
  1522  		}
  1523  		// right-shift b by k-1 bits
  1524  		b[0] = (b[0] >> approxLowBitsN) | ((b[1]) << approxHighBitsN)
  1525  		b[1] = (b[1] >> approxLowBitsN) | ((b[2]) << approxHighBitsN)
  1526  		b[2] = (b[2] >> approxLowBitsN) | ((b[3]) << approxHighBitsN)
  1527  		b[3] = (b[3] >> approxLowBitsN) | ((b[4]) << approxHighBitsN)
  1528  		b[4] = (b[4] >> approxLowBitsN) | ((b[5]) << approxHighBitsN)
  1529  		b[5] = (b[5] >> approxLowBitsN) | (bHi << approxHighBitsN)
  1530  
  1531  		if i&1 == 1 {
  1532  			// Combine current update factors with previously stored ones
  1533  			// [F₀, G₀; F₁, G₁] ← [f₀, g₀; f₁, g₁] [pf₀, pg₀; pf₁, pg₁], with capital letters denoting new combined values
  1534  			// We get |F₀| = | f₀pf₀ + g₀pf₁ | ≤ |f₀pf₀| + |g₀pf₁| = |f₀| |pf₀| + |g₀| |pf₁| ≤ 2ᵏ⁻¹|pf₀| + 2ᵏ⁻¹|pf₁|
  1535  			// = 2ᵏ⁻¹ (|pf₀| + |pf₁|) < 2ᵏ⁻¹ 2ᵏ = 2²ᵏ⁻¹
  1536  			// So |F₀| < 2²ᵏ⁻¹ meaning it fits in a 2k-bit signed register
  1537  
  1538  			// c₀ aliases f₀, c₁ aliases g₁
  1539  			c0, g0, f1, c1 = c0*pf0+g0*pf1,
  1540  				c0*pg0+g0*pg1,
  1541  				f1*pf0+c1*pf1,
  1542  				f1*pg0+c1*pg1
  1543  
  1544  			s = u
  1545  
  1546  			// 0 ≤ u, v < 2²⁵⁵
  1547  			// |F₀|, |G₀| < 2⁶³
  1548  			u.linearComb(&u, c0, &v, g0)
  1549  			// |F₁|, |G₁| < 2⁶³
  1550  			v.linearComb(&s, f1, &v, c1)
  1551  
  1552  		} else {
  1553  			// Save update factors
  1554  			pf0, pg0, pf1, pg1 = c0, g0, f1, c1
  1555  		}
  1556  	}
  1557  
  1558  	// For every iteration that we miss, v is not being multiplied by 2ᵏ⁻²
  1559  	const pSq uint64 = 1 << (2 * (k - 1))
  1560  	a = Element{pSq}
  1561  	// If the function is constant-time ish, this loop will not run (no need to take it out explicitly)
  1562  	for ; i < invIterationsN; i += 2 {
  1563  		// could optimize further with mul by word routine or by pre-computing a table since with k=26,
  1564  		// we would multiply by pSq up to 13times;
  1565  		// on x86, the assembly routine outperforms generic code for mul by word
  1566  		// on arm64, we may loose up to ~5% for 6 limbs
  1567  		v.Mul(&v, &a)
  1568  	}
  1569  
  1570  	u.Set(x) // for correctness check
  1571  
  1572  	z.Mul(&v, &Element{
  1573  		inversionCorrectionFactorWord0,
  1574  		inversionCorrectionFactorWord1,
  1575  		inversionCorrectionFactorWord2,
  1576  		inversionCorrectionFactorWord3,
  1577  		inversionCorrectionFactorWord4,
  1578  		inversionCorrectionFactorWord5,
  1579  	})
  1580  
  1581  	// correctness check
  1582  	v.Mul(&u, z)
  1583  	if !v.IsOne() && !u.IsZero() {
  1584  		return z.inverseExp(u)
  1585  	}
  1586  
  1587  	return z
  1588  }
  1589  
  1590  // inverseExp computes z = x⁻¹ (mod q) = x**(q-2) (mod q)
  1591  func (z *Element) inverseExp(x Element) *Element {
  1592  	// e == q-2
  1593  	e := Modulus()
  1594  	e.Sub(e, big.NewInt(2))
  1595  
  1596  	z.Set(&x)
  1597  
  1598  	for i := e.BitLen() - 2; i >= 0; i-- {
  1599  		z.Square(z)
  1600  		if e.Bit(i) == 1 {
  1601  			z.Mul(z, &x)
  1602  		}
  1603  	}
  1604  
  1605  	return z
  1606  }
  1607  
  1608  // approximate a big number x into a single 64 bit word using its uppermost and lowermost bits
  1609  // if x fits in a word as is, no approximation necessary
  1610  func approximate(x *Element, nBits int) uint64 {
  1611  
  1612  	if nBits <= 64 {
  1613  		return x[0]
  1614  	}
  1615  
  1616  	const mask = (uint64(1) << (k - 1)) - 1 // k-1 ones
  1617  	lo := mask & x[0]
  1618  
  1619  	hiWordIndex := (nBits - 1) / 64
  1620  
  1621  	hiWordBitsAvailable := nBits - hiWordIndex*64
  1622  	hiWordBitsUsed := min(hiWordBitsAvailable, approxHighBitsN)
  1623  
  1624  	mask_ := uint64(^((1 << (hiWordBitsAvailable - hiWordBitsUsed)) - 1))
  1625  	hi := (x[hiWordIndex] & mask_) << (64 - hiWordBitsAvailable)
  1626  
  1627  	mask_ = ^(1<<(approxLowBitsN+hiWordBitsUsed) - 1)
  1628  	mid := (mask_ & x[hiWordIndex-1]) >> hiWordBitsUsed
  1629  
  1630  	return lo | mid | hi
  1631  }
  1632  
  1633  // linearComb z = xC * x + yC * y;
  1634  // 0 ≤ x, y < 2³⁷⁸
  1635  // |xC|, |yC| < 2⁶³
  1636  func (z *Element) linearComb(x *Element, xC int64, y *Element, yC int64) {
  1637  	// | (hi, z) | < 2 * 2⁶³ * 2³⁷⁸ = 2⁴⁴²
  1638  	// therefore | hi | < 2⁵⁸ ≤ 2⁶³
  1639  	hi := z.linearCombNonModular(x, xC, y, yC)
  1640  	z.montReduceSigned(z, hi)
  1641  }
  1642  
  1643  // montReduceSigned z = (xHi * r + x) * r⁻¹ using the SOS algorithm
  1644  // Requires |xHi| < 2⁶³. Most significant bit of xHi is the sign bit.
  1645  func (z *Element) montReduceSigned(x *Element, xHi uint64) {
  1646  	const signBitRemover = ^signBitSelector
  1647  	mustNeg := xHi&signBitSelector != 0
  1648  	// the SOS implementation requires that most significant bit is 0
  1649  	// Let X be xHi*r + x
  1650  	// If X is negative we would have initially stored it as 2⁶⁴ r + X (à la 2's complement)
  1651  	xHi &= signBitRemover
  1652  	// with this a negative X is now represented as 2⁶³ r + X
  1653  
  1654  	var t [2*Limbs - 1]uint64
  1655  	var C uint64
  1656  
  1657  	m := x[0] * qInvNeg
  1658  
  1659  	C = madd0(m, q0, x[0])
  1660  	C, t[1] = madd2(m, q1, x[1], C)
  1661  	C, t[2] = madd2(m, q2, x[2], C)
  1662  	C, t[3] = madd2(m, q3, x[3], C)
  1663  	C, t[4] = madd2(m, q4, x[4], C)
  1664  	C, t[5] = madd2(m, q5, x[5], C)
  1665  
  1666  	// m * qElement[5] ≤ (2⁶⁴ - 1) * (2⁶³ - 1) = 2¹²⁷ - 2⁶⁴ - 2⁶³ + 1
  1667  	// x[5] + C ≤ 2*(2⁶⁴ - 1) = 2⁶⁵ - 2
  1668  	// On LHS, (C, t[5]) ≤ 2¹²⁷ - 2⁶⁴ - 2⁶³ + 1 + 2⁶⁵ - 2 = 2¹²⁷ + 2⁶³ - 1
  1669  	// So on LHS, C ≤ 2⁶³
  1670  	t[6] = xHi + C
  1671  	// xHi + C < 2⁶³ + 2⁶³ = 2⁶⁴
  1672  
  1673  	// <standard SOS>
  1674  	{
  1675  		const i = 1
  1676  		m = t[i] * qInvNeg
  1677  
  1678  		C = madd0(m, q0, t[i+0])
  1679  		C, t[i+1] = madd2(m, q1, t[i+1], C)
  1680  		C, t[i+2] = madd2(m, q2, t[i+2], C)
  1681  		C, t[i+3] = madd2(m, q3, t[i+3], C)
  1682  		C, t[i+4] = madd2(m, q4, t[i+4], C)
  1683  		C, t[i+5] = madd2(m, q5, t[i+5], C)
  1684  
  1685  		t[i+Limbs] += C
  1686  	}
  1687  	{
  1688  		const i = 2
  1689  		m = t[i] * qInvNeg
  1690  
  1691  		C = madd0(m, q0, t[i+0])
  1692  		C, t[i+1] = madd2(m, q1, t[i+1], C)
  1693  		C, t[i+2] = madd2(m, q2, t[i+2], C)
  1694  		C, t[i+3] = madd2(m, q3, t[i+3], C)
  1695  		C, t[i+4] = madd2(m, q4, t[i+4], C)
  1696  		C, t[i+5] = madd2(m, q5, t[i+5], C)
  1697  
  1698  		t[i+Limbs] += C
  1699  	}
  1700  	{
  1701  		const i = 3
  1702  		m = t[i] * qInvNeg
  1703  
  1704  		C = madd0(m, q0, t[i+0])
  1705  		C, t[i+1] = madd2(m, q1, t[i+1], C)
  1706  		C, t[i+2] = madd2(m, q2, t[i+2], C)
  1707  		C, t[i+3] = madd2(m, q3, t[i+3], C)
  1708  		C, t[i+4] = madd2(m, q4, t[i+4], C)
  1709  		C, t[i+5] = madd2(m, q5, t[i+5], C)
  1710  
  1711  		t[i+Limbs] += C
  1712  	}
  1713  	{
  1714  		const i = 4
  1715  		m = t[i] * qInvNeg
  1716  
  1717  		C = madd0(m, q0, t[i+0])
  1718  		C, t[i+1] = madd2(m, q1, t[i+1], C)
  1719  		C, t[i+2] = madd2(m, q2, t[i+2], C)
  1720  		C, t[i+3] = madd2(m, q3, t[i+3], C)
  1721  		C, t[i+4] = madd2(m, q4, t[i+4], C)
  1722  		C, t[i+5] = madd2(m, q5, t[i+5], C)
  1723  
  1724  		t[i+Limbs] += C
  1725  	}
  1726  	{
  1727  		const i = 5
  1728  		m := t[i] * qInvNeg
  1729  
  1730  		C = madd0(m, q0, t[i+0])
  1731  		C, z[0] = madd2(m, q1, t[i+1], C)
  1732  		C, z[1] = madd2(m, q2, t[i+2], C)
  1733  		C, z[2] = madd2(m, q3, t[i+3], C)
  1734  		C, z[3] = madd2(m, q4, t[i+4], C)
  1735  		z[5], z[4] = madd2(m, q5, t[i+5], C)
  1736  	}
  1737  
  1738  	// if z ⩾ q → z -= q
  1739  	if !z.smallerThanModulus() {
  1740  		var b uint64
  1741  		z[0], b = bits.Sub64(z[0], q0, 0)
  1742  		z[1], b = bits.Sub64(z[1], q1, b)
  1743  		z[2], b = bits.Sub64(z[2], q2, b)
  1744  		z[3], b = bits.Sub64(z[3], q3, b)
  1745  		z[4], b = bits.Sub64(z[4], q4, b)
  1746  		z[5], _ = bits.Sub64(z[5], q5, b)
  1747  	}
  1748  	// </standard SOS>
  1749  
  1750  	if mustNeg {
  1751  		// We have computed ( 2⁶³ r + X ) r⁻¹ = 2⁶³ + X r⁻¹ instead
  1752  		var b uint64
  1753  		z[0], b = bits.Sub64(z[0], signBitSelector, 0)
  1754  		z[1], b = bits.Sub64(z[1], 0, b)
  1755  		z[2], b = bits.Sub64(z[2], 0, b)
  1756  		z[3], b = bits.Sub64(z[3], 0, b)
  1757  		z[4], b = bits.Sub64(z[4], 0, b)
  1758  		z[5], b = bits.Sub64(z[5], 0, b)
  1759  
  1760  		// Occurs iff x == 0 && xHi < 0, i.e. X = rX' for -2⁶³ ≤ X' < 0
  1761  
  1762  		if b != 0 {
  1763  			// z[5] = -1
  1764  			// negative: add q
  1765  			const neg1 = 0xFFFFFFFFFFFFFFFF
  1766  
  1767  			var carry uint64
  1768  
  1769  			z[0], carry = bits.Add64(z[0], q0, 0)
  1770  			z[1], carry = bits.Add64(z[1], q1, carry)
  1771  			z[2], carry = bits.Add64(z[2], q2, carry)
  1772  			z[3], carry = bits.Add64(z[3], q3, carry)
  1773  			z[4], carry = bits.Add64(z[4], q4, carry)
  1774  			z[5], _ = bits.Add64(neg1, q5, carry)
  1775  		}
  1776  	}
  1777  }
  1778  
  1779  const (
  1780  	updateFactorsConversionBias    int64 = 0x7fffffff7fffffff // (2³¹ - 1)(2³² + 1)
  1781  	updateFactorIdentityMatrixRow0       = 1
  1782  	updateFactorIdentityMatrixRow1       = 1 << 32
  1783  )
  1784  
  1785  func updateFactorsDecompose(c int64) (int64, int64) {
  1786  	c += updateFactorsConversionBias
  1787  	const low32BitsFilter int64 = 0xFFFFFFFF
  1788  	f := c&low32BitsFilter - 0x7FFFFFFF
  1789  	g := c>>32&low32BitsFilter - 0x7FFFFFFF
  1790  	return f, g
  1791  }
  1792  
  1793  // negL negates in place [x | xHi] and return the new most significant word xHi
  1794  func negL(x *Element, xHi uint64) uint64 {
  1795  	var b uint64
  1796  
  1797  	x[0], b = bits.Sub64(0, x[0], 0)
  1798  	x[1], b = bits.Sub64(0, x[1], b)
  1799  	x[2], b = bits.Sub64(0, x[2], b)
  1800  	x[3], b = bits.Sub64(0, x[3], b)
  1801  	x[4], b = bits.Sub64(0, x[4], b)
  1802  	x[5], b = bits.Sub64(0, x[5], b)
  1803  	xHi, _ = bits.Sub64(0, xHi, b)
  1804  
  1805  	return xHi
  1806  }
  1807  
  1808  // mulWNonModular multiplies by one word in non-montgomery, without reducing
  1809  func (z *Element) mulWNonModular(x *Element, y int64) uint64 {
  1810  
  1811  	// w := abs(y)
  1812  	m := y >> 63
  1813  	w := uint64((y ^ m) - m)
  1814  
  1815  	var c uint64
  1816  	c, z[0] = bits.Mul64(x[0], w)
  1817  	c, z[1] = madd1(x[1], w, c)
  1818  	c, z[2] = madd1(x[2], w, c)
  1819  	c, z[3] = madd1(x[3], w, c)
  1820  	c, z[4] = madd1(x[4], w, c)
  1821  	c, z[5] = madd1(x[5], w, c)
  1822  
  1823  	if y < 0 {
  1824  		c = negL(z, c)
  1825  	}
  1826  
  1827  	return c
  1828  }
  1829  
  1830  // linearCombNonModular computes a linear combination without modular reduction
  1831  func (z *Element) linearCombNonModular(x *Element, xC int64, y *Element, yC int64) uint64 {
  1832  	var yTimes Element
  1833  
  1834  	yHi := yTimes.mulWNonModular(y, yC)
  1835  	xHi := z.mulWNonModular(x, xC)
  1836  
  1837  	var carry uint64
  1838  	z[0], carry = bits.Add64(z[0], yTimes[0], 0)
  1839  	z[1], carry = bits.Add64(z[1], yTimes[1], carry)
  1840  	z[2], carry = bits.Add64(z[2], yTimes[2], carry)
  1841  	z[3], carry = bits.Add64(z[3], yTimes[3], carry)
  1842  	z[4], carry = bits.Add64(z[4], yTimes[4], carry)
  1843  	z[5], carry = bits.Add64(z[5], yTimes[5], carry)
  1844  
  1845  	yHi, _ = bits.Add64(xHi, yHi, carry)
  1846  
  1847  	return yHi
  1848  }