diff --git a/node/Constants.hpp b/node/Constants.hpp index c41b7c696..8357bb5e9 100644 --- a/node/Constants.hpp +++ b/node/Constants.hpp @@ -261,7 +261,7 @@ error_no_ZT_ARCH_defined; /** * Expiration time in ms for multicast deduplication history items */ -#define ZT_MULTICAST_DEDUP_HISTORY_EXPIRE 4000 +#define ZT_MULTICAST_DEDUP_HISTORY_EXPIRE 2000 /** * Period between announcements of all multicast 'likes' in ms diff --git a/node/Network.cpp b/node/Network.cpp index d01eb2951..fa5b86d31 100644 --- a/node/Network.cpp +++ b/node/Network.cpp @@ -117,8 +117,7 @@ bool Network::CertificateOfMembership::compare(const CertificateOfMembership &ot return true; } -// A low default global rate, fast enough for something like ARP -const Network::MulticastRates::Rate Network::MulticastRates::GLOBAL_DEFAULT_RATE(128,128,64); +const Network::MulticastRates::Rate Network::MulticastRates::GLOBAL_DEFAULT_RATE(65535,65535,64); const char *Network::statusString(const Status s) throw() diff --git a/node/Switch.cpp b/node/Switch.cpp index 5ba56555a..e0ffba0bd 100644 --- a/node/Switch.cpp +++ b/node/Switch.cpp @@ -105,10 +105,16 @@ void Switch::onLocalEthernet(const SharedPtr &network,const MAC &from,c mg = MulticastGroup::deriveMulticastGroupForAddressResolution(InetAddress(data.field(24,4),4,0)); } - // Check our own multicasts against the global rate for this network - // just to be polite. + uint64_t crc = Multicaster::computeMulticastDedupCrc(network->id(),from,mg,etherType,data.data(),data.size()); + uint64_t now = Utils::now(); + + if (_r->multicaster->checkDuplicate(crc,now)) { + LOG("%s/%.16llx: multicast group %s: dropped %u bytes, duplicate multicast in too short a time frame",network->tap().deviceName().c_str(),(unsigned long long)network->id(),mg.toString().c_str(),(unsigned int)data.size()); + return; + } + _r->multicaster->addToDedupHistory(crc,now); if (!network->updateAndCheckMulticastBalance(_r->identity.address(),mg,data.size())) { - LOG("didn't send local multicast %u byte multicast packet to network %.16llx: not within budget for multicast group %s",(unsigned int)data.size(),(unsigned long long)network->id(),mg.toString().c_str()); + LOG("%s/%.16llx: multicast group %s: dropped %u bytes, out of budget",network->tap().deviceName().c_str(),(unsigned long long)network->id(),mg.toString().c_str(),(unsigned int)data.size()); return; } @@ -124,7 +130,7 @@ void Switch::onLocalEthernet(const SharedPtr &network,const MAC &from,c bloom, ZT_MULTICAST_PROPAGATION_BREADTH, propPeers, - Utils::now()); + now); if (!np) return;