diff --git a/src/core/common/message.hpp b/src/core/common/message.hpp index 523e4cddf..10c86036f 100644 --- a/src/core/common/message.hpp +++ b/src/core/common/message.hpp @@ -351,6 +351,16 @@ public: kOriginHostUntrusted = OT_MESSAGE_ORIGIN_HOST_UNTRUSTED, // Message from an untrusted source on host. }; + /** + * Defines a predicate function reference which is used to check or filter a message. + * + * @param[in] aMessage The message to check. + * + * @retval TRUE If the message matches the criteria. + * @retval FALSE If the message does not match the criteria. + */ + typedef bool (&Checker)(const Message &aMessage); + /** * Represents settings used for creating a new message. */ @@ -1595,6 +1605,59 @@ public: #endif // #if OPENTHREAD_CONFIG_MULTI_RADIO + //- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + // Helper common predicate `Checker` functions + + /** + * Predicate checker function that matches and accepts any message. + * + * @param[in] aMessage The message to check. + * + * @retval TRUE Always matches and accepts the message. + */ + static bool AcceptAny(const Message &aMessage) + { + OT_UNUSED_VARIABLE(aMessage); + return true; + } + + /** + * Predicate checker function that checks whether a message matches a specific type. + * + * @tparam kType The message type to match. + * + * @param[in] aMessage The message to check. + * + * @retval TRUE The message type matches @p kType. + * @retval FALSE The message type does not match @p kType. + */ + template static bool AcceptType(const Message &aMessage) { return aMessage.GetType() == kType; } + + /** + * Predicate checker function that checks whether a message is of MLE subtype. + * + * @param[in] aMessage The message to check. + * + * @retval TRUE The message is of MLE subtype. + * @retval FALSE The message is not of MLE subtype. + */ + static bool AcceptAnyMle(const Message &aMessage) { return aMessage.IsSubTypeMle(); } + + /** + * Predicate checker function that checks whether a message is a specific MLE command. + * + * @tparam kMleCommand The MLE command to match. + * + * @param[in] aMessage The message to check. + * + * @retval TRUE The message is an MLE command of @p kMleCommand type. + * @retval FALSE The message is not an MLE command of @p kMleCommand type. + */ + template static bool AcceptMle(const Message &aMessage) + { + return aMessage.IsMleCommand(kMleCommand); + } + protected: class OT_GSL_POINTER ConstIterator : public ItemPtrIterator { diff --git a/src/core/thread/indirect_sender.cpp b/src/core/thread/indirect_sender.cpp index e886772cc..cecb6a935 100644 --- a/src/core/thread/indirect_sender.cpp +++ b/src/core/thread/indirect_sender.cpp @@ -104,7 +104,9 @@ void IndirectSender::AddMessageForSleepyChild(Message &aMessage, Child &aChild) if ((aMessage.GetType() != Message::kTypeSupervision) && (aChild.GetIndirectMessageCount() > 1)) { - Message *supervisionMessage = FindQueuedMessageForSleepyChild(aChild, AcceptSupervisionMessage); + Message *supervisionMessage; + + supervisionMessage = FindQueuedMessageForSleepyChild(aChild, Message::AcceptType); if (supervisionMessage != nullptr) { @@ -158,7 +160,7 @@ exit: return; } -const Message *IndirectSender::FindQueuedMessageForSleepyChild(const Child &aChild, MessageChecker aChecker) const +const Message *IndirectSender::FindQueuedMessageForSleepyChild(const Child &aChild, Message::Checker aChecker) const { const Message *match = nullptr; uint16_t childIndex = Get().GetChildIndex(aChild); @@ -260,7 +262,7 @@ void IndirectSender::RequestMessageUpdate(Child &aChild) VerifyOrExit(!aChild.IsWaitingForMessageUpdate()); - newMessage = FindQueuedMessageForSleepyChild(aChild, AcceptAnyMessage); + newMessage = FindQueuedMessageForSleepyChild(aChild, Message::AcceptAny); VerifyOrExit(curMessage != newMessage); @@ -303,7 +305,7 @@ exit: void IndirectSender::UpdateIndirectMessage(Child &aChild) { - Message *message = FindQueuedMessageForSleepyChild(aChild, AcceptAnyMessage); + Message *message = FindQueuedMessageForSleepyChild(aChild, Message::AcceptAny); aChild.SetWaitingForMessageUpdate(false); aChild.SetIndirectMessage(message); @@ -533,18 +535,6 @@ void IndirectSender::ClearMessagesForRemovedChildren(void) } } -bool IndirectSender::AcceptAnyMessage(const Message &aMessage) -{ - OT_UNUSED_VARIABLE(aMessage); - - return true; -} - -bool IndirectSender::AcceptSupervisionMessage(const Message &aMessage) -{ - return aMessage.GetType() == Message::kTypeSupervision; -} - #endif // OPENTHREAD_FTD #if OPENTHREAD_CONFIG_MAC_CSL_TRANSMITTER_ENABLE diff --git a/src/core/thread/indirect_sender.hpp b/src/core/thread/indirect_sender.hpp index 4928e6202..5fd054836 100644 --- a/src/core/thread/indirect_sender.hpp +++ b/src/core/thread/indirect_sender.hpp @@ -137,16 +137,6 @@ public: "mQueuedMessageCount cannot fit max required!"); }; - /** - * Represents a predicate function for checking if a given `Message` meets specific criteria. - * - * @param[in] aMessage The message to evaluate. - * - * @retval TRUE If the @p aMessage satisfies the predicate condition. - * @retval FALSE If the @p aMessage does not satisfy the predicate condition. - */ - typedef bool (&MessageChecker)(const Message &aMessage); - /** * Initializes the object. * @@ -195,7 +185,7 @@ public: /** * Finds the first queued message for a given sleepy child that also satisfies the conditions of a given - * `MessageChecker`. + * `Message::Checker`. * * The caller MUST ensure that @p aChild is sleepy. * @@ -204,14 +194,14 @@ public: * * @returns A pointer to the matching queued message, or `nullptr` if none is found. */ - Message *FindQueuedMessageForSleepyChild(const Child &aChild, MessageChecker aChecker) + Message *FindQueuedMessageForSleepyChild(const Child &aChild, Message::Checker aChecker) { return AsNonConst(AsConst(this)->FindQueuedMessageForSleepyChild(aChild, aChecker)); } /** * Finds the first queued message for a given sleepy child that also satisfies the conditions of a given - * `MessageChecker`. + * `Message::Checker`. * * The caller MUST ensure that @p aChild is sleepy. * @@ -220,11 +210,11 @@ public: * * @returns A pointer to the matching queued message, or `nullptr` if none is found. */ - const Message *FindQueuedMessageForSleepyChild(const Child &aChild, MessageChecker aChecker) const; + const Message *FindQueuedMessageForSleepyChild(const Child &aChild, Message::Checker aChecker) const; /** * Indicates whether there is any queued message for a given sleepy child that also satisfies the conditions of a - * given `MessageChecker`. + * given `Message::Checker`. * * The caller MUST ensure that @p aChild is sleepy. * @@ -234,7 +224,7 @@ public: * @retval TRUE There is a queued message satisfying @p aChecker for sleepy child @p aChild. * @retval FALSE There is no queued message satisfying @p aChecker for sleepy child @p aChild. */ - bool HasQueuedMessageForSleepyChild(const Child &aChild, MessageChecker aChecker) const + bool HasQueuedMessageForSleepyChild(const Child &aChild, Message::Checker aChecker) const { return (FindQueuedMessageForSleepyChild(aChild, aChecker) != nullptr); } @@ -279,9 +269,6 @@ private: void UpdateIndirectMessage(Child &aChild); void RequestMessageUpdate(Child &aChild); void ClearMessagesForRemovedChildren(void); - - static bool AcceptAnyMessage(const Message &aMessage); - static bool AcceptSupervisionMessage(const Message &aMessage); #endif // OPENTHREAD_FTD bool mEnabled; diff --git a/src/core/thread/mesh_forwarder.hpp b/src/core/thread/mesh_forwarder.hpp index 95852d55d..c91707ca1 100644 --- a/src/core/thread/mesh_forwarder.hpp +++ b/src/core/thread/mesh_forwarder.hpp @@ -162,17 +162,15 @@ public: void SetRxOnWhenIdle(bool aRxOnWhenIdle); #if OPENTHREAD_FTD - typedef IndirectSender::MessageChecker MessageChecker; ///< General predicate function checking a message. - /** * Removes and frees messages queued for a child, based on a given predicate. * * The `aChild` can be either sleepy or non-sleepy. * - * @param[in] aChild The child whose messages are to be evaluated. - * @param[in] aMessageChecker The predicate function to filter messages. + * @param[in] aChild The child whose messages are to be evaluated. + * @param[in] aChecker The predicate function to filter messages. */ - void RemoveMessagesForChild(Child &aChild, MessageChecker aMessageChecker); + void RemoveMessagesForChild(Child &aChild, Message::Checker aChecker); #endif /** diff --git a/src/core/thread/mesh_forwarder_ftd.cpp b/src/core/thread/mesh_forwarder_ftd.cpp index 8c2c91e06..90e4aad0c 100644 --- a/src/core/thread/mesh_forwarder_ftd.cpp +++ b/src/core/thread/mesh_forwarder_ftd.cpp @@ -259,11 +259,11 @@ exit: return error; } -void MeshForwarder::RemoveMessagesForChild(Child &aChild, MessageChecker &aMessageChecker) +void MeshForwarder::RemoveMessagesForChild(Child &aChild, Message::Checker aChecker) { for (Message &message : mSendQueue) { - if (!aMessageChecker(message)) + if (!aChecker(message)) { continue; } diff --git a/src/core/thread/mle.hpp b/src/core/thread/mle.hpp index 720a32437..19d692ada 100644 --- a/src/core/thread/mle.hpp +++ b/src/core/thread/mle.hpp @@ -2429,8 +2429,6 @@ private: DeclareTmfResponseHandlerIn(Mle, HandleAddressSolicitResponse); - static bool IsMessageMleSubType(const Message &aMessage); - static bool IsMessageChildUpdateRequest(const Message &aMessage); static void HandleAdvertiseTrickleTimer(TrickleTimer &aTimer); #if OT_SHOULD_LOG_AT(OT_LOG_LEVEL_INFO) diff --git a/src/core/thread/mle_ftd.cpp b/src/core/thread/mle_ftd.cpp index 1686b30aa..57210e57f 100644 --- a/src/core/thread/mle_ftd.cpp +++ b/src/core/thread/mle_ftd.cpp @@ -2022,13 +2022,6 @@ exit: return error; } -bool Mle::IsMessageMleSubType(const Message &aMessage) { return aMessage.IsSubTypeMle(); } - -bool Mle::IsMessageChildUpdateRequest(const Message &aMessage) -{ - return aMessage.IsMleCommand(kCommandChildUpdateRequest); -} - void Mle::HandleChildIdRequest(RxInfo &aRxInfo) { Error error = kErrorNone; @@ -2059,7 +2052,7 @@ void Mle::HandleChildIdRequest(RxInfo &aRxInfo) SuccessOrExit(error = aRxInfo.mMessage.ReadAndMatchResponseTlvWith(child->GetChallenge())); - Get().RemoveMessagesForChild(*child, IsMessageMleSubType); + Get().RemoveMessagesForChild(*child, Message::AcceptAnyMle); SuccessOrExit(error = aRxInfo.mMessage.ReadFrameCounterTlvs(linkFrameCounter, mleFrameCounter)); @@ -2939,10 +2932,11 @@ Error Mle::SendChildUpdateRequestToChild(Child &aChild) // to the sleepy child if there is one already // queued. - VerifyOrExit(!Get().HasQueuedMessageForSleepyChild(aChild, IsMessageChildUpdateRequest)); + VerifyOrExit(!Get().HasQueuedMessageForSleepyChild( + aChild, Message::AcceptMle)); } - Get().RemoveMessagesForChild(aChild, IsMessageChildUpdateRequest); + Get().RemoveMessagesForChild(aChild, Message::AcceptMle); VerifyOrExit((message = NewMleMessage(kCommandChildUpdateRequest)) != nullptr, error = kErrorNoBufs); SuccessOrExit(error = message->AppendSourceAddressAndLeaderDataTlvs());