Browse Source

Cluster sub-optimal is in fact necessary...

Adam Ierymenko 9 years ago
parent
commit
4992ac2d9f
4 changed files with 22 additions and 41 deletions
  1. 2 2
      node/IncomingPacket.cpp
  2. 0 8
      node/Path.hpp
  3. 13 27
      node/Peer.cpp
  4. 7 4
      node/Peer.hpp

+ 2 - 2
node/IncomingPacket.cpp

@@ -1042,7 +1042,7 @@ bool IncomingPacket::_doPUSH_DIRECT_PATHS(const RuntimeEnvironment *RR,const Sha
 
 					bool redundant = false;
 					if ((flags & ZT_PUSH_DIRECT_PATHS_FLAG_CLUSTER_REDIRECT) != 0) {
-						peer->makeExclusive(a);
+						peer->setClusterOptimal(a);
 					} else {
 						redundant = peer->hasActivePathTo(now,a);
 					}
@@ -1061,7 +1061,7 @@ bool IncomingPacket::_doPUSH_DIRECT_PATHS(const RuntimeEnvironment *RR,const Sha
 
 					bool redundant = false;
 					if ((flags & ZT_PUSH_DIRECT_PATHS_FLAG_CLUSTER_REDIRECT) != 0) {
-						peer->makeExclusive(a);
+						peer->setClusterOptimal(a);
 					} else {
 						redundant = peer->hasActivePathTo(now,a);
 					}

+ 0 - 8
node/Path.hpp

@@ -165,14 +165,6 @@ public:
 		return ( ((unsigned int)_ipScope << 1) | (unsigned int)(_addr.ss_family == AF_INET6) );
 	}
 
-	/**
-	 * @return This path's overall quality score (higher is better)
-	 */
-	inline uint64_t score() const
-	{
-		return (_lastIn + (preferenceRank() * (ZT_PEER_PING_PERIOD / ZT_PATH_MAX_PREFERENCE_RANK)));
-	}
-
 	/**
 	 * Check whether this address is valid for a ZeroTier path
 	 *

+ 13 - 27
node/Peer.cpp

@@ -156,9 +156,10 @@ void Peer::received(
 				_paths[slot].lastReceive = now;
 #ifdef ZT_ENABLE_CLUSTER
 				_paths[slot].clusterSuboptimal = suboptimalPath;
-
 				if (RR->cluster)
 					RR->cluster->broadcastHavePeer(_id);
+#else
+				_paths[slot].clusterSuboptimal = false;
 #endif
 			} else {
 
@@ -196,36 +197,21 @@ bool Peer::hasActivePathTo(uint64_t now,const InetAddress &addr) const
 	return false;
 }
 
-void Peer::makeExclusive(const InetAddress &addr)
+void Peer::setClusterOptimal(const InetAddress &addr)
 {
 	Mutex::Lock _l(_paths_m);
 
-	bool have = false;
+	int have = -1;
 	for(unsigned int p=0;p<_numPaths;++p) {
 		if (_paths[p].path->address() == addr) {
-			have = true;
+			have = (int)p;
 			break;
 		}
 	}
 
-	if (have) {
-		unsigned int np = _numPaths;
-		unsigned int x = 0;
-		unsigned int y = 0;
-		while (x < np) {
-			if ((_paths[x].path->address().ss_family != addr.ss_family)||(_paths[x].path->address() == addr)) {
-				if (y != x) {
-					_paths[y].path = _paths[x].path;
-					_paths[y].lastReceive = _paths[x].lastReceive;
-	#ifdef ZT_ENABLE_CLUSTER
-					_paths[y].clusterSuboptimal = _paths[x].clusterSuboptimal;
-	#endif
-				}
-				++y;
-			}
-			++x;
-		}
-		_numPaths = y;
+	if (have >= 0) {
+		for(unsigned int p=0;p<_numPaths;++p)
+			_paths[p].clusterSuboptimal = (p != have);
 	}
 }
 
@@ -237,7 +223,7 @@ bool Peer::sendDirect(const void *data,unsigned int len,uint64_t now,bool forceE
 	uint64_t best = 0ULL;
 	for(unsigned int p=0;p<_numPaths;++p) {
 		if (_paths[p].path->alive(now)||(forceEvenIfDead)) {
-			const uint64_t s = _paths[p].path->score();
+			const uint64_t s = _pathScore(p);
 			if (s >= best) {
 				best = s;
 				bestp = (int)p;
@@ -259,7 +245,7 @@ SharedPtr<Path> Peer::getBestPath(uint64_t now)
 	int bestp = -1;
 	uint64_t best = 0ULL;
 	for(unsigned int p=0;p<_numPaths;++p) {
-		const uint64_t s = _paths[p].path->score();
+		const uint64_t s = _pathScore(p);
 		if (s >= best) {
 			best = s;
 			bestp = (int)p;
@@ -296,7 +282,7 @@ bool Peer::doPingAndKeepalive(uint64_t now,int inetAddressFamily)
 	int bestp = -1;
 	uint64_t best = 0ULL;
 	for(unsigned int p=0;p<_numPaths;++p) {
-		const uint64_t s = _paths[p].path->score();
+		const uint64_t s = _pathScore(p);
 		if (s >= best) {
 			best = s;
 			bestp = (int)p;
@@ -361,13 +347,13 @@ void Peer::getBestActiveAddresses(uint64_t now,InetAddress &v4,InetAddress &v6)
 	uint64_t best4 = 0ULL,best6 = 0ULL;
 	for(unsigned int p=0;p<_numPaths;++p) {
 		if (_paths[p].path->address().ss_family == AF_INET) {
-			const uint64_t s = _paths[p].path->score();
+			const uint64_t s = _pathScore(p);
 			if (s >= best4) {
 				best4 = s;
 				bestp4 = (int)p;
 			}
 		} else if (_paths[p].path->address().ss_family == AF_INET6) {
-			const uint64_t s = _paths[p].path->score();
+			const uint64_t s = _pathScore(p);
 			if (s >= best6) {
 				best6 = s;
 				bestp6 = (int)p;

+ 7 - 4
node/Peer.hpp

@@ -121,11 +121,11 @@ public:
 	bool hasActivePathTo(uint64_t now,const InetAddress &addr) const;
 
 	/**
-	 * If we have a confirmed path to this address, forget all others within the same address family
+	 * If we have a confirmed path to this address, mark others as cluster suboptimal
 	 *
 	 * @param addr Address to make exclusive
 	 */
-	void makeExclusive(const InetAddress &addr);
+	void setClusterOptimal(const InetAddress &addr);
 
 	/**
 	 * Send via best direct path
@@ -363,6 +363,11 @@ public:
 private:
 	bool _pushDirectPaths(const SharedPtr<Path> &path,uint64_t now);
 
+	inline uint64_t _pathScore(const unsigned int p) const
+	{
+		return ( (_paths[p].path->lastIn() + (_paths[p].path->preferenceRank() * (ZT_PEER_PING_PERIOD / ZT_PATH_MAX_PREFERENCE_RANK))) - ((ZT_PEER_PING_PERIOD * 10) * (uint64_t)_paths[p].clusterSuboptimal) );
+	}
+
 	unsigned char _key[ZT_PEER_SECRET_KEY_LENGTH];
 
 	const RuntimeEnvironment *RR;
@@ -381,9 +386,7 @@ private:
 	struct {
 		SharedPtr<Path> path;
 		uint64_t lastReceive;
-#ifdef ZT_ENABLE_CLUSTER
 		bool clusterSuboptimal;
-#endif
 	} _paths[ZT_MAX_PEER_NETWORK_PATHS];
 	Mutex _paths_m;
 	unsigned int _numPaths;