• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *  Copyright (c) 2017 The WebRTC project authors. All Rights Reserved.
3  *
4  *  Use of this source code is governed by a BSD-style license
5  *  that can be found in the LICENSE file in the root of the source
6  *  tree. An additional intellectual property rights grant can be found
7  *  in the file PATENTS.  All contributing project authors may
8  *  be found in the AUTHORS file in the root of the source tree.
9  */
10 
11 #include <deque>
12 #include <limits>
13 #include <memory>
14 #include <string>
15 #include <tuple>
16 
17 #include "logging/rtc_event_log/encoder/rtc_event_log_encoder_legacy.h"
18 #include "logging/rtc_event_log/encoder/rtc_event_log_encoder_new_format.h"
19 #include "logging/rtc_event_log/encoder/rtc_event_log_encoder_v3.h"
20 #include "logging/rtc_event_log/events/rtc_event_alr_state.h"
21 #include "logging/rtc_event_log/events/rtc_event_audio_network_adaptation.h"
22 #include "logging/rtc_event_log/events/rtc_event_audio_playout.h"
23 #include "logging/rtc_event_log/events/rtc_event_audio_receive_stream_config.h"
24 #include "logging/rtc_event_log/events/rtc_event_audio_send_stream_config.h"
25 #include "logging/rtc_event_log/events/rtc_event_bwe_update_delay_based.h"
26 #include "logging/rtc_event_log/events/rtc_event_bwe_update_loss_based.h"
27 #include "logging/rtc_event_log/events/rtc_event_probe_cluster_created.h"
28 #include "logging/rtc_event_log/events/rtc_event_probe_result_failure.h"
29 #include "logging/rtc_event_log/events/rtc_event_probe_result_success.h"
30 #include "logging/rtc_event_log/events/rtc_event_rtcp_packet_incoming.h"
31 #include "logging/rtc_event_log/events/rtc_event_rtcp_packet_outgoing.h"
32 #include "logging/rtc_event_log/events/rtc_event_rtp_packet_incoming.h"
33 #include "logging/rtc_event_log/events/rtc_event_rtp_packet_outgoing.h"
34 #include "logging/rtc_event_log/events/rtc_event_video_receive_stream_config.h"
35 #include "logging/rtc_event_log/events/rtc_event_video_send_stream_config.h"
36 #include "logging/rtc_event_log/rtc_event_log_parser.h"
37 #include "logging/rtc_event_log/rtc_event_log_unittest_helper.h"
38 #include "modules/audio_coding/audio_network_adaptor/include/audio_network_adaptor_config.h"
39 #include "modules/rtp_rtcp/source/rtcp_packet/bye.h"
40 #include "modules/rtp_rtcp/source/rtp_header_extensions.h"
41 #include "rtc_base/fake_clock.h"
42 #include "rtc_base/random.h"
43 #include "test/gtest.h"
44 
45 namespace webrtc {
46 class RtcEventLogEncoderTest
47     : public ::testing::TestWithParam<
48           std::tuple<int, RtcEventLog::EncodingType, size_t, bool>> {
49  protected:
RtcEventLogEncoderTest()50   RtcEventLogEncoderTest()
51       : seed_(std::get<0>(GetParam())),
52         prng_(seed_),
53         encoding_type_(std::get<1>(GetParam())),
54         event_count_(std::get<2>(GetParam())),
55         force_repeated_fields_(std::get<3>(GetParam())),
56         gen_(seed_ * 880001UL),
57         verifier_(encoding_type_) {
58     switch (encoding_type_) {
59       case RtcEventLog::EncodingType::Legacy:
60         encoder_ = std::make_unique<RtcEventLogEncoderLegacy>();
61         break;
62       case RtcEventLog::EncodingType::NewFormat:
63         encoder_ = std::make_unique<RtcEventLogEncoderNewFormat>();
64         break;
65       case RtcEventLog::EncodingType::ProtoFree:
66         encoder_ = std::make_unique<RtcEventLogEncoderV3>();
67         break;
68     }
69     encoded_ =
70         encoder_->EncodeLogStart(rtc::TimeMillis(), rtc::TimeUTCMillis());
71   }
72   ~RtcEventLogEncoderTest() override = default;
73 
74   // ANA events have some optional fields, so we want to make sure that we get
75   // correct behavior both when all of the values are there, as well as when
76   // only some.
77   void TestRtcEventAudioNetworkAdaptation(
78       const std::vector<std::unique_ptr<RtcEventAudioNetworkAdaptation>>&);
79 
80   template <typename EventType>
81   std::unique_ptr<EventType> NewRtpPacket(
82       uint32_t ssrc,
83       const RtpHeaderExtensionMap& extension_map);
84 
85   template <typename ParsedType>
86   const std::vector<ParsedType>* GetRtpPacketsBySsrc(
87       const ParsedRtcEventLog* parsed_log,
88       uint32_t ssrc);
89 
90   template <typename EventType, typename ParsedType>
91   void TestRtpPackets();
92 
93   std::deque<std::unique_ptr<RtcEvent>> history_;
94   std::unique_ptr<RtcEventLogEncoder> encoder_;
95   ParsedRtcEventLog parsed_log_;
96   const uint64_t seed_;
97   Random prng_;
98   const RtcEventLog::EncodingType encoding_type_;
99   const size_t event_count_;
100   const bool force_repeated_fields_;
101   test::EventGenerator gen_;
102   test::EventVerifier verifier_;
103   std::string encoded_;
104 };
105 
TestRtcEventAudioNetworkAdaptation(const std::vector<std::unique_ptr<RtcEventAudioNetworkAdaptation>> & events)106 void RtcEventLogEncoderTest::TestRtcEventAudioNetworkAdaptation(
107     const std::vector<std::unique_ptr<RtcEventAudioNetworkAdaptation>>&
108         events) {
109   ASSERT_TRUE(history_.empty()) << "Function should be called once per test.";
110 
111   for (auto& event : events) {
112     history_.push_back(event->Copy());
113   }
114 
115   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
116   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
117   const auto& ana_configs = parsed_log_.audio_network_adaptation_events();
118 
119   ASSERT_EQ(ana_configs.size(), events.size());
120   for (size_t i = 0; i < events.size(); ++i) {
121     verifier_.VerifyLoggedAudioNetworkAdaptationEvent(*events[i],
122                                                       ana_configs[i]);
123   }
124 }
125 
126 template <>
NewRtpPacket(uint32_t ssrc,const RtpHeaderExtensionMap & extension_map)127 std::unique_ptr<RtcEventRtpPacketIncoming> RtcEventLogEncoderTest::NewRtpPacket(
128     uint32_t ssrc,
129     const RtpHeaderExtensionMap& extension_map) {
130   return gen_.NewRtpPacketIncoming(ssrc, extension_map, false);
131 }
132 
133 template <>
NewRtpPacket(uint32_t ssrc,const RtpHeaderExtensionMap & extension_map)134 std::unique_ptr<RtcEventRtpPacketOutgoing> RtcEventLogEncoderTest::NewRtpPacket(
135     uint32_t ssrc,
136     const RtpHeaderExtensionMap& extension_map) {
137   return gen_.NewRtpPacketOutgoing(ssrc, extension_map, false);
138 }
139 
140 template <>
141 const std::vector<LoggedRtpPacketIncoming>*
GetRtpPacketsBySsrc(const ParsedRtcEventLog * parsed_log,uint32_t ssrc)142 RtcEventLogEncoderTest::GetRtpPacketsBySsrc(const ParsedRtcEventLog* parsed_log,
143                                             uint32_t ssrc) {
144   const auto& incoming_streams = parsed_log->incoming_rtp_packets_by_ssrc();
145   for (const auto& stream : incoming_streams) {
146     if (stream.ssrc == ssrc) {
147       return &stream.incoming_packets;
148     }
149   }
150   return nullptr;
151 }
152 
153 template <>
154 const std::vector<LoggedRtpPacketOutgoing>*
GetRtpPacketsBySsrc(const ParsedRtcEventLog * parsed_log,uint32_t ssrc)155 RtcEventLogEncoderTest::GetRtpPacketsBySsrc(const ParsedRtcEventLog* parsed_log,
156                                             uint32_t ssrc) {
157   const auto& outgoing_streams = parsed_log->outgoing_rtp_packets_by_ssrc();
158   for (const auto& stream : outgoing_streams) {
159     if (stream.ssrc == ssrc) {
160       return &stream.outgoing_packets;
161     }
162   }
163   return nullptr;
164 }
165 
166 template <typename EventType, typename ParsedType>
TestRtpPackets()167 void RtcEventLogEncoderTest::TestRtpPackets() {
168   // SSRCs will be randomly assigned out of this small pool, significant only
169   // in that it also covers such edge cases as SSRC = 0 and SSRC = 0xffffffff.
170   // The pool is intentionally small, so as to produce collisions.
171   const std::vector<uint32_t> kSsrcPool = {0x00000000, 0x12345678, 0xabcdef01,
172                                            0xffffffff, 0x20171024, 0x19840730,
173                                            0x19831230};
174 
175   // TODO(terelius): Test extensions for legacy encoding, too.
176   RtpHeaderExtensionMap extension_map;
177   if (encoding_type_ != RtcEventLog::EncodingType::Legacy) {
178     extension_map = gen_.NewRtpHeaderExtensionMap(true);
179   }
180 
181   // Simulate `event_count_` RTP packets, with SSRCs assigned randomly
182   // out of the small pool above.
183   std::map<uint32_t, std::vector<std::unique_ptr<EventType>>> events_by_ssrc;
184   for (size_t i = 0; i < event_count_; ++i) {
185     const uint32_t ssrc = kSsrcPool[prng_.Rand(kSsrcPool.size() - 1)];
186     std::unique_ptr<EventType> event =
187         (events_by_ssrc[ssrc].empty() || !force_repeated_fields_)
188             ? NewRtpPacket<EventType>(ssrc, extension_map)
189             : events_by_ssrc[ssrc][0]->Copy();
190     history_.push_back(event->Copy());
191     events_by_ssrc[ssrc].emplace_back(std::move(event));
192   }
193 
194   // Encode and parse.
195   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
196   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
197 
198   // For each SSRC, make sure the RTP packets associated with it to have been
199   // correctly encoded and parsed.
200   for (auto it = events_by_ssrc.begin(); it != events_by_ssrc.end(); ++it) {
201     const uint32_t ssrc = it->first;
202     const auto& original_packets = it->second;
203     const std::vector<ParsedType>* parsed_rtp_packets =
204         GetRtpPacketsBySsrc<ParsedType>(&parsed_log_, ssrc);
205     ASSERT_NE(parsed_rtp_packets, nullptr);
206     ASSERT_EQ(original_packets.size(), parsed_rtp_packets->size());
207     for (size_t i = 0; i < original_packets.size(); ++i) {
208       verifier_.VerifyLoggedRtpPacket<EventType, ParsedType>(
209           *original_packets[i], (*parsed_rtp_packets)[i]);
210     }
211   }
212 }
213 
TEST_P(RtcEventLogEncoderTest,RtcEventAlrState)214 TEST_P(RtcEventLogEncoderTest, RtcEventAlrState) {
215   std::vector<std::unique_ptr<RtcEventAlrState>> events(event_count_);
216   for (size_t i = 0; i < event_count_; ++i) {
217     events[i] = (i == 0 || !force_repeated_fields_) ? gen_.NewAlrState()
218                                                     : events[0]->Copy();
219     history_.push_back(events[i]->Copy());
220   }
221 
222   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
223   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
224   const auto& alr_state_events = parsed_log_.alr_state_events();
225 
226   ASSERT_EQ(alr_state_events.size(), event_count_);
227   for (size_t i = 0; i < event_count_; ++i) {
228     verifier_.VerifyLoggedAlrStateEvent(*events[i], alr_state_events[i]);
229   }
230 }
231 
TEST_P(RtcEventLogEncoderTest,RtcEventRouteChange)232 TEST_P(RtcEventLogEncoderTest, RtcEventRouteChange) {
233   if (encoding_type_ == RtcEventLog::EncodingType::Legacy) {
234     return;
235   }
236   std::vector<std::unique_ptr<RtcEventRouteChange>> events(event_count_);
237   for (size_t i = 0; i < event_count_; ++i) {
238     events[i] = (i == 0 || !force_repeated_fields_) ? gen_.NewRouteChange()
239                                                     : events[0]->Copy();
240     history_.push_back(events[i]->Copy());
241   }
242 
243   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
244   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
245   const auto& route_change_events = parsed_log_.route_change_events();
246 
247   ASSERT_EQ(route_change_events.size(), event_count_);
248   for (size_t i = 0; i < event_count_; ++i) {
249     verifier_.VerifyLoggedRouteChangeEvent(*events[i], route_change_events[i]);
250   }
251 }
252 
TEST_P(RtcEventLogEncoderTest,RtcEventRemoteEstimate)253 TEST_P(RtcEventLogEncoderTest, RtcEventRemoteEstimate) {
254   std::vector<std::unique_ptr<RtcEventRemoteEstimate>> events(event_count_);
255   for (size_t i = 0; i < event_count_; ++i) {
256     events[i] = (i == 0 || !force_repeated_fields_)
257                     ? gen_.NewRemoteEstimate()
258                     : std::make_unique<RtcEventRemoteEstimate>(*events[0]);
259     history_.push_back(std::make_unique<RtcEventRemoteEstimate>(*events[i]));
260   }
261 
262   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
263   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
264   const auto& parsed_events = parsed_log_.remote_estimate_events();
265 
266   ASSERT_EQ(parsed_events.size(), event_count_);
267   for (size_t i = 0; i < event_count_; ++i) {
268     verifier_.VerifyLoggedRemoteEstimateEvent(*events[i], parsed_events[i]);
269   }
270 }
271 
TEST_P(RtcEventLogEncoderTest,RtcEventAudioNetworkAdaptationBitrate)272 TEST_P(RtcEventLogEncoderTest, RtcEventAudioNetworkAdaptationBitrate) {
273   std::vector<std::unique_ptr<RtcEventAudioNetworkAdaptation>> events(
274       event_count_);
275   for (size_t i = 0; i < event_count_; ++i) {
276     if (i == 0 || !force_repeated_fields_) {
277       auto runtime_config = std::make_unique<AudioEncoderRuntimeConfig>();
278       const int bitrate_bps = rtc::checked_cast<int>(
279           prng_.Rand(0, std::numeric_limits<int32_t>::max()));
280       runtime_config->bitrate_bps = bitrate_bps;
281       events[i] = std::make_unique<RtcEventAudioNetworkAdaptation>(
282           std::move(runtime_config));
283     } else {
284       events[i] = events[0]->Copy();
285     }
286   }
287   TestRtcEventAudioNetworkAdaptation(events);
288 }
289 
TEST_P(RtcEventLogEncoderTest,RtcEventAudioNetworkAdaptationFrameLength)290 TEST_P(RtcEventLogEncoderTest, RtcEventAudioNetworkAdaptationFrameLength) {
291   std::vector<std::unique_ptr<RtcEventAudioNetworkAdaptation>> events(
292       event_count_);
293   for (size_t i = 0; i < event_count_; ++i) {
294     if (i == 0 || !force_repeated_fields_) {
295       auto runtime_config = std::make_unique<AudioEncoderRuntimeConfig>();
296       const int frame_length_ms = prng_.Rand(1, 1000);
297       runtime_config->frame_length_ms = frame_length_ms;
298       events[i] = std::make_unique<RtcEventAudioNetworkAdaptation>(
299           std::move(runtime_config));
300     } else {
301       events[i] = events[0]->Copy();
302     }
303   }
304   TestRtcEventAudioNetworkAdaptation(events);
305 }
306 
TEST_P(RtcEventLogEncoderTest,RtcEventAudioNetworkAdaptationPacketLoss)307 TEST_P(RtcEventLogEncoderTest, RtcEventAudioNetworkAdaptationPacketLoss) {
308   std::vector<std::unique_ptr<RtcEventAudioNetworkAdaptation>> events(
309       event_count_);
310   for (size_t i = 0; i < event_count_; ++i) {
311     if (i == 0 || !force_repeated_fields_) {
312       // To simplify the test, we just check powers of two.
313       const float plr = std::pow(0.5f, prng_.Rand(1, 8));
314       auto runtime_config = std::make_unique<AudioEncoderRuntimeConfig>();
315       runtime_config->uplink_packet_loss_fraction = plr;
316       events[i] = std::make_unique<RtcEventAudioNetworkAdaptation>(
317           std::move(runtime_config));
318     } else {
319       events[i] = events[0]->Copy();
320     }
321   }
322   TestRtcEventAudioNetworkAdaptation(events);
323 }
324 
TEST_P(RtcEventLogEncoderTest,RtcEventAudioNetworkAdaptationFec)325 TEST_P(RtcEventLogEncoderTest, RtcEventAudioNetworkAdaptationFec) {
326   std::vector<std::unique_ptr<RtcEventAudioNetworkAdaptation>> events(
327       event_count_);
328   for (size_t i = 0; i < event_count_; ++i) {
329     if (i == 0 || !force_repeated_fields_) {
330       auto runtime_config = std::make_unique<AudioEncoderRuntimeConfig>();
331       runtime_config->enable_fec = prng_.Rand<bool>();
332       events[i] = std::make_unique<RtcEventAudioNetworkAdaptation>(
333           std::move(runtime_config));
334     } else {
335       events[i] = events[0]->Copy();
336     }
337   }
338   TestRtcEventAudioNetworkAdaptation(events);
339 }
340 
TEST_P(RtcEventLogEncoderTest,RtcEventAudioNetworkAdaptationDtx)341 TEST_P(RtcEventLogEncoderTest, RtcEventAudioNetworkAdaptationDtx) {
342   std::vector<std::unique_ptr<RtcEventAudioNetworkAdaptation>> events(
343       event_count_);
344   for (size_t i = 0; i < event_count_; ++i) {
345     if (i == 0 || !force_repeated_fields_) {
346       auto runtime_config = std::make_unique<AudioEncoderRuntimeConfig>();
347       runtime_config->enable_dtx = prng_.Rand<bool>();
348       events[i] = std::make_unique<RtcEventAudioNetworkAdaptation>(
349           std::move(runtime_config));
350     } else {
351       events[i] = events[0]->Copy();
352     }
353   }
354   TestRtcEventAudioNetworkAdaptation(events);
355 }
356 
TEST_P(RtcEventLogEncoderTest,RtcEventAudioNetworkAdaptationChannels)357 TEST_P(RtcEventLogEncoderTest, RtcEventAudioNetworkAdaptationChannels) {
358   std::vector<std::unique_ptr<RtcEventAudioNetworkAdaptation>> events(
359       event_count_);
360   for (size_t i = 0; i < event_count_; ++i) {
361     if (i == 0 || !force_repeated_fields_) {
362       auto runtime_config = std::make_unique<AudioEncoderRuntimeConfig>();
363       runtime_config->num_channels = prng_.Rand(1, 2);
364       events[i] = std::make_unique<RtcEventAudioNetworkAdaptation>(
365           std::move(runtime_config));
366     } else {
367       events[i] = events[0]->Copy();
368     }
369   }
370   TestRtcEventAudioNetworkAdaptation(events);
371 }
372 
TEST_P(RtcEventLogEncoderTest,RtcEventAudioNetworkAdaptationAll)373 TEST_P(RtcEventLogEncoderTest, RtcEventAudioNetworkAdaptationAll) {
374   std::vector<std::unique_ptr<RtcEventAudioNetworkAdaptation>> events(
375       event_count_);
376   for (size_t i = 0; i < event_count_; ++i) {
377     if (i == 0 || !force_repeated_fields_) {
378       auto runtime_config = std::make_unique<AudioEncoderRuntimeConfig>();
379       runtime_config->bitrate_bps = rtc::checked_cast<int>(
380           prng_.Rand(0, std::numeric_limits<int32_t>::max()));
381       runtime_config->frame_length_ms = prng_.Rand(1, 1000);
382       runtime_config->uplink_packet_loss_fraction =
383           std::pow(0.5f, prng_.Rand(1, 8));
384       runtime_config->enable_fec = prng_.Rand<bool>();
385       runtime_config->enable_dtx = prng_.Rand<bool>();
386       runtime_config->num_channels = prng_.Rand(1, 2);
387       events[i] = std::make_unique<RtcEventAudioNetworkAdaptation>(
388           std::move(runtime_config));
389     } else {
390       events[i] = events[0]->Copy();
391     }
392   }
393   TestRtcEventAudioNetworkAdaptation(events);
394 }
395 
TEST_P(RtcEventLogEncoderTest,RtcEventAudioPlayout)396 TEST_P(RtcEventLogEncoderTest, RtcEventAudioPlayout) {
397   // SSRCs will be randomly assigned out of this small pool, significant only
398   // in that it also covers such edge cases as SSRC = 0 and SSRC = 0xffffffff.
399   // The pool is intentionally small, so as to produce collisions.
400   const std::vector<uint32_t> kSsrcPool = {0x00000000, 0x12345678, 0xabcdef01,
401                                            0xffffffff, 0x20171024, 0x19840730,
402                                            0x19831230};
403 
404   std::map<uint32_t, std::vector<std::unique_ptr<RtcEventAudioPlayout>>>
405       original_events_by_ssrc;
406   for (size_t i = 0; i < event_count_; ++i) {
407     const uint32_t ssrc = kSsrcPool[prng_.Rand(kSsrcPool.size() - 1)];
408     std::unique_ptr<RtcEventAudioPlayout> event =
409         (original_events_by_ssrc[ssrc].empty() || !force_repeated_fields_)
410             ? gen_.NewAudioPlayout(ssrc)
411             : original_events_by_ssrc[ssrc][0]->Copy();
412     history_.push_back(event->Copy());
413     original_events_by_ssrc[ssrc].push_back(std::move(event));
414   }
415 
416   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
417   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
418 
419   const auto& parsed_playout_events_by_ssrc =
420       parsed_log_.audio_playout_events();
421 
422   // Same number of distinct SSRCs.
423   ASSERT_EQ(parsed_playout_events_by_ssrc.size(),
424             original_events_by_ssrc.size());
425 
426   for (auto& original_event_it : original_events_by_ssrc) {
427     const uint32_t ssrc = original_event_it.first;
428     const auto& original_playout_events = original_event_it.second;
429 
430     const auto& parsed_event_it = parsed_playout_events_by_ssrc.find(ssrc);
431     ASSERT_TRUE(parsed_event_it != parsed_playout_events_by_ssrc.end());
432     const auto& parsed_playout_events = parsed_event_it->second;
433 
434     // Same number playout events for the SSRC under examination.
435     ASSERT_EQ(original_playout_events.size(), parsed_playout_events.size());
436 
437     for (size_t i = 0; i < original_playout_events.size(); ++i) {
438       verifier_.VerifyLoggedAudioPlayoutEvent(*original_playout_events[i],
439                                               parsed_playout_events[i]);
440     }
441   }
442 }
443 
444 // TODO(eladalon/terelius): Test with multiple events in the batch.
TEST_P(RtcEventLogEncoderTest,RtcEventAudioReceiveStreamConfig)445 TEST_P(RtcEventLogEncoderTest, RtcEventAudioReceiveStreamConfig) {
446   uint32_t ssrc = prng_.Rand<uint32_t>();
447   RtpHeaderExtensionMap extensions = gen_.NewRtpHeaderExtensionMap();
448   std::unique_ptr<RtcEventAudioReceiveStreamConfig> event =
449       gen_.NewAudioReceiveStreamConfig(ssrc, extensions);
450   history_.push_back(event->Copy());
451 
452   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
453   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
454   const auto& audio_recv_configs = parsed_log_.audio_recv_configs();
455 
456   ASSERT_EQ(audio_recv_configs.size(), 1u);
457   verifier_.VerifyLoggedAudioRecvConfig(*event, audio_recv_configs[0]);
458 }
459 
460 // TODO(eladalon/terelius): Test with multiple events in the batch.
TEST_P(RtcEventLogEncoderTest,RtcEventAudioSendStreamConfig)461 TEST_P(RtcEventLogEncoderTest, RtcEventAudioSendStreamConfig) {
462   uint32_t ssrc = prng_.Rand<uint32_t>();
463   RtpHeaderExtensionMap extensions = gen_.NewRtpHeaderExtensionMap();
464   std::unique_ptr<RtcEventAudioSendStreamConfig> event =
465       gen_.NewAudioSendStreamConfig(ssrc, extensions);
466   history_.push_back(event->Copy());
467 
468   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
469   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
470   const auto& audio_send_configs = parsed_log_.audio_send_configs();
471 
472   ASSERT_EQ(audio_send_configs.size(), 1u);
473   verifier_.VerifyLoggedAudioSendConfig(*event, audio_send_configs[0]);
474 }
475 
TEST_P(RtcEventLogEncoderTest,RtcEventBweUpdateDelayBased)476 TEST_P(RtcEventLogEncoderTest, RtcEventBweUpdateDelayBased) {
477   std::vector<std::unique_ptr<RtcEventBweUpdateDelayBased>> events(
478       event_count_);
479   for (size_t i = 0; i < event_count_; ++i) {
480     events[i] = (i == 0 || !force_repeated_fields_)
481                     ? gen_.NewBweUpdateDelayBased()
482                     : events[0]->Copy();
483     history_.push_back(events[i]->Copy());
484   }
485 
486   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
487   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
488 
489   const auto& bwe_delay_updates = parsed_log_.bwe_delay_updates();
490   ASSERT_EQ(bwe_delay_updates.size(), event_count_);
491 
492   for (size_t i = 0; i < event_count_; ++i) {
493     verifier_.VerifyLoggedBweDelayBasedUpdate(*events[i], bwe_delay_updates[i]);
494   }
495 }
496 
TEST_P(RtcEventLogEncoderTest,RtcEventBweUpdateLossBased)497 TEST_P(RtcEventLogEncoderTest, RtcEventBweUpdateLossBased) {
498   std::vector<std::unique_ptr<RtcEventBweUpdateLossBased>> events(event_count_);
499   for (size_t i = 0; i < event_count_; ++i) {
500     events[i] = (i == 0 || !force_repeated_fields_)
501                     ? gen_.NewBweUpdateLossBased()
502                     : events[0]->Copy();
503     history_.push_back(events[i]->Copy());
504   }
505 
506   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
507   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
508 
509   const auto& bwe_loss_updates = parsed_log_.bwe_loss_updates();
510   ASSERT_EQ(bwe_loss_updates.size(), event_count_);
511 
512   for (size_t i = 0; i < event_count_; ++i) {
513     verifier_.VerifyLoggedBweLossBasedUpdate(*events[i], bwe_loss_updates[i]);
514   }
515 }
516 
TEST_P(RtcEventLogEncoderTest,RtcEventGenericPacketReceived)517 TEST_P(RtcEventLogEncoderTest, RtcEventGenericPacketReceived) {
518   if (encoding_type_ == RtcEventLog::EncodingType::Legacy) {
519     return;
520   }
521   std::vector<std::unique_ptr<RtcEventGenericPacketReceived>> events(
522       event_count_);
523   for (size_t i = 0; i < event_count_; ++i) {
524     events[i] = (i == 0 || !force_repeated_fields_)
525                     ? gen_.NewGenericPacketReceived()
526                     : events[0]->Copy();
527     history_.push_back(events[i]->Copy());
528   }
529 
530   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
531   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
532 
533   const auto& packets_received = parsed_log_.generic_packets_received();
534   ASSERT_EQ(packets_received.size(), event_count_);
535 
536   for (size_t i = 0; i < event_count_; ++i) {
537     verifier_.VerifyLoggedGenericPacketReceived(*events[i],
538                                                 packets_received[i]);
539   }
540 }
541 
TEST_P(RtcEventLogEncoderTest,RtcEventGenericPacketSent)542 TEST_P(RtcEventLogEncoderTest, RtcEventGenericPacketSent) {
543   if (encoding_type_ == RtcEventLog::EncodingType::Legacy) {
544     return;
545   }
546   std::vector<std::unique_ptr<RtcEventGenericPacketSent>> events(event_count_);
547   for (size_t i = 0; i < event_count_; ++i) {
548     events[i] = (i == 0 || !force_repeated_fields_)
549                     ? gen_.NewGenericPacketSent()
550                     : events[0]->Copy();
551     history_.push_back(events[i]->Copy());
552   }
553 
554   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
555   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
556 
557   const auto& packets_sent = parsed_log_.generic_packets_sent();
558   ASSERT_EQ(packets_sent.size(), event_count_);
559 
560   for (size_t i = 0; i < event_count_; ++i) {
561     verifier_.VerifyLoggedGenericPacketSent(*events[i], packets_sent[i]);
562   }
563 }
564 
TEST_P(RtcEventLogEncoderTest,RtcEventGenericAcksReceived)565 TEST_P(RtcEventLogEncoderTest, RtcEventGenericAcksReceived) {
566   if (encoding_type_ == RtcEventLog::EncodingType::Legacy) {
567     return;
568   }
569   std::vector<std::unique_ptr<RtcEventGenericAckReceived>> events(event_count_);
570   for (size_t i = 0; i < event_count_; ++i) {
571     events[i] = (i == 0 || !force_repeated_fields_)
572                     ? gen_.NewGenericAckReceived()
573                     : events[0]->Copy();
574     history_.push_back(events[i]->Copy());
575   }
576 
577   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
578   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
579 
580   const auto& decoded_events = parsed_log_.generic_acks_received();
581   ASSERT_EQ(decoded_events.size(), event_count_);
582 
583   for (size_t i = 0; i < event_count_; ++i) {
584     verifier_.VerifyLoggedGenericAckReceived(*events[i], decoded_events[i]);
585   }
586 }
587 
TEST_P(RtcEventLogEncoderTest,RtcEventDtlsTransportState)588 TEST_P(RtcEventLogEncoderTest, RtcEventDtlsTransportState) {
589   std::vector<std::unique_ptr<RtcEventDtlsTransportState>> events(event_count_);
590   for (size_t i = 0; i < event_count_; ++i) {
591     events[i] = (i == 0 || !force_repeated_fields_)
592                     ? gen_.NewDtlsTransportState()
593                     : events[0]->Copy();
594     history_.push_back(events[i]->Copy());
595   }
596 
597   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
598   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
599 
600   const auto& dtls_transport_states = parsed_log_.dtls_transport_states();
601   if (encoding_type_ == RtcEventLog::EncodingType::Legacy) {
602     ASSERT_EQ(dtls_transport_states.size(), 0u);
603     return;
604   }
605 
606   ASSERT_EQ(dtls_transport_states.size(), event_count_);
607   for (size_t i = 0; i < event_count_; ++i) {
608     verifier_.VerifyLoggedDtlsTransportState(*events[i],
609                                              dtls_transport_states[i]);
610   }
611 }
612 
TEST_P(RtcEventLogEncoderTest,RtcEventDtlsWritableState)613 TEST_P(RtcEventLogEncoderTest, RtcEventDtlsWritableState) {
614   std::vector<std::unique_ptr<RtcEventDtlsWritableState>> events(event_count_);
615   for (size_t i = 0; i < event_count_; ++i) {
616     events[i] = (i == 0 || !force_repeated_fields_)
617                     ? gen_.NewDtlsWritableState()
618                     : events[0]->Copy();
619     history_.push_back(events[i]->Copy());
620   }
621 
622   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
623   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
624 
625   const auto& dtls_writable_states = parsed_log_.dtls_writable_states();
626   if (encoding_type_ == RtcEventLog::EncodingType::Legacy) {
627     ASSERT_EQ(dtls_writable_states.size(), 0u);
628     return;
629   }
630 
631   ASSERT_EQ(dtls_writable_states.size(), event_count_);
632 
633   for (size_t i = 0; i < event_count_; ++i) {
634     verifier_.VerifyLoggedDtlsWritableState(*events[i],
635                                             dtls_writable_states[i]);
636   }
637 }
638 
TEST_P(RtcEventLogEncoderTest,RtcEventFrameDecoded)639 TEST_P(RtcEventLogEncoderTest, RtcEventFrameDecoded) {
640   // SSRCs will be randomly assigned out of this small pool, significant only
641   // in that it also covers such edge cases as SSRC = 0 and SSRC = 0xffffffff.
642   // The pool is intentionally small, so as to produce collisions.
643   const std::vector<uint32_t> kSsrcPool = {0x00000000, 0x12345678, 0xabcdef01,
644                                            0xffffffff, 0x20171024, 0x19840730,
645                                            0x19831230};
646 
647   std::map<uint32_t, std::vector<std::unique_ptr<RtcEventFrameDecoded>>>
648       original_events_by_ssrc;
649   for (size_t i = 0; i < event_count_; ++i) {
650     const uint32_t ssrc = kSsrcPool[prng_.Rand(kSsrcPool.size() - 1)];
651     std::unique_ptr<RtcEventFrameDecoded> event =
652         (original_events_by_ssrc[ssrc].empty() || !force_repeated_fields_)
653             ? gen_.NewFrameDecodedEvent(ssrc)
654             : original_events_by_ssrc[ssrc][0]->Copy();
655     history_.push_back(event->Copy());
656     original_events_by_ssrc[ssrc].push_back(std::move(event));
657   }
658 
659   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
660   auto status = parsed_log_.ParseString(encoded_);
661   if (!status.ok())
662     RTC_LOG(LS_ERROR) << status.message();
663   ASSERT_TRUE(status.ok());
664 
665   const auto& decoded_frames_by_ssrc = parsed_log_.decoded_frames();
666   if (encoding_type_ == RtcEventLog::EncodingType::Legacy) {
667     ASSERT_EQ(decoded_frames_by_ssrc.size(), 0u);
668     return;
669   }
670 
671   // Same number of distinct SSRCs.
672   ASSERT_EQ(decoded_frames_by_ssrc.size(), original_events_by_ssrc.size());
673 
674   for (const auto& original_event_it : original_events_by_ssrc) {
675     const uint32_t ssrc = original_event_it.first;
676     const std::vector<std::unique_ptr<RtcEventFrameDecoded>>& original_frames =
677         original_event_it.second;
678 
679     const auto& parsed_event_it = decoded_frames_by_ssrc.find(ssrc);
680     ASSERT_TRUE(parsed_event_it != decoded_frames_by_ssrc.end());
681     const std::vector<LoggedFrameDecoded>& parsed_frames =
682         parsed_event_it->second;
683 
684     // Same number events for the SSRC under examination.
685     ASSERT_EQ(original_frames.size(), parsed_frames.size());
686 
687     for (size_t i = 0; i < original_frames.size(); ++i) {
688       verifier_.VerifyLoggedFrameDecoded(*original_frames[i], parsed_frames[i]);
689     }
690   }
691 }
692 
693 // TODO(eladalon/terelius): Test with multiple events in the batch.
TEST_P(RtcEventLogEncoderTest,RtcEventIceCandidatePairConfig)694 TEST_P(RtcEventLogEncoderTest, RtcEventIceCandidatePairConfig) {
695   std::unique_ptr<RtcEventIceCandidatePairConfig> event =
696       gen_.NewIceCandidatePairConfig();
697   history_.push_back(event->Copy());
698 
699   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
700   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
701   const auto& ice_candidate_pair_configs =
702       parsed_log_.ice_candidate_pair_configs();
703 
704   ASSERT_EQ(ice_candidate_pair_configs.size(), 1u);
705   verifier_.VerifyLoggedIceCandidatePairConfig(*event,
706                                                ice_candidate_pair_configs[0]);
707 }
708 
709 // TODO(eladalon/terelius): Test with multiple events in the batch.
TEST_P(RtcEventLogEncoderTest,RtcEventIceCandidatePair)710 TEST_P(RtcEventLogEncoderTest, RtcEventIceCandidatePair) {
711   std::unique_ptr<RtcEventIceCandidatePair> event = gen_.NewIceCandidatePair();
712   history_.push_back(event->Copy());
713 
714   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
715   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
716   const auto& ice_candidate_pair_events =
717       parsed_log_.ice_candidate_pair_events();
718 
719   ASSERT_EQ(ice_candidate_pair_events.size(), 1u);
720   verifier_.VerifyLoggedIceCandidatePairEvent(*event,
721                                               ice_candidate_pair_events[0]);
722 }
723 
TEST_P(RtcEventLogEncoderTest,RtcEventLoggingStarted)724 TEST_P(RtcEventLogEncoderTest, RtcEventLoggingStarted) {
725   const int64_t timestamp_ms = prng_.Rand(1'000'000'000);
726   const int64_t utc_time_ms = prng_.Rand(1'000'000'000);
727 
728   // Overwrite the previously encoded LogStart event.
729   encoded_ = encoder_->EncodeLogStart(timestamp_ms * 1000, utc_time_ms * 1000);
730   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
731   const auto& start_log_events = parsed_log_.start_log_events();
732 
733   ASSERT_EQ(start_log_events.size(), 1u);
734   verifier_.VerifyLoggedStartEvent(timestamp_ms * 1000, utc_time_ms * 1000,
735                                    start_log_events[0]);
736 }
737 
TEST_P(RtcEventLogEncoderTest,RtcEventLoggingStopped)738 TEST_P(RtcEventLogEncoderTest, RtcEventLoggingStopped) {
739   const int64_t start_timestamp_ms = prng_.Rand(1'000'000'000);
740   const int64_t start_utc_time_ms = prng_.Rand(1'000'000'000);
741 
742   // Overwrite the previously encoded LogStart event.
743   encoded_ = encoder_->EncodeLogStart(start_timestamp_ms * 1000,
744                                       start_utc_time_ms * 1000);
745 
746   const int64_t stop_timestamp_ms =
747       prng_.Rand(start_timestamp_ms, 2'000'000'000);
748   encoded_ += encoder_->EncodeLogEnd(stop_timestamp_ms * 1000);
749   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
750   const auto& stop_log_events = parsed_log_.stop_log_events();
751 
752   ASSERT_EQ(stop_log_events.size(), 1u);
753   verifier_.VerifyLoggedStopEvent(stop_timestamp_ms * 1000, stop_log_events[0]);
754 }
755 
756 // TODO(eladalon/terelius): Test with multiple events in the batch.
TEST_P(RtcEventLogEncoderTest,RtcEventProbeClusterCreated)757 TEST_P(RtcEventLogEncoderTest, RtcEventProbeClusterCreated) {
758   std::unique_ptr<RtcEventProbeClusterCreated> event =
759       gen_.NewProbeClusterCreated();
760   history_.push_back(event->Copy());
761 
762   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
763   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
764   const auto& bwe_probe_cluster_created_events =
765       parsed_log_.bwe_probe_cluster_created_events();
766 
767   ASSERT_EQ(bwe_probe_cluster_created_events.size(), 1u);
768   verifier_.VerifyLoggedBweProbeClusterCreatedEvent(
769       *event, bwe_probe_cluster_created_events[0]);
770 }
771 
772 // TODO(eladalon/terelius): Test with multiple events in the batch.
TEST_P(RtcEventLogEncoderTest,RtcEventProbeResultFailure)773 TEST_P(RtcEventLogEncoderTest, RtcEventProbeResultFailure) {
774   std::unique_ptr<RtcEventProbeResultFailure> event =
775       gen_.NewProbeResultFailure();
776   history_.push_back(event->Copy());
777 
778   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
779   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
780   const auto& bwe_probe_failure_events = parsed_log_.bwe_probe_failure_events();
781 
782   ASSERT_EQ(bwe_probe_failure_events.size(), 1u);
783   verifier_.VerifyLoggedBweProbeFailureEvent(*event,
784                                              bwe_probe_failure_events[0]);
785 }
786 
787 // TODO(eladalon/terelius): Test with multiple events in the batch.
TEST_P(RtcEventLogEncoderTest,RtcEventProbeResultSuccess)788 TEST_P(RtcEventLogEncoderTest, RtcEventProbeResultSuccess) {
789   std::unique_ptr<RtcEventProbeResultSuccess> event =
790       gen_.NewProbeResultSuccess();
791   history_.push_back(event->Copy());
792 
793   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
794   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
795   const auto& bwe_probe_success_events = parsed_log_.bwe_probe_success_events();
796 
797   ASSERT_EQ(bwe_probe_success_events.size(), 1u);
798   verifier_.VerifyLoggedBweProbeSuccessEvent(*event,
799                                              bwe_probe_success_events[0]);
800 }
801 
TEST_P(RtcEventLogEncoderTest,RtcEventRtcpPacketIncoming)802 TEST_P(RtcEventLogEncoderTest, RtcEventRtcpPacketIncoming) {
803   if (force_repeated_fields_) {
804     // RTCP packets maybe delivered twice (once for audio and once for video).
805     // As a work around, we're removing duplicates in the parser.
806     return;
807   }
808 
809   std::vector<std::unique_ptr<RtcEventRtcpPacketIncoming>> events(event_count_);
810   for (size_t i = 0; i < event_count_; ++i) {
811     events[i] = (i == 0 || !force_repeated_fields_)
812                     ? gen_.NewRtcpPacketIncoming()
813                     : events[0]->Copy();
814     history_.push_back(events[i]->Copy());
815   }
816 
817   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
818   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
819 
820   const auto& incoming_rtcp_packets = parsed_log_.incoming_rtcp_packets();
821   ASSERT_EQ(incoming_rtcp_packets.size(), event_count_);
822 
823   for (size_t i = 0; i < event_count_; ++i) {
824     verifier_.VerifyLoggedRtcpPacketIncoming(*events[i],
825                                              incoming_rtcp_packets[i]);
826   }
827 }
828 
TEST_P(RtcEventLogEncoderTest,RtcEventRtcpPacketOutgoing)829 TEST_P(RtcEventLogEncoderTest, RtcEventRtcpPacketOutgoing) {
830   std::vector<std::unique_ptr<RtcEventRtcpPacketOutgoing>> events(event_count_);
831   for (size_t i = 0; i < event_count_; ++i) {
832     events[i] = (i == 0 || !force_repeated_fields_)
833                     ? gen_.NewRtcpPacketOutgoing()
834                     : events[0]->Copy();
835     history_.push_back(events[i]->Copy());
836   }
837 
838   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
839   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
840 
841   const auto& outgoing_rtcp_packets = parsed_log_.outgoing_rtcp_packets();
842   ASSERT_EQ(outgoing_rtcp_packets.size(), event_count_);
843 
844   for (size_t i = 0; i < event_count_; ++i) {
845     verifier_.VerifyLoggedRtcpPacketOutgoing(*events[i],
846                                              outgoing_rtcp_packets[i]);
847   }
848 }
849 
TEST_P(RtcEventLogEncoderTest,RtcEventRtcpReceiverReport)850 TEST_P(RtcEventLogEncoderTest, RtcEventRtcpReceiverReport) {
851   if (force_repeated_fields_) {
852     return;
853   }
854 
855   rtc::ScopedFakeClock fake_clock;
856   fake_clock.SetTime(Timestamp::Millis(prng_.Rand<uint32_t>()));
857 
858   for (auto direction : {kIncomingPacket, kOutgoingPacket}) {
859     std::vector<rtcp::ReceiverReport> events(event_count_);
860     std::vector<int64_t> timestamps_ms(event_count_);
861     for (size_t i = 0; i < event_count_; ++i) {
862       timestamps_ms[i] = rtc::TimeMillis();
863       events[i] = gen_.NewReceiverReport();
864       rtc::Buffer buffer = events[i].Build();
865       if (direction == kIncomingPacket) {
866         history_.push_back(
867             std::make_unique<RtcEventRtcpPacketIncoming>(buffer));
868       } else {
869         history_.push_back(
870             std::make_unique<RtcEventRtcpPacketOutgoing>(buffer));
871       }
872       fake_clock.AdvanceTime(TimeDelta::Millis(prng_.Rand(0, 1000)));
873     }
874 
875     encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
876     ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
877 
878     const auto& receiver_reports = parsed_log_.receiver_reports(direction);
879     ASSERT_EQ(receiver_reports.size(), event_count_);
880 
881     for (size_t i = 0; i < event_count_; ++i) {
882       verifier_.VerifyLoggedReceiverReport(timestamps_ms[i], events[i],
883                                            receiver_reports[i]);
884     }
885   }
886 }
887 
TEST_P(RtcEventLogEncoderTest,RtcEventRtcpSenderReport)888 TEST_P(RtcEventLogEncoderTest, RtcEventRtcpSenderReport) {
889   if (force_repeated_fields_) {
890     return;
891   }
892 
893   rtc::ScopedFakeClock fake_clock;
894   fake_clock.SetTime(Timestamp::Millis(prng_.Rand<uint32_t>()));
895 
896   for (auto direction : {kIncomingPacket, kOutgoingPacket}) {
897     std::vector<rtcp::SenderReport> events(event_count_);
898     std::vector<int64_t> timestamps_ms(event_count_);
899     for (size_t i = 0; i < event_count_; ++i) {
900       timestamps_ms[i] = rtc::TimeMillis();
901       events[i] = gen_.NewSenderReport();
902       rtc::Buffer buffer = events[i].Build();
903       if (direction == kIncomingPacket) {
904         history_.push_back(
905             std::make_unique<RtcEventRtcpPacketIncoming>(buffer));
906       } else {
907         history_.push_back(
908             std::make_unique<RtcEventRtcpPacketOutgoing>(buffer));
909       }
910       fake_clock.AdvanceTime(TimeDelta::Millis(prng_.Rand(0, 1000)));
911     }
912 
913     encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
914     ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
915 
916     const auto& sender_reports = parsed_log_.sender_reports(direction);
917     ASSERT_EQ(sender_reports.size(), event_count_);
918 
919     for (size_t i = 0; i < event_count_; ++i) {
920       verifier_.VerifyLoggedSenderReport(timestamps_ms[i], events[i],
921                                          sender_reports[i]);
922     }
923   }
924 }
925 
TEST_P(RtcEventLogEncoderTest,RtcEventRtcpExtendedReports)926 TEST_P(RtcEventLogEncoderTest, RtcEventRtcpExtendedReports) {
927   if (force_repeated_fields_) {
928     return;
929   }
930 
931   rtc::ScopedFakeClock fake_clock;
932   fake_clock.SetTime(Timestamp::Millis(prng_.Rand<uint32_t>()));
933 
934   for (auto direction : {kIncomingPacket, kOutgoingPacket}) {
935     std::vector<rtcp::ExtendedReports> events(event_count_);
936     std::vector<int64_t> timestamps_ms(event_count_);
937     for (size_t i = 0; i < event_count_; ++i) {
938       timestamps_ms[i] = rtc::TimeMillis();
939       events[i] = gen_.NewExtendedReports();
940       rtc::Buffer buffer = events[i].Build();
941       if (direction == kIncomingPacket) {
942         history_.push_back(
943             std::make_unique<RtcEventRtcpPacketIncoming>(buffer));
944       } else {
945         history_.push_back(
946             std::make_unique<RtcEventRtcpPacketOutgoing>(buffer));
947       }
948       fake_clock.AdvanceTime(TimeDelta::Millis(prng_.Rand(0, 1000)));
949     }
950 
951     encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
952     ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
953 
954     const auto& extended_reports = parsed_log_.extended_reports(direction);
955     ASSERT_EQ(extended_reports.size(), event_count_);
956 
957     for (size_t i = 0; i < event_count_; ++i) {
958       verifier_.VerifyLoggedExtendedReports(timestamps_ms[i], events[i],
959                                             extended_reports[i]);
960     }
961   }
962 }
963 
TEST_P(RtcEventLogEncoderTest,RtcEventRtcpFir)964 TEST_P(RtcEventLogEncoderTest, RtcEventRtcpFir) {
965   if (force_repeated_fields_) {
966     return;
967   }
968 
969   rtc::ScopedFakeClock fake_clock;
970   fake_clock.SetTime(Timestamp::Millis(prng_.Rand<uint32_t>()));
971 
972   for (auto direction : {kIncomingPacket, kOutgoingPacket}) {
973     std::vector<rtcp::Fir> events(event_count_);
974     std::vector<int64_t> timestamps_ms(event_count_);
975     for (size_t i = 0; i < event_count_; ++i) {
976       timestamps_ms[i] = rtc::TimeMillis();
977       events[i] = gen_.NewFir();
978       rtc::Buffer buffer = events[i].Build();
979       if (direction == kIncomingPacket) {
980         history_.push_back(
981             std::make_unique<RtcEventRtcpPacketIncoming>(buffer));
982       } else {
983         history_.push_back(
984             std::make_unique<RtcEventRtcpPacketOutgoing>(buffer));
985       }
986       fake_clock.AdvanceTime(TimeDelta::Millis(prng_.Rand(0, 1000)));
987     }
988 
989     encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
990     ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
991 
992     const auto& firs = parsed_log_.firs(direction);
993     ASSERT_EQ(firs.size(), event_count_);
994 
995     for (size_t i = 0; i < event_count_; ++i) {
996       verifier_.VerifyLoggedFir(timestamps_ms[i], events[i], firs[i]);
997     }
998   }
999 }
1000 
TEST_P(RtcEventLogEncoderTest,RtcEventRtcpPli)1001 TEST_P(RtcEventLogEncoderTest, RtcEventRtcpPli) {
1002   if (force_repeated_fields_) {
1003     return;
1004   }
1005 
1006   rtc::ScopedFakeClock fake_clock;
1007   fake_clock.SetTime(Timestamp::Millis(prng_.Rand<uint32_t>()));
1008 
1009   for (auto direction : {kIncomingPacket, kOutgoingPacket}) {
1010     std::vector<rtcp::Pli> events(event_count_);
1011     std::vector<int64_t> timestamps_ms(event_count_);
1012     for (size_t i = 0; i < event_count_; ++i) {
1013       timestamps_ms[i] = rtc::TimeMillis();
1014       events[i] = gen_.NewPli();
1015       rtc::Buffer buffer = events[i].Build();
1016       if (direction == kIncomingPacket) {
1017         history_.push_back(
1018             std::make_unique<RtcEventRtcpPacketIncoming>(buffer));
1019       } else {
1020         history_.push_back(
1021             std::make_unique<RtcEventRtcpPacketOutgoing>(buffer));
1022       }
1023       fake_clock.AdvanceTime(TimeDelta::Millis(prng_.Rand(0, 1000)));
1024     }
1025 
1026     encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
1027     ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
1028 
1029     const auto& plis = parsed_log_.plis(direction);
1030     ASSERT_EQ(plis.size(), event_count_);
1031 
1032     for (size_t i = 0; i < event_count_; ++i) {
1033       verifier_.VerifyLoggedPli(timestamps_ms[i], events[i], plis[i]);
1034     }
1035   }
1036 }
1037 
TEST_P(RtcEventLogEncoderTest,RtcEventRtcpBye)1038 TEST_P(RtcEventLogEncoderTest, RtcEventRtcpBye) {
1039   if (force_repeated_fields_) {
1040     return;
1041   }
1042 
1043   rtc::ScopedFakeClock fake_clock;
1044   fake_clock.SetTime(Timestamp::Millis(prng_.Rand<uint32_t>()));
1045 
1046   for (auto direction : {kIncomingPacket, kOutgoingPacket}) {
1047     std::vector<rtcp::Bye> events(event_count_);
1048     std::vector<int64_t> timestamps_ms(event_count_);
1049     for (size_t i = 0; i < event_count_; ++i) {
1050       timestamps_ms[i] = rtc::TimeMillis();
1051       events[i] = gen_.NewBye();
1052       rtc::Buffer buffer = events[i].Build();
1053       if (direction == kIncomingPacket) {
1054         history_.push_back(
1055             std::make_unique<RtcEventRtcpPacketIncoming>(buffer));
1056       } else {
1057         history_.push_back(
1058             std::make_unique<RtcEventRtcpPacketOutgoing>(buffer));
1059       }
1060       fake_clock.AdvanceTime(TimeDelta::Millis(prng_.Rand(0, 1000)));
1061     }
1062 
1063     encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
1064     ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
1065 
1066     const auto& byes = parsed_log_.byes(direction);
1067     ASSERT_EQ(byes.size(), event_count_);
1068 
1069     for (size_t i = 0; i < event_count_; ++i) {
1070       verifier_.VerifyLoggedBye(timestamps_ms[i], events[i], byes[i]);
1071     }
1072   }
1073 }
1074 
TEST_P(RtcEventLogEncoderTest,RtcEventRtcpNack)1075 TEST_P(RtcEventLogEncoderTest, RtcEventRtcpNack) {
1076   if (force_repeated_fields_) {
1077     return;
1078   }
1079 
1080   rtc::ScopedFakeClock fake_clock;
1081   fake_clock.SetTime(Timestamp::Millis(prng_.Rand<uint32_t>()));
1082 
1083   for (auto direction : {kIncomingPacket, kOutgoingPacket}) {
1084     std::vector<rtcp::Nack> events(event_count_);
1085     std::vector<int64_t> timestamps_ms(event_count_);
1086     for (size_t i = 0; i < event_count_; ++i) {
1087       timestamps_ms[i] = rtc::TimeMillis();
1088       events[i] = gen_.NewNack();
1089       rtc::Buffer buffer = events[i].Build();
1090       if (direction == kIncomingPacket) {
1091         history_.push_back(
1092             std::make_unique<RtcEventRtcpPacketIncoming>(buffer));
1093       } else {
1094         history_.push_back(
1095             std::make_unique<RtcEventRtcpPacketOutgoing>(buffer));
1096       }
1097       fake_clock.AdvanceTime(TimeDelta::Millis(prng_.Rand(0, 1000)));
1098     }
1099 
1100     encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
1101     ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
1102 
1103     const auto& nacks = parsed_log_.nacks(direction);
1104     ASSERT_EQ(nacks.size(), event_count_);
1105 
1106     for (size_t i = 0; i < event_count_; ++i) {
1107       verifier_.VerifyLoggedNack(timestamps_ms[i], events[i], nacks[i]);
1108     }
1109   }
1110 }
1111 
TEST_P(RtcEventLogEncoderTest,RtcEventRtcpRemb)1112 TEST_P(RtcEventLogEncoderTest, RtcEventRtcpRemb) {
1113   if (force_repeated_fields_) {
1114     return;
1115   }
1116 
1117   rtc::ScopedFakeClock fake_clock;
1118   fake_clock.SetTime(Timestamp::Millis(prng_.Rand<uint32_t>()));
1119 
1120   for (auto direction : {kIncomingPacket, kOutgoingPacket}) {
1121     std::vector<rtcp::Remb> events(event_count_);
1122     std::vector<int64_t> timestamps_ms(event_count_);
1123     for (size_t i = 0; i < event_count_; ++i) {
1124       timestamps_ms[i] = rtc::TimeMillis();
1125       events[i] = gen_.NewRemb();
1126       rtc::Buffer buffer = events[i].Build();
1127       if (direction == kIncomingPacket) {
1128         history_.push_back(
1129             std::make_unique<RtcEventRtcpPacketIncoming>(buffer));
1130       } else {
1131         history_.push_back(
1132             std::make_unique<RtcEventRtcpPacketOutgoing>(buffer));
1133       }
1134       fake_clock.AdvanceTime(TimeDelta::Millis(prng_.Rand(0, 1000)));
1135     }
1136 
1137     encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
1138     ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
1139 
1140     const auto& rembs = parsed_log_.rembs(direction);
1141     ASSERT_EQ(rembs.size(), event_count_);
1142 
1143     for (size_t i = 0; i < event_count_; ++i) {
1144       verifier_.VerifyLoggedRemb(timestamps_ms[i], events[i], rembs[i]);
1145     }
1146   }
1147 }
1148 
TEST_P(RtcEventLogEncoderTest,RtcEventRtcpTransportFeedback)1149 TEST_P(RtcEventLogEncoderTest, RtcEventRtcpTransportFeedback) {
1150   if (force_repeated_fields_) {
1151     return;
1152   }
1153 
1154   rtc::ScopedFakeClock fake_clock;
1155   fake_clock.SetTime(Timestamp::Millis(prng_.Rand<uint32_t>()));
1156 
1157   for (auto direction : {kIncomingPacket, kOutgoingPacket}) {
1158     std::vector<rtcp::TransportFeedback> events;
1159     events.reserve(event_count_);
1160     std::vector<int64_t> timestamps_ms(event_count_);
1161     for (size_t i = 0; i < event_count_; ++i) {
1162       timestamps_ms[i] = rtc::TimeMillis();
1163       events.emplace_back(gen_.NewTransportFeedback());
1164       rtc::Buffer buffer = events[i].Build();
1165       if (direction == kIncomingPacket) {
1166         history_.push_back(
1167             std::make_unique<RtcEventRtcpPacketIncoming>(buffer));
1168       } else {
1169         history_.push_back(
1170             std::make_unique<RtcEventRtcpPacketOutgoing>(buffer));
1171       }
1172       fake_clock.AdvanceTime(TimeDelta::Millis(prng_.Rand(0, 1000)));
1173     }
1174 
1175     encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
1176     ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
1177 
1178     const auto& transport_feedbacks =
1179         parsed_log_.transport_feedbacks(direction);
1180     ASSERT_EQ(transport_feedbacks.size(), event_count_);
1181 
1182     for (size_t i = 0; i < event_count_; ++i) {
1183       verifier_.VerifyLoggedTransportFeedback(timestamps_ms[i], events[i],
1184                                               transport_feedbacks[i]);
1185     }
1186   }
1187 }
1188 
TEST_P(RtcEventLogEncoderTest,RtcEventRtcpLossNotification)1189 TEST_P(RtcEventLogEncoderTest, RtcEventRtcpLossNotification) {
1190   if (force_repeated_fields_) {
1191     return;
1192   }
1193 
1194   rtc::ScopedFakeClock fake_clock;
1195   fake_clock.SetTime(Timestamp::Millis(prng_.Rand<uint32_t>()));
1196 
1197   for (auto direction : {kIncomingPacket, kOutgoingPacket}) {
1198     std::vector<rtcp::LossNotification> events;
1199     events.reserve(event_count_);
1200     std::vector<int64_t> timestamps_ms(event_count_);
1201     for (size_t i = 0; i < event_count_; ++i) {
1202       timestamps_ms[i] = rtc::TimeMillis();
1203       events.emplace_back(gen_.NewLossNotification());
1204       rtc::Buffer buffer = events[i].Build();
1205       if (direction == kIncomingPacket) {
1206         history_.push_back(
1207             std::make_unique<RtcEventRtcpPacketIncoming>(buffer));
1208       } else {
1209         history_.push_back(
1210             std::make_unique<RtcEventRtcpPacketOutgoing>(buffer));
1211       }
1212       fake_clock.AdvanceTime(TimeDelta::Millis(prng_.Rand(0, 1000)));
1213     }
1214 
1215     encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
1216     ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
1217 
1218     const auto& loss_notifications = parsed_log_.loss_notifications(direction);
1219     ASSERT_EQ(loss_notifications.size(), event_count_);
1220 
1221     for (size_t i = 0; i < event_count_; ++i) {
1222       verifier_.VerifyLoggedLossNotification(timestamps_ms[i], events[i],
1223                                              loss_notifications[i]);
1224     }
1225   }
1226 }
1227 
TEST_P(RtcEventLogEncoderTest,RtcEventRtpPacketIncoming)1228 TEST_P(RtcEventLogEncoderTest, RtcEventRtpPacketIncoming) {
1229   TestRtpPackets<RtcEventRtpPacketIncoming, LoggedRtpPacketIncoming>();
1230 }
1231 
TEST_P(RtcEventLogEncoderTest,RtcEventRtpPacketOutgoing)1232 TEST_P(RtcEventLogEncoderTest, RtcEventRtpPacketOutgoing) {
1233   TestRtpPackets<RtcEventRtpPacketOutgoing, LoggedRtpPacketOutgoing>();
1234 }
1235 
1236 // TODO(eladalon/terelius): Test with multiple events in the batch.
TEST_P(RtcEventLogEncoderTest,RtcEventVideoReceiveStreamConfig)1237 TEST_P(RtcEventLogEncoderTest, RtcEventVideoReceiveStreamConfig) {
1238   uint32_t ssrc = prng_.Rand<uint32_t>();
1239   RtpHeaderExtensionMap extensions = gen_.NewRtpHeaderExtensionMap();
1240   std::unique_ptr<RtcEventVideoReceiveStreamConfig> event =
1241       gen_.NewVideoReceiveStreamConfig(ssrc, extensions);
1242   history_.push_back(event->Copy());
1243 
1244   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
1245   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
1246   const auto& video_recv_configs = parsed_log_.video_recv_configs();
1247 
1248   ASSERT_EQ(video_recv_configs.size(), 1u);
1249   verifier_.VerifyLoggedVideoRecvConfig(*event, video_recv_configs[0]);
1250 }
1251 
1252 // TODO(eladalon/terelius): Test with multiple events in the batch.
TEST_P(RtcEventLogEncoderTest,RtcEventVideoSendStreamConfig)1253 TEST_P(RtcEventLogEncoderTest, RtcEventVideoSendStreamConfig) {
1254   uint32_t ssrc = prng_.Rand<uint32_t>();
1255   RtpHeaderExtensionMap extensions = gen_.NewRtpHeaderExtensionMap();
1256   std::unique_ptr<RtcEventVideoSendStreamConfig> event =
1257       gen_.NewVideoSendStreamConfig(ssrc, extensions);
1258   history_.push_back(event->Copy());
1259 
1260   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
1261   ASSERT_TRUE(parsed_log_.ParseString(encoded_).ok());
1262   const auto& video_send_configs = parsed_log_.video_send_configs();
1263 
1264   ASSERT_EQ(video_send_configs.size(), 1u);
1265   verifier_.VerifyLoggedVideoSendConfig(*event, video_send_configs[0]);
1266 }
1267 
1268 INSTANTIATE_TEST_SUITE_P(
1269     RandomSeeds,
1270     RtcEventLogEncoderTest,
1271     ::testing::Combine(/* Random seed*: */ ::testing::Values(1, 2, 3, 4, 5),
1272                        /* Encoding: */
1273                        ::testing::Values(RtcEventLog::EncodingType::Legacy,
1274                                          RtcEventLog::EncodingType::NewFormat),
1275                        /* Event count: */ ::testing::Values(1, 2, 10, 100),
1276                        /* Repeated fields: */ ::testing::Bool()));
1277 
1278 class RtcEventLogEncoderSimpleTest
1279     : public ::testing::TestWithParam<RtcEventLog::EncodingType> {
1280  protected:
RtcEventLogEncoderSimpleTest()1281   RtcEventLogEncoderSimpleTest() : encoding_type_(GetParam()) {
1282     switch (encoding_type_) {
1283       case RtcEventLog::EncodingType::Legacy:
1284         encoder_ = std::make_unique<RtcEventLogEncoderLegacy>();
1285         break;
1286       case RtcEventLog::EncodingType::NewFormat:
1287         encoder_ = std::make_unique<RtcEventLogEncoderNewFormat>();
1288         break;
1289       case RtcEventLog::EncodingType::ProtoFree:
1290         encoder_ = std::make_unique<RtcEventLogEncoderV3>();
1291         break;
1292     }
1293     encoded_ =
1294         encoder_->EncodeLogStart(rtc::TimeMillis(), rtc::TimeUTCMillis());
1295   }
1296   ~RtcEventLogEncoderSimpleTest() override = default;
1297 
1298   std::deque<std::unique_ptr<RtcEvent>> history_;
1299   std::unique_ptr<RtcEventLogEncoder> encoder_;
1300   ParsedRtcEventLog parsed_log_;
1301   const RtcEventLog::EncodingType encoding_type_;
1302   std::string encoded_;
1303 };
1304 
TEST_P(RtcEventLogEncoderSimpleTest,RtcEventLargeCompoundRtcpPacketIncoming)1305 TEST_P(RtcEventLogEncoderSimpleTest, RtcEventLargeCompoundRtcpPacketIncoming) {
1306   // Create a compound packet containing multiple Bye messages.
1307   rtc::Buffer packet;
1308   size_t index = 0;
1309   for (int i = 0; i < 8; i++) {
1310     rtcp::Bye bye;
1311     std::string reason(255, 'a');  // Add some arbitrary data.
1312     bye.SetReason(reason);
1313     bye.SetSenderSsrc(0x12345678);
1314     packet.SetSize(packet.size() + bye.BlockLength());
1315     bool created =
1316         bye.Create(packet.data(), &index, packet.capacity(), nullptr);
1317     ASSERT_TRUE(created);
1318     ASSERT_EQ(index, packet.size());
1319   }
1320 
1321   EXPECT_GT(packet.size(), static_cast<size_t>(IP_PACKET_SIZE));
1322   auto event = std::make_unique<RtcEventRtcpPacketIncoming>(packet);
1323   history_.push_back(event->Copy());
1324   encoded_ += encoder_->EncodeBatch(history_.begin(), history_.end());
1325 
1326   ParsedRtcEventLog::ParseStatus status = parsed_log_.ParseString(encoded_);
1327   ASSERT_TRUE(status.ok()) << status.message();
1328 
1329   const auto& incoming_rtcp_packets = parsed_log_.incoming_rtcp_packets();
1330   ASSERT_EQ(incoming_rtcp_packets.size(), 1u);
1331   ASSERT_EQ(incoming_rtcp_packets[0].rtcp.raw_data.size(), packet.size());
1332   EXPECT_EQ(memcmp(incoming_rtcp_packets[0].rtcp.raw_data.data(), packet.data(),
1333                    packet.size()),
1334             0);
1335 }
1336 
1337 INSTANTIATE_TEST_SUITE_P(
1338     LargeCompoundRtcp,
1339     RtcEventLogEncoderSimpleTest,
1340     ::testing::Values(RtcEventLog::EncodingType::Legacy,
1341                       RtcEventLog::EncodingType::NewFormat));
1342 
1343 }  // namespace webrtc
1344