This commit is contained in:
Adam Ierymenko 2017-06-05 12:15:28 -07:00
parent aa06470cb6
commit 9b287392a4
7 changed files with 636 additions and 294 deletions

View file

@ -297,7 +297,7 @@ enum ZT_ResultCode
* @param x Result code * @param x Result code
* @return True if result code indicates a fatal error * @return True if result code indicates a fatal error
*/ */
#define ZT_ResultCode_isFatal(x) ((((int)(x)) > 0)&&(((int)(x)) < 1000)) #define ZT_ResultCode_isFatal(x) ((((int)(x)) >= 100)&&(((int)(x)) < 1000))
/** /**
* Status codes sent to status update callback when things happen * Status codes sent to status update callback when things happen
@ -393,6 +393,13 @@ enum ZT_Event
/** /**
* User message used with ZT_EVENT_USER_MESSAGE * User message used with ZT_EVENT_USER_MESSAGE
*
* These are direct VL1 P2P messages for application use. Encryption and
* authentication in the ZeroTier protocol will guarantee the origin
* address and message content, but you are responsible for any other
* levels of authentication or access control that are required. Any node
* in the world can send you a user message! (Unless your network is air
* gapped.)
*/ */
typedef struct typedef struct
{ {
@ -720,24 +727,6 @@ typedef struct
} v; } v;
} ZT_VirtualNetworkRule; } ZT_VirtualNetworkRule;
typedef struct
{
/**
* 128-bit ID (GUID) of this capability
*/
uint64_t id[2];
/**
* Expiration time (measured vs. network config timestamp issued by controller)
*/
uint64_t expiration;
struct {
uint64_t from;
uint64_t to;
} custody[ZT_MAX_CAPABILITY_CUSTODY_CHAIN_LENGTH];
} ZT_VirtualNetworkCapability;
/** /**
* A route to be pushed on a virtual network * A route to be pushed on a virtual network
*/ */
@ -1102,7 +1091,7 @@ enum ZT_StateObjectType
ZT_STATE_OBJECT_NULL = 0, ZT_STATE_OBJECT_NULL = 0,
/** /**
* identity.public * Public address and public key
* *
* Object ID: this node's address if known, or 0 if unknown (first query) * Object ID: this node's address if known, or 0 if unknown (first query)
* Canonical path: <HOME>/identity.public * Canonical path: <HOME>/identity.public
@ -1111,10 +1100,10 @@ enum ZT_StateObjectType
ZT_STATE_OBJECT_IDENTITY_PUBLIC = 1, ZT_STATE_OBJECT_IDENTITY_PUBLIC = 1,
/** /**
* identity.secret * Full identity with secret key
* *
* Object ID: this node's address if known, or 0 if unknown (first query) * Object ID: this node's address if known, or 0 if unknown (first query)
* Canonical path: <HOME>/identity.public * Canonical path: <HOME>/identity.secret
* Persistence: required, should be stored with restricted permissions e.g. mode 0600 on *nix * Persistence: required, should be stored with restricted permissions e.g. mode 0600 on *nix
*/ */
ZT_STATE_OBJECT_IDENTITY_SECRET = 2, ZT_STATE_OBJECT_IDENTITY_SECRET = 2,
@ -1280,7 +1269,7 @@ typedef int (*ZT_StateGetFunction)(
unsigned int); /* Length of data buffer in bytes */ unsigned int); /* Length of data buffer in bytes */
/** /**
* Function to send a ZeroTier packet out over the wire * Function to send a ZeroTier packet out over the physical wire (L2/L3)
* *
* Parameters: * Parameters:
* (1) Node * (1) Node
@ -1335,9 +1324,6 @@ typedef int (*ZT_WirePacketSendFunction)(
* all configured ZeroTier interfaces and check to ensure that the supplied * all configured ZeroTier interfaces and check to ensure that the supplied
* addresses will not result in ZeroTier traffic being sent over a ZeroTier * addresses will not result in ZeroTier traffic being sent over a ZeroTier
* interface (recursion). * interface (recursion).
*
* Obviously this is not required in configurations where this can't happen,
* such as network containers or embedded.
*/ */
typedef int (*ZT_PathCheckFunction)( typedef int (*ZT_PathCheckFunction)(
ZT_Node *, /* Node */ ZT_Node *, /* Node */
@ -1426,13 +1412,12 @@ struct ZT_Node_Callbacks
}; };
/** /**
* Create a new ZeroTier One node * Create a new ZeroTier node
* *
* Note that this can take a few seconds the first time it's called, as it * This will attempt to load its identity via the state get function in the
* will generate an identity. * callback struct. If that fails it will generate a new identity and store
* * it. Identity generation can take anywhere from a few hundred milliseconds
* TODO: should consolidate function pointers into versioned structure for * to a few seconds depending on your CPU speed.
* better API stability.
* *
* @param node Result: pointer is set to new node instance on success * @param node Result: pointer is set to new node instance on success
* @param uptr User pointer to pass to functions/callbacks * @param uptr User pointer to pass to functions/callbacks

View file

@ -262,6 +262,19 @@ public:
_b[_l++] = (char)c; _b[_l++] = (char)c;
} }
/**
* Append secure random bytes
*
* @param n Number of random bytes to append
*/
inline void appendRandom(unsigned int n)
{
if (unlikely((_l + n) > C))
throw std::out_of_range("Buffer: append beyond capacity");
Utils::getSecureRandom(_b + _l,n);
_l += n;
}
/** /**
* Append a C-array of bytes * Append a C-array of bytes
* *

View file

@ -701,7 +701,26 @@ Network::Network(const RuntimeEnvironment *renv,void *tPtr,uint64_t nwid,void *u
this->setConfiguration(tPtr,*nconf,false); this->setConfiguration(tPtr,*nconf,false);
_lastConfigUpdate = 0; // still want to re-request since it's likely outdated _lastConfigUpdate = 0; // still want to re-request since it's likely outdated
} else { } else {
RR->node->stateObjectPut(tPtr,ZT_STATE_OBJECT_NETWORK_CONFIG,nwid,"\n",1); bool got = false;
Dictionary<ZT_NETWORKCONFIG_DICT_CAPACITY> *dict = new Dictionary<ZT_NETWORKCONFIG_DICT_CAPACITY>();
try {
int n = RR->node->stateObjectGet(tPtr,ZT_STATE_OBJECT_NETWORK_CONFIG,nwid,dict->unsafeData(),ZT_NETWORKCONFIG_DICT_CAPACITY - 1);
if (n > 1) {
NetworkConfig *nconf = new NetworkConfig();
try {
if (nconf->fromDictionary(*dict)) {
this->setConfiguration(tPtr,*nconf,false);
_lastConfigUpdate = 0; // still want to re-request an update since it's likely outdated
got = true;
}
} catch ( ... ) {}
delete nconf;
}
} catch ( ... ) {}
delete dict;
if (!got)
RR->node->stateObjectPut(tPtr,ZT_STATE_OBJECT_NETWORK_CONFIG,nwid,"\n",1);
} }
if (!_portInitialized) { if (!_portInitialized) {

View file

@ -161,8 +161,10 @@ ZT_ResultCode Node::processStateUpdate(
if (len < 2) { if (len < 2) {
Mutex::Lock _l(_networks_m); Mutex::Lock _l(_networks_m);
SharedPtr<Network> &nw = _networks[id]; SharedPtr<Network> &nw = _networks[id];
if (!nw) if (!nw) {
nw = SharedPtr<Network>(new Network(RR,tptr,id,(void *)0,(const NetworkConfig *)0)); nw = SharedPtr<Network>(new Network(RR,tptr,id,(void *)0,(const NetworkConfig *)0));
r = ZT_RESULT_OK;
}
} else { } else {
Dictionary<ZT_NETWORKCONFIG_DICT_CAPACITY> *dict = new Dictionary<ZT_NETWORKCONFIG_DICT_CAPACITY>(reinterpret_cast<const char *>(data),len); Dictionary<ZT_NETWORKCONFIG_DICT_CAPACITY> *dict = new Dictionary<ZT_NETWORKCONFIG_DICT_CAPACITY>(reinterpret_cast<const char *>(data),len);
try { try {

View file

@ -214,6 +214,8 @@ public:
World planet() const; World planet() const;
std::vector<World> moons() const; std::vector<World> moons() const;
inline const Identity &identity() const { return _RR.identity; }
/** /**
* Register that we are expecting a reply to a packet ID * Register that we are expecting a reply to a packet ID
* *

View file

@ -446,6 +446,16 @@ public:
return aa; return aa;
} }
/**
* @param aa Vector to append local interface addresses to
*/
inline void allBoundLocalInterfaceAddresses(std::vector<InetAddress> &aa)
{
Mutex::Lock _l(_lock);
for(std::vector<_Binding>::const_iterator i(_bindings.begin());i!=_bindings.end();++i)
aa.push_back(i->address);
}
private: private:
std::vector<_Binding> _bindings; std::vector<_Binding> _bindings;
Mutex _lock; Mutex _lock;

File diff suppressed because it is too large Load diff