Browse Source

Ping automatically every 2 minutes (unconditionally)

... instead of after 30 minutes of no sending, for latency measurement
and keep-alive. Also, disconnect if no reply arrives within 20 minutes,
instead of 90 of inactivity (for peers supporting the 'pong' message).
0.10
Pieter Wuille 11 years ago
parent
commit
f1920e8606
  1. 13
      src/main.cpp
  2. 18
      src/net.cpp
  3. 13
      src/net.h

13
src/main.cpp

@ -4296,8 +4296,8 @@ bool SendMessages(CNode* pto, bool fSendTrickle) @@ -4296,8 +4296,8 @@ bool SendMessages(CNode* pto, bool fSendTrickle)
// RPC ping request by user
pingSend = true;
}
if (pto->nLastSend && GetTime() - pto->nLastSend > 30 * 60 && pto->vSendMsg.empty()) {
// Ping automatically sent as a keepalive
if (pto->nPingNonceSent == 0 && pto->nPingUsecStart + PING_INTERVAL * 1000000 < GetTimeMicros()) {
// Ping automatically sent as a latency probe & keepalive.
pingSend = true;
}
if (pingSend) {
@ -4305,15 +4305,14 @@ bool SendMessages(CNode* pto, bool fSendTrickle) @@ -4305,15 +4305,14 @@ bool SendMessages(CNode* pto, bool fSendTrickle)
while (nonce == 0) {
RAND_bytes((unsigned char*)&nonce, sizeof(nonce));
}
pto->nPingNonceSent = nonce;
pto->fPingQueued = false;
if (pto->nVersion > BIP0031_VERSION) {
// Take timestamp as close as possible before transmitting ping
pto->nPingUsecStart = GetTimeMicros();
if (pto->nVersion > BIP0031_VERSION) {
pto->nPingNonceSent = nonce;
pto->PushMessage("ping", nonce);
} else {
// Peer is too old to support ping command with nonce, pong will never arrive, disable timing
pto->nPingUsecStart = 0;
// Peer is too old to support ping command with nonce, pong will never arrive.
pto->nPingNonceSent = 0;
pto->PushMessage("ping");
}
}

18
src/net.cpp

@ -1028,23 +1028,27 @@ void ThreadSocketHandler() @@ -1028,23 +1028,27 @@ void ThreadSocketHandler()
//
// Inactivity checking
//
if (pnode->vSendMsg.empty())
pnode->nLastSendEmpty = GetTime();
if (GetTime() - pnode->nTimeConnected > 60)
int64_t nTime = GetTime();
if (nTime - pnode->nTimeConnected > 60)
{
if (pnode->nLastRecv == 0 || pnode->nLastSend == 0)
{
LogPrint("net", "socket no message in first 60 seconds, %d %d\n", pnode->nLastRecv != 0, pnode->nLastSend != 0);
pnode->fDisconnect = true;
}
else if (GetTime() - pnode->nLastSend > 90*60 && GetTime() - pnode->nLastSendEmpty > 90*60)
else if (nTime - pnode->nLastSend > TIMEOUT_INTERVAL)
{
LogPrintf("socket not sending\n");
LogPrintf("socket sending timeout: %is\n", nTime - pnode->nLastSend);
pnode->fDisconnect = true;
}
else if (GetTime() - pnode->nLastRecv > 90*60)
else if (nTime - pnode->nLastRecv > (pnode->nVersion > BIP0031_VERSION ? TIMEOUT_INTERVAL : 90*60))
{
LogPrintf("socket inactivity timeout\n");
LogPrintf("socket receive timeout: %is\n", nTime - pnode->nLastRecv);
pnode->fDisconnect = true;
}
else if (pnode->nPingNonceSent && pnode->nPingUsecStart + TIMEOUT_INTERVAL * 1000000 < GetTimeMicros())
{
LogPrintf("ping timeout: %fs\n", 0.000001 * (GetTimeMicros() - pnode->nPingUsecStart));
pnode->fDisconnect = true;
}
}

13
src/net.h

@ -28,6 +28,7 @@ @@ -28,6 +28,7 @@
#include <boost/signals2/signal.hpp>
#include <openssl/rand.h>
class CAddrMan;
class CBlockIndex;
class CNode;
@ -36,6 +37,10 @@ namespace boost { @@ -36,6 +37,10 @@ namespace boost {
class thread_group;
}
/** Time between pings automatically sent out for latency probing and keepalive (in seconds). */
static const int PING_INTERVAL = 2 * 60;
/** Time after which to disconnect, after waiting for a ping response (or inactivity). */
static const int TIMEOUT_INTERVAL = 20 * 60;
/** The maximum number of entries in an 'inv' protocol message */
static const unsigned int MAX_INV_SZ = 50000;
/** -upnp default */
@ -217,7 +222,6 @@ public: @@ -217,7 +222,6 @@ public:
int64_t nLastSend;
int64_t nLastRecv;
int64_t nLastSendEmpty;
int64_t nTimeConnected;
CAddress addr;
std::string addrName;
@ -273,10 +277,14 @@ public: @@ -273,10 +277,14 @@ public:
CCriticalSection cs_inventory;
std::multimap<int64_t, CInv> mapAskFor;
// Ping time measurement
// Ping time measurement:
// The pong reply we're expecting, or 0 if no pong expected.
uint64_t nPingNonceSent;
// Time (in usec) the last ping was sent, or 0 if no ping was ever sent.
int64_t nPingUsecStart;
// Last measured round-trip time.
int64_t nPingUsecTime;
// Whether a ping is requested.
bool fPingQueued;
CNode(SOCKET hSocketIn, CAddress addrIn, std::string addrNameIn = "", bool fInboundIn=false) : ssSend(SER_NETWORK, INIT_PROTO_VERSION), setAddrKnown(5000)
@ -288,7 +296,6 @@ public: @@ -288,7 +296,6 @@ public:
nLastRecv = 0;
nSendBytes = 0;
nRecvBytes = 0;
nLastSendEmpty = GetTime();
nTimeConnected = GetTime();
addr = addrIn;
addrName = addrNameIn == "" ? addr.ToStringIPPort() : addrNameIn;

Loading…
Cancel
Save