Index: content/renderer/media/webrtc_local_audio_track_unittest.cc |
diff --git a/content/renderer/media/webrtc_local_audio_track_unittest.cc b/content/renderer/media/webrtc_local_audio_track_unittest.cc |
deleted file mode 100644 |
index 51af138563639080e6770681332ea88ed4b5508a..0000000000000000000000000000000000000000 |
--- a/content/renderer/media/webrtc_local_audio_track_unittest.cc |
+++ /dev/null |
@@ -1,579 +0,0 @@ |
-// Copyright 2013 The Chromium Authors. All rights reserved. |
-// Use of this source code is governed by a BSD-style license that can be |
-// found in the LICENSE file. |
- |
-#include "base/macros.h" |
-#include "base/synchronization/waitable_event.h" |
-#include "base/test/test_timeouts.h" |
-#include "build/build_config.h" |
-#include "content/public/renderer/media_stream_audio_sink.h" |
-#include "content/renderer/media/media_stream_audio_source.h" |
-#include "content/renderer/media/mock_constraint_factory.h" |
-#include "content/renderer/media/webrtc/webrtc_local_audio_track_adapter.h" |
-#include "content/renderer/media/webrtc_audio_capturer.h" |
-#include "content/renderer/media/webrtc_local_audio_track.h" |
-#include "media/base/audio_bus.h" |
-#include "media/base/audio_capturer_source.h" |
-#include "media/base/audio_parameters.h" |
-#include "testing/gmock/include/gmock/gmock.h" |
-#include "testing/gtest/include/gtest/gtest.h" |
-#include "third_party/WebKit/public/platform/WebMediaConstraints.h" |
-#include "third_party/WebKit/public/web/WebHeap.h" |
-#include "third_party/webrtc/api/mediastreaminterface.h" |
- |
-using ::testing::_; |
-using ::testing::AnyNumber; |
-using ::testing::AtLeast; |
-using ::testing::Return; |
- |
-namespace content { |
- |
-namespace { |
- |
-ACTION_P(SignalEvent, event) { |
- event->Signal(); |
-} |
- |
-// A simple thread that we use to fake the audio thread which provides data to |
-// the |WebRtcAudioCapturer|. |
-class FakeAudioThread : public base::PlatformThread::Delegate { |
- public: |
- FakeAudioThread(WebRtcAudioCapturer* capturer, |
- const media::AudioParameters& params) |
- : capturer_(capturer), |
- thread_(), |
- closure_(false, false) { |
- DCHECK(capturer); |
- audio_bus_ = media::AudioBus::Create(params); |
- } |
- |
- ~FakeAudioThread() override { DCHECK(thread_.is_null()); } |
- |
- // base::PlatformThread::Delegate: |
- void ThreadMain() override { |
- while (true) { |
- if (closure_.IsSignaled()) |
- return; |
- |
- media::AudioCapturerSource::CaptureCallback* callback = |
- static_cast<media::AudioCapturerSource::CaptureCallback*>( |
- capturer_); |
- audio_bus_->Zero(); |
- callback->Capture(audio_bus_.get(), 0, 0, false); |
- |
- // Sleep 1ms to yield the resource for the main thread. |
- base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(1)); |
- } |
- } |
- |
- void Start() { |
- base::PlatformThread::CreateWithPriority( |
- 0, this, &thread_, base::ThreadPriority::REALTIME_AUDIO); |
- CHECK(!thread_.is_null()); |
- } |
- |
- void Stop() { |
- closure_.Signal(); |
- base::PlatformThread::Join(thread_); |
- thread_ = base::PlatformThreadHandle(); |
- } |
- |
- private: |
- std::unique_ptr<media::AudioBus> audio_bus_; |
- WebRtcAudioCapturer* capturer_; |
- base::PlatformThreadHandle thread_; |
- base::WaitableEvent closure_; |
- DISALLOW_COPY_AND_ASSIGN(FakeAudioThread); |
-}; |
- |
-class MockCapturerSource : public media::AudioCapturerSource { |
- public: |
- explicit MockCapturerSource(WebRtcAudioCapturer* capturer) |
- : capturer_(capturer) {} |
- MOCK_METHOD3(OnInitialize, void(const media::AudioParameters& params, |
- CaptureCallback* callback, |
- int session_id)); |
- MOCK_METHOD0(OnStart, void()); |
- MOCK_METHOD0(OnStop, void()); |
- void SetVolume(double volume) final {} |
- MOCK_METHOD1(SetAutomaticGainControl, void(bool enable)); |
- |
- void Initialize(const media::AudioParameters& params, |
- CaptureCallback* callback, |
- int session_id) override { |
- DCHECK(params.IsValid()); |
- params_ = params; |
- OnInitialize(params, callback, session_id); |
- } |
- void Start() override { |
- audio_thread_.reset(new FakeAudioThread(capturer_, params_)); |
- audio_thread_->Start(); |
- OnStart(); |
- } |
- void Stop() override { |
- audio_thread_->Stop(); |
- audio_thread_.reset(); |
- OnStop(); |
- } |
- |
- protected: |
- ~MockCapturerSource() override {} |
- |
- private: |
- std::unique_ptr<FakeAudioThread> audio_thread_; |
- WebRtcAudioCapturer* capturer_; |
- media::AudioParameters params_; |
-}; |
- |
-class MockMediaStreamAudioSink : public MediaStreamAudioSink { |
- public: |
- MockMediaStreamAudioSink() {} |
- ~MockMediaStreamAudioSink() {} |
- void OnData(const media::AudioBus& audio_bus, |
- base::TimeTicks estimated_capture_time) override { |
- EXPECT_EQ(params_.channels(), audio_bus.channels()); |
- EXPECT_EQ(params_.frames_per_buffer(), audio_bus.frames()); |
- EXPECT_FALSE(estimated_capture_time.is_null()); |
- CaptureData(); |
- } |
- MOCK_METHOD0(CaptureData, void()); |
- void OnSetFormat(const media::AudioParameters& params) { |
- params_ = params; |
- FormatIsSet(); |
- } |
- MOCK_METHOD0(FormatIsSet, void()); |
- |
- const media::AudioParameters& audio_params() const { return params_; } |
- |
- private: |
- media::AudioParameters params_; |
-}; |
- |
-} // namespace |
- |
-class WebRtcLocalAudioTrackTest : public ::testing::Test { |
- protected: |
- void SetUp() override { |
- params_.Reset(media::AudioParameters::AUDIO_PCM_LOW_LATENCY, |
- media::CHANNEL_LAYOUT_STEREO, 48000, 16, 480); |
- MockConstraintFactory constraint_factory; |
- blink_source_.initialize("dummy", blink::WebMediaStreamSource::TypeAudio, |
- "dummy", |
- false /* remote */); |
- MediaStreamAudioSource* audio_source = new MediaStreamAudioSource(); |
- blink_source_.setExtraData(audio_source); |
- |
- StreamDeviceInfo device(MEDIA_DEVICE_AUDIO_CAPTURE, |
- std::string(), std::string()); |
- { |
- std::unique_ptr<WebRtcAudioCapturer> capturer = |
- WebRtcAudioCapturer::CreateCapturer( |
- -1, device, constraint_factory.CreateWebMediaConstraints(), |
- nullptr, audio_source); |
- capturer_ = capturer.get(); |
- audio_source->SetAudioCapturer(std::move(capturer)); |
- } |
- capturer_source_ = new MockCapturerSource(capturer_); |
- EXPECT_CALL(*capturer_source_.get(), OnInitialize(_, capturer_, -1)) |
- .WillOnce(Return()); |
- EXPECT_CALL(*capturer_source_.get(), SetAutomaticGainControl(true)); |
- EXPECT_CALL(*capturer_source_.get(), OnStart()); |
- capturer_->SetCapturerSource(capturer_source_, params_); |
- } |
- |
- void TearDown() override { |
- blink_source_.reset(); |
- blink::WebHeap::collectAllGarbageForTesting(); |
- } |
- |
- media::AudioParameters params_; |
- blink::WebMediaStreamSource blink_source_; |
- WebRtcAudioCapturer* capturer_; // Owned by |blink_source_|. |
- scoped_refptr<MockCapturerSource> capturer_source_; |
-}; |
- |
-// Creates a capturer and audio track, fakes its audio thread, and |
-// connect/disconnect the sink to the audio track on the fly, the sink should |
-// get data callback when the track is connected to the capturer but not when |
-// the track is disconnected from the capturer. |
-TEST_F(WebRtcLocalAudioTrackTest, ConnectAndDisconnectOneSink) { |
- scoped_refptr<WebRtcLocalAudioTrackAdapter> adapter( |
- WebRtcLocalAudioTrackAdapter::Create(std::string(), NULL)); |
- std::unique_ptr<WebRtcLocalAudioTrack> track( |
- new WebRtcLocalAudioTrack(adapter.get())); |
- track->Start( |
- base::Bind(&MediaStreamAudioSource::StopAudioDeliveryTo, |
- MediaStreamAudioSource::From(blink_source_)->GetWeakPtr(), |
- track.get())); |
- capturer_->AddTrack(track.get()); |
- EXPECT_TRUE(track->GetAudioAdapter()->enabled()); |
- |
- std::unique_ptr<MockMediaStreamAudioSink> sink( |
- new MockMediaStreamAudioSink()); |
- base::WaitableEvent event(false, false); |
- EXPECT_CALL(*sink, FormatIsSet()); |
- EXPECT_CALL(*sink, |
- CaptureData()).Times(AtLeast(1)) |
- .WillRepeatedly(SignalEvent(&event)); |
- track->AddSink(sink.get()); |
- EXPECT_TRUE(event.TimedWait(TestTimeouts::tiny_timeout())); |
- track->RemoveSink(sink.get()); |
- |
- EXPECT_CALL(*capturer_source_.get(), OnStop()).WillOnce(Return()); |
- capturer_->Stop(); |
-} |
- |
-// The same setup as ConnectAndDisconnectOneSink, but enable and disable the |
-// audio track on the fly. When the audio track is disabled, there is no data |
-// callback to the sink; when the audio track is enabled, there comes data |
-// callback. |
-// TODO(xians): Enable this test after resolving the racing issue that TSAN |
-// reports on MediaStreamTrack::enabled(); |
-TEST_F(WebRtcLocalAudioTrackTest, DISABLED_DisableEnableAudioTrack) { |
- EXPECT_CALL(*capturer_source_.get(), SetAutomaticGainControl(true)); |
- EXPECT_CALL(*capturer_source_.get(), OnStart()); |
- scoped_refptr<WebRtcLocalAudioTrackAdapter> adapter( |
- WebRtcLocalAudioTrackAdapter::Create(std::string(), NULL)); |
- std::unique_ptr<WebRtcLocalAudioTrack> track( |
- new WebRtcLocalAudioTrack(adapter.get())); |
- track->Start( |
- base::Bind(&MediaStreamAudioSource::StopAudioDeliveryTo, |
- MediaStreamAudioSource::From(blink_source_)->GetWeakPtr(), |
- track.get())); |
- capturer_->AddTrack(track.get()); |
- EXPECT_TRUE(track->GetAudioAdapter()->enabled()); |
- EXPECT_TRUE(track->GetAudioAdapter()->set_enabled(false)); |
- std::unique_ptr<MockMediaStreamAudioSink> sink( |
- new MockMediaStreamAudioSink()); |
- const media::AudioParameters params = capturer_->GetInputFormat(); |
- base::WaitableEvent event(false, false); |
- EXPECT_CALL(*sink, FormatIsSet()).Times(1); |
- EXPECT_CALL(*sink, CaptureData()).Times(0); |
- EXPECT_EQ(sink->audio_params().frames_per_buffer(), |
- params.sample_rate() / 100); |
- track->AddSink(sink.get()); |
- EXPECT_FALSE(event.TimedWait(TestTimeouts::tiny_timeout())); |
- |
- event.Reset(); |
- EXPECT_CALL(*sink, CaptureData()).Times(AtLeast(1)) |
- .WillRepeatedly(SignalEvent(&event)); |
- EXPECT_TRUE(track->GetAudioAdapter()->set_enabled(true)); |
- EXPECT_TRUE(event.TimedWait(TestTimeouts::tiny_timeout())); |
- track->RemoveSink(sink.get()); |
- |
- EXPECT_CALL(*capturer_source_.get(), OnStop()).WillOnce(Return()); |
- capturer_->Stop(); |
- track.reset(); |
-} |
- |
-// Create multiple audio tracks and enable/disable them, verify that the audio |
-// callbacks appear/disappear. |
-// Flaky due to a data race, see http://crbug.com/295418 |
-TEST_F(WebRtcLocalAudioTrackTest, DISABLED_MultipleAudioTracks) { |
- scoped_refptr<WebRtcLocalAudioTrackAdapter> adapter_1( |
- WebRtcLocalAudioTrackAdapter::Create(std::string(), NULL)); |
- std::unique_ptr<WebRtcLocalAudioTrack> track_1( |
- new WebRtcLocalAudioTrack(adapter_1.get())); |
- track_1->Start( |
- base::Bind(&MediaStreamAudioSource::StopAudioDeliveryTo, |
- MediaStreamAudioSource::From(blink_source_)->GetWeakPtr(), |
- track_1.get())); |
- capturer_->AddTrack(track_1.get()); |
- EXPECT_TRUE(track_1->GetAudioAdapter()->enabled()); |
- std::unique_ptr<MockMediaStreamAudioSink> sink_1( |
- new MockMediaStreamAudioSink()); |
- const media::AudioParameters params = capturer_->GetInputFormat(); |
- base::WaitableEvent event_1(false, false); |
- EXPECT_CALL(*sink_1, FormatIsSet()).WillOnce(Return()); |
- EXPECT_CALL(*sink_1, CaptureData()).Times(AtLeast(1)) |
- .WillRepeatedly(SignalEvent(&event_1)); |
- EXPECT_EQ(sink_1->audio_params().frames_per_buffer(), |
- params.sample_rate() / 100); |
- track_1->AddSink(sink_1.get()); |
- EXPECT_TRUE(event_1.TimedWait(TestTimeouts::tiny_timeout())); |
- |
- scoped_refptr<WebRtcLocalAudioTrackAdapter> adapter_2( |
- WebRtcLocalAudioTrackAdapter::Create(std::string(), NULL)); |
- std::unique_ptr<WebRtcLocalAudioTrack> track_2( |
- new WebRtcLocalAudioTrack(adapter_2.get())); |
- track_2->Start( |
- base::Bind(&MediaStreamAudioSource::StopAudioDeliveryTo, |
- MediaStreamAudioSource::From(blink_source_)->GetWeakPtr(), |
- track_2.get())); |
- capturer_->AddTrack(track_2.get()); |
- EXPECT_TRUE(track_2->GetAudioAdapter()->enabled()); |
- |
- // Verify both |sink_1| and |sink_2| get data. |
- event_1.Reset(); |
- base::WaitableEvent event_2(false, false); |
- |
- std::unique_ptr<MockMediaStreamAudioSink> sink_2( |
- new MockMediaStreamAudioSink()); |
- EXPECT_CALL(*sink_2, FormatIsSet()).WillOnce(Return()); |
- EXPECT_CALL(*sink_1, CaptureData()).Times(AtLeast(1)) |
- .WillRepeatedly(SignalEvent(&event_1)); |
- EXPECT_EQ(sink_1->audio_params().frames_per_buffer(), |
- params.sample_rate() / 100); |
- EXPECT_CALL(*sink_2, CaptureData()).Times(AtLeast(1)) |
- .WillRepeatedly(SignalEvent(&event_2)); |
- EXPECT_EQ(sink_2->audio_params().frames_per_buffer(), |
- params.sample_rate() / 100); |
- track_2->AddSink(sink_2.get()); |
- EXPECT_TRUE(event_1.TimedWait(TestTimeouts::tiny_timeout())); |
- EXPECT_TRUE(event_2.TimedWait(TestTimeouts::tiny_timeout())); |
- |
- track_1->RemoveSink(sink_1.get()); |
- track_1->Stop(); |
- track_1.reset(); |
- |
- EXPECT_CALL(*capturer_source_.get(), OnStop()).WillOnce(Return()); |
- track_2->RemoveSink(sink_2.get()); |
- track_2->Stop(); |
- track_2.reset(); |
-} |
- |
- |
-// Start one track and verify the capturer is correctly starting its source. |
-// And it should be fine to not to call Stop() explicitly. |
-TEST_F(WebRtcLocalAudioTrackTest, StartOneAudioTrack) { |
- scoped_refptr<WebRtcLocalAudioTrackAdapter> adapter( |
- WebRtcLocalAudioTrackAdapter::Create(std::string(), NULL)); |
- std::unique_ptr<WebRtcLocalAudioTrack> track( |
- new WebRtcLocalAudioTrack(adapter.get())); |
- track->Start( |
- base::Bind(&MediaStreamAudioSource::StopAudioDeliveryTo, |
- MediaStreamAudioSource::From(blink_source_)->GetWeakPtr(), |
- track.get())); |
- capturer_->AddTrack(track.get()); |
- |
- // When the track goes away, it will automatically stop the |
- // |capturer_source_|. |
- EXPECT_CALL(*capturer_source_.get(), OnStop()); |
- track.reset(); |
-} |
- |
-// Start two tracks and verify the capturer is correctly starting its source. |
-// When the last track connected to the capturer is stopped, the source is |
-// stopped. |
-TEST_F(WebRtcLocalAudioTrackTest, StartTwoAudioTracks) { |
- scoped_refptr<WebRtcLocalAudioTrackAdapter> adapter1( |
- WebRtcLocalAudioTrackAdapter::Create(std::string(), NULL)); |
- std::unique_ptr<WebRtcLocalAudioTrack> track1( |
- new WebRtcLocalAudioTrack(adapter1.get())); |
- track1->Start( |
- base::Bind(&MediaStreamAudioSource::StopAudioDeliveryTo, |
- MediaStreamAudioSource::From(blink_source_)->GetWeakPtr(), |
- track1.get())); |
- capturer_->AddTrack(track1.get()); |
- |
- scoped_refptr<WebRtcLocalAudioTrackAdapter> adapter2( |
- WebRtcLocalAudioTrackAdapter::Create(std::string(), NULL)); |
- std::unique_ptr<WebRtcLocalAudioTrack> track2( |
- new WebRtcLocalAudioTrack(adapter2.get())); |
- track2->Start( |
- base::Bind(&MediaStreamAudioSource::StopAudioDeliveryTo, |
- MediaStreamAudioSource::From(blink_source_)->GetWeakPtr(), |
- track2.get())); |
- capturer_->AddTrack(track2.get()); |
- |
- track1->Stop(); |
- // When the last track is stopped, it will automatically stop the |
- // |capturer_source_|. |
- EXPECT_CALL(*capturer_source_.get(), OnStop()); |
- track2->Stop(); |
-} |
- |
-// Start/Stop tracks and verify the capturer is correctly starting/stopping |
-// its source. |
-TEST_F(WebRtcLocalAudioTrackTest, StartAndStopAudioTracks) { |
- base::WaitableEvent event(false, false); |
- scoped_refptr<WebRtcLocalAudioTrackAdapter> adapter_1( |
- WebRtcLocalAudioTrackAdapter::Create(std::string(), NULL)); |
- std::unique_ptr<WebRtcLocalAudioTrack> track_1( |
- new WebRtcLocalAudioTrack(adapter_1.get())); |
- track_1->Start( |
- base::Bind(&MediaStreamAudioSource::StopAudioDeliveryTo, |
- MediaStreamAudioSource::From(blink_source_)->GetWeakPtr(), |
- track_1.get())); |
- capturer_->AddTrack(track_1.get()); |
- |
- // Verify the data flow by connecting the sink to |track_1|. |
- std::unique_ptr<MockMediaStreamAudioSink> sink( |
- new MockMediaStreamAudioSink()); |
- event.Reset(); |
- EXPECT_CALL(*sink, FormatIsSet()).WillOnce(SignalEvent(&event)); |
- EXPECT_CALL(*sink, CaptureData()) |
- .Times(AnyNumber()).WillRepeatedly(Return()); |
- track_1->AddSink(sink.get()); |
- EXPECT_TRUE(event.TimedWait(TestTimeouts::tiny_timeout())); |
- |
- // Start the second audio track will not start the |capturer_source_| |
- // since it has been started. |
- EXPECT_CALL(*capturer_source_.get(), OnStart()).Times(0); |
- scoped_refptr<WebRtcLocalAudioTrackAdapter> adapter_2( |
- WebRtcLocalAudioTrackAdapter::Create(std::string(), NULL)); |
- std::unique_ptr<WebRtcLocalAudioTrack> track_2( |
- new WebRtcLocalAudioTrack(adapter_2.get())); |
- track_2->Start( |
- base::Bind(&MediaStreamAudioSource::StopAudioDeliveryTo, |
- MediaStreamAudioSource::From(blink_source_)->GetWeakPtr(), |
- track_2.get())); |
- capturer_->AddTrack(track_2.get()); |
- |
- // Stop the capturer will clear up the track lists in the capturer. |
- EXPECT_CALL(*capturer_source_.get(), OnStop()); |
- capturer_->Stop(); |
- |
- // Adding a new track to the capturer. |
- track_2->AddSink(sink.get()); |
- EXPECT_CALL(*sink, FormatIsSet()).Times(0); |
- |
- // Stop the capturer again will not trigger stopping the source of the |
- // capturer again.. |
- event.Reset(); |
- EXPECT_CALL(*capturer_source_.get(), OnStop()).Times(0); |
- capturer_->Stop(); |
-} |
- |
-// Create a new capturer with new source, connect it to a new audio track. |
-#if defined(THREAD_SANITIZER) |
-// Fails under TSan, see https://crbug.com/576634. |
-#define MAYBE_ConnectTracksToDifferentCapturers \ |
- DISABLED_ConnectTracksToDifferentCapturers |
-#else |
-#define MAYBE_ConnectTracksToDifferentCapturers \ |
- ConnectTracksToDifferentCapturers |
-#endif |
-TEST_F(WebRtcLocalAudioTrackTest, MAYBE_ConnectTracksToDifferentCapturers) { |
- // Setup the first audio track and start it. |
- scoped_refptr<WebRtcLocalAudioTrackAdapter> adapter_1( |
- WebRtcLocalAudioTrackAdapter::Create(std::string(), NULL)); |
- std::unique_ptr<WebRtcLocalAudioTrack> track_1( |
- new WebRtcLocalAudioTrack(adapter_1.get())); |
- track_1->Start( |
- base::Bind(&MediaStreamAudioSource::StopAudioDeliveryTo, |
- MediaStreamAudioSource::From(blink_source_)->GetWeakPtr(), |
- track_1.get())); |
- capturer_->AddTrack(track_1.get()); |
- |
- // Verify the data flow by connecting the |sink_1| to |track_1|. |
- std::unique_ptr<MockMediaStreamAudioSink> sink_1( |
- new MockMediaStreamAudioSink()); |
- EXPECT_CALL(*sink_1.get(), CaptureData()) |
- .Times(AnyNumber()).WillRepeatedly(Return()); |
- EXPECT_CALL(*sink_1.get(), FormatIsSet()).Times(AnyNumber()); |
- track_1->AddSink(sink_1.get()); |
- |
- // Create a new capturer with new source with different audio format. |
- MockConstraintFactory constraint_factory; |
- StreamDeviceInfo device(MEDIA_DEVICE_AUDIO_CAPTURE, |
- std::string(), std::string()); |
- std::unique_ptr<WebRtcAudioCapturer> new_capturer( |
- WebRtcAudioCapturer::CreateCapturer( |
- -1, device, constraint_factory.CreateWebMediaConstraints(), NULL, |
- NULL)); |
- scoped_refptr<MockCapturerSource> new_source( |
- new MockCapturerSource(new_capturer.get())); |
- EXPECT_CALL(*new_source.get(), OnInitialize(_, new_capturer.get(), -1)); |
- EXPECT_CALL(*new_source.get(), SetAutomaticGainControl(true)); |
- EXPECT_CALL(*new_source.get(), OnStart()); |
- |
- media::AudioParameters new_param( |
- media::AudioParameters::AUDIO_PCM_LOW_LATENCY, |
- media::CHANNEL_LAYOUT_MONO, 44100, 16, 441); |
- new_capturer->SetCapturerSource(new_source, new_param); |
- |
- // Setup the second audio track, connect it to the new capturer and start it. |
- scoped_refptr<WebRtcLocalAudioTrackAdapter> adapter_2( |
- WebRtcLocalAudioTrackAdapter::Create(std::string(), NULL)); |
- std::unique_ptr<WebRtcLocalAudioTrack> track_2( |
- new WebRtcLocalAudioTrack(adapter_2.get())); |
- track_2->Start( |
- base::Bind(&MediaStreamAudioSource::StopAudioDeliveryTo, |
- MediaStreamAudioSource::From(blink_source_)->GetWeakPtr(), |
- track_2.get())); |
- new_capturer->AddTrack(track_2.get()); |
- |
- // Verify the data flow by connecting the |sink_2| to |track_2|. |
- std::unique_ptr<MockMediaStreamAudioSink> sink_2( |
- new MockMediaStreamAudioSink()); |
- base::WaitableEvent event(false, false); |
- EXPECT_CALL(*sink_2, CaptureData()) |
- .Times(AnyNumber()).WillRepeatedly(Return()); |
- EXPECT_CALL(*sink_2, FormatIsSet()).WillOnce(SignalEvent(&event)); |
- track_2->AddSink(sink_2.get()); |
- EXPECT_TRUE(event.TimedWait(TestTimeouts::tiny_timeout())); |
- |
- // Stopping the new source will stop the second track. |
- event.Reset(); |
- EXPECT_CALL(*new_source.get(), OnStop()) |
- .Times(1).WillOnce(SignalEvent(&event)); |
- new_capturer->Stop(); |
- EXPECT_TRUE(event.TimedWait(TestTimeouts::tiny_timeout())); |
- |
- // Stop the capturer of the first audio track. |
- EXPECT_CALL(*capturer_source_.get(), OnStop()); |
- capturer_->Stop(); |
-} |
- |
-// Make sure a audio track can deliver packets with a buffer size smaller than |
-// 10ms when it is not connected with a peer connection. |
-TEST_F(WebRtcLocalAudioTrackTest, TrackWorkWithSmallBufferSize) { |
- // Setup a capturer which works with a buffer size smaller than 10ms. |
- media::AudioParameters params(media::AudioParameters::AUDIO_PCM_LOW_LATENCY, |
- media::CHANNEL_LAYOUT_STEREO, 48000, 16, 128); |
- |
- // Create a capturer with new source which works with the format above. |
- MockConstraintFactory factory; |
- factory.DisableDefaultAudioConstraints(); |
- std::unique_ptr<WebRtcAudioCapturer> capturer( |
- WebRtcAudioCapturer::CreateCapturer( |
- -1, StreamDeviceInfo(MEDIA_DEVICE_AUDIO_CAPTURE, "", "", |
- params.sample_rate(), params.channel_layout(), |
- params.frames_per_buffer()), |
- factory.CreateWebMediaConstraints(), NULL, NULL)); |
- scoped_refptr<MockCapturerSource> source( |
- new MockCapturerSource(capturer.get())); |
- EXPECT_CALL(*source.get(), OnInitialize(_, capturer.get(), -1)); |
- EXPECT_CALL(*source.get(), SetAutomaticGainControl(true)); |
- EXPECT_CALL(*source.get(), OnStart()); |
- capturer->SetCapturerSource(source, params); |
- |
- // Setup a audio track, connect it to the capturer and start it. |
- scoped_refptr<WebRtcLocalAudioTrackAdapter> adapter( |
- WebRtcLocalAudioTrackAdapter::Create(std::string(), NULL)); |
- std::unique_ptr<WebRtcLocalAudioTrack> track( |
- new WebRtcLocalAudioTrack(adapter.get())); |
- track->Start( |
- base::Bind(&MediaStreamAudioSource::StopAudioDeliveryTo, |
- MediaStreamAudioSource::From(blink_source_)->GetWeakPtr(), |
- track.get())); |
- capturer->AddTrack(track.get()); |
- |
- // Verify the data flow by connecting the |sink| to |track|. |
- std::unique_ptr<MockMediaStreamAudioSink> sink( |
- new MockMediaStreamAudioSink()); |
- base::WaitableEvent event(false, false); |
- EXPECT_CALL(*sink, FormatIsSet()).Times(1); |
- // Verify the sinks are getting the packets with an expecting buffer size. |
-#if defined(OS_ANDROID) |
- const int expected_buffer_size = params.sample_rate() / 100; |
-#else |
- const int expected_buffer_size = params.frames_per_buffer(); |
-#endif |
- EXPECT_CALL(*sink, CaptureData()) |
- .Times(AtLeast(1)).WillRepeatedly(SignalEvent(&event)); |
- track->AddSink(sink.get()); |
- EXPECT_TRUE(event.TimedWait(TestTimeouts::tiny_timeout())); |
- EXPECT_EQ(expected_buffer_size, sink->audio_params().frames_per_buffer()); |
- |
- // Stopping the new source will stop the second track. |
- EXPECT_CALL(*source.get(), OnStop()).Times(1); |
- capturer->Stop(); |
- |
- // Even though this test don't use |capturer_source_| it will be stopped |
- // during teardown of the test harness. |
- EXPECT_CALL(*capturer_source_.get(), OnStop()); |
-} |
- |
-} // namespace content |