github.com/cloudflare/circl@v1.5.0/ecc/goldilocks/twist_basemult.go (about)

     1  package goldilocks
     2  
     3  import (
     4  	"crypto/subtle"
     5  
     6  	mlsb "github.com/cloudflare/circl/math/mlsbset"
     7  )
     8  
     9  const (
    10  	// MLSBRecoding parameters
    11  	fxT   = 448
    12  	fxV   = 2
    13  	fxW   = 3
    14  	fx2w1 = 1 << (uint(fxW) - 1)
    15  )
    16  
    17  // ScalarBaseMult returns kG where G is the generator point.
    18  func (e twistCurve) ScalarBaseMult(k *Scalar) *twistPoint {
    19  	m, err := mlsb.New(fxT, fxV, fxW)
    20  	if err != nil {
    21  		panic(err)
    22  	}
    23  	if m.IsExtended() {
    24  		panic("not extended")
    25  	}
    26  
    27  	var isZero int
    28  	if k.IsZero() {
    29  		isZero = 1
    30  	}
    31  	subtle.ConstantTimeCopy(isZero, k[:], order[:])
    32  
    33  	minusK := *k
    34  	isEven := 1 - int(k[0]&0x1)
    35  	minusK.Neg()
    36  	subtle.ConstantTimeCopy(isEven, k[:], minusK[:])
    37  	c, err := m.Encode(k[:])
    38  	if err != nil {
    39  		panic(err)
    40  	}
    41  
    42  	gP := c.Exp(groupMLSB{})
    43  	P := gP.(*twistPoint)
    44  	P.cneg(uint(isEven))
    45  	return P
    46  }
    47  
    48  type groupMLSB struct{}
    49  
    50  func (e groupMLSB) ExtendedEltP() mlsb.EltP      { return nil }
    51  func (e groupMLSB) Sqr(x mlsb.EltG)              { x.(*twistPoint).Double() }
    52  func (e groupMLSB) Mul(x mlsb.EltG, y mlsb.EltP) { x.(*twistPoint).mixAddZ1(y.(*preTwistPointAffine)) }
    53  func (e groupMLSB) Identity() mlsb.EltG          { return twistCurve{}.Identity() }
    54  func (e groupMLSB) NewEltP() mlsb.EltP           { return &preTwistPointAffine{} }
    55  func (e groupMLSB) Lookup(a mlsb.EltP, v uint, s, u int32) {
    56  	Tabj := &tabFixMult[v]
    57  	P := a.(*preTwistPointAffine)
    58  	for k := range Tabj {
    59  		P.cmov(&Tabj[k], uint(subtle.ConstantTimeEq(int32(k), u)))
    60  	}
    61  	P.cneg(int(s >> 31))
    62  }