summaryrefslogtreecommitdiff
path: root/node/Peer.cpp
diff options
context:
space:
mode:
authorAdam Ierymenko <adam.ierymenko@gmail.com>2016-08-24 16:16:39 -0700
committerAdam Ierymenko <adam.ierymenko@gmail.com>2016-08-24 16:16:39 -0700
commitc476285bd638da01e0297c76951609c70f4ab3cf (patch)
treeff7d99720b453f9742dc1a4f4e023f75cc69a499 /node/Peer.cpp
parent63e8ad4cc3b91cf0de89012da1ef78deee1a566a (diff)
downloadinfinitytier-c476285bd638da01e0297c76951609c70f4ab3cf.tar.gz
infinitytier-c476285bd638da01e0297c76951609c70f4ab3cf.zip
Harden PUSH_DIRECT_PATHS and simplify things by only doing it on receive when hops>0 and trust has been established.
Diffstat (limited to 'node/Peer.cpp')
-rw-r--r--node/Peer.cpp171
1 files changed, 86 insertions, 85 deletions
diff --git a/node/Peer.cpp b/node/Peer.cpp
index 77e1d0b5..7691408e 100644
--- a/node/Peer.cpp
+++ b/node/Peer.cpp
@@ -66,7 +66,8 @@ void Peer::received(
uint64_t packetId,
Packet::Verb verb,
uint64_t inRePacketId,
- Packet::Verb inReVerb)
+ Packet::Verb inReVerb,
+ const bool trustEstablished)
{
#ifdef ZT_ENABLE_CLUSTER
bool suboptimalPath = false;
@@ -184,6 +185,8 @@ void Peer::received(
}
}
+ } else if (trustEstablished) {
+ _pushDirectPaths(localAddr,remoteAddr,now);
}
if ((now - _lastAnnouncedTo) >= ((ZT_MULTICAST_LIKE_EXPIRE / 2) - 1000)) {
@@ -241,90 +244,6 @@ bool Peer::doPingAndKeepalive(uint64_t now,int inetAddressFamily)
return false;
}
-bool Peer::pushDirectPaths(const InetAddress &localAddr,const InetAddress &toAddress,uint64_t now,bool force)
-{
-#ifdef ZT_ENABLE_CLUSTER
- // Cluster mode disables normal PUSH_DIRECT_PATHS in favor of cluster-based peer redirection
- if (RR->cluster)
- return false;
-#endif
-
- if (!force) {
- if ((now - _lastDirectPathPushSent) < ZT_DIRECT_PATH_PUSH_INTERVAL)
- return false;
- else _lastDirectPathPushSent = now;
- }
-
- std::vector<InetAddress> pathsToPush;
-
- std::vector<InetAddress> dps(RR->node->directPaths());
- for(std::vector<InetAddress>::const_iterator i(dps.begin());i!=dps.end();++i)
- pathsToPush.push_back(*i);
-
- std::vector<InetAddress> sym(RR->sa->getSymmetricNatPredictions());
- for(unsigned long i=0,added=0;i<sym.size();++i) {
- InetAddress tmp(sym[(unsigned long)RR->node->prng() % sym.size()]);
- if (std::find(pathsToPush.begin(),pathsToPush.end(),tmp) == pathsToPush.end()) {
- pathsToPush.push_back(tmp);
- if (++added >= ZT_PUSH_DIRECT_PATHS_MAX_PER_SCOPE_AND_FAMILY)
- break;
- }
- }
- if (pathsToPush.empty())
- return false;
-
-#ifdef ZT_TRACE
- {
- std::string ps;
- for(std::vector<InetAddress>::const_iterator p(pathsToPush.begin());p!=pathsToPush.end();++p) {
- if (ps.length() > 0)
- ps.push_back(',');
- ps.append(p->toString());
- }
- TRACE("pushing %u direct paths to %s: %s",(unsigned int)pathsToPush.size(),_id.address().toString().c_str(),ps.c_str());
- }
-#endif
-
- std::vector<InetAddress>::const_iterator p(pathsToPush.begin());
- while (p != pathsToPush.end()) {
- Packet outp(_id.address(),RR->identity.address(),Packet::VERB_PUSH_DIRECT_PATHS);
- outp.addSize(2); // leave room for count
-
- unsigned int count = 0;
- while ((p != pathsToPush.end())&&((outp.size() + 24) < 1200)) {
- uint8_t addressType = 4;
- switch(p->ss_family) {
- case AF_INET:
- break;
- case AF_INET6:
- addressType = 6;
- break;
- default: // we currently only push IP addresses
- ++p;
- continue;
- }
-
- outp.append((uint8_t)0); // no flags
- outp.append((uint16_t)0); // no extensions
- outp.append(addressType);
- outp.append((uint8_t)((addressType == 4) ? 6 : 18));
- outp.append(p->rawIpData(),((addressType == 4) ? 4 : 16));
- outp.append((uint16_t)p->port());
-
- ++count;
- ++p;
- }
-
- if (count) {
- outp.setAt(ZT_PACKET_IDX_PAYLOAD,(uint16_t)count);
- outp.armor(_key,true);
- RR->node->putPacket(localAddr,toAddress,outp.data(),outp.size(),0);
- }
- }
-
- return true;
-}
-
bool Peer::resetWithinScope(InetAddress::IpScope scope,uint64_t now)
{
unsigned int np = _numPaths;
@@ -453,4 +372,86 @@ Path *Peer::_getBestPath(const uint64_t now,int inetAddressFamily)
return bestPath;
}
+bool Peer::_pushDirectPaths(const InetAddress &localAddr,const InetAddress &toAddress,uint64_t now)
+{
+#ifdef ZT_ENABLE_CLUSTER
+ // Cluster mode disables normal PUSH_DIRECT_PATHS in favor of cluster-based peer redirection
+ if (RR->cluster)
+ return false;
+#endif
+
+ if ((now - _lastDirectPathPushSent) < ZT_DIRECT_PATH_PUSH_INTERVAL)
+ return false;
+ else _lastDirectPathPushSent = now;
+
+ std::vector<InetAddress> pathsToPush;
+
+ std::vector<InetAddress> dps(RR->node->directPaths());
+ for(std::vector<InetAddress>::const_iterator i(dps.begin());i!=dps.end();++i)
+ pathsToPush.push_back(*i);
+
+ std::vector<InetAddress> sym(RR->sa->getSymmetricNatPredictions());
+ for(unsigned long i=0,added=0;i<sym.size();++i) {
+ InetAddress tmp(sym[(unsigned long)RR->node->prng() % sym.size()]);
+ if (std::find(pathsToPush.begin(),pathsToPush.end(),tmp) == pathsToPush.end()) {
+ pathsToPush.push_back(tmp);
+ if (++added >= ZT_PUSH_DIRECT_PATHS_MAX_PER_SCOPE_AND_FAMILY)
+ break;
+ }
+ }
+ if (pathsToPush.empty())
+ return false;
+
+#ifdef ZT_TRACE
+ {
+ std::string ps;
+ for(std::vector<InetAddress>::const_iterator p(pathsToPush.begin());p!=pathsToPush.end();++p) {
+ if (ps.length() > 0)
+ ps.push_back(',');
+ ps.append(p->toString());
+ }
+ TRACE("pushing %u direct paths to %s: %s",(unsigned int)pathsToPush.size(),_id.address().toString().c_str(),ps.c_str());
+ }
+#endif
+
+ std::vector<InetAddress>::const_iterator p(pathsToPush.begin());
+ while (p != pathsToPush.end()) {
+ Packet outp(_id.address(),RR->identity.address(),Packet::VERB_PUSH_DIRECT_PATHS);
+ outp.addSize(2); // leave room for count
+
+ unsigned int count = 0;
+ while ((p != pathsToPush.end())&&((outp.size() + 24) < 1200)) {
+ uint8_t addressType = 4;
+ switch(p->ss_family) {
+ case AF_INET:
+ break;
+ case AF_INET6:
+ addressType = 6;
+ break;
+ default: // we currently only push IP addresses
+ ++p;
+ continue;
+ }
+
+ outp.append((uint8_t)0); // no flags
+ outp.append((uint16_t)0); // no extensions
+ outp.append(addressType);
+ outp.append((uint8_t)((addressType == 4) ? 6 : 18));
+ outp.append(p->rawIpData(),((addressType == 4) ? 4 : 16));
+ outp.append((uint16_t)p->port());
+
+ ++count;
+ ++p;
+ }
+
+ if (count) {
+ outp.setAt(ZT_PACKET_IDX_PAYLOAD,(uint16_t)count);
+ outp.armor(_key,true);
+ RR->node->putPacket(localAddr,toAddress,outp.data(),outp.size(),0);
+ }
+ }
+
+ return true;
+}
+
} // namespace ZeroTier