From bd7bc70c4efd074b7c5f1002dac6b79bfed70189 Mon Sep 17 00:00:00 2001 From: Boris Zbarsky Date: Mon, 15 Aug 2022 19:03:03 -0400 Subject: [PATCH] When a client detects subscription drop, mark sessions defunct. (#21841) This marks defunct the session the subscripton is on, as well as any sessions that are "more stale" than it, in the sense of not having seen anything from the peer for at least as long. This should increase the chance that our next attempt to communicate with the peer will not use a stale session. --- src/app/ReadClient.cpp | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) diff --git a/src/app/ReadClient.cpp b/src/app/ReadClient.cpp index 7ba7e9b9b1fb35..340b0d441554dc 100644 --- a/src/app/ReadClient.cpp +++ b/src/app/ReadClient.cpp @@ -828,6 +828,29 @@ void ReadClient::OnLivenessTimeoutCallback(System::Layer * apSystemLayer, void * "Subscription Liveness timeout with SubscriptionID = 0x%08" PRIx32 ", Peer = %02x:" ChipLogFormatX64, _this->mSubscriptionId, _this->GetFabricIndex(), ChipLogValueX64(_this->GetPeerNodeId())); + // We didn't get a message from the server on time; it's possible that it no + // longer has a useful CASE session to us. Mark defunct all sessions that + // have not seen peer activity in at least as long as our session. + const auto & holder = _this->mReadPrepareParams.mSessionHolder; + if (holder) + { + System::Clock::Timestamp lastPeerActivity = holder->AsSecureSession()->GetLastPeerActivityTime(); + _this->mpImEngine->GetExchangeManager()->GetSessionManager()->ForEachMatchingSession( + _this->mPeer, [&lastPeerActivity](auto * session) { + if (!session->IsCASESession()) + { + return; + } + + if (session->GetLastPeerActivityTime() > lastPeerActivity) + { + return; + } + + session->MarkAsDefunct(); + }); + } + // TODO: add a more specific error here for liveness timeout failure to distinguish between other classes of timeouts (i.e // response timeouts). _this->Close(CHIP_ERROR_TIMEOUT);