1 // Copyright 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 // This test generate synthetic data. For audio it's a sinusoid waveform with
6 // frequency kSoundFrequency and different amplitudes. For video it's a pattern
7 // that is shifting by one pixel per frame, each pixels neighbors right and down
8 // is this pixels value +1, since the pixel value is 8 bit it will wrap
9 // frequently within the image. Visually this will create diagonally color bands
10 // that moves across the screen
16 #include "base/bind.h"
17 #include "base/bind_helpers.h"
18 #include "base/test/simple_test_tick_clock.h"
19 #include "base/time/tick_clock.h"
20 #include "media/base/video_frame.h"
21 #include "media/cast/cast_config.h"
22 #include "media/cast/cast_environment.h"
23 #include "media/cast/cast_receiver.h"
24 #include "media/cast/cast_sender.h"
25 #include "media/cast/test/audio_utility.h"
26 #include "media/cast/test/crypto_utility.h"
27 #include "media/cast/test/fake_task_runner.h"
28 #include "media/cast/test/video_utility.h"
29 #include "media/cast/transport/cast_transport_config.h"
30 #include "media/cast/transport/cast_transport_defines.h"
31 #include "media/cast/transport/cast_transport_sender.h"
32 #include "media/cast/transport/cast_transport_sender_impl.h"
33 #include "testing/gtest/include/gtest/gtest.h"
38 static const int64 kStartMillisecond = GG_INT64_C(1245);
39 static const int kAudioChannels = 2;
40 static const double kSoundFrequency = 314.15926535897; // Freq of sine wave.
41 static const float kSoundVolume = 0.5f;
42 static const int kVideoWidth = 1280;
43 static const int kVideoHeight = 720;
44 static const int kCommonRtpHeaderLength = 12;
45 static const uint8 kCastReferenceFrameIdBitReset = 0xDF; // Mask is 0x40.
47 // Since the video encoded and decoded an error will be introduced; when
48 // comparing individual pixels the error can be quite large; we allow a PSNR of
49 // at least |kVideoAcceptedPSNR|.
50 static const double kVideoAcceptedPSNR = 38.0;
52 // The tests are commonly implemented with |kFrameTimerMs| RunTask function;
53 // a normal video is 30 fps hence the 33 ms between frames.
54 static const int kFrameTimerMs = 33;
56 // The packets pass through the pacer which can delay the beginning of the
57 // frame by 10 ms if there is packets belonging to the previous frame being
59 static const int kTimerErrorMs = 15;
62 // Dummy callback function that does nothing except to accept ownership of
63 // |audio_bus| for destruction.
64 void OwnThatAudioBus(scoped_ptr<AudioBus> audio_bus) {
66 void UpdateCastTransportStatus(transport::CastTransportStatus status) {
67 EXPECT_EQ(status, transport::TRANSPORT_INITIALIZED);
71 // Class that sends the packet direct from sender into the receiver with the
72 // ability to drop packets between the two.
73 class LoopBackTransport : public transport::PacketSender {
75 explicit LoopBackTransport(scoped_refptr<CastEnvironment> cast_environment)
76 : packet_receiver_(NULL),
78 drop_packets_belonging_to_odd_frames_(false),
79 reset_reference_frame_id_(false),
80 cast_environment_(cast_environment) {
83 void SetPacketReceiver(transport::PacketReceiver* packet_receiver) {
84 DCHECK(packet_receiver);
85 packet_receiver_ = packet_receiver;
88 virtual bool SendPacket(const Packet& packet) OVERRIDE {
89 DCHECK(packet_receiver_);
90 DCHECK(cast_environment_->CurrentlyOn(CastEnvironment::MAIN));
91 if (!send_packets_) return false;
93 if (drop_packets_belonging_to_odd_frames_) {
94 uint32 frame_id = packet[13];
95 if (frame_id % 2 == 1) return true;
98 uint8* packet_copy = new uint8[packet.size()];
99 memcpy(packet_copy, packet.data(), packet.size());
101 if (reset_reference_frame_id_) {
102 // Reset the is_reference bit in the cast header.
103 packet_copy[kCommonRtpHeaderLength] &= kCastReferenceFrameIdBitReset;
105 packet_receiver_->ReceivedPacket(packet_copy, packet.size(),
106 base::Bind(transport::PacketReceiver::DeletePacket, packet_copy));
110 void SetSendPackets(bool send_packets) {
111 send_packets_ = send_packets;
114 void DropAllPacketsBelongingToOddFrames() {
115 drop_packets_belonging_to_odd_frames_ = true;
118 void AlwaysResetReferenceFrameId() {
119 reset_reference_frame_id_ = true;
123 transport::PacketReceiver* packet_receiver_;
125 bool drop_packets_belonging_to_odd_frames_;
126 bool reset_reference_frame_id_;
127 scoped_refptr<CastEnvironment> cast_environment_;
130 // Class that verifies the audio frames coming out of the receiver.
131 class TestReceiverAudioCallback :
132 public base::RefCountedThreadSafe<TestReceiverAudioCallback> {
134 struct ExpectedAudioFrame {
135 PcmAudioFrame audio_frame;
137 base::TimeTicks record_time;
140 TestReceiverAudioCallback()
143 void SetExpectedSamplingFrequency(int expected_sampling_frequency) {
144 expected_sampling_frequency_ = expected_sampling_frequency;
147 void AddExpectedResult(scoped_ptr<PcmAudioFrame> audio_frame,
148 int expected_num_10ms_blocks,
149 const base::TimeTicks& record_time) {
150 ExpectedAudioFrame expected_audio_frame;
151 expected_audio_frame.audio_frame = *audio_frame;
152 expected_audio_frame.num_10ms_blocks = expected_num_10ms_blocks;
153 expected_audio_frame.record_time = record_time;
154 expected_frame_.push_back(expected_audio_frame);
157 void IgnoreAudioFrame(scoped_ptr<PcmAudioFrame> audio_frame,
158 const base::TimeTicks& playout_time) {}
160 // Check the audio frame parameters but not the audio samples.
161 void CheckBasicAudioFrame(const scoped_ptr<PcmAudioFrame>& audio_frame,
162 const base::TimeTicks& playout_time) {
163 EXPECT_FALSE(expected_frame_.empty()); // Test for bug in test code.
164 ExpectedAudioFrame expected_audio_frame = expected_frame_.front();
165 EXPECT_EQ(audio_frame->channels, kAudioChannels);
166 EXPECT_EQ(audio_frame->frequency, expected_sampling_frequency_);
167 EXPECT_EQ(static_cast<int>(audio_frame->samples.size()),
168 expected_audio_frame.num_10ms_blocks * kAudioChannels *
169 expected_sampling_frequency_ / 100);
171 const base::TimeTicks upper_bound = expected_audio_frame.record_time +
172 base::TimeDelta::FromMilliseconds(kDefaultRtpMaxDelayMs +
174 EXPECT_GE(upper_bound, playout_time)
175 << "playout_time - upper_bound == "
176 << (playout_time - upper_bound).InMicroseconds() << " usec";
177 EXPECT_LT(expected_audio_frame.record_time, playout_time)
178 << "playout_time - expected == "
179 << (playout_time - expected_audio_frame.record_time).InMilliseconds()
182 EXPECT_EQ(audio_frame->samples.size(),
183 expected_audio_frame.audio_frame.samples.size());
186 void CheckPcmAudioFrame(scoped_ptr<PcmAudioFrame> audio_frame,
187 const base::TimeTicks& playout_time) {
190 CheckBasicAudioFrame(audio_frame, playout_time);
191 ExpectedAudioFrame expected_audio_frame = expected_frame_.front();
192 expected_frame_.pop_front();
193 if (audio_frame->samples.size() == 0) return; // No more checks needed.
195 EXPECT_NEAR(CountZeroCrossings(expected_audio_frame.audio_frame.samples),
196 CountZeroCrossings(audio_frame->samples),
200 void CheckCodedPcmAudioFrame(
201 scoped_ptr<transport::EncodedAudioFrame> audio_frame,
202 const base::TimeTicks& playout_time) {
205 EXPECT_FALSE(expected_frame_.empty()); // Test for bug in test code.
206 ExpectedAudioFrame expected_audio_frame = expected_frame_.front();
207 expected_frame_.pop_front();
209 EXPECT_EQ(static_cast<int>(audio_frame->data.size()),
210 2 * kAudioChannels * expected_sampling_frequency_ / 100);
212 base::TimeDelta time_since_recording =
213 playout_time - expected_audio_frame.record_time;
215 EXPECT_LE(time_since_recording, base::TimeDelta::FromMilliseconds(
216 kDefaultRtpMaxDelayMs + kTimerErrorMs));
218 EXPECT_LT(expected_audio_frame.record_time, playout_time);
219 if (audio_frame->data.size() == 0) return; // No more checks needed.
221 // We need to convert our "coded" audio frame to our raw format.
222 std::vector<int16> output_audio_samples;
223 size_t number_of_samples = audio_frame->data.size() / 2;
225 for (size_t i = 0; i < number_of_samples; ++i) {
227 static_cast<uint8>(audio_frame->data[1 + i * sizeof(uint16)]) +
228 (static_cast<uint16>(audio_frame->data[i * sizeof(uint16)]) << 8);
229 output_audio_samples.push_back(static_cast<int16>(sample));
232 EXPECT_NEAR(CountZeroCrossings(expected_audio_frame.audio_frame.samples),
233 CountZeroCrossings(output_audio_samples),
237 int number_times_called() const {
242 virtual ~TestReceiverAudioCallback() {}
245 friend class base::RefCountedThreadSafe<TestReceiverAudioCallback>;
248 int expected_sampling_frequency_;
249 std::list<ExpectedAudioFrame> expected_frame_;
252 // Class that verifies the video frames coming out of the receiver.
253 class TestReceiverVideoCallback :
254 public base::RefCountedThreadSafe<TestReceiverVideoCallback> {
256 struct ExpectedVideoFrame {
260 base::TimeTicks capture_time;
263 TestReceiverVideoCallback()
266 void AddExpectedResult(int start_value,
269 const base::TimeTicks& capture_time) {
270 ExpectedVideoFrame expected_video_frame;
271 expected_video_frame.start_value = start_value;
272 expected_video_frame.capture_time = capture_time;
273 expected_video_frame.width = width;
274 expected_video_frame.height = height;
275 expected_frame_.push_back(expected_video_frame);
278 void CheckVideoFrame(const scoped_refptr<media::VideoFrame>& video_frame,
279 const base::TimeTicks& render_time) {
282 EXPECT_FALSE(expected_frame_.empty()); // Test for bug in test code.
283 ExpectedVideoFrame expected_video_frame = expected_frame_.front();
284 expected_frame_.pop_front();
286 base::TimeDelta time_since_capture =
287 render_time - expected_video_frame.capture_time;
288 const base::TimeDelta upper_bound = base::TimeDelta::FromMilliseconds(
289 kDefaultRtpMaxDelayMs + kTimerErrorMs);
291 EXPECT_GE(upper_bound, time_since_capture)
292 << "time_since_capture - upper_bound == "
293 << (time_since_capture - upper_bound).InMilliseconds() << " mS";
294 EXPECT_LE(expected_video_frame.capture_time, render_time);
295 EXPECT_EQ(expected_video_frame.width, video_frame->coded_size().width());
296 EXPECT_EQ(expected_video_frame.height, video_frame->coded_size().height());
298 gfx::Size size(expected_video_frame.width, expected_video_frame.height);
299 scoped_refptr<media::VideoFrame> expected_I420_frame =
300 media::VideoFrame::CreateFrame(
301 VideoFrame::I420, size, gfx::Rect(size), size, base::TimeDelta());
302 PopulateVideoFrame(expected_I420_frame, expected_video_frame.start_value);
304 EXPECT_GE(I420PSNR(expected_I420_frame, video_frame), kVideoAcceptedPSNR);
307 int number_times_called() { return num_called_;}
310 virtual ~TestReceiverVideoCallback() {}
313 friend class base::RefCountedThreadSafe<TestReceiverVideoCallback>;
316 std::list<ExpectedVideoFrame> expected_frame_;
319 CastLoggingConfig EnableCastLoggingConfig(bool sender) {
320 CastLoggingConfig config(sender);
321 config.enable_raw_data_collection = true;
322 config.enable_stats_data_collection = true;
325 // The actual test class, generate synthetic data for both audio and video and
326 // send those through the sender and receiver and analyzes the result.
327 class End2EndTest : public ::testing::Test {
331 testing_clock_(new base::SimpleTestTickClock()),
332 task_runner_(new test::FakeTaskRunner(testing_clock_)),
333 transport_task_runner_(new test::FakeTaskRunner(testing_clock_)),
334 cast_environment_(new CastEnvironment(
335 scoped_ptr<base::TickClock>(testing_clock_).Pass(),
336 task_runner_, task_runner_, task_runner_, task_runner_,
337 task_runner_, task_runner_, EnableCastLoggingConfig(true))),
338 receiver_to_sender_(cast_environment_),
339 sender_to_receiver_(cast_environment_),
340 test_receiver_audio_callback_(new TestReceiverAudioCallback()),
341 test_receiver_video_callback_(new TestReceiverVideoCallback()) {
342 testing_clock_->Advance(
343 base::TimeDelta::FromMilliseconds(kStartMillisecond));
346 void SetupConfig(transport::AudioCodec audio_codec,
347 int audio_sampling_frequency,
348 // TODO(miu): 3rd arg is meaningless?!?
349 bool external_audio_decoder,
350 int max_number_of_video_buffers_used) {
351 audio_sender_config_.sender_ssrc = 1;
352 audio_sender_config_.incoming_feedback_ssrc = 2;
353 audio_sender_config_.rtp_payload_type = 96;
354 audio_sender_config_.use_external_encoder = false;
355 audio_sender_config_.frequency = audio_sampling_frequency;
356 audio_sender_config_.channels = kAudioChannels;
357 audio_sender_config_.bitrate = kDefaultAudioEncoderBitrate;
358 audio_sender_config_.codec = audio_codec;
360 audio_receiver_config_.feedback_ssrc =
361 audio_sender_config_.incoming_feedback_ssrc;
362 audio_receiver_config_.incoming_ssrc =
363 audio_sender_config_.sender_ssrc;
364 audio_receiver_config_.rtp_payload_type =
365 audio_sender_config_.rtp_payload_type;
366 audio_receiver_config_.use_external_decoder = external_audio_decoder;
367 audio_receiver_config_.frequency = audio_sender_config_.frequency;
368 audio_receiver_config_.channels = kAudioChannels;
369 audio_receiver_config_.codec = audio_sender_config_.codec;
371 test_receiver_audio_callback_->SetExpectedSamplingFrequency(
372 audio_receiver_config_.frequency);
374 video_sender_config_.sender_ssrc = 3;
375 video_sender_config_.incoming_feedback_ssrc = 4;
376 video_sender_config_.rtp_payload_type = 97;
377 video_sender_config_.use_external_encoder = false;
378 video_sender_config_.width = kVideoWidth;
379 video_sender_config_.height = kVideoHeight;
380 video_sender_config_.max_bitrate = 5000000;
381 video_sender_config_.min_bitrate = 1000000;
382 video_sender_config_.start_bitrate = 5000000;
383 video_sender_config_.max_qp = 30;
384 video_sender_config_.min_qp = 4;
385 video_sender_config_.max_frame_rate = 30;
386 video_sender_config_.max_number_of_video_buffers_used =
387 max_number_of_video_buffers_used;
388 video_sender_config_.codec = transport::kVp8;
389 video_sender_config_.number_of_cores = 1;
391 video_receiver_config_.feedback_ssrc =
392 video_sender_config_.incoming_feedback_ssrc;
393 video_receiver_config_.incoming_ssrc =
394 video_sender_config_.sender_ssrc;
395 video_receiver_config_.rtp_payload_type =
396 video_sender_config_.rtp_payload_type;
397 video_receiver_config_.use_external_decoder = false;
398 video_receiver_config_.codec = video_sender_config_.codec;
400 transport_config_.audio_ssrc = audio_sender_config_.sender_ssrc;
401 transport_config_.video_ssrc = video_sender_config_.sender_ssrc;
402 transport_config_.video_codec = video_sender_config_.codec;
403 transport_config_.audio_codec = audio_sender_config_.codec;
404 transport_config_.video_rtp_payload_type =
405 video_sender_config_.rtp_payload_type;
406 transport_config_.audio_rtp_payload_type =
407 audio_sender_config_.rtp_payload_type;
408 transport_config_.audio_frequency = audio_sender_config_.frequency;
409 transport_config_.audio_channels = audio_sender_config_.channels;
410 transport_config_.video_rtp_max_delay_ms =
411 video_sender_config_.rtp_max_delay_ms;
412 transport_config_.audio_rtp_max_delay_ms =
413 audio_sender_config_.rtp_max_delay_ms;
417 cast_receiver_.reset(CastReceiver::CreateCastReceiver(
419 audio_receiver_config_,
420 video_receiver_config_,
421 &receiver_to_sender_));
422 transport_sender_.reset(new transport::CastTransportSenderImpl(
425 base::Bind(&UpdateCastTransportStatus),
426 transport_task_runner_));
427 transport_sender_->InsertFakeTransportForTesting(&sender_to_receiver_);
429 cast_sender_.reset(CastSender::CreateCastSender(cast_environment_,
430 audio_sender_config_,
431 video_sender_config_,
433 transport_sender_.get()));
435 receiver_to_sender_.SetPacketReceiver(cast_sender_->packet_receiver());
436 sender_to_receiver_.SetPacketReceiver(cast_receiver_->packet_receiver());
438 frame_input_ = cast_sender_->frame_input();
439 frame_receiver_ = cast_receiver_->frame_receiver();
441 audio_bus_factory_.reset(new TestAudioBusFactory(
442 audio_sender_config_.channels, audio_sender_config_.frequency,
443 kSoundFrequency, kSoundVolume));
446 virtual ~End2EndTest() {}
448 virtual void TearDown() OVERRIDE {
449 cast_sender_.reset();
450 cast_receiver_.reset();
451 task_runner_->RunTasks();
454 void SendVideoFrame(int start_value, const base::TimeTicks& capture_time) {
455 if (start_time_.is_null())
456 start_time_ = testing_clock_->NowTicks();
457 start_time_ = testing_clock_->NowTicks();
458 base::TimeDelta time_diff = testing_clock_->NowTicks() - start_time_;
459 gfx::Size size(kVideoWidth, kVideoHeight);
460 EXPECT_TRUE(VideoFrame::IsValidConfig(VideoFrame::I420,
461 size, gfx::Rect(size), size));
462 scoped_refptr<media::VideoFrame> video_frame =
463 media::VideoFrame::CreateFrame(
464 VideoFrame::I420, size, gfx::Rect(size), size, time_diff);
465 PopulateVideoFrame(video_frame, start_value);
466 frame_input_->InsertRawVideoFrame(video_frame, capture_time);
469 void RunTasks(int during_ms) {
470 for (int i = 0; i < during_ms; ++i) {
471 // Call process the timers every 1 ms.
472 testing_clock_->Advance(base::TimeDelta::FromMilliseconds(1));
473 task_runner_->RunTasks();
474 transport_task_runner_->RunTasks();
478 AudioReceiverConfig audio_receiver_config_;
479 VideoReceiverConfig video_receiver_config_;
480 AudioSenderConfig audio_sender_config_;
481 VideoSenderConfig video_sender_config_;
482 transport::CastTransportConfig transport_config_;
484 base::TimeTicks start_time_;
485 base::SimpleTestTickClock* testing_clock_; // Owned by CastEnvironment.
486 scoped_refptr<test::FakeTaskRunner> task_runner_;
487 scoped_refptr<test::FakeTaskRunner> transport_task_runner_;
488 scoped_refptr<CastEnvironment> cast_environment_;
490 LoopBackTransport receiver_to_sender_;
491 LoopBackTransport sender_to_receiver_;
492 scoped_ptr<transport::CastTransportSenderImpl> transport_sender_;
494 scoped_ptr<CastReceiver> cast_receiver_;
495 scoped_ptr<CastSender> cast_sender_;
496 scoped_refptr<FrameInput> frame_input_;
497 scoped_refptr<FrameReceiver> frame_receiver_;
499 scoped_refptr<TestReceiverAudioCallback> test_receiver_audio_callback_;
500 scoped_refptr<TestReceiverVideoCallback> test_receiver_video_callback_;
502 scoped_ptr<TestAudioBusFactory> audio_bus_factory_;
505 // Audio and video test without packet loss using raw PCM 16 audio "codec";
506 // This test is too slow. Disabled for now: crbug.com/329333.
507 TEST_F(End2EndTest, DISABLED_LoopNoLossPcm16) {
508 SetupConfig(transport::kPcm16, 32000, false, 1);
512 int audio_diff = kFrameTimerMs;
515 for (; i < 10; ++i) {
516 int num_10ms_blocks = audio_diff / 10;
517 audio_diff -= num_10ms_blocks * 10;
518 base::TimeTicks send_time = testing_clock_->NowTicks();
520 test_receiver_video_callback_->AddExpectedResult(video_start,
521 video_sender_config_.width, video_sender_config_.height, send_time);
523 scoped_ptr<AudioBus> audio_bus(audio_bus_factory_->NextAudioBus(
524 base::TimeDelta::FromMilliseconds(10) * num_10ms_blocks));
527 // Due to the re-sampler and NetEq in the webrtc AudioCodingModule the
528 // first samples will be 0 and then slowly ramp up to its real amplitude;
529 // ignore the first frame.
530 test_receiver_audio_callback_->AddExpectedResult(
531 ToPcmAudioFrame(*audio_bus, audio_sender_config_.frequency),
532 num_10ms_blocks, send_time);
535 AudioBus* const audio_bus_ptr = audio_bus.get();
536 frame_input_->InsertAudio(audio_bus_ptr, send_time,
537 base::Bind(&OwnThatAudioBus, base::Passed(&audio_bus)));
539 SendVideoFrame(video_start, send_time);
541 RunTasks(kFrameTimerMs);
542 audio_diff += kFrameTimerMs;
545 frame_receiver_->GetRawAudioFrame(num_10ms_blocks,
546 audio_sender_config_.frequency,
547 base::Bind(&TestReceiverAudioCallback::IgnoreAudioFrame,
548 test_receiver_audio_callback_));
550 frame_receiver_->GetRawAudioFrame(num_10ms_blocks,
551 audio_sender_config_.frequency,
552 base::Bind(&TestReceiverAudioCallback::CheckPcmAudioFrame,
553 test_receiver_audio_callback_));
556 frame_receiver_->GetRawVideoFrame(
557 base::Bind(&TestReceiverVideoCallback::CheckVideoFrame,
558 test_receiver_video_callback_));
562 std::cout << std::endl;
564 RunTasks(2 * kFrameTimerMs + 1); // Empty the receiver pipeline.
565 EXPECT_EQ(i - 1, test_receiver_audio_callback_->number_times_called());
566 EXPECT_EQ(i, test_receiver_video_callback_->number_times_called());
569 // TODO(mikhal): Crashes on the Win7 x64 bots. Re-enable.
570 // http://crbug.com/329563
572 #define MAYBE_LoopNoLossPcm16ExternalDecoder DISABLED_LoopNoLossPcm16ExternalDecoder
574 #define MAYBE_LoopNoLossPcm16ExternalDecoder LoopNoLossPcm16ExternalDecoder
576 // This tests our external decoder interface for Audio.
577 // Audio test without packet loss using raw PCM 16 audio "codec";
578 TEST_F(End2EndTest, MAYBE_LoopNoLossPcm16ExternalDecoder) {
579 SetupConfig(transport::kPcm16, 32000, true, 1);
583 for (; i < 10; ++i) {
584 base::TimeTicks send_time = testing_clock_->NowTicks();
585 scoped_ptr<AudioBus> audio_bus(audio_bus_factory_->NextAudioBus(
586 base::TimeDelta::FromMilliseconds(10)));
587 test_receiver_audio_callback_->AddExpectedResult(
588 ToPcmAudioFrame(*audio_bus, audio_sender_config_.frequency),
591 AudioBus* const audio_bus_ptr = audio_bus.get();
592 frame_input_->InsertAudio(audio_bus_ptr, send_time,
593 base::Bind(&OwnThatAudioBus, base::Passed(&audio_bus)));
596 frame_receiver_->GetCodedAudioFrame(
597 base::Bind(&TestReceiverAudioCallback::CheckCodedPcmAudioFrame,
598 test_receiver_audio_callback_));
600 RunTasks(2 * kFrameTimerMs + 1); // Empty the receiver pipeline.
601 EXPECT_EQ(10, test_receiver_audio_callback_->number_times_called());
604 // TODO(mikhal): Crashes on the bots. Re-enable. http://crbug.com/329563
606 #define MAYBE_LoopNoLossOpus DISABLED_LoopNoLossOpus
608 #define MAYBE_LoopNoLossOpus LoopNoLossOpus
610 // This tests our Opus audio codec without video.
611 TEST_F(End2EndTest, MAYBE_LoopNoLossOpus) {
612 SetupConfig(transport::kOpus, kDefaultAudioSamplingRate, false, 1);
616 for (; i < 10; ++i) {
617 int num_10ms_blocks = 3;
618 base::TimeTicks send_time = testing_clock_->NowTicks();
620 scoped_ptr<AudioBus> audio_bus(audio_bus_factory_->NextAudioBus(
621 base::TimeDelta::FromMilliseconds(10) * num_10ms_blocks));
624 test_receiver_audio_callback_->AddExpectedResult(
625 ToPcmAudioFrame(*audio_bus, audio_sender_config_.frequency),
626 num_10ms_blocks, send_time);
629 AudioBus* const audio_bus_ptr = audio_bus.get();
630 frame_input_->InsertAudio(audio_bus_ptr, send_time,
631 base::Bind(&OwnThatAudioBus, base::Passed(&audio_bus)));
636 frame_receiver_->GetRawAudioFrame(num_10ms_blocks,
637 audio_sender_config_.frequency,
638 base::Bind(&TestReceiverAudioCallback::IgnoreAudioFrame,
639 test_receiver_audio_callback_));
641 frame_receiver_->GetRawAudioFrame(num_10ms_blocks,
642 audio_sender_config_.frequency,
643 base::Bind(&TestReceiverAudioCallback::CheckPcmAudioFrame,
644 test_receiver_audio_callback_));
647 RunTasks(2 * kFrameTimerMs + 1); // Empty the receiver pipeline.
648 EXPECT_EQ(i - 1, test_receiver_audio_callback_->number_times_called());
651 // This tests start sending audio and video before the receiver is ready.
653 // TODO(miu): Test disabled because of non-determinism.
654 // http://crbug.com/314233
655 TEST_F(End2EndTest, DISABLED_StartSenderBeforeReceiver) {
656 SetupConfig(transport::kOpus, kDefaultAudioSamplingRate, false, 1);
660 int audio_diff = kFrameTimerMs;
662 sender_to_receiver_.SetSendPackets(false);
664 for (int i = 0; i < 3; ++i) {
665 int num_10ms_blocks = audio_diff / 10;
666 audio_diff -= num_10ms_blocks * 10;
668 base::TimeTicks send_time = testing_clock_->NowTicks();
669 scoped_ptr<AudioBus> audio_bus(audio_bus_factory_->NextAudioBus(
670 base::TimeDelta::FromMilliseconds(10) * num_10ms_blocks));
672 AudioBus* const audio_bus_ptr = audio_bus.get();
673 frame_input_->InsertAudio(audio_bus_ptr, send_time,
674 base::Bind(&OwnThatAudioBus, base::Passed(&audio_bus)));
676 SendVideoFrame(video_start, send_time);
677 RunTasks(kFrameTimerMs);
678 audio_diff += kFrameTimerMs;
682 sender_to_receiver_.SetSendPackets(true);
685 const int number_of_audio_frames_to_ignore = 3;
686 for (; j < 10; ++j) {
687 int num_10ms_blocks = audio_diff / 10;
688 audio_diff -= num_10ms_blocks * 10;
689 base::TimeTicks send_time = testing_clock_->NowTicks();
691 scoped_ptr<AudioBus> audio_bus(audio_bus_factory_->NextAudioBus(
692 base::TimeDelta::FromMilliseconds(10) * num_10ms_blocks));
694 if (j >= number_of_audio_frames_to_ignore) {
695 test_receiver_audio_callback_->AddExpectedResult(
696 ToPcmAudioFrame(*audio_bus, audio_sender_config_.frequency),
697 num_10ms_blocks, send_time);
700 AudioBus* const audio_bus_ptr = audio_bus.get();
701 frame_input_->InsertAudio(audio_bus_ptr, send_time,
702 base::Bind(&OwnThatAudioBus, base::Passed(&audio_bus)));
704 test_receiver_video_callback_->AddExpectedResult(video_start,
705 video_sender_config_.width, video_sender_config_.height, send_time);
707 SendVideoFrame(video_start, send_time);
708 RunTasks(kFrameTimerMs);
709 audio_diff += kFrameTimerMs;
711 if (j < number_of_audio_frames_to_ignore) {
712 frame_receiver_->GetRawAudioFrame(num_10ms_blocks,
713 audio_sender_config_.frequency,
714 base::Bind(&TestReceiverAudioCallback::IgnoreAudioFrame,
715 test_receiver_audio_callback_));
717 frame_receiver_->GetRawAudioFrame(num_10ms_blocks,
718 audio_sender_config_.frequency,
719 base::Bind(&TestReceiverAudioCallback::CheckPcmAudioFrame,
720 test_receiver_audio_callback_));
722 frame_receiver_->GetRawVideoFrame(
723 base::Bind(&TestReceiverVideoCallback::CheckVideoFrame,
724 test_receiver_video_callback_));
727 RunTasks(2 * kFrameTimerMs + 1); // Empty the receiver pipeline.
728 EXPECT_EQ(j - number_of_audio_frames_to_ignore,
729 test_receiver_audio_callback_->number_times_called());
730 EXPECT_EQ(j, test_receiver_video_callback_->number_times_called());
733 // This tests a network glitch lasting for 10 video frames.
734 TEST_F(End2EndTest, GlitchWith3Buffers) {
735 SetupConfig(transport::kOpus, kDefaultAudioSamplingRate, false, 3);
736 video_sender_config_.rtp_max_delay_ms = 67;
737 video_receiver_config_.rtp_max_delay_ms = 67;
740 int video_start = 50;
741 base::TimeTicks send_time = testing_clock_->NowTicks();
742 SendVideoFrame(video_start, send_time);
743 RunTasks(kFrameTimerMs);
745 test_receiver_video_callback_->AddExpectedResult(video_start,
746 video_sender_config_.width, video_sender_config_.height, send_time);
747 frame_receiver_->GetRawVideoFrame(
748 base::Bind(&TestReceiverVideoCallback::CheckVideoFrame,
749 test_receiver_video_callback_));
751 RunTasks(750); // Make sure that we send a RTCP packet.
755 // Introduce a glitch lasting for 10 frames.
756 sender_to_receiver_.SetSendPackets(false);
757 for (int i = 0; i < 10; ++i) {
758 send_time = testing_clock_->NowTicks();
759 // First 3 will be sent and lost.
760 SendVideoFrame(video_start, send_time);
761 RunTasks(kFrameTimerMs);
764 sender_to_receiver_.SetSendPackets(true);
766 send_time = testing_clock_->NowTicks();
768 // Frame 1 should be acked by now and we should have an opening to send 4.
769 SendVideoFrame(video_start, send_time);
770 RunTasks(kFrameTimerMs);
772 test_receiver_video_callback_->AddExpectedResult(video_start,
773 video_sender_config_.width, video_sender_config_.height, send_time);
775 frame_receiver_->GetRawVideoFrame(
776 base::Bind(&TestReceiverVideoCallback::CheckVideoFrame,
777 test_receiver_video_callback_));
779 RunTasks(2 * kFrameTimerMs + 1); // Empty the receiver pipeline.
780 EXPECT_EQ(2, test_receiver_video_callback_->number_times_called());
783 TEST_F(End2EndTest, DropEveryOtherFrame3Buffers) {
784 SetupConfig(transport::kOpus, kDefaultAudioSamplingRate, false, 3);
785 video_sender_config_.rtp_max_delay_ms = 67;
786 video_receiver_config_.rtp_max_delay_ms = 67;
788 sender_to_receiver_.DropAllPacketsBelongingToOddFrames();
790 int video_start = 50;
791 base::TimeTicks send_time;
794 for (; i < 20; ++i) {
795 send_time = testing_clock_->NowTicks();
796 SendVideoFrame(video_start, send_time);
799 test_receiver_video_callback_->AddExpectedResult(video_start,
800 video_sender_config_.width, video_sender_config_.height, send_time);
802 // GetRawVideoFrame will not return the frame until we are close in
803 // time before we should render the frame.
804 frame_receiver_->GetRawVideoFrame(
805 base::Bind(&TestReceiverVideoCallback::CheckVideoFrame,
806 test_receiver_video_callback_));
808 RunTasks(kFrameTimerMs);
811 std::cout << std::endl;
812 RunTasks(2 * kFrameTimerMs + 1); // Empty the pipeline.
813 EXPECT_EQ(i / 2, test_receiver_video_callback_->number_times_called());
816 TEST_F(End2EndTest, ResetReferenceFrameId) {
817 SetupConfig(transport::kOpus, kDefaultAudioSamplingRate, false, 3);
818 video_sender_config_.rtp_max_delay_ms = 67;
819 video_receiver_config_.rtp_max_delay_ms = 67;
821 sender_to_receiver_.AlwaysResetReferenceFrameId();
823 int frames_counter = 0;
824 for (; frames_counter < 20; ++frames_counter) {
825 const base::TimeTicks send_time = testing_clock_->NowTicks();
826 SendVideoFrame(frames_counter, send_time);
828 test_receiver_video_callback_->AddExpectedResult(frames_counter,
829 video_sender_config_.width, video_sender_config_.height, send_time);
831 // GetRawVideoFrame will not return the frame until we are close to the
832 // time in which we should render the frame.
833 frame_receiver_->GetRawVideoFrame(
834 base::Bind(&TestReceiverVideoCallback::CheckVideoFrame,
835 test_receiver_video_callback_));
836 RunTasks(kFrameTimerMs);
838 RunTasks(2 * kFrameTimerMs + 1); // Empty the pipeline.
839 EXPECT_EQ(frames_counter,
840 test_receiver_video_callback_->number_times_called());
843 TEST_F(End2EndTest, CryptoVideo) {
844 SetupConfig(transport::kPcm16, 32000, false, 1);
846 transport_config_.aes_iv_mask =
847 ConvertFromBase16String("1234567890abcdeffedcba0987654321");
848 transport_config_.aes_key =
849 ConvertFromBase16String("deadbeefcafeb0b0b0b0cafedeadbeef");
851 video_receiver_config_.aes_iv_mask = transport_config_.aes_iv_mask;
852 video_receiver_config_.aes_key = transport_config_.aes_key;
856 int frames_counter = 0;
857 for (; frames_counter < 3; ++frames_counter) {
858 const base::TimeTicks send_time = testing_clock_->NowTicks();
860 SendVideoFrame(frames_counter, send_time);
862 test_receiver_video_callback_->AddExpectedResult(frames_counter,
863 video_sender_config_.width, video_sender_config_.height, send_time);
865 // GetRawVideoFrame will not return the frame until we are close to the
866 // time in which we should render the frame.
867 frame_receiver_->GetRawVideoFrame(
868 base::Bind(&TestReceiverVideoCallback::CheckVideoFrame,
869 test_receiver_video_callback_));
870 RunTasks(kFrameTimerMs);
872 RunTasks(2 * kFrameTimerMs + 1); // Empty the pipeline.
873 EXPECT_EQ(frames_counter,
874 test_receiver_video_callback_->number_times_called());
877 // TODO(mikhal): Crashes on the bots. Re-enable. http://crbug.com/329563
879 #define MAYBE_CryptoAudio DISABLED_CryptoAudio
881 #define MAYBE_CryptoAudio CryptoAudio
883 TEST_F(End2EndTest, MAYBE_CryptoAudio) {
884 SetupConfig(transport::kPcm16, 32000, false, 1);
886 transport_config_.aes_iv_mask =
887 ConvertFromBase16String("abcdeffedcba12345678900987654321");
888 transport_config_.aes_key =
889 ConvertFromBase16String("deadbeefcafecafedeadbeefb0b0b0b0");
891 audio_receiver_config_.aes_iv_mask = transport_config_.aes_iv_mask;
892 audio_receiver_config_.aes_key = transport_config_.aes_key;
896 int frames_counter = 0;
897 for (; frames_counter < 3; ++frames_counter) {
898 int num_10ms_blocks = 2;
900 const base::TimeTicks send_time = testing_clock_->NowTicks();
902 scoped_ptr<AudioBus> audio_bus(audio_bus_factory_->NextAudioBus(
903 base::TimeDelta::FromMilliseconds(10) * num_10ms_blocks));
905 if (frames_counter != 0) {
906 // Due to the re-sampler and NetEq in the webrtc AudioCodingModule the
907 // first samples will be 0 and then slowly ramp up to its real amplitude;
908 // ignore the first frame.
909 test_receiver_audio_callback_->AddExpectedResult(
910 ToPcmAudioFrame(*audio_bus, audio_sender_config_.frequency),
911 num_10ms_blocks, send_time);
913 AudioBus* const audio_bus_ptr = audio_bus.get();
914 frame_input_->InsertAudio(audio_bus_ptr, send_time,
915 base::Bind(&OwnThatAudioBus, base::Passed(&audio_bus)));
917 RunTasks(num_10ms_blocks * 10);
919 if (frames_counter == 0) {
920 frame_receiver_->GetRawAudioFrame(num_10ms_blocks,
922 base::Bind(&TestReceiverAudioCallback::IgnoreAudioFrame,
923 test_receiver_audio_callback_));
925 frame_receiver_->GetRawAudioFrame(num_10ms_blocks,
927 base::Bind(&TestReceiverAudioCallback::CheckPcmAudioFrame,
928 test_receiver_audio_callback_));
931 RunTasks(2 * kFrameTimerMs + 1); // Empty the pipeline.
932 EXPECT_EQ(frames_counter - 1,
933 test_receiver_audio_callback_->number_times_called());
936 // Video test without packet loss; This test is targeted at testing the logging
937 // aspects of the end2end, but is basically equivalent to LoopNoLossPcm16.
938 TEST_F(End2EndTest, VideoLogging) {
939 SetupConfig(transport::kPcm16, 32000, false, 1);
945 base::TimeTicks send_time = testing_clock_->NowTicks();
946 test_receiver_video_callback_->AddExpectedResult(video_start,
947 video_sender_config_.width, video_sender_config_.height, send_time);
949 SendVideoFrame(video_start, send_time);
950 RunTasks(kFrameTimerMs);
952 frame_receiver_->GetRawVideoFrame(
953 base::Bind(&TestReceiverVideoCallback::CheckVideoFrame,
954 test_receiver_video_callback_));
960 RunTasks(2 * kFrameTimerMs + 1); // Empty the receiver pipeline.
961 EXPECT_EQ(i, test_receiver_video_callback_->number_times_called());
963 // Sender logging tests.
964 LoggingImpl* sender_log = cast_environment_->Logging();
966 // Verify that all frames and all required events were logged.
967 FrameRawMap frame_raw_log = sender_log->GetFrameRawData();
969 // Every frame should have only one entry.
970 EXPECT_EQ(static_cast<unsigned int>(i), frame_raw_log.size());
971 FrameRawMap::const_iterator frame_it = frame_raw_log.begin();
973 // Choose a video frame, and verify that all events were logged.
974 std::vector<CastLoggingEvent> event_log = frame_it->second.type;
975 std::vector<CastLoggingEvent>::iterator event_it;
976 event_it = std::find(event_log.begin(), event_log.end(),
977 kVideoFrameSentToEncoder);
978 EXPECT_TRUE(event_it != event_log.end());
979 event_log.erase(event_it);
981 event_it = std::find(event_log.begin(), event_log.end(),
983 EXPECT_TRUE(event_it != event_log.end());
984 event_log.erase(event_it);
986 event_it = std::find(event_log.begin(), event_log.end(),
987 kVideoFrameReceived);
988 EXPECT_TRUE(event_it != event_log.end());
989 event_log.erase(event_it);
991 event_it = std::find(event_log.begin(), event_log.end(),
993 EXPECT_TRUE(event_it != event_log.end());
994 event_log.erase(event_it);
996 // TODO(mikhal): Plumb this one through.
997 event_it = std::find(event_log.begin(), event_log.end(),
999 EXPECT_TRUE(event_it == event_log.end());
1001 // Verify that there were no other events logged with respect to this frame.
1002 EXPECT_EQ(0u, event_log.size());
1005 // Verify that all packet related events were logged.
1006 PacketRawMap packet_raw_log = sender_log->GetPacketRawData();
1007 // Every rtp_timestamp should have only one entry.
1008 EXPECT_EQ(static_cast<unsigned int>(i), packet_raw_log.size());
1009 PacketRawMap::const_iterator packet_it = packet_raw_log.begin();
1010 // Choose a packet, and verify that all events were logged.
1011 event_log = (++(packet_it->second.packet_map.begin()))->second.type;
1012 EXPECT_TRUE((std::find(event_log.begin(), event_log.end(),
1013 kVideoPacketReceived)) != event_log.end());
1015 RunTasks(750); // Make sure that we send a RTCP message with the log.
1017 // Receiver logging tests.
1018 LoggingImpl* receiver_log = cast_environment_->Logging();
1020 // Verify that all frames and all required events were logged.
1021 frame_raw_log = receiver_log->GetFrameRawData();
1022 EXPECT_EQ(static_cast<unsigned int>(i), frame_raw_log.size());
1023 frame_it = frame_raw_log.begin();
1025 // Choose a video frame, and verify that all events were logged.
1026 event_log = frame_it->second.type;
1028 event_it = std::find(event_log.begin(), event_log.end(),
1029 kVideoFrameEncoded);
1030 EXPECT_TRUE(event_it != event_log.end());
1032 event_it = std::find(event_log.begin(), event_log.end(),
1035 EXPECT_TRUE(event_it != event_log.end());
1038 // TODO(mikhal): Crashes on the bots. Re-enable. http://crbug.com/329563
1040 #define MAYBE_AudioLogging DISABLED_AudioLogging
1042 #define MAYBE_AudioLogging AudioLogging
1044 // Audio test without packet loss; This test is targeted at testing the logging
1045 // aspects of the end2end, but is basically equivalent to LoopNoLossPcm16.
1046 TEST_F(End2EndTest, MAYBE_AudioLogging) {
1047 SetupConfig(transport::kPcm16, 32000, false, 1);
1050 int audio_diff = kFrameTimerMs;
1053 for (; i < 10; ++i) {
1054 int num_10ms_blocks = audio_diff / 10;
1055 audio_diff -= num_10ms_blocks * 10;
1056 base::TimeTicks send_time = testing_clock_->NowTicks();
1058 scoped_ptr<AudioBus> audio_bus(audio_bus_factory_->NextAudioBus(
1059 base::TimeDelta::FromMilliseconds(10) * num_10ms_blocks));
1062 // Due to the re-sampler and NetEq in the webrtc AudioCodingModule the
1063 // first samples will be 0 and then slowly ramp up to its real amplitude;
1064 // ignore the first frame.
1065 test_receiver_audio_callback_->AddExpectedResult(
1066 ToPcmAudioFrame(*audio_bus, audio_sender_config_.frequency),
1067 num_10ms_blocks, send_time);
1070 AudioBus* const audio_bus_ptr = audio_bus.get();
1071 frame_input_->InsertAudio(audio_bus_ptr, send_time,
1072 base::Bind(&OwnThatAudioBus, base::Passed(&audio_bus)));
1074 RunTasks(kFrameTimerMs);
1075 audio_diff += kFrameTimerMs;
1078 frame_receiver_->GetRawAudioFrame(num_10ms_blocks,
1079 audio_sender_config_.frequency,
1080 base::Bind(&TestReceiverAudioCallback::IgnoreAudioFrame,
1081 test_receiver_audio_callback_));
1083 frame_receiver_->GetRawAudioFrame(num_10ms_blocks,
1084 audio_sender_config_.frequency,
1085 base::Bind(&TestReceiverAudioCallback::CheckPcmAudioFrame,
1086 test_receiver_audio_callback_));
1091 RunTasks(2 * kFrameTimerMs + 1); // Empty the receiver pipeline.
1092 //EXPECT_EQ(i - 1, test_receiver_audio_callback_->number_times_called());
1093 EXPECT_EQ(i - 1, test_receiver_audio_callback_->number_times_called());
1095 LoggingImpl* sender_log = cast_environment_->Logging();
1096 // Verify that all frames and all required events were logged.
1097 FrameRawMap frame_raw_log = sender_log->GetFrameRawData();
1098 // TODO(mikhal): Results are wrong. Need to resolve passing/calculation of
1099 // rtp_timestamp for audio for this to work.
1100 // Should have logged both audio and video. Every frame should have only one
1102 //EXPECT_EQ(static_cast<unsigned int>(i - 1), frame_raw_log.size());
1103 FrameRawMap::const_iterator frame_it = frame_raw_log.begin();
1104 // Choose a video frame, and verify that all events were logged.
1105 std::vector<CastLoggingEvent> event_log = frame_it->second.type;
1106 EXPECT_TRUE((std::find(event_log.begin(), event_log.end(),
1107 kAudioFrameReceived)) != event_log.end());
1108 EXPECT_TRUE((std::find(event_log.begin(), event_log.end(),
1109 kAudioFrameEncoded)) != event_log.end());
1110 // EXPECT_TRUE((std::find(event_log.begin(), event_log.end(),
1111 // kAudioPlayoutDelay)) != event_log.end());
1112 // TODO(mikhal): Plumb this one through.
1113 EXPECT_TRUE((std::find(event_log.begin(), event_log.end(),
1114 kAudioFrameDecoded)) == event_log.end());
1115 // Verify that there were no other events logged with respect to this frame.
1116 EXPECT_EQ(2u, event_log.size());
1120 // TODO(pwestin): Add repeatable packet loss test.
1121 // TODO(pwestin): Add test for misaligned send get calls.
1122 // TODO(pwestin): Add more tests that does not resample.
1123 // TODO(pwestin): Add test when we have starvation for our RunTask.
1126 } // namespace media