- B9880001CD7A0ADC289E3F1EBC71B48EFF6CB1079EEB5A21BF32A81BA4E0E0F3F9917FFFDD02E0C1AC2F06553610FA0F396408680C411C8DB3B6A80A8E1E978D+ 7DCF2EE0EFC97EA57C360131F2EE836775FE2D57195D454C655E74CD030E72AA6D3109E2736A04AAE0F305859DE52E29EDD38005B6249E0548950F1E91F36D4Affa/libffa/fz_modex.adb(60 . 41)(60 . 44)
212 Modulus : in FZ;
213 Result : out FZ) is
214
215 -- Working register for the squaring
216 -- Working register for the squaring; initially is copy of Base
217 B : FZ(Base'Range) := Base;
218
219 -- Register for cycling through the bits of E
220 -- Copy of Exponent, for cycling through its bits
221 E : FZ(Exponent'Range) := Exponent;
222
223 -- Register for the Mux operation
224 T : FZ(Result'Range);
225
226 -- Buffer register for the Result
227 R : FZ(Result'Range);
228
229 begin
230 -- Result := 1
231 WBool_To_FZ(1, Result);
232 WBool_To_FZ(1, R);
233
234 -- For each bit of Result width:
235 for i in 1 .. FZ_Bitness(Result) loop
236 -- For each bit of R width:
237 for i in 1 .. FZ_Bitness(R) loop
238
239 -- T := Result * B mod Modulus
240 FZ_Mod_Mul(X => Result, Y => B, Modulus => Modulus,
241 Product => T);
242 FZ_Mod_Mul(X => R, Y => B, Modulus => Modulus, Product => T);
243
244 -- Sel is the current low bit of E;
245 -- When Sel=0 -> Result := Result;
246 -- When Sel=1 -> Result := T
247 FZ_Mux(X => Result, Y => T, Result => Result,
248 Sel => FZ_OddP(E));
249 FZ_Mux(X => R, Y => T, Result => R, Sel => FZ_OddP(E));
250
251 -- Advance to the next bit of E
252 FZ_ShiftRight(E, E, 1);
253
254 -- B := B*B mod Modulus
255 FZ_Mod_Mul(X => B, Y => B, Modulus => Modulus,
256 Product => B);
257 FZ_Mod_Mul(X => B, Y => B, Modulus => Modulus, Product => B);
258
259 end loop;
260
261 -- Output the Result:
262 Result := R;
263
264 end FZ_Mod_Exp;
265 pragma Inline_Always(FZ_Mod_Exp);
266