Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(363)

Side by Side Diff: webrtc/modules/audio_device/audio_device_buffer.cc

Issue 2117303002: Minor refactoring of the AudioDeviceBuffer class (Closed) Base URL: https://chromium.googlesource.com/external/webrtc.git@master
Patch Set: Feedback from magjed@ Created 4 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « webrtc/modules/audio_device/audio_device_buffer.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. 2 * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved.
3 * 3 *
4 * Use of this source code is governed by a BSD-style license 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 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 6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may 7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree. 8 * be found in the AUTHORS file in the root of the source tree.
9 */ 9 */
10 10
11 #include "webrtc/modules/audio_device/audio_device_buffer.h" 11 #include "webrtc/modules/audio_device/audio_device_buffer.h"
12 12
13 #include <assert.h> 13 #include "webrtc/base/checks.h"
14 #include <string.h> 14 #include "webrtc/base/logging.h"
15
16 #include "webrtc/base/format_macros.h" 15 #include "webrtc/base/format_macros.h"
17 #include "webrtc/modules/audio_device/audio_device_config.h" 16 #include "webrtc/modules/audio_device/audio_device_config.h"
18 #include "webrtc/system_wrappers/include/critical_section_wrapper.h" 17 #include "webrtc/system_wrappers/include/critical_section_wrapper.h"
19 #include "webrtc/system_wrappers/include/logging.h"
20 #include "webrtc/system_wrappers/include/trace.h"
21 18
22 namespace webrtc { 19 namespace webrtc {
23 20
24 static const int kHighDelayThresholdMs = 300; 21 static const int kHighDelayThresholdMs = 300;
25 static const int kLogHighDelayIntervalFrames = 500; // 5 seconds. 22 static const int kLogHighDelayIntervalFrames = 500; // 5 seconds.
26 23
27 // ----------------------------------------------------------------------------
28 // ctor
29 // ----------------------------------------------------------------------------
30
31 AudioDeviceBuffer::AudioDeviceBuffer() 24 AudioDeviceBuffer::AudioDeviceBuffer()
32 : _id(-1), 25 : _critSect(*CriticalSectionWrapper::CreateCriticalSection()),
33 _critSect(*CriticalSectionWrapper::CreateCriticalSection()),
34 _critSectCb(*CriticalSectionWrapper::CreateCriticalSection()), 26 _critSectCb(*CriticalSectionWrapper::CreateCriticalSection()),
35 _ptrCbAudioTransport(NULL), 27 _ptrCbAudioTransport(nullptr),
36 _recSampleRate(0), 28 _recSampleRate(0),
37 _playSampleRate(0), 29 _playSampleRate(0),
38 _recChannels(0), 30 _recChannels(0),
39 _playChannels(0), 31 _playChannels(0),
40 _recChannel(AudioDeviceModule::kChannelBoth), 32 _recChannel(AudioDeviceModule::kChannelBoth),
41 _recBytesPerSample(0), 33 _recBytesPerSample(0),
42 _playBytesPerSample(0), 34 _playBytesPerSample(0),
43 _recSamples(0), 35 _recSamples(0),
44 _recSize(0), 36 _recSize(0),
45 _playSamples(0), 37 _playSamples(0),
46 _playSize(0), 38 _playSize(0),
47 _recFile(*FileWrapper::Create()), 39 _recFile(*FileWrapper::Create()),
48 _playFile(*FileWrapper::Create()), 40 _playFile(*FileWrapper::Create()),
49 _currentMicLevel(0), 41 _currentMicLevel(0),
50 _newMicLevel(0), 42 _newMicLevel(0),
51 _typingStatus(false), 43 _typingStatus(false),
52 _playDelayMS(0), 44 _playDelayMS(0),
53 _recDelayMS(0), 45 _recDelayMS(0),
54 _clockDrift(0), 46 _clockDrift(0),
55 // Set to the interval in order to log on the first occurrence. 47 // Set to the interval in order to log on the first occurrence.
56 high_delay_counter_(kLogHighDelayIntervalFrames) { 48 high_delay_counter_(kLogHighDelayIntervalFrames) {
57 // valid ID will be set later by SetId, use -1 for now 49 LOG(INFO) << "AudioDeviceBuffer::ctor";
58 WEBRTC_TRACE(kTraceMemory, kTraceAudioDevice, _id, "%s created",
59 __FUNCTION__);
60 memset(_recBuffer, 0, kMaxBufferSizeBytes); 50 memset(_recBuffer, 0, kMaxBufferSizeBytes);
61 memset(_playBuffer, 0, kMaxBufferSizeBytes); 51 memset(_playBuffer, 0, kMaxBufferSizeBytes);
62 } 52 }
63 53
64 // ----------------------------------------------------------------------------
65 // dtor
66 // ----------------------------------------------------------------------------
67
68 AudioDeviceBuffer::~AudioDeviceBuffer() { 54 AudioDeviceBuffer::~AudioDeviceBuffer() {
69 WEBRTC_TRACE(kTraceMemory, kTraceAudioDevice, _id, "%s destroyed", 55 LOG(INFO) << "AudioDeviceBuffer::~dtor";
70 __FUNCTION__);
71 { 56 {
72 CriticalSectionScoped lock(&_critSect); 57 CriticalSectionScoped lock(&_critSect);
73 58
74 _recFile.Flush(); 59 _recFile.Flush();
75 _recFile.CloseFile(); 60 _recFile.CloseFile();
76 delete &_recFile; 61 delete &_recFile;
77 62
78 _playFile.Flush(); 63 _playFile.Flush();
79 _playFile.CloseFile(); 64 _playFile.CloseFile();
80 delete &_playFile; 65 delete &_playFile;
81 } 66 }
82 67
83 delete &_critSect; 68 delete &_critSect;
84 delete &_critSectCb; 69 delete &_critSectCb;
85 } 70 }
86 71
87 // ----------------------------------------------------------------------------
88 // SetId
89 // ----------------------------------------------------------------------------
90
91 void AudioDeviceBuffer::SetId(uint32_t id) {
92 WEBRTC_TRACE(kTraceMemory, kTraceAudioDevice, id,
93 "AudioDeviceBuffer::SetId(id=%d)", id);
94 _id = id;
95 }
96
97 // ----------------------------------------------------------------------------
98 // RegisterAudioCallback
99 // ----------------------------------------------------------------------------
100
101 int32_t AudioDeviceBuffer::RegisterAudioCallback( 72 int32_t AudioDeviceBuffer::RegisterAudioCallback(
102 AudioTransport* audioCallback) { 73 AudioTransport* audioCallback) {
74 LOG(INFO) << __FUNCTION__;
103 CriticalSectionScoped lock(&_critSectCb); 75 CriticalSectionScoped lock(&_critSectCb);
104 _ptrCbAudioTransport = audioCallback; 76 _ptrCbAudioTransport = audioCallback;
105
106 return 0; 77 return 0;
107 } 78 }
108 79
109 // ----------------------------------------------------------------------------
110 // InitPlayout
111 // ----------------------------------------------------------------------------
112
113 int32_t AudioDeviceBuffer::InitPlayout() { 80 int32_t AudioDeviceBuffer::InitPlayout() {
114 WEBRTC_TRACE(kTraceMemory, kTraceAudioDevice, _id, "%s", __FUNCTION__); 81 LOG(INFO) << __FUNCTION__;
115 return 0; 82 return 0;
116 } 83 }
117 84
118 // ----------------------------------------------------------------------------
119 // InitRecording
120 // ----------------------------------------------------------------------------
121
122 int32_t AudioDeviceBuffer::InitRecording() { 85 int32_t AudioDeviceBuffer::InitRecording() {
123 WEBRTC_TRACE(kTraceMemory, kTraceAudioDevice, _id, "%s", __FUNCTION__); 86 LOG(INFO) << __FUNCTION__;
124 return 0; 87 return 0;
125 } 88 }
126 89
127 // ----------------------------------------------------------------------------
128 // SetRecordingSampleRate
129 // ----------------------------------------------------------------------------
130
131 int32_t AudioDeviceBuffer::SetRecordingSampleRate(uint32_t fsHz) { 90 int32_t AudioDeviceBuffer::SetRecordingSampleRate(uint32_t fsHz) {
91 LOG(INFO) << "SetRecordingSampleRate(" << fsHz << ")";
132 CriticalSectionScoped lock(&_critSect); 92 CriticalSectionScoped lock(&_critSect);
133 _recSampleRate = fsHz; 93 _recSampleRate = fsHz;
134 return 0; 94 return 0;
135 } 95 }
136 96
137 // ----------------------------------------------------------------------------
138 // SetPlayoutSampleRate
139 // ----------------------------------------------------------------------------
140
141 int32_t AudioDeviceBuffer::SetPlayoutSampleRate(uint32_t fsHz) { 97 int32_t AudioDeviceBuffer::SetPlayoutSampleRate(uint32_t fsHz) {
98 LOG(INFO) << "SetPlayoutSampleRate(" << fsHz << ")";
142 CriticalSectionScoped lock(&_critSect); 99 CriticalSectionScoped lock(&_critSect);
143 _playSampleRate = fsHz; 100 _playSampleRate = fsHz;
144 return 0; 101 return 0;
145 } 102 }
146 103
147 // ----------------------------------------------------------------------------
148 // RecordingSampleRate
149 // ----------------------------------------------------------------------------
150
151 int32_t AudioDeviceBuffer::RecordingSampleRate() const { 104 int32_t AudioDeviceBuffer::RecordingSampleRate() const {
152 return _recSampleRate; 105 return _recSampleRate;
153 } 106 }
154 107
155 // ----------------------------------------------------------------------------
156 // PlayoutSampleRate
157 // ----------------------------------------------------------------------------
158
159 int32_t AudioDeviceBuffer::PlayoutSampleRate() const { 108 int32_t AudioDeviceBuffer::PlayoutSampleRate() const {
160 return _playSampleRate; 109 return _playSampleRate;
161 } 110 }
162 111
163 // ----------------------------------------------------------------------------
164 // SetRecordingChannels
165 // ----------------------------------------------------------------------------
166
167 int32_t AudioDeviceBuffer::SetRecordingChannels(size_t channels) { 112 int32_t AudioDeviceBuffer::SetRecordingChannels(size_t channels) {
168 CriticalSectionScoped lock(&_critSect); 113 CriticalSectionScoped lock(&_critSect);
169 _recChannels = channels; 114 _recChannels = channels;
170 _recBytesPerSample = 115 _recBytesPerSample =
171 2 * channels; // 16 bits per sample in mono, 32 bits in stereo 116 2 * channels; // 16 bits per sample in mono, 32 bits in stereo
172 return 0; 117 return 0;
173 } 118 }
174 119
175 // ----------------------------------------------------------------------------
176 // SetPlayoutChannels
177 // ----------------------------------------------------------------------------
178
179 int32_t AudioDeviceBuffer::SetPlayoutChannels(size_t channels) { 120 int32_t AudioDeviceBuffer::SetPlayoutChannels(size_t channels) {
180 CriticalSectionScoped lock(&_critSect); 121 CriticalSectionScoped lock(&_critSect);
181 _playChannels = channels; 122 _playChannels = channels;
182 // 16 bits per sample in mono, 32 bits in stereo 123 // 16 bits per sample in mono, 32 bits in stereo
183 _playBytesPerSample = 2 * channels; 124 _playBytesPerSample = 2 * channels;
184 return 0; 125 return 0;
185 } 126 }
186 127
187 // ----------------------------------------------------------------------------
188 // SetRecordingChannel
189 //
190 // Select which channel to use while recording.
191 // This API requires that stereo is enabled.
192 //
193 // Note that, the nChannel parameter in RecordedDataIsAvailable will be
194 // set to 2 even for kChannelLeft and kChannelRight. However, nBytesPerSample
195 // will be 2 instead of 4 four these cases.
196 // ----------------------------------------------------------------------------
197
198 int32_t AudioDeviceBuffer::SetRecordingChannel( 128 int32_t AudioDeviceBuffer::SetRecordingChannel(
199 const AudioDeviceModule::ChannelType channel) { 129 const AudioDeviceModule::ChannelType channel) {
200 CriticalSectionScoped lock(&_critSect); 130 CriticalSectionScoped lock(&_critSect);
201 131
202 if (_recChannels == 1) { 132 if (_recChannels == 1) {
203 return -1; 133 return -1;
204 } 134 }
205 135
206 if (channel == AudioDeviceModule::kChannelBoth) { 136 if (channel == AudioDeviceModule::kChannelBoth) {
207 // two bytes per channel 137 // two bytes per channel
208 _recBytesPerSample = 4; 138 _recBytesPerSample = 4;
209 } else { 139 } else {
210 // only utilize one out of two possible channels (left or right) 140 // only utilize one out of two possible channels (left or right)
211 _recBytesPerSample = 2; 141 _recBytesPerSample = 2;
212 } 142 }
213 _recChannel = channel; 143 _recChannel = channel;
214 144
215 return 0; 145 return 0;
216 } 146 }
217 147
218 // ----------------------------------------------------------------------------
219 // RecordingChannel
220 // ----------------------------------------------------------------------------
221
222 int32_t AudioDeviceBuffer::RecordingChannel( 148 int32_t AudioDeviceBuffer::RecordingChannel(
223 AudioDeviceModule::ChannelType& channel) const { 149 AudioDeviceModule::ChannelType& channel) const {
224 channel = _recChannel; 150 channel = _recChannel;
225 return 0; 151 return 0;
226 } 152 }
227 153
228 // ----------------------------------------------------------------------------
229 // RecordingChannels
230 // ----------------------------------------------------------------------------
231
232 size_t AudioDeviceBuffer::RecordingChannels() const { 154 size_t AudioDeviceBuffer::RecordingChannels() const {
233 return _recChannels; 155 return _recChannels;
234 } 156 }
235 157
236 // ----------------------------------------------------------------------------
237 // PlayoutChannels
238 // ----------------------------------------------------------------------------
239
240 size_t AudioDeviceBuffer::PlayoutChannels() const { 158 size_t AudioDeviceBuffer::PlayoutChannels() const {
241 return _playChannels; 159 return _playChannels;
242 } 160 }
243 161
244 // ----------------------------------------------------------------------------
245 // SetCurrentMicLevel
246 // ----------------------------------------------------------------------------
247
248 int32_t AudioDeviceBuffer::SetCurrentMicLevel(uint32_t level) { 162 int32_t AudioDeviceBuffer::SetCurrentMicLevel(uint32_t level) {
249 _currentMicLevel = level; 163 _currentMicLevel = level;
250 return 0; 164 return 0;
251 } 165 }
252 166
253 int32_t AudioDeviceBuffer::SetTypingStatus(bool typingStatus) { 167 int32_t AudioDeviceBuffer::SetTypingStatus(bool typingStatus) {
254 _typingStatus = typingStatus; 168 _typingStatus = typingStatus;
255 return 0; 169 return 0;
256 } 170 }
257 171
258 // ----------------------------------------------------------------------------
259 // NewMicLevel
260 // ----------------------------------------------------------------------------
261
262 uint32_t AudioDeviceBuffer::NewMicLevel() const { 172 uint32_t AudioDeviceBuffer::NewMicLevel() const {
263 return _newMicLevel; 173 return _newMicLevel;
264 } 174 }
265 175
266 // ----------------------------------------------------------------------------
267 // SetVQEData
268 // ----------------------------------------------------------------------------
269
270 void AudioDeviceBuffer::SetVQEData(int playDelayMs, 176 void AudioDeviceBuffer::SetVQEData(int playDelayMs,
271 int recDelayMs, 177 int recDelayMs,
272 int clockDrift) { 178 int clockDrift) {
273 if (high_delay_counter_ < kLogHighDelayIntervalFrames) { 179 if (high_delay_counter_ < kLogHighDelayIntervalFrames) {
274 ++high_delay_counter_; 180 ++high_delay_counter_;
275 } else { 181 } else {
276 if (playDelayMs + recDelayMs > kHighDelayThresholdMs) { 182 if (playDelayMs + recDelayMs > kHighDelayThresholdMs) {
277 high_delay_counter_ = 0; 183 high_delay_counter_ = 0;
278 LOG(LS_WARNING) << "High audio device delay reported (render=" 184 LOG(LS_WARNING) << "High audio device delay reported (render="
279 << playDelayMs << " ms, capture=" << recDelayMs << " ms)"; 185 << playDelayMs << " ms, capture=" << recDelayMs << " ms)";
280 } 186 }
281 } 187 }
282 188
283 _playDelayMS = playDelayMs; 189 _playDelayMS = playDelayMs;
284 _recDelayMS = recDelayMs; 190 _recDelayMS = recDelayMs;
285 _clockDrift = clockDrift; 191 _clockDrift = clockDrift;
286 } 192 }
287 193
288 // ----------------------------------------------------------------------------
289 // StartInputFileRecording
290 // ----------------------------------------------------------------------------
291
292 int32_t AudioDeviceBuffer::StartInputFileRecording( 194 int32_t AudioDeviceBuffer::StartInputFileRecording(
293 const char fileName[kAdmMaxFileNameSize]) { 195 const char fileName[kAdmMaxFileNameSize]) {
294 WEBRTC_TRACE(kTraceMemory, kTraceAudioDevice, _id, "%s", __FUNCTION__);
295
296 CriticalSectionScoped lock(&_critSect); 196 CriticalSectionScoped lock(&_critSect);
297 197
298 _recFile.Flush(); 198 _recFile.Flush();
299 _recFile.CloseFile(); 199 _recFile.CloseFile();
300 200
301 return _recFile.OpenFile(fileName, false) ? 0 : -1; 201 return _recFile.OpenFile(fileName, false) ? 0 : -1;
302 } 202 }
303 203
304 // ----------------------------------------------------------------------------
305 // StopInputFileRecording
306 // ----------------------------------------------------------------------------
307
308 int32_t AudioDeviceBuffer::StopInputFileRecording() { 204 int32_t AudioDeviceBuffer::StopInputFileRecording() {
309 WEBRTC_TRACE(kTraceMemory, kTraceAudioDevice, _id, "%s", __FUNCTION__);
310
311 CriticalSectionScoped lock(&_critSect); 205 CriticalSectionScoped lock(&_critSect);
312 206
313 _recFile.Flush(); 207 _recFile.Flush();
314 _recFile.CloseFile(); 208 _recFile.CloseFile();
315 209
316 return 0; 210 return 0;
317 } 211 }
318 212
319 // ----------------------------------------------------------------------------
320 // StartOutputFileRecording
321 // ----------------------------------------------------------------------------
322
323 int32_t AudioDeviceBuffer::StartOutputFileRecording( 213 int32_t AudioDeviceBuffer::StartOutputFileRecording(
324 const char fileName[kAdmMaxFileNameSize]) { 214 const char fileName[kAdmMaxFileNameSize]) {
325 WEBRTC_TRACE(kTraceMemory, kTraceAudioDevice, _id, "%s", __FUNCTION__);
326
327 CriticalSectionScoped lock(&_critSect); 215 CriticalSectionScoped lock(&_critSect);
328 216
329 _playFile.Flush(); 217 _playFile.Flush();
330 _playFile.CloseFile(); 218 _playFile.CloseFile();
331 219
332 return _playFile.OpenFile(fileName, false) ? 0 : -1; 220 return _playFile.OpenFile(fileName, false) ? 0 : -1;
333 } 221 }
334 222
335 // ----------------------------------------------------------------------------
336 // StopOutputFileRecording
337 // ----------------------------------------------------------------------------
338
339 int32_t AudioDeviceBuffer::StopOutputFileRecording() { 223 int32_t AudioDeviceBuffer::StopOutputFileRecording() {
340 WEBRTC_TRACE(kTraceMemory, kTraceAudioDevice, _id, "%s", __FUNCTION__);
341
342 CriticalSectionScoped lock(&_critSect); 224 CriticalSectionScoped lock(&_critSect);
343 225
344 _playFile.Flush(); 226 _playFile.Flush();
345 _playFile.CloseFile(); 227 _playFile.CloseFile();
346 228
347 return 0; 229 return 0;
348 } 230 }
349 231
350 // ----------------------------------------------------------------------------
351 // SetRecordedBuffer
352 //
353 // Store recorded audio buffer in local memory ready for the actual
354 // "delivery" using a callback.
355 //
356 // This method can also parse out left or right channel from a stereo
357 // input signal, i.e., emulate mono.
358 //
359 // Examples:
360 //
361 // 16-bit,48kHz mono, 10ms => nSamples=480 => _recSize=2*480=960 bytes
362 // 16-bit,48kHz stereo,10ms => nSamples=480 => _recSize=4*480=1920 bytes
363 // ----------------------------------------------------------------------------
364
365 int32_t AudioDeviceBuffer::SetRecordedBuffer(const void* audioBuffer, 232 int32_t AudioDeviceBuffer::SetRecordedBuffer(const void* audioBuffer,
366 size_t nSamples) { 233 size_t nSamples) {
367 CriticalSectionScoped lock(&_critSect); 234 CriticalSectionScoped lock(&_critSect);
368 235
369 if (_recBytesPerSample == 0) { 236 if (_recBytesPerSample == 0) {
370 assert(false); 237 assert(false);
371 return -1; 238 return -1;
372 } 239 }
373 240
374 _recSamples = nSamples; 241 _recSamples = nSamples;
(...skipping 24 matching lines...) Expand all
399 } 266 }
400 267
401 if (_recFile.is_open()) { 268 if (_recFile.is_open()) {
402 // write to binary file in mono or stereo (interleaved) 269 // write to binary file in mono or stereo (interleaved)
403 _recFile.Write(&_recBuffer[0], _recSize); 270 _recFile.Write(&_recBuffer[0], _recSize);
404 } 271 }
405 272
406 return 0; 273 return 0;
407 } 274 }
408 275
409 // ----------------------------------------------------------------------------
410 // DeliverRecordedData
411 // ----------------------------------------------------------------------------
412
413 int32_t AudioDeviceBuffer::DeliverRecordedData() { 276 int32_t AudioDeviceBuffer::DeliverRecordedData() {
414 CriticalSectionScoped lock(&_critSectCb); 277 CriticalSectionScoped lock(&_critSectCb);
415
416 // Ensure that user has initialized all essential members 278 // Ensure that user has initialized all essential members
417 if ((_recSampleRate == 0) || (_recSamples == 0) || 279 if ((_recSampleRate == 0) || (_recSamples == 0) ||
418 (_recBytesPerSample == 0) || (_recChannels == 0)) { 280 (_recBytesPerSample == 0) || (_recChannels == 0)) {
419 assert(false); 281 RTC_NOTREACHED();
420 return -1; 282 return -1;
421 } 283 }
422 284
423 if (_ptrCbAudioTransport == NULL) { 285 if (!_ptrCbAudioTransport) {
424 WEBRTC_TRACE( 286 LOG(LS_WARNING) << "Invalid audio transport";
425 kTraceWarning, kTraceAudioDevice, _id,
426 "failed to deliver recorded data (AudioTransport does not exist)");
427 return 0; 287 return 0;
428 } 288 }
429 289
430 int32_t res(0); 290 int32_t res(0);
431 uint32_t newMicLevel(0); 291 uint32_t newMicLevel(0);
432 uint32_t totalDelayMS = _playDelayMS + _recDelayMS; 292 uint32_t totalDelayMS = _playDelayMS + _recDelayMS;
433
434 res = _ptrCbAudioTransport->RecordedDataIsAvailable( 293 res = _ptrCbAudioTransport->RecordedDataIsAvailable(
435 &_recBuffer[0], _recSamples, _recBytesPerSample, _recChannels, 294 &_recBuffer[0], _recSamples, _recBytesPerSample, _recChannels,
436 _recSampleRate, totalDelayMS, _clockDrift, _currentMicLevel, 295 _recSampleRate, totalDelayMS, _clockDrift, _currentMicLevel,
437 _typingStatus, newMicLevel); 296 _typingStatus, newMicLevel);
438 if (res != -1) { 297 if (res != -1) {
439 _newMicLevel = newMicLevel; 298 _newMicLevel = newMicLevel;
440 } 299 }
441 300
442 return 0; 301 return 0;
443 } 302 }
444 303
445 // ----------------------------------------------------------------------------
446 // RequestPlayoutData
447 // ----------------------------------------------------------------------------
448
449 int32_t AudioDeviceBuffer::RequestPlayoutData(size_t nSamples) { 304 int32_t AudioDeviceBuffer::RequestPlayoutData(size_t nSamples) {
450 uint32_t playSampleRate = 0; 305 uint32_t playSampleRate = 0;
451 size_t playBytesPerSample = 0; 306 size_t playBytesPerSample = 0;
452 size_t playChannels = 0; 307 size_t playChannels = 0;
308
309 // TOOD(henrika): improve bad locking model and make it more clear that only
310 // 10ms buffer sizes is supported in WebRTC.
453 { 311 {
454 CriticalSectionScoped lock(&_critSect); 312 CriticalSectionScoped lock(&_critSect);
455 313
456 // Store copies under lock and use copies hereafter to avoid race with 314 // Store copies under lock and use copies hereafter to avoid race with
457 // setter methods. 315 // setter methods.
458 playSampleRate = _playSampleRate; 316 playSampleRate = _playSampleRate;
459 playBytesPerSample = _playBytesPerSample; 317 playBytesPerSample = _playBytesPerSample;
460 playChannels = _playChannels; 318 playChannels = _playChannels;
461 319
462 // Ensure that user has initialized all essential members 320 // Ensure that user has initialized all essential members
463 if ((playBytesPerSample == 0) || (playChannels == 0) || 321 if ((playBytesPerSample == 0) || (playChannels == 0) ||
464 (playSampleRate == 0)) { 322 (playSampleRate == 0)) {
465 assert(false); 323 RTC_NOTREACHED();
466 return -1; 324 return -1;
467 } 325 }
468 326
469 _playSamples = nSamples; 327 _playSamples = nSamples;
470 _playSize = playBytesPerSample * nSamples; // {2,4}*nSamples 328 _playSize = playBytesPerSample * nSamples; // {2,4}*nSamples
471 if (_playSize > kMaxBufferSizeBytes) { 329 RTC_CHECK_LE(_playSize, kMaxBufferSizeBytes);
472 assert(false); 330 RTC_CHECK_EQ(nSamples, _playSamples);
473 return -1;
474 }
475
476 if (nSamples != _playSamples) {
477 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id,
478 "invalid number of samples to be played out (%d)", nSamples);
479 return -1;
480 }
481 } 331 }
482 332
483 size_t nSamplesOut(0); 333 size_t nSamplesOut(0);
484 334
485 CriticalSectionScoped lock(&_critSectCb); 335 CriticalSectionScoped lock(&_critSectCb);
486 336
487 if (_ptrCbAudioTransport == NULL) { 337 // It is currently supported to start playout without a valid audio
488 WEBRTC_TRACE( 338 // transport object. Leads to warning and silence.
489 kTraceWarning, kTraceAudioDevice, _id, 339 if (!_ptrCbAudioTransport) {
490 "failed to feed data to playout (AudioTransport does not exist)"); 340 LOG(LS_WARNING) << "Invalid audio transport";
491 return 0; 341 return 0;
492 } 342 }
493 343
494 if (_ptrCbAudioTransport) { 344 uint32_t res(0);
495 uint32_t res(0); 345 int64_t elapsed_time_ms = -1;
496 int64_t elapsed_time_ms = -1; 346 int64_t ntp_time_ms = -1;
497 int64_t ntp_time_ms = -1; 347 res = _ptrCbAudioTransport->NeedMorePlayData(
498 res = _ptrCbAudioTransport->NeedMorePlayData( 348 _playSamples, playBytesPerSample, playChannels, playSampleRate,
499 _playSamples, playBytesPerSample, playChannels, playSampleRate, 349 &_playBuffer[0], nSamplesOut, &elapsed_time_ms, &ntp_time_ms);
500 &_playBuffer[0], nSamplesOut, &elapsed_time_ms, &ntp_time_ms); 350 if (res != 0) {
501 if (res != 0) { 351 LOG(LS_ERROR) << "NeedMorePlayData() failed";
502 WEBRTC_TRACE(kTraceError, kTraceAudioDevice, _id,
503 "NeedMorePlayData() failed");
504 }
505 } 352 }
506 353
507 return static_cast<int32_t>(nSamplesOut); 354 return static_cast<int32_t>(nSamplesOut);
508 } 355 }
509 356
510 // ----------------------------------------------------------------------------
511 // GetPlayoutData
512 // ----------------------------------------------------------------------------
513
514 int32_t AudioDeviceBuffer::GetPlayoutData(void* audioBuffer) { 357 int32_t AudioDeviceBuffer::GetPlayoutData(void* audioBuffer) {
515 CriticalSectionScoped lock(&_critSect); 358 CriticalSectionScoped lock(&_critSect);
516 359 RTC_CHECK_LE(_playSize, kMaxBufferSizeBytes);
517 if (_playSize > kMaxBufferSizeBytes) {
518 WEBRTC_TRACE(kTraceError, kTraceUtility, _id,
519 "_playSize %" PRIuS
520 " exceeds kMaxBufferSizeBytes in "
521 "AudioDeviceBuffer::GetPlayoutData",
522 _playSize);
523 assert(false);
524 return -1;
525 }
526 360
527 memcpy(audioBuffer, &_playBuffer[0], _playSize); 361 memcpy(audioBuffer, &_playBuffer[0], _playSize);
528 362
529 if (_playFile.is_open()) { 363 if (_playFile.is_open()) {
530 // write to binary file in mono or stereo (interleaved) 364 // write to binary file in mono or stereo (interleaved)
531 _playFile.Write(&_playBuffer[0], _playSize); 365 _playFile.Write(&_playBuffer[0], _playSize);
532 } 366 }
533 367
534 return static_cast<int32_t>(_playSamples); 368 return static_cast<int32_t>(_playSamples);
535 } 369 }
536 370
537 } // namespace webrtc 371 } // namespace webrtc
OLDNEW
« no previous file with comments | « webrtc/modules/audio_device/audio_device_buffer.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698