aboutsummaryrefslogtreecommitdiff
path: root/src/main.cpp
diff options
context:
space:
mode:
authorlangerhans <[email protected]>2015-07-02 19:54:14 +0200
committerlangerhans <[email protected]>2015-07-02 19:54:14 +0200
commit66eb58e86c04432d0ef218e0df9d6b28e0ea5904 (patch)
treef96a918113239134511c06153cd87b50f1c23776 /src/main.cpp
parentMerge branch '1.8.2-dev' into 1.8-maint (diff)
parentMerge pull request #1191 from langerhans/1.8.3-releaseprep (diff)
downloaddiscoin-66eb58e86c04432d0ef218e0df9d6b28e0ea5904.tar.xz
discoin-66eb58e86c04432d0ef218e0df9d6b28e0ea5904.zip
Merge branch '1.8.3-dev' into 1.8-maint
Diffstat (limited to 'src/main.cpp')
-rw-r--r--src/main.cpp62
1 files changed, 40 insertions, 22 deletions
diff --git a/src/main.cpp b/src/main.cpp
index ed237a73c..9d1eca948 100644
--- a/src/main.cpp
+++ b/src/main.cpp
@@ -207,9 +207,13 @@ struct CBlockReject {
// processing of incoming data is done after the ProcessMessage call returns,
// and we're no longer holding the node's locks.
struct CNodeState {
+ //! The peer's address
+ CService address;
+ //! Whether we have a fully established connection.
+ bool fCurrentlyConnected;
// Accumulated misbehaviour score for this peer.
int nMisbehavior;
- // Whether this peer should be disconnected and banned.
+ // Whether this peer should be disconnected and banned (unless whitelisted).
bool fShouldBan;
// String name of this peer (debugging/logging purposes).
std::string name;
@@ -223,6 +227,7 @@ struct CNodeState {
int64_t nLastBlockProcess;
CNodeState() {
+ fCurrentlyConnected = false;
nMisbehavior = 0;
fShouldBan = false;
nBlocksToDownload = 0;
@@ -253,12 +258,16 @@ void InitializeNode(NodeId nodeid, const CNode *pnode) {
LOCK(cs_main);
CNodeState &state = mapNodeState.insert(std::make_pair(nodeid, CNodeState())).first->second;
state.name = pnode->addrName;
+ state.address = pnode->addr;
}
void FinalizeNode(NodeId nodeid) {
LOCK(cs_main);
CNodeState *state = State(nodeid);
+ if (state->nMisbehavior == 0 && state->fCurrentlyConnected) {
+ AddressCurrentlyConnected(state->address);
+ }
BOOST_FOREACH(const QueuedBlock& entry, state->vBlocksInFlight)
mapBlocksInFlight.erase(entry.hash);
BOOST_FOREACH(const uint256& hash, state->vBlocksToDownload)
@@ -1571,7 +1580,8 @@ void Misbehaving(NodeId pnode, int howmuch)
return;
state->nMisbehavior += howmuch;
- if (state->nMisbehavior >= GetArg("-banscore", 100))
+ int banscore = GetArg("-banscore", 100);
+ if (state->nMisbehavior >= banscore && state->nMisbehavior - howmuch < banscore)
{
LogPrintf("Misbehaving: %s (%d -> %d) BAN THRESHOLD EXCEEDED\n", state->name, state->nMisbehavior-howmuch, state->nMisbehavior);
state->fShouldBan = true;
@@ -3737,7 +3747,7 @@ void static ProcessGetData(CNode* pfrom)
}
}
-bool static ProcessMessage(CNode* pfrom, string strCommand, CDataStream& vRecv)
+bool static ProcessMessage(CNode* pfrom, string strCommand, CDataStream& vRecv, int64_t nTimeReceived)
{
RandAddSeedPerfmon();
LogPrint("net", "received: %s (%" PRIszu" bytes)\n", strCommand, vRecv.size());
@@ -3822,7 +3832,7 @@ bool static ProcessMessage(CNode* pfrom, string strCommand, CDataStream& vRecv)
if (!pfrom->fInbound)
{
// Advertise our address
- if (!fNoListen && !IsInitialBlockDownload())
+ if (fListen && !IsInitialBlockDownload())
{
CAddress addr = GetLocalAddress(&pfrom->addr);
if (addr.IsRoutable())
@@ -3870,6 +3880,12 @@ bool static ProcessMessage(CNode* pfrom, string strCommand, CDataStream& vRecv)
else if (strCommand == "verack")
{
pfrom->SetRecvVersion(min(pfrom->nVersion, PROTOCOL_VERSION));
+
+ // Mark this node as currently connected, so we update its timestamp later.
+ if (pfrom->fNetworkNode) {
+ LOCK(cs_main);
+ State(pfrom->GetId())->fCurrentlyConnected = true;
+ }
}
@@ -4163,6 +4179,11 @@ bool static ProcessMessage(CNode* pfrom, string strCommand, CDataStream& vRecv)
unsigned int nEvicted = LimitOrphanTxSize(nMaxOrphanTx);
if (nEvicted > 0)
LogPrint("mempool", "mapOrphan overflow, removed %u tx\n", nEvicted);
+ } else if (pfrom->fWhitelisted) {
+ // Always relay transactions received from whitelisted peers, even
+ // if they are already in the mempool (allowing the node to function
+ // as a gateway for nodes hidden behind it).
+ RelayTransaction(tx, tx.GetHash());
}
int nDoS = 0;
if (state.IsInvalid(nDoS))
@@ -4257,7 +4278,7 @@ bool static ProcessMessage(CNode* pfrom, string strCommand, CDataStream& vRecv)
else if (strCommand == "pong")
{
- int64_t pingUsecEnd = GetTimeMicros();
+ int64_t pingUsecEnd = nTimeReceived;
uint64_t nonce = 0;
size_t nAvail = vRecv.in_avail();
bool bPingFinished = false;
@@ -4426,11 +4447,6 @@ bool static ProcessMessage(CNode* pfrom, string strCommand, CDataStream& vRecv)
}
- // Update the last seen time for this node's address
- if (pfrom->fNetworkNode)
- if (strCommand == "version" || strCommand == "addr" || strCommand == "inv" || strCommand == "getdata" || strCommand == "ping")
- AddressCurrentlyConnected(pfrom->addr);
-
return true;
}
@@ -4513,7 +4529,7 @@ bool ProcessMessages(CNode* pfrom)
bool fRet = false;
try
{
- fRet = ProcessMessage(pfrom, strCommand, vRecv);
+ fRet = ProcessMessage(pfrom, strCommand, vRecv, msg.nTime);
boost::this_thread::interruption_point();
}
catch (std::ios_base::failure& e)
@@ -4572,8 +4588,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) {
@@ -4581,15 +4597,14 @@ bool SendMessages(CNode* pto, bool fSendTrickle)
while (nonce == 0) {
RAND_bytes((unsigned char*)&nonce, sizeof(nonce));
}
- pto->nPingNonceSent = nonce;
pto->fPingQueued = false;
+ pto->nPingUsecStart = GetTimeMicros();
if (pto->nVersion > BIP0031_VERSION) {
- // Take timestamp as close as possible before transmitting ping
- pto->nPingUsecStart = GetTimeMicros();
+ 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");
}
}
@@ -4611,7 +4626,7 @@ bool SendMessages(CNode* pto, bool fSendTrickle)
pnode->setAddrKnown.clear();
// Rebroadcast our address
- if (!fNoListen)
+ if (fListen)
{
CAddress addr = GetLocalAddress(&pnode->addr);
if (addr.IsRoutable())
@@ -4650,11 +4665,14 @@ bool SendMessages(CNode* pto, bool fSendTrickle)
CNodeState &state = *State(pto->GetId());
if (state.fShouldBan) {
- if (pto->addr.IsLocal())
- LogPrintf("Warning: not banning local node %s!\n", pto->addr.ToString());
+ if (pto->fWhitelisted)
+ LogPrintf("Warning: not punishing whitelisted peer %s!\n", pto->addr.ToString());
else {
pto->fDisconnect = true;
- CNode::Ban(pto->addr);
+ if (pto->addr.IsLocal())
+ LogPrintf("Warning: not banning local peer %s!\n", pto->addr.ToString());
+ else
+ CNode::Ban(pto->addr);
}
state.fShouldBan = false;
}