diff --git a/src/fne/network/TrafficNetwork.cpp b/src/fne/network/TrafficNetwork.cpp index 8b9e9b0f..78ef18b7 100644 --- a/src/fne/network/TrafficNetwork.cpp +++ b/src/fne/network/TrafficNetwork.cpp @@ -1818,6 +1818,13 @@ std::vector TrafficNetwork::peerAffiliat bool TrafficNetwork::updatePeerAffiliation(uint32_t peerId, uint32_t srcId, uint32_t dstId) { std::unordered_map aggregate; + + if (srcId == P25DEF::WUID_FNE) { + LogWarning(LOG_MASTER, "PEER %u ignoring affiliation for FNE source ID", peerId); + return false; + } + + // scope is intentional { std::lock_guard updateLock(m_affiliationUpdateMutex); std::shared_ptr affiliations = getPeerAffiliations(peerId); @@ -1838,6 +1845,8 @@ bool TrafficNetwork::updatePeerAffiliation(uint32_t peerId, uint32_t srcId, uint bool TrafficNetwork::removePeerAffiliation(uint32_t peerId, uint32_t srcId) { std::unordered_map aggregate; + + // scope is intentional { std::lock_guard updateLock(m_affiliationUpdateMutex); std::shared_ptr affiliations = getPeerAffiliations(peerId); @@ -1857,6 +1866,8 @@ bool TrafficNetwork::removePeerAffiliation(uint32_t peerId, uint32_t srcId) bool TrafficNetwork::replacePeerAffiliations(uint32_t peerId, const std::unordered_map& affiliations) { std::unordered_map aggregate; + + // scope is intentional { std::lock_guard updateLock(m_affiliationUpdateMutex); std::shared_ptr peerAffiliations = getPeerAffiliations(peerId); @@ -1880,11 +1891,13 @@ std::unordered_map TrafficNetwork::buildAggregatedAffiliatio return lhs.first < rhs.first; }); + // build the aggregate affiliation map from the peer snapshot std::unordered_map aggregate; for (const auto& peer : peerSnapshot) { if (peer.second == nullptr) continue; + // iterate over the peer's group affiliations and merge into the aggregate map const std::unordered_map affiliations = peer.second->grpAffTable(); for (const auto& affiliation : affiliations) { const auto result = aggregate.emplace(affiliation.first, affiliation.second); @@ -1914,6 +1927,13 @@ void TrafficNetwork::publishAggregatedAffiliations(const std::unordered_map aggregate; + + if (srcId == P25DEF::WUID_FNE) { + LogWarning(LOG_MASTER, "PEER %u ignoring unit registration for FNE source ID", peerId); + return false; + } + + // scope is intentional { std::lock_guard updateLock(m_affiliationUpdateMutex); std::shared_ptr registrations = getPeerAffiliations(peerId); @@ -1937,6 +1957,8 @@ bool TrafficNetwork::removePeerUnitRegistration(uint32_t peerId, uint32_t srcId) { std::vector aggregate; std::unordered_map aggregateAffiliations; + + // scope is intentional { std::lock_guard updateLock(m_affiliationUpdateMutex); std::shared_ptr registrations = getPeerAffiliations(peerId); @@ -1959,20 +1981,22 @@ bool TrafficNetwork::removePeerUnitRegistration(uint32_t peerId, uint32_t srcId) bool TrafficNetwork::replacePeerUnitRegistrations(uint32_t peerId, const std::vector& registrations, uint32_t ssrc) { std::vector aggregate; + + // scope is intentional { std::lock_guard updateLock(m_affiliationUpdateMutex); std::shared_ptr peerRegistrations = getPeerAffiliations(peerId); if (peerRegistrations == nullptr) return false; + // build a map of source ID to SSRC for the new registrations std::unordered_map registrationOrigins; registrationOrigins.reserve(registrations.size()); for (const uint32_t srcId : registrations) registrationOrigins[srcId] = ssrc; peerRegistrations->replaceUnitRegistrations(registrationOrigins); - const uint64_t now = std::chrono::duration_cast( - std::chrono::system_clock::now().time_since_epoch()).count(); + const uint64_t now = std::chrono::duration_cast(std::chrono::system_clock::now().time_since_epoch()).count(); m_unitRouteRegistry.replacePeer(peerId, registrations, ssrc, now); aggregate = buildAggregatedUnitRegistrations(); } @@ -1995,6 +2019,7 @@ std::vector TrafficNetwork::buildAggregatedUnitRegistrations() if (peer.second == nullptr) continue; + // iterate over the peer's unit registrations and merge into the aggregate map const std::vector registrations = peer.second->unitRegTable(); for (const uint32_t srcId : registrations) { const uint32_t ssrc = peer.second->getSSRCByUnitReg(srcId); diff --git a/src/fne/network/packet/Announce.cpp b/src/fne/network/packet/Announce.cpp index 7b96b5cf..b4d1dab3 100644 --- a/src/fne/network/packet/Announce.cpp +++ b/src/fne/network/packet/Announce.cpp @@ -171,12 +171,19 @@ void MetadataNetwork::PacketHandler::announce(TrafficNetwork* network, MetadataN break; } + // build a map of source ID to destination ID for the new affiliations std::unordered_map affiliations; affiliations.reserve(len); uint32_t offs = 4U; for (uint32_t i = 0U; i < len; i++) { const uint32_t srcId = GET_UINT24(req->buffer, offs); const uint32_t dstId = GET_UINT24(req->buffer, offs + 4U); + + if (srcId == P25DEF::WUID_FNE) { + LogWarning(LOG_MASTER, "PEER %u (%s) ignoring affiliation for FNE source ID", peerId, connection->identWithQualifier().c_str()); + continue; + } + affiliations[srcId] = dstId; offs += 8U; } @@ -226,6 +233,12 @@ void MetadataNetwork::PacketHandler::announce(TrafficNetwork* network, MetadataN uint32_t offs = 4U; for (uint32_t i = 0U; i < len; i++) { const uint32_t srcId = GET_UINT24(req->buffer, offs); + + if (srcId == P25DEF::WUID_FNE) { + LogWarning(LOG_MASTER, "PEER %u (%s) ignoring unit registration for FNE source ID", peerId, connection->identWithQualifier().c_str()); + continue; + } + registrations.push_back(srcId); offs += 3U; }