Cleanup, warning removal, cppcheck informed cleanup.

This commit is contained in:
Adam Ierymenko 2019-08-14 10:35:57 -07:00
parent a028e04ab9
commit d7a31088ba
No known key found for this signature in database
GPG Key ID: 1657198823E52A61
43 changed files with 398 additions and 668 deletions

View File

@ -49,7 +49,7 @@ DBMirrorSet::DBMirrorSet(DB::ChangeListener *listener) :
}
for(auto db=dbs.begin();db!=dbs.end();++db) {
(*db)->each([this,&dbs,&db](uint64_t networkId,const nlohmann::json &network,uint64_t memberId,const nlohmann::json &member) {
(*db)->each([&dbs,&db](uint64_t networkId,const nlohmann::json &network,uint64_t memberId,const nlohmann::json &member) {
try {
if (network.is_object()) {
if (memberId == 0) {

View File

@ -42,8 +42,14 @@
#include <thread>
#include <memory>
#include "../node/Constants.hpp"
#include "../node/Node.hpp"
#include "../node/CertificateOfMembership.hpp"
#include "../node/NetworkConfig.hpp"
#include "../node/Dictionary.hpp"
#include "../node/MAC.hpp"
#include "../include/ZeroTierOne.h"
#include "../version.h"
#include "EmbeddedNetworkController.hpp"
#include "LFDB.hpp"
@ -52,12 +58,6 @@
#include "PostgreSQL.hpp"
#endif
#include "../node/Node.hpp"
#include "../node/CertificateOfMembership.hpp"
#include "../node/NetworkConfig.hpp"
#include "../node/Dictionary.hpp"
#include "../node/MAC.hpp"
using json = nlohmann::json;
// API version reported via JSON control plane

View File

@ -124,8 +124,8 @@ private:
} sw;
} _k;
#ifdef ZT_AES_AESNI
static inline __m128i _init256_1(__m128i a,__m128i b)
#ifdef ZT_AES_AESNI /********************************************************/
static inline __m128i _init256_1_aesni(__m128i a,__m128i b)
{
__m128i x,y;
b = _mm_shuffle_epi32(b,0xff);
@ -138,7 +138,7 @@ private:
x = _mm_xor_si128(x,b);
return x;
}
static inline __m128i _init256_2(__m128i a,__m128i b)
static inline __m128i _init256_2_aesni(__m128i a,__m128i b)
{
__m128i x,y,z;
y = _mm_aeskeygenassist_si128(a,0x00);
@ -154,23 +154,25 @@ private:
}
inline void _init_aesni(const uint8_t key[32])
{
/* Init AES itself */
__m128i t1,t2;
_k.ni.k[0] = t1 = _mm_loadu_si128((const __m128i *)key);
_k.ni.k[1] = t2 = _mm_loadu_si128((const __m128i *)(key+16));
_k.ni.k[2] = t1 = _init256_1(t1,_mm_aeskeygenassist_si128(t2,0x01));
_k.ni.k[3] = t2 = _init256_2(t1,t2);
_k.ni.k[4] = t1 = _init256_1(t1,_mm_aeskeygenassist_si128(t2,0x02));
_k.ni.k[5] = t2 = _init256_2(t1,t2);
_k.ni.k[6] = t1 = _init256_1(t1,_mm_aeskeygenassist_si128(t2,0x04));
_k.ni.k[7] = t2 = _init256_2(t1,t2);
_k.ni.k[8] = t1 = _init256_1(t1,_mm_aeskeygenassist_si128(t2,0x08));
_k.ni.k[9] = t2 = _init256_2(t1,t2);
_k.ni.k[10] = t1 = _init256_1(t1,_mm_aeskeygenassist_si128(t2,0x10));
_k.ni.k[11] = t2 = _init256_2(t1,t2);
_k.ni.k[12] = t1 = _init256_1(t1,_mm_aeskeygenassist_si128(t2,0x20));
_k.ni.k[13] = t2 = _init256_2(t1,t2);
_k.ni.k[14] = _init256_1(t1,_mm_aeskeygenassist_si128(t2,0x40));
_k.ni.k[2] = t1 = _init256_1_aesni(t1,_mm_aeskeygenassist_si128(t2,0x01));
_k.ni.k[3] = t2 = _init256_2_aesni(t1,t2);
_k.ni.k[4] = t1 = _init256_1_aesni(t1,_mm_aeskeygenassist_si128(t2,0x02));
_k.ni.k[5] = t2 = _init256_2_aesni(t1,t2);
_k.ni.k[6] = t1 = _init256_1_aesni(t1,_mm_aeskeygenassist_si128(t2,0x04));
_k.ni.k[7] = t2 = _init256_2_aesni(t1,t2);
_k.ni.k[8] = t1 = _init256_1_aesni(t1,_mm_aeskeygenassist_si128(t2,0x08));
_k.ni.k[9] = t2 = _init256_2_aesni(t1,t2);
_k.ni.k[10] = t1 = _init256_1_aesni(t1,_mm_aeskeygenassist_si128(t2,0x10));
_k.ni.k[11] = t2 = _init256_2_aesni(t1,t2);
_k.ni.k[12] = t1 = _init256_1_aesni(t1,_mm_aeskeygenassist_si128(t2,0x20));
_k.ni.k[13] = t2 = _init256_2_aesni(t1,t2);
_k.ni.k[14] = _init256_1_aesni(t1,_mm_aeskeygenassist_si128(t2,0x40));
/* Init GCM / GHASH */
__m128i h = _mm_xor_si128(_mm_setzero_si128(),_k.ni.k[0]);
h = _mm_aesenc_si128(h,_k.ni.k[1]);
h = _mm_aesenc_si128(h,_k.ni.k[2]);
@ -357,7 +359,6 @@ private:
return x;
}
static inline void _htoun64_aesni(void *network,const uint64_t host) { *((uint64_t *)network) = Utils::hton(host); }
static inline void _htoun32_aesni(void *network,const uint64_t host) { *((uint32_t *)network) = Utils::hton(host); }
inline __m128i _create_j_aesni(const uint8_t *iv) const
{
@ -731,7 +732,7 @@ private:
y = _icv_tailer_aesni(y,alen,len);
_icv_crypt_aesni(y,j,icv,icvsize);
}
#endif
#endif /* ZT_AES_AESNI ******************************************************/
};
} // namespace ZeroTier

View File

@ -46,15 +46,15 @@ namespace ZeroTier {
class Address
{
public:
Address() : _a(0) {}
Address(const Address &a) : _a(a._a) {}
Address(uint64_t a) : _a(a & 0xffffffffffULL) {}
inline Address() : _a(0) {}
inline Address(const Address &a) : _a(a._a) {}
inline Address(uint64_t a) : _a(a & 0xffffffffffULL) {}
/**
* @param bits Raw address -- 5 bytes, big-endian byte order
* @param len Length of array
*/
Address(const void *bits,unsigned int len) { setTo(bits,len); }
inline Address(const void *bits,unsigned int len) { setTo(bits,len); }
inline Address &operator=(const Address &a) { _a = a._a; return *this; }
inline Address &operator=(const uint64_t a) { _a = (a & 0xffffffffffULL); return *this; }

View File

@ -41,7 +41,7 @@ namespace ZeroTier {
class AtomicCounter
{
public:
AtomicCounter() { _v = 0; }
inline AtomicCounter() { _v = 0; }
inline int load() const
{
@ -71,7 +71,7 @@ public:
}
private:
AtomicCounter(const AtomicCounter &) {}
inline AtomicCounter(const AtomicCounter &) {}
const AtomicCounter &operator=(const AtomicCounter &) { return *this; }
#ifdef __GNUC__

View File

@ -87,12 +87,12 @@ public:
inline const_reverse_iterator rbegin() const { return const_reverse_iterator(begin()); }
inline const_reverse_iterator rend() const { return const_reverse_iterator(end()); }
Buffer() :
inline Buffer() :
_l(0)
{
}
Buffer(unsigned int l)
inline Buffer(const unsigned int l)
{
if (l > C)
throw ZT_EXCEPTION_OUT_OF_BOUNDS;
@ -100,12 +100,12 @@ public:
}
template<unsigned int C2>
Buffer(const Buffer<C2> &b)
inline Buffer(const Buffer<C2> &b)
{
*this = b;
}
Buffer(const void *b,unsigned int l)
inline Buffer(const void *b,unsigned int l)
{
copyFrom(b,l);
}

View File

@ -392,63 +392,36 @@ static inline void fcontract(u8 *output, limb *input_limbs) {
s32 input[10];
s32 mask;
/* |input_limbs[i]| < 2^26, so it's valid to convert to an s32. */
for (i = 0; i < 10; i++) {
input[i] = input_limbs[i];
}
for (j = 0; j < 2; ++j) {
for (i = 0; i < 9; ++i) {
if ((i & 1) == 1) {
/* This calculation is a time-invariant way to make input[i]
* non-negative by borrowing from the next-larger limb. */
const s32 mask = input[i] >> 31;
const s32 carry = -((input[i] & mask) >> 25);
const s32 mm = input[i] >> 31;
const s32 carry = -((input[i] & mm) >> 25);
input[i] = input[i] + (carry << 25);
input[i+1] = input[i+1] - carry;
} else {
const s32 mask = input[i] >> 31;
const s32 carry = -((input[i] & mask) >> 26);
const s32 mm = input[i] >> 31;
const s32 carry = -((input[i] & mm) >> 26);
input[i] = input[i] + (carry << 26);
input[i+1] = input[i+1] - carry;
}
}
/* There's no greater limb for input[9] to borrow from, but we can multiply
* by 19 and borrow from input[0], which is valid mod 2^255-19. */
{
const s32 mask = input[9] >> 31;
const s32 carry = -((input[9] & mask) >> 25);
const s32 mm = input[9] >> 31;
const s32 carry = -((input[9] & mm) >> 25);
input[9] = input[9] + (carry << 25);
input[0] = input[0] - (carry * 19);
}
/* After the first iteration, input[1..9] are non-negative and fit within
* 25 or 26 bits, depending on position. However, input[0] may be
* negative. */
}
/* The first borrow-propagation pass above ended with every limb
except (possibly) input[0] non-negative.
If input[0] was negative after the first pass, then it was because of a
carry from input[9]. On entry, input[9] < 2^26 so the carry was, at most,
one, since (2**26-1) >> 25 = 1. Thus input[0] >= -19.
In the second pass, each limb is decreased by at most one. Thus the second
borrow-propagation pass could only have wrapped around to decrease
input[0] again if the first pass left input[0] negative *and* input[1]
through input[9] were all zero. In that case, input[1] is now 2^25 - 1,
and this last borrow-propagation step will leave input[1] non-negative. */
{
const s32 mask = input[0] >> 31;
const s32 carry = -((input[0] & mask) >> 26);
const s32 mm = input[0] >> 31;
const s32 carry = -((input[0] & mm) >> 26);
input[0] = input[0] + (carry << 26);
input[1] = input[1] - carry;
}
/* All input[i] are now non-negative. However, there might be values between
* 2^25 and 2^26 in a limb which is, nominally, 25 bits wide. */
for (j = 0; j < 2; j++) {
for (i = 0; i < 9; i++) {
if ((i & 1) == 1) {
@ -461,24 +434,12 @@ static inline void fcontract(u8 *output, limb *input_limbs) {
input[i+1] += carry;
}
}
{
const s32 carry = input[9] >> 25;
input[9] &= 0x1ffffff;
input[0] += 19*carry;
}
}
/* If the first carry-chain pass, just above, ended up with a carry from
* input[9], and that caused input[0] to be out-of-bounds, then input[0] was
* < 2^26 + 2*19, because the carry was, at most, two.
*
* If the second pass carried from input[9] again then input[0] is < 2*19 and
* the input[9] -> input[0] carry didn't push input[0] out of bounds. */
/* It still remains the case that input might be between 2^255-19 and 2^255.
* In this case, input[1..9] must take their maximum value and input[0] must
* be >= (2^255-19) & 0x3ffffff, which is 0x3ffffed. */
mask = s32_gte(input[0], 0x3ffffed);
for (i = 1; i < 10; i++) {
if ((i & 1) == 1) {
@ -487,11 +448,7 @@ static inline void fcontract(u8 *output, limb *input_limbs) {
mask &= s32_eq(input[i], 0x3ffffff);
}
}
/* mask is either 0xffffffff (if input >= 2^255-19) and zero otherwise. Thus
* this conditionally subtracts 2^255-19. */
input[0] -= mask & 0x3ffffed;
for (i = 1; i < 10; i++) {
if ((i & 1) == 1) {
input[i] -= mask & 0x1ffffff;
@ -834,12 +791,10 @@ static inline crypto_uint32 times38(crypto_uint32 a)
static inline void reduce_add_sub(fe25519 *r)
{
crypto_uint32 t;
int i,rep;
for(rep=0;rep<4;rep++)
{
t = r->v[31] >> 7;
crypto_uint32 t = r->v[31] >> 7;
r->v[31] &= 127;
t = times19(t);
r->v[0] += t;
@ -854,12 +809,10 @@ static inline void reduce_add_sub(fe25519 *r)
static inline void reduce_mul(fe25519 *r)
{
crypto_uint32 t;
int i,rep;
for(rep=0;rep<2;rep++)
{
t = r->v[31] >> 7;
crypto_uint32 t = r->v[31] >> 7;
r->v[31] &= 127;
t = times19(t);
r->v[0] += t;
@ -876,17 +829,17 @@ static inline void reduce_mul(fe25519 *r)
static inline void fe25519_freeze(fe25519 *r)
{
int i;
crypto_uint32 m = equal(r->v[31],127);
crypto_uint32 mm = equal(r->v[31],127);
for(i=30;i>0;i--)
m &= equal(r->v[i],255);
m &= ge(r->v[0],237);
mm &= equal(r->v[i],255);
mm &= ge(r->v[0],237);
m = -m;
mm = -mm;
r->v[31] -= m&127;
r->v[31] -= mm&127;
for(i=30;i>0;i--)
r->v[i] -= m&255;
r->v[0] -= m&237;
r->v[i] -= mm&255;
r->v[0] -= mm&237;
}
static inline void fe25519_unpack(fe25519 *r, const unsigned char x[32])
@ -1157,9 +1110,7 @@ static inline void barrett_reduce(sc25519 *r, const crypto_uint32 x[64])
crypto_uint32 *q3 = q2 + 33;
crypto_uint32 r1[33];
crypto_uint32 r2[33];
crypto_uint32 carry;
crypto_uint32 pb = 0;
crypto_uint32 b;
for (i = 0;i < 66;++i) q2[i] = 0;
for (i = 0;i < 33;++i) r2[i] = 0;
@ -1167,10 +1118,8 @@ static inline void barrett_reduce(sc25519 *r, const crypto_uint32 x[64])
for(i=0;i<33;i++)
for(j=0;j<33;j++)
if(i+j >= 31) q2[i+j] += mu[i]*x[j+31];
carry = q2[31] >> 8;
q2[32] += carry;
carry = q2[32] >> 8;
q2[33] += carry;
q2[32] += (q2[31] >> 8);
q2[33] += (q2[32] >> 8);
for(i=0;i<33;i++)r1[i] = x[i];
for(i=0;i<32;i++)
@ -1179,15 +1128,14 @@ static inline void barrett_reduce(sc25519 *r, const crypto_uint32 x[64])
for(i=0;i<32;i++)
{
carry = r2[i] >> 8;
r2[i+1] += carry;
r2[i+1] += (r2[i] >> 8);
r2[i] &= 0xff;
}
for(i=0;i<32;i++)
{
pb += r2[i];
b = lt(r1[i],pb);
crypto_uint32 b = lt(r1[i],pb);
r->v[i] = r1[i]-pb+(b<<8);
pb = b;
}
@ -1225,12 +1173,11 @@ static inline void sc25519_to32bytes(unsigned char r[32], const sc25519 *x)
static inline void sc25519_add(sc25519 *r, const sc25519 *x, const sc25519 *y)
{
int i, carry;
int i;
for(i=0;i<32;i++) r->v[i] = x->v[i] + y->v[i];
for(i=0;i<31;i++)
{
carry = r->v[i] >> 8;
r->v[i+1] += carry;
r->v[i+1] += (r->v[i] >> 8);
r->v[i] &= 0xff;
}
reduce_add_sub(r);
@ -1238,7 +1185,7 @@ static inline void sc25519_add(sc25519 *r, const sc25519 *x, const sc25519 *y)
static inline void sc25519_mul(sc25519 *r, const sc25519 *x, const sc25519 *y)
{
int i,j,carry;
int i,j;
crypto_uint32 t[64];
for(i=0;i<64;i++)t[i] = 0;
@ -1248,8 +1195,7 @@ static inline void sc25519_mul(sc25519 *r, const sc25519 *x, const sc25519 *y)
for(i=0;i<63;i++)
{
carry = t[i] >> 8;
t[i+1] += carry;
t[i+1] += (t[i] >> 8);
t[i] &= 0xff;
}

View File

@ -72,7 +72,7 @@ class Capability : public Credential
public:
static inline Credential::Type credentialType() { return Credential::CREDENTIAL_TYPE_CAPABILITY; }
Capability() :
inline Capability() :
_nwid(0),
_ts(0),
_id(0),
@ -91,7 +91,7 @@ public:
* @param rules Network flow rules for this capability
* @param ruleCount Number of flow rules
*/
Capability(uint32_t id,uint64_t nwid,int64_t ts,unsigned int mccl,const ZT_VirtualNetworkRule *rules,unsigned int ruleCount) :
inline Capability(uint32_t id,uint64_t nwid,int64_t ts,unsigned int mccl,const ZT_VirtualNetworkRule *rules,unsigned int ruleCount) :
_nwid(nwid),
_ts(ts),
_id(id),

View File

@ -112,7 +112,7 @@ public:
/**
* Create an empty certificate of membership
*/
CertificateOfMembership() :
inline CertificateOfMembership() :
_qualifierCount(0),
_signatureLength(0) {}
@ -124,7 +124,7 @@ public:
* @param nwid Network ID
* @param issuedTo Certificate recipient
*/
CertificateOfMembership(uint64_t timestamp,uint64_t timestampMaxDelta,uint64_t nwid,const Address &issuedTo)
inline CertificateOfMembership(uint64_t timestamp,uint64_t timestampMaxDelta,uint64_t nwid,const Address &issuedTo)
{
_qualifiers[0].id = COM_RESERVED_ID_TIMESTAMP;
_qualifiers[0].value = timestamp;
@ -146,7 +146,7 @@ public:
* @param startAt Position to start in buffer
*/
template<unsigned int C>
CertificateOfMembership(const Buffer<C> &b,unsigned int startAt = 0)
inline CertificateOfMembership(const Buffer<C> &b,unsigned int startAt = 0)
{
deserialize(b,startAt);
}

View File

@ -67,12 +67,12 @@ public:
THING_IPV6_ADDRESS = 3
};
CertificateOfOwnership()
inline CertificateOfOwnership()
{
memset(reinterpret_cast<void *>(this),0,sizeof(CertificateOfOwnership));
}
CertificateOfOwnership(const uint64_t nwid,const int64_t ts,const Address &issuedTo,const uint32_t id)
inline CertificateOfOwnership(const uint64_t nwid,const int64_t ts,const Address &issuedTo,const uint32_t id)
{
memset(reinterpret_cast<void *>(this),0,sizeof(CertificateOfOwnership));
_networkId = nwid;

View File

@ -29,6 +29,22 @@
#include "../include/ZeroTierOne.h"
#if __has_include("../version.h")
#include "../version.h"
#else /* dummy values for use inside IDEs, etc. */
#define ZEROTIER_ONE_VERSION_MAJOR 255
#define ZEROTIER_ONE_VERSION_MINOR 255
#define ZEROTIER_ONE_VERSION_REVISION 255
#define ZEROTIER_ONE_VERSION_BUILD 255
#endif
#ifndef ZT_BUILD_ARCHITECTURE
#define ZT_BUILD_ARCHITECTURE 0
#endif
#ifndef ZT_BUILD_PLATFORM
#define ZT_BUILD_PLATFORM 0
#endif
//
// This include file also auto-detects and canonicalizes some environment
// information defines:
@ -603,11 +619,6 @@
*/
#define ZT_TRUST_EXPIRATION 600000
/**
* Enable support for older network configurations from older (pre-1.1.6) controllers
*/
#define ZT_SUPPORT_OLD_STYLE_NETCONF 1
/**
* Size of a buffer to store either a C25519 or an ECC P-384 signature
*/

View File

@ -62,9 +62,9 @@ template<unsigned int C>
class Dictionary
{
public:
Dictionary() { memset(_d,0,sizeof(_d)); }
Dictionary(const char *s) { this->load(s); }
Dictionary(const char *s,unsigned int len)
inline Dictionary() { memset(_d,0,sizeof(_d)); }
inline Dictionary(const char *s) { this->load(s); }
inline Dictionary(const char *s,unsigned int len)
{
for(unsigned int i=0;i<C;++i) {
if ((s)&&(i < len)) {
@ -75,7 +75,7 @@ public:
}
_d[C - 1] = (char)0;
}
Dictionary(const Dictionary &d) { memcpy(_d,d._d,C); }
inline Dictionary(const Dictionary &d) { memcpy(_d,d._d,C); }
inline Dictionary &operator=(const Dictionary &d)
{

View File

@ -49,9 +49,9 @@ class Hashtable
private:
struct _Bucket
{
_Bucket(const K &k,const V &v) : k(k),v(v) {}
_Bucket(const K &k) : k(k),v() {}
_Bucket(const _Bucket &b) : k(b.k),v(b.v) {}
inline _Bucket(const K &k,const V &v) : k(k),v(v) {}
inline _Bucket(const K &k) : k(k),v() {}
inline _Bucket(const _Bucket &b) : k(b.k),v(b.v) {}
inline _Bucket &operator=(const _Bucket &b) { k = b.k; v = b.v; return *this; }
K k;
V v;
@ -72,7 +72,7 @@ public:
/**
* @param ht Hash table to iterate over
*/
Iterator(Hashtable &ht) :
inline Iterator(Hashtable &ht) :
_idx(0),
_ht(&ht),
_b(ht._t[0])
@ -110,7 +110,7 @@ public:
/**
* @param bc Initial capacity in buckets (default: 64, must be nonzero)
*/
Hashtable(unsigned long bc = 64) :
inline Hashtable(unsigned long bc = 64) :
_t(reinterpret_cast<_Bucket **>(::malloc(sizeof(_Bucket *) * bc))),
_bc(bc),
_s(0)
@ -121,7 +121,7 @@ public:
_t[i] = (_Bucket *)0;
}
Hashtable(const Hashtable<K,V> &ht) :
inline Hashtable(const Hashtable<K,V> &ht) :
_t(reinterpret_cast<_Bucket **>(::malloc(sizeof(_Bucket *) * ht._bc))),
_bc(ht._bc),
_s(ht._s)
@ -141,7 +141,7 @@ public:
}
}
~Hashtable()
inline ~Hashtable()
{
this->clear();
::free(_t);

View File

@ -64,19 +64,19 @@ public:
P384 = ZT_CRYPTO_ALG_P384 // Type 1 -- NIST P-384 ECDH and ECDSA (2.0+ only)
};
Identity() { memset(reinterpret_cast<void *>(this),0,sizeof(Identity)); }
Identity(const Identity &id) { memcpy(reinterpret_cast<void *>(this),&id,sizeof(Identity)); }
inline Identity() { memset(reinterpret_cast<void *>(this),0,sizeof(Identity)); }
inline Identity(const Identity &id) { memcpy(reinterpret_cast<void *>(this),&id,sizeof(Identity)); }
Identity(const char *str)
inline Identity(const char *str)
{
if (!fromString(str))
throw ZT_EXCEPTION_INVALID_SERIALIZED_DATA_INVALID_TYPE;
}
template<unsigned int C>
Identity(const Buffer<C> &b,unsigned int startAt = 0) { deserialize(b,startAt); }
inline Identity(const Buffer<C> &b,unsigned int startAt = 0) { deserialize(b,startAt); }
~Identity() { Utils::burn(reinterpret_cast<void *>(this),sizeof(Identity)); }
inline ~Identity() { Utils::burn(reinterpret_cast<void *>(this),sizeof(Identity)); }
inline void zero() { Utils::burn(reinterpret_cast<void *>(this),sizeof(Identity)); }

View File

@ -30,7 +30,6 @@
#include <list>
#include "../version.h"
#include "../include/ZeroTierOne.h"
#include "Constants.hpp"

View File

@ -62,7 +62,7 @@ class Network;
class IncomingPacket : public Packet
{
public:
IncomingPacket() :
inline IncomingPacket() :
Packet(),
_receiveTime(0)
{
@ -77,7 +77,7 @@ public:
* @param now Current time
* @throws std::out_of_range Range error processing packet
*/
IncomingPacket(const void *data,unsigned int len,const SharedPtr<Path> &path,int64_t now) :
inline IncomingPacket(const void *data,unsigned int len,const SharedPtr<Path> &path,int64_t now) :
Packet(data,len),
_receiveTime(now),
_path(path)

View File

@ -90,20 +90,20 @@ struct InetAddress : public sockaddr_storage
inline std::size_t operator()(const InetAddress &a) const { return (std::size_t)a.hashCode(); }
};
InetAddress() { memset(this,0,sizeof(InetAddress)); }
InetAddress(const InetAddress &a) { memcpy(this,&a,sizeof(InetAddress)); }
InetAddress(const InetAddress *a) { memcpy(this,a,sizeof(InetAddress)); }
InetAddress(const struct sockaddr_storage &ss) { *this = ss; }
InetAddress(const struct sockaddr_storage *ss) { *this = ss; }
InetAddress(const struct sockaddr &sa) { *this = sa; }
InetAddress(const struct sockaddr *sa) { *this = sa; }
InetAddress(const struct sockaddr_in &sa) { *this = sa; }
InetAddress(const struct sockaddr_in *sa) { *this = sa; }
InetAddress(const struct sockaddr_in6 &sa) { *this = sa; }
InetAddress(const struct sockaddr_in6 *sa) { *this = sa; }
InetAddress(const void *ipBytes,unsigned int ipLen,unsigned int port) { this->set(ipBytes,ipLen,port); }
InetAddress(const uint32_t ipv4,unsigned int port) { this->set(&ipv4,4,port); }
InetAddress(const char *ipSlashPort) { this->fromString(ipSlashPort); }
inline InetAddress() { memset(this,0,sizeof(InetAddress)); }
inline InetAddress(const InetAddress &a) { memcpy(this,&a,sizeof(InetAddress)); }
inline InetAddress(const InetAddress *a) { memcpy(this,a,sizeof(InetAddress)); }
inline InetAddress(const struct sockaddr_storage &ss) { *this = ss; }
inline InetAddress(const struct sockaddr_storage *ss) { *this = ss; }
inline InetAddress(const struct sockaddr &sa) { *this = sa; }
inline InetAddress(const struct sockaddr *sa) { *this = sa; }
inline InetAddress(const struct sockaddr_in &sa) { *this = sa; }
inline InetAddress(const struct sockaddr_in *sa) { *this = sa; }
inline InetAddress(const struct sockaddr_in6 &sa) { *this = sa; }
inline InetAddress(const struct sockaddr_in6 *sa) { *this = sa; }
inline InetAddress(const void *ipBytes,unsigned int ipLen,unsigned int port) { this->set(ipBytes,ipLen,port); }
inline InetAddress(const uint32_t ipv4,unsigned int port) { this->set(&ipv4,4,port); }
inline InetAddress(const char *ipSlashPort) { this->fromString(ipSlashPort); }
inline InetAddress &operator=(const InetAddress &a)
{

View File

@ -46,30 +46,51 @@ namespace ZeroTier {
/**
* Signed information about a node's location on the network
*
* A locator can be stored in DNS as a series of TXT records with a DNS name
* that includes a public key that can be used to validate the locator's
* signature. That way DNS records can't be spoofed even if no DNSSEC or
* anything else is present to secure DNS.
* A locator is a signed record that contains information about where a node
* may be found. It can contain static physical addresses or virtual ZeroTier
* addresses of nodes that can forward to the target node. Locator records
* can be stored in signed DNS TXT record sets, in LF by roots, in caches,
* etc. Version 2.x nodes can sign their own locators. Roots can create
* signed locators using their own signature for version 1.x nodes. Locators
* signed by the node whose location they describe always take precedence
* over locators signed by other nodes.
*/
class Locator
{
public:
Locator() : _signatureLength(0) {}
inline Locator() : _signatureLength(0) {}
inline const Identity &id() const { return _id; }
inline const Identity &signer() const { return ((_signedBy) ? _signedBy : _id); }
inline const std::vector<InetAddress> &phy() const { return _physical; }
inline const std::vector<Identity> &virt() const { return _virtual; }
/**
* Add a physical address to this locator (call before finish() to build a new Locator)
*/
inline void add(const InetAddress &ip)
{
if (_physical.size() < ZT_LOCATOR_MAX_PHYSICAL_ADDRESSES)
_physical.push_back(ip);
}
/**
* Add a forwarding ZeroTier node to this locator (call before finish() to build a new Locator)
*/
inline void add(const Identity &zt)
{
if (_virtual.size() < ZT_LOCATOR_MAX_VIRTUAL_ADDRESSES)
_virtual.push_back(zt);
}
/**
* Method to be called after add() is called for each address or forwarding node
*
* This sets timestamp and ID information and sorts and deduplicates target
* lists but does not sign the locator. The sign() method should be used after
* finish().
*/
inline void finish(const Identity &id,const int64_t ts)
{
_ts = ts;
@ -80,6 +101,9 @@ public:
_virtual.erase(std::unique(_virtual.begin(),_virtual.end()),_virtual.end());
}
/**
* Sign this locator (must be called after finish())
*/
inline bool sign(const Identity &signingId)
{
if (!signingId.hasPrivate())
@ -101,6 +125,9 @@ public:
}
}
/**
* Verify this locator's signature against its embedded signing identity
*/
inline bool verify() const
{
if ((_signatureLength == 0)||(_signatureLength > sizeof(_signature)))
@ -118,6 +145,18 @@ public:
}
}
/**
* Make DNS TXT records for this locator
*
* DNS TXT records are signed by an entirely separate key that is added along
* with DNS names to nodes to allow them to verify DNS results. It's separate
* from the locator's signature so that a single DNS record can point to more
* than one locator or be served by things like geo-aware DNS.
*
* Right now only NIST P-384 is supported for signing DNS records. NIST EDDSA
* is used here so that FIPS-only nodes can always use DNS to locate roots as
* FIPS-only nodes may be required to disable non-FIPS algorithms.
*/
inline std::vector<Str> makeTxtRecords(const uint8_t p384SigningKeyPublic[ZT_ECC384_PUBLIC_KEY_SIZE],const uint8_t p384SigningKeyPrivate[ZT_ECC384_PUBLIC_KEY_SIZE])
{
uint8_t s384[48],dnsSig[ZT_ECC384_SIGNATURE_SIZE];
@ -144,6 +183,19 @@ public:
return txtRecords;
}
/**
* Decode TXT records
*
* The supplied TXT records must be sorted in ascending natural sort order prior
* to calling this method. The iterators supplied must be read iterators that
* point to string objects supporting the c_str() method, which can be Str or
* std::string.
*
* This method checks the decoded locator's signature using the supplied DNS TXT
* record signing public key. False is returned if the TXT records are invalid,
* incomplete, or fail signature check. If true is returned this Locator object
* now contains the contents of the supplied TXT records.
*/
template<typename I>
inline bool decodeTxtRecords(I start,I end,const uint8_t p384SigningKeyPublic[ZT_ECC384_PUBLIC_KEY_SIZE])
{
@ -215,7 +267,7 @@ public:
_ts = (int64_t)b.template at<uint64_t>(p); p += 8;
p += _id.deserialize(b,p);
const unsigned int signerCount = b[p++];
if (signerCount > 1)
if (signerCount > 1) /* only one third party signer is currently supported */
throw ZT_EXCEPTION_INVALID_SERIALIZED_DATA_OVERFLOW;
if (signerCount == 1) {
p += _signedBy.deserialize(b,p);
@ -242,6 +294,25 @@ public:
return (p - startAt);
}
inline operator bool() const { return (_id); }
inline bool operator==(const Locator &l) const { return ((_ts == l._ts)&&(_id == l._id)&&(_signedBy == l._signedBy)&&(_physical == l._physical)&&(_virtual == l._virtual)&&(_signatureLength == l._signatureLength)&&(memcmp(_signature,l._signature,_signatureLength) == 0)); }
inline bool operator!=(const Locator &l) const { return (!(*this == l)); }
inline bool operator<(const Locator &l) const
{
if (_id < l._id) return true;
if (_ts < l._ts) return true;
if (_signedBy < l._signedBy) return true;
if (_physical < l._physical) return true;
if (_virtual < l._virtual) return true;
return false;
}
inline bool operator>(const Locator &l) const { return (l < *this); }
inline bool operator<=(const Locator &l) const { return (!(l < *this)); }
inline bool operator>=(const Locator &l) const { return (!(*this < l)); }
inline unsigned long hashCode() const { return (unsigned long)(_id.address().toInt() ^ (uint64_t)_ts); }
private:
int64_t _ts;
Identity _id;

View File

@ -44,19 +44,19 @@ namespace ZeroTier {
class MAC
{
public:
MAC() : _m(0ULL) {}
MAC(const MAC &m) : _m(m._m) {}
inline MAC() : _m(0ULL) {}
inline MAC(const MAC &m) : _m(m._m) {}
MAC(const unsigned char a,const unsigned char b,const unsigned char c,const unsigned char d,const unsigned char e,const unsigned char f) :
inline MAC(const unsigned char a,const unsigned char b,const unsigned char c,const unsigned char d,const unsigned char e,const unsigned char f) :
_m( ((((uint64_t)a) & 0xffULL) << 40) |
((((uint64_t)b) & 0xffULL) << 32) |
((((uint64_t)c) & 0xffULL) << 24) |
((((uint64_t)d) & 0xffULL) << 16) |
((((uint64_t)e) & 0xffULL) << 8) |
(((uint64_t)f) & 0xffULL) ) {}
MAC(const void *bits,unsigned int len) { setTo(bits,len); }
MAC(const Address &ztaddr,uint64_t nwid) { fromAddress(ztaddr,nwid); }
MAC(const uint64_t m) : _m(m & 0xffffffffffffULL) {}
inline MAC(const void *bits,unsigned int len) { setTo(bits,len); }
inline MAC(const Address &ztaddr,uint64_t nwid) { fromAddress(ztaddr,nwid); }
inline MAC(const uint64_t m) : _m(m & 0xffffffffffffULL) {}
/**
* @return MAC in 64-bit integer

View File

@ -53,13 +53,13 @@ namespace ZeroTier {
class MulticastGroup
{
public:
MulticastGroup() :
inline MulticastGroup() :
_mac(),
_adi(0)
{
}
MulticastGroup(const MAC &m,uint32_t a) :
inline MulticastGroup(const MAC &m,uint32_t a) :
_mac(m),
_adi(a)
{

View File

@ -43,7 +43,7 @@ namespace ZeroTier {
class Mutex
{
public:
Mutex() :
inline Mutex() :
nextTicket(0),
nowServing(0)
{
@ -69,29 +69,15 @@ public:
class Lock
{
public:
Lock(Mutex &m) :
_m(&m)
{
m.lock();
}
Lock(const Mutex &m) :
_m(const_cast<Mutex *>(&m))
{
_m->lock();
}
~Lock()
{
_m->unlock();
}
inline Lock(Mutex &m) : _m(&m) { m.lock(); }
inline Lock(const Mutex &m) : _m(const_cast<Mutex *>(&m)) { _m->lock(); }
inline ~Lock() { _m->unlock(); }
private:
Mutex *const _m;
};
private:
Mutex(const Mutex &) {}
inline Mutex(const Mutex &) {}
const Mutex &operator=(const Mutex &) { return *this; }
uint16_t nextTicket;
@ -104,12 +90,12 @@ private:
class Mutex
{
public:
Mutex()
inline Mutex()
{
pthread_mutex_init(&_mh,(const pthread_mutexattr_t *)0);
}
~Mutex()
inline ~Mutex()
{
pthread_mutex_destroy(&_mh);
}
@ -127,19 +113,19 @@ public:
class Lock
{
public:
Lock(Mutex &m) :
inline Lock(Mutex &m) :
_m(&m)
{
m.lock();
}
Lock(const Mutex &m) :
inline Lock(const Mutex &m) :
_m(const_cast<Mutex *>(&m))
{
_m->lock();
}
~Lock()
inline ~Lock()
{
_m->unlock();
}
@ -149,7 +135,7 @@ public:
};
private:
Mutex(const Mutex &) {}
inline Mutex(const Mutex &) {}
const Mutex &operator=(const Mutex &) { return *this; }
pthread_mutex_t _mh;
@ -172,12 +158,12 @@ namespace ZeroTier {
class Mutex
{
public:
Mutex()
inline Mutex()
{
InitializeCriticalSection(&_cs);
}
~Mutex()
inline ~Mutex()
{
DeleteCriticalSection(&_cs);
}
@ -205,19 +191,19 @@ public:
class Lock
{
public:
Lock(Mutex &m) :
inline Lock(Mutex &m) :
_m(&m)
{
m.lock();
}
Lock(const Mutex &m) :
inline Lock(const Mutex &m) :
_m(const_cast<Mutex *>(&m))
{
_m->lock();
}
~Lock()
inline ~Lock()
{
_m->unlock();
}
@ -227,7 +213,7 @@ public:
};
private:
Mutex(const Mutex &) {}
inline Mutex(const Mutex &) {}
const Mutex &operator=(const Mutex &) { return *this; }
CRITICAL_SECTION _cs;

View File

@ -32,7 +32,6 @@
#include "../include/ZeroTierDebug.h"
#include "Constants.hpp"
#include "../version.h"
#include "Network.hpp"
#include "RuntimeEnvironment.hpp"
#include "MAC.hpp"

View File

@ -56,77 +56,6 @@ bool NetworkConfig::toDictionary(Dictionary<ZT_NETWORKCONFIG_DICT_CAPACITY> &d,b
if (!d.add(ZT_NETWORKCONFIG_DICT_KEY_NAME,this->name)) return false;
if (!d.add(ZT_NETWORKCONFIG_DICT_KEY_MTU,(uint64_t)this->mtu)) return false;
#ifdef ZT_SUPPORT_OLD_STYLE_NETCONF
if (includeLegacy) {
if (!d.add(ZT_NETWORKCONFIG_DICT_KEY_ENABLE_BROADCAST_OLD,this->enableBroadcast())) return false;
if (!d.add(ZT_NETWORKCONFIG_DICT_KEY_PRIVATE_OLD,this->isPrivate())) return false;
std::string v4s;
for(unsigned int i=0;i<staticIpCount;++i) {
if (this->staticIps[i].ss_family == AF_INET) {
if (v4s.length() > 0)
v4s.push_back(',');
char buf[64];
v4s.append(this->staticIps[i].toString(buf));
}
}
if (v4s.length() > 0) {
if (!d.add(ZT_NETWORKCONFIG_DICT_KEY_IPV4_STATIC_OLD,v4s.c_str())) return false;
}
std::string v6s;
for(unsigned int i=0;i<staticIpCount;++i) {
if (this->staticIps[i].ss_family == AF_INET6) {
if (v6s.length() > 0)
v6s.push_back(',');
char buf[64];
v6s.append(this->staticIps[i].toString(buf));
}
}
if (v6s.length() > 0) {
if (!d.add(ZT_NETWORKCONFIG_DICT_KEY_IPV6_STATIC_OLD,v6s.c_str())) return false;
}
std::string ets;
unsigned int et = 0;
ZT_VirtualNetworkRuleType lastrt = ZT_NETWORK_RULE_ACTION_ACCEPT;
for(unsigned int i=0;i<ruleCount;++i) {
ZT_VirtualNetworkRuleType rt = (ZT_VirtualNetworkRuleType)(rules[i].t & 0x7f);
if (rt == ZT_NETWORK_RULE_MATCH_ETHERTYPE) {
et = rules[i].v.etherType;
} else if (rt == ZT_NETWORK_RULE_ACTION_ACCEPT) {
if (((int)lastrt < 32)||(lastrt == ZT_NETWORK_RULE_MATCH_ETHERTYPE)) {
if (ets.length() > 0)
ets.push_back(',');
char tmp2[16];
ets.append(Utils::hex((uint16_t)et,tmp2));
}
et = 0;
}
lastrt = rt;
}
if (ets.length() > 0) {
if (!d.add(ZT_NETWORKCONFIG_DICT_KEY_ALLOWED_ETHERNET_TYPES_OLD,ets.c_str())) return false;
}
if (this->com) {
if (!d.add(ZT_NETWORKCONFIG_DICT_KEY_CERTIFICATE_OF_MEMBERSHIP_OLD,this->com.toString().c_str())) return false;
}
std::string ab;
for(unsigned int i=0;i<this->specialistCount;++i) {
if ((this->specialists[i] & ZT_NETWORKCONFIG_SPECIALIST_TYPE_ACTIVE_BRIDGE) != 0) {
if (ab.length() > 0)
ab.push_back(',');
char tmp2[16];
ab.append(Address(this->specialists[i]).toString(tmp2));
}
}
if (ab.length() > 0) {
if (!d.add(ZT_NETWORKCONFIG_DICT_KEY_ACTIVE_BRIDGES_OLD,ab.c_str())) return false;
}
}
#endif // ZT_SUPPORT_OLD_STYLE_NETCONF
// Then add binary blobs
if (this->com) {
@ -201,7 +130,7 @@ bool NetworkConfig::toDictionary(Dictionary<ZT_NETWORKCONFIG_DICT_CAPACITY> &d,b
bool NetworkConfig::fromDictionary(const Dictionary<ZT_NETWORKCONFIG_DICT_CAPACITY> &d)
{
static const NetworkConfig NIL_NC;
Buffer<ZT_NETWORKCONFIG_DICT_CAPACITY> *tmp = new Buffer<ZT_NETWORKCONFIG_DICT_CAPACITY>();
Buffer<ZT_NETWORKCONFIG_DICT_CAPACITY> *const tmp = new Buffer<ZT_NETWORKCONFIG_DICT_CAPACITY>();
try {
*this = NIL_NC;
@ -232,65 +161,8 @@ bool NetworkConfig::fromDictionary(const Dictionary<ZT_NETWORKCONFIG_DICT_CAPACI
this->mtu = ZT_MAX_MTU;
if (d.getUI(ZT_NETWORKCONFIG_DICT_KEY_VERSION,0) < 6) {
#ifdef ZT_SUPPORT_OLD_STYLE_NETCONF
char tmp2[1024];
// Decode legacy fields if version is old
if (d.getB(ZT_NETWORKCONFIG_DICT_KEY_ENABLE_BROADCAST_OLD))
this->flags |= ZT_NETWORKCONFIG_FLAG_ENABLE_BROADCAST;
this->flags |= ZT_NETWORKCONFIG_FLAG_ENABLE_IPV6_NDP_EMULATION; // always enable for old-style netconf
this->type = (d.getB(ZT_NETWORKCONFIG_DICT_KEY_PRIVATE_OLD,true)) ? ZT_NETWORK_TYPE_PRIVATE : ZT_NETWORK_TYPE_PUBLIC;
if (d.get(ZT_NETWORKCONFIG_DICT_KEY_IPV4_STATIC_OLD,tmp2,sizeof(tmp2)) > 0) {
char *saveptr = (char *)0;
for(char *f=Utils::stok(tmp2,",",&saveptr);(f);f=Utils::stok((char *)0,",",&saveptr)) {
if (this->staticIpCount >= ZT_MAX_ZT_ASSIGNED_ADDRESSES) break;
InetAddress ip(f);
if (!ip.isNetwork())
this->staticIps[this->staticIpCount++] = ip;
}
}
if (d.get(ZT_NETWORKCONFIG_DICT_KEY_IPV6_STATIC_OLD,tmp2,sizeof(tmp2)) > 0) {
char *saveptr = (char *)0;
for(char *f=Utils::stok(tmp2,",",&saveptr);(f);f=Utils::stok((char *)0,",",&saveptr)) {
if (this->staticIpCount >= ZT_MAX_ZT_ASSIGNED_ADDRESSES) break;
InetAddress ip(f);
if (!ip.isNetwork())
this->staticIps[this->staticIpCount++] = ip;
}
}
if (d.get(ZT_NETWORKCONFIG_DICT_KEY_CERTIFICATE_OF_MEMBERSHIP_OLD,tmp2,sizeof(tmp2)) > 0) {
this->com.fromString(tmp2);
}
if (d.get(ZT_NETWORKCONFIG_DICT_KEY_ALLOWED_ETHERNET_TYPES_OLD,tmp2,sizeof(tmp2)) > 0) {
char *saveptr = (char *)0;
for(char *f=Utils::stok(tmp2,",",&saveptr);(f);f=Utils::stok((char *)0,",",&saveptr)) {
unsigned int et = Utils::hexStrToUInt(f) & 0xffff;
if ((this->ruleCount + 2) > ZT_MAX_NETWORK_RULES) break;
if (et > 0) {
this->rules[this->ruleCount].t = (uint8_t)ZT_NETWORK_RULE_MATCH_ETHERTYPE;
this->rules[this->ruleCount].v.etherType = (uint16_t)et;
++this->ruleCount;
}
this->rules[this->ruleCount++].t = (uint8_t)ZT_NETWORK_RULE_ACTION_ACCEPT;
}
} else {
this->rules[0].t = ZT_NETWORK_RULE_ACTION_ACCEPT;
this->ruleCount = 1;
}
if (d.get(ZT_NETWORKCONFIG_DICT_KEY_ACTIVE_BRIDGES_OLD,tmp2,sizeof(tmp2)) > 0) {
char *saveptr = (char *)0;
for(char *f=Utils::stok(tmp2,",",&saveptr);(f);f=Utils::stok((char *)0,",",&saveptr)) {
this->addSpecialist(Address(Utils::hexStrToU64(f)),ZT_NETWORKCONFIG_SPECIALIST_TYPE_ACTIVE_BRIDGE);
}
}
#else
delete tmp;
return false;
#endif // ZT_SUPPORT_OLD_STYLE_NETCONF
} else {
// Otherwise we can use the new fields
this->flags = d.getUI(ZT_NETWORKCONFIG_DICT_KEY_FLAGS,0);
@ -369,10 +241,6 @@ bool NetworkConfig::fromDictionary(const Dictionary<ZT_NETWORKCONFIG_DICT_CAPACI
}
}
//printf("~~~\n%s\n~~~\n",d.data());
//dump();
//printf("~~~\n");
delete tmp;
return true;
} catch ( ... ) {

View File

@ -216,7 +216,7 @@ namespace ZeroTier {
class NetworkConfig
{
public:
NetworkConfig() :
inline NetworkConfig() :
networkId(0),
timestamp(0),
credentialTimeMaxDelta(0),

View File

@ -30,8 +30,6 @@
#include <string.h>
#include <stdint.h>
#include "../version.h"
#include "Constants.hpp"
#include "SharedPtr.hpp"
#include "Node.hpp"
@ -573,10 +571,6 @@ bool Node::shouldUsePathForZeroTierTraffic(void *tPtr,const Address &ztaddr,cons
{
if (!Path::isAddressValidForPath(remoteAddress))
return false;
if (RR->topology->isProhibitedEndpoint(ztaddr,remoteAddress))
return false;
{
Mutex::Lock _l(_networks_m);
Hashtable< uint64_t,SharedPtr<Network> >::Iterator i(_networks);
@ -591,7 +585,6 @@ bool Node::shouldUsePathForZeroTierTraffic(void *tPtr,const Address &ztaddr,cons
}
}
}
return ( (_cb.pathCheckFunction) ? (_cb.pathCheckFunction(reinterpret_cast<ZT_Node *>(this),_uPtr,tPtr,ztaddr.toInt(),localSocket,reinterpret_cast<const struct sockaddr_storage *>(&remoteAddress)) != 0) : true);
}

View File

@ -56,7 +56,7 @@ public:
*
* It must be initialized with init().
*/
OutboundMulticast() {}
inline OutboundMulticast() {}
/**
* Initialize outbound multicast

View File

@ -70,16 +70,19 @@
* 9 - 1.2.0 ... 1.2.14
* 10 - 1.4.0 ... 1.6.0
* + Multipath capability and load balancing
* 11 - 1.6.0 ... CURRENT
* 11 - 2.0.0 ... CURRENT
* + Peer-to-peer multicast replication (optional)
* + Old planet/moon stuff is DEAD!
* + AES256-GCM encryption is now the default
* + NIST P-384 type identities now supported (25519 still default)
* + Min proto version is now 8 (1.1.17 and newer)
*/
#define ZT_PROTO_VERSION 11
/**
* Minimum supported protocol version
*/
#define ZT_PROTO_VERSION_MIN 4
#define ZT_PROTO_VERSION_MIN 8
/**
* Maximum hop count allowed by packet structure (3 bits, 0-7)
@ -406,18 +409,18 @@ public:
class Fragment : public Buffer<ZT_PROTO_MAX_PACKET_LENGTH>
{
public:
Fragment() :
inline Fragment() :
Buffer<ZT_PROTO_MAX_PACKET_LENGTH>()
{
}
template<unsigned int C2>
Fragment(const Buffer<C2> &b) :
inline Fragment(const Buffer<C2> &b) :
Buffer<ZT_PROTO_MAX_PACKET_LENGTH>(b)
{
}
Fragment(const void *data,unsigned int len) :
inline Fragment(const void *data,unsigned int len) :
Buffer<ZT_PROTO_MAX_PACKET_LENGTH>(data,len)
{
}
@ -431,7 +434,7 @@ public:
* @param fragNo Which fragment (>= 1, since 0 is Packet with end chopped off)
* @param fragTotal Total number of fragments (including 0)
*/
Fragment(const Packet &p,unsigned int fragStart,unsigned int fragLen,unsigned int fragNo,unsigned int fragTotal)
inline Fragment(const Packet &p,unsigned int fragStart,unsigned int fragLen,unsigned int fragNo,unsigned int fragTotal)
{
init(p,fragStart,fragLen,fragNo,fragTotal);
}
@ -1003,12 +1006,12 @@ public:
};
template<unsigned int C2>
Packet(const Buffer<C2> &b) :
inline Packet(const Buffer<C2> &b) :
Buffer<ZT_PROTO_MAX_PACKET_LENGTH>(b)
{
}
Packet(const void *data,unsigned int len) :
inline Packet(const void *data,unsigned int len) :
Buffer<ZT_PROTO_MAX_PACKET_LENGTH>(data,len)
{
}
@ -1020,7 +1023,7 @@ public:
* Use the header access methods (setDestination() and friends) to fill out
* the header. Payload should be appended; initial size is header size.
*/
Packet() :
inline Packet() :
Buffer<ZT_PROTO_MAX_PACKET_LENGTH>(ZT_PROTO_MIN_PACKET_LENGTH)
{
Utils::getSecureRandom(field(ZT_PACKET_IDX_IV,8),8);
@ -1036,7 +1039,7 @@ public:
* @param prototype Prototype packet
* @param dest Destination ZeroTier address for new packet
*/
Packet(const Packet &prototype,const Address &dest) :
inline Packet(const Packet &prototype,const Address &dest) :
Buffer<ZT_PROTO_MAX_PACKET_LENGTH>(prototype)
{
Utils::getSecureRandom(field(ZT_PACKET_IDX_IV,8),8);
@ -1050,7 +1053,7 @@ public:
* @param source Source ZT address
* @param v Verb
*/
Packet(const Address &dest,const Address &source,const Verb v) :
inline Packet(const Address &dest,const Address &source,const Verb v) :
Buffer<ZT_PROTO_MAX_PACKET_LENGTH>(ZT_PROTO_MIN_PACKET_LENGTH)
{
Utils::getSecureRandom(field(ZT_PACKET_IDX_IV,8),8);

View File

@ -68,9 +68,9 @@ public:
class HashKey
{
public:
HashKey() {}
inline HashKey() {}
HashKey(const int64_t l,const InetAddress &r)
inline HashKey(const int64_t l,const InetAddress &r)
{
if (r.ss_family == AF_INET) {
_k[0] = (uint64_t)reinterpret_cast<const struct sockaddr_in *>(&r)->sin_addr.s_addr;
@ -94,7 +94,7 @@ public:
uint64_t _k[3];
};
Path() :
inline Path() :
_lastOut(0),
_lastIn(0),
_lastTrustEstablishedPacketReceived(0),
@ -127,7 +127,7 @@ public:
memset(_addrString, 0, sizeof(_addrString));
}
Path(const int64_t localSocket,const InetAddress &addr) :
inline Path(const int64_t localSocket,const InetAddress &addr) :
_lastOut(0),
_lastIn(0),
_lastTrustEstablishedPacketReceived(0),

View File

@ -24,7 +24,6 @@
* of your own application.
*/
#include "../version.h"
#include "Constants.hpp"
#include "Peer.hpp"
#include "Node.hpp"

View File

@ -57,10 +57,10 @@ class Peer
friend class SharedPtr<Peer>;
private:
Peer() {} // disabled to prevent bugs -- should not be constructed uninitialized
inline Peer() {} // disabled to prevent bugs -- should not be constructed uninitialized
public:
~Peer() { Utils::burn(_key,sizeof(_key)); }
inline ~Peer() { Utils::burn(_key,sizeof(_key)); }
/**
* Construct a new peer

View File

@ -25,7 +25,7 @@ typedef struct poly1305_context {
unsigned char opaque[136];
} poly1305_context;
#if (defined(_MSC_VER) || defined(__GNUC__)) && (defined(__amd64) || defined(__amd64__) || defined(__x86_64) || defined(__x86_64__) || defined(__AMD64) || defined(__AMD64__) || defined(_M_X64))
#if (defined(_MSC_VER) || defined(__GNUC__) || defined(__clang)) && (defined(__amd64) || defined(__amd64__) || defined(__x86_64) || defined(__x86_64__) || defined(__AMD64) || defined(__AMD64__) || defined(_M_X64))
//////////////////////////////////////////////////////////////////////////////
// 128-bit implementation for MSC and GCC from Poly1305-donna
@ -136,7 +136,6 @@ static inline void poly1305_blocks(poly1305_state_internal_t *st, const unsigned
unsigned long long r0,r1,r2;
unsigned long long s1,s2;
unsigned long long h0,h1,h2;
unsigned long long c;
uint128_t d0,d1,d2,d;
r0 = st->r[0];
@ -167,7 +166,7 @@ static inline void poly1305_blocks(poly1305_state_internal_t *st, const unsigned
MUL(d2, h0, r2); MUL(d, h1, r1); ADD(d2, d); MUL(d, h2, r0); ADD(d2, d);
/* (partial) h %= p */
c = SHR(d0, 44); h0 = LO(d0) & 0xfffffffffff;
unsigned long long c = SHR(d0, 44); h0 = LO(d0) & 0xfffffffffff;
ADDLO(d1, c); c = SHR(d1, 44); h1 = LO(d1) & 0xfffffffffff;
ADDLO(d2, c); c = SHR(d2, 42); h2 = LO(d2) & 0x3ffffffffff;
h0 += c * 5; c = (h0 >> 44); h0 = h0 & 0xfffffffffff;
@ -324,8 +323,6 @@ poly1305_blocks(poly1305_state_internal_t *st, const unsigned char *m, size_t by
unsigned long r0,r1,r2,r3,r4;
unsigned long s1,s2,s3,s4;
unsigned long h0,h1,h2,h3,h4;
unsigned long long d0,d1,d2,d3,d4;
unsigned long c;
r0 = st->r[0];
r1 = st->r[1];
@ -353,14 +350,14 @@ poly1305_blocks(poly1305_state_internal_t *st, const unsigned char *m, size_t by
h4 += (U8TO32(m+12) >> 8) | hibit;
/* h *= r */
d0 = ((unsigned long long)h0 * r0) + ((unsigned long long)h1 * s4) + ((unsigned long long)h2 * s3) + ((unsigned long long)h3 * s2) + ((unsigned long long)h4 * s1);
d1 = ((unsigned long long)h0 * r1) + ((unsigned long long)h1 * r0) + ((unsigned long long)h2 * s4) + ((unsigned long long)h3 * s3) + ((unsigned long long)h4 * s2);
d2 = ((unsigned long long)h0 * r2) + ((unsigned long long)h1 * r1) + ((unsigned long long)h2 * r0) + ((unsigned long long)h3 * s4) + ((unsigned long long)h4 * s3);
d3 = ((unsigned long long)h0 * r3) + ((unsigned long long)h1 * r2) + ((unsigned long long)h2 * r1) + ((unsigned long long)h3 * r0) + ((unsigned long long)h4 * s4);
d4 = ((unsigned long long)h0 * r4) + ((unsigned long long)h1 * r3) + ((unsigned long long)h2 * r2) + ((unsigned long long)h3 * r1) + ((unsigned long long)h4 * r0);
unsigned long long d0 = ((unsigned long long)h0 * r0) + ((unsigned long long)h1 * s4) + ((unsigned long long)h2 * s3) + ((unsigned long long)h3 * s2) + ((unsigned long long)h4 * s1);
unsigned long long d1 = ((unsigned long long)h0 * r1) + ((unsigned long long)h1 * r0) + ((unsigned long long)h2 * s4) + ((unsigned long long)h3 * s3) + ((unsigned long long)h4 * s2);
unsigned long long d2 = ((unsigned long long)h0 * r2) + ((unsigned long long)h1 * r1) + ((unsigned long long)h2 * r0) + ((unsigned long long)h3 * s4) + ((unsigned long long)h4 * s3);
unsigned long long d3 = ((unsigned long long)h0 * r3) + ((unsigned long long)h1 * r2) + ((unsigned long long)h2 * r1) + ((unsigned long long)h3 * r0) + ((unsigned long long)h4 * s4);
unsigned long long d4 = ((unsigned long long)h0 * r4) + ((unsigned long long)h1 * r3) + ((unsigned long long)h2 * r2) + ((unsigned long long)h3 * r1) + ((unsigned long long)h4 * r0);
/* (partial) h %= p */
c = (unsigned long)(d0 >> 26); h0 = (unsigned long)d0 & 0x3ffffff;
unsigned long c = (unsigned long)(d0 >> 26); h0 = (unsigned long)d0 & 0x3ffffff;
d1 += c; c = (unsigned long)(d1 >> 26); h1 = (unsigned long)d1 & 0x3ffffff;
d2 += c; c = (unsigned long)(d2 >> 26); h2 = (unsigned long)d2 & 0x3ffffff;
d3 += c; c = (unsigned long)(d3 >> 26); h3 = (unsigned long)d3 & 0x3ffffff;

View File

@ -31,8 +31,8 @@ namespace ZeroTier {
class Salsa20
{
public:
Salsa20() {}
~Salsa20() { Utils::burn(&_state,sizeof(_state)); }
inline Salsa20() {}
inline ~Salsa20() { Utils::burn(&_state,sizeof(_state)); }
/**
* XOR d with s
@ -114,10 +114,7 @@ public:
* @param key 256-bit (32 byte) key
* @param iv 64-bit initialization vector
*/
Salsa20(const void *key,const void *iv)
{
init(key,iv);
}
inline Salsa20(const void *key,const void *iv) { init(key,iv); }
/**
* Initialize cipher

View File

@ -31,7 +31,6 @@
#include <utility>
#include <stdexcept>
#include "../version.h"
#include "../include/ZeroTierOne.h"
#include "Constants.hpp"

View File

@ -65,7 +65,7 @@ class Tag : public Credential
public:
static inline Credential::Type credentialType() { return Credential::CREDENTIAL_TYPE_TAG; }
Tag() :
inline Tag() :
_id(0),
_value(0),
_networkId(0),
@ -81,7 +81,7 @@ public:
* @param id Tag ID
* @param value Tag value
*/
Tag(const uint64_t nwid,const int64_t ts,const Address &issuedTo,const uint32_t id,const uint32_t value) :
inline Tag(const uint64_t nwid,const int64_t ts,const Address &issuedTo,const uint32_t id,const uint32_t value) :
_id(id),
_value(value),
_networkId(nwid),

View File

@ -1,203 +0,0 @@
/*
* ZeroTier One - Network Virtualization Everywhere
* Copyright (C) 2011-2019 ZeroTier, Inc. https://www.zerotier.com/
*
* 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/>.
*
* --
*
* You can be released from the requirements of the license by purchasing
* a commercial license. Buying such a license is mandatory as soon as you
* develop commercial closed-source software that incorporates or links
* directly against ZeroTier software without disclosing the source code
* of your own application.
*/
#include "Constants.hpp"
#include "Topology.hpp"
#include "RuntimeEnvironment.hpp"
#include "Node.hpp"
#include "Network.hpp"
#include "NetworkConfig.hpp"
#include "Buffer.hpp"
#include "Switch.hpp"
namespace ZeroTier {
Topology::Topology(const RuntimeEnvironment *renv,void *tPtr) :
RR(renv),
_numConfiguredPhysicalPaths(0)
{
}
Topology::~Topology()
{
Hashtable< Address,SharedPtr<Peer> >::Iterator i(_peers);
Address *a = (Address *)0;
SharedPtr<Peer> *p = (SharedPtr<Peer> *)0;
while (i.next(a,p))
_savePeer((void *)0,*p);
}
SharedPtr<Peer> Topology::addPeer(void *tPtr,const SharedPtr<Peer> &peer)
{
SharedPtr<Peer> np;
{
Mutex::Lock _l(_peers_m);
SharedPtr<Peer> &hp = _peers[peer->address()];
if (!hp)
hp = peer;
np = hp;
}
return np;
}
SharedPtr<Peer> Topology::getPeer(void *tPtr,const Address &zta)
{
if (zta == RR->identity.address())
return SharedPtr<Peer>();
{
Mutex::Lock _l(_peers_m);
const SharedPtr<Peer> *const ap = _peers.get(zta);
if (ap)
return *ap;
}
try {
Buffer<ZT_PEER_MAX_SERIALIZED_STATE_SIZE> buf;
uint64_t idbuf[2]; idbuf[0] = zta.toInt(); idbuf[1] = 0;
int len = RR->node->stateObjectGet(tPtr,ZT_STATE_OBJECT_PEER,idbuf,buf.unsafeData(),ZT_PEER_MAX_SERIALIZED_STATE_SIZE);
if (len > 0) {
buf.setSize(len);
Mutex::Lock _l(_peers_m);
SharedPtr<Peer> &ap = _peers[zta];
if (ap)
return ap;
ap = Peer::deserializeFromCache(RR->node->now(),tPtr,buf,RR);
if (!ap) {
_peers.erase(zta);
}
return SharedPtr<Peer>();
}
} catch ( ... ) {} // ignore invalid identities or other strange failures
return SharedPtr<Peer>();
}
Identity Topology::getIdentity(void *tPtr,const Address &zta)
{
if (zta == RR->identity.address()) {
return RR->identity;
} else {
Mutex::Lock _l(_peers_m);
const SharedPtr<Peer> *const ap = _peers.get(zta);
if (ap)
return (*ap)->identity();
}
return Identity();
}
SharedPtr<Peer> Topology::getUpstreamPeer()
{
return SharedPtr<Peer>();
}
bool Topology::isUpstream(const Identity &id) const
{
return false;
}
ZT_PeerRole Topology::role(const Address &ztaddr) const
{
return ZT_PEER_ROLE_LEAF;
}
bool Topology::isProhibitedEndpoint(const Address &ztaddr,const InetAddress &ipaddr) const
{
return false;
}
void Topology::doPeriodicTasks(void *tPtr,int64_t now)
{
{
Mutex::Lock _l1(_peers_m);
Hashtable< Address,SharedPtr<Peer> >::Iterator i(_peers);
Address *a = (Address *)0;
SharedPtr<Peer> *p = (SharedPtr<Peer> *)0;
while (i.next(a,p)) {
if (!(*p)->isAlive(now)) {
_savePeer(tPtr,*p);
_peers.erase(*a);
}
}
}
{
Mutex::Lock _l(_paths_m);
Hashtable< Path::HashKey,SharedPtr<Path> >::Iterator i(_paths);
Path::HashKey *k = (Path::HashKey *)0;
SharedPtr<Path> *p = (SharedPtr<Path> *)0;
while (i.next(k,p)) {
if (p->references() <= 1)
_paths.erase(*k);
}
}
}
void Topology::setPhysicalPathConfiguration(const struct sockaddr_storage *pathNetwork,const ZT_PhysicalPathConfiguration *pathConfig)
{
if (!pathNetwork) {
_numConfiguredPhysicalPaths = 0;
} else {
std::map<InetAddress,ZT_PhysicalPathConfiguration> cpaths;
for(unsigned int i=0,j=_numConfiguredPhysicalPaths;i<j;++i)
cpaths[_physicalPathConfig[i].first] = _physicalPathConfig[i].second;
if (pathConfig) {
ZT_PhysicalPathConfiguration pc(*pathConfig);
if (pc.mtu <= 0)
pc.mtu = ZT_DEFAULT_PHYSMTU;
else if (pc.mtu < ZT_MIN_PHYSMTU)
pc.mtu = ZT_MIN_PHYSMTU;
else if (pc.mtu > ZT_MAX_PHYSMTU)
pc.mtu = ZT_MAX_PHYSMTU;
cpaths[*(reinterpret_cast<const InetAddress *>(pathNetwork))] = pc;
} else {
cpaths.erase(*(reinterpret_cast<const InetAddress *>(pathNetwork)));
}
unsigned int cnt = 0;
for(std::map<InetAddress,ZT_PhysicalPathConfiguration>::const_iterator i(cpaths.begin());((i!=cpaths.end())&&(cnt<ZT_MAX_CONFIGURABLE_PATHS));++i) {
_physicalPathConfig[cnt].first = i->first;
_physicalPathConfig[cnt].second = i->second;
++cnt;
}
_numConfiguredPhysicalPaths = cnt;
}
}
void Topology::_savePeer(void *tPtr,const SharedPtr<Peer> &peer)
{
try {
Buffer<ZT_PEER_MAX_SERIALIZED_STATE_SIZE> buf;
peer->serializeForCache(buf);
uint64_t tmpid[2]; tmpid[0] = peer->address().toInt(); tmpid[1] = 0;
RR->node->stateObjectPut(tPtr,ZT_STATE_OBJECT_PEER,tmpid,buf.data(),buf.size());
} catch ( ... ) {} // sanity check, discard invalid entries
}
} // namespace ZeroTier

View File

@ -56,8 +56,10 @@ class RuntimeEnvironment;
class Topology
{
public:
Topology(const RuntimeEnvironment *renv,void *tPtr);
~Topology();
inline Topology(const RuntimeEnvironment *renv,void *tPtr) :
RR(renv),
_numConfiguredPhysicalPaths(0) {}
inline ~Topology() {}
/**
* Add a peer to database
@ -69,7 +71,18 @@ public:
* @param peer Peer to add
* @return New or existing peer (should replace 'peer')
*/
SharedPtr<Peer> addPeer(void *tPtr,const SharedPtr<Peer> &peer);
inline SharedPtr<Peer> addPeer(void *tPtr,const SharedPtr<Peer> &peer)
{
SharedPtr<Peer> np;
{
Mutex::Lock _l(_peers_m);
SharedPtr<Peer> &hp = _peers[peer->address()];
if (!hp)
hp = peer;
np = hp;
}
return np;
}
/**
* Get a peer from its address
@ -78,15 +91,37 @@ public:
* @param zta ZeroTier address of peer
* @return Peer or NULL if not found
*/
SharedPtr<Peer> getPeer(void *tPtr,const Address &zta);
inline SharedPtr<Peer> getPeer(void *tPtr,const Address &zta) const
{
if (zta == RR->identity.address())
return SharedPtr<Peer>();
{
Mutex::Lock _l(_peers_m);
const SharedPtr<Peer> *const ap = _peers.get(zta);
if (ap)
return *ap;
}
return SharedPtr<Peer>();
}
/**
* @param tPtr Thread pointer to be handed through to any callbacks called as a result of this call
* @param zta ZeroTier address of peer
* @return Identity or NULL identity if not found
*/
Identity getIdentity(void *tPtr,const Address &zta);
inline Identity getIdentity(void *tPtr,const Address &zta)
{
if (zta == RR->identity.address()) {
return RR->identity;
} else {
Mutex::Lock _l(_peers_m);
const SharedPtr<Peer> *const ap = _peers.get(zta);
if (ap)
return (*ap)->identity();
}
return Identity();
}
/**
* Get a peer only if it is presently in memory (no disk cache)
*
@ -127,35 +162,20 @@ public:
*
* @return Upstream or NULL if none available
*/
SharedPtr<Peer> getUpstreamPeer();
inline SharedPtr<Peer> getUpstreamPeer() const
{
return SharedPtr<Peer>();
}
/**
* @param id Identity to check
* @return True if this is a root server or a network preferred relay from one of our networks
*/
bool isUpstream(const Identity &id) const;
/**
* @param ztaddr ZeroTier address
* @return Peer role for this device
*/
ZT_PeerRole role(const Address &ztaddr) const;
/**
* Check for prohibited endpoints
*
* Right now this returns true if the designated ZT address is a root and if
* the IP (IP only, not port) does not equal any of the IPs defined in the
* current World. This is an extra little security feature in case root keys
* get appropriated or something.
*
* Otherwise it returns false.
*
* @param ztaddr ZeroTier address
* @param ipaddr IP address
* @return True if this ZT/IP pair should not be allowed to be used
*/
bool isProhibitedEndpoint(const Address &ztaddr,const InetAddress &ipaddr) const;
inline bool isUpstream(const Identity &id) const
{
return false;
}
inline ZT_PeerRole role(const Address &ztaddr) const
{
return ZT_PEER_ROLE_LEAF;
}
/**
* Gets upstreams to contact and their stable endpoints (if known)
@ -175,10 +195,30 @@ public:
return std::vector<Address>();
}
/**
* Clean and flush database
*/
void doPeriodicTasks(void *tPtr,int64_t now);
inline void doPeriodicTasks(void *tPtr,int64_t now)
{
{
Mutex::Lock _l1(_peers_m);
Hashtable< Address,SharedPtr<Peer> >::Iterator i(_peers);
Address *a = (Address *)0;
SharedPtr<Peer> *p = (SharedPtr<Peer> *)0;
while (i.next(a,p)) {
if (!(*p)->isAlive(now)) {
_peers.erase(*a);
}
}
}
{
Mutex::Lock _l(_paths_m);
Hashtable< Path::HashKey,SharedPtr<Path> >::Iterator i(_paths);
Path::HashKey *k = (Path::HashKey *)0;
SharedPtr<Path> *p = (SharedPtr<Path> *)0;
while (i.next(k,p)) {
if (p->references() <= 1)
_paths.erase(*k);
}
}
}
/**
* @param now Current time
@ -218,7 +258,7 @@ public:
}
/**
* @return All currently active peers by address (unsorted)
* @return All peers by address (unsorted)
*/
inline std::vector< std::pair< Address,SharedPtr<Peer> > > allPeers() const
{
@ -294,21 +334,46 @@ public:
/**
* Set or clear physical path configuration (called via Node::setPhysicalPathConfiguration)
*/
void setPhysicalPathConfiguration(const struct sockaddr_storage *pathNetwork,const ZT_PhysicalPathConfiguration *pathConfig);
inline void setPhysicalPathConfiguration(const struct sockaddr_storage *pathNetwork,const ZT_PhysicalPathConfiguration *pathConfig)
{
if (!pathNetwork) {
_numConfiguredPhysicalPaths = 0;
} else {
std::map<InetAddress,ZT_PhysicalPathConfiguration> cpaths;
for(unsigned int i=0,j=_numConfiguredPhysicalPaths;i<j;++i)
cpaths[_physicalPathConfig[i].first] = _physicalPathConfig[i].second;
if (pathConfig) {
ZT_PhysicalPathConfiguration pc(*pathConfig);
if (pc.mtu <= 0)
pc.mtu = ZT_DEFAULT_PHYSMTU;
else if (pc.mtu < ZT_MIN_PHYSMTU)
pc.mtu = ZT_MIN_PHYSMTU;
else if (pc.mtu > ZT_MAX_PHYSMTU)
pc.mtu = ZT_MAX_PHYSMTU;
cpaths[*(reinterpret_cast<const InetAddress *>(pathNetwork))] = pc;
} else {
cpaths.erase(*(reinterpret_cast<const InetAddress *>(pathNetwork)));
}
unsigned int cnt = 0;
for(std::map<InetAddress,ZT_PhysicalPathConfiguration>::const_iterator i(cpaths.begin());((i!=cpaths.end())&&(cnt<ZT_MAX_CONFIGURABLE_PATHS));++i) {
_physicalPathConfig[cnt].first = i->first;
_physicalPathConfig[cnt].second = i->second;
++cnt;
}
_numConfiguredPhysicalPaths = cnt;
}
}
private:
Identity _getIdentity(void *tPtr,const Address &zta);
void _memoizeUpstreams(void *tPtr);
void _savePeer(void *tPtr,const SharedPtr<Peer> &peer);
const RuntimeEnvironment *const RR;
std::pair<InetAddress,ZT_PhysicalPathConfiguration> _physicalPathConfig[ZT_MAX_CONFIGURABLE_PATHS];
unsigned int _numConfiguredPhysicalPaths;
Hashtable< Address,SharedPtr<Peer> > _peers;
Mutex _peers_m;
Hashtable< Path::HashKey,SharedPtr<Path> > _paths;
Mutex _paths_m;
};

View File

@ -89,7 +89,7 @@ public:
class RuleResultLog
{
public:
RuleResultLog() {}
inline RuleResultLog() {}
inline void log(const unsigned int rn,const uint8_t thisRuleMatches,const uint8_t thisSetMatches)
{
@ -112,7 +112,7 @@ public:
uint8_t _l[ZT_MAX_NETWORK_RULES / 2];
};
Trace(const RuntimeEnvironment *renv) :
inline Trace(const RuntimeEnvironment *renv) :
RR(renv),
_byNet(8)
{

View File

@ -338,28 +338,16 @@ public:
/**
* Count the number of bits set in an integer
*
* @param v 32-bit integer
* @return Number of bits set in this integer (0-32)
* @param v Unsigned integer
* @return Number of bits set in this integer (0-bits in integer)
*/
static inline uint32_t countBits(uint32_t v)
template<typename T>
static inline uint64_t countBits(T v)
{
v = v - ((v >> 1) & (uint32_t)0x55555555);
v = (v & (uint32_t)0x33333333) + ((v >> 2) & (uint32_t)0x33333333);
return ((((v + (v >> 4)) & (uint32_t)0xF0F0F0F) * (uint32_t)0x1010101) >> 24);
}
/**
* Count the number of bits set in an integer
*
* @param v 64-bit integer
* @return Number of bits set in this integer (0-64)
*/
static inline uint64_t countBits(uint64_t v)
{
v = v - ((v >> 1) & (uint64_t)~(uint64_t)0/3);
v = (v & (uint64_t)~(uint64_t)0/15*3) + ((v >> 2) & (uint64_t)~(uint64_t)0/15*3);
v = (v + (v >> 4)) & (uint64_t)~(uint64_t)0/255*15;
return (uint64_t)(v * ((uint64_t)~(uint64_t)0/255)) >> 56;
v = v - ((v >> 1) & (T)~(T)0/3);
v = (v & (T)~(T)0/15*3) + ((v >> 2) & (T)~(T)0/15*3);
v = (v + (v >> 4)) & (T)~(T)0/255*15;
return (T)(v * ((~((T)0))/((T)255))) >> ((sizeof(T) - 1) * 8);
}
/**

View File

@ -24,7 +24,6 @@ CORE_OBJS=\
node/SHA512.o \
node/Switch.o \
node/Tag.o \
node/Topology.o \
node/Trace.o \
node/Utils.o

View File

@ -696,6 +696,27 @@ static int testOther()
char buf2[4096];
char buf3[1024];
std::cout << "[other] Testing bit count... "; std::cout.flush();
uint32_t i32 = 0;
uint64_t i64 = 0;
for(int i=0;i<=32;++i) {
if ((int)Utils::countBits(i32) != i) {
std::cout << "FAIL!" << std::endl;
return -1;
}
i32 <<= 1;
i32 |= 1;
}
for(int i=0;i<=64;++i) {
if ((int)Utils::countBits(i64) != i) {
std::cout << "FAIL!" << std::endl;
return -1;
}
i64 <<= 1;
i64 |= 1;
}
std::cout << "PASS" << std::endl;
std::cout << "[other] Testing hex/unhex... "; std::cout.flush();
Utils::getSecureRandom(buf,(unsigned int)sizeof(buf));
Utils::hex(buf,(unsigned int)sizeof(buf),buf2);

View File

@ -38,7 +38,6 @@
#include <mutex>
#include <condition_variable>
#include "../version.h"
#include "../include/ZeroTierOne.h"
#include "../node/Constants.hpp"

View File

@ -30,7 +30,6 @@
#include <stdint.h>
#include "../node/Constants.hpp"
#include "../version.h"
#ifdef __WINDOWS__
#include <WinSock2.h>

View File

@ -51,11 +51,4 @@
*/
#define ZEROTIER_ONE_VERSION_BUILD @ZEROTIER_ONE_VERSION_BUILD@
#ifndef ZT_BUILD_ARCHITECTURE
#define ZT_BUILD_ARCHITECTURE 0
#endif
#ifndef ZT_BUILD_PLATFORM
#define ZT_BUILD_PLATFORM 0
#endif
#endif