-
Notifications
You must be signed in to change notification settings - Fork 168
/
group.go
193 lines (154 loc) · 6.32 KB
/
group.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
package kyber
import (
"crypto/cipher"
"math/big"
)
// ByteOrder denotes the endianness of the operation.
type ByteOrder bool
const (
// LittleEndian endianness
LittleEndian ByteOrder = true
// BigEndian endianness
BigEndian ByteOrder = false
)
// Scalar represents a scalar value by which
// a Point (group element) may be encrypted to produce another Point.
// This is an exponent in DSA-style groups,
// in which security is based on the Discrete Logarithm assumption,
// and a scalar multiplier in elliptic curve groups.
type Scalar interface {
Marshaling
// Equality test for two Scalars derived from the same Group.
Equal(s2 Scalar) bool
// Set sets the receiver equal to another Scalar a.
Set(a Scalar) Scalar
// Clone creates a new Scalar with the same value.
Clone() Scalar
// SetInt64 sets the receiver to a small integer value.
SetInt64(v int64) Scalar
// Set to the additive identity (0).
Zero() Scalar
// Set to the modular sum of scalars a and b.
Add(a, b Scalar) Scalar
// Set to the modular difference a - b.
Sub(a, b Scalar) Scalar
// Set to the modular negation of scalar a.
Neg(a Scalar) Scalar
// Set to the multiplicative identity (1).
One() Scalar
// Set to the modular product of scalars a and b.
Mul(a, b Scalar) Scalar
// Set to the modular division of scalar a by scalar b.
Div(a, b Scalar) Scalar
// Set to the modular inverse of scalar a.
Inv(a Scalar) Scalar
// Set to a fresh random or pseudo-random scalar.
Pick(rand cipher.Stream) Scalar
// SetBytes sets the scalar from a byte-slice,
// reducing if necessary to the appropriate modulus.
// The endianess of the byte-slice is determined by the
// implementation.
SetBytes([]byte) Scalar
// ByteOrder return the byte representation type (big or little endian)
ByteOrder() ByteOrder
// GroupOrder returns the order of the underlying group
GroupOrder() *big.Int
}
// Point represents an element of a public-key cryptographic Group.
// For example,
// this is a number modulo the prime P in a DSA-style Schnorr group,
// or an (x, y) point on an elliptic curve.
// A Point can contain a Diffie-Hellman public key, an ElGamal ciphertext, etc.
type Point interface {
Marshaling
// Equality test for two Points derived from the same Group.
Equal(s2 Point) bool
// Null sets the receiver to the neutral identity element.
Null() Point
// Base sets the receiver to this group's standard base point.
Base() Point
// Pick sets the receiver to a fresh random or pseudo-random Point.
Pick(rand cipher.Stream) Point
// Set sets the receiver equal to another Point p.
Set(p Point) Point
// Clone clones the underlying point.
Clone() Point
// Maximum number of bytes that can be embedded in a single
// group element via Pick().
EmbedLen() int
// Embed encodes a limited amount of specified data in the
// Point, using r as a source of cryptographically secure
// random data. Implementations only embed the first EmbedLen
// bytes of the given data.
Embed(data []byte, r cipher.Stream) Point
// Extract data embedded in a point chosen via Embed().
// Returns an error if doesn't represent valid embedded data.
Data() ([]byte, error)
// Add points so that their scalars add homomorphically.
Add(a, b Point) Point
// Subtract points so that their scalars subtract homomorphically.
Sub(a, b Point) Point
// Set to the negation of point a.
Neg(a Point) Point
// Multiply point p by the scalar s.
// If p == nil, multiply with the standard base point Base().
Mul(s Scalar, p Point) Point
}
// AllowsVarTime allows callers to determine if a given kyber.Scalar
// or kyber.Point supports opting-in to variable time operations. If
// an object implements AllowsVarTime, then the caller can use
// AllowVarTime(true) in order to allow variable time operations on
// that object until AllowVarTime(false) is called. Variable time
// operations may be faster, but also risk leaking information via a
// timing side channel. Thus they are only safe to use on public
// Scalars and Points, never on secret ones.
type AllowsVarTime interface {
AllowVarTime(bool)
}
// Group interface represents a mathematical group
// usable for Diffie-Hellman key exchange, ElGamal encryption,
// and the related body of public-key cryptographic algorithms
// and zero-knowledge proof methods.
// The Group interface is designed in particular to be a generic front-end
// to both traditional DSA-style modular arithmetic groups
// and ECDSA-style elliptic curves:
// the caller of this interface's methods
// need not know or care which specific mathematical construction
// underlies the interface.
//
// The Group interface is essentially just a "constructor" interface
// enabling the caller to generate the two particular types of objects
// relevant to DSA-style public-key cryptography;
// we call these objects Points and Scalars.
// The caller must explicitly initialize or set a new Point or Scalar object
// to some value before using it as an input to some other operation
// involving Point and/or Scalar objects.
// For example, to compare a point P against the neutral (identity) element,
// you might use P.Equal(suite.Point().Null()),
// but not just P.Equal(suite.Point()).
//
// It is expected that any implementation of this interface
// should satisfy suitable hardness assumptions for the applicable group:
// e.g., that it is cryptographically hard for an adversary to
// take an encrypted Point and the known generator it was based on,
// and derive the Scalar with which the Point was encrypted.
// Any implementation is also expected to satisfy
// the standard homomorphism properties that Diffie-Hellman
// and the associated body of public-key cryptography are based on.
type Group interface {
String() string
ScalarLen() int // Max length of scalars in bytes
Scalar() Scalar // Create new scalar
PointLen() int // Max length of point in bytes
Point() Point // Create new point
}
// SubGroupElement allows to verify if a Point is in the correct group or not.
// For curves which don't have a prime order, we need to only consider the
// points lying in the subgroup of prime order. That check returns true if the
// point is correct or not. If the curve forms already a prime order// group,
// then this method should be implemented as a nop returning true, to be able to
// use the Schnorr signature scheme for example.
type SubGroupElement interface {
Point
IsInCorrectGroup() bool
}