mediasoup 3.27.0 → 3.28.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (213) hide show
  1. package/CHANGELOG.md +19 -0
  2. package/node/lib/Consumer.d.ts.map +1 -1
  3. package/node/lib/Consumer.js +4 -51
  4. package/node/lib/Producer.d.ts.map +1 -1
  5. package/node/lib/Producer.js +4 -8
  6. package/node/lib/ProducerTypes.d.ts +4 -2
  7. package/node/lib/ProducerTypes.d.ts.map +1 -1
  8. package/node/lib/Router.d.ts.map +1 -1
  9. package/node/lib/Router.js +4 -0
  10. package/node/lib/Transport.d.ts.map +1 -1
  11. package/node/lib/Transport.js +7 -10
  12. package/node/lib/fbs/rtp-parameters/rtp-header-extension-uri.d.ts +3 -4
  13. package/node/lib/fbs/rtp-parameters/rtp-header-extension-uri.d.ts.map +1 -1
  14. package/node/lib/fbs/rtp-parameters/rtp-header-extension-uri.js +3 -4
  15. package/node/lib/ortc.d.ts +0 -2
  16. package/node/lib/ortc.d.ts.map +1 -1
  17. package/node/lib/ortc.js +11 -21
  18. package/node/lib/rtpMappingFbsUtils.d.ts +6 -0
  19. package/node/lib/rtpMappingFbsUtils.d.ts.map +1 -0
  20. package/node/lib/rtpMappingFbsUtils.js +65 -0
  21. package/node/lib/rtpParametersFbsUtils.d.ts.map +1 -1
  22. package/node/lib/rtpParametersFbsUtils.js +0 -6
  23. package/node/lib/rtpParametersTypes.d.ts +1 -1
  24. package/node/lib/rtpParametersTypes.d.ts.map +1 -1
  25. package/node/lib/rtpStreamFbsUtils.d.ts +4 -0
  26. package/node/lib/rtpStreamFbsUtils.d.ts.map +1 -0
  27. package/node/lib/rtpStreamFbsUtils.js +51 -0
  28. package/node/lib/supportedRtpCapabilities.d.ts.map +1 -1
  29. package/node/lib/supportedRtpCapabilities.js +6 -13
  30. package/node/lib/test/test-Consumer.js +1 -13
  31. package/node/lib/test/test-DataConsumer.js +9 -0
  32. package/node/lib/test/test-DataProducer.js +38 -0
  33. package/node/lib/test/test-PipeTransport.js +27 -29
  34. package/node/lib/test/test-Producer.js +97 -0
  35. package/node/lib/test/test-ortc.js +34 -14
  36. package/package.json +10 -10
  37. package/worker/fbs/FBS/meson.build +25 -0
  38. package/worker/fbs/meson.build +15 -18
  39. package/worker/fbs/rtpParameters.fbs +0 -1
  40. package/worker/fuzzer/src/FuzzerUtils.cpp +5 -3
  41. package/worker/fuzzer/src/RTC/RTP/FuzzerPacket.cpp +16 -2
  42. package/worker/include/DepLibUV.hpp +13 -0
  43. package/worker/include/RTC/BWE/AlrDetector.hpp +97 -0
  44. package/worker/include/RTC/BWE/BitrateProber.hpp +217 -0
  45. package/worker/include/RTC/BWE/BitrateUtils.hpp +39 -0
  46. package/worker/include/RTC/BWE/BweTypes.hpp +171 -3
  47. package/worker/include/RTC/BWE/FeedbackAdapter.hpp +0 -14
  48. package/worker/include/RTC/BWE/InterArrival.hpp +117 -0
  49. package/worker/include/RTC/BWE/IntervalBudget.hpp +81 -0
  50. package/worker/include/RTC/BWE/LossBasedController.hpp +625 -0
  51. package/worker/include/RTC/BWE/OveruseDetector.hpp +71 -0
  52. package/worker/include/RTC/BWE/OveruseEstimator.hpp +115 -0
  53. package/worker/include/RTC/BWE/ProbeBitrateEstimator.hpp +84 -0
  54. package/worker/include/RTC/BWE/ProbeController.hpp +379 -0
  55. package/worker/include/RTC/BWE/ProbePacketGenerator.hpp +130 -0
  56. package/worker/include/RTC/BWE/ProbingScheduler.hpp +187 -0
  57. package/worker/include/RTC/BWE/RembGenerator.hpp +96 -0
  58. package/worker/include/RTC/BWE/RemoteBitrateEstimatorAbsSendTime.hpp +237 -0
  59. package/worker/include/RTC/BWE/RobustThroughputEstimator.hpp +26 -0
  60. package/worker/include/RTC/BWE/SendPacketHistory.hpp +161 -25
  61. package/worker/include/RTC/BWE/TargetRateController.hpp +306 -0
  62. package/worker/include/RTC/BWE/TransportWideCcFeedbackGenerator.hpp +146 -0
  63. package/worker/include/RTC/BWE/TrendlineEstimator.hpp +73 -16
  64. package/worker/include/RTC/Consts.hpp +70 -0
  65. package/worker/include/RTC/DataConsumer.hpp +3 -5
  66. package/worker/include/RTC/DirectTransport.hpp +4 -5
  67. package/worker/include/RTC/PipeTransport.hpp +4 -5
  68. package/worker/include/RTC/PlainTransport.hpp +4 -5
  69. package/worker/include/RTC/RTCP/FeedbackPsRemb.hpp +6 -7
  70. package/worker/include/RTC/RTCP/FeedbackRtpTransport.hpp +3 -1
  71. package/worker/include/RTC/RTP/Codecs/Tools.hpp +1 -1
  72. package/worker/include/RTC/RTP/HeaderExtensionIds.hpp +0 -1
  73. package/worker/include/RTC/RTP/Packet.hpp +16 -4
  74. package/worker/include/RTC/RTP/ProbationGenerator.hpp +0 -8
  75. package/worker/include/RTC/RTP/RtpStream.hpp +12 -9
  76. package/worker/include/RTC/RTP/RtpStreamRecv.hpp +22 -4
  77. package/worker/include/RTC/RTP/RtpStreamSend.hpp +4 -2
  78. package/worker/include/RTC/RTP/RtxStream.hpp +10 -4
  79. package/worker/include/RTC/RateCalculator.hpp +103 -24
  80. package/worker/include/RTC/RemoteCaptureTimeEstimator.hpp +33 -3
  81. package/worker/include/RTC/{RtcLogger.hpp → RtcLogger/RtpPacket.hpp} +5 -3
  82. package/worker/include/RTC/RtcLogger/SendBurst.hpp +88 -0
  83. package/worker/include/RTC/RtpDictionaries.hpp +3 -4
  84. package/worker/include/RTC/SCTP/association/Association.hpp +1 -1
  85. package/worker/include/RTC/SCTP/association/StreamResetHandler.hpp +36 -0
  86. package/worker/include/RTC/SCTP/public/AssociationMetrics.hpp +0 -1
  87. package/worker/include/RTC/SCTP/public/SctpTypes.hpp +9 -9
  88. package/worker/include/RTC/SCTP/rx/DataTracker.hpp +1 -1
  89. package/worker/include/RTC/SCTP/rx/ReassemblyQueue.hpp +11 -1
  90. package/worker/include/RTC/SctpDictionaries.hpp +2 -2
  91. package/worker/include/RTC/TcpConnection.hpp +2 -1
  92. package/worker/include/RTC/Transport.hpp +23 -8
  93. package/worker/include/RTC/TransportTuple.hpp +61 -6
  94. package/worker/include/RTC/WebRtcTransport.hpp +4 -5
  95. package/worker/include/Shared.hpp +5 -0
  96. package/worker/include/SharedInterface.hpp +10 -0
  97. package/worker/include/Utils.hpp +72 -3
  98. package/worker/include/common.hpp +12 -4
  99. package/worker/include/handles/SendCallbacks.hpp +34 -0
  100. package/worker/include/handles/TcpConnectionHandle.hpp +4 -12
  101. package/worker/include/handles/UdpSocketHandle.hpp +4 -8
  102. package/worker/meson.build +45 -1
  103. package/worker/meson_options.txt +1 -0
  104. package/worker/mocks/include/MockShared.hpp +16 -2
  105. package/worker/mocks/include/handles/MockBackoffTimerHandle.hpp +1 -1
  106. package/worker/scripts/package-lock.json +6 -6
  107. package/worker/src/RTC/BWE/AimdRateControl.cpp +4 -5
  108. package/worker/src/RTC/BWE/AlrDetector.cpp +80 -0
  109. package/worker/src/RTC/BWE/BitrateProber.cpp +256 -0
  110. package/worker/src/RTC/BWE/BitrateUtils.cpp +54 -0
  111. package/worker/src/RTC/BWE/DelayBasedBwe.cpp +2 -2
  112. package/worker/src/RTC/BWE/FeedbackAdapter.cpp +20 -37
  113. package/worker/src/RTC/BWE/InterArrival.cpp +216 -0
  114. package/worker/src/RTC/BWE/IntervalBudget.cpp +93 -0
  115. package/worker/src/RTC/BWE/LossBasedController.cpp +1194 -0
  116. package/worker/src/RTC/BWE/OveruseDetector.cpp +128 -0
  117. package/worker/src/RTC/BWE/OveruseEstimator.cpp +166 -0
  118. package/worker/src/RTC/BWE/ProbeBitrateEstimator.cpp +222 -0
  119. package/worker/src/RTC/BWE/ProbeController.cpp +645 -0
  120. package/worker/src/RTC/BWE/ProbePacketGenerator.cpp +140 -0
  121. package/worker/src/RTC/BWE/ProbingScheduler.cpp +196 -0
  122. package/worker/src/RTC/BWE/RembGenerator.cpp +169 -0
  123. package/worker/src/RTC/BWE/RemoteBitrateEstimatorAbsSendTime.cpp +497 -0
  124. package/worker/src/RTC/BWE/RobustThroughputEstimator.cpp +47 -0
  125. package/worker/src/RTC/BWE/SendPacketHistory.cpp +173 -50
  126. package/worker/src/RTC/BWE/TargetRateController.cpp +433 -0
  127. package/worker/src/RTC/BWE/TransportWideCcFeedbackGenerator.cpp +377 -0
  128. package/worker/src/RTC/BWE/TrendlineEstimator.cpp +102 -5
  129. package/worker/src/RTC/Consumer.cpp +7 -5
  130. package/worker/src/RTC/DataConsumer.cpp +8 -10
  131. package/worker/src/RTC/DirectTransport.cpp +14 -8
  132. package/worker/src/RTC/DtlsTransport.cpp +8 -8
  133. package/worker/src/RTC/ICE/IceCandidate.cpp +4 -4
  134. package/worker/src/RTC/ICE/IceServer.cpp +1 -1
  135. package/worker/src/RTC/PipeTransport.cpp +13 -8
  136. package/worker/src/RTC/PlainTransport.cpp +13 -8
  137. package/worker/src/RTC/Producer.cpp +14 -31
  138. package/worker/src/RTC/RTCP/Bye.cpp +1 -1
  139. package/worker/src/RTC/RTCP/FeedbackPsRemb.cpp +18 -0
  140. package/worker/src/RTC/RTCP/FeedbackPsRpsi.cpp +2 -2
  141. package/worker/src/RTC/RTCP/FeedbackPsVbcm.cpp +2 -1
  142. package/worker/src/RTC/RTCP/FeedbackRtpTransport.cpp +2 -2
  143. package/worker/src/RTC/RTCP/Sdes.cpp +1 -1
  144. package/worker/src/RTC/RTP/Codecs/DependencyDescriptor.cpp +2 -1
  145. package/worker/src/RTC/RTP/Packet.cpp +26 -11
  146. package/worker/src/RTC/RTP/ProbationGenerator.cpp +5 -6
  147. package/worker/src/RTC/RTP/RtpStream.cpp +1 -1
  148. package/worker/src/RTC/RTP/RtpStreamRecv.cpp +69 -48
  149. package/worker/src/RTC/RTP/RtpStreamSend.cpp +31 -31
  150. package/worker/src/RTC/RTP/RtxStream.cpp +22 -7
  151. package/worker/src/RTC/RateCalculator.cpp +133 -28
  152. package/worker/src/RTC/RemoteCaptureTimeEstimator.cpp +56 -1
  153. package/worker/src/RTC/{RtcLogger.cpp → RtcLogger/RtpPacket.cpp} +2 -2
  154. package/worker/src/RTC/RtcLogger/SendBurst.cpp +124 -0
  155. package/worker/src/RTC/RtpDictionaries/RtpHeaderExtensionUri.cpp +2 -12
  156. package/worker/src/RTC/RtpDictionaries/RtpParameters.cpp +1 -1
  157. package/worker/src/RTC/SCTP/association/Association.cpp +16 -2
  158. package/worker/src/RTC/SCTP/association/StreamResetHandler.cpp +106 -1
  159. package/worker/src/RTC/SCTP/public/AssociationMetrics.cpp +1 -1
  160. package/worker/src/RTC/SCTP/rx/InterleavedReassemblyStreams.cpp +3 -3
  161. package/worker/src/RTC/SCTP/rx/ReassemblyQueue.cpp +2 -1
  162. package/worker/src/RTC/SCTP/rx/TraditionalReassemblyStreams.cpp +4 -4
  163. package/worker/src/RTC/SCTP/tx/RetransmissionTimeout.cpp +4 -4
  164. package/worker/src/RTC/SctpDictionaries/SctpStreamParameters.cpp +6 -10
  165. package/worker/src/RTC/SimulcastProducerStreamManager.cpp +2 -2
  166. package/worker/src/RTC/SrtpSession.cpp +2 -2
  167. package/worker/src/RTC/SvcProducerStreamManager.cpp +2 -2
  168. package/worker/src/RTC/TcpConnection.cpp +2 -2
  169. package/worker/src/RTC/Transport.cpp +112 -75
  170. package/worker/src/RTC/TransportTuple.cpp +4 -4
  171. package/worker/src/RTC/WebRtcServer.cpp +4 -3
  172. package/worker/src/RTC/WebRtcTransport.cpp +20 -13
  173. package/worker/src/Utils/BitStream.cpp +24 -0
  174. package/worker/src/handles/BackoffTimerHandle.cpp +1 -1
  175. package/worker/src/handles/TcpConnectionHandle.cpp +13 -23
  176. package/worker/src/handles/UdpSocketHandle.cpp +14 -21
  177. package/worker/tasks.py +43 -18
  178. package/worker/test/include/RTC/BWE/helpers/LinkSimulator.hpp +68 -14
  179. package/worker/test/include/RTC/BWE/helpers/RemoteBitrateEstimatorAbsSendTimeTestHelper.hpp +125 -0
  180. package/worker/test/src/RTC/BWE/TestAlrDetector.cpp +110 -0
  181. package/worker/test/src/RTC/BWE/TestBitrateProber.cpp +418 -0
  182. package/worker/test/src/RTC/BWE/TestBitrateUtils.cpp +61 -0
  183. package/worker/test/src/RTC/BWE/TestDelayBasedBwe.cpp +4 -4
  184. package/worker/test/src/RTC/BWE/TestFeedbackAdapter.cpp +53 -37
  185. package/worker/test/src/RTC/BWE/TestInterArrival.cpp +643 -0
  186. package/worker/test/src/RTC/BWE/TestIntervalBudget.cpp +130 -0
  187. package/worker/test/src/RTC/BWE/TestLossBasedController.cpp +1199 -0
  188. package/worker/test/src/RTC/BWE/TestOveruseDetector.cpp +519 -0
  189. package/worker/test/src/RTC/BWE/TestProbeBitrateEstimator.cpp +266 -0
  190. package/worker/test/src/RTC/BWE/TestProbeController.cpp +1682 -0
  191. package/worker/test/src/RTC/BWE/TestProbePacketGenerator.cpp +265 -0
  192. package/worker/test/src/RTC/BWE/TestProbingScheduler.cpp +260 -0
  193. package/worker/test/src/RTC/BWE/TestRembGenerator.cpp +285 -0
  194. package/worker/test/src/RTC/BWE/TestRemoteBitrateEstimatorAbsSendTime.cpp +414 -0
  195. package/worker/test/src/RTC/BWE/TestSendPacketHistory.cpp +296 -77
  196. package/worker/test/src/RTC/BWE/TestTargetRateController.cpp +337 -0
  197. package/worker/test/src/RTC/BWE/TestTransportWideCcFeedbackGenerator.cpp +578 -0
  198. package/worker/test/src/RTC/BWE/TestTrendlineEstimator.cpp +45 -0
  199. package/worker/test/src/RTC/BWE/helpers/LinkSimulator.cpp +133 -29
  200. package/worker/test/src/RTC/BWE/helpers/RemoteBitrateEstimatorAbsSendTimeTestHelper.cpp +625 -0
  201. package/worker/test/src/RTC/RTCP/TestFeedbackPsRemb.cpp +19 -0
  202. package/worker/test/src/RTC/RTP/TestPacket.cpp +58 -4
  203. package/worker/test/src/RTC/RTP/TestProbationGenerator.cpp +3 -2
  204. package/worker/test/src/RTC/RTP/TestRtpStreamRecv.cpp +50 -0
  205. package/worker/test/src/RTC/RTP/TestRtpStreamSend.cpp +59 -0
  206. package/worker/test/src/RTC/SCTP/association/TestStreamResetHandler.cpp +111 -0
  207. package/worker/test/src/RTC/TestRateCalculator.cpp +322 -60
  208. package/worker/test/src/RTC/TestRemoteCaptureTimeEstimator.cpp +95 -7
  209. package/worker/test/src/RTC/TestSimpleProducerStreamManager.cpp +34 -16
  210. package/worker/test/src/RTC/TestSimulcastProducerStreamManager.cpp +31 -13
  211. package/worker/test/src/RTC/TestSvcProducerStreamManager.cpp +37 -19
  212. package/worker/test/src/RTC/TestTransportCongestionControlServer.cpp +10 -10
  213. package/worker/test/src/Utils/TestTime.cpp +120 -21
