commit 7e9015af7aabfb591d2e347da518b204caa62f0f
parent b0890f33e67fb78675103641f314f3def5d48a54
Author: Dan Baker <dbaker@mozilla.com>
Date: Tue, 2 Dec 2025 00:40:12 -0700
Bug 2000941 - Vendor libwebrtc from 0891b89570
Upstream commit: https://webrtc.googlesource.com/src/+/0891b8957088d6695a93cb4c34865a86a0270ac6
Calculate Smoothed RTT based on CongestionFeedback
It is only calculated from feedback following RFC8888.
Bug: webrtc:447037083
Change-Id: I14309a329633f7043f95f00798506ed418b6b007
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/411561
Commit-Queue: Per Kjellander <perkj@webrtc.org>
Reviewed-by: Björn Terelius <terelius@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#45739}
Diffstat:
5 files changed, 144 insertions(+), 2 deletions(-)
diff --git a/third_party/libwebrtc/README.mozilla.last-vendor b/third_party/libwebrtc/README.mozilla.last-vendor
@@ -1,4 +1,4 @@
# ./mach python dom/media/webrtc/third_party_build/vendor-libwebrtc.py --from-local /Users/danielbaker/elm/.moz-fast-forward/moz-libwebrtc --commit mozpatches libwebrtc
-libwebrtc updated from /Users/danielbaker/elm/.moz-fast-forward/moz-libwebrtc commit mozpatches on 2025-12-02T07:37:37.149253+00:00.
+libwebrtc updated from /Users/danielbaker/elm/.moz-fast-forward/moz-libwebrtc commit mozpatches on 2025-12-02T07:39:58.584232+00:00.
# base of lastest vendoring
-181c224ec0
+0891b89570
diff --git a/third_party/libwebrtc/api/transport/network_types.h b/third_party/libwebrtc/api/transport/network_types.h
@@ -189,6 +189,11 @@ struct RTC_EXPORT TransportPacketsFeedback {
DataSize data_in_flight = DataSize::Zero();
bool transport_supports_ecn = false;
std::vector<PacketResult> packet_feedbacks;
+ // Smoothed RTT calculated on the current network route.
+ // Calculated similarly as RFC 6298 using exponentially weighted moving
+ // average with alpha 1/8. Note that it is not calculated for all feedback
+ // types.
+ TimeDelta smoothed_rtt = TimeDelta::PlusInfinity();
// Arrival times for messages without send time information.
std::vector<Timestamp> sendless_arrival_times;
diff --git a/third_party/libwebrtc/modules/congestion_controller/rtp/transport_feedback_adapter.cc b/third_party/libwebrtc/modules/congestion_controller/rtp/transport_feedback_adapter.cc
@@ -303,6 +303,12 @@ TransportFeedbackAdapter::ProcessCongestionControlFeedback(
result.sent_packet = packet_feedback->sent;
if (packet_info.arrival_time_offset.IsFinite()) {
result.receive_time = current_offset_ - packet_info.arrival_time_offset;
+ TimeDelta rtt = feedback_receive_time - result.sent_packet.send_time -
+ packet_info.arrival_time_offset;
+ if (smoothed_rtt_.IsInfinite()) {
+ smoothed_rtt_ = rtt;
+ }
+ smoothed_rtt_ = (smoothed_rtt_ * 7 + rtt) / 8; // RFC 6298, alpha = 1/8
supports_ecn &= packet_info.ecn != EcnMarking::kNotEct;
}
result.ecn = packet_info.ecn;
@@ -346,6 +352,7 @@ TransportFeedbackAdapter::ToTransportFeedback(
msg.packet_feedbacks = std::move(packet_results);
msg.data_in_flight = in_flight_.GetOutstandingData(network_route_);
msg.transport_supports_ecn = supports_ecn;
+ msg.smoothed_rtt = smoothed_rtt_;
return msg;
}
@@ -353,6 +360,7 @@ TransportFeedbackAdapter::ToTransportFeedback(
void TransportFeedbackAdapter::SetNetworkRoute(
const NetworkRoute& network_route) {
network_route_ = network_route;
+ smoothed_rtt_ = TimeDelta::PlusInfinity();
}
DataSize TransportFeedbackAdapter::GetOutstandingData() const {
diff --git a/third_party/libwebrtc/modules/congestion_controller/rtp/transport_feedback_adapter.h b/third_party/libwebrtc/modules/congestion_controller/rtp/transport_feedback_adapter.h
@@ -20,6 +20,7 @@
#include "api/transport/network_types.h"
#include "api/units/data_size.h"
+#include "api/units/time_delta.h"
#include "api/units/timestamp.h"
#include "modules/rtp_rtcp/include/rtp_rtcp_defines.h"
#include "modules/rtp_rtcp/source/rtcp_packet/congestion_control_feedback.h"
@@ -121,6 +122,8 @@ class TransportFeedbackAdapter {
InFlightBytesTracker in_flight_;
NetworkRoute network_route_;
+ TimeDelta smoothed_rtt_ = TimeDelta::PlusInfinity();
+
Timestamp current_offset_ = Timestamp::MinusInfinity();
// `last_transport_feedback_base_time` is only used for transport feedback to
diff --git a/third_party/libwebrtc/modules/congestion_controller/rtp/transport_feedback_adapter_unittest.cc b/third_party/libwebrtc/modules/congestion_controller/rtp/transport_feedback_adapter_unittest.cc
@@ -608,4 +608,130 @@ TEST(TransportFeedbackAdapterCongestionFeedbackTest,
ASSERT_THAT(adapted_feedback->packet_feedbacks, SizeIs(2));
}
+TEST(TransportFeedbackAdapterTest, SmoothedRttIsInfiniteForTransportFeedback) {
+ // Smoothed RTT is not implemented for transport sequence number feedback.
+ TransportFeedbackAdapter adapter;
+ const Timestamp kFirstSendTime = Timestamp::Seconds(1234);
+
+ const PacketTemplate packet = {.transport_sequence_number = 1,
+ .rtp_sequence_number = 101,
+ .send_timestamp = kFirstSendTime,
+ .receive_timestamp = Timestamp::Millis(200)};
+ adapter.AddPacket(CreatePacketToSend(packet), packet.pacing_info,
+ /*overhead=*/0u, packet.send_timestamp);
+
+ adapter.ProcessSentPacket(SentPacketInfo(packet.transport_sequence_number,
+ packet.send_timestamp.ms()));
+ rtcp::TransportFeedback rtcp_feedback =
+ BuildRtcpTransportFeedbackPacket(MakeArrayView(&packet, 1));
+ std::optional<TransportPacketsFeedback> adapted_feedback =
+ adapter.ProcessTransportFeedback(
+ rtcp_feedback,
+ /*feedback_receive_time=*/packet.send_timestamp +
+ TimeDelta::Millis(10));
+ EXPECT_TRUE(adapted_feedback->smoothed_rtt.IsInfinite());
+}
+
+TEST(TransportFeedbackAdapterCongestionFeedbackTest,
+ CalculateSmoothedRttForConstantOneWayDelay) {
+ TransportFeedbackAdapter adapter;
+ const Timestamp kFirstSendTime = Timestamp::Seconds(1234);
+
+ // Send 3 packets with a constant one way delay. // send timestamp and
+ // receive timestamp may use different epoch.
+ const PacketTemplate packets[] = {
+ {
+ .transport_sequence_number = 1,
+ .rtp_sequence_number = 101,
+ .send_timestamp = kFirstSendTime,
+ .receive_timestamp = Timestamp::Millis(200),
+ },
+ {
+ .transport_sequence_number = 2,
+ .rtp_sequence_number = 102,
+ .send_timestamp = kFirstSendTime + TimeDelta::Millis(10),
+ .receive_timestamp = Timestamp::Millis(210),
+ },
+ {
+ .transport_sequence_number = 3,
+ .rtp_sequence_number = 103,
+ .send_timestamp = kFirstSendTime + TimeDelta::Millis(50),
+ .receive_timestamp = Timestamp::Millis(250),
+ },
+ {
+ .transport_sequence_number = 4,
+ .rtp_sequence_number = 105,
+ .send_timestamp = kFirstSendTime + TimeDelta::Millis(55),
+ .receive_timestamp = Timestamp::Millis(255),
+ }};
+
+ for (const PacketTemplate& packet : packets) {
+ adapter.AddPacket(CreatePacketToSend(packet), packet.pacing_info,
+ /*overhead=*/0u, packet.send_timestamp);
+
+ adapter.ProcessSentPacket(SentPacketInfo(packet.transport_sequence_number,
+ packet.send_timestamp.ms()));
+ }
+
+ const TimeDelta kExpectedRtt = TimeDelta::Millis(20);
+ for (int i = 0; i < 4; i = i + 2) {
+ rtcp::CongestionControlFeedback rtcp_feedback =
+ BuildRtcpCongestionControlFeedbackPacket(MakeArrayView(&packets[i], 2));
+ std::optional<TransportPacketsFeedback> adapted_feedback =
+ adapter.ProcessCongestionControlFeedback(
+ rtcp_feedback,
+ /*feedback_receive_time=*/packets[i + 1].send_timestamp +
+ kExpectedRtt);
+ EXPECT_EQ(adapted_feedback->smoothed_rtt, kExpectedRtt);
+ }
+}
+
+TEST(TransportFeedbackAdapterCongestionFeedbackTest,
+ SmoothedRttIncreaseIfOneWayDelayIncrease) {
+ TransportFeedbackAdapter adapter;
+ const Timestamp kFirstSendTime = Timestamp::Seconds(1234);
+
+ const PacketTemplate packets[] = {
+ {
+ .transport_sequence_number = 1,
+ .rtp_sequence_number = 101,
+ .send_timestamp = kFirstSendTime,
+ .receive_timestamp = Timestamp::Millis(200),
+ },
+ {
+ .transport_sequence_number = 2,
+ .rtp_sequence_number = 102,
+ .send_timestamp = kFirstSendTime + TimeDelta::Millis(10),
+ .receive_timestamp = Timestamp::Millis(210),
+ },
+ };
+
+ for (const PacketTemplate& packet : packets) {
+ adapter.AddPacket(CreatePacketToSend(packet), packet.pacing_info,
+ /*overhead=*/0u, packet.send_timestamp);
+
+ adapter.ProcessSentPacket(SentPacketInfo(packet.transport_sequence_number,
+ packet.send_timestamp.ms()));
+ }
+
+ const TimeDelta kExpectedBaseRtt = TimeDelta::Millis(20);
+ rtcp::CongestionControlFeedback first_rtcp_feedback =
+ BuildRtcpCongestionControlFeedbackPacket(MakeArrayView(&packets[0], 1));
+ std::optional<TransportPacketsFeedback> first_adapted_feedback =
+ adapter.ProcessCongestionControlFeedback(
+ first_rtcp_feedback,
+ /*feedback_receive_time=*/packets[0].send_timestamp +
+ kExpectedBaseRtt);
+ EXPECT_EQ(first_adapted_feedback->smoothed_rtt, kExpectedBaseRtt);
+
+ rtcp::CongestionControlFeedback rtcp_feedback =
+ BuildRtcpCongestionControlFeedbackPacket(MakeArrayView(&packets[1], 1));
+ std::optional<TransportPacketsFeedback> adapted_feedback =
+ adapter.ProcessCongestionControlFeedback(
+ rtcp_feedback,
+ /*feedback_receive_time=*/packets[1].send_timestamp +
+ kExpectedBaseRtt + TimeDelta::Millis(10));
+ EXPECT_GT(adapted_feedback->smoothed_rtt,
+ first_adapted_feedback->smoothed_rtt);
+}
} // namespace webrtc