Clean dead paths from peers.

This commit is contained in:
Adam Ierymenko 2014-03-31 11:41:14 -07:00
parent acb056e3b1
commit 8e587ae481
5 changed files with 41 additions and 1 deletions

View File

@ -51,6 +51,8 @@ namespace ZeroTier {
/** /**
* Wrapper for sockaddr structures for IPV4 and IPV6 * Wrapper for sockaddr structures for IPV4 and IPV6
*
* Note: this class is raw memcpy'able, which is used in a couple places.
*/ */
class InetAddress class InetAddress
{ {

View File

@ -29,6 +29,7 @@
#define ZT_PATH_HPP #define ZT_PATH_HPP
#include <stdint.h> #include <stdint.h>
#include <string.h>
#include <stdexcept> #include <stdexcept>
#include <string> #include <string>
@ -57,6 +58,12 @@ public:
_tcp(false), _tcp(false),
_fixed(false) {} _fixed(false) {}
Path(const Path &p)
{
// InetAddress is memcpy'able
memcpy(this,&p,sizeof(Path));
}
Path(const InetAddress &addr,bool tcp,bool fixed = false) : Path(const InetAddress &addr,bool tcp,bool fixed = false) :
_lastSend(0), _lastSend(0),
_lastReceived(0), _lastReceived(0),
@ -66,6 +73,13 @@ public:
_tcp(tcp), _tcp(tcp),
_fixed(fixed) {} _fixed(fixed) {}
inline Path &operator=(const Path &p)
{
if (this != &p)
memcpy(this,&p,sizeof(Path));
return *this;
}
inline const InetAddress &address() const throw() { return _addr; } inline const InetAddress &address() const throw() { return _addr; }
inline bool tcp() const throw() { return _tcp; } inline bool tcp() const throw() { return _tcp; }
inline uint64_t lastSend() const throw() { return _lastSend; } inline uint64_t lastSend() const throw() { return _lastSend; }
@ -81,6 +95,10 @@ public:
inline void firewallOpenerSent(uint64_t t) throw() { _lastFirewallOpener = t; } inline void firewallOpenerSent(uint64_t t) throw() { _lastFirewallOpener = t; }
inline void pinged(uint64_t t) throw() { _lastPing = t; } inline void pinged(uint64_t t) throw() { _lastPing = t; }
/**
* @param now Current time
* @return True if this path is fixed or has received data in last ACTIVITY_TIMEOUT ms
*/
inline bool active(uint64_t now) const inline bool active(uint64_t now) const
throw() throw()
{ {

View File

@ -187,4 +187,16 @@ bool Peer::sendPing(const RuntimeEnvironment *_r,uint64_t now,bool firstSinceRes
return sent; return sent;
} }
void Peer::clean(uint64_t now)
{
Mutex::Lock _l(_lock);
unsigned long i = 0,o = 0,l = _paths.size();
while (i != l) {
if (_paths[i].active(now))
_paths[o++] = _paths[i];
++i;
}
_paths.resize(o);
}
} // namespace ZeroTier } // namespace ZeroTier

View File

@ -165,6 +165,11 @@ public:
*/ */
bool sendPing(const RuntimeEnvironment *_r,uint64_t now,bool firstSinceReset); bool sendPing(const RuntimeEnvironment *_r,uint64_t now,bool firstSinceReset);
/**
* Called periodically by Topology::clean() to remove stale paths and do other cleanup
*/
void clean(uint64_t now);
/** /**
* @return All known direct paths to this peer * @return All known direct paths to this peer
*/ */

View File

@ -210,7 +210,10 @@ void Topology::clean()
for(std::map< Address,SharedPtr<Peer> >::iterator p(_activePeers.begin());p!=_activePeers.end();) { for(std::map< Address,SharedPtr<Peer> >::iterator p(_activePeers.begin());p!=_activePeers.end();) {
if (((now - p->second->lastUsed()) >= ZT_PEER_IN_MEMORY_EXPIRATION)&&(!_supernodeAddresses.count(p->second->address()))) if (((now - p->second->lastUsed()) >= ZT_PEER_IN_MEMORY_EXPIRATION)&&(!_supernodeAddresses.count(p->second->address())))
_activePeers.erase(p++); _activePeers.erase(p++);
else ++p; else {
p->second->clean(now);
++p;
}
} }
} }