mirror of https://github.com/ntop/n2n.git
Logan oos Even
3 years ago
committed by
GitHub
22 changed files with 1622 additions and 306 deletions
@ -0,0 +1,43 @@ |
|||||
|
/*
|
||||
|
* (C) 2007-21 - ntop.org and contributors |
||||
|
* |
||||
|
* This program is free software; you can redistribute it and/or modify |
||||
|
* it under the terms of the GNU General Public License as published by |
||||
|
* the Free Software Foundation; either version 3 of the License, or |
||||
|
* (at your option) any later version. |
||||
|
* |
||||
|
* This program is distributed in the hope that it will be useful, |
||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||||
|
* GNU General Public License for more details. |
||||
|
* |
||||
|
* You should have received a copy of the GNU General Public License |
||||
|
* along with this program; if not, see <http://www.gnu.org/licenses/>
|
||||
|
* |
||||
|
*/ |
||||
|
|
||||
|
|
||||
|
#include "n2n.h" |
||||
|
|
||||
|
|
||||
|
#ifndef AUTH_H |
||||
|
#define AUTH_H |
||||
|
|
||||
|
|
||||
|
int bin_to_ascii (uint8_t *out, uint8_t *in, size_t in_len); |
||||
|
|
||||
|
int ascii_to_bin (uint8_t *out, uint8_t *in); |
||||
|
|
||||
|
int generate_private_key(n2n_private_public_key_t key, uint8_t *in); |
||||
|
|
||||
|
int generate_public_key (n2n_private_public_key_t pub, n2n_private_public_key_t prv); |
||||
|
|
||||
|
int generate_shared_secret (n2n_private_public_key_t shared, n2n_private_public_key_t prv, n2n_private_public_key_t pub); |
||||
|
|
||||
|
int bind_private_key_to_username (n2n_private_public_key_t prv, uint8_t *username); |
||||
|
|
||||
|
int calculate_dynamic_key (uint8_t out_key[N2N_AUTH_CHALLENGE_SIZE], |
||||
|
uint32_t key_time, n2n_community_t comm, n2n_community_t fed); |
||||
|
|
||||
|
|
||||
|
#endif |
@ -0,0 +1,20 @@ |
|||||
|
/**
|
||||
|
* (C) 2007-21 - ntop.org and contributors |
||||
|
* |
||||
|
* This program is free software; you can redistribute it and/or modify |
||||
|
* it under the terms of the GNU General Public License as published by |
||||
|
* the Free Software Foundation; either version 3 of the License, or |
||||
|
* (at your option) any later version. |
||||
|
* |
||||
|
* This program is distributed in the hope that it will be useful, |
||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||||
|
* GNU General Public License for more details. |
||||
|
* |
||||
|
* You should have received a copy of the GNU General Public License |
||||
|
* along with this program; if not see see <http://www.gnu.org/licenses/>
|
||||
|
* |
||||
|
*/ |
||||
|
|
||||
|
|
||||
|
void curve25519 (unsigned char *q, const unsigned char *n, const unsigned char *p); |
@ -0,0 +1,171 @@ |
|||||
|
/*
|
||||
|
* (C) 2007-21 - ntop.org and contributors |
||||
|
* |
||||
|
* This program is free software; you can redistribute it and/or modify |
||||
|
* it under the terms of the GNU General Public License as published by |
||||
|
* the Free Software Foundation; either version 3 of the License, or |
||||
|
* (at your option) any later version. |
||||
|
* |
||||
|
* This program is distributed in the hope that it will be useful, |
||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||||
|
* GNU General Public License for more details. |
||||
|
* |
||||
|
* You should have received a copy of the GNU General Public License |
||||
|
* along with this program; if not, see <http://www.gnu.org/licenses/>
|
||||
|
* |
||||
|
*/ |
||||
|
|
||||
|
|
||||
|
#include "auth.h" |
||||
|
|
||||
|
|
||||
|
// mapping six binary bits to printable ascii character
|
||||
|
static uint8_t b2a[64] = { 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, /* 0 ... 9, A ... F */ |
||||
|
0x47, 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f, 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, /* G ... V */ |
||||
|
0x57, 0x58, 0x59, 0x5a, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, 0x68, 0x69, 0x6a, 0x6b, 0x6c, /* W ... Z, a ... l */ |
||||
|
0x6d, 0x6e, 0x6f, 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78, 0x79, 0x7a, 0x2b, 0x2d }; /* m ... z, + , - */ |
||||
|
|
||||
|
// mapping ascii 0x30 ...0x7f back to 6 bit binary, invalids are mapped to 0xff
|
||||
|
static uint8_t a2b[256] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x3e, 0xff, 0x3f, 0xff, 0xff, /* 0x20 ... 0x2f */ |
||||
|
0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0xff, 0xff, 0x3e, 0xff, 0x3f, 0xff, /* 0x30 ... 0x3f */ |
||||
|
0xff, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, /* 0x40 ... 0x4f */ |
||||
|
0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20, 0x21, 0x22, 0x23, 0xff, 0xff, 0xff, 0xff, 0xff, /* 0x50 ... 0x5f */ |
||||
|
0xff, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 0x30, 0x31, 0x32, /* 0x60 ... 0x6f */ |
||||
|
0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0xff, 0xff, 0xff, 0xff, 0xff }; /* 0x70 ... 0x7f */ |
||||
|
|
||||
|
|
||||
|
int bin_to_ascii (uint8_t *out, uint8_t *in, size_t in_len) { |
||||
|
|
||||
|
// in buffer contains binary data of length in_len
|
||||
|
|
||||
|
// out buffer is already allocated and of size ceiling(in_len * 8 / 6) + 1
|
||||
|
// out buffer will be filled with a string including trailing 0x00
|
||||
|
|
||||
|
size_t bit_count = 0; |
||||
|
size_t out_count = 0; |
||||
|
uint8_t buf1, buf2; |
||||
|
|
||||
|
for(bit_count = 0; bit_count < 8 * in_len; bit_count += 6) { |
||||
|
buf1 = in[bit_count / 8]; |
||||
|
buf1 <<= bit_count % 8; |
||||
|
|
||||
|
buf2 = ((bit_count + 6) < (8 * in_len)) ? in[bit_count / 8 + 1] : 0; |
||||
|
buf2 >>= 8 - (bit_count % 8); |
||||
|
|
||||
|
buf1 |= buf2; |
||||
|
buf1 >>= 2; |
||||
|
|
||||
|
out[out_count++] = b2a[buf1]; |
||||
|
} |
||||
|
out[out_count] = 0; |
||||
|
|
||||
|
return 0; |
||||
|
} |
||||
|
|
||||
|
|
||||
|
int ascii_to_bin (uint8_t *out, uint8_t *in) { |
||||
|
|
||||
|
// in buffer contains 0x00-terminated string to be decoded
|
||||
|
|
||||
|
// out buffer will contain decoded binary data
|
||||
|
// out buffer is already allocated and of size floor(strlen(in) * 6 / 8)
|
||||
|
|
||||
|
size_t in_count, out_count, bit_count; |
||||
|
uint16_t buf = 0; |
||||
|
|
||||
|
bit_count = 0; |
||||
|
out_count = 0; |
||||
|
for(in_count = 0; in_count < strlen(in); in_count++) { |
||||
|
buf <<= 6; |
||||
|
|
||||
|
if((in[in_count] > 0x20) && (in[in_count] < 0x80)) { |
||||
|
if(a2b[in[in_count]] != 0xFF) { |
||||
|
buf |= a2b[in[in_count] - 0x20]; |
||||
|
} else { |
||||
|
traceEvent(TRACE_NORMAL, "ascii_to_bin encountered the unknown character '%c'", in[in_count]); |
||||
|
} |
||||
|
} else { |
||||
|
traceEvent(TRACE_WARNING, "ascii_to_bin encountered a completely out-of-range character"); |
||||
|
} |
||||
|
bit_count += 6; |
||||
|
|
||||
|
if(bit_count / 8) { |
||||
|
bit_count -= 8; |
||||
|
out[out_count++] = ((uint8_t)(buf >> bit_count)); |
||||
|
} |
||||
|
|
||||
|
} |
||||
|
|
||||
|
return 0; |
||||
|
} |
||||
|
|
||||
|
|
||||
|
int generate_private_key (n2n_private_public_key_t key, uint8_t *in) { |
||||
|
|
||||
|
// hash the 0-terminated string input twice to generate private key
|
||||
|
|
||||
|
pearson_hash_256(key, in, strlen(in)); |
||||
|
pearson_hash_256(key, key, sizeof(n2n_private_public_key_t)); |
||||
|
|
||||
|
return 0; |
||||
|
} |
||||
|
|
||||
|
|
||||
|
int generate_public_key (n2n_private_public_key_t pub, n2n_private_public_key_t prv) { |
||||
|
|
||||
|
// generator point '9' on curve
|
||||
|
static uint8_t gen[32] = { 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, 0, 9 }; |
||||
|
|
||||
|
curve25519(pub, prv, gen); |
||||
|
|
||||
|
return 0; |
||||
|
} |
||||
|
|
||||
|
|
||||
|
int generate_shared_secret (n2n_private_public_key_t shared, n2n_private_public_key_t prv, n2n_private_public_key_t pub) { |
||||
|
|
||||
|
curve25519(shared, prv, pub); |
||||
|
pearson_hash_256(shared, shared, sizeof(n2n_private_public_key_t)); |
||||
|
|
||||
|
return 0; |
||||
|
} |
||||
|
|
||||
|
|
||||
|
int bind_private_key_to_username (n2n_private_public_key_t prv, uint8_t *username) { |
||||
|
|
||||
|
uint8_t tmp[32]; |
||||
|
size_t i; |
||||
|
|
||||
|
pearson_hash_256(tmp, username, strlen(username)); |
||||
|
memxor(prv, tmp, sizeof(n2n_private_public_key_t)); |
||||
|
|
||||
|
return 0; |
||||
|
} |
||||
|
|
||||
|
|
||||
|
// calculate HASH( HASH³(time) ^ HASH²(comm) ^ HASH(fed) )
|
||||
|
int calculate_dynamic_key (uint8_t out_key[N2N_AUTH_CHALLENGE_SIZE], |
||||
|
uint32_t key_time, n2n_community_t comm, n2n_community_t fed) { |
||||
|
|
||||
|
uint8_t tmp[N2N_AUTH_CHALLENGE_SIZE]; |
||||
|
|
||||
|
memset(tmp, 0, N2N_AUTH_CHALLENGE_SIZE); |
||||
|
|
||||
|
// we know that N2N_AUTH_CHALLENGE_TYPE == 16, i.e. 128 bit that can take the hash value
|
||||
|
pearson_hash_128(out_key, (uint8_t*)&key_time, sizeof(key_time)); |
||||
|
pearson_hash_128(out_key, out_key, N2N_AUTH_CHALLENGE_SIZE); |
||||
|
pearson_hash_128(out_key, out_key, N2N_AUTH_CHALLENGE_SIZE); |
||||
|
|
||||
|
pearson_hash_128(tmp, comm, sizeof(n2n_community_t)); |
||||
|
pearson_hash_128(tmp, tmp, N2N_AUTH_CHALLENGE_SIZE); |
||||
|
memxor(out_key, tmp, N2N_AUTH_CHALLENGE_SIZE); |
||||
|
|
||||
|
pearson_hash_128(tmp, fed, sizeof(n2n_community_t)); |
||||
|
memxor(out_key, tmp, N2N_AUTH_CHALLENGE_SIZE); |
||||
|
|
||||
|
pearson_hash_128(out_key, out_key, N2N_AUTH_CHALLENGE_SIZE); |
||||
|
|
||||
|
return 0; |
||||
|
} |
@ -0,0 +1,357 @@ |
|||||
|
/**
|
||||
|
* (C) 2007-21 - ntop.org and contributors |
||||
|
* |
||||
|
* This program is free software; you can redistribute it and/or modify |
||||
|
* it under the terms of the GNU General Public License as published by |
||||
|
* the Free Software Foundation; either version 3 of the License, or |
||||
|
* (at your option) any later version. |
||||
|
* |
||||
|
* This program is distributed in the hope that it will be useful, |
||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||||
|
* GNU General Public License for more details. |
||||
|
* |
||||
|
* You should have received a copy of the GNU General Public License |
||||
|
* along with this program; if not see see <http://www.gnu.org/licenses/>
|
||||
|
* |
||||
|
*/ |
||||
|
|
||||
|
|
||||
|
/**
|
||||
|
* version 20081011 |
||||
|
* Matthew Dempsky |
||||
|
* Public domain. |
||||
|
* Derived from public domain code by D. J. Bernstein. |
||||
|
* 20140216 tweak: Mask top bit of point input. |
||||
|
* |
||||
|
*/ |
||||
|
|
||||
|
|
||||
|
static void add (unsigned int out[32], const unsigned int a[32], const unsigned int b[32]) { |
||||
|
|
||||
|
unsigned int j; |
||||
|
unsigned int u; |
||||
|
|
||||
|
u = 0; |
||||
|
for(j = 0; j < 31; ++j) { |
||||
|
u += a[j] + b[j]; |
||||
|
out[j] = u & 255; |
||||
|
u >>= 8; |
||||
|
} |
||||
|
u += a[31] + b[31]; |
||||
|
out[31] = u; |
||||
|
} |
||||
|
|
||||
|
|
||||
|
static void sub (unsigned int out[32], const unsigned int a[32], const unsigned int b[32]) { |
||||
|
|
||||
|
unsigned int j; |
||||
|
unsigned int u; |
||||
|
|
||||
|
u = 218; |
||||
|
for(j = 0; j < 31; ++j) { |
||||
|
u += a[j] + 65280 - b[j]; |
||||
|
out[j] = u & 255; |
||||
|
u >>= 8; |
||||
|
} |
||||
|
u += a[31] - b[31]; |
||||
|
out[31] = u; |
||||
|
} |
||||
|
|
||||
|
|
||||
|
static void squeeze (unsigned int a[32]) { |
||||
|
|
||||
|
unsigned int j; |
||||
|
unsigned int u; |
||||
|
|
||||
|
u = 0; |
||||
|
for(j = 0; j < 31; ++j) { |
||||
|
u += a[j]; |
||||
|
a[j] = u & 255; |
||||
|
u >>= 8; |
||||
|
} |
||||
|
u += a[31]; |
||||
|
a[31] = u & 127; |
||||
|
u = 19 * (u >> 7); |
||||
|
for(j = 0; j < 31; ++j) { |
||||
|
u += a[j]; |
||||
|
a[j] = u & 255; |
||||
|
u >>= 8; |
||||
|
} |
||||
|
u += a[31]; |
||||
|
a[31] = u; |
||||
|
} |
||||
|
|
||||
|
|
||||
|
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 }; |
||||
|
|
||||
|
|
||||
|
static void freeze (unsigned int a[32]) { |
||||
|
|
||||
|
unsigned int aorig[32]; |
||||
|
unsigned int j; |
||||
|
unsigned int negative; |
||||
|
|
||||
|
for(j = 0; j < 32; ++j) |
||||
|
aorig[j] = a[j]; |
||||
|
add(a, a, minusp); |
||||
|
negative = -((a[31] >> 7) & 1); |
||||
|
for(j = 0; j < 32; ++j) |
||||
|
a[j] ^= negative & (aorig[j] ^ a[j]); |
||||
|
} |
||||
|
|
||||
|
|
||||
|
static void mult (unsigned int out[32], const unsigned int a[32], const unsigned int b[32]) { |
||||
|
|
||||
|
unsigned int i; |
||||
|
unsigned int j; |
||||
|
unsigned int u; |
||||
|
|
||||
|
for(i = 0; i < 32; ++i) { |
||||
|
u = 0; |
||||
|
for(j = 0; j <= i; ++j) |
||||
|
u += a[j] * b[i - j]; |
||||
|
for(j = i + 1; j < 32; ++j) |
||||
|
u += 38 * a[j] * b[i + 32 - j]; |
||||
|
out[i] = u; |
||||
|
} |
||||
|
squeeze(out); |
||||
|
} |
||||
|
|
||||
|
|
||||
|
static void mult121665 (unsigned int out[32], const unsigned int a[32]) { |
||||
|
|
||||
|
unsigned int j; |
||||
|
unsigned int u; |
||||
|
|
||||
|
u = 0; |
||||
|
for(j = 0; j < 31; ++j) { |
||||
|
u += 121665 * a[j]; |
||||
|
out[j] = u & 255; |
||||
|
u >>= 8; |
||||
|
} |
||||
|
u += 121665 * a[31]; |
||||
|
out[31] = u & 127; |
||||
|
u = 19 * (u >> 7); |
||||
|
for(j = 0; j < 31; ++j) { |
||||
|
u += out[j]; |
||||
|
out[j] = u & 255; |
||||
|
u >>= 8; |
||||
|
} |
||||
|
u += out[j]; |
||||
|
out[j] = u; |
||||
|
} |
||||
|
|
||||
|
|
||||
|
static void square (unsigned int out[32], const unsigned int a[32]) { |
||||
|
|
||||
|
unsigned int i; |
||||
|
unsigned int j; |
||||
|
unsigned int u; |
||||
|
|
||||
|
for(i = 0; i < 32; ++i) { |
||||
|
u = 0; |
||||
|
for(j = 0; j < i - j; ++j) |
||||
|
u += a[j] * a[i - j]; |
||||
|
for(j = i + 1; j < i + 32 - j; ++j) |
||||
|
u += 38 * a[j] * a[i + 32 - j]; |
||||
|
u *= 2; |
||||
|
if((i & 1) == 0) { |
||||
|
u += a[i / 2] * a[i / 2]; |
||||
|
u += 38 * a[i / 2 + 16] * a[i / 2 + 16]; |
||||
|
} |
||||
|
out[i] = u; |
||||
|
} |
||||
|
squeeze(out); |
||||
|
} |
||||
|
|
||||
|
|
||||
|
static 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 t; |
||||
|
unsigned int bminus1; |
||||
|
|
||||
|
bminus1 = b - 1; |
||||
|
for(j = 0; j < 64; ++j) { |
||||
|
t = bminus1 & (r[j] ^ s[j]); |
||||
|
p[j] = s[j] ^ t; |
||||
|
q[j] = r[j] ^ t; |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
|
||||
|
static void mainloop (unsigned int work[64], const unsigned char e[32]) { |
||||
|
|
||||
|
unsigned int xzm1[64]; |
||||
|
unsigned int xzm[64]; |
||||
|
unsigned int xzmb[64]; |
||||
|
unsigned int xzm1b[64]; |
||||
|
unsigned int xznb[64]; |
||||
|
unsigned int xzn1b[64]; |
||||
|
unsigned int a0[64]; |
||||
|
unsigned int a1[64]; |
||||
|
unsigned int b0[64]; |
||||
|
unsigned int b1[64]; |
||||
|
unsigned int c1[64]; |
||||
|
unsigned int r[32]; |
||||
|
unsigned int s[32]; |
||||
|
unsigned int t[32]; |
||||
|
unsigned int u[32]; |
||||
|
unsigned int i; |
||||
|
unsigned int j; |
||||
|
unsigned int b; |
||||
|
int pos; |
||||
|
|
||||
|
for(j = 0; j < 32; ++j) |
||||
|
xzm1[j] = work[j]; |
||||
|
xzm1[32] = 1; |
||||
|
for(j = 33; j < 64; ++j) |
||||
|
xzm1[j] = 0; |
||||
|
|
||||
|
xzm[0] = 1; |
||||
|
for(j = 1; j < 64; ++j) |
||||
|
xzm[j] = 0; |
||||
|
|
||||
|
for(pos = 254; pos >= 0; --pos) { |
||||
|
b = e[pos / 8] >> (pos & 7); |
||||
|
b &= 1; |
||||
|
select(xzmb, xzm1b, xzm, xzm1, b); |
||||
|
add(a0, xzmb, xzmb + 32); |
||||
|
sub(a0 + 32, xzmb, xzmb + 32); |
||||
|
add (a1, xzm1b, xzm1b + 32); |
||||
|
sub(a1 + 32, xzm1b, xzm1b + 32); |
||||
|
square(b0, a0); |
||||
|
square(b0 + 32, a0 + 32); |
||||
|
mult(b1, a1, a0 + 32); |
||||
|
mult(b1 + 32, a1 + 32, a0); |
||||
|
add(c1, b1, b1 + 32); |
||||
|
sub(c1 + 32, b1, b1 + 32); |
||||
|
square(r, c1 + 32); |
||||
|
sub(s, b0, b0 + 32); |
||||
|
mult121665 (t, s); |
||||
|
add(u, t, b0); |
||||
|
mult(xznb, b0, b0 + 32); |
||||
|
mult(xznb + 32, s, u); |
||||
|
square(xzn1b, c1); |
||||
|
mult(xzn1b + 32, r, work); |
||||
|
select(xzm, xzm1, xznb, xzn1b, b); |
||||
|
} |
||||
|
|
||||
|
for(j = 0; j < 64; ++j) |
||||
|
work[j] = xzm[j]; |
||||
|
} |
||||
|
|
||||
|
|
||||
|
static void recip (unsigned int out[32], const unsigned int z[32]) { |
||||
|
|
||||
|
unsigned int z2[32]; |
||||
|
unsigned int z9[32]; |
||||
|
unsigned int z11[32]; |
||||
|
unsigned int z2_5_0[32]; |
||||
|
unsigned int z2_10_0[32]; |
||||
|
unsigned int z2_20_0[32]; |
||||
|
unsigned int z2_50_0[32]; |
||||
|
unsigned int z2_100_0[32]; |
||||
|
unsigned int t0[32]; |
||||
|
unsigned int t1[32]; |
||||
|
int i; |
||||
|
|
||||
|
/* 2 */ square(z2, z); |
||||
|
/* 4 */ square(t1, z2); |
||||
|
/* 8 */ square(t0, t1); |
||||
|
/* 9 */ mult(z9, t0, z); |
||||
|
/* 11 */ mult(z11, z9, z2); |
||||
|
/* 22 */ square(t0, z11); |
||||
|
/* 2^5 - 2^0 = 31 */ mult(z2_5_0, t0, z9); |
||||
|
|
||||
|
/* 2^6 - 2^1 */ square(t0, z2_5_0); |
||||
|
/* 2^7 - 2^2 */ square(t1, t0); |
||||
|
/* 2^8 - 2^3 */ square(t0, t1); |
||||
|
/* 2^9 - 2^4 */ square(t1, t0); |
||||
|
/* 2^10 - 2^5 */ square(t0, t1); |
||||
|
/* 2^10 - 2^0 */ mult(z2_10_0, t0, z2_5_0); |
||||
|
|
||||
|
/* 2^11 - 2^1 */ square(t0, z2_10_0); |
||||
|
/* 2^12 - 2^2 */ square(t1, t0); |
||||
|
/* 2^20 - 2^10 */ for(i = 2; i < 10; i += 2) { |
||||
|
square(t0, t1); |
||||
|
square(t1, t0); |
||||
|
} |
||||
|
/* 2^20 - 2^0 */ mult(z2_20_0, t1, z2_10_0); |
||||
|
|
||||
|
/* 2^21 - 2^1 */ square(t0, z2_20_0); |
||||
|
/* 2^22 - 2^2 */ square(t1, t0); |
||||
|
/* 2^40 - 2^20 */ for(i = 2; i < 20; i += 2) { |
||||
|
square(t0, t1); |
||||
|
square(t1, t0); |
||||
|
} |
||||
|
/* 2^40 - 2^0 */ mult(t0, t1, z2_20_0); |
||||
|
|
||||
|
/* 2^41 - 2^1 */ square(t1, t0); |
||||
|
/* 2^42 - 2^2 */ square(t0, t1); |
||||
|
/* 2^50 - 2^10 */ for(i = 2; i < 10; i += 2) { |
||||
|
square(t1, t0); |
||||
|
square(t0, t1); |
||||
|
} |
||||
|
/* 2^50 - 2^0 */ mult(z2_50_0, t0, z2_10_0); |
||||
|
|
||||
|
/* 2^51 - 2^1 */ square(t0, z2_50_0); |
||||
|
/* 2^52 - 2^2 */ square(t1, t0); |
||||
|
/* 2^100 - 2^50 */ for(i = 2; i < 50; i += 2) { |
||||
|
square(t0, t1); |
||||
|
square(t1, t0); |
||||
|
} |
||||
|
/* 2^100 - 2^0 */ mult(z2_100_0, t1, z2_50_0); |
||||
|
|
||||
|
/* 2^101 - 2^1 */ square(t1, z2_100_0); |
||||
|
/* 2^102 - 2^2 */ square(t0, t1); |
||||
|
/* 2^200 - 2^100 */ for(i = 2; i < 100; i += 2) { |
||||
|
square(t1, t0); |
||||
|
square(t0, t1); |
||||
|
} |
||||
|
/* 2^200 - 2^0 */ mult(t1, t0, z2_100_0); |
||||
|
|
||||
|
/* 2^201 - 2^1 */ square(t0, t1); |
||||
|
/* 2^202 - 2^2 */ square(t1, t0); |
||||
|
/* 2^250 - 2^50 */ for(i = 2; i < 50; i += 2) { |
||||
|
square(t0, t1); |
||||
|
square(t1, t0); |
||||
|
} |
||||
|
/* 2^250 - 2^0 */ mult(t0, t1, z2_50_0); |
||||
|
|
||||
|
/* 2^251 - 2^1 */ square(t1, t0); |
||||
|
/* 2^252 - 2^2 */ square(t0, t1); |
||||
|
/* 2^253 - 2^3 */ square(t1, t0); |
||||
|
/* 2^254 - 2^4 */ square(t0, t1); |
||||
|
/* 2^255 - 2^5 */ square(t1, t0); |
||||
|
/* 2^255 - 21 */ mult(out, t1, z11); |
||||
|
} |
||||
|
|
||||
|
|
||||
|
void curve25519 (unsigned char *q, const unsigned char *n, const unsigned char *p) { |
||||
|
|
||||
|
unsigned int work[96]; |
||||
|
unsigned char e[32]; |
||||
|
unsigned int i; |
||||
|
|
||||
|
for (i = 0; i < 32; ++i) |
||||
|
e[i] = n[i]; |
||||
|
e[0] &= 248; |
||||
|
e[31] &= 127; |
||||
|
e[31] |= 64; |
||||
|
|
||||
|
for (i = 0; i < 32; ++i) |
||||
|
work[i] = p[i]; |
||||
|
work[31] &= 127; |
||||
|
|
||||
|
mainloop(work, e); |
||||
|
recip(work + 32, work + 32); |
||||
|
mult(work + 64, work, work + 32); |
||||
|
freeze(work + 64); |
||||
|
|
||||
|
for(i = 0; i < 32; ++i) |
||||
|
q[i] = work[64 + i]; |
||||
|
} |
@ -0,0 +1,76 @@ |
|||||
|
/*
|
||||
|
* (C) 2007-21 - ntop.org and contributors |
||||
|
* |
||||
|
* This program is free software; you can redistribute it and/or modify |
||||
|
* it under the terms of the GNU General Public License as published by |
||||
|
* the Free Software Foundation; either version 3 of the License, or |
||||
|
* (at your option) any later version. |
||||
|
* |
||||
|
* This program is distributed in the hope that it will be useful, |
||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||||
|
* GNU General Public License for more details. |
||||
|
* |
||||
|
* You should have received a copy of the GNU General Public License |
||||
|
* along with this program; if not, see <http://www.gnu.org/licenses/>
|
||||
|
* |
||||
|
*/ |
||||
|
|
||||
|
|
||||
|
#include "n2n.h" |
||||
|
|
||||
|
|
||||
|
int main(int argc, char * argv[]) { |
||||
|
|
||||
|
n2n_private_public_key_t prv; /* 32 bytes private key */ |
||||
|
n2n_private_public_key_t bin; /* 32 bytes public key binary output buffer */ |
||||
|
uint8_t asc[44]; /* 43 bytes + 0-terminator ascii string output */ |
||||
|
uint8_t fed = 0; |
||||
|
|
||||
|
// exactly two parameters required
|
||||
|
if(argc != 3) { |
||||
|
// error message to stderr to not interfere with batch usage
|
||||
|
fprintf(stderr, "\n" |
||||
|
"n2n-keygen tool\n\n" |
||||
|
" usage: n2n-keygen <username> <password>\n\n" |
||||
|
" or n2n-keygen -F <federation name>\n\n" |
||||
|
" outputs a line to insert at supernode's community file for user-and-\n" |
||||
|
" password authentication or a command line parameter with the public\n" |
||||
|
" federation key for use at edge's command line, please refer to the\n" |
||||
|
" doc/Authentication.md document or the man pages for more details\n\n"); |
||||
|
return 1; |
||||
|
} |
||||
|
|
||||
|
// federation mode?
|
||||
|
if(strcmp(argv[1], "-F") == 0) |
||||
|
fed = 1; |
||||
|
|
||||
|
// derive private key from username and password:
|
||||
|
// hash username once, hash password twice (so password is bound
|
||||
|
// to username but username and password are not interchangeable),
|
||||
|
// finally xor the result
|
||||
|
// in federation mode: only hash federation name, twice
|
||||
|
generate_private_key(prv, (uint8_t*)argv[2]); |
||||
|
|
||||
|
// hash user name only if required
|
||||
|
if(!fed) { |
||||
|
bind_private_key_to_username(prv, (uint8_t*)argv[1]); |
||||
|
} |
||||
|
|
||||
|
// calculate the public key into binary output buffer
|
||||
|
generate_public_key(bin, prv); |
||||
|
|
||||
|
// clear out the private key
|
||||
|
memset(prv, 0, sizeof(prv)); |
||||
|
|
||||
|
// convert binary output to 6-bit-ascii string output
|
||||
|
bin_to_ascii(asc, bin, sizeof(bin)); |
||||
|
|
||||
|
// output
|
||||
|
if(fed) |
||||
|
fprintf(stdout, "-P %s\n", asc); |
||||
|
else |
||||
|
fprintf(stdout, "%c %s %s\n", N2N_USER_KEY_LINE_STARTER, argv[1], asc); |
||||
|
|
||||
|
return 0; |
||||
|
} |
Loading…
Reference in new issue