1
1
use super :: { EdwardsPoint , EdwardsScalar } ;
2
2
use crate :: field:: FieldElement ;
3
+ use core:: ops:: Add ;
3
4
use subtle:: { Choice , ConditionallyNegatable , ConditionallySelectable , ConstantTimeEq } ;
4
5
5
6
pub ( super ) fn scalar_mul ( point : & EdwardsPoint , scalar : & EdwardsScalar ) -> EdwardsPoint {
@@ -25,7 +26,7 @@ pub(super) fn scalar_mul(point: &EdwardsPoint, scalar: &EdwardsScalar) -> Edward
25
26
let mut neg_P = lookup. select ( abs_value) ;
26
27
neg_P. conditional_negate ( Choice :: from ( ( sign) as u8 ) ) ;
27
28
28
- result = ( EdwardsPoint :: from ( result) + neg_P) . into ( ) ;
29
+ result = & EdwardsPoint :: from ( result) + & neg_P;
29
30
}
30
31
31
32
result. into ( )
@@ -90,15 +91,89 @@ impl From<EdwardsPoint> for ExtensiblePoint {
90
91
}
91
92
}
92
93
93
- pub struct LookupTable ( [ EdwardsPoint ; 8 ] ) ;
94
+ #[ derive( Clone , Copy ) ]
95
+ struct MixedAdditionPoint {
96
+ X : FieldElement ,
97
+ Y : FieldElement ,
98
+ Z : FieldElement ,
99
+ Td : FieldElement ,
100
+ }
101
+
102
+ impl MixedAdditionPoint {
103
+ const IDENTITY : Self = Self {
104
+ X : FieldElement :: ZERO ,
105
+ Y : FieldElement :: ONE ,
106
+ Z : FieldElement :: ONE ,
107
+ Td : FieldElement :: ZERO ,
108
+ } ;
109
+ }
110
+
111
+ impl From < & EdwardsPoint > for MixedAdditionPoint {
112
+ fn from ( value : & EdwardsPoint ) -> Self {
113
+ Self {
114
+ X : value. X ,
115
+ Y : value. Y ,
116
+ Z : value. Z ,
117
+ Td : value. T * FieldElement :: EDWARDS_D ,
118
+ }
119
+ }
120
+ }
121
+
122
+ impl From < EdwardsPoint > for MixedAdditionPoint {
123
+ fn from ( value : EdwardsPoint ) -> Self {
124
+ ( & value) . into ( )
125
+ }
126
+ }
127
+
128
+ impl Add < & MixedAdditionPoint > for & EdwardsPoint {
129
+ type Output = ExtensiblePoint ;
130
+
131
+ fn add ( self , rhs : & MixedAdditionPoint ) -> Self :: Output {
132
+ let A = self . X * rhs. X ;
133
+ let B = self . Y * rhs. Y ;
134
+ let C = self . T * rhs. Td ;
135
+ let D = self . Z * rhs. Z ;
136
+ let E = ( self . X + self . Y ) * ( rhs. X + rhs. Y ) - A - B ;
137
+ let F = D - C ;
138
+ let G = D + C ;
139
+ let H = B - A ;
140
+ ExtensiblePoint {
141
+ X : E * F ,
142
+ Y : G * H ,
143
+ Z : F * G ,
144
+ T1 : E ,
145
+ T2 : H ,
146
+ }
147
+ }
148
+ }
149
+
150
+ impl ConditionallySelectable for MixedAdditionPoint {
151
+ fn conditional_select ( a : & Self , b : & Self , choice : Choice ) -> Self {
152
+ Self {
153
+ X : FieldElement :: conditional_select ( & a. X , & b. X , choice) ,
154
+ Y : FieldElement :: conditional_select ( & a. Y , & b. Y , choice) ,
155
+ Z : FieldElement :: conditional_select ( & a. Z , & b. Z , choice) ,
156
+ Td : FieldElement :: conditional_select ( & a. Td , & b. Td , choice) ,
157
+ }
158
+ }
159
+ }
160
+
161
+ impl ConditionallyNegatable for MixedAdditionPoint {
162
+ fn conditional_negate ( & mut self , choice : Choice ) {
163
+ self . X . conditional_negate ( choice) ;
164
+ self . Td . conditional_negate ( choice) ;
165
+ }
166
+ }
167
+
168
+ struct LookupTable ( [ MixedAdditionPoint ; 8 ] ) ;
94
169
95
170
/// Precomputes odd multiples of the point passed in
96
171
impl From < & EdwardsPoint > for LookupTable {
97
172
fn from ( P : & EdwardsPoint ) -> LookupTable {
98
- let mut table = [ * P ; 8 ] ;
173
+ let mut table = [ MixedAdditionPoint :: from ( P ) ; 8 ] ;
99
174
100
175
for i in 1 ..8 {
101
- table[ i] = P + table[ i - 1 ] ;
176
+ table[ i] = EdwardsPoint :: from ( P + & table[ i - 1 ] ) . into ( ) ;
102
177
}
103
178
104
179
LookupTable ( table)
@@ -107,8 +182,8 @@ impl From<&EdwardsPoint> for LookupTable {
107
182
108
183
impl LookupTable {
109
184
/// Selects a projective niels point from a lookup table in constant time
110
- pub fn select ( & self , index : u32 ) -> EdwardsPoint {
111
- let mut result = EdwardsPoint :: IDENTITY ;
185
+ fn select ( & self , index : u32 ) -> MixedAdditionPoint {
186
+ let mut result = MixedAdditionPoint :: IDENTITY ;
112
187
113
188
for i in 1 ..9 {
114
189
let swap = index. ct_eq ( & ( i as u32 ) ) ;
0 commit comments