diff options
Diffstat (limited to 'webrtc/test/fake_audio_device.cc')
-rw-r--r-- | webrtc/test/fake_audio_device.cc | 151 |
1 files changed, 151 insertions, 0 deletions
diff --git a/webrtc/test/fake_audio_device.cc b/webrtc/test/fake_audio_device.cc new file mode 100644 index 0000000000..e307dd7664 --- /dev/null +++ b/webrtc/test/fake_audio_device.cc @@ -0,0 +1,151 @@ +/* + * Copyright (c) 2013 The WebRTC project authors. All Rights Reserved. + * + * Use of this source code is governed by a BSD-style license + * that can be found in the LICENSE file in the root of the source + * tree. An additional intellectual property rights grant can be found + * in the file PATENTS. All contributing project authors may + * be found in the AUTHORS file in the root of the source tree. + */ + +#include "webrtc/test/fake_audio_device.h" + +#include <algorithm> + +#include "testing/gtest/include/gtest/gtest.h" +#include "webrtc/modules/media_file/source/media_file_utility.h" +#include "webrtc/system_wrappers/include/clock.h" +#include "webrtc/system_wrappers/include/event_wrapper.h" +#include "webrtc/system_wrappers/include/file_wrapper.h" +#include "webrtc/system_wrappers/include/thread_wrapper.h" + +namespace webrtc { +namespace test { + +FakeAudioDevice::FakeAudioDevice(Clock* clock, const std::string& filename) + : audio_callback_(NULL), + capturing_(false), + captured_audio_(), + playout_buffer_(), + last_playout_ms_(-1), + clock_(clock), + tick_(EventTimerWrapper::Create()), + file_utility_(new ModuleFileUtility(0)), + input_stream_(FileWrapper::Create()) { + memset(captured_audio_, 0, sizeof(captured_audio_)); + memset(playout_buffer_, 0, sizeof(playout_buffer_)); + // Open audio input file as read-only and looping. + EXPECT_EQ(0, input_stream_->OpenFile(filename.c_str(), true, true)) + << filename; +} + +FakeAudioDevice::~FakeAudioDevice() { + Stop(); + + if (thread_.get() != NULL) + thread_->Stop(); +} + +int32_t FakeAudioDevice::Init() { + rtc::CritScope cs(&lock_); + if (file_utility_->InitPCMReading(*input_stream_.get()) != 0) + return -1; + + if (!tick_->StartTimer(true, 10)) + return -1; + thread_ = ThreadWrapper::CreateThread(FakeAudioDevice::Run, this, + "FakeAudioDevice"); + if (thread_.get() == NULL) + return -1; + if (!thread_->Start()) { + thread_.reset(); + return -1; + } + thread_->SetPriority(webrtc::kHighPriority); + return 0; +} + +int32_t FakeAudioDevice::RegisterAudioCallback(AudioTransport* callback) { + rtc::CritScope cs(&lock_); + audio_callback_ = callback; + return 0; +} + +bool FakeAudioDevice::Playing() const { + rtc::CritScope cs(&lock_); + return capturing_; +} + +int32_t FakeAudioDevice::PlayoutDelay(uint16_t* delay_ms) const { + *delay_ms = 0; + return 0; +} + +bool FakeAudioDevice::Recording() const { + rtc::CritScope cs(&lock_); + return capturing_; +} + +bool FakeAudioDevice::Run(void* obj) { + static_cast<FakeAudioDevice*>(obj)->CaptureAudio(); + return true; +} + +void FakeAudioDevice::CaptureAudio() { + { + rtc::CritScope cs(&lock_); + if (capturing_) { + int bytes_read = file_utility_->ReadPCMData( + *input_stream_.get(), captured_audio_, kBufferSizeBytes); + if (bytes_read <= 0) + return; + // 2 bytes per sample. + size_t num_samples = static_cast<size_t>(bytes_read / 2); + uint32_t new_mic_level; + EXPECT_EQ(0, + audio_callback_->RecordedDataIsAvailable(captured_audio_, + num_samples, + 2, + 1, + kFrequencyHz, + 0, + 0, + 0, + false, + new_mic_level)); + size_t samples_needed = kFrequencyHz / 100; + int64_t now_ms = clock_->TimeInMilliseconds(); + uint32_t time_since_last_playout_ms = now_ms - last_playout_ms_; + if (last_playout_ms_ > 0 && time_since_last_playout_ms > 0) { + samples_needed = std::min( + static_cast<size_t>(kFrequencyHz / time_since_last_playout_ms), + kBufferSizeBytes / 2); + } + size_t samples_out = 0; + int64_t elapsed_time_ms = -1; + int64_t ntp_time_ms = -1; + EXPECT_EQ(0, + audio_callback_->NeedMorePlayData(samples_needed, + 2, + 1, + kFrequencyHz, + playout_buffer_, + samples_out, + &elapsed_time_ms, + &ntp_time_ms)); + } + } + tick_->Wait(WEBRTC_EVENT_INFINITE); +} + +void FakeAudioDevice::Start() { + rtc::CritScope cs(&lock_); + capturing_ = true; +} + +void FakeAudioDevice::Stop() { + rtc::CritScope cs(&lock_); + capturing_ = false; +} +} // namespace test +} // namespace webrtc |