mirror of
https://github.com/zerotier/ZeroTierOne.git
synced 2024-12-19 13:07:55 +00:00
Tweaks to path handling...
This commit is contained in:
parent
4931e44998
commit
4f8253dcdb
@ -1163,8 +1163,8 @@ bool IncomingPacket::_doCIRCUIT_TEST(const RuntimeEnvironment *RR,const SharedPt
|
|||||||
remainingHopsPtr += ZT_ADDRESS_LENGTH;
|
remainingHopsPtr += ZT_ADDRESS_LENGTH;
|
||||||
SharedPtr<Peer> nhp(RR->topology->getPeer(nextHop[h]));
|
SharedPtr<Peer> nhp(RR->topology->getPeer(nextHop[h]));
|
||||||
if (nhp) {
|
if (nhp) {
|
||||||
SharedPtr<Path> nhbp(nhp->getBestPath(now,false));
|
SharedPtr<Path> nhbp(nhp->getBestPath(now));
|
||||||
if (nhbp)
|
if ((nhbp)&&(nhbp->alive(now)))
|
||||||
nextHopBestPathAddress[h] = nhbp->address();
|
nextHopBestPathAddress[h] = nhbp->address();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -416,7 +416,7 @@ ZT_PeerList *Node::peers() const
|
|||||||
p->role = RR->topology->isRoot(pi->second->identity()) ? ZT_PEER_ROLE_ROOT : ZT_PEER_ROLE_LEAF;
|
p->role = RR->topology->isRoot(pi->second->identity()) ? ZT_PEER_ROLE_ROOT : ZT_PEER_ROLE_LEAF;
|
||||||
|
|
||||||
std::vector< SharedPtr<Path> > paths(pi->second->paths());
|
std::vector< SharedPtr<Path> > paths(pi->second->paths());
|
||||||
SharedPtr<Path> bestp(pi->second->getBestPath(_now,true));
|
SharedPtr<Path> bestp(pi->second->getBestPath(_now));
|
||||||
p->pathCount = 0;
|
p->pathCount = 0;
|
||||||
for(std::vector< SharedPtr<Path> >::iterator path(paths.begin());path!=paths.end();++path) {
|
for(std::vector< SharedPtr<Path> >::iterator path(paths.begin());path!=paths.end();++path) {
|
||||||
memcpy(&(p->paths[p->pathCount].address),&((*path)->address()),sizeof(struct sockaddr_storage));
|
memcpy(&(p->paths[p->pathCount].address),&((*path)->address()),sizeof(struct sockaddr_storage));
|
||||||
|
@ -229,7 +229,7 @@ void Peer::makeExclusive(const InetAddress &addr)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Peer::send(const void *data,unsigned int len,uint64_t now,bool forceEvenIfDead)
|
bool Peer::sendDirect(const void *data,unsigned int len,uint64_t now,bool forceEvenIfDead)
|
||||||
{
|
{
|
||||||
Mutex::Lock _l(_paths_m);
|
Mutex::Lock _l(_paths_m);
|
||||||
|
|
||||||
@ -252,19 +252,17 @@ bool Peer::send(const void *data,unsigned int len,uint64_t now,bool forceEvenIfD
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SharedPtr<Path> Peer::getBestPath(uint64_t now,bool forceEvenIfDead)
|
SharedPtr<Path> Peer::getBestPath(uint64_t now)
|
||||||
{
|
{
|
||||||
Mutex::Lock _l(_paths_m);
|
Mutex::Lock _l(_paths_m);
|
||||||
|
|
||||||
int bestp = -1;
|
int bestp = -1;
|
||||||
uint64_t best = 0ULL;
|
uint64_t best = 0ULL;
|
||||||
for(unsigned int p=0;p<_numPaths;++p) {
|
for(unsigned int p=0;p<_numPaths;++p) {
|
||||||
if (_paths[p].path->alive(now)||(forceEvenIfDead)) {
|
const uint64_t s = _paths[p].path->score();
|
||||||
const uint64_t s = _paths[p].path->score();
|
if (s >= best) {
|
||||||
if (s >= best) {
|
best = s;
|
||||||
best = s;
|
bestp = (int)p;
|
||||||
bestp = (int)p;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -293,18 +291,29 @@ void Peer::sendHELLO(const InetAddress &localAddr,const InetAddress &atAddress,u
|
|||||||
|
|
||||||
bool Peer::doPingAndKeepalive(uint64_t now,int inetAddressFamily)
|
bool Peer::doPingAndKeepalive(uint64_t now,int inetAddressFamily)
|
||||||
{
|
{
|
||||||
bool somethingAlive = false;
|
|
||||||
Mutex::Lock _l(_paths_m);
|
Mutex::Lock _l(_paths_m);
|
||||||
|
|
||||||
|
int bestp = -1;
|
||||||
|
uint64_t best = 0ULL;
|
||||||
for(unsigned int p=0;p<_numPaths;++p) {
|
for(unsigned int p=0;p<_numPaths;++p) {
|
||||||
if ((now - _paths[p].lastReceive) >= ZT_PEER_PING_PERIOD) {
|
const uint64_t s = _paths[p].path->score();
|
||||||
sendHELLO(_paths[p].path->localAddress(),_paths[p].path->address(),now);
|
if (s >= best) {
|
||||||
} else if (_paths[p].path->needsHeartbeat(now)) {
|
best = s;
|
||||||
_natKeepaliveBuf += (uint32_t)((now * 0x9e3779b1) >> 1); // tumble this around to send constantly varying (meaningless) payloads
|
bestp = (int)p;
|
||||||
_paths[p].path->send(RR,&_natKeepaliveBuf,sizeof(_natKeepaliveBuf),now);
|
|
||||||
}
|
}
|
||||||
somethingAlive |= _paths[p].path->alive(now);
|
|
||||||
}
|
}
|
||||||
return somethingAlive;
|
|
||||||
|
if (bestp >= 0) {
|
||||||
|
if ((now - _paths[bestp].lastReceive) >= ZT_PEER_PING_PERIOD) {
|
||||||
|
sendHELLO(_paths[bestp].path->localAddress(),_paths[bestp].path->address(),now);
|
||||||
|
} else if (_paths[bestp].path->needsHeartbeat(now)) {
|
||||||
|
_natKeepaliveBuf += (uint32_t)((now * 0x9e3779b1) >> 1); // tumble this around to send constantly varying (meaningless) payloads
|
||||||
|
_paths[bestp].path->send(RR,&_natKeepaliveBuf,sizeof(_natKeepaliveBuf),now);
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
} else {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Peer::hasActiveDirectPath(uint64_t now) const
|
bool Peer::hasActiveDirectPath(uint64_t now) const
|
||||||
|
@ -128,7 +128,7 @@ public:
|
|||||||
void makeExclusive(const InetAddress &addr);
|
void makeExclusive(const InetAddress &addr);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Send via best path
|
* Send via best direct path
|
||||||
*
|
*
|
||||||
* @param data Packet data
|
* @param data Packet data
|
||||||
* @param len Packet length
|
* @param len Packet length
|
||||||
@ -136,16 +136,15 @@ public:
|
|||||||
* @param forceEvenIfDead If true, send even if the path is not 'alive'
|
* @param forceEvenIfDead If true, send even if the path is not 'alive'
|
||||||
* @return True if we actually sent something
|
* @return True if we actually sent something
|
||||||
*/
|
*/
|
||||||
bool send(const void *data,unsigned int len,uint64_t now,bool forceEvenIfDead);
|
bool sendDirect(const void *data,unsigned int len,uint64_t now,bool forceEvenIfDead);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the best current direct path
|
* Get the best current direct path
|
||||||
*
|
*
|
||||||
* @param now Current time
|
* @param now Current time
|
||||||
* @param forceEvenIfDead If true, pick even if path is not alive
|
|
||||||
* @return Best current path or NULL if none
|
* @return Best current path or NULL if none
|
||||||
*/
|
*/
|
||||||
SharedPtr<Path> getBestPath(uint64_t now,bool forceEvenIfDead);
|
SharedPtr<Path> getBestPath(uint64_t now);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Send a HELLO to this peer at a specified physical address
|
* Send a HELLO to this peer at a specified physical address
|
||||||
|
@ -75,6 +75,7 @@ void Switch::onRemotePacket(const InetAddress &localAddr,const InetAddress &from
|
|||||||
|
|
||||||
SharedPtr<Path> path(RR->topology->getPath(localAddr,fromAddr));
|
SharedPtr<Path> path(RR->topology->getPath(localAddr,fromAddr));
|
||||||
path->received(now);
|
path->received(now);
|
||||||
|
printf("<< %s %u\n",fromAddr.toString().c_str(),len);
|
||||||
|
|
||||||
if (len == 13) {
|
if (len == 13) {
|
||||||
/* LEGACY: before VERB_PUSH_DIRECT_PATHS, peers used broadcast
|
/* LEGACY: before VERB_PUSH_DIRECT_PATHS, peers used broadcast
|
||||||
@ -112,7 +113,7 @@ void Switch::onRemotePacket(const InetAddress &localAddr,const InetAddress &from
|
|||||||
// Note: we don't bother initiating NAT-t for fragments, since heads will set that off.
|
// Note: we don't bother initiating NAT-t for fragments, since heads will set that off.
|
||||||
// It wouldn't hurt anything, just redundant and unnecessary.
|
// It wouldn't hurt anything, just redundant and unnecessary.
|
||||||
SharedPtr<Peer> relayTo = RR->topology->getPeer(destination);
|
SharedPtr<Peer> relayTo = RR->topology->getPeer(destination);
|
||||||
if ((!relayTo)||(!relayTo->send(fragment.data(),fragment.size(),now,true))) {
|
if ((!relayTo)||(!relayTo->sendDirect(fragment.data(),fragment.size(),now,false))) {
|
||||||
#ifdef ZT_ENABLE_CLUSTER
|
#ifdef ZT_ENABLE_CLUSTER
|
||||||
if (RR->cluster) {
|
if (RR->cluster) {
|
||||||
RR->cluster->sendViaCluster(Address(),destination,fragment.data(),fragment.size(),false);
|
RR->cluster->sendViaCluster(Address(),destination,fragment.data(),fragment.size(),false);
|
||||||
@ -123,7 +124,7 @@ void Switch::onRemotePacket(const InetAddress &localAddr,const InetAddress &from
|
|||||||
// Don't know peer or no direct path -- so relay via root server
|
// Don't know peer or no direct path -- so relay via root server
|
||||||
relayTo = RR->topology->getBestRoot();
|
relayTo = RR->topology->getBestRoot();
|
||||||
if (relayTo)
|
if (relayTo)
|
||||||
relayTo->send(fragment.data(),fragment.size(),now,true);
|
relayTo->sendDirect(fragment.data(),fragment.size(),now,true);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
TRACE("dropped relay [fragment](%s) -> %s, max hops exceeded",fromAddr.toString().c_str(),destination.toString().c_str());
|
TRACE("dropped relay [fragment](%s) -> %s, max hops exceeded",fromAddr.toString().c_str(),destination.toString().c_str());
|
||||||
@ -210,7 +211,7 @@ void Switch::onRemotePacket(const InetAddress &localAddr,const InetAddress &from
|
|||||||
packet.incrementHops();
|
packet.incrementHops();
|
||||||
|
|
||||||
SharedPtr<Peer> relayTo = RR->topology->getPeer(destination);
|
SharedPtr<Peer> relayTo = RR->topology->getPeer(destination);
|
||||||
if ((relayTo)&&((relayTo->send(packet.data(),packet.size(),now,true)))) {
|
if ((relayTo)&&((relayTo->sendDirect(packet.data(),packet.size(),now,false)))) {
|
||||||
Mutex::Lock _l(_lastUniteAttempt_m);
|
Mutex::Lock _l(_lastUniteAttempt_m);
|
||||||
uint64_t &luts = _lastUniteAttempt[_LastUniteKey(source,destination)];
|
uint64_t &luts = _lastUniteAttempt[_LastUniteKey(source,destination)];
|
||||||
if ((now - luts) >= ZT_MIN_UNITE_INTERVAL) {
|
if ((now - luts) >= ZT_MIN_UNITE_INTERVAL) {
|
||||||
@ -234,7 +235,7 @@ void Switch::onRemotePacket(const InetAddress &localAddr,const InetAddress &from
|
|||||||
#endif
|
#endif
|
||||||
relayTo = RR->topology->getBestRoot(&source,1,true);
|
relayTo = RR->topology->getBestRoot(&source,1,true);
|
||||||
if (relayTo)
|
if (relayTo)
|
||||||
relayTo->send(packet.data(),packet.size(),now,true);
|
relayTo->sendDirect(packet.data(),packet.size(),now,true);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
TRACE("dropped relay %s(%s) -> %s, max hops exceeded",packet.source().toString().c_str(),fromAddr.toString().c_str(),destination.toString().c_str());
|
TRACE("dropped relay %s(%s) -> %s, max hops exceeded",packet.source().toString().c_str(),fromAddr.toString().c_str(),destination.toString().c_str());
|
||||||
@ -607,7 +608,7 @@ bool Switch::unite(const Address &p1,const Address &p2)
|
|||||||
outp.append(cg.first.rawIpData(),4);
|
outp.append(cg.first.rawIpData(),4);
|
||||||
}
|
}
|
||||||
outp.armor(p1p->key(),true);
|
outp.armor(p1p->key(),true);
|
||||||
p1p->send(outp.data(),outp.size(),now,true);
|
p1p->sendDirect(outp.data(),outp.size(),now,true);
|
||||||
} else {
|
} else {
|
||||||
// Tell p2 where to find p1.
|
// Tell p2 where to find p1.
|
||||||
Packet outp(p2,RR->identity.address(),Packet::VERB_RENDEZVOUS);
|
Packet outp(p2,RR->identity.address(),Packet::VERB_RENDEZVOUS);
|
||||||
@ -622,7 +623,7 @@ bool Switch::unite(const Address &p1,const Address &p2)
|
|||||||
outp.append(cg.second.rawIpData(),4);
|
outp.append(cg.second.rawIpData(),4);
|
||||||
}
|
}
|
||||||
outp.armor(p2p->key(),true);
|
outp.armor(p2p->key(),true);
|
||||||
p2p->send(outp.data(),outp.size(),now,true);
|
p2p->sendDirect(outp.data(),outp.size(),now,true);
|
||||||
}
|
}
|
||||||
++alt; // counts up and also flips LSB
|
++alt; // counts up and also flips LSB
|
||||||
}
|
}
|
||||||
@ -739,7 +740,7 @@ Address Switch::_sendWhoisRequest(const Address &addr,const Address *peersAlread
|
|||||||
Packet outp(root->address(),RR->identity.address(),Packet::VERB_WHOIS);
|
Packet outp(root->address(),RR->identity.address(),Packet::VERB_WHOIS);
|
||||||
addr.appendTo(outp);
|
addr.appendTo(outp);
|
||||||
outp.armor(root->key(),true);
|
outp.armor(root->key(),true);
|
||||||
if (root->send(outp.data(),outp.size(),RR->node->now(),true))
|
if (root->sendDirect(outp.data(),outp.size(),RR->node->now(),true))
|
||||||
return root->address();
|
return root->address();
|
||||||
}
|
}
|
||||||
return Address();
|
return Address();
|
||||||
@ -752,10 +753,10 @@ bool Switch::_trySend(const Packet &packet,bool encrypt)
|
|||||||
if (peer) {
|
if (peer) {
|
||||||
const uint64_t now = RR->node->now();
|
const uint64_t now = RR->node->now();
|
||||||
|
|
||||||
SharedPtr<Path> viaPath(peer->getBestPath(now,false));
|
SharedPtr<Path> viaPath(peer->getBestPath(now));
|
||||||
if (!viaPath) {
|
if ( (!viaPath) || ((!viaPath->alive(now))&&(!RR->topology->isRoot(peer->identity()))) ) {
|
||||||
SharedPtr<Peer> relay(RR->topology->getBestRoot());
|
SharedPtr<Peer> relay(RR->topology->getBestRoot());
|
||||||
if ( (!relay) || (!(viaPath = relay->getBestPath(now,true))) )
|
if ( (!relay) || (!(viaPath = relay->getBestPath(now))) )
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user