Documentation ¶
Overview ¶
Pure Go implementation of the Ristretto prime-order group built from the Edwards curve Edwards25519.
Many cryptographic schemes need a group of prime order. Popular and efficient elliptic curves like (Edwards25519 of `ed25519` fame) are rarely of prime order. There is, however, a convenient method to construct a prime order group from such curves, using a method called Ristretto proposed by Mike Hamburg.
This package implements the Ristretto group constructed from Edwards25519. The Point type represents a group element. The API mimics that of the math/big package. For instance, to set c to a+b, one writes
var c ristretto.Point c.Add(&a, &b) // sets c to a + b
Warning: contrary to math.Big's interface, an uninitialized Point is not the same thing as the zero (neutral element) of the group:
var c ristretto.Point // c is uninitialized now --- not zero! c.SetZero() // c is zero now; ready to use!
Most methods return the receiver, so that function can be chained:
s.Add(&a, &b).Add(&s, &c) // sets s to a + b + c
The order of the Ristretto group is l = 2^252 + 27742317777372353535851937790883648493 = 7237005577332262213973186563042994240857116359379907606001950938285454250989. The Scalar type implement the numbers modulo l and also has an API similar to math/big.
Example ¶
// Generate an El'Gamal keypair var secretKey ristretto.Scalar var publicKey ristretto.Point secretKey.Rand() // generate a new secret key publicKey.ScalarMultBase(&secretKey) // compute public key // El'Gamal encrypt a random curve point p into a ciphertext-pair (c1,c2) var p ristretto.Point var r ristretto.Scalar var c1 ristretto.Point var c2 ristretto.Point p.Rand() r.Rand() c2.ScalarMultBase(&r) c1.PublicScalarMult(&publicKey, &r) c1.Add(&c1, &p) // Decrypt (c1,c2) back to p var blinding, p2 ristretto.Point blinding.ScalarMult(&c2, &secretKey) p2.Sub(&c1, &blinding) fmt.Printf("%v", bytes.Equal(p.Bytes(), p2.Bytes()))
Output: true
Index ¶
- type Point
- func (p *Point) Add(q, r *Point) *Point
- func (p *Point) Bytes() []byte
- func (p *Point) BytesInto(buf *[32]byte) *Point
- func (p *Point) ConditionalSet(q *Point, b int32)
- func (p *Point) Derive(buf []byte) *Point
- func (p *Point) DeriveDalek(data []byte) *Point
- func (p *Point) Double(q *Point) *Point
- func (p *Point) Equals(q *Point) bool
- func (p *Point) EqualsI(q *Point) int32
- func (p *Point) Lizard() []byte
- func (p *Point) LizardInto(buf *[16]byte) error
- func (p *Point) MarshalBinary() ([]byte, error)
- func (p *Point) MarshalText() ([]byte, error)
- func (p *Point) Neg(q *Point) *Point
- func (p *Point) PublicScalarMult(q *Point, s *Scalar) *Point
- func (p *Point) PublicScalarMultBase(s *Scalar) *Point
- func (p *Point) PublicScalarMultTable(t *ScalarMultTable, s *Scalar) *Point
- func (p *Point) Rand() *Point
- func (p *Point) ScalarMult(q *Point, s *Scalar) *Point
- func (p *Point) ScalarMultBase(s *Scalar) *Point
- func (p *Point) ScalarMultTable(t *ScalarMultTable, s *Scalar) *Point
- func (p *Point) Set(q *Point) *Point
- func (p *Point) SetBase() *Point
- func (p *Point) SetBytes(buf *[32]byte) bool
- func (p *Point) SetElligator(buf *[32]byte) *Point
- func (p *Point) SetLizard(data *[16]byte) *Point
- func (p *Point) SetZero() *Point
- func (p Point) String() string
- func (p *Point) Sub(q, r *Point) *Point
- func (p *Point) UnmarshalBinary(data []byte) error
- func (p *Point) UnmarshalText(txt []byte) error
- type Scalar
- func (s *Scalar) Add(a, b *Scalar) *Scalar
- func (s *Scalar) BigInt() *big.Int
- func (s *Scalar) Bytes() []byte
- func (s *Scalar) BytesInto(buf *[32]byte) *Scalar
- func (s *Scalar) ConditionalSet(t *Scalar, b int32)
- func (s *Scalar) Derive(buf []byte) *Scalar
- func (s *Scalar) DeriveShort(buf []byte) *Scalar
- func (s *Scalar) Equals(a *Scalar) bool
- func (s *Scalar) EqualsI(a *Scalar) int32
- func (s *Scalar) Inverse(t *Scalar) *Scalar
- func (s *Scalar) IsNonZeroI() int32
- func (s *Scalar) MarshalBinary() ([]byte, error)
- func (s *Scalar) MarshalText() ([]byte, error)
- func (s *Scalar) Mul(a, b *Scalar) *Scalar
- func (s *Scalar) MulAdd(a, b, c *Scalar) *Scalar
- func (s *Scalar) MulSub(a, b, c *Scalar) *Scalar
- func (s *Scalar) Neg(a *Scalar) *Scalar
- func (s *Scalar) Rand() *Scalar
- func (s *Scalar) Set(t *Scalar) *Scalar
- func (s *Scalar) SetBigInt(x *big.Int) *Scalar
- func (s *Scalar) SetBytes(x *[32]byte) *Scalar
- func (s *Scalar) SetOne() *Scalar
- func (s *Scalar) SetReduced(t *[64]byte) *Scalar
- func (s *Scalar) SetUint64(x uint64) *Scalar
- func (s *Scalar) SetZero() *Scalar
- func (s *Scalar) Square(a *Scalar) *Scalar
- func (s Scalar) String() string
- func (s *Scalar) Sub(a, b *Scalar) *Scalar
- func (s *Scalar) UnmarshalBinary(data []byte) error
- func (s *Scalar) UnmarshalText(txt []byte) error
- type ScalarMultTable
Examples ¶
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
This section is empty.
Types ¶
type Point ¶
type Point edwards25519.ExtendedPoint
Represents an element of the Ristretto group over Edwards25519.
Warning: an uninitialized Point is not the same thing as a zero. Use the SetZero() method to set an (uninitialized) Point to zero.
func (*Point) ConditionalSet ¶ added in v1.2.2
Set p to q if b=1 in constant-time. b must be either 0 or 1.
func (*Point) Derive ¶
Sets p to the point derived from the buffer using SHA512 and Elligator2. Returns p.
NOTE curve25519-dalek uses a different (more conservative) method to derive a point from raw data with a hash. This is implemented in Point.DeriveDalek().
func (*Point) DeriveDalek ¶
Sets p to the point derived from the buffer using SHA512 and Elligator2 in the fashion of curve25519-dalek.
NOTE See also Derive(), which is a different method which is twice as fast, but which might not be as secure as this method.
func (*Point) Lizard ¶ added in v1.1.0
Decodes 16 bytes encoded into this point using SetLizard().
Returns nil if this point does not contain data encoded using Lizard.
See SetLizard() for notes on usage.
func (*Point) LizardInto ¶ added in v1.1.0
Decodes 16 bytes into the given buffer encoded into this point using SetLizard().
See SetLizard() for notes on usage.
func (*Point) MarshalBinary ¶
Implements encoding/BinaryMarshaler. Use BytesInto, if convenient, instead.
func (*Point) MarshalText ¶
func (*Point) PublicScalarMult ¶
Sets p to s * q assuming s is *not* secret. Returns p.
Warning: this method uses a non-constant time implementation and thus leaks information about s. Use this function only if s is public knowledge.
func (*Point) PublicScalarMultBase ¶
Sets p to s * B, where B is the edwards25519 basepoint. Returns p.
Warning: this method uses a non-constant time implementation and thus leaks information about s. Use this function only if s is public knowledge.
func (*Point) PublicScalarMultTable ¶
func (p *Point) PublicScalarMultTable(t *ScalarMultTable, s *Scalar) *Point
Sets p to s * q, where q is the point for which the table t was computed. Returns p.
Warning: this method uses a non-constant time implementation and thus leaks information about s. Use this function only if s is public knowledge.
func (*Point) ScalarMult ¶
Sets p to s * q. Returns p.
func (*Point) ScalarMultBase ¶
Sets p to s * B, where B is the edwards25519 basepoint. Returns p.
func (*Point) ScalarMultTable ¶
func (p *Point) ScalarMultTable(t *ScalarMultTable, s *Scalar) *Point
Sets p to s * q, where q is the point for which the table t was computed. Returns p.
func (*Point) SetBytes ¶
Sets p to the point encoded in buf using Bytes(). Not every input encodes a point. Returns whether the buffer encoded a point.
func (*Point) SetElligator ¶
Sets p to the point corresponding to buf using the Elligator2 encoding.
In contrast to SetBytes() (1) Every input buffer will decode to a point and (2) SetElligator() is not injective: for every point there are approximately four buffers that will encode to it.
func (*Point) SetLizard ¶ added in v1.1.0
Encode 16 bytes into a point using the Lizard method.
Use Lizard() or LizardInto() to decode the bytes from a Point.
Notes on usage:
If you want to create a Point from random data, you should rather create a random Point with Point.Rand() and then use (a hash of) Point.Bytes() as the random data.
If you want to derive a Point from data, but you do not care about decoding the data back from the point, you should use the Point.Derive() method instead.
There are some (and with high probability at most 80) inputs to SetLizard() which cannot be decoded. The chance that you hit such an input is around 1 in 2^122.
In Lizard there are 256 - 128 - 3 = 125 check bits to pick out the right preimage among at most eight. Conservatively assuming there are seven other preimages, the chance that one of them passes the check as well is given by:
1 - (1 - 2^-125)^7 = 7*2^-125 + 21*2^-250 - ... =~ 2^(-125 - 2log(7)) = 2^-122.192...
Presuming a random hash function, the number of "bad" inputs is binomially distributed with n=2^128 and p=2^-122.192... For such large n, the Poisson distribution with lambda=n*p=56 is a very good approximation. In fact: the cumulative distribution function (CDF) of the Poission distribution is larger than that of the binomial distribution for k > lambda.[1] The value of the former on k=80 is larger than 0.999 and so with a probability of 99.9%, there are fewer than 80 bad inputs.
[1] See "Some Inequalities Among Binomial and Poisson Probabilities" by Anderson and Samuels in Proc. Fifth Berkeley Symp. on Math. Statist. and Prob., Vol. 1 (Univ. of Calif. Press, 1967).
func (*Point) UnmarshalBinary ¶
Implements encoding/BinaryUnmarshaler. Use SetBytes, if convenient, instead.
func (*Point) UnmarshalText ¶
type Scalar ¶
type Scalar [8]uint32
A number modulo the prime l, where l is the order of the Ristretto group over Edwards25519.
The scalar s is represented as an array s[0], ... s[7] with 0 <= s[i] < 2^32 and s = s[0] + s[1] * 2^32 + s[2] * 2^64 + ... + s[7] * 2^224.
func (*Scalar) BigInt ¶
Returns s as a big.Int.
Warning: operations on big.Ints are not constant-time: do not use them for cryptography unless you're sure this is not an issue.
func (*Scalar) ConditionalSet ¶ added in v1.2.2
Set s to t if b=1 in constant-time. b must be either 0 or 1.
func (*Scalar) Derive ¶
Derive sets s to the scalar derived from the given buffer using SHA512 and Scalar.SetReduced() Returns s.
func (*Scalar) DeriveShort ¶ added in v1.1.0
Derive sets s to the half-length scalar derived from the given buffer using SHA512. Returns s
Warning: half-length scalars are insecure in almost every application.
func (*Scalar) IsNonZeroI ¶
IsNonZeroI returns 1 if s is non-zero and 0 otherwise.
func (*Scalar) MarshalBinary ¶
Implements encoding/BinaryMarshaler. Use BytesInto, if convenient, instead.
func (*Scalar) MarshalText ¶
func (*Scalar) SetBigInt ¶
Sets s to x modulo l.
Warning: operations on big.Ints are not constant-time: do not use them for cryptography unless you're sure this is not an issue.
func (*Scalar) SetBytes ¶
Sets s to x mod l, where x is interpreted little endian and the top 3 bits are ignored. Returns s.
func (*Scalar) SetReduced ¶
Sets s to t mod l, where t is interpreted little endian. Returns s.
func (*Scalar) UnmarshalBinary ¶
Implements encoding/BinaryUnmarshaler. Use SetBytes, if convenient, instead.
func (*Scalar) UnmarshalText ¶
type ScalarMultTable ¶
type ScalarMultTable edwards25519.ScalarMultTable
A table to speed up scalar multiplication of a fixed point
func (*ScalarMultTable) Compute ¶
func (t *ScalarMultTable) Compute(p *Point)
Fills the table for point p.
Directories ¶
Path | Synopsis |
---|---|
A C implementation of the Ristretto group based on the PandA library by Chuengsatiansup, Ribarski and Schwabe, which we use as a reference of our pure Go implementation.
|
A C implementation of the Ristretto group based on the PandA library by Chuengsatiansup, Ribarski and Schwabe, which we use as a reference of our pure Go implementation. |
Go implementation of the elliptic curve Edwards25519 of which the Ristretto group is a subquotient.
|
Go implementation of the elliptic curve Edwards25519 of which the Ristretto group is a subquotient. |