Преглед изворни кода

Push more than one packet for credentials if we happen to have a whole lot. Should not happen often but might if a member has tons of tags.

Adam Ierymenko пре 9 година
родитељ
комит
a3c7627acf
2 измењених фајлова са 46 додато и 43 уклоњено
  1. 45 41
      node/Membership.cpp
  2. 1 2
      node/Membership.hpp

+ 45 - 41
node/Membership.cpp

@@ -28,61 +28,65 @@
 
 namespace ZeroTier {
 
-bool Membership::sendCredentialsIfNeeded(const RuntimeEnvironment *RR,const uint64_t now,const Address &peerAddress,const NetworkConfig &nconf,const Capability *cap)
+void Membership::sendCredentialsIfNeeded(const RuntimeEnvironment *RR,const uint64_t now,const Address &peerAddress,const NetworkConfig &nconf,const Capability *cap)
 {
 	if ((now - _lastPushAttempt) < 1000ULL)
-		return false;
+		return;
 	_lastPushAttempt = now;
 
 	try {
-		Buffer<ZT_PROTO_MAX_PACKET_LENGTH> capsAndTags;
+		bool unfinished;
+		do {
+			unfinished = false;
+			Buffer<ZT_PROTO_MAX_PACKET_LENGTH> capsAndTags;
 
-		unsigned int appendedCaps = 0;
-		if (cap) {
-			capsAndTags.addSize(2);
-			std::map<uint32_t,CState>::iterator cs(_caps.find(cap->id()));
-			if ((cs != _caps.end())&&((now - cs->second.lastPushed) >= ZT_CREDENTIAL_PUSH_EVERY)) {
-				cap->serialize(capsAndTags);
-				cs->second.lastPushed = now;
-				++appendedCaps;
+			unsigned int appendedCaps = 0;
+			if (cap) {
+				capsAndTags.addSize(2);
+				std::map<uint32_t,CState>::iterator cs(_caps.find(cap->id()));
+				if ((cs != _caps.end())&&((now - cs->second.lastPushed) >= ZT_CREDENTIAL_PUSH_EVERY)) {
+					cap->serialize(capsAndTags);
+					cs->second.lastPushed = now;
+					++appendedCaps;
+				}
+				capsAndTags.setAt<uint16_t>(0,(uint16_t)appendedCaps);
+			} else {
+				capsAndTags.append((uint16_t)0);
 			}
-			capsAndTags.setAt<uint16_t>(0,(uint16_t)appendedCaps);
-		} else {
-			capsAndTags.append((uint16_t)0);
-		}
 
-		unsigned int appendedTags = 0;
-		const unsigned int tagCountPos = capsAndTags.size();
-		capsAndTags.addSize(2);
-		for(unsigned int i=0;i<nconf.tagCount;++i) {
-			TState *const ts = _tags.get(nconf.tags[i].id());
-			if ((now - ts->lastPushed) >= ZT_CREDENTIAL_PUSH_EVERY) {
-				if ((capsAndTags.size() + sizeof(Tag)) > (ZT_PROTO_MAX_PACKET_LENGTH - sizeof(CertificateOfMembership)))
-					break;
-				nconf.tags[i].serialize(capsAndTags);
-				ts->lastPushed = now;
-				++appendedTags;
+			unsigned int appendedTags = 0;
+			const unsigned int tagCountPos = capsAndTags.size();
+			capsAndTags.addSize(2);
+			for(unsigned int i=0;i<nconf.tagCount;++i) {
+				TState *const ts = _tags.get(nconf.tags[i].id());
+				if ((now - ts->lastPushed) >= ZT_CREDENTIAL_PUSH_EVERY) {
+					if ((capsAndTags.size() + sizeof(Tag)) >= (ZT_PROTO_MAX_PACKET_LENGTH - sizeof(CertificateOfMembership))) {
+						unfinished = true;
+						break;
+					}
+					nconf.tags[i].serialize(capsAndTags);
+					ts->lastPushed = now;
+					++appendedTags;
+				}
 			}
-		}
-		capsAndTags.setAt<uint16_t>(tagCountPos,(uint16_t)appendedTags);
+			capsAndTags.setAt<uint16_t>(tagCountPos,(uint16_t)appendedTags);
 
-		const bool needCom = ((nconf.isPrivate())&&(nconf.com)&&((now - _lastPushedCom) >= ZT_CREDENTIAL_PUSH_EVERY));
-		if ( (needCom) || (appendedCaps) || (appendedTags) ) {
-			Packet outp(peerAddress,RR->identity.address(),Packet::VERB_NETWORK_CREDENTIALS);
-			if (needCom) {
-				nconf.com.serialize(outp);
-				_lastPushedCom = now;
+			const bool needCom = ((nconf.isPrivate())&&(nconf.com)&&((now - _lastPushedCom) >= ZT_CREDENTIAL_PUSH_EVERY));
+			if ( (needCom) || (appendedCaps) || (appendedTags) ) {
+				Packet outp(peerAddress,RR->identity.address(),Packet::VERB_NETWORK_CREDENTIALS);
+				if (needCom) {
+					nconf.com.serialize(outp);
+					_lastPushedCom = now;
+				}
+				outp.append((uint8_t)0x00);
+				outp.append(capsAndTags.data(),capsAndTags.size());
+				outp.compress();
+				RR->sw->send(outp,true);
 			}
-			outp.append((uint8_t)0x00);
-			outp.append(capsAndTags.data(),capsAndTags.size());
-			outp.compress();
-			RR->sw->send(outp,true);
-			return true;
-		}
+		} while (unfinished); // if there are many tags, etc., we can send more than one
 	} catch ( ... ) {
 		TRACE("unable to send credentials due to unexpected exception");
 	}
-	return false;
 }
 
 int Membership::addCredential(const RuntimeEnvironment *RR,const CertificateOfMembership &com)

+ 1 - 2
node/Membership.hpp

@@ -127,9 +127,8 @@ public:
 	 * @param peerAddress Address of member peer
 	 * @param nconf My network config
 	 * @param cap Capability to send or 0 if none
-	 * @return True if we pushed something
 	 */
-	bool sendCredentialsIfNeeded(const RuntimeEnvironment *RR,const uint64_t now,const Address &peerAddress,const NetworkConfig &nconf,const Capability *cap);
+	void sendCredentialsIfNeeded(const RuntimeEnvironment *RR,const uint64_t now,const Address &peerAddress,const NetworkConfig &nconf,const Capability *cap);
 
 	/**
 	 * @param nconf Our network config