ge_double_scalarmult.c (2371B)
1 #include "ge.h" 2 3 static void slide(signed char *r,const unsigned char *a) 4 { 5 int i; 6 int b; 7 int k; 8 9 for (i = 0;i < 256;++i) 10 r[i] = 1 & (a[i >> 3] >> (i & 7)); 11 12 for (i = 0;i < 256;++i) 13 if (r[i]) { 14 for (b = 1;b <= 6 && i + b < 256;++b) { 15 if (r[i + b]) { 16 if (r[i] + (r[i + b] << b) <= 15) { 17 r[i] += r[i + b] << b; r[i + b] = 0; 18 } else if (r[i] - (r[i + b] << b) >= -15) { 19 r[i] -= r[i + b] << b; 20 for (k = i + b;k < 256;++k) { 21 if (!r[k]) { 22 r[k] = 1; 23 break; 24 } 25 r[k] = 0; 26 } 27 } else 28 break; 29 } 30 } 31 } 32 33 } 34 35 static ge_precomp Bi[8] = { 36 #include "base2.h" 37 } ; 38 39 /* 40 r = a * A + b * B 41 where a = a[0]+256*a[1]+...+256^31 a[31]. 42 and b = b[0]+256*b[1]+...+256^31 b[31]. 43 B is the Ed25519 base point (x,4/5) with x positive. 44 */ 45 46 void ge_double_scalarmult_vartime(ge_p2 *r,const unsigned char *a,const ge_p3 *A,const unsigned char *b) 47 { 48 signed char aslide[256]; 49 signed char bslide[256]; 50 ge_cached Ai[8]; /* A,3A,5A,7A,9A,11A,13A,15A */ 51 ge_p1p1 t; 52 ge_p3 u; 53 ge_p3 A2; 54 int i; 55 56 slide(aslide,a); 57 slide(bslide,b); 58 59 ge_p3_to_cached(&Ai[0],A); 60 ge_p3_dbl(&t,A); ge_p1p1_to_p3(&A2,&t); 61 ge_add(&t,&A2,&Ai[0]); ge_p1p1_to_p3(&u,&t); ge_p3_to_cached(&Ai[1],&u); 62 ge_add(&t,&A2,&Ai[1]); ge_p1p1_to_p3(&u,&t); ge_p3_to_cached(&Ai[2],&u); 63 ge_add(&t,&A2,&Ai[2]); ge_p1p1_to_p3(&u,&t); ge_p3_to_cached(&Ai[3],&u); 64 ge_add(&t,&A2,&Ai[3]); ge_p1p1_to_p3(&u,&t); ge_p3_to_cached(&Ai[4],&u); 65 ge_add(&t,&A2,&Ai[4]); ge_p1p1_to_p3(&u,&t); ge_p3_to_cached(&Ai[5],&u); 66 ge_add(&t,&A2,&Ai[5]); ge_p1p1_to_p3(&u,&t); ge_p3_to_cached(&Ai[6],&u); 67 ge_add(&t,&A2,&Ai[6]); ge_p1p1_to_p3(&u,&t); ge_p3_to_cached(&Ai[7],&u); 68 69 ge_p2_0(r); 70 71 for (i = 255;i >= 0;--i) { 72 if (aslide[i] || bslide[i]) break; 73 } 74 75 for (;i >= 0;--i) { 76 ge_p2_dbl(&t,r); 77 78 if (aslide[i] > 0) { 79 ge_p1p1_to_p3(&u,&t); 80 ge_add(&t,&u,&Ai[aslide[i]/2]); 81 } else if (aslide[i] < 0) { 82 ge_p1p1_to_p3(&u,&t); 83 ge_sub(&t,&u,&Ai[(-aslide[i])/2]); 84 } 85 86 if (bslide[i] > 0) { 87 ge_p1p1_to_p3(&u,&t); 88 ge_madd(&t,&u,&Bi[bslide[i]/2]); 89 } else if (bslide[i] < 0) { 90 ge_p1p1_to_p3(&u,&t); 91 ge_msub(&t,&u,&Bi[(-bslide[i])/2]); 92 } 93 94 ge_p1p1_to_p2(r,&t); 95 } 96 }