Speed tweaks for signatures, etc.

This commit is contained in:
Adam Ierymenko 2018-03-12 16:16:20 -07:00
parent b4e2547052
commit 610e594a50
3 changed files with 1287 additions and 1260 deletions

View file

@ -20,7 +20,7 @@ Derived from public domain code by D. J. Bernstein.
#pragma warning(disable: 4146) #pragma warning(disable: 4146)
#endif #endif
namespace ZeroTier { namespace {
////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////
@ -31,7 +31,7 @@ namespace ZeroTier {
#define crypto_uint64 uint64_t #define crypto_uint64 uint64_t
#define crypto_hash_sha512_BYTES 64 #define crypto_hash_sha512_BYTES 64
static inline void add(unsigned int out[32],const unsigned int a[32],const unsigned int b[32]) void add(unsigned int out[32],const unsigned int a[32],const unsigned int b[32])
{ {
unsigned int j; unsigned int j;
unsigned int u; unsigned int u;
@ -40,7 +40,7 @@ static inline void add(unsigned int out[32],const unsigned int a[32],const unsig
u += a[31] + b[31]; out[31] = u; u += a[31] + b[31]; out[31] = u;
} }
static inline void sub(unsigned int out[32],const unsigned int a[32],const unsigned int b[32]) void sub(unsigned int out[32],const unsigned int a[32],const unsigned int b[32])
{ {
unsigned int j; unsigned int j;
unsigned int u; unsigned int u;
@ -54,7 +54,7 @@ static inline void sub(unsigned int out[32],const unsigned int a[32],const unsig
out[31] = u; out[31] = u;
} }
static inline void squeeze(unsigned int a[32]) void squeeze(unsigned int a[32])
{ {
unsigned int j; unsigned int j;
unsigned int u; unsigned int u;
@ -70,7 +70,7 @@ static const unsigned int minusp[32] = {
19, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 128 19, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 128
} ; } ;
static inline void freeze(unsigned int a[32]) void freeze(unsigned int a[32])
{ {
unsigned int aorig[32]; unsigned int aorig[32];
unsigned int j; unsigned int j;
@ -82,7 +82,7 @@ static inline void freeze(unsigned int a[32])
for (j = 0;j < 32;++j) a[j] ^= negative & (aorig[j] ^ a[j]); for (j = 0;j < 32;++j) a[j] ^= negative & (aorig[j] ^ a[j]);
} }
static inline void mult(unsigned int out[32],const unsigned int a[32],const unsigned int b[32]) void mult(unsigned int out[32],const unsigned int a[32],const unsigned int b[32])
{ {
unsigned int i; unsigned int i;
unsigned int j; unsigned int j;
@ -97,7 +97,7 @@ static inline void mult(unsigned int out[32],const unsigned int a[32],const unsi
squeeze(out); squeeze(out);
} }
static inline void mult121665(unsigned int out[32],const unsigned int a[32]) void mult121665(unsigned int out[32],const unsigned int a[32])
{ {
unsigned int j; unsigned int j;
unsigned int u; unsigned int u;
@ -110,7 +110,7 @@ static inline void mult121665(unsigned int out[32],const unsigned int a[32])
u += out[j]; out[j] = u; u += out[j]; out[j] = u;
} }
static inline void square(unsigned int out[32],const unsigned int a[32]) void square(unsigned int out[32],const unsigned int a[32])
{ {
unsigned int i; unsigned int i;
unsigned int j; unsigned int j;
@ -130,7 +130,7 @@ static inline void square(unsigned int out[32],const unsigned int a[32])
squeeze(out); squeeze(out);
} }
static inline void select(unsigned int p[64],unsigned int q[64],const unsigned int r[64],const unsigned int s[64],unsigned int b) void select(unsigned int p[64],unsigned int q[64],const unsigned int r[64],const unsigned int s[64],unsigned int b)
{ {
unsigned int j; unsigned int j;
unsigned int t; unsigned int t;
@ -268,7 +268,7 @@ static void recip(unsigned int out[32],const unsigned int z[32])
/* 2^255 - 21 */ mult(out,t1,z11); /* 2^255 - 21 */ mult(out,t1,z11);
} }
static inline int crypto_scalarmult(unsigned char *q,const unsigned char *n,const unsigned char *p) int crypto_scalarmult(unsigned char *q,const unsigned char *n,const unsigned char *p)
{ {
unsigned int work[96]; unsigned int work[96];
unsigned char e[32]; unsigned char e[32];
@ -287,7 +287,7 @@ static inline int crypto_scalarmult(unsigned char *q,const unsigned char *n,cons
} }
static const unsigned char base[32] = {9}; static const unsigned char base[32] = {9};
static inline int crypto_scalarmult_base(unsigned char *q,const unsigned char *n) int crypto_scalarmult_base(unsigned char *q,const unsigned char *n)
{ {
return crypto_scalarmult(q,n,base); return crypto_scalarmult(q,n,base);
} }
@ -308,7 +308,7 @@ fe25519;
static void fe25519_sub(fe25519 *r, const fe25519 *x, const fe25519 *y); static void fe25519_sub(fe25519 *r, const fe25519 *x, const fe25519 *y);
static inline crypto_uint32 equal(crypto_uint32 a,crypto_uint32 b) /* 16-bit inputs */ crypto_uint32 equal(crypto_uint32 a,crypto_uint32 b) /* 16-bit inputs */
{ {
crypto_uint32 x = a ^ b; /* 0: yes; 1..65535: no */ crypto_uint32 x = a ^ b; /* 0: yes; 1..65535: no */
x -= 1; /* 4294967295: yes; 0..65534: no */ x -= 1; /* 4294967295: yes; 0..65534: no */
@ -316,7 +316,7 @@ static inline crypto_uint32 equal(crypto_uint32 a,crypto_uint32 b) /* 16-bit inp
return x; return x;
} }
static inline crypto_uint32 ge(crypto_uint32 a,crypto_uint32 b) /* 16-bit inputs */ crypto_uint32 ge(crypto_uint32 a,crypto_uint32 b) /* 16-bit inputs */
{ {
unsigned int x = a; unsigned int x = a;
x -= (unsigned int) b; /* 0..65535: yes; 4294901761..4294967295: no */ x -= (unsigned int) b; /* 0..65535: yes; 4294901761..4294967295: no */
@ -325,17 +325,17 @@ static inline crypto_uint32 ge(crypto_uint32 a,crypto_uint32 b) /* 16-bit inputs
return x; return x;
} }
static inline crypto_uint32 times19(crypto_uint32 a) crypto_uint32 times19(crypto_uint32 a)
{ {
return (a << 4) + (a << 1) + a; return (a << 4) + (a << 1) + a;
} }
static inline crypto_uint32 times38(crypto_uint32 a) crypto_uint32 times38(crypto_uint32 a)
{ {
return (a << 5) + (a << 2) + (a << 1); return (a << 5) + (a << 2) + (a << 1);
} }
static inline void reduce_add_sub(fe25519 *r) void reduce_add_sub(fe25519 *r)
{ {
crypto_uint32 t; crypto_uint32 t;
int i,rep; int i,rep;
@ -355,7 +355,7 @@ static inline void reduce_add_sub(fe25519 *r)
} }
} }
static inline void reduce_mul(fe25519 *r) void reduce_mul(fe25519 *r)
{ {
crypto_uint32 t; crypto_uint32 t;
int i,rep; int i,rep;
@ -376,7 +376,7 @@ static inline void reduce_mul(fe25519 *r)
} }
/* reduction modulo 2^255-19 */ /* reduction modulo 2^255-19 */
static inline void fe25519_freeze(fe25519 *r) void fe25519_freeze(fe25519 *r)
{ {
int i; int i;
crypto_uint32 m = equal(r->v[31],127); crypto_uint32 m = equal(r->v[31],127);
@ -392,7 +392,7 @@ static inline void fe25519_freeze(fe25519 *r)
r->v[0] -= m&237; r->v[0] -= m&237;
} }
static inline void fe25519_unpack(fe25519 *r, const unsigned char x[32]) void fe25519_unpack(fe25519 *r, const unsigned char x[32])
{ {
int i; int i;
for(i=0;i<32;i++) r->v[i] = x[i]; for(i=0;i<32;i++) r->v[i] = x[i];
@ -400,7 +400,7 @@ static inline void fe25519_unpack(fe25519 *r, const unsigned char x[32])
} }
/* Assumes input x being reduced below 2^255 */ /* Assumes input x being reduced below 2^255 */
static inline void fe25519_pack(unsigned char r[32], const fe25519 *x) void fe25519_pack(unsigned char r[32], const fe25519 *x)
{ {
int i; int i;
fe25519 y = *x; fe25519 y = *x;
@ -409,7 +409,7 @@ static inline void fe25519_pack(unsigned char r[32], const fe25519 *x)
r[i] = y.v[i]; r[i] = y.v[i];
} }
static inline int fe25519_iseq_vartime(const fe25519 *x, const fe25519 *y) int fe25519_iseq_vartime(const fe25519 *x, const fe25519 *y)
{ {
int i; int i;
fe25519 t1 = *x; fe25519 t1 = *x;
@ -421,7 +421,7 @@ static inline int fe25519_iseq_vartime(const fe25519 *x, const fe25519 *y)
return 1; return 1;
} }
static inline void fe25519_cmov(fe25519 *r, const fe25519 *x, unsigned char b) void fe25519_cmov(fe25519 *r, const fe25519 *x, unsigned char b)
{ {
int i; int i;
crypto_uint32 mask = b; crypto_uint32 mask = b;
@ -429,27 +429,27 @@ static inline void fe25519_cmov(fe25519 *r, const fe25519 *x, unsigned char b)
for(i=0;i<32;i++) r->v[i] ^= mask & (x->v[i] ^ r->v[i]); for(i=0;i<32;i++) r->v[i] ^= mask & (x->v[i] ^ r->v[i]);
} }
static inline unsigned char fe25519_getparity(const fe25519 *x) unsigned char fe25519_getparity(const fe25519 *x)
{ {
fe25519 t = *x; fe25519 t = *x;
fe25519_freeze(&t); fe25519_freeze(&t);
return t.v[0] & 1; return t.v[0] & 1;
} }
static inline void fe25519_setone(fe25519 *r) void fe25519_setone(fe25519 *r)
{ {
int i; int i;
r->v[0] = 1; r->v[0] = 1;
for(i=1;i<32;i++) r->v[i]=0; for(i=1;i<32;i++) r->v[i]=0;
} }
static inline void fe25519_setzero(fe25519 *r) void fe25519_setzero(fe25519 *r)
{ {
int i; int i;
for(i=0;i<32;i++) r->v[i]=0; for(i=0;i<32;i++) r->v[i]=0;
} }
static inline void fe25519_neg(fe25519 *r, const fe25519 *x) void fe25519_neg(fe25519 *r, const fe25519 *x)
{ {
fe25519 t; fe25519 t;
int i; int i;
@ -458,14 +458,14 @@ static inline void fe25519_neg(fe25519 *r, const fe25519 *x)
fe25519_sub(r, r, &t); fe25519_sub(r, r, &t);
} }
static inline void fe25519_add(fe25519 *r, const fe25519 *x, const fe25519 *y) void fe25519_add(fe25519 *r, const fe25519 *x, const fe25519 *y)
{ {
int i; int i;
for(i=0;i<32;i++) r->v[i] = x->v[i] + y->v[i]; for(i=0;i<32;i++) r->v[i] = x->v[i] + y->v[i];
reduce_add_sub(r); reduce_add_sub(r);
} }
static inline void fe25519_sub(fe25519 *r, const fe25519 *x, const fe25519 *y) void fe25519_sub(fe25519 *r, const fe25519 *x, const fe25519 *y)
{ {
int i; int i;
crypto_uint32 t[32]; crypto_uint32 t[32];
@ -476,7 +476,7 @@ static inline void fe25519_sub(fe25519 *r, const fe25519 *x, const fe25519 *y)
reduce_add_sub(r); reduce_add_sub(r);
} }
static inline void fe25519_mul(fe25519 *r, const fe25519 *x, const fe25519 *y) void fe25519_mul(fe25519 *r, const fe25519 *x, const fe25519 *y)
{ {
int i,j; int i,j;
crypto_uint32 t[63]; crypto_uint32 t[63];
@ -493,12 +493,12 @@ static inline void fe25519_mul(fe25519 *r, const fe25519 *x, const fe25519 *y)
reduce_mul(r); reduce_mul(r);
} }
static inline void fe25519_square(fe25519 *r, const fe25519 *x) void fe25519_square(fe25519 *r, const fe25519 *x)
{ {
fe25519_mul(r, x, x); fe25519_mul(r, x, x);
} }
static void fe25519_invert(fe25519 *r, const fe25519 *x) void fe25519_invert(fe25519 *r, const fe25519 *x)
{ {
fe25519 z2; fe25519 z2;
fe25519 z9; fe25519 z9;
@ -565,7 +565,7 @@ static void fe25519_invert(fe25519 *r, const fe25519 *x)
/* 2^255 - 21 */ fe25519_mul(r,&t1,&z11); /* 2^255 - 21 */ fe25519_mul(r,&t1,&z11);
} }
static void fe25519_pow2523(fe25519 *r, const fe25519 *x) void fe25519_pow2523(fe25519 *r, const fe25519 *x)
{ {
fe25519 z2; fe25519 z2;
fe25519 z9; fe25519 z9;
@ -637,7 +637,7 @@ static const crypto_uint32 m[32] = {0xED, 0xD3, 0xF5, 0x5C, 0x1A, 0x63, 0x12, 0x
static const crypto_uint32 mu[33] = {0x1B, 0x13, 0x2C, 0x0A, 0xA3, 0xE5, 0x9C, 0xED, 0xA7, 0x29, 0x63, 0x08, 0x5D, 0x21, 0x06, 0x21, static const crypto_uint32 mu[33] = {0x1B, 0x13, 0x2C, 0x0A, 0xA3, 0xE5, 0x9C, 0xED, 0xA7, 0x29, 0x63, 0x08, 0x5D, 0x21, 0x06, 0x21,
0xEB, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F}; 0xEB, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0F};
static inline crypto_uint32 lt(crypto_uint32 a,crypto_uint32 b) /* 16-bit inputs */ crypto_uint32 lt(crypto_uint32 a,crypto_uint32 b) /* 16-bit inputs */
{ {
unsigned int x = a; unsigned int x = a;
x -= (unsigned int) b; /* 0..65535: no; 4294901761..4294967295: yes */ x -= (unsigned int) b; /* 0..65535: no; 4294901761..4294967295: yes */
@ -646,7 +646,7 @@ static inline crypto_uint32 lt(crypto_uint32 a,crypto_uint32 b) /* 16-bit inputs
} }
/* Reduce coefficients of r before calling reduce_add_sub */ /* Reduce coefficients of r before calling reduce_add_sub */
static inline void reduce_add_sub(sc25519 *r) void reduce_add_sub(sc25519 *r)
{ {
crypto_uint32 pb = 0; crypto_uint32 pb = 0;
crypto_uint32 b; crypto_uint32 b;
@ -667,7 +667,7 @@ static inline void reduce_add_sub(sc25519 *r)
} }
/* Reduce coefficients of x before calling barrett_reduce */ /* Reduce coefficients of x before calling barrett_reduce */
static inline void barrett_reduce(sc25519 *r, const crypto_uint32 x[64]) void barrett_reduce(sc25519 *r, const crypto_uint32 x[64])
{ {
/* See HAC, Alg. 14.42 */ /* See HAC, Alg. 14.42 */
int i,j; int i,j;
@ -718,7 +718,7 @@ static inline void barrett_reduce(sc25519 *r, const crypto_uint32 x[64])
reduce_add_sub(r); reduce_add_sub(r);
} }
static inline void sc25519_from32bytes(sc25519 *r, const unsigned char x[32]) void sc25519_from32bytes(sc25519 *r, const unsigned char x[32])
{ {
int i; int i;
crypto_uint32 t[64]; crypto_uint32 t[64];
@ -727,7 +727,7 @@ static inline void sc25519_from32bytes(sc25519 *r, const unsigned char x[32])
barrett_reduce(r, t); barrett_reduce(r, t);
} }
static inline void sc25519_from64bytes(sc25519 *r, const unsigned char x[64]) void sc25519_from64bytes(sc25519 *r, const unsigned char x[64])
{ {
int i; int i;
crypto_uint32 t[64]; crypto_uint32 t[64];
@ -735,13 +735,13 @@ static inline void sc25519_from64bytes(sc25519 *r, const unsigned char x[64])
barrett_reduce(r, t); barrett_reduce(r, t);
} }
static inline void sc25519_to32bytes(unsigned char r[32], const sc25519 *x) void sc25519_to32bytes(unsigned char r[32], const sc25519 *x)
{ {
int i; int i;
for(i=0;i<32;i++) r[i] = x->v[i]; for(i=0;i<32;i++) r[i] = x->v[i];
} }
static inline void sc25519_add(sc25519 *r, const sc25519 *x, const sc25519 *y) void sc25519_add(sc25519 *r, const sc25519 *x, const sc25519 *y)
{ {
int i, carry; int i, carry;
for(i=0;i<32;i++) r->v[i] = x->v[i] + y->v[i]; for(i=0;i<32;i++) r->v[i] = x->v[i] + y->v[i];
@ -754,7 +754,7 @@ static inline void sc25519_add(sc25519 *r, const sc25519 *x, const sc25519 *y)
reduce_add_sub(r); reduce_add_sub(r);
} }
static inline void sc25519_mul(sc25519 *r, const sc25519 *x, const sc25519 *y) void sc25519_mul(sc25519 *r, const sc25519 *x, const sc25519 *y)
{ {
int i,j,carry; int i,j,carry;
crypto_uint32 t[64]; crypto_uint32 t[64];
@ -775,7 +775,7 @@ static inline void sc25519_mul(sc25519 *r, const sc25519 *x, const sc25519 *y)
barrett_reduce(r, t); barrett_reduce(r, t);
} }
static inline void sc25519_window3(signed char r[85], const sc25519 *s) void sc25519_window3(signed char r[85], const sc25519 *s)
{ {
char carry; char carry;
int i; int i;
@ -812,7 +812,7 @@ static inline void sc25519_window3(signed char r[85], const sc25519 *s)
r[84] += carry; r[84] += carry;
} }
static inline void sc25519_2interleave2(unsigned char r[127], const sc25519 *s1, const sc25519 *s2) void sc25519_2interleave2(unsigned char r[127], const sc25519 *s1, const sc25519 *s2)
{ {
int i; int i;
for(i=0;i<31;i++) for(i=0;i<31;i++)
@ -1733,27 +1733,27 @@ static const ge25519_aff ge25519_base_multiples_affine[425] = {
{{0x69, 0x3e, 0x47, 0x97, 0x2c, 0xaf, 0x52, 0x7c, 0x78, 0x83, 0xad, 0x1b, 0x39, 0x82, 0x2f, 0x02, 0x6f, 0x47, 0xdb, 0x2a, 0xb0, 0xe1, 0x91, 0x99, 0x55, 0xb8, 0x99, 0x3a, 0xa0, 0x44, 0x11, 0x51}}} {{0x69, 0x3e, 0x47, 0x97, 0x2c, 0xaf, 0x52, 0x7c, 0x78, 0x83, 0xad, 0x1b, 0x39, 0x82, 0x2f, 0x02, 0x6f, 0x47, 0xdb, 0x2a, 0xb0, 0xe1, 0x91, 0x99, 0x55, 0xb8, 0x99, 0x3a, 0xa0, 0x44, 0x11, 0x51}}}
}; };
static inline void p1p1_to_p2(ge25519_p2 *r, const ge25519_p1p1 *p) void p1p1_to_p2(ge25519_p2 *r, const ge25519_p1p1 *p)
{ {
fe25519_mul(&r->x, &p->x, &p->t); fe25519_mul(&r->x, &p->x, &p->t);
fe25519_mul(&r->y, &p->y, &p->z); fe25519_mul(&r->y, &p->y, &p->z);
fe25519_mul(&r->z, &p->z, &p->t); fe25519_mul(&r->z, &p->z, &p->t);
} }
static inline void p1p1_to_p2_2(ge25519_p3 *r, const ge25519_p1p1 *p) void p1p1_to_p2_2(ge25519_p3 *r, const ge25519_p1p1 *p)
{ {
fe25519_mul(&r->x, &p->x, &p->t); fe25519_mul(&r->x, &p->x, &p->t);
fe25519_mul(&r->y, &p->y, &p->z); fe25519_mul(&r->y, &p->y, &p->z);
fe25519_mul(&r->z, &p->z, &p->t); fe25519_mul(&r->z, &p->z, &p->t);
} }
static inline void p1p1_to_p3(ge25519_p3 *r, const ge25519_p1p1 *p) void p1p1_to_p3(ge25519_p3 *r, const ge25519_p1p1 *p)
{ {
p1p1_to_p2_2(r, p); p1p1_to_p2_2(r, p);
fe25519_mul(&r->t, &p->x, &p->y); fe25519_mul(&r->t, &p->x, &p->y);
} }
static void ge25519_mixadd2(ge25519_p3 *r, const ge25519_aff *q) void ge25519_mixadd2(ge25519_p3 *r, const ge25519_aff *q)
{ {
fe25519 a,b,t1,t2,c,d,e,f,g,h,qt; fe25519 a,b,t1,t2,c,d,e,f,g,h,qt;
fe25519_mul(&qt, &q->x, &q->y); fe25519_mul(&qt, &q->x, &q->y);
@ -1776,7 +1776,7 @@ static void ge25519_mixadd2(ge25519_p3 *r, const ge25519_aff *q)
fe25519_mul(&r->t, &e, &h); fe25519_mul(&r->t, &e, &h);
} }
static void add_p1p1(ge25519_p1p1 *r, const ge25519_p3 *p, const ge25519_p3 *q) void add_p1p1(ge25519_p1p1 *r, const ge25519_p3 *p, const ge25519_p3 *q)
{ {
fe25519 a, b, c, d, t; fe25519 a, b, c, d, t;
@ -1797,7 +1797,7 @@ static void add_p1p1(ge25519_p1p1 *r, const ge25519_p3 *p, const ge25519_p3 *q)
} }
/* See http://www.hyperelliptic.org/EFD/g1p/auto-twisted-extended-1.html#doubling-dbl-2008-hwcd */ /* See http://www.hyperelliptic.org/EFD/g1p/auto-twisted-extended-1.html#doubling-dbl-2008-hwcd */
static void dbl_p1p1(ge25519_p1p1 *r, const ge25519_p2 *p) void dbl_p1p1(ge25519_p1p1 *r, const ge25519_p2 *p)
{ {
fe25519 a,b,c,d; fe25519 a,b,c,d;
fe25519_square(&a, &p->x); fe25519_square(&a, &p->x);
@ -1816,13 +1816,13 @@ static void dbl_p1p1(ge25519_p1p1 *r, const ge25519_p2 *p)
} }
/* Constant-time version of: if(b) r = p */ /* Constant-time version of: if(b) r = p */
static inline void cmov_aff(ge25519_aff *r, const ge25519_aff *p, unsigned char b) void cmov_aff(ge25519_aff *r, const ge25519_aff *p, unsigned char b)
{ {
fe25519_cmov(&r->x, &p->x, b); fe25519_cmov(&r->x, &p->x, b);
fe25519_cmov(&r->y, &p->y, b); fe25519_cmov(&r->y, &p->y, b);
} }
static inline unsigned char equal(signed char b,signed char c) unsigned char equal(signed char b,signed char c)
{ {
unsigned char ub = b; unsigned char ub = b;
unsigned char uc = c; unsigned char uc = c;
@ -1833,14 +1833,14 @@ static inline unsigned char equal(signed char b,signed char c)
return (unsigned char)y; return (unsigned char)y;
} }
static inline unsigned char negative(signed char b) unsigned char negative(signed char b)
{ {
unsigned long long x = b; /* 18446744073709551361..18446744073709551615: yes; 0..255: no */ unsigned long long x = b; /* 18446744073709551361..18446744073709551615: yes; 0..255: no */
x >>= 63; /* 1: yes; 0: no */ x >>= 63; /* 1: yes; 0: no */
return (unsigned char)x; return (unsigned char)x;
} }
static inline void choose_t(ge25519_aff *t, unsigned long long pos, signed char b) void choose_t(ge25519_aff *t, unsigned long long pos, signed char b)
{ {
/* constant time */ /* constant time */
fe25519 v; fe25519 v;
@ -1853,7 +1853,7 @@ static inline void choose_t(ge25519_aff *t, unsigned long long pos, signed char
fe25519_cmov(&t->x, &v, negative(b)); fe25519_cmov(&t->x, &v, negative(b));
} }
static inline void setneutral(ge25519 *r) void setneutral(ge25519 *r)
{ {
fe25519_setzero(&r->x); fe25519_setzero(&r->x);
fe25519_setone(&r->y); fe25519_setone(&r->y);
@ -1862,7 +1862,7 @@ static inline void setneutral(ge25519 *r)
} }
/* return 0 on success, -1 otherwise */ /* return 0 on success, -1 otherwise */
static int ge25519_unpackneg_vartime(ge25519_p3 *r, const unsigned char p[32]) int ge25519_unpackneg_vartime(ge25519_p3 *r, const unsigned char p[32])
{ {
unsigned char par; unsigned char par;
fe25519 t, chk, num, den, den2, den4, den6; fe25519 t, chk, num, den, den2, den4, den6;
@ -1909,7 +1909,7 @@ static int ge25519_unpackneg_vartime(ge25519_p3 *r, const unsigned char p[32])
return 0; return 0;
} }
static inline void ge25519_pack(unsigned char r[32], const ge25519_p3 *p) void ge25519_pack(unsigned char r[32], const ge25519_p3 *p)
{ {
fe25519 tx, ty, zi; fe25519 tx, ty, zi;
fe25519_invert(&zi, &p->z); fe25519_invert(&zi, &p->z);
@ -1920,7 +1920,7 @@ static inline void ge25519_pack(unsigned char r[32], const ge25519_p3 *p)
} }
/* computes [s1]p1 + [s2]p2 */ /* computes [s1]p1 + [s2]p2 */
static void ge25519_double_scalarmult_vartime(ge25519_p3 *r, const ge25519_p3 *p1, const sc25519 *s1, const ge25519_p3 *p2, const sc25519 *s2) void ge25519_double_scalarmult_vartime(ge25519_p3 *r, const ge25519_p3 *p1, const sc25519 *s1, const ge25519_p3 *p2, const sc25519 *s2)
{ {
ge25519_p1p1 tp1p1; ge25519_p1p1 tp1p1;
ge25519_p3 pre[16]; ge25519_p3 pre[16];
@ -1965,7 +1965,7 @@ static void ge25519_double_scalarmult_vartime(ge25519_p3 *r, const ge25519_p3 *p
} }
} }
static inline void ge25519_scalarmult_base(ge25519_p3 *r, const sc25519 *s) void ge25519_scalarmult_base(ge25519_p3 *r, const sc25519 *s)
{ {
signed char b[85]; signed char b[85];
int i; int i;
@ -1982,7 +1982,7 @@ static inline void ge25519_scalarmult_base(ge25519_p3 *r, const sc25519 *s)
} }
} }
static inline void get_hram(unsigned char *hram, const unsigned char *sm, const unsigned char *pk, unsigned char *playground, unsigned long long smlen) void get_hram(unsigned char *hram, const unsigned char *sm, const unsigned char *pk, unsigned char *playground, unsigned long long smlen)
{ {
unsigned long long i; unsigned long long i;
@ -1991,12 +1991,16 @@ static inline void get_hram(unsigned char *hram, const unsigned char *sm, const
for (i = 64;i < smlen;++i) playground[i] = sm[i]; for (i = 64;i < smlen;++i) playground[i] = sm[i];
//crypto_hash_sha512(hram,playground,smlen); //crypto_hash_sha512(hram,playground,smlen);
SHA512::hash(hram,playground,(unsigned int)smlen); ZeroTier::SHA512::hash(hram,playground,(unsigned int)smlen);
} }
////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////
} // anonymous namespace
namespace ZeroTier {
void C25519::agree(const C25519::Private &mine,const C25519::Public &their,void *keybuf,unsigned int keylen) void C25519::agree(const C25519::Private &mine,const C25519::Public &their,void *keybuf,unsigned int keylen)
{ {
unsigned char rawkey[32]; unsigned char rawkey[32];
@ -2038,7 +2042,6 @@ void C25519::sign(const C25519::Private &myPrivate,const C25519::Public &myPubli
sig[64 + i] = digest[i]; sig[64 + i] = digest[i];
SHA512::hash(hmg,sig + 32,64); SHA512::hash(hmg,sig + 32,64);
//crypto_hash_sha512(hmg, sm+32, mlen+32); /* Generate k as h(extsk[32],...,extsk[63],m) */
/* Computation of R */ /* Computation of R */
sc25519_from64bytes(&sck, hmg); sc25519_from64bytes(&sck, hmg);

View file

@ -14,6 +14,22 @@ Public domain.
#include "SHA512.hpp" #include "SHA512.hpp"
#include "Utils.hpp" #include "Utils.hpp"
#ifdef __APPLE__
#include <CommonCrypto/CommonDigest.h>
#define ZT_HAVE_NATIVE_SHA512
namespace ZeroTier {
void SHA512::hash(void *digest,const void *data,unsigned int len)
{
CC_SHA512_CTX ctx;
CC_SHA512_Init(&ctx);
CC_SHA512_Update(&ctx,data,len);
CC_SHA512_Final(reinterpret_cast<unsigned char *>(digest),&ctx);
}
}
#endif
#ifndef ZT_HAVE_NATIVE_SHA512
namespace ZeroTier { namespace ZeroTier {
#define uint64 uint64_t #define uint64 uint64_t
@ -276,9 +292,6 @@ static const unsigned char iv[64] = {
0x5b,0xe0,0xcd,0x19,0x13,0x7e,0x21,0x79 0x5b,0xe0,0xcd,0x19,0x13,0x7e,0x21,0x79
}; };
//////////////////////////////////////////////////////////////////////////////
//////////////////////////////////////////////////////////////////////////////
void SHA512::hash(void *digest,const void *data,unsigned int len) void SHA512::hash(void *digest,const void *data,unsigned int len)
{ {
unsigned char h[64]; unsigned char h[64];
@ -329,3 +342,5 @@ void SHA512::hash(void *digest,const void *data,unsigned int len)
} }
} // namespace ZeroTier } // namespace ZeroTier
#endif

View file

@ -376,11 +376,11 @@ static int testCrypto()
C25519::Pair bp[8]; C25519::Pair bp[8];
for(int k=0;k<8;++k) for(int k=0;k<8;++k)
bp[k] = C25519::generate(); bp[k] = C25519::generate();
const uint64_t st = OSUtils::now(); uint64_t st = OSUtils::now();
for(unsigned int k=0;k<50;++k) { for(unsigned int k=0;k<50;++k) {
C25519::agree(bp[~k & 7],bp[k & 7].pub,buf1,64); C25519::agree(bp[~k & 7],bp[k & 7].pub,buf1,64);
} }
const uint64_t et = OSUtils::now(); uint64_t et = OSUtils::now();
std::cout << ((double)(et - st) / 50.0) << "ms per agreement." << std::endl; std::cout << ((double)(et - st) / 50.0) << "ms per agreement." << std::endl;
std::cout << "[crypto] Testing Ed25519 ECC signatures... "; std::cout.flush(); std::cout << "[crypto] Testing Ed25519 ECC signatures... "; std::cout.flush();
@ -419,6 +419,15 @@ static int testCrypto()
} }
std::cout << "PASS" << std::endl; std::cout << "PASS" << std::endl;
std::cout << "[crypto] Benchmarking Ed25519 ECC signatures... "; std::cout.flush();
st = OSUtils::now();
for(int k=0;k<1000;++k) {
C25519::Signature sig;
C25519::sign(didntSign.priv,didntSign.pub,buf1,sizeof(buf1),sig.data);
}
et = OSUtils::now();
std::cout << ((double)(et - st) / 50.0) << "ms per signature." << std::endl;
return 0; return 0;
} }