diff --git a/src/core/radio/trel_peer_discoverer.cpp b/src/core/radio/trel_peer_discoverer.cpp index 30e9c39f2..e9c8e73bf 100644 --- a/src/core/radio/trel_peer_discoverer.cpp +++ b/src/core/radio/trel_peer_discoverer.cpp @@ -41,9 +41,6 @@ namespace Trel { RegisterLogModule("TrelDiscoverer"); -const char PeerDiscoverer::kTxtRecordExtAddressKey[] = "xa"; -const char PeerDiscoverer::kTxtRecordExtPanIdKey[] = "xp"; - PeerDiscoverer::PeerDiscoverer(Instance &aInstance) : InstanceLocator(aInstance) , mIsRunning(false) @@ -89,30 +86,17 @@ void PeerDiscoverer::PostRegisterServiceTask(void) void PeerDiscoverer::RegisterService(void) { - // TXT data consists of two entries: the length fields, the - // "key" string, "=" char, and binary representation of the MAC - // or Extended PAN ID values. - static constexpr uint8_t kTxtDataSize = - /* ExtAddr */ sizeof(uint8_t) + sizeof(kTxtRecordExtAddressKey) - 1 + sizeof(char) + sizeof(Mac::ExtAddress) + - /* ExtPanId */ sizeof(uint8_t) + sizeof(kTxtRecordExtPanIdKey) - 1 + sizeof(char) + - sizeof(MeshCoP::ExtendedPanId); - - uint8_t txtData[kTxtDataSize]; - Dns::TxtDataEncoder encoder(txtData, sizeof(txtData)); - uint16_t port; + TxtDataEncoder txtData(GetInstance()); + uint16_t port; VerifyOrExit(mIsRunning); port = Get().GetUdpPort(); - SuccessOrAssert(encoder.AppendEntry(kTxtRecordExtAddressKey, Get().GetExtAddress())); - SuccessOrAssert(encoder.AppendEntry(kTxtRecordExtPanIdKey, Get().GetExtPanId())); + txtData.Encode(); - LogInfo("Registering DNS-SD service: port:%u, txt:\"%s=%s, %s=%s\"", port, kTxtRecordExtAddressKey, - Get().GetExtAddress().ToString().AsCString(), kTxtRecordExtPanIdKey, - Get().GetExtPanId().ToString().AsCString()); - - otPlatTrelRegisterService(&GetInstance(), port, txtData, static_cast(encoder.GetLength())); + LogInfo("Registering DNS-SD service: port:%u", port); + otPlatTrelRegisterService(&GetInstance(), port, txtData.GetBytes(), static_cast(txtData.GetLength())); exit: return; @@ -131,20 +115,21 @@ exit: void PeerDiscoverer::HandleDiscoveredPeerInfo(const PeerInfo &aInfo) { - Peer *peer; - Mac::ExtAddress extAddress; - MeshCoP::ExtendedPanId extPanId; - bool isNew = false; + Peer *peer; + TxtData txtData; + TxtData::Info txtInfo; + bool isNew = false; VerifyOrExit(mIsRunning); - SuccessOrExit(aInfo.ParseTxtData(extAddress, extPanId)); + txtData.Init(aInfo.mTxtData, aInfo.mTxtLength); + SuccessOrExit(txtData.Decode(txtInfo)); - VerifyOrExit(extAddress != Get().GetExtAddress()); + VerifyOrExit(txtInfo.mExtAddress != Get().GetExtAddress()); if (aInfo.IsRemoved()) { - Get().RemoveAndFreeAllMatching(extAddress); + Get().RemoveAndFreeAllMatching(txtInfo.mExtAddress); ExitNow(); } @@ -156,7 +141,7 @@ void PeerDiscoverer::HandleDiscoveredPeerInfo(const PeerInfo &aInfo) peer = Get().FindMatching(aInfo.GetSockAddr()); - if ((peer != nullptr) && !peer->Matches(extAddress)) + if ((peer != nullptr) && !peer->Matches(txtInfo.mExtAddress)) { Get().RemoveMatching(aInfo.GetSockAddr()); peer = nullptr; @@ -164,7 +149,7 @@ void PeerDiscoverer::HandleDiscoveredPeerInfo(const PeerInfo &aInfo) if (peer == nullptr) { - peer = Get().FindMatching(extAddress); + peer = Get().FindMatching(txtInfo.mExtAddress); } if (peer == nullptr) @@ -172,16 +157,16 @@ void PeerDiscoverer::HandleDiscoveredPeerInfo(const PeerInfo &aInfo) peer = Get().AllocateAndAddNewPeer(); VerifyOrExit(peer != nullptr); - peer->SetExtAddress(extAddress); + peer->SetExtAddress(txtInfo.mExtAddress); isNew = true; } if (!isNew) { - VerifyOrExit((peer->GetExtPanId() != extPanId) || (peer->GetSockAddr() != aInfo.GetSockAddr())); + VerifyOrExit((peer->GetExtPanId() != txtInfo.mExtPanId) || (peer->GetSockAddr() != aInfo.GetSockAddr())); } - peer->SetExtPanId(extPanId); + peer->SetExtPanId(txtInfo.mExtPanId); peer->SetSockAddr(aInfo.GetSockAddr()); peer->Log(isNew ? Peer::kAdded : Peer::kUpdated); @@ -190,7 +175,19 @@ exit: return; } -Error PeerDiscoverer::PeerInfo::ParseTxtData(Mac::ExtAddress &aExtAddress, MeshCoP::ExtendedPanId &aExtPanId) const +//---------------------------------------------------------------------------------------------------------------------- +// PeerDiscoverer::TxtData + +const char PeerDiscoverer::TxtData::kExtAddressKey[] = "xa"; +const char PeerDiscoverer::TxtData::kExtPanIdKey[] = "xp"; + +void PeerDiscoverer::TxtData::Init(const uint8_t *aData, uint16_t aLength) +{ + mData = aData; + mLength = aLength; +} + +Error PeerDiscoverer::TxtData::Decode(Info &aInfo) { Error error; Dns::TxtEntry entry; @@ -198,9 +195,9 @@ Error PeerDiscoverer::PeerInfo::ParseTxtData(Mac::ExtAddress &aExtAddress, MeshC bool parsedExtAddress = false; bool parsedExtPanId = false; - aExtPanId.Clear(); + aInfo.Clear(); - iterator.Init(mTxtData, mTxtLength); + iterator.Init(mData, mLength); while ((error = iterator.GetNextEntry(entry)) == kErrorNone) { @@ -213,18 +210,18 @@ Error PeerDiscoverer::PeerInfo::ParseTxtData(Mac::ExtAddress &aExtAddress, MeshC continue; } - if (StringMatch(entry.mKey, kTxtRecordExtAddressKey)) + if (StringMatch(entry.mKey, kExtAddressKey)) { VerifyOrExit(!parsedExtAddress, error = kErrorParse); VerifyOrExit(entry.mValueLength >= sizeof(Mac::ExtAddress), error = kErrorParse); - aExtAddress.Set(entry.mValue); + aInfo.mExtAddress.Set(entry.mValue); parsedExtAddress = true; } - else if (StringMatch(entry.mKey, kTxtRecordExtPanIdKey)) + else if (StringMatch(entry.mKey, kExtPanIdKey)) { VerifyOrExit(!parsedExtPanId, error = kErrorParse); VerifyOrExit(entry.mValueLength >= sizeof(MeshCoP::ExtendedPanId), error = kErrorParse); - memcpy(aExtPanId.m8, entry.mValue, sizeof(MeshCoP::ExtendedPanId)); + memcpy(aInfo.mExtPanId.m8, entry.mValue, sizeof(MeshCoP::ExtendedPanId)); parsedExtPanId = true; } @@ -240,6 +237,25 @@ exit: return error; } +//---------------------------------------------------------------------------------------------------------------------- +// PeerDiscoverer::TxtDataEncoder + +PeerDiscoverer::TxtDataEncoder::TxtDataEncoder(Instance &aInstance) + : InstanceLocator(aInstance) +{ +} + +void PeerDiscoverer::TxtDataEncoder::Encode(void) +{ + Dns::TxtDataEncoder encoder(mBuffer, sizeof(mBuffer)); + + SuccessOrAssert(encoder.AppendEntry(kExtAddressKey, Get().GetExtAddress())); + SuccessOrAssert(encoder.AppendEntry(kExtPanIdKey, Get().GetExtPanId())); + + mData = mBuffer; + mLength = encoder.GetLength(); +} + } // namespace Trel } // namespace ot diff --git a/src/core/radio/trel_peer_discoverer.hpp b/src/core/radio/trel_peer_discoverer.hpp index b25fd2f16..79641133a 100644 --- a/src/core/radio/trel_peer_discoverer.hpp +++ b/src/core/radio/trel_peer_discoverer.hpp @@ -40,6 +40,7 @@ #include +#include "common/clearable.hpp" #include "common/locator.hpp" #include "common/tasklet.hpp" #include "radio/trel_peer.hpp" @@ -90,14 +91,50 @@ public: void NotifyPeerSocketAddressDifference(const Ip6::SockAddr &aPeerSockAddr, const Ip6::SockAddr &aRxSockAddr); private: - static const char kTxtRecordExtAddressKey[]; - static const char kTxtRecordExtPanIdKey[]; + class TxtData + { + public: + struct Info : public Clearable + { + Mac::ExtAddress mExtAddress; + MeshCoP::ExtendedPanId mExtPanId; + }; + + void Init(const uint8_t *aData, uint16_t aLength); + const uint8_t *GetBytes(void) const { return mData; } + uint16_t GetLength(void) const { return mLength; } + Error Decode(Info &aInfo); + + protected: + static const char kExtAddressKey[]; // "xa" + static const char kExtPanIdKey[]; // "xp" + + const uint8_t *mData; + uint16_t mLength; + }; + + class TxtDataEncoder : public InstanceLocator, public TxtData + { + public: + explicit TxtDataEncoder(Instance &aInstance); + void Encode(void); + + private: + // TXT data consists of two entries: `xa` for extended address + // and `xp` for extended PAN ID. Each entry starts with one + // byte for length, then the two-character key, followed by + // an `=` character, and then the value. This adds up to + // (4 + 8 [value]) = 12 bytes total per entry. The value of + // 32 accommodates these two entries and more. + static constexpr uint8_t kMaxSize = 32; + + uint8_t mBuffer[kMaxSize]; + }; struct PeerInfo : public otPlatTrelPeerInfo { bool IsRemoved(void) const { return mRemoved; } const Ip6::SockAddr &GetSockAddr(void) const { return AsCoreType(&mSockAddr); } - Error ParseTxtData(Mac::ExtAddress &aExtAddress, MeshCoP::ExtendedPanId &aExtPanId) const; }; explicit PeerDiscoverer(Instance &aInstance);