From 7af59a1fef60d50cf8d4a3066f983cd8c3acbe95 Mon Sep 17 00:00:00 2001 From: Jonathan Hui Date: Mon, 30 Mar 2026 18:56:38 -0700 Subject: [PATCH] [nexus] route TREL traffic through simulated infrastructure link (#12801) This commit updates the TREL traffic simulation in the Nexus platform to flow through the simulated infrastructure link. This ensures that TREL packets are captured in the pcap file generated by the infrastructure link, matching the behavior of mDNS traffic. Key changes: - Updated Trel::Send to use InfraIf::SendUdp instead of direct delivery. - Modified InfraIf::Receive to recognize TREL UDP packets and pass them to the TREL platform layer. - Removed the manual mPendingTxList from the Trel struct as packets are now managed by the infrastructure interface's queue. - Added initialization for the TREL platform layer in Core::CreateNode. - Removed Core::ProcessTrel as TREL packets are now processed within Core::ProcessInfraIf. This change improves the realism of the TREL simulation and simplifies packet capture for TREL-related tests. --- tests/nexus/platform/nexus_core.cpp | 34 +++---------------------- tests/nexus/platform/nexus_core.hpp | 3 --- tests/nexus/platform/nexus_infra_if.cpp | 20 +++++++++++++++ tests/nexus/platform/nexus_trel.cpp | 25 +++++++++--------- tests/nexus/platform/nexus_trel.hpp | 18 +++++-------- 5 files changed, 43 insertions(+), 57 deletions(-) diff --git a/tests/nexus/platform/nexus_core.cpp b/tests/nexus/platform/nexus_core.cpp index d046f43c3..115ec8265 100644 --- a/tests/nexus/platform/nexus_core.cpp +++ b/tests/nexus/platform/nexus_core.cpp @@ -330,6 +330,9 @@ Node &Core::CreateNode(void) node->mInfraIf.Init(*node); node->mMdns.Init(*node); +#if OPENTHREAD_CONFIG_RADIO_LINK_TREL_ENABLE + node->mTrel.Init(*node); +#endif mNodes.Push(*node); @@ -409,9 +412,6 @@ void Core::Process(Node &aNode) ProcessRadio(aNode); ProcessInfraIf(aNode); -#if OPENTHREAD_CONFIG_RADIO_LINK_TREL_ENABLE - ProcessTrel(aNode); -#endif if (aNode.mAlarmMilli.mScheduled && (GetNow() >= aNode.mAlarmMilli.mAlarmTime)) { @@ -665,34 +665,6 @@ Node *Core::FindNodeByInfraIfAddress(const Ip6::Address &aAddress) return matchedNode; } -#if OPENTHREAD_CONFIG_RADIO_LINK_TREL_ENABLE - -void Core::ProcessTrel(Node &aNode) -{ - Ip6::SockAddr senderSockAddr; - Ip6::SockAddr rxNodeSockAddr; - - aNode.GetTrelSockAddr(senderSockAddr); - - for (Trel::PendingTx &pendingTx : aNode.mTrel.mPendingTxList) - { - for (Node &rxNode : mNodes) - { - rxNode.GetTrelSockAddr(rxNodeSockAddr); - - if (pendingTx.mDestSockAddr == rxNodeSockAddr) - { - rxNode.mTrel.Receive(rxNode.GetInstance(), pendingTx.mPayloadData, senderSockAddr); - break; - } - } - } - - aNode.mTrel.mPendingTxList.Free(); -} - -#endif // OPENTHREAD_CONFIG_RADIO_LINK_TREL_ENABLE - //--------------------------------------------------------------------------------------------------------------------- Core::IcmpEchoResponseContext::IcmpEchoResponseContext(Node &aNode, uint16_t aIdentifier) diff --git a/tests/nexus/platform/nexus_core.hpp b/tests/nexus/platform/nexus_core.hpp index 4db442582..ebfa82d72 100644 --- a/tests/nexus/platform/nexus_core.hpp +++ b/tests/nexus/platform/nexus_core.hpp @@ -109,9 +109,6 @@ private: void Process(Node &aNode); void ProcessRadio(Node &aNode); void ProcessInfraIf(Node &aNode); -#if OPENTHREAD_CONFIG_RADIO_LINK_TREL_ENABLE - void ProcessTrel(Node &aNode); -#endif Node *FindNodeByInfraIfAddress(const Ip6::Address &aAddress); diff --git a/tests/nexus/platform/nexus_infra_if.cpp b/tests/nexus/platform/nexus_infra_if.cpp index 9b503f7d8..e6f660740 100644 --- a/tests/nexus/platform/nexus_infra_if.cpp +++ b/tests/nexus/platform/nexus_infra_if.cpp @@ -482,6 +482,26 @@ void InfraIf::Receive(Message &aMessage) ExitNow(); } +#if OPENTHREAD_CONFIG_RADIO_LINK_TREL_ENABLE + if (headers.IsUdp() && headers.GetDestinationPort() == node.mTrel.mUdpPort && node.mTrel.mEnabled) + { + if (headers.GetDestinationAddress().IsMulticast() || node.mInfraIf.HasAddress(headers.GetDestinationAddress())) + { + Ip6::SockAddr senderAddr; + Heap::Data payload; + uint16_t offset = sizeof(Ip6::Header) + sizeof(Ip6::Udp::Header); + + senderAddr.SetAddress(headers.GetSourceAddress()); + senderAddr.SetPort(headers.GetSourcePort()); + + SuccessOrQuit( + payload.SetFrom(aMessage, offset, headers.GetUdpHeader().GetLength() - sizeof(Ip6::Udp::Header))); + node.mTrel.Receive(node.GetInstance(), payload, senderAddr); + } + ExitNow(); + } +#endif + { // We also deliver generic IPv6 packets to the stack if they are NOT ICMPv6 ND packets. // (ND packets were already delivered via otPlatInfraIfRecvIcmp6Nd above). diff --git a/tests/nexus/platform/nexus_trel.cpp b/tests/nexus/platform/nexus_trel.cpp index 92cd285eb..a21054e86 100644 --- a/tests/nexus/platform/nexus_trel.cpp +++ b/tests/nexus/platform/nexus_trel.cpp @@ -74,17 +74,19 @@ void otPlatTrelResetCounters(otInstance *aInstance) { AsNode(aInstance).mTrel.Re uint16_t Trel::sLastUsedUdpPort = kUdpPortStart; Trel::Trel(void) - : mEnabled(false) + : mNode(nullptr) + , mEnabled(false) , mUdpPort(sLastUsedUdpPort++) { ClearAllBytes(mCounters); } +void Trel::Init(Node &aNode) { mNode = &aNode; } + void Trel::Reset(void) { mEnabled = false; ClearAllBytes(mCounters); - mPendingTxList.Free(); } void Trel::Enable(uint16_t &aUdpPort) @@ -93,21 +95,20 @@ void Trel::Enable(uint16_t &aUdpPort) aUdpPort = mUdpPort; } -void Trel::Disable(void) -{ - mEnabled = false; - mPendingTxList.Free(); -} +void Trel::Disable(void) { mEnabled = false; } void Trel::Send(const uint8_t *aUdpPayload, uint16_t aUdpPayloadLen, const Ip6::SockAddr &aDestSockAddr) { - PendingTx *pendingTx = PendingTx::Allocate(); + Message *message; - VerifyOrQuit(pendingTx != nullptr); - SuccessOrQuit(pendingTx->mPayloadData.SetFrom(aUdpPayload, aUdpPayloadLen)); - pendingTx->mDestSockAddr = aDestSockAddr; + VerifyOrQuit(mNode != nullptr); - mPendingTxList.PushAfterTail(*pendingTx); + message = mNode->Get().Allocate(Message::kTypeIp6); + VerifyOrQuit(message != nullptr); + SuccessOrQuit(message->AppendBytes(aUdpPayload, aUdpPayloadLen)); + + mNode->mInfraIf.SendUdp(mNode->mInfraIf.GetLinkLocalAddress(), aDestSockAddr.GetAddress(), mUdpPort, + aDestSockAddr.GetPort(), *message); mCounters.mTxPackets++; mCounters.mTxBytes += aUdpPayloadLen; diff --git a/tests/nexus/platform/nexus_trel.hpp b/tests/nexus/platform/nexus_trel.hpp index df25bdf53..a6c77778b 100644 --- a/tests/nexus/platform/nexus_trel.hpp +++ b/tests/nexus/platform/nexus_trel.hpp @@ -36,6 +36,8 @@ namespace ot { namespace Nexus { +class Node; + struct Trel { static constexpr uint16_t kUdpPortStart = 49152; @@ -43,6 +45,7 @@ struct Trel typedef otPlatTrelCounters Counters; Trel(void); + void Init(Node &aNode); void Reset(void); void Enable(uint16_t &aUdpPort); void Disable(void); @@ -50,19 +53,12 @@ struct Trel void ResetCounters(void) { ClearAllBytes(mCounters); } void Receive(Instance &aInstance, Heap::Data &aPayloadData, const Ip6::SockAddr &aSenderAddr); - struct PendingTx : public Heap::Allocatable, public LinkedListEntry - { - PendingTx *mNext; - Heap::Data mPayloadData; - Ip6::SockAddr mDestSockAddr; - }; - static uint16_t sLastUsedUdpPort; - bool mEnabled; - uint16_t mUdpPort; - OwningList mPendingTxList; - Counters mCounters; + Node *mNode; + bool mEnabled; + uint16_t mUdpPort; + Counters mCounters; }; } // namespace Nexus