@@ -0,0 +1,285 @@
1
+ #include "common.hpp"
2
+ #include "RTC/BWE/RembGenerator.hpp"
3
+ #include "RTC/RTCP/FeedbackPsRemb.hpp"
4
+ #include <catch2/catch_test_macros.hpp>
5
+ #include <vector>
6
+
7
+ SCENARIO("BWE RembGenerator", "[bwe][rembgenerator]")
8
+ {
9
+ struct TestRemb
10
+ {
11
+ int64_t bitrate;
12
+ std::vector<uint32_t> ssrcs;
13
+ };
14
+
15
+ class TestRembGeneratorListener : public RTC::BWE::RembGenerator::Listener
16
+ {
17
+ public:
18
+ void OnRembGeneratorSendRemb(
19
+ RTC::BWE::RembGenerator* /*rembGenerator*/, RTC::RTCP::FeedbackPsRembPacket* packet) override
20
+ {
21
+ this->rembs.push_back(TestRemb{ .bitrate = packet->GetBitrate(), .ssrcs = packet->GetSsrcs() });
22
+ }
23
+
24
+ public:
25
+ std::vector<TestRemb> rembs;
26
+ };
27
+
28
+ // Instant the scenarios below start at, which is irrelevant other than for
29
+ // being far from zero.
30
+ constexpr int64_t BaseTimeMs{ 1000 };
31
+ const std::vector<uint32_t> ssrcs{ 1, 2, 3 };
32
+
33
+ SECTION("the first estimation is announced right away")
34
+ {
35
+ TestRembGeneratorListener listener;
36
+ RTC::BWE::RembGenerator rembGenerator(std::addressof(listener));
37
+
38
+ rembGenerator.OnReceiveBitrateChanged(BaseTimeMs, ssrcs, 12345);
39
+
40
+ REQUIRE(listener.rembs.size() == 1);
41
+ REQUIRE(listener.rembs.at(0).bitrate == 12345);
42
+ REQUIRE(listener.rembs.at(0).ssrcs == ssrcs);
43
+ }
44
+
45
+ SECTION("an estimation that barely drops waits")
46
+ {
47
+ TestRembGeneratorListener listener;
48
+ RTC::BWE::RembGenerator rembGenerator(std::addressof(listener));
49
+
50
+ rembGenerator.OnReceiveBitrateChanged(BaseTimeMs, ssrcs, 12346);
51
+
52
+ REQUIRE(listener.rembs.size() == 1);
53
+
54
+ // Less than 3 % below the one announced, so it waits.
55
+ rembGenerator.OnReceiveBitrateChanged(BaseTimeMs + 100, ssrcs, 12345);
56
+
57
+ REQUIRE(listener.rembs.size() == 1);
58
+
59
+ // Past the 200 ms, so it goes out even though it barely moved.
60
+ rembGenerator.OnReceiveBitrateChanged(BaseTimeMs + 201, ssrcs, 12345);
61
+
62
+ REQUIRE(listener.rembs.size() == 2);
63
+ REQUIRE(listener.rembs.at(1).bitrate == 12345);
64
+ }
65
+
66
+ SECTION("an estimation that drops a lot is announced right away")
67
+ {
68
+ TestRembGeneratorListener listener;
69
+ RTC::BWE::RembGenerator rembGenerator(std::addressof(listener));
70
+
71
+ rembGenerator.OnReceiveBitrateChanged(BaseTimeMs, ssrcs, 2345);
72
+ rembGenerator.OnReceiveBitrateChanged(BaseTimeMs + 1, ssrcs, 1234);
73
+
74
+ REQUIRE(listener.rembs.size() == 2);
75
+ REQUIRE(listener.rembs.at(0).bitrate == 2345);
76
+ REQUIRE(listener.rembs.at(1).bitrate == 1234);
77
+ }
78
+
79
+ SECTION("an estimation that rises waits")
80
+ {
81
+ TestRembGeneratorListener listener;
82
+ RTC::BWE::RembGenerator rembGenerator(std::addressof(listener));
83
+
84
+ rembGenerator.OnReceiveBitrateChanged(BaseTimeMs, ssrcs, 1234);
85
+ rembGenerator.OnReceiveBitrateChanged(BaseTimeMs + 100, ssrcs, 2345);
86
+
87
+ REQUIRE(listener.rembs.size() == 1);
88
+
89
+ rembGenerator.OnReceiveBitrateChanged(BaseTimeMs + 201, ssrcs, 2345);
90
+
91
+ REQUIRE(listener.rembs.size() == 2);
92
+ REQUIRE(listener.rembs.at(1).bitrate == 2345);
93
+ }
94
+
95
+ SECTION("setting a cap announces it")
96
+ {
97
+ TestRembGeneratorListener listener;
98
+ RTC::BWE::RembGenerator rembGenerator(std::addressof(listener));
99
+
100
+ rembGenerator.SetMaxIncomingBitrate(BaseTimeMs, 1234);
101
+
102
+ REQUIRE(listener.rembs.size() == 1);
103
+ REQUIRE(listener.rembs.at(0).bitrate == 1234);
104
+ // The cap says nothing about which streams it applies to.
105
+ REQUIRE(listener.rembs.at(0).ssrcs.empty());
106
+ }
107
+
108
+ SECTION("a cap that cannot be expressed is ignored")
109
+ {
110
+ TestRembGeneratorListener listener;
111
+ RTC::BWE::RembGenerator rembGenerator(std::addressof(listener));
112
+
113
+ rembGenerator.SetMaxIncomingBitrate(BaseTimeMs, 1000);
114
+
115
+ REQUIRE(listener.rembs.size() == 1);
116
+
117
+ // A REMB of zero is how the wire says there is no limit, so zero cannot be
118
+ // a cap, and a negative one means nothing.
119
+ rembGenerator.SetMaxIncomingBitrate(BaseTimeMs + 1000, 0);
120
+ rembGenerator.SetMaxIncomingBitrate(BaseTimeMs + 2000, -1);
121
+
122
+ REQUIRE(listener.rembs.size() == 1);
123
+
124
+ // The cap that was set is still the one in force.
125
+ rembGenerator.OnReceiveBitrateChanged(BaseTimeMs + 3000, ssrcs, 5000);
126
+
127
+ REQUIRE(listener.rembs.size() == 2);
128
+ REQUIRE(listener.rembs.at(1).bitrate == 1000);
129
+ }
130
+
131
+ SECTION("the lowest of the cap and the estimation is announced")
132
+ {
133
+ TestRembGeneratorListener listener;
134
+ RTC::BWE::RembGenerator rembGenerator(std::addressof(listener));
135
+
136
+ rembGenerator.OnReceiveBitrateChanged(BaseTimeMs, ssrcs, 1234);
137
+
138
+ REQUIRE(listener.rembs.size() == 1);
139
+ REQUIRE(listener.rembs.at(0).bitrate == 1234);
140
+
141
+ // Nothing to tell, since what was just announced is already below the cap.
142
+ rembGenerator.SetMaxIncomingBitrate(BaseTimeMs + 1, 4567);
143
+
144
+ REQUIRE(listener.rembs.size() == 1);
145
+
146
+ rembGenerator.OnReceiveBitrateChanged(BaseTimeMs + 201, ssrcs, 5678);
147
+
148
+ REQUIRE(listener.rembs.size() == 2);
149
+ REQUIRE(listener.rembs.at(1).bitrate == 4567);
150
+ }
151
+
152
+ SECTION("a cap that needs no telling is not told at the next packet either")
153
+ {
154
+ TestRembGeneratorListener listener;
155
+ RTC::BWE::RembGenerator rembGenerator(std::addressof(listener));
156
+
157
+ rembGenerator.OnReceiveBitrateChanged(BaseTimeMs, ssrcs, 1234);
158
+
159
+ REQUIRE(listener.rembs.size() == 1);
160
+
161
+ // Nothing to tell, since what was just announced is already below the cap.
162
+ rembGenerator.SetMaxIncomingBitrate(BaseTimeMs + 1, 4567);
163
+
164
+ REQUIRE(listener.rembs.size() == 1);
165
+
166
+ // And nothing right behind that REMB either, which would undo the wait
167
+ // between one REMB and the next.
168
+ rembGenerator.MaySendLimitationRembFeedback(BaseTimeMs + 2);
169
+
170
+ REQUIRE(listener.rembs.size() == 1);
171
+ }
172
+
173
+ SECTION("a cap is not announced while the estimation keeps going out")
174
+ {
175
+ TestRembGeneratorListener listener;
176
+ RTC::BWE::RembGenerator rembGenerator(std::addressof(listener));
177
+
178
+ rembGenerator.SetMaxIncomingBitrate(BaseTimeMs, 1000);
179
+
180
+ REQUIRE(listener.rembs.size() == 1);
181
+
182
+ // Well past the interval the cap would be announced again at, but the
183
+ // estimation went out in between and that one is no higher than the cap.
184
+ rembGenerator.OnReceiveBitrateChanged(BaseTimeMs + 1400, ssrcs, 5000);
185
+
186
+ REQUIRE(listener.rembs.size() == 2);
187
+ REQUIRE(listener.rembs.at(1).bitrate == 1000);
188
+
189
+ rembGenerator.MaySendLimitationRembFeedback(BaseTimeMs + 1501);
190
+
191
+ REQUIRE(listener.rembs.size() == 2);
192
+
193
+ // Once the estimation stops, the cap has to be told again.
194
+ rembGenerator.MaySendLimitationRembFeedback(BaseTimeMs + 2902);
195
+
196
+ REQUIRE(listener.rembs.size() == 3);
197
+ REQUIRE(listener.rembs.at(2).bitrate == 1000);
198
+ }
199
+
200
+ SECTION("removing the cap is announced four times")
201
+ {
202
+ TestRembGeneratorListener listener;
203
+ RTC::BWE::RembGenerator rembGenerator(std::addressof(listener));
204
+
205
+ rembGenerator.SetMaxIncomingBitrate(BaseTimeMs, 1000);
206
+
207
+ REQUIRE(listener.rembs.size() == 1);
208
+
209
+ // The first of the four goes out without waiting.
210
+ rembGenerator.SetMaxIncomingBitrate(BaseTimeMs + 1, std::nullopt);
211
+
212
+ REQUIRE(listener.rembs.size() == 2);
213
+ REQUIRE(listener.rembs.at(1).bitrate == 0);
214
+
215
+ int64_t nowMs = BaseTimeMs + 1;
216
+
217
+ for (size_t idx{ 0 }; idx < 3; ++idx)
218
+ {
219
+ // Before the interval is up nothing goes out.
220
+ rembGenerator.MaySendLimitationRembFeedback(nowMs + 1);
221
+
222
+ REQUIRE(listener.rembs.size() == idx + 2);
223
+
224
+ nowMs += 1501;
225
+
226
+ rembGenerator.MaySendLimitationRembFeedback(nowMs);
227
+
228
+ REQUIRE(listener.rembs.size() == idx + 3);
229
+ REQUIRE(listener.rembs.back().bitrate == 0);
230
+ }
231
+
232
+ REQUIRE(listener.rembs.size() == 5);
233
+
234
+ // The four are spent, and with no cap there is nothing left to announce.
235
+ nowMs += 1501;
236
+
237
+ rembGenerator.MaySendLimitationRembFeedback(nowMs);
238
+
239
+ REQUIRE(listener.rembs.size() == 5);
240
+ }
241
+
242
+ SECTION("a cap in force is announced again")
243
+ {
244
+ TestRembGeneratorListener listener;
245
+ RTC::BWE::RembGenerator rembGenerator(std::addressof(listener));
246
+
247
+ rembGenerator.SetMaxIncomingBitrate(BaseTimeMs, 1000);
248
+
249
+ REQUIRE(listener.rembs.size() == 1);
250
+
251
+ rembGenerator.MaySendLimitationRembFeedback(BaseTimeMs + 1500);
252
+
253
+ REQUIRE(listener.rembs.size() == 1);
254
+
255
+ rembGenerator.MaySendLimitationRembFeedback(BaseTimeMs + 1501);
256
+
257
+ REQUIRE(listener.rembs.size() == 2);
258
+ REQUIRE(listener.rembs.at(1).bitrate == 1000);
259
+ }
260
+
261
+ SECTION("a cap set again stops announcing that it was removed")
262
+ {
263
+ TestRembGeneratorListener listener;
264
+ RTC::BWE::RembGenerator rembGenerator(std::addressof(listener));
265
+
266
+ rembGenerator.SetMaxIncomingBitrate(BaseTimeMs, 1000);
267
+ rembGenerator.SetMaxIncomingBitrate(BaseTimeMs + 1, std::nullopt);
268
+
269
+ REQUIRE(listener.rembs.size() == 2);
270
+ REQUIRE(listener.rembs.at(1).bitrate == 0);
271
+
272
+ // Three of the four were still owed, and they no longer say anything true.
273
+ rembGenerator.SetMaxIncomingBitrate(BaseTimeMs + 2, 2000);
274
+
275
+ REQUIRE(listener.rembs.size() == 3);
276
+ REQUIRE(listener.rembs.at(2).bitrate == 2000);
277
+
278
+ // What comes out once the interval is up is the cap, not one of the zeros
279
+ // that were owed.
280
+ rembGenerator.MaySendLimitationRembFeedback(BaseTimeMs + 2000);
281
+
282
+ REQUIRE(listener.rembs.size() == 4);
283
+ REQUIRE(listener.rembs.at(3).bitrate == 2000);
284
+ }
285
+ }
@@ -0,0 +1,414 @@
1
+ #include "common.hpp"
2
+ #include "RTC/BWE/RemoteBitrateEstimatorAbsSendTime.hpp"
3
+ #include "RTC/RTP/HeaderExtensionIds.hpp"
4
+ #include "RTC/RTP/Packet.hpp"
5
+ #include "RTC/RtpDictionaries.hpp"
6
+ #include "Utils.hpp"
7
+ #include "test/include/RTC/BWE/helpers/RemoteBitrateEstimatorAbsSendTimeTestHelper.hpp"
8
+ #include "test/include/RTC/RTP/rtpCommon.hpp"
9
+ #include <catch2/catch_test_macros.hpp>
10
+ #include <cstdlib> // std::abs()
11
+ #include <vector>
12
+
13
+ SCENARIO("BWE RemoteBitrateEstimatorAbsSendTime", "[bwe][remotebitrateestimatorabssendtime]")
14
+ {
15
+ class TestRemoteBitrateEstimatorAbsSendTimeListener
16
+ : public RTC::BWE::RemoteBitrateEstimatorAbsSendTime::Listener
17
+ {
18
+ public:
19
+ void OnRemoteBitrateEstimatorAbsSendTimeBitrateChanged(
20
+ RTC::BWE::RemoteBitrateEstimatorAbsSendTime* /*remoteBitrateEstimator*/,
21
+ const std::vector<uint32_t>& ssrcs,
22
+ int64_t bitrate) override
23
+ {
24
+ this->updated = true;
25
+ this->latestBitrate = bitrate;
26
+ this->latestSsrcs = ssrcs;
27
+ }
28
+
29
+ public:
30
+ bool updated{ false };
31
+ int64_t latestBitrate{ 0 };
32
+ std::vector<uint32_t> latestSsrcs;
33
+ };
34
+
35
+ constexpr uint32_t Ssrc{ 1111 };
36
+ // Instant the scenarios below start at, which is irrelevant other than for
37
+ // being far from zero.
38
+ constexpr int64_t BaseTimeUs{ 1000 * 1000 };
39
+ // Fewest packets a burst needs for it to be taken as one.
40
+ constexpr int Probes{ 5 };
41
+
42
+ // Builds a packet of the given size carrying the given instant in its
43
+ // `abs-send-time` extension.
44
+ //
45
+ // NOTE: Every scenario reuses `rtpCommon::FactoryBuffer`, so the returned
46
+ // packet is only valid until the next call.
47
+ auto buildPacket = [](size_t payloadSize, int64_t sendTimeUs) -> std::unique_ptr<RTC::RTP::Packet>
48
+ {
49
+ std::unique_ptr<RTC::RTP::Packet> packet(
50
+ RTC::RTP::Packet::Factory(rtpCommon::FactoryBuffer, sizeof(rtpCommon::FactoryBuffer)));
51
+
52
+ REQUIRE(packet);
53
+
54
+ packet->SetSsrc(Ssrc);
55
+
56
+ const auto absSendTimeId = static_cast<uint8_t>(RTC::RtpHeaderExtensionUri::Type::ABS_SEND_TIME);
57
+
58
+ const std::vector<RTC::RTP::Packet::Extension> extensions{
59
+ { RTC::RtpHeaderExtensionUri::Type::ABS_SEND_TIME, absSendTimeId, /*len*/ 3, rtpCommon::DataBuffer }
60
+ };
61
+
62
+ packet->SetExtensions(RTC::RTP::Packet::ExtensionsType::OneByte, extensions);
63
+
64
+ RTC::RTP::HeaderExtensionIds headerExtensionIds;
65
+
66
+ headerExtensionIds.absSendTime = absSendTimeId;
67
+
68
+ packet->AssignExtensionIds(headerExtensionIds);
69
+
70
+ packet->SetPayloadLength(payloadSize);
71
+
72
+ REQUIRE(packet->UpdateAbsSendTime(Utils::Time::TimeUsToAbsSendTime(sendTimeUs)));
73
+
74
+ return packet;
75
+ };
76
+
77
+ // Feeds a packet that says it left at `sendTimeUs` and arrived at
78
+ // `arrivalTimeUs`, which is also taken as the current instant.
79
+ auto feedPacket = [&buildPacket](
80
+ RTC::BWE::RemoteBitrateEstimatorAbsSendTime& remoteBitrateEstimator,
81
+ size_t payloadSize,
82
+ int64_t sendTimeUs,
83
+ int64_t arrivalTimeUs,
84
+ int64_t nowUs) -> void
85
+ {
86
+ const auto packet = buildPacket(payloadSize, sendTimeUs);
87
+
88
+ remoteBitrateEstimator.IncomingPacket(packet.get(), arrivalTimeUs, nowUs);
89
+ };
90
+
91
+ SECTION("a burst faster than the one before it raises the estimation")
92
+ {
93
+ TestRemoteBitrateEstimatorAbsSendTimeListener listener;
94
+ RTC::BWE::RemoteBitrateEstimatorAbsSendTime remoteBitrateEstimator(std::addressof(listener));
95
+
96
+ int64_t nowUs{ BaseTimeUs };
97
+
98
+ // First burst sent at 8 * 1000 / 10 = 800 kbps.
99
+ for (int i{ 0 }; i < Probes; ++i)
100
+ {
101
+ nowUs += 10 * 1000;
102
+
103
+ feedPacket(remoteBitrateEstimator, 1000, nowUs, nowUs, nowUs);
104
+ }
105
+
106
+ // Second burst sent at 8 * 1000 / 5 = 1600 kbps.
107
+ for (int i{ 0 }; i < Probes; ++i)
108
+ {
109
+ nowUs += 5 * 1000;
110
+
111
+ feedPacket(remoteBitrateEstimator, 1000, nowUs, nowUs, nowUs);
112
+ }
113
+
114
+ REQUIRE(listener.updated);
115
+ REQUIRE(listener.latestBitrate > 1500000);
116
+ }
117
+
118
+ SECTION("packets that were not paced do not spoil the burst")
119
+ {
120
+ TestRemoteBitrateEstimatorAbsSendTimeListener listener;
121
+ RTC::BWE::RemoteBitrateEstimatorAbsSendTime remoteBitrateEstimator(std::addressof(listener));
122
+
123
+ int64_t nowUs{ BaseTimeUs };
124
+
125
+ // Burst sent at 8 * 1000 / 10 = 800 kbps, with a small packet in between
126
+ // each pair of its packets.
127
+ for (int i{ 0 }; i < Probes; ++i)
128
+ {
129
+ nowUs += 5 * 1000;
130
+
131
+ const int64_t burstTimeUs = nowUs;
132
+
133
+ feedPacket(remoteBitrateEstimator, 1000, burstTimeUs, burstTimeUs, nowUs);
134
+
135
+ nowUs += 5 * 1000;
136
+
137
+ feedPacket(remoteBitrateEstimator, 100, burstTimeUs, burstTimeUs, nowUs);
138
+ }
139
+
140
+ REQUIRE(listener.updated);
141
+ REQUIRE(listener.latestBitrate > 800000);
142
+ }
143
+
144
+ SECTION("a burst that arrives dispersed is measured by how it arrived")
145
+ {
146
+ TestRemoteBitrateEstimatorAbsSendTimeListener listener;
147
+ RTC::BWE::RemoteBitrateEstimatorAbsSendTime remoteBitrateEstimator(std::addressof(listener));
148
+
149
+ int64_t nowUs{ BaseTimeUs };
150
+ int64_t sendTimeUs{ BaseTimeUs };
151
+
152
+ // First burst sent at 8 * 1000 / 10 = 800 kbps.
153
+ for (int i{ 0 }; i < Probes; ++i)
154
+ {
155
+ nowUs += 10 * 1000;
156
+ sendTimeUs += 10 * 1000;
157
+
158
+ feedPacket(remoteBitrateEstimator, 1000, sendTimeUs, nowUs, nowUs);
159
+ }
160
+
161
+ // Second burst sent at 8 * 1000 / 5 = 1600 kbps but arriving at
162
+ // 8 * 1000 / 8 = 1000 kbps, so the link did not take it.
163
+ for (int i{ 0 }; i < Probes; ++i)
164
+ {
165
+ nowUs += 8 * 1000;
166
+ sendTimeUs += 5 * 1000;
167
+
168
+ feedPacket(remoteBitrateEstimator, 1000, sendTimeUs, nowUs, nowUs);
169
+ }
170
+
171
+ REQUIRE(listener.updated);
172
+ REQUIRE(std::abs(listener.latestBitrate - 800000) <= 10000);
173
+ }
174
+
175
+ SECTION("a burst that arrives slightly faster than it was sent is taken")
176
+ {
177
+ TestRemoteBitrateEstimatorAbsSendTimeListener listener;
178
+ RTC::BWE::RemoteBitrateEstimatorAbsSendTime remoteBitrateEstimator(std::addressof(listener));
179
+
180
+ int64_t nowUs{ BaseTimeUs };
181
+ int64_t sendTimeUs{ BaseTimeUs };
182
+
183
+ // Sent at 8 * 1000 / 10 = 800 kbps, arriving at 8 * 1000 / 5 = 1600 kbps.
184
+ for (int i{ 0 }; i < Probes; ++i)
185
+ {
186
+ nowUs += 5 * 1000;
187
+ sendTimeUs += 10 * 1000;
188
+
189
+ feedPacket(remoteBitrateEstimator, 1000, sendTimeUs, nowUs, nowUs);
190
+ }
191
+
192
+ REQUIRE(listener.updated);
193
+ REQUIRE(listener.latestBitrate > 800000);
194
+ }
195
+
196
+ SECTION("a burst that arrives far faster than it was sent says nothing")
197
+ {
198
+ TestRemoteBitrateEstimatorAbsSendTimeListener listener;
199
+ RTC::BWE::RemoteBitrateEstimatorAbsSendTime remoteBitrateEstimator(std::addressof(listener));
200
+
201
+ int64_t nowUs{ BaseTimeUs };
202
+ int64_t sendTimeUs{ BaseTimeUs };
203
+
204
+ // Sent at 8 * 1000 / 10 = 800 kbps, arriving ten times faster, which no
205
+ // link explains.
206
+ for (int i{ 0 }; i < Probes; ++i)
207
+ {
208
+ nowUs += 1 * 1000;
209
+ sendTimeUs += 10 * 1000;
210
+
211
+ feedPacket(remoteBitrateEstimator, 1000, sendTimeUs, nowUs, nowUs);
212
+ }
213
+
214
+ REQUIRE(!listener.updated);
215
+ }
216
+
217
+ SECTION("a burst that arrives slower than it was sent is measured by how it arrived")
218
+ {
219
+ TestRemoteBitrateEstimatorAbsSendTimeListener listener;
220
+ RTC::BWE::RemoteBitrateEstimatorAbsSendTime remoteBitrateEstimator(std::addressof(listener));
221
+
222
+ int64_t nowUs{ BaseTimeUs };
223
+ int64_t sendTimeUs{ BaseTimeUs };
224
+
225
+ // Sent at 8 * 1000 / 5 = 1600 kbps, arriving at 8 * 1000 / 7 = 1142 kbps.
226
+ for (int i{ 0 }; i < Probes; ++i)
227
+ {
228
+ nowUs += 7 * 1000;
229
+ sendTimeUs += 5 * 1000;
230
+
231
+ feedPacket(remoteBitrateEstimator, 1000, sendTimeUs, nowUs, nowUs);
232
+ }
233
+
234
+ REQUIRE(listener.updated);
235
+ REQUIRE(std::abs(listener.latestBitrate - 1140000) <= 10000);
236
+ }
237
+
238
+ SECTION("a fast burst that arrives slower is measured by how it arrived")
239
+ {
240
+ TestRemoteBitrateEstimatorAbsSendTimeListener listener;
241
+ RTC::BWE::RemoteBitrateEstimatorAbsSendTime remoteBitrateEstimator(std::addressof(listener));
242
+
243
+ int64_t nowUs{ BaseTimeUs };
244
+ int64_t sendTimeUs{ BaseTimeUs };
245
+
246
+ // Sent at 8 * 1000 / 1 = 8000 kbps, arriving at 8 * 1000 / 2 = 4000 kbps.
247
+ for (int i{ 0 }; i < Probes; ++i)
248
+ {
249
+ nowUs += 2 * 1000;
250
+ sendTimeUs += 1 * 1000;
251
+
252
+ feedPacket(remoteBitrateEstimator, 1000, sendTimeUs, nowUs, nowUs);
253
+ }
254
+
255
+ REQUIRE(listener.updated);
256
+ REQUIRE(std::abs(listener.latestBitrate - 4000000) <= 10000);
257
+ }
258
+
259
+ SECTION("packets too small to have been paced are not taken as a burst")
260
+ {
261
+ TestRemoteBitrateEstimatorAbsSendTimeListener listener;
262
+ RTC::BWE::RemoteBitrateEstimatorAbsSendTime remoteBitrateEstimator(std::addressof(listener));
263
+
264
+ int64_t nowUs{ BaseTimeUs };
265
+
266
+ // 200 bytes every 10 ms, which is not big enough to have been paced.
267
+ for (int i{ 0 }; i < Probes; ++i)
268
+ {
269
+ nowUs += 10 * 1000;
270
+
271
+ feedPacket(remoteBitrateEstimator, 200, nowUs, nowUs, nowUs);
272
+ }
273
+
274
+ REQUIRE(!listener.updated);
275
+
276
+ // The same cadence with packets that are big enough is a burst.
277
+ for (int i{ 0 }; i < Probes; ++i)
278
+ {
279
+ nowUs += 10 * 1000;
280
+
281
+ feedPacket(remoteBitrateEstimator, 1000, nowUs, nowUs, nowUs);
282
+ }
283
+
284
+ REQUIRE(listener.updated);
285
+ REQUIRE(std::abs(listener.latestBitrate - 800000) <= 10000);
286
+ }
287
+
288
+ // NOTE: What this pins is that a packet arriving after every stream has timed
289
+ // out, and every packet after that one, never reach a null inter arrival or
290
+ // overuse estimator.
291
+ SECTION("a packet after every stream timed out is handled")
292
+ {
293
+ TestRemoteBitrateEstimatorAbsSendTimeListener listener;
294
+ RTC::BWE::RemoteBitrateEstimatorAbsSendTime remoteBitrateEstimator(std::addressof(listener));
295
+
296
+ int64_t nowUs{ BaseTimeUs };
297
+
298
+ feedPacket(remoteBitrateEstimator, 1000, nowUs, nowUs, nowUs);
299
+
300
+ // Longer than the two seconds a stream may be silent for.
301
+ nowUs += 2001 * 1000;
302
+
303
+ feedPacket(remoteBitrateEstimator, 1000, nowUs, nowUs, nowUs);
304
+
305
+ nowUs += 1000 * 1000;
306
+
307
+ feedPacket(remoteBitrateEstimator, 1000, nowUs, nowUs, nowUs);
308
+ }
309
+
310
+ SECTION("initial behavior")
311
+ {
312
+ bweHelpers::RemoteBitrateEstimatorAbsSendTimeTestHelper helper;
313
+
314
+ helper.InitialBehaviorTestHelper(674840);
315
+ }
316
+
317
+ SECTION("a rate increase with reordered packets")
318
+ {
319
+ bweHelpers::RemoteBitrateEstimatorAbsSendTimeTestHelper helper;
320
+
321
+ helper.RateIncreaseReorderingTestHelper(674840);
322
+ }
323
+
324
+ SECTION("a rate increase measured in rtp timestamps")
325
+ {
326
+ bweHelpers::RemoteBitrateEstimatorAbsSendTimeTestHelper helper;
327
+
328
+ helper.RateIncreaseRtpTimestampsTestHelper(1237);
329
+ }
330
+
331
+ SECTION("a capacity drop with one stream")
332
+ {
333
+ bweHelpers::RemoteBitrateEstimatorAbsSendTimeTestHelper helper;
334
+
335
+ helper.CapacityDropTestHelper(1, false, 633, 0);
336
+ }
337
+
338
+ SECTION("a capacity drop with the receiver clock moved forward")
339
+ {
340
+ bweHelpers::RemoteBitrateEstimatorAbsSendTimeTestHelper helper;
341
+
342
+ helper.CapacityDropTestHelper(1, false, 267, 30000);
343
+ }
344
+
345
+ SECTION("a capacity drop with the receiver clock moved back")
346
+ {
347
+ bweHelpers::RemoteBitrateEstimatorAbsSendTimeTestHelper helper;
348
+
349
+ helper.CapacityDropTestHelper(1, false, 267, -30000);
350
+ }
351
+
352
+ SECTION("a capacity drop with one stream whose timestamps wrap")
353
+ {
354
+ bweHelpers::RemoteBitrateEstimatorAbsSendTimeTestHelper helper;
355
+
356
+ helper.CapacityDropTestHelper(1, true, 633, 0);
357
+ }
358
+
359
+ SECTION("a capacity drop with two streams whose timestamps wrap")
360
+ {
361
+ bweHelpers::RemoteBitrateEstimatorAbsSendTimeTestHelper helper;
362
+
363
+ helper.CapacityDropTestHelper(2, true, 700, 0);
364
+ }
365
+
366
+ SECTION("a capacity drop with three streams whose timestamps wrap")
367
+ {
368
+ bweHelpers::RemoteBitrateEstimatorAbsSendTimeTestHelper helper;
369
+
370
+ helper.CapacityDropTestHelper(3, true, 633, 0);
371
+ }
372
+
373
+ SECTION("a capacity drop with thirteen streams whose timestamps wrap")
374
+ {
375
+ bweHelpers::RemoteBitrateEstimatorAbsSendTimeTestHelper helper;
376
+
377
+ helper.CapacityDropTestHelper(13, true, 667, 0);
378
+ }
379
+
380
+ SECTION("a capacity drop with nineteen streams whose timestamps wrap")
381
+ {
382
+ bweHelpers::RemoteBitrateEstimatorAbsSendTimeTestHelper helper;
383
+
384
+ helper.CapacityDropTestHelper(19, true, 667, 0);
385
+ }
386
+
387
+ SECTION("a capacity drop with thirty streams whose timestamps wrap")
388
+ {
389
+ bweHelpers::RemoteBitrateEstimatorAbsSendTimeTestHelper helper;
390
+
391
+ helper.CapacityDropTestHelper(30, true, 667, 0);
392
+ }
393
+
394
+ SECTION("packets sent very close together are taken as one group")
395
+ {
396
+ bweHelpers::RemoteBitrateEstimatorAbsSendTimeTestHelper helper;
397
+
398
+ helper.TestTimestampGroupingTestHelper();
399
+ }
400
+
401
+ SECTION("a sender rejoining after a short silence, which wraps abs-send-time")
402
+ {
403
+ bweHelpers::RemoteBitrateEstimatorAbsSendTimeTestHelper helper;
404
+
405
+ helper.TestWrappingHelper(35);
406
+ }
407
+
408
+ SECTION("a sender rejoining after a silence that leaves abs-send-time unchanged")
409
+ {
410
+ bweHelpers::RemoteBitrateEstimatorAbsSendTimeTestHelper helper;
411
+
412
+ helper.TestWrappingHelper(10 * 64);
413
+ }
414
+ }