xref: /aosp_15_r20/external/webrtc/pc/test/fake_audio_capture_module_unittest.cc (revision d9f758449e529ab9291ac668be2861e7a55c2422)
1 /*
2  *  Copyright 2012 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 "pc/test/fake_audio_capture_module.h"
12 
13 #include <string.h>
14 
15 #include <algorithm>
16 
17 #include "api/scoped_refptr.h"
18 #include "rtc_base/gunit.h"
19 #include "rtc_base/synchronization/mutex.h"
20 #include "test/gtest.h"
21 
22 class FakeAdmTest : public ::testing::Test, public webrtc::AudioTransport {
23  protected:
24   static const int kMsInSecond = 1000;
25 
FakeAdmTest()26   FakeAdmTest()
27       : push_iterations_(0), pull_iterations_(0), rec_buffer_bytes_(0) {
28     memset(rec_buffer_, 0, sizeof(rec_buffer_));
29   }
30 
SetUp()31   void SetUp() override {
32     fake_audio_capture_module_ = FakeAudioCaptureModule::Create();
33     EXPECT_TRUE(fake_audio_capture_module_.get() != NULL);
34   }
35 
36   // Callbacks inherited from webrtc::AudioTransport.
37   // ADM is pushing data.
RecordedDataIsAvailable(const void * audioSamples,const size_t nSamples,const size_t nBytesPerSample,const size_t nChannels,const uint32_t samplesPerSec,const uint32_t totalDelayMS,const int32_t clockDrift,const uint32_t currentMicLevel,const bool keyPressed,uint32_t & newMicLevel)38   int32_t RecordedDataIsAvailable(const void* audioSamples,
39                                   const size_t nSamples,
40                                   const size_t nBytesPerSample,
41                                   const size_t nChannels,
42                                   const uint32_t samplesPerSec,
43                                   const uint32_t totalDelayMS,
44                                   const int32_t clockDrift,
45                                   const uint32_t currentMicLevel,
46                                   const bool keyPressed,
47                                   uint32_t& newMicLevel) override {
48     webrtc::MutexLock lock(&mutex_);
49     rec_buffer_bytes_ = nSamples * nBytesPerSample;
50     if ((rec_buffer_bytes_ == 0) ||
51         (rec_buffer_bytes_ >
52          FakeAudioCaptureModule::kNumberSamples *
53              FakeAudioCaptureModule::kNumberBytesPerSample)) {
54       ADD_FAILURE();
55       return -1;
56     }
57     memcpy(rec_buffer_, audioSamples, rec_buffer_bytes_);
58     ++push_iterations_;
59     newMicLevel = currentMicLevel;
60     return 0;
61   }
62 
PullRenderData(int bits_per_sample,int sample_rate,size_t number_of_channels,size_t number_of_frames,void * audio_data,int64_t * elapsed_time_ms,int64_t * ntp_time_ms)63   void PullRenderData(int bits_per_sample,
64                       int sample_rate,
65                       size_t number_of_channels,
66                       size_t number_of_frames,
67                       void* audio_data,
68                       int64_t* elapsed_time_ms,
69                       int64_t* ntp_time_ms) override {}
70 
71   // ADM is pulling data.
NeedMorePlayData(const size_t nSamples,const size_t nBytesPerSample,const size_t nChannels,const uint32_t samplesPerSec,void * audioSamples,size_t & nSamplesOut,int64_t * elapsed_time_ms,int64_t * ntp_time_ms)72   int32_t NeedMorePlayData(const size_t nSamples,
73                            const size_t nBytesPerSample,
74                            const size_t nChannels,
75                            const uint32_t samplesPerSec,
76                            void* audioSamples,
77                            size_t& nSamplesOut,
78                            int64_t* elapsed_time_ms,
79                            int64_t* ntp_time_ms) override {
80     webrtc::MutexLock lock(&mutex_);
81     ++pull_iterations_;
82     const size_t audio_buffer_size = nSamples * nBytesPerSample;
83     const size_t bytes_out =
84         RecordedDataReceived()
85             ? CopyFromRecBuffer(audioSamples, audio_buffer_size)
86             : GenerateZeroBuffer(audioSamples, audio_buffer_size);
87     nSamplesOut = bytes_out / nBytesPerSample;
88     *elapsed_time_ms = 0;
89     *ntp_time_ms = 0;
90     return 0;
91   }
92 
push_iterations() const93   int push_iterations() const {
94     webrtc::MutexLock lock(&mutex_);
95     return push_iterations_;
96   }
pull_iterations() const97   int pull_iterations() const {
98     webrtc::MutexLock lock(&mutex_);
99     return pull_iterations_;
100   }
101 
102   rtc::scoped_refptr<FakeAudioCaptureModule> fake_audio_capture_module_;
103 
104  private:
RecordedDataReceived() const105   bool RecordedDataReceived() const { return rec_buffer_bytes_ != 0; }
GenerateZeroBuffer(void * audio_buffer,size_t audio_buffer_size)106   size_t GenerateZeroBuffer(void* audio_buffer, size_t audio_buffer_size) {
107     memset(audio_buffer, 0, audio_buffer_size);
108     return audio_buffer_size;
109   }
CopyFromRecBuffer(void * audio_buffer,size_t audio_buffer_size)110   size_t CopyFromRecBuffer(void* audio_buffer, size_t audio_buffer_size) {
111     EXPECT_EQ(audio_buffer_size, rec_buffer_bytes_);
112     const size_t min_buffer_size =
113         std::min(audio_buffer_size, rec_buffer_bytes_);
114     memcpy(audio_buffer, rec_buffer_, min_buffer_size);
115     return min_buffer_size;
116   }
117 
118   rtc::AutoThread main_thread_;
119 
120   mutable webrtc::Mutex mutex_;
121 
122   int push_iterations_;
123   int pull_iterations_;
124 
125   char rec_buffer_[FakeAudioCaptureModule::kNumberSamples *
126                    FakeAudioCaptureModule::kNumberBytesPerSample];
127   size_t rec_buffer_bytes_;
128 };
129 
TEST_F(FakeAdmTest,PlayoutTest)130 TEST_F(FakeAdmTest, PlayoutTest) {
131   EXPECT_EQ(0, fake_audio_capture_module_->RegisterAudioCallback(this));
132 
133   bool stereo_available = false;
134   EXPECT_EQ(0, fake_audio_capture_module_->StereoPlayoutIsAvailable(
135                    &stereo_available));
136   EXPECT_TRUE(stereo_available);
137 
138   EXPECT_NE(0, fake_audio_capture_module_->StartPlayout());
139   EXPECT_FALSE(fake_audio_capture_module_->PlayoutIsInitialized());
140   EXPECT_FALSE(fake_audio_capture_module_->Playing());
141   EXPECT_EQ(0, fake_audio_capture_module_->StopPlayout());
142 
143   EXPECT_EQ(0, fake_audio_capture_module_->InitPlayout());
144   EXPECT_TRUE(fake_audio_capture_module_->PlayoutIsInitialized());
145   EXPECT_FALSE(fake_audio_capture_module_->Playing());
146 
147   EXPECT_EQ(0, fake_audio_capture_module_->StartPlayout());
148   EXPECT_TRUE(fake_audio_capture_module_->Playing());
149 
150   uint16_t delay_ms = 10;
151   EXPECT_EQ(0, fake_audio_capture_module_->PlayoutDelay(&delay_ms));
152   EXPECT_EQ(0, delay_ms);
153 
154   EXPECT_TRUE_WAIT(pull_iterations() > 0, kMsInSecond);
155   EXPECT_GE(0, push_iterations());
156 
157   EXPECT_EQ(0, fake_audio_capture_module_->StopPlayout());
158   EXPECT_FALSE(fake_audio_capture_module_->Playing());
159 }
160 
TEST_F(FakeAdmTest,RecordTest)161 TEST_F(FakeAdmTest, RecordTest) {
162   EXPECT_EQ(0, fake_audio_capture_module_->RegisterAudioCallback(this));
163 
164   bool stereo_available = false;
165   EXPECT_EQ(0, fake_audio_capture_module_->StereoRecordingIsAvailable(
166                    &stereo_available));
167   EXPECT_FALSE(stereo_available);
168 
169   EXPECT_NE(0, fake_audio_capture_module_->StartRecording());
170   EXPECT_FALSE(fake_audio_capture_module_->Recording());
171   EXPECT_EQ(0, fake_audio_capture_module_->StopRecording());
172 
173   EXPECT_EQ(0, fake_audio_capture_module_->InitRecording());
174   EXPECT_EQ(0, fake_audio_capture_module_->StartRecording());
175   EXPECT_TRUE(fake_audio_capture_module_->Recording());
176 
177   EXPECT_TRUE_WAIT(push_iterations() > 0, kMsInSecond);
178   EXPECT_GE(0, pull_iterations());
179 
180   EXPECT_EQ(0, fake_audio_capture_module_->StopRecording());
181   EXPECT_FALSE(fake_audio_capture_module_->Recording());
182 }
183 
TEST_F(FakeAdmTest,DuplexTest)184 TEST_F(FakeAdmTest, DuplexTest) {
185   EXPECT_EQ(0, fake_audio_capture_module_->RegisterAudioCallback(this));
186 
187   EXPECT_EQ(0, fake_audio_capture_module_->InitPlayout());
188   EXPECT_EQ(0, fake_audio_capture_module_->StartPlayout());
189 
190   EXPECT_EQ(0, fake_audio_capture_module_->InitRecording());
191   EXPECT_EQ(0, fake_audio_capture_module_->StartRecording());
192 
193   EXPECT_TRUE_WAIT(push_iterations() > 0, kMsInSecond);
194   EXPECT_TRUE_WAIT(pull_iterations() > 0, kMsInSecond);
195 
196   EXPECT_EQ(0, fake_audio_capture_module_->StopPlayout());
197   EXPECT_EQ(0, fake_audio_capture_module_->StopRecording());
198 }
199