Fix TCP connection accumulation problem, still having issues with TCP tunneling.

This commit is contained in:
Adam Ierymenko 2014-03-26 17:59:45 -07:00
parent e6b23059ac
commit 2ac56fd120
7 changed files with 44 additions and 44 deletions

View File

@ -141,27 +141,29 @@ bool InetAddress::operator==(const InetAddress &a) const
return (!memcmp(_sa.sin6.sin6_addr.s6_addr,a._sa.sin6.sin6_addr.s6_addr,sizeof(_sa.sin6.sin6_addr.s6_addr))); return (!memcmp(_sa.sin6.sin6_addr.s6_addr,a._sa.sin6.sin6_addr.s6_addr,sizeof(_sa.sin6.sin6_addr.s6_addr)));
} }
return false; return false;
} else if (!_sa.saddr.sa_family) } else return (memcmp(&_sa,&a._sa,sizeof(_sa)) == 0);
return (!a._sa.saddr.sa_family);
return (!memcmp(&_sa,&a._sa,sizeof(_sa)));
} }
bool InetAddress::operator<(const InetAddress &a) const bool InetAddress::operator<(const InetAddress &a) const
throw() throw()
{ {
if (_sa.saddr.sa_family == AF_INET) { if (_sa.saddr.sa_family < a._sa.saddr.sa_family)
if (a._sa.saddr.sa_family == AF_INET)
return ((ntohl(_sa.sin.sin_addr.s_addr < ntohl(a._sa.sin.sin_addr.s_addr)))||((_sa.sin.sin_addr.s_addr == a._sa.sin.sin_addr.s_addr)&&(ntohs(_sa.sin.sin_port) < ntohs(a._sa.sin.sin_port))));
else if (a._sa.saddr.sa_family == AF_INET6)
return true; return true;
else if (_sa.saddr.sa_family == a._sa.saddr.sa_family) {
if (_sa.saddr.sa_family == AF_INET) {
unsigned long x = ntohl(_sa.sin.sin_addr.s_addr);
unsigned long y = ntohl(a._sa.sin.sin_addr.s_addr);
if (x == y)
return (ntohs(_sa.sin.sin_port) < ntohs(a._sa.sin.sin_port));
else return (x < y);
} else if (_sa.saddr.sa_family == AF_INET6) { } else if (_sa.saddr.sa_family == AF_INET6) {
if (a._sa.saddr.sa_family == AF_INET6) { int cmp = (int)memcmp(_sa.sin6.sin6_addr.s6_addr,a._sa.sin6.sin6_addr.s6_addr,16);
int cmp = memcmp(_sa.sin6.sin6_addr.s6_addr,a._sa.sin6.sin6_addr.s6_addr,16); if (cmp == 0)
return ((cmp < 0)||((!cmp)&&(ntohs(_sa.sin6.sin6_port) < ntohs(a._sa.sin6.sin6_port)))); return (ntohs(_sa.sin6.sin6_port) < ntohs(a._sa.sin6.sin6_port));
} else if (a._sa.saddr.sa_family == AF_INET) else return (cmp < 0);
return false; } else return (memcmp(&_sa,&a._sa,sizeof(_sa)) < 0);
} }
return (_sa.saddr.sa_family < a._sa.saddr.sa_family); return false;
} }
} // namespace ZeroTier } // namespace ZeroTier

View File

@ -577,8 +577,9 @@ Node::ReasonForTermination Node::run()
} }
// Ping supernodes separately for two reasons: (1) supernodes only ping each // Ping supernodes separately for two reasons: (1) supernodes only ping each
// other, and (2) we still want to ping them first on resynchronize. // other, and (2) we still want to ping them first on resynchronize. Also ping
if ((resynchronize)||((now - lastSupernodePing) >= ZT_PEER_DIRECT_PING_DELAY)) { // more aggressively if nothing seems to be happening at all.
if ((resynchronize)||((now - lastSupernodePing) >= ZT_PEER_DIRECT_PING_DELAY)||((now - _r->timeOfLastPacketReceived) >= ZT_PING_UNANSWERED_AFTER)) {
lastSupernodePing = now; lastSupernodePing = now;
std::vector< SharedPtr<Peer> > sns(_r->topology->supernodePeers()); std::vector< SharedPtr<Peer> > sns(_r->topology->supernodePeers());
TRACE("pinging %d supernodes",(int)sns.size()); TRACE("pinging %d supernodes",(int)sns.size());

View File

@ -69,6 +69,8 @@ void Peer::receive(
Packet::Verb inReVerb, Packet::Verb inReVerb,
uint64_t now) uint64_t now)
{ {
*((const_cast<uint64_t *>(&(_r->timeOfLastPacketReceived)))) = now;
if (!hops) { // direct packet if (!hops) { // direct packet
{ {
Mutex::Lock _l(_lock); Mutex::Lock _l(_lock);

View File

@ -65,6 +65,7 @@ public:
RuntimeEnvironment() : RuntimeEnvironment() :
shutdownInProgress(false), shutdownInProgress(false),
timeOfLastNetworkEnvironmentChange(0), timeOfLastNetworkEnvironmentChange(0),
timeOfLastPacketReceived(0),
log((Logger *)0), log((Logger *)0),
prng((CMWC4096 *)0), prng((CMWC4096 *)0),
mc((Multicaster *)0), mc((Multicaster *)0),
@ -92,6 +93,10 @@ public:
// Time network environment (e.g. fingerprint) last changed -- used to determine online-ness // Time network environment (e.g. fingerprint) last changed -- used to determine online-ness
volatile uint64_t timeOfLastNetworkEnvironmentChange; volatile uint64_t timeOfLastNetworkEnvironmentChange;
// Time last packet was received -- from anywhere. This is updated in Peer::receive()
// via an ugly const_cast<>.
volatile uint64_t timeOfLastPacketReceived;
/* /*
* Order matters a bit here. These are constructed in this order * Order matters a bit here. These are constructed in this order
* and then deleted in the opposite order on Node exit. The order ensures * and then deleted in the opposite order on Node exit. The order ensures

View File

@ -395,17 +395,17 @@ bool SocketManager::send(const InetAddress &to,bool tcp,const void *msg,unsigned
if (!ts->send(to,msg,msglen)) if (!ts->send(to,msg,msglen))
return false; return false;
{
Mutex::Lock _l(_tcpSockets_m);
_tcpSockets[to] = ts;
}
_fdSetLock.lock(); _fdSetLock.lock();
FD_SET(s,&_readfds); FD_SET(s,&_readfds);
if (connecting) if (connecting)
FD_SET(s,&_writefds); FD_SET(s,&_writefds);
_fdSetLock.unlock(); _fdSetLock.unlock();
{
Mutex::Lock _l(_tcpSockets_m);
_tcpSockets[to] = ts;
}
return true; return true;
} else if (to.isV4()) { } else if (to.isV4()) {
if (_udpV4Socket) if (_udpV4Socket)

View File

@ -164,32 +164,22 @@ bool TcpSocket::notifyAvailableForWrite(const SharedPtr<Socket> &self,SocketMana
if (_outptr) { if (_outptr) {
int n = (int)::send(_sock,(const char *)_outbuf,_outptr,0); int n = (int)::send(_sock,(const char *)_outbuf,_outptr,0);
if (n < 0) { if (n <= 0) {
switch(errno) { switch(errno) {
#ifdef EBADF #ifdef EAGAIN
case EBADF: case EAGAIN:
#endif #endif
#ifdef EINVAL #if defined(EWOULDBLOCK) && ( !defined(EAGAIN) || (EWOULDBLOCK != EAGAIN) )
case EINVAL: case EWOULDBLOCK:
#endif #endif
#ifdef ENOTSOCK #ifdef EINTR
case ENOTSOCK: case EINTR:
#endif #endif
#ifdef ECONNRESET
case ECONNRESET:
#endif
#ifdef EPIPE
case EPIPE:
#endif
#ifdef ENETDOWN
case ENETDOWN:
#endif
return false;
default:
break; break;
default:
return false;
} }
} else if (n > 0) } else memmove(_outbuf,_outbuf + (unsigned int)n,_outptr -= (unsigned int)n);
memmove(_outbuf,_outbuf + (unsigned int)n,_outptr -= (unsigned int)n);
} }
if (!_outptr) if (!_outptr)

View File

@ -207,11 +207,11 @@ void Utils::getSecureRandom(void *buf,unsigned int bytes)
{ {
int fd = ::open("/dev/urandom",O_RDONLY); int fd = ::open("/dev/urandom",O_RDONLY);
if (fd < 0) { if (fd < 0) {
fprintf(stderr,"FATAL ERROR: unable to open /dev/urandom%s",ZT_EOL_S); fprintf(stderr,"FATAL ERROR: unable to open /dev/urandom (%d)"ZT_EOL_S,errno);
exit(-1); exit(-1);
} }
if ((int)::read(fd,randbuf,sizeof(randbuf)) != (int)sizeof(randbuf)) { if ((int)::read(fd,randbuf,sizeof(randbuf)) != (int)sizeof(randbuf)) {
fprintf(stderr,"FATAL ERROR: unable to read from /dev/urandom%s",ZT_EOL_S); fprintf(stderr,"FATAL ERROR: unable to read from /dev/urandom"ZT_EOL_S);
exit(-1); exit(-1);
} }
::close(fd); ::close(fd);