mirror of
https://github.com/espressif/openthread.git
synced 2026-06-06 05:24:51 +00:00
[netdiag] define AnswerTlvValue to allow reuse (#12792)
This commit defines `AnswerTlvValue` to represent the value of an Answer TLV, allowing it to be reused across different modules, specifically `NetworkDiagnostic` and `HistoryTracker`. The `AnswerTlv` implementation is also updated to use the template-based `SimpleTlvInfo` pattern. This enables the use of generic `Tlv::Append<AnswerTlv>()` and `Tlv::Find<AnswerTlv>()` methods, which improves type safety and reduces manual TLV handling.
This commit is contained in:
committed by
GitHub
parent
9bb7e37ff9
commit
771c430df0
@@ -511,7 +511,7 @@ void Server::SendAnswer(const Ip6::Address &aDestination, const Message &aReques
|
||||
{
|
||||
Error error = kErrorNone;
|
||||
Coap::Message *answer = nullptr;
|
||||
AnswerTlv answerTlv;
|
||||
AnswerTlvValue answerTlvValue;
|
||||
uint16_t queryId;
|
||||
|
||||
answer = Get<Tmf::Agent>().AllocateAndInitConfirmablePostMessage(kUriDiagnosticGetAnswer);
|
||||
@@ -526,8 +526,8 @@ void Server::SendAnswer(const Ip6::Address &aDestination, const Message &aReques
|
||||
|
||||
SuccessOrExit(error = AppendRequestedTlvs(aRequest, *answer));
|
||||
|
||||
answerTlv.Init(0, AnswerTlv::kIsLast);
|
||||
SuccessOrExit(answer->Append(answerTlv));
|
||||
answerTlvValue.Init(0, AnswerTlvValue::kIsLast);
|
||||
SuccessOrExit(error = Tlv::Append<AnswerTlv>(*answer, answerTlvValue));
|
||||
|
||||
error = Get<Tmf::Agent>().SendMessageAllowMulticastLoop(*answer, aDestination);
|
||||
|
||||
@@ -572,13 +572,13 @@ bool Server::IsLastAnswer(const Coap::Message &aAnswer) const
|
||||
// Indicates whether `aAnswer` is the last one associated with
|
||||
// the same query.
|
||||
|
||||
bool isLast = true;
|
||||
AnswerTlv answerTlv;
|
||||
bool isLast = true;
|
||||
AnswerTlvValue answerTlvValue;
|
||||
|
||||
// If there is no Answer TLV, we assume it is the last answer.
|
||||
|
||||
SuccessOrExit(Tlv::FindTlv(aAnswer, answerTlv));
|
||||
isLast = answerTlv.IsLast();
|
||||
SuccessOrExit(Tlv::Find<AnswerTlv>(aAnswer, answerTlvValue));
|
||||
isLast = answerTlvValue.IsLast();
|
||||
|
||||
exit:
|
||||
return isLast;
|
||||
@@ -608,7 +608,7 @@ void Server::PrepareAndSendAnswers(const Ip6::Address &aDestination, const Messa
|
||||
AnswerInfo info;
|
||||
uint8_t tlvType;
|
||||
TlvTypeListIterator iterator;
|
||||
AnswerTlv answerTlv;
|
||||
AnswerTlvValue answerTlvValue;
|
||||
|
||||
if (Tlv::Find<QueryIdTlv>(aRequest, info.mQueryId) == kErrorNone)
|
||||
{
|
||||
@@ -642,8 +642,8 @@ void Server::PrepareAndSendAnswers(const Ip6::Address &aDestination, const Messa
|
||||
SuccessOrExit(error = CheckAnswerLength(answer, info));
|
||||
}
|
||||
|
||||
answerTlv.Init(info.mAnswerIndex, AnswerTlv::kIsLast);
|
||||
SuccessOrExit(error = answer->Append(answerTlv));
|
||||
answerTlvValue.Init(info.mAnswerIndex, AnswerTlvValue::kIsLast);
|
||||
SuccessOrExit(error = Tlv::Append<AnswerTlv>(*answer, answerTlvValue));
|
||||
|
||||
SendNextAnswer(*info.mFirstAnswer, aDestination);
|
||||
|
||||
@@ -662,13 +662,13 @@ Error Server::CheckAnswerLength(Coap::Message *&aAnswer, AnswerInfo &aInfo)
|
||||
// message. In this case, it will also allocate a new answer
|
||||
// message.
|
||||
|
||||
Error error = kErrorNone;
|
||||
AnswerTlv answerTlv;
|
||||
Error error = kErrorNone;
|
||||
AnswerTlvValue answerTlvValue;
|
||||
|
||||
VerifyOrExit(aAnswer->GetLength() >= kAnswerMessageLengthThreshold);
|
||||
|
||||
answerTlv.Init(aInfo.mAnswerIndex++, AnswerTlv::kMoreToFollow);
|
||||
SuccessOrExit(error = aAnswer->Append(answerTlv));
|
||||
answerTlvValue.Init(aInfo.mAnswerIndex++, AnswerTlvValue::kMoreToFollow);
|
||||
SuccessOrExit(error = Tlv::Append<AnswerTlv>(*aAnswer, answerTlvValue));
|
||||
|
||||
error = AllocateAnswer(aAnswer, aInfo);
|
||||
|
||||
|
||||
@@ -197,13 +197,10 @@ void RouterNeighborTlv::InitFrom(const Router &aRouter)
|
||||
#endif // OPENTHREAD_FTD
|
||||
|
||||
//---------------------------------------------------------------------------------------------------------------------
|
||||
// AnswerTlv
|
||||
// AnswerTlvValue
|
||||
|
||||
void AnswerTlv::Init(uint16_t aIndex, IsLastFlag aIsLastFlag)
|
||||
void AnswerTlvValue::Init(uint16_t aIndex, IsLastFlag aIsLastFlag)
|
||||
{
|
||||
SetType(kAnswer);
|
||||
SetLength(sizeof(*this) - sizeof(Tlv));
|
||||
|
||||
SetFlagsIndex((aIndex & kIndexMask) | (aIsLastFlag == kIsLast ? kIsLastFlag : 0));
|
||||
}
|
||||
|
||||
|
||||
@@ -802,10 +802,10 @@ private:
|
||||
} OT_TOOL_PACKED_END;
|
||||
|
||||
/**
|
||||
* Implements Answer TLV generation and parsing.
|
||||
* Represents an Answer TLV value.
|
||||
*/
|
||||
OT_TOOL_PACKED_BEGIN
|
||||
class AnswerTlv : public Tlv, public TlvInfo<Tlv::kAnswer>
|
||||
class AnswerTlvValue
|
||||
{
|
||||
public:
|
||||
enum IsLastFlag : uint8_t
|
||||
@@ -815,7 +815,7 @@ public:
|
||||
};
|
||||
|
||||
/**
|
||||
* Initializes the TLV.
|
||||
* Initializes the TLV value.
|
||||
*
|
||||
* @param[in] aIndex The index value.
|
||||
* @param[in] aIsLastFlag Indicates the `IsLastFlag` value.
|
||||
@@ -847,6 +847,11 @@ private:
|
||||
uint16_t mFlagsIndex;
|
||||
} OT_TOOL_PACKED_END;
|
||||
|
||||
/**
|
||||
* Defines Answer TLV constants and types.
|
||||
*/
|
||||
typedef SimpleTlvInfo<Tlv::kAnswer, AnswerTlvValue> AnswerTlv;
|
||||
|
||||
/**
|
||||
* Represents the MLE Counters.
|
||||
*/
|
||||
|
||||
@@ -133,9 +133,9 @@ exit:
|
||||
|
||||
Error Client::ProcessAnswer(const Coap::Msg &aMsg)
|
||||
{
|
||||
Error error = kErrorFailed;
|
||||
AnswerTlv answerTlv;
|
||||
uint16_t queryId;
|
||||
Error error = kErrorFailed;
|
||||
AnswerTlvValue answerTlvValue;
|
||||
uint16_t queryId;
|
||||
|
||||
VerifyOrExit(mActive);
|
||||
VerifyOrExit(Get<Mle::Mle>().IsRoutingLocator(aMsg.mMessageInfo.GetPeerAddr()));
|
||||
@@ -144,9 +144,9 @@ Error Client::ProcessAnswer(const Coap::Msg &aMsg)
|
||||
SuccessOrExit(Tlv::Find<QueryIdTlv>(aMsg.mMessage, queryId));
|
||||
VerifyOrExit(queryId == mQueryId);
|
||||
|
||||
SuccessOrExit(Tlv::FindTlv(aMsg.mMessage, answerTlv));
|
||||
SuccessOrExit(Tlv::Find<AnswerTlv>(aMsg.mMessage, answerTlvValue));
|
||||
|
||||
if (answerTlv.GetIndex() != mAnswerIndex)
|
||||
if (answerTlvValue.GetIndex() != mAnswerIndex)
|
||||
{
|
||||
Finalize(kErrorResponseTimeout);
|
||||
ExitNow();
|
||||
|
||||
@@ -93,13 +93,13 @@ bool Server::IsLastAnswer(const Coap::Message &aAnswer) const
|
||||
// Indicates whether `aAnswer` is the last one associated with
|
||||
// the same query.
|
||||
|
||||
bool isLast = true;
|
||||
AnswerTlv answerTlv;
|
||||
bool isLast = true;
|
||||
AnswerTlvValue answerTlvValue;
|
||||
|
||||
// If there is no Answer TLV, we assume it is the last answer.
|
||||
|
||||
SuccessOrExit(Tlv::FindTlv(aAnswer, answerTlv));
|
||||
isLast = answerTlv.IsLast();
|
||||
SuccessOrExit(Tlv::Find<AnswerTlv>(aAnswer, answerTlvValue));
|
||||
isLast = answerTlvValue.IsLast();
|
||||
|
||||
exit:
|
||||
return isLast;
|
||||
@@ -130,7 +130,7 @@ void Server::PrepareAndSendAnswers(const Ip6::Address &aDestination, const Messa
|
||||
OffsetRange offsetRange;
|
||||
Tlv::Info tlvInfo;
|
||||
RequestTlv requestTlv;
|
||||
AnswerTlv answerTlv;
|
||||
AnswerTlvValue answerTlvValue;
|
||||
|
||||
if (Tlv::Find<QueryIdTlv>(aRequest, info.mQueryId) == kErrorNone)
|
||||
{
|
||||
@@ -171,8 +171,8 @@ void Server::PrepareAndSendAnswers(const Ip6::Address &aDestination, const Messa
|
||||
}
|
||||
}
|
||||
|
||||
answerTlv.Init(info.mAnswerIndex, /* aIsLast */ true);
|
||||
SuccessOrExit(error = answer->Append(answerTlv));
|
||||
answerTlvValue.Init(info.mAnswerIndex, AnswerTlvValue::kIsLast);
|
||||
SuccessOrExit(error = Tlv::Append<AnswerTlv>(*answer, answerTlvValue));
|
||||
|
||||
SendNextAnswer(*info.mFirstAnswer, aDestination);
|
||||
|
||||
@@ -190,13 +190,13 @@ Error Server::CheckAnswerLength(Coap::Message *&aAnswer, AnswerInfo &aInfo)
|
||||
// appending an Answer TLV with the current index to the message.
|
||||
// In this case, it will also allocate a new answer message.
|
||||
|
||||
Error error = kErrorNone;
|
||||
AnswerTlv answerTlv;
|
||||
Error error = kErrorNone;
|
||||
AnswerTlvValue answerTlvValue;
|
||||
|
||||
VerifyOrExit(aAnswer->GetLength() >= kAnswerMessageLengthThreshold);
|
||||
|
||||
answerTlv.Init(aInfo.mAnswerIndex++, /* aIsLast */ false);
|
||||
SuccessOrExit(error = aAnswer->Append(answerTlv));
|
||||
answerTlvValue.Init(aInfo.mAnswerIndex++, AnswerTlvValue::kMoreToFollow);
|
||||
SuccessOrExit(error = Tlv::Append<AnswerTlv>(*aAnswer, answerTlvValue));
|
||||
|
||||
error = AllocateAnswer(aAnswer, aInfo);
|
||||
|
||||
|
||||
@@ -38,14 +38,6 @@
|
||||
namespace ot {
|
||||
namespace HistoryTracker {
|
||||
|
||||
void AnswerTlv::Init(uint16_t aIndex, bool aIsLast)
|
||||
{
|
||||
SetType(kAnswer);
|
||||
SetLength(sizeof(*this) - sizeof(Tlv));
|
||||
|
||||
SetFlagsIndex((aIndex & kIndexMask) | (aIsLast ? kIsLastFlag : 0));
|
||||
}
|
||||
|
||||
void RequestTlv::Init(uint8_t aTlvType, uint16_t aNumEntries, uint32_t aMaxEntryAge)
|
||||
{
|
||||
SetType(kRequest);
|
||||
|
||||
@@ -42,6 +42,7 @@
|
||||
|
||||
#include "common/encoding.hpp"
|
||||
#include "common/tlvs.hpp"
|
||||
#include "thread/network_diagnostic_tlvs.hpp"
|
||||
#include "utils/history_tracker.hpp"
|
||||
|
||||
namespace ot {
|
||||
@@ -72,44 +73,14 @@ public:
|
||||
typedef UintTlvInfo<Tlv::kQueryId, uint16_t> QueryIdTlv;
|
||||
|
||||
/**
|
||||
* Implements Answer TLV generation and parsing.
|
||||
* Represents an Answer TLV value.
|
||||
*/
|
||||
OT_TOOL_PACKED_BEGIN
|
||||
class AnswerTlv : public Tlv, public TlvInfo<Tlv::kAnswer>
|
||||
{
|
||||
public:
|
||||
/**
|
||||
* Initializes the TLV.
|
||||
*
|
||||
* @param[in] aIndex The index value.
|
||||
* @param[in] aIsLast The "IsLast" flag value.
|
||||
*/
|
||||
void Init(uint16_t aIndex, bool aIsLast);
|
||||
typedef NetworkDiagnostic::AnswerTlvValue AnswerTlvValue;
|
||||
|
||||
/**
|
||||
* Indicates whether or not the "IsLast" flag is set
|
||||
*
|
||||
* @retval TRUE "IsLast" flag is set (this is the last answer for this query).
|
||||
* @retval FALSE "IsLast" flag is not set (more answer messages are expected for this query).
|
||||
*/
|
||||
bool IsLast(void) const { return GetFlagsIndex() & kIsLastFlag; }
|
||||
|
||||
/**
|
||||
* Gets the index.
|
||||
*
|
||||
* @returns The index.
|
||||
*/
|
||||
uint16_t GetIndex(void) const { return GetFlagsIndex() & kIndexMask; }
|
||||
|
||||
private:
|
||||
static constexpr uint16_t kIsLastFlag = 1 << 15;
|
||||
static constexpr uint16_t kIndexMask = 0x7fff;
|
||||
|
||||
uint16_t GetFlagsIndex(void) const { return BigEndian::HostSwap16(mFlagsIndex); }
|
||||
void SetFlagsIndex(uint16_t aFlagsIndex) { mFlagsIndex = BigEndian::HostSwap16(aFlagsIndex); }
|
||||
|
||||
uint16_t mFlagsIndex;
|
||||
} OT_TOOL_PACKED_END;
|
||||
/**
|
||||
* Defines Answer TLV constants and types.
|
||||
*/
|
||||
typedef SimpleTlvInfo<Tlv::kAnswer, AnswerTlvValue> AnswerTlv;
|
||||
|
||||
/**
|
||||
* Implements Request TLV generation and parsing.
|
||||
|
||||
@@ -258,9 +258,9 @@ Error MeshDiag::ProcessMessage(Coap::Message &aMessage, const Ip6::MessageInfo &
|
||||
// check whether it is from the intended sender and matches
|
||||
// the expected query ID and answer index.
|
||||
|
||||
Error error = kErrorFailed;
|
||||
AnswerTlv answerTlv;
|
||||
uint16_t queryId;
|
||||
Error error = kErrorFailed;
|
||||
AnswerTlvValue answerTlvValue;
|
||||
uint16_t queryId;
|
||||
|
||||
VerifyOrExit(Get<Mle::Mle>().IsRoutingLocator(aMessageInfo.GetPeerAddr()));
|
||||
VerifyOrExit(aMessageInfo.GetPeerAddr().GetIid().GetLocator() == aSenderRloc16);
|
||||
@@ -268,9 +268,9 @@ Error MeshDiag::ProcessMessage(Coap::Message &aMessage, const Ip6::MessageInfo &
|
||||
SuccessOrExit(Tlv::Find<QueryIdTlv>(aMessage, queryId));
|
||||
VerifyOrExit(queryId == mExpectedQueryId);
|
||||
|
||||
SuccessOrExit(Tlv::FindTlv(aMessage, answerTlv));
|
||||
SuccessOrExit(Tlv::Find<AnswerTlv>(aMessage, answerTlvValue));
|
||||
|
||||
if (answerTlv.GetIndex() != mExpectedAnswerIndex)
|
||||
if (answerTlvValue.GetIndex() != mExpectedAnswerIndex)
|
||||
{
|
||||
Finalize(kErrorResponseTimeout);
|
||||
ExitNow();
|
||||
|
||||
Reference in New Issue
Block a user