From c5168b783a8c603b3d4e5d47725c6201d828af3b Mon Sep 17 00:00:00 2001 From: Griffin Francis Date: Mon, 27 Jul 2026 19:20:35 -0400 Subject: [PATCH] [history] parse TLV headers safely in client answer processing (#13410) This commit updates `HistoryTracker::Client::ProcessNetInfoAnswer()` to iterate over answer TLVs using `Tlv::Info::ParseFrom()`, which reads the full TLV header, including any extended-length field, and validates that the entire TLV is contained within the remaining offset range. Extended TLVs are skipped, since all answer TLVs the client consumes are non-extended. --- src/core/utils/history_tracker_client.cpp | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/src/core/utils/history_tracker_client.cpp b/src/core/utils/history_tracker_client.cpp index 9e4809990..1b194d46a 100644 --- a/src/core/utils/history_tracker_client.cpp +++ b/src/core/utils/history_tracker_client.cpp @@ -163,23 +163,27 @@ void Client::ProcessNetInfoAnswer(const Coap::Message &aMessage) { Error error = kErrorNone; OffsetRange offsetRange; - Tlv tlv; + Tlv::Info tlvInfo; NetworkInfoTlv netInfoTlv; NetworkInfo netInfo; offsetRange.InitFromMessageOffsetToEnd(aMessage); - for (; !offsetRange.IsEmpty(); offsetRange.AdvanceOffset(tlv.GetSize())) + for (; !offsetRange.IsEmpty(); offsetRange.AdvanceOffset(tlvInfo.GetSize())) { - SuccessOrExit(error = aMessage.Read(offsetRange, tlv)); - VerifyOrExit(offsetRange.Contains(tlv.GetSize()), error = kErrorParse); + SuccessOrExit(error = tlvInfo.ParseFrom(aMessage, offsetRange)); - if (tlv.GetType() != Tlv::kNetworkInfo) + if (tlvInfo.IsExtended()) { continue; } - if (tlv.GetLength() == 0) + if (tlvInfo.GetType() != Tlv::kNetworkInfo) + { + continue; + } + + if (tlvInfo.GetLength() == 0) { Finalize(kErrorNone); ExitNow();