OLD | NEW |
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 <assert.h> | 11 #include <assert.h> |
12 | 12 |
13 #include "webrtc/modules/audio_device/linux/audio_mixer_manager_pulse_linux.h" | 13 #include "webrtc/modules/audio_device/linux/audio_mixer_manager_pulse_linux.h" |
14 #include "webrtc/rtc_base/checks.h" | 14 #include "webrtc/rtc_base/checks.h" |
15 #include "webrtc/system_wrappers/include/trace.h" | 15 #include "webrtc/rtc_base/logging.h" |
16 | 16 |
17 extern webrtc::adm_linux_pulse::PulseAudioSymbolTable PaSymbolTable; | 17 extern webrtc::adm_linux_pulse::PulseAudioSymbolTable PaSymbolTable; |
18 | 18 |
19 // Accesses Pulse functions through our late-binding symbol table instead of | 19 // Accesses Pulse functions through our late-binding symbol table instead of |
20 // directly. This way we don't have to link to libpulse, which means our | 20 // directly. This way we don't have to link to libpulse, which means our |
21 // binary will work on systems that don't have it. | 21 // binary will work on systems that don't have it. |
22 #define LATE(sym) \ | 22 #define LATE(sym) \ |
23 LATESYM_GET(webrtc::adm_linux_pulse::PulseAudioSymbolTable, &PaSymbolTable, \ | 23 LATESYM_GET(webrtc::adm_linux_pulse::PulseAudioSymbolTable, &PaSymbolTable, \ |
24 sym) | 24 sym) |
25 | 25 |
26 namespace webrtc | 26 namespace webrtc |
27 { | 27 { |
28 | 28 |
29 class AutoPulseLock { | 29 class AutoPulseLock { |
30 public: | 30 public: |
31 explicit AutoPulseLock(pa_threaded_mainloop* pa_mainloop) | 31 explicit AutoPulseLock(pa_threaded_mainloop* pa_mainloop) |
32 : pa_mainloop_(pa_mainloop) { | 32 : pa_mainloop_(pa_mainloop) { |
33 LATE(pa_threaded_mainloop_lock)(pa_mainloop_); | 33 LATE(pa_threaded_mainloop_lock)(pa_mainloop_); |
34 } | 34 } |
35 | 35 |
36 ~AutoPulseLock() { | 36 ~AutoPulseLock() { |
37 LATE(pa_threaded_mainloop_unlock)(pa_mainloop_); | 37 LATE(pa_threaded_mainloop_unlock)(pa_mainloop_); |
38 } | 38 } |
39 | 39 |
40 private: | 40 private: |
41 pa_threaded_mainloop* const pa_mainloop_; | 41 pa_threaded_mainloop* const pa_mainloop_; |
42 }; | 42 }; |
43 | 43 |
44 AudioMixerManagerLinuxPulse::AudioMixerManagerLinuxPulse(const int32_t id) : | 44 AudioMixerManagerLinuxPulse::AudioMixerManagerLinuxPulse() : |
45 _id(id), | |
46 _paOutputDeviceIndex(-1), | 45 _paOutputDeviceIndex(-1), |
47 _paInputDeviceIndex(-1), | 46 _paInputDeviceIndex(-1), |
48 _paPlayStream(NULL), | 47 _paPlayStream(NULL), |
49 _paRecStream(NULL), | 48 _paRecStream(NULL), |
50 _paMainloop(NULL), | 49 _paMainloop(NULL), |
51 _paContext(NULL), | 50 _paContext(NULL), |
52 _paVolume(0), | 51 _paVolume(0), |
53 _paMute(0), | 52 _paMute(0), |
54 _paVolSteps(0), | 53 _paVolSteps(0), |
55 _paSpeakerMute(false), | 54 _paSpeakerMute(false), |
56 _paSpeakerVolume(PA_VOLUME_NORM), | 55 _paSpeakerVolume(PA_VOLUME_NORM), |
57 _paChannels(0), | 56 _paChannels(0), |
58 _paObjectsSet(false) | 57 _paObjectsSet(false) |
59 { | 58 { |
60 WEBRTC_TRACE(kTraceMemory, kTraceAudioDevice, _id, | 59 LOG(LS_INFO) << __FUNCTION__ << " created"; |
61 "%s constructed", __FUNCTION__); | |
62 } | 60 } |
63 | 61 |
64 AudioMixerManagerLinuxPulse::~AudioMixerManagerLinuxPulse() | 62 AudioMixerManagerLinuxPulse::~AudioMixerManagerLinuxPulse() |
65 { | 63 { |
66 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 64 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
67 WEBRTC_TRACE(kTraceMemory, kTraceAudioDevice, _id, | 65 LOG(LS_INFO) << __FUNCTION__ << " destroyed"; |
68 "%s destructed", __FUNCTION__); | |
69 | 66 |
70 Close(); | 67 Close(); |
71 } | 68 } |
72 | 69 |
73 // =========================================================================== | 70 // =========================================================================== |
74 // PUBLIC METHODS | 71 // PUBLIC METHODS |
75 // =========================================================================== | 72 // =========================================================================== |
76 | 73 |
77 int32_t AudioMixerManagerLinuxPulse::SetPulseAudioObjects( | 74 int32_t AudioMixerManagerLinuxPulse::SetPulseAudioObjects( |
78 pa_threaded_mainloop* mainloop, | 75 pa_threaded_mainloop* mainloop, |
79 pa_context* context) | 76 pa_context* context) |
80 { | 77 { |
81 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 78 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
82 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, "%s", | 79 LOG(LS_VERBOSE) << __FUNCTION__; |
83 __FUNCTION__); | |
84 | 80 |
85 if (!mainloop || !context) | 81 if (!mainloop || !context) |
86 { | 82 { |
87 WEBRTC_TRACE(kTraceError, kTraceAudioDevice, _id, | 83 LOG(LS_ERROR) << "could not set PulseAudio objects for mixer"; |
88 " could not set PulseAudio objects for mixer"); | |
89 return -1; | 84 return -1; |
90 } | 85 } |
91 | 86 |
92 _paMainloop = mainloop; | 87 _paMainloop = mainloop; |
93 _paContext = context; | 88 _paContext = context; |
94 _paObjectsSet = true; | 89 _paObjectsSet = true; |
95 | 90 |
96 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 91 LOG(LS_VERBOSE) << "the PulseAudio objects for the mixer has been set"; |
97 " the PulseAudio objects for the mixer has been set"); | |
98 | 92 |
99 return 0; | 93 return 0; |
100 } | 94 } |
101 | 95 |
102 int32_t AudioMixerManagerLinuxPulse::Close() | 96 int32_t AudioMixerManagerLinuxPulse::Close() |
103 { | 97 { |
104 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 98 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
105 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, "%s", | 99 LOG(LS_VERBOSE) << __FUNCTION__; |
106 __FUNCTION__); | |
107 | 100 |
108 CloseSpeaker(); | 101 CloseSpeaker(); |
109 CloseMicrophone(); | 102 CloseMicrophone(); |
110 | 103 |
111 _paMainloop = NULL; | 104 _paMainloop = NULL; |
112 _paContext = NULL; | 105 _paContext = NULL; |
113 _paObjectsSet = false; | 106 _paObjectsSet = false; |
114 | 107 |
115 return 0; | 108 return 0; |
116 | 109 |
117 } | 110 } |
118 | 111 |
119 int32_t AudioMixerManagerLinuxPulse::CloseSpeaker() | 112 int32_t AudioMixerManagerLinuxPulse::CloseSpeaker() |
120 { | 113 { |
121 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 114 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
122 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, "%s", | 115 LOG(LS_VERBOSE) << __FUNCTION__; |
123 __FUNCTION__); | |
124 | 116 |
125 // Reset the index to -1 | 117 // Reset the index to -1 |
126 _paOutputDeviceIndex = -1; | 118 _paOutputDeviceIndex = -1; |
127 _paPlayStream = NULL; | 119 _paPlayStream = NULL; |
128 | 120 |
129 return 0; | 121 return 0; |
130 } | 122 } |
131 | 123 |
132 int32_t AudioMixerManagerLinuxPulse::CloseMicrophone() | 124 int32_t AudioMixerManagerLinuxPulse::CloseMicrophone() |
133 { | 125 { |
134 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 126 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
135 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, "%s", | 127 LOG(LS_VERBOSE) << __FUNCTION__; |
136 __FUNCTION__); | |
137 | 128 |
138 // Reset the index to -1 | 129 // Reset the index to -1 |
139 _paInputDeviceIndex = -1; | 130 _paInputDeviceIndex = -1; |
140 _paRecStream = NULL; | 131 _paRecStream = NULL; |
141 | 132 |
142 return 0; | 133 return 0; |
143 } | 134 } |
144 | 135 |
145 int32_t AudioMixerManagerLinuxPulse::SetPlayStream(pa_stream* playStream) | 136 int32_t AudioMixerManagerLinuxPulse::SetPlayStream(pa_stream* playStream) |
146 { | 137 { |
147 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 138 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
148 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 139 LOG(LS_VERBOSE) << "AudioMixerManagerLinuxPulse::SetPlayStream(playStream)"; |
149 "AudioMixerManagerLinuxPulse::SetPlayStream(playStream)"); | |
150 | 140 |
151 _paPlayStream = playStream; | 141 _paPlayStream = playStream; |
152 return 0; | 142 return 0; |
153 } | 143 } |
154 | 144 |
155 int32_t AudioMixerManagerLinuxPulse::SetRecStream(pa_stream* recStream) | 145 int32_t AudioMixerManagerLinuxPulse::SetRecStream(pa_stream* recStream) |
156 { | 146 { |
157 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 147 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
158 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 148 LOG(LS_VERBOSE) << "AudioMixerManagerLinuxPulse::SetRecStream(recStream)"; |
159 "AudioMixerManagerLinuxPulse::SetRecStream(recStream)"); | |
160 | 149 |
161 _paRecStream = recStream; | 150 _paRecStream = recStream; |
162 return 0; | 151 return 0; |
163 } | 152 } |
164 | 153 |
165 int32_t AudioMixerManagerLinuxPulse::OpenSpeaker( | 154 int32_t AudioMixerManagerLinuxPulse::OpenSpeaker( |
166 uint16_t deviceIndex) | 155 uint16_t deviceIndex) |
167 { | 156 { |
168 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 157 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
169 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 158 LOG(LS_VERBOSE) << "AudioMixerManagerLinuxPulse::OpenSpeaker(deviceIndex=" |
170 "AudioMixerManagerLinuxPulse::OpenSpeaker(deviceIndex=%d)", | 159 << deviceIndex << ")"; |
171 deviceIndex); | |
172 | 160 |
173 // No point in opening the speaker | 161 // No point in opening the speaker |
174 // if PA objects have not been set | 162 // if PA objects have not been set |
175 if (!_paObjectsSet) | 163 if (!_paObjectsSet) |
176 { | 164 { |
177 WEBRTC_TRACE(kTraceError, kTraceAudioDevice, _id, | 165 LOG(LS_ERROR) << "PulseAudio objects has not been set"; |
178 " PulseAudio objects has not been set"); | |
179 return -1; | 166 return -1; |
180 } | 167 } |
181 | 168 |
182 // Set the index for the PulseAudio | 169 // Set the index for the PulseAudio |
183 // output device to control | 170 // output device to control |
184 _paOutputDeviceIndex = deviceIndex; | 171 _paOutputDeviceIndex = deviceIndex; |
185 | 172 |
186 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 173 LOG(LS_VERBOSE) << "the output mixer device is now open"; |
187 " the output mixer device is now open"); | |
188 | 174 |
189 return 0; | 175 return 0; |
190 } | 176 } |
191 | 177 |
192 int32_t AudioMixerManagerLinuxPulse::OpenMicrophone( | 178 int32_t AudioMixerManagerLinuxPulse::OpenMicrophone( |
193 uint16_t deviceIndex) | 179 uint16_t deviceIndex) |
194 { | 180 { |
195 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 181 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
196 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 182 LOG(LS_VERBOSE) |
197 "AudioMixerManagerLinuxPulse::OpenMicrophone" | 183 << "AudioMixerManagerLinuxPulse::OpenMicrophone(deviceIndex=" |
198 "(deviceIndex=%d)", deviceIndex); | 184 << deviceIndex << ")"; |
199 | 185 |
200 // No point in opening the microphone | 186 // No point in opening the microphone |
201 // if PA objects have not been set | 187 // if PA objects have not been set |
202 if (!_paObjectsSet) | 188 if (!_paObjectsSet) |
203 { | 189 { |
204 WEBRTC_TRACE(kTraceError, kTraceAudioDevice, _id, | 190 LOG(LS_ERROR) << "PulseAudio objects have not been set"; |
205 " PulseAudio objects have not been set"); | |
206 return -1; | 191 return -1; |
207 } | 192 } |
208 | 193 |
209 // Set the index for the PulseAudio | 194 // Set the index for the PulseAudio |
210 // input device to control | 195 // input device to control |
211 _paInputDeviceIndex = deviceIndex; | 196 _paInputDeviceIndex = deviceIndex; |
212 | 197 |
213 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 198 LOG(LS_VERBOSE) << "the input mixer device is now open"; |
214 " the input mixer device is now open"); | |
215 | 199 |
216 return 0; | 200 return 0; |
217 } | 201 } |
218 | 202 |
219 bool AudioMixerManagerLinuxPulse::SpeakerIsInitialized() const | 203 bool AudioMixerManagerLinuxPulse::SpeakerIsInitialized() const |
220 { | 204 { |
221 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 205 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
222 WEBRTC_TRACE(kTraceMemory, kTraceAudioDevice, _id, "%s", | 206 LOG(LS_INFO) << __FUNCTION__; |
223 __FUNCTION__); | |
224 | 207 |
225 return (_paOutputDeviceIndex != -1); | 208 return (_paOutputDeviceIndex != -1); |
226 } | 209 } |
227 | 210 |
228 bool AudioMixerManagerLinuxPulse::MicrophoneIsInitialized() const | 211 bool AudioMixerManagerLinuxPulse::MicrophoneIsInitialized() const |
229 { | 212 { |
230 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 213 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
231 WEBRTC_TRACE(kTraceMemory, kTraceAudioDevice, _id, "%s", | 214 LOG(LS_INFO) << __FUNCTION__; |
232 __FUNCTION__); | |
233 | 215 |
234 return (_paInputDeviceIndex != -1); | 216 return (_paInputDeviceIndex != -1); |
235 } | 217 } |
236 | 218 |
237 int32_t AudioMixerManagerLinuxPulse::SetSpeakerVolume( | 219 int32_t AudioMixerManagerLinuxPulse::SetSpeakerVolume( |
238 uint32_t volume) | 220 uint32_t volume) |
239 { | 221 { |
240 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 222 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
241 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 223 LOG(LS_VERBOSE) << "AudioMixerManagerLinuxPulse::SetSpeakerVolume(volume=" |
242 "AudioMixerManagerLinuxPulse::SetSpeakerVolume(volume=%u)", | 224 << volume << ")"; |
243 volume); | |
244 | 225 |
245 if (_paOutputDeviceIndex == -1) | 226 if (_paOutputDeviceIndex == -1) |
246 { | 227 { |
247 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 228 LOG(LS_WARNING) << "output device index has not been set"; |
248 " output device index has not been set"); | |
249 return -1; | 229 return -1; |
250 } | 230 } |
251 | 231 |
252 bool setFailed(false); | 232 bool setFailed(false); |
253 | 233 |
254 if (_paPlayStream && (LATE(pa_stream_get_state)(_paPlayStream) | 234 if (_paPlayStream && (LATE(pa_stream_get_state)(_paPlayStream) |
255 != PA_STREAM_UNCONNECTED)) | 235 != PA_STREAM_UNCONNECTED)) |
256 { | 236 { |
257 // We can only really set the volume if we have a connected stream | 237 // We can only really set the volume if we have a connected stream |
258 AutoPulseLock auto_lock(_paMainloop); | 238 AutoPulseLock auto_lock(_paMainloop); |
259 | 239 |
260 // Get the number of channels from the sample specification | 240 // Get the number of channels from the sample specification |
261 const pa_sample_spec *spec = | 241 const pa_sample_spec *spec = |
262 LATE(pa_stream_get_sample_spec)(_paPlayStream); | 242 LATE(pa_stream_get_sample_spec)(_paPlayStream); |
263 if (!spec) | 243 if (!spec) |
264 { | 244 { |
265 WEBRTC_TRACE(kTraceError, kTraceAudioDevice, _id, | 245 LOG(LS_ERROR) << "could not get sample specification"; |
266 " could not get sample specification"); | |
267 return -1; | 246 return -1; |
268 } | 247 } |
269 | 248 |
270 // Set the same volume for all channels | 249 // Set the same volume for all channels |
271 pa_cvolume cVolumes; | 250 pa_cvolume cVolumes; |
272 LATE(pa_cvolume_set)(&cVolumes, spec->channels, volume); | 251 LATE(pa_cvolume_set)(&cVolumes, spec->channels, volume); |
273 | 252 |
274 pa_operation* paOperation = NULL; | 253 pa_operation* paOperation = NULL; |
275 paOperation = LATE(pa_context_set_sink_input_volume)( | 254 paOperation = LATE(pa_context_set_sink_input_volume)( |
276 _paContext, | 255 _paContext, |
277 LATE(pa_stream_get_index)(_paPlayStream), | 256 LATE(pa_stream_get_index)(_paPlayStream), |
278 &cVolumes, | 257 &cVolumes, |
279 PaSetVolumeCallback, NULL); | 258 PaSetVolumeCallback, NULL); |
280 if (!paOperation) | 259 if (!paOperation) |
281 { | 260 { |
282 setFailed = true; | 261 setFailed = true; |
283 } | 262 } |
284 | 263 |
285 // Don't need to wait for the completion | 264 // Don't need to wait for the completion |
286 LATE(pa_operation_unref)(paOperation); | 265 LATE(pa_operation_unref)(paOperation); |
287 } else | 266 } else |
288 { | 267 { |
289 // We have not created a stream or it's not connected to the sink | 268 // We have not created a stream or it's not connected to the sink |
290 // Save the volume to be set at connection | 269 // Save the volume to be set at connection |
291 _paSpeakerVolume = volume; | 270 _paSpeakerVolume = volume; |
292 } | 271 } |
293 | 272 |
294 if (setFailed) | 273 if (setFailed) |
295 { | 274 { |
296 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 275 LOG(LS_WARNING) << "could not set speaker volume, error=" |
297 " could not set speaker volume, error%d", | 276 << LATE(pa_context_errno)(_paContext); |
298 LATE(pa_context_errno)(_paContext)); | |
299 | 277 |
300 return -1; | 278 return -1; |
301 } | 279 } |
302 | 280 |
303 return 0; | 281 return 0; |
304 } | 282 } |
305 | 283 |
306 int32_t | 284 int32_t |
307 AudioMixerManagerLinuxPulse::SpeakerVolume(uint32_t& volume) const | 285 AudioMixerManagerLinuxPulse::SpeakerVolume(uint32_t& volume) const |
308 { | 286 { |
309 if (_paOutputDeviceIndex == -1) | 287 if (_paOutputDeviceIndex == -1) |
310 { | 288 { |
311 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 289 LOG(LS_WARNING) << "output device index has not been set"; |
312 " output device index has not been set"); | |
313 return -1; | 290 return -1; |
314 } | 291 } |
315 | 292 |
316 if (_paPlayStream && (LATE(pa_stream_get_state)(_paPlayStream) | 293 if (_paPlayStream && (LATE(pa_stream_get_state)(_paPlayStream) |
317 != PA_STREAM_UNCONNECTED)) | 294 != PA_STREAM_UNCONNECTED)) |
318 { | 295 { |
319 // We can only get the volume if we have a connected stream | 296 // We can only get the volume if we have a connected stream |
320 if (!GetSinkInputInfo()) | 297 if (!GetSinkInputInfo()) |
321 return -1; | 298 return -1; |
322 | 299 |
323 AutoPulseLock auto_lock(_paMainloop); | 300 AutoPulseLock auto_lock(_paMainloop); |
324 volume = static_cast<uint32_t> (_paVolume); | 301 volume = static_cast<uint32_t> (_paVolume); |
325 } else | 302 } else |
326 { | 303 { |
327 AutoPulseLock auto_lock(_paMainloop); | 304 AutoPulseLock auto_lock(_paMainloop); |
328 volume = _paSpeakerVolume; | 305 volume = _paSpeakerVolume; |
329 } | 306 } |
330 | 307 |
331 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 308 LOG(LS_VERBOSE) << "AudioMixerManagerLinuxPulse::SpeakerVolume() => vol=" |
332 "\tAudioMixerManagerLinuxPulse::SpeakerVolume() => vol=%i", | 309 << volume; |
333 volume); | |
334 | 310 |
335 return 0; | 311 return 0; |
336 } | 312 } |
337 | 313 |
338 int32_t | 314 int32_t |
339 AudioMixerManagerLinuxPulse::MaxSpeakerVolume(uint32_t& maxVolume) const | 315 AudioMixerManagerLinuxPulse::MaxSpeakerVolume(uint32_t& maxVolume) const |
340 { | 316 { |
341 | 317 |
342 if (_paOutputDeviceIndex == -1) | 318 if (_paOutputDeviceIndex == -1) |
343 { | 319 { |
344 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 320 LOG(LS_WARNING) << "output device index has not been set"; |
345 " output device index has not been set"); | |
346 return -1; | 321 return -1; |
347 } | 322 } |
348 | 323 |
349 // PA_VOLUME_NORM corresponds to 100% (0db) | 324 // PA_VOLUME_NORM corresponds to 100% (0db) |
350 // but PA allows up to 150 db amplification | 325 // but PA allows up to 150 db amplification |
351 maxVolume = static_cast<uint32_t> (PA_VOLUME_NORM); | 326 maxVolume = static_cast<uint32_t> (PA_VOLUME_NORM); |
352 | 327 |
353 return 0; | 328 return 0; |
354 } | 329 } |
355 | 330 |
356 int32_t | 331 int32_t |
357 AudioMixerManagerLinuxPulse::MinSpeakerVolume(uint32_t& minVolume) const | 332 AudioMixerManagerLinuxPulse::MinSpeakerVolume(uint32_t& minVolume) const |
358 { | 333 { |
359 | 334 |
360 if (_paOutputDeviceIndex == -1) | 335 if (_paOutputDeviceIndex == -1) |
361 { | 336 { |
362 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 337 LOG(LS_WARNING) << "output device index has not been set"; |
363 " output device index has not been set"); | |
364 return -1; | 338 return -1; |
365 } | 339 } |
366 | 340 |
367 minVolume = static_cast<uint32_t> (PA_VOLUME_MUTED); | 341 minVolume = static_cast<uint32_t> (PA_VOLUME_MUTED); |
368 | 342 |
369 return 0; | 343 return 0; |
370 } | 344 } |
371 | 345 |
372 int32_t | 346 int32_t |
373 AudioMixerManagerLinuxPulse::SpeakerVolumeStepSize(uint16_t& stepSize) const | 347 AudioMixerManagerLinuxPulse::SpeakerVolumeStepSize(uint16_t& stepSize) const |
374 { | 348 { |
375 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 349 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
376 if (_paOutputDeviceIndex == -1) | 350 if (_paOutputDeviceIndex == -1) |
377 { | 351 { |
378 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 352 LOG(LS_WARNING) << "output device index has not been set"; |
379 " output device index has not been set"); | |
380 return -1; | 353 return -1; |
381 } | 354 } |
382 | 355 |
383 // The sink input (stream) will always have step size = 1 | 356 // The sink input (stream) will always have step size = 1 |
384 // There are PA_VOLUME_NORM+1 steps | 357 // There are PA_VOLUME_NORM+1 steps |
385 stepSize = 1; | 358 stepSize = 1; |
386 | 359 |
387 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 360 LOG(LS_VERBOSE) |
388 "\tAudioMixerManagerLinuxPulse::SpeakerVolumeStepSize() => " | 361 << "AudioMixerManagerLinuxPulse::SpeakerVolumeStepSize() => size=" |
389 "size=%i", stepSize); | 362 << stepSize; |
390 | 363 |
391 return 0; | 364 return 0; |
392 } | 365 } |
393 | 366 |
394 int32_t | 367 int32_t |
395 AudioMixerManagerLinuxPulse::SpeakerVolumeIsAvailable(bool& available) | 368 AudioMixerManagerLinuxPulse::SpeakerVolumeIsAvailable(bool& available) |
396 { | 369 { |
397 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 370 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
398 if (_paOutputDeviceIndex == -1) | 371 if (_paOutputDeviceIndex == -1) |
399 { | 372 { |
400 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 373 LOG(LS_WARNING) << "output device index has not been set"; |
401 " output device index has not been set"); | |
402 return -1; | 374 return -1; |
403 } | 375 } |
404 | 376 |
405 // Always available in Pulse Audio | 377 // Always available in Pulse Audio |
406 available = true; | 378 available = true; |
407 | 379 |
408 return 0; | 380 return 0; |
409 } | 381 } |
410 | 382 |
411 int32_t | 383 int32_t |
412 AudioMixerManagerLinuxPulse::SpeakerMuteIsAvailable(bool& available) | 384 AudioMixerManagerLinuxPulse::SpeakerMuteIsAvailable(bool& available) |
413 { | 385 { |
414 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 386 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
415 if (_paOutputDeviceIndex == -1) | 387 if (_paOutputDeviceIndex == -1) |
416 { | 388 { |
417 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 389 LOG(LS_WARNING) << "output device index has not been set"; |
418 " output device index has not been set"); | |
419 return -1; | 390 return -1; |
420 } | 391 } |
421 | 392 |
422 // Always available in Pulse Audio | 393 // Always available in Pulse Audio |
423 available = true; | 394 available = true; |
424 | 395 |
425 return 0; | 396 return 0; |
426 } | 397 } |
427 | 398 |
428 int32_t AudioMixerManagerLinuxPulse::SetSpeakerMute(bool enable) | 399 int32_t AudioMixerManagerLinuxPulse::SetSpeakerMute(bool enable) |
429 { | 400 { |
430 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 401 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
431 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 402 LOG(LS_VERBOSE) << "AudioMixerManagerLinuxPulse::SetSpeakerMute(enable=" |
432 "AudioMixerManagerLinuxPulse::SetSpeakerMute(enable=%u)", | 403 << enable << ")"; |
433 enable); | |
434 | 404 |
435 if (_paOutputDeviceIndex == -1) | 405 if (_paOutputDeviceIndex == -1) |
436 { | 406 { |
437 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 407 LOG(LS_WARNING) << "output device index has not been set"; |
438 " output device index has not been set"); | |
439 return -1; | 408 return -1; |
440 } | 409 } |
441 | 410 |
442 bool setFailed(false); | 411 bool setFailed(false); |
443 | 412 |
444 if (_paPlayStream && (LATE(pa_stream_get_state)(_paPlayStream) | 413 if (_paPlayStream && (LATE(pa_stream_get_state)(_paPlayStream) |
445 != PA_STREAM_UNCONNECTED)) | 414 != PA_STREAM_UNCONNECTED)) |
446 { | 415 { |
447 // We can only really mute if we have a connected stream | 416 // We can only really mute if we have a connected stream |
448 AutoPulseLock auto_lock(_paMainloop); | 417 AutoPulseLock auto_lock(_paMainloop); |
(...skipping 14 matching lines...) Expand all Loading... |
463 LATE(pa_operation_unref)(paOperation); | 432 LATE(pa_operation_unref)(paOperation); |
464 } else | 433 } else |
465 { | 434 { |
466 // We have not created a stream or it's not connected to the sink | 435 // We have not created a stream or it's not connected to the sink |
467 // Save the mute status to be set at connection | 436 // Save the mute status to be set at connection |
468 _paSpeakerMute = enable; | 437 _paSpeakerMute = enable; |
469 } | 438 } |
470 | 439 |
471 if (setFailed) | 440 if (setFailed) |
472 { | 441 { |
473 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 442 LOG(LS_WARNING) << "could not mute speaker, error=" |
474 " could not mute speaker, error%d", | 443 << LATE(pa_context_errno)(_paContext); |
475 LATE(pa_context_errno)(_paContext)); | |
476 return -1; | 444 return -1; |
477 } | 445 } |
478 | 446 |
479 return 0; | 447 return 0; |
480 } | 448 } |
481 | 449 |
482 int32_t AudioMixerManagerLinuxPulse::SpeakerMute(bool& enabled) const | 450 int32_t AudioMixerManagerLinuxPulse::SpeakerMute(bool& enabled) const |
483 { | 451 { |
484 | 452 |
485 if (_paOutputDeviceIndex == -1) | 453 if (_paOutputDeviceIndex == -1) |
486 { | 454 { |
487 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 455 LOG(LS_WARNING) << "output device index has not been set"; |
488 " output device index has not been set"); | |
489 return -1; | 456 return -1; |
490 } | 457 } |
491 | 458 |
492 if (_paPlayStream && (LATE(pa_stream_get_state)(_paPlayStream) | 459 if (_paPlayStream && (LATE(pa_stream_get_state)(_paPlayStream) |
493 != PA_STREAM_UNCONNECTED)) | 460 != PA_STREAM_UNCONNECTED)) |
494 { | 461 { |
495 // We can only get the mute status if we have a connected stream | 462 // We can only get the mute status if we have a connected stream |
496 if (!GetSinkInputInfo()) | 463 if (!GetSinkInputInfo()) |
497 return -1; | 464 return -1; |
498 | 465 |
499 enabled = static_cast<bool> (_paMute); | 466 enabled = static_cast<bool> (_paMute); |
500 } else | 467 } else |
501 { | 468 { |
502 enabled = _paSpeakerMute; | 469 enabled = _paSpeakerMute; |
503 } | 470 } |
504 | 471 LOG(LS_VERBOSE) << "AudioMixerManagerLinuxPulse::SpeakerMute() => enabled=" |
505 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 472 << enabled; |
506 " AudioMixerManagerLinuxPulse::SpeakerMute() => " | |
507 "enabled=%i, enabled"); | |
508 | 473 |
509 return 0; | 474 return 0; |
510 } | 475 } |
511 | 476 |
512 int32_t | 477 int32_t |
513 AudioMixerManagerLinuxPulse::StereoPlayoutIsAvailable(bool& available) | 478 AudioMixerManagerLinuxPulse::StereoPlayoutIsAvailable(bool& available) |
514 { | 479 { |
515 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 480 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
516 if (_paOutputDeviceIndex == -1) | 481 if (_paOutputDeviceIndex == -1) |
517 { | 482 { |
518 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 483 LOG(LS_WARNING) << "output device index has not been set"; |
519 " output device index has not been set"); | |
520 return -1; | 484 return -1; |
521 } | 485 } |
522 | 486 |
523 uint32_t deviceIndex = (uint32_t) _paOutputDeviceIndex; | 487 uint32_t deviceIndex = (uint32_t) _paOutputDeviceIndex; |
524 | 488 |
525 { | 489 { |
526 AutoPulseLock auto_lock(_paMainloop); | 490 AutoPulseLock auto_lock(_paMainloop); |
527 | 491 |
528 // Get the actual stream device index if we have a connected stream | 492 // Get the actual stream device index if we have a connected stream |
529 // The device used by the stream can be changed | 493 // The device used by the stream can be changed |
(...skipping 12 matching lines...) Expand all Loading... |
542 | 506 |
543 return 0; | 507 return 0; |
544 } | 508 } |
545 | 509 |
546 int32_t | 510 int32_t |
547 AudioMixerManagerLinuxPulse::StereoRecordingIsAvailable(bool& available) | 511 AudioMixerManagerLinuxPulse::StereoRecordingIsAvailable(bool& available) |
548 { | 512 { |
549 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 513 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
550 if (_paInputDeviceIndex == -1) | 514 if (_paInputDeviceIndex == -1) |
551 { | 515 { |
552 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 516 LOG(LS_WARNING) << "input device index has not been set"; |
553 " input device index has not been set"); | |
554 return -1; | 517 return -1; |
555 } | 518 } |
556 | 519 |
557 uint32_t deviceIndex = (uint32_t) _paInputDeviceIndex; | 520 uint32_t deviceIndex = (uint32_t) _paInputDeviceIndex; |
558 | 521 |
559 AutoPulseLock auto_lock(_paMainloop); | 522 AutoPulseLock auto_lock(_paMainloop); |
560 | 523 |
561 // Get the actual stream device index if we have a connected stream | 524 // Get the actual stream device index if we have a connected stream |
562 // The device used by the stream can be changed | 525 // The device used by the stream can be changed |
563 // during the call | 526 // during the call |
564 if (_paRecStream && (LATE(pa_stream_get_state)(_paRecStream) | 527 if (_paRecStream && (LATE(pa_stream_get_state)(_paRecStream) |
565 != PA_STREAM_UNCONNECTED)) | 528 != PA_STREAM_UNCONNECTED)) |
566 { | 529 { |
567 deviceIndex = LATE(pa_stream_get_device_index)(_paRecStream); | 530 deviceIndex = LATE(pa_stream_get_device_index)(_paRecStream); |
568 } | 531 } |
569 | 532 |
570 pa_operation* paOperation = NULL; | 533 pa_operation* paOperation = NULL; |
571 | 534 |
572 // Get info for this source | 535 // Get info for this source |
573 // We want to know if the actual device can record in stereo | 536 // We want to know if the actual device can record in stereo |
574 paOperation = LATE(pa_context_get_source_info_by_index)( | 537 paOperation = LATE(pa_context_get_source_info_by_index)( |
575 _paContext, deviceIndex, | 538 _paContext, deviceIndex, |
576 PaSourceInfoCallback, | 539 PaSourceInfoCallback, |
577 (void*) this); | 540 (void*) this); |
578 | 541 |
579 WaitForOperationCompletion(paOperation); | 542 WaitForOperationCompletion(paOperation); |
580 | 543 |
581 available = static_cast<bool> (_paChannels == 2); | 544 available = static_cast<bool> (_paChannels == 2); |
582 | 545 |
583 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 546 LOG(LS_VERBOSE) |
584 " AudioMixerManagerLinuxPulse::StereoRecordingIsAvailable()" | 547 << "AudioMixerManagerLinuxPulse::StereoRecordingIsAvailable()" |
585 " => available=%i, available"); | 548 << " => available=" << available; |
586 | 549 |
587 return 0; | 550 return 0; |
588 } | 551 } |
589 | 552 |
590 int32_t AudioMixerManagerLinuxPulse::MicrophoneMuteIsAvailable( | 553 int32_t AudioMixerManagerLinuxPulse::MicrophoneMuteIsAvailable( |
591 bool& available) | 554 bool& available) |
592 { | 555 { |
593 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 556 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
594 if (_paInputDeviceIndex == -1) | 557 if (_paInputDeviceIndex == -1) |
595 { | 558 { |
596 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 559 LOG(LS_WARNING) << "input device index has not been set"; |
597 " input device index has not been set"); | |
598 return -1; | 560 return -1; |
599 } | 561 } |
600 | 562 |
601 // Always available in Pulse Audio | 563 // Always available in Pulse Audio |
602 available = true; | 564 available = true; |
603 | 565 |
604 return 0; | 566 return 0; |
605 } | 567 } |
606 | 568 |
607 int32_t AudioMixerManagerLinuxPulse::SetMicrophoneMute(bool enable) | 569 int32_t AudioMixerManagerLinuxPulse::SetMicrophoneMute(bool enable) |
608 { | 570 { |
609 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 571 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
610 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 572 LOG(LS_VERBOSE) << "AudioMixerManagerLinuxPulse::SetMicrophoneMute(enable=" |
611 "AudioMixerManagerLinuxPulse::SetMicrophoneMute(enable=%u)", | 573 << enable << ")"; |
612 enable); | |
613 | 574 |
614 if (_paInputDeviceIndex == -1) | 575 if (_paInputDeviceIndex == -1) |
615 { | 576 { |
616 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 577 LOG(LS_WARNING) << "input device index has not been set"; |
617 " input device index has not been set"); | |
618 return -1; | 578 return -1; |
619 } | 579 } |
620 | 580 |
621 bool setFailed(false); | 581 bool setFailed(false); |
622 pa_operation* paOperation = NULL; | 582 pa_operation* paOperation = NULL; |
623 | 583 |
624 uint32_t deviceIndex = (uint32_t) _paInputDeviceIndex; | 584 uint32_t deviceIndex = (uint32_t) _paInputDeviceIndex; |
625 | 585 |
626 AutoPulseLock auto_lock(_paMainloop); | 586 AutoPulseLock auto_lock(_paMainloop); |
627 | 587 |
(...skipping 15 matching lines...) Expand all Loading... |
643 if (!paOperation) | 603 if (!paOperation) |
644 { | 604 { |
645 setFailed = true; | 605 setFailed = true; |
646 } | 606 } |
647 | 607 |
648 // Don't need to wait for this to complete. | 608 // Don't need to wait for this to complete. |
649 LATE(pa_operation_unref)(paOperation); | 609 LATE(pa_operation_unref)(paOperation); |
650 | 610 |
651 if (setFailed) | 611 if (setFailed) |
652 { | 612 { |
653 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 613 LOG(LS_WARNING) << "could not mute microphone, error=" |
654 " could not mute microphone, error%d", | 614 << LATE(pa_context_errno)(_paContext); |
655 LATE(pa_context_errno)(_paContext)); | |
656 return -1; | 615 return -1; |
657 } | 616 } |
658 | 617 |
659 return 0; | 618 return 0; |
660 } | 619 } |
661 | 620 |
662 int32_t AudioMixerManagerLinuxPulse::MicrophoneMute(bool& enabled) const | 621 int32_t AudioMixerManagerLinuxPulse::MicrophoneMute(bool& enabled) const |
663 { | 622 { |
664 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 623 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
665 if (_paInputDeviceIndex == -1) | 624 if (_paInputDeviceIndex == -1) |
666 { | 625 { |
667 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 626 LOG(LS_WARNING) << "input device index has not been set"; |
668 " input device index has not been set"); | |
669 return -1; | 627 return -1; |
670 } | 628 } |
671 | 629 |
672 uint32_t deviceIndex = (uint32_t) _paInputDeviceIndex; | 630 uint32_t deviceIndex = (uint32_t) _paInputDeviceIndex; |
673 | 631 |
674 { | 632 { |
675 AutoPulseLock auto_lock(_paMainloop); | 633 AutoPulseLock auto_lock(_paMainloop); |
676 // Get the actual stream device index if we have a connected stream | 634 // Get the actual stream device index if we have a connected stream |
677 // The device used by the stream can be changed | 635 // The device used by the stream can be changed |
678 // during the call | 636 // during the call |
679 if (_paRecStream && (LATE(pa_stream_get_state)(_paRecStream) | 637 if (_paRecStream && (LATE(pa_stream_get_state)(_paRecStream) |
680 != PA_STREAM_UNCONNECTED)) | 638 != PA_STREAM_UNCONNECTED)) |
681 { | 639 { |
682 deviceIndex = LATE(pa_stream_get_device_index)(_paRecStream); | 640 deviceIndex = LATE(pa_stream_get_device_index)(_paRecStream); |
683 } | 641 } |
684 } | 642 } |
685 | 643 |
686 if (!GetSourceInfoByIndex(deviceIndex)) | 644 if (!GetSourceInfoByIndex(deviceIndex)) |
687 return -1; | 645 return -1; |
688 | 646 |
689 enabled = static_cast<bool> (_paMute); | 647 enabled = static_cast<bool> (_paMute); |
690 | 648 |
691 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 649 LOG(LS_VERBOSE) |
692 "\tAudioMixerManagerLinuxPulse::MicrophoneMute() =>" | 650 << "AudioMixerManagerLinuxPulse::MicrophoneMute() => enabled=" |
693 " enabled=%i", enabled); | 651 << enabled; |
694 | 652 |
695 return 0; | 653 return 0; |
696 } | 654 } |
697 | 655 |
698 int32_t | 656 int32_t |
699 AudioMixerManagerLinuxPulse::MicrophoneBoostIsAvailable(bool& available) | 657 AudioMixerManagerLinuxPulse::MicrophoneBoostIsAvailable(bool& available) |
700 { | 658 { |
701 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 659 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
702 if (_paInputDeviceIndex == -1) | 660 if (_paInputDeviceIndex == -1) |
703 { | 661 { |
704 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 662 LOG(LS_WARNING) << "input device index has not been set"; |
705 " input device index has not been set"); | |
706 return -1; | 663 return -1; |
707 } | 664 } |
708 | 665 |
709 // Always unavailable in Pulse Audio | 666 // Always unavailable in Pulse Audio |
710 // Could make it possible to use PA_VOLUME_MAX | 667 // Could make it possible to use PA_VOLUME_MAX |
711 // but that gives bad audio with some sound cards | 668 // but that gives bad audio with some sound cards |
712 available = false; | 669 available = false; |
713 | 670 |
714 return 0; | 671 return 0; |
715 } | 672 } |
716 | 673 |
717 int32_t AudioMixerManagerLinuxPulse::SetMicrophoneBoost(bool enable) | 674 int32_t AudioMixerManagerLinuxPulse::SetMicrophoneBoost(bool enable) |
718 { | 675 { |
719 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 676 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
720 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 677 LOG(LS_VERBOSE) << "AudioMixerManagerLinuxPulse::SetMicrophoneBoost(enable=" |
721 "AudioMixerManagerLinuxPulse::SetMicrophoneBoost(enable=%u)", | 678 << enable << ")"; |
722 enable); | |
723 | 679 |
724 if (_paInputDeviceIndex == -1) | 680 if (_paInputDeviceIndex == -1) |
725 { | 681 { |
726 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 682 LOG(LS_WARNING) << "input device index has not been set"; |
727 " input device index has not been set"); | |
728 return -1; | 683 return -1; |
729 } | 684 } |
730 | 685 |
731 // Ensure the selected microphone destination has a valid boost control | 686 // Ensure the selected microphone destination has a valid boost control |
732 bool available(false); | 687 bool available(false); |
733 MicrophoneBoostIsAvailable(available); | 688 MicrophoneBoostIsAvailable(available); |
734 if (!available) | 689 if (!available) |
735 { | 690 { |
736 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 691 LOG(LS_WARNING) << "it is not possible to enable microphone boost"; |
737 " it is not possible to enable microphone boost"); | |
738 return -1; | 692 return -1; |
739 } | 693 } |
740 | 694 |
741 // It is assumed that the call above fails! | 695 // It is assumed that the call above fails! |
742 | 696 |
743 return 0; | 697 return 0; |
744 } | 698 } |
745 | 699 |
746 int32_t AudioMixerManagerLinuxPulse::MicrophoneBoost(bool& enabled) const | 700 int32_t AudioMixerManagerLinuxPulse::MicrophoneBoost(bool& enabled) const |
747 { | 701 { |
748 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 702 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
749 if (_paInputDeviceIndex == -1) | 703 if (_paInputDeviceIndex == -1) |
750 { | 704 { |
751 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 705 LOG(LS_WARNING) << "input device index has not been set"; |
752 " input device index has not been set"); | |
753 return -1; | 706 return -1; |
754 } | 707 } |
755 | 708 |
756 // Microphone boost cannot be enabled on this platform! | 709 // Microphone boost cannot be enabled on this platform! |
757 enabled = false; | 710 enabled = false; |
758 | 711 |
759 return 0; | 712 return 0; |
760 } | 713 } |
761 | 714 |
762 int32_t AudioMixerManagerLinuxPulse::MicrophoneVolumeIsAvailable( | 715 int32_t AudioMixerManagerLinuxPulse::MicrophoneVolumeIsAvailable( |
763 bool& available) | 716 bool& available) |
764 { | 717 { |
765 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 718 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
766 if (_paInputDeviceIndex == -1) | 719 if (_paInputDeviceIndex == -1) |
767 { | 720 { |
768 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 721 LOG(LS_WARNING) << "input device index has not been set"; |
769 " input device index has not been set"); | |
770 return -1; | 722 return -1; |
771 } | 723 } |
772 | 724 |
773 // Always available in Pulse Audio | 725 // Always available in Pulse Audio |
774 available = true; | 726 available = true; |
775 | 727 |
776 return 0; | 728 return 0; |
777 } | 729 } |
778 | 730 |
779 int32_t | 731 int32_t |
780 AudioMixerManagerLinuxPulse::SetMicrophoneVolume(uint32_t volume) | 732 AudioMixerManagerLinuxPulse::SetMicrophoneVolume(uint32_t volume) |
781 { | 733 { |
782 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 734 LOG(LS_VERBOSE) |
783 "AudioMixerManagerLinuxPulse::SetMicrophoneVolume" | 735 << "AudioMixerManagerLinuxPulse::SetMicrophoneVolume(volume=" << volume |
784 "(volume=%u)", volume); | 736 << ")"; |
785 | 737 |
786 if (_paInputDeviceIndex == -1) | 738 if (_paInputDeviceIndex == -1) |
787 { | 739 { |
788 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 740 LOG(LS_WARNING) << "input device index has not been set"; |
789 " input device index has not been set"); | |
790 return -1; | 741 return -1; |
791 } | 742 } |
792 | 743 |
793 // Unlike output streams, input streams have no concept of a stream | 744 // Unlike output streams, input streams have no concept of a stream |
794 // volume, only a device volume. So we have to change the volume of the | 745 // volume, only a device volume. So we have to change the volume of the |
795 // device itself. | 746 // device itself. |
796 | 747 |
797 // The device may have a different number of channels than the stream and | 748 // The device may have a different number of channels than the stream and |
798 // their mapping may be different, so we don't want to use the channel | 749 // their mapping may be different, so we don't want to use the channel |
799 // count from our sample spec. We could use PA_CHANNELS_MAX to cover our | 750 // count from our sample spec. We could use PA_CHANNELS_MAX to cover our |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
838 if (!paOperation) | 789 if (!paOperation) |
839 { | 790 { |
840 setFailed = true; | 791 setFailed = true; |
841 } | 792 } |
842 | 793 |
843 // Don't need to wait for this to complete. | 794 // Don't need to wait for this to complete. |
844 LATE(pa_operation_unref)(paOperation); | 795 LATE(pa_operation_unref)(paOperation); |
845 | 796 |
846 if (setFailed) | 797 if (setFailed) |
847 { | 798 { |
848 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 799 LOG(LS_WARNING) << "could not set microphone volume, error=" |
849 " could not set microphone volume, error%d", | 800 << LATE(pa_context_errno)(_paContext); |
850 LATE(pa_context_errno)(_paContext)); | |
851 return -1; | 801 return -1; |
852 } | 802 } |
853 | 803 |
854 return 0; | 804 return 0; |
855 } | 805 } |
856 | 806 |
857 int32_t | 807 int32_t |
858 AudioMixerManagerLinuxPulse::MicrophoneVolume(uint32_t& volume) const | 808 AudioMixerManagerLinuxPulse::MicrophoneVolume(uint32_t& volume) const |
859 { | 809 { |
860 | 810 |
861 if (_paInputDeviceIndex == -1) | 811 if (_paInputDeviceIndex == -1) |
862 { | 812 { |
863 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 813 LOG(LS_WARNING) << "input device index has not been set"; |
864 " input device index has not been set"); | |
865 return -1; | 814 return -1; |
866 } | 815 } |
867 | 816 |
868 uint32_t deviceIndex = (uint32_t) _paInputDeviceIndex; | 817 uint32_t deviceIndex = (uint32_t) _paInputDeviceIndex; |
869 | 818 |
870 { | 819 { |
871 AutoPulseLock auto_lock(_paMainloop); | 820 AutoPulseLock auto_lock(_paMainloop); |
872 // Get the actual stream device index if we have a connected stream. | 821 // Get the actual stream device index if we have a connected stream. |
873 // The device used by the stream can be changed during the call. | 822 // The device used by the stream can be changed during the call. |
874 if (_paRecStream && (LATE(pa_stream_get_state)(_paRecStream) | 823 if (_paRecStream && (LATE(pa_stream_get_state)(_paRecStream) |
875 != PA_STREAM_UNCONNECTED)) | 824 != PA_STREAM_UNCONNECTED)) |
876 { | 825 { |
877 deviceIndex = LATE(pa_stream_get_device_index)(_paRecStream); | 826 deviceIndex = LATE(pa_stream_get_device_index)(_paRecStream); |
878 } | 827 } |
879 } | 828 } |
880 | 829 |
881 if (!GetSourceInfoByIndex(deviceIndex)) | 830 if (!GetSourceInfoByIndex(deviceIndex)) |
882 return -1; | 831 return -1; |
883 | 832 |
884 { | 833 { |
885 AutoPulseLock auto_lock(_paMainloop); | 834 AutoPulseLock auto_lock(_paMainloop); |
886 volume = static_cast<uint32_t> (_paVolume); | 835 volume = static_cast<uint32_t> (_paVolume); |
887 } | 836 } |
888 | 837 |
889 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 838 LOG(LS_VERBOSE) |
890 " AudioMixerManagerLinuxPulse::MicrophoneVolume()" | 839 << "AudioMixerManagerLinuxPulse::MicrophoneVolume() => vol=" |
891 " => vol=%i, volume"); | 840 << volume; |
892 | 841 |
893 return 0; | 842 return 0; |
894 } | 843 } |
895 | 844 |
896 int32_t | 845 int32_t |
897 AudioMixerManagerLinuxPulse::MaxMicrophoneVolume(uint32_t& maxVolume) const | 846 AudioMixerManagerLinuxPulse::MaxMicrophoneVolume(uint32_t& maxVolume) const |
898 { | 847 { |
899 | 848 |
900 if (_paInputDeviceIndex == -1) | 849 if (_paInputDeviceIndex == -1) |
901 { | 850 { |
902 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 851 LOG(LS_WARNING) << "input device index has not been set"; |
903 " input device index has not been set"); | |
904 return -1; | 852 return -1; |
905 } | 853 } |
906 | 854 |
907 // PA_VOLUME_NORM corresponds to 100% (0db) | 855 // PA_VOLUME_NORM corresponds to 100% (0db) |
908 // PA allows up to 150 db amplification (PA_VOLUME_MAX) | 856 // PA allows up to 150 db amplification (PA_VOLUME_MAX) |
909 // but that doesn't work well for all sound cards | 857 // but that doesn't work well for all sound cards |
910 maxVolume = static_cast<uint32_t> (PA_VOLUME_NORM); | 858 maxVolume = static_cast<uint32_t> (PA_VOLUME_NORM); |
911 | 859 |
912 return 0; | 860 return 0; |
913 } | 861 } |
914 | 862 |
915 int32_t | 863 int32_t |
916 AudioMixerManagerLinuxPulse::MinMicrophoneVolume(uint32_t& minVolume) const | 864 AudioMixerManagerLinuxPulse::MinMicrophoneVolume(uint32_t& minVolume) const |
917 { | 865 { |
918 | 866 |
919 if (_paInputDeviceIndex == -1) | 867 if (_paInputDeviceIndex == -1) |
920 { | 868 { |
921 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 869 LOG(LS_WARNING) << "input device index has not been set"; |
922 " input device index has not been set"); | |
923 return -1; | 870 return -1; |
924 } | 871 } |
925 | 872 |
926 minVolume = static_cast<uint32_t> (PA_VOLUME_MUTED); | 873 minVolume = static_cast<uint32_t> (PA_VOLUME_MUTED); |
927 | 874 |
928 return 0; | 875 return 0; |
929 } | 876 } |
930 | 877 |
931 int32_t AudioMixerManagerLinuxPulse::MicrophoneVolumeStepSize( | 878 int32_t AudioMixerManagerLinuxPulse::MicrophoneVolumeStepSize( |
932 uint16_t& stepSize) const | 879 uint16_t& stepSize) const |
933 { | 880 { |
934 RTC_DCHECK(thread_checker_.CalledOnValidThread()); | 881 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
935 if (_paInputDeviceIndex == -1) | 882 if (_paInputDeviceIndex == -1) |
936 { | 883 { |
937 WEBRTC_TRACE(kTraceWarning, kTraceAudioDevice, _id, | 884 LOG(LS_WARNING) << "input device index has not been set"; |
938 " input device index has not been set"); | |
939 return -1; | 885 return -1; |
940 } | 886 } |
941 | 887 |
942 uint32_t deviceIndex = (uint32_t) _paInputDeviceIndex; | 888 uint32_t deviceIndex = (uint32_t) _paInputDeviceIndex; |
943 | 889 |
944 AutoPulseLock auto_lock(_paMainloop); | 890 AutoPulseLock auto_lock(_paMainloop); |
945 | 891 |
946 // Get the actual stream device index if we have a connected stream | 892 // Get the actual stream device index if we have a connected stream |
947 // The device used by the stream can be changed | 893 // The device used by the stream can be changed |
948 // during the call | 894 // during the call |
949 if (_paRecStream && (LATE(pa_stream_get_state)(_paRecStream) | 895 if (_paRecStream && (LATE(pa_stream_get_state)(_paRecStream) |
950 != PA_STREAM_UNCONNECTED)) | 896 != PA_STREAM_UNCONNECTED)) |
951 { | 897 { |
952 deviceIndex = LATE(pa_stream_get_device_index)(_paRecStream); | 898 deviceIndex = LATE(pa_stream_get_device_index)(_paRecStream); |
953 } | 899 } |
954 | 900 |
955 pa_operation* paOperation = NULL; | 901 pa_operation* paOperation = NULL; |
956 | 902 |
957 // Get info for this source | 903 // Get info for this source |
958 paOperation | 904 paOperation |
959 = LATE(pa_context_get_source_info_by_index)(_paContext, deviceIndex, | 905 = LATE(pa_context_get_source_info_by_index)(_paContext, deviceIndex, |
960 PaSourceInfoCallback, | 906 PaSourceInfoCallback, |
961 (void*) this); | 907 (void*) this); |
962 | 908 |
963 WaitForOperationCompletion(paOperation); | 909 WaitForOperationCompletion(paOperation); |
964 | 910 |
965 stepSize = static_cast<uint16_t> ((PA_VOLUME_NORM + 1) / _paVolSteps); | 911 stepSize = static_cast<uint16_t> ((PA_VOLUME_NORM + 1) / _paVolSteps); |
966 | 912 |
967 WEBRTC_TRACE(kTraceInfo, kTraceAudioDevice, _id, | 913 LOG(LS_VERBOSE) |
968 "\tAudioMixerManagerLinuxPulse::MicrophoneVolumeStepSize()" | 914 << "AudioMixerManagerLinuxPulse::MicrophoneVolumeStepSize() => size=" |
969 " => size=%i", stepSize); | 915 << stepSize; |
970 | 916 |
971 return 0; | 917 return 0; |
972 } | 918 } |
973 | 919 |
974 // =========================================================================== | 920 // =========================================================================== |
975 // Private Methods | 921 // Private Methods |
976 // =========================================================================== | 922 // =========================================================================== |
977 | 923 |
978 void | 924 void |
979 AudioMixerManagerLinuxPulse::PaSinkInfoCallback(pa_context */*c*/, | 925 AudioMixerManagerLinuxPulse::PaSinkInfoCallback(pa_context */*c*/, |
(...skipping 27 matching lines...) Expand all Loading... |
1007 PaSourceInfoCallbackHandler(i, eol); | 953 PaSourceInfoCallbackHandler(i, eol); |
1008 } | 954 } |
1009 | 955 |
1010 void | 956 void |
1011 AudioMixerManagerLinuxPulse::PaSetVolumeCallback(pa_context * c, | 957 AudioMixerManagerLinuxPulse::PaSetVolumeCallback(pa_context * c, |
1012 int success, | 958 int success, |
1013 void */*pThis*/) | 959 void */*pThis*/) |
1014 { | 960 { |
1015 if (!success) | 961 if (!success) |
1016 { | 962 { |
1017 WEBRTC_TRACE(kTraceError, kTraceAudioDevice, -1, | 963 LOG(LS_ERROR) << "failed to set volume"; |
1018 " failed to set volume"); | |
1019 } | 964 } |
1020 } | 965 } |
1021 | 966 |
1022 void AudioMixerManagerLinuxPulse::PaSinkInfoCallbackHandler( | 967 void AudioMixerManagerLinuxPulse::PaSinkInfoCallbackHandler( |
1023 const pa_sink_info *i, | 968 const pa_sink_info *i, |
1024 int eol) | 969 int eol) |
1025 { | 970 { |
1026 if (eol) | 971 if (eol) |
1027 { | 972 { |
1028 // Signal that we are done | 973 // Signal that we are done |
(...skipping 116 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1145 | 1090 |
1146 AutoPulseLock auto_lock(_paMainloop); | 1091 AutoPulseLock auto_lock(_paMainloop); |
1147 paOperation = LATE(pa_context_get_source_info_by_index)( | 1092 paOperation = LATE(pa_context_get_source_info_by_index)( |
1148 _paContext, device_index, PaSourceInfoCallback, (void*) this); | 1093 _paContext, device_index, PaSourceInfoCallback, (void*) this); |
1149 | 1094 |
1150 WaitForOperationCompletion(paOperation); | 1095 WaitForOperationCompletion(paOperation); |
1151 return true; | 1096 return true; |
1152 } | 1097 } |
1153 | 1098 |
1154 } | 1099 } |
OLD | NEW |