168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com/* 228f3913ca95de8bd489ce3f6afd891864e8779cbleozwang@webrtc.org * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. 368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com * 468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com * Use of this source code is governed by a BSD-style license 568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com * that can be found in the LICENSE file in the root of the source 668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com * tree. An additional intellectual property rights grant can be found 768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com * in the file PATENTS. All contributing project authors may 868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com * be found in the AUTHORS file in the root of the source tree. 968efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com */ 1068efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 1168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com#ifndef WEBRTC_AUDIO_DEVICE_AUDIO_DEVICE_PULSE_LINUX_H 1268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com#define WEBRTC_AUDIO_DEVICE_AUDIO_DEVICE_PULSE_LINUX_H 1368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 1412411ef40e08c5e28ccde54ab3418c96676ffcbcpbos#include "webrtc/base/platform_thread.h" 1512411ef40e08c5e28ccde54ab3418c96676ffcbcpbos#include "webrtc/base/thread_checker.h" 16811269df40fd8cd036b68cfe39bc04cacac0a698pbos@webrtc.org#include "webrtc/modules/audio_device/audio_device_generic.h" 17811269df40fd8cd036b68cfe39bc04cacac0a698pbos@webrtc.org#include "webrtc/modules/audio_device/linux/audio_mixer_manager_pulse_linux.h" 1898f53510b222f71fdd8b799b2f33737ceeb28c61Henrik Kjellander#include "webrtc/system_wrappers/include/critical_section_wrapper.h" 1968efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 20e2a800644c25cccff782096e69f432bbc78336fbniklas.enbom@webrtc.org#include <X11/Xlib.h> 21811269df40fd8cd036b68cfe39bc04cacac0a698pbos@webrtc.org#include <pulse/pulseaudio.h> 2268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 2368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// We define this flag if it's missing from our headers, because we want to be 2468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// able to compile against old headers but still use PA_STREAM_ADJUST_LATENCY 2568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// if run against a recent version of the library. 2668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com#ifndef PA_STREAM_ADJUST_LATENCY 2768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com#define PA_STREAM_ADJUST_LATENCY 0x2000U 2868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com#endif 2968efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com#ifndef PA_STREAM_START_MUTED 3068efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com#define PA_STREAM_START_MUTED 0x1000U 3168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com#endif 3268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 3368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// Set this constant to 0 to disable latency reading 342550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.orgconst uint32_t WEBRTC_PA_REPORT_LATENCY = 1; 3568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 3668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// Constants from implementation by Tristan Schmelcher [tschmelcher@google.com] 3768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 3868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// First PulseAudio protocol version that supports PA_STREAM_ADJUST_LATENCY. 392550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.orgconst uint32_t WEBRTC_PA_ADJUST_LATENCY_PROTOCOL_VERSION = 13; 4068efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 4168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// Some timing constants for optimal operation. See 4268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// https://tango.0pointer.de/pipermail/pulseaudio-discuss/2008-January/001170.html 4368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// for a good explanation of some of the factors that go into this. 4468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 4568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// Playback. 4668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 4768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// For playback, there is a round-trip delay to fill the server-side playback 4868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// buffer, so setting too low of a latency is a buffer underflow risk. We will 4968efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// automatically increase the latency if a buffer underflow does occur, but we 5068efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// also enforce a sane minimum at start-up time. Anything lower would be 5168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// virtually guaranteed to underflow at least once, so there's no point in 5268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// allowing lower latencies. 532550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.orgconst uint32_t WEBRTC_PA_PLAYBACK_LATENCY_MINIMUM_MSECS = 20; 5468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 5568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// Every time a playback stream underflows, we will reconfigure it with target 5668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// latency that is greater by this amount. 572550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.orgconst uint32_t WEBRTC_PA_PLAYBACK_LATENCY_INCREMENT_MSECS = 20; 5868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 5968efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// We also need to configure a suitable request size. Too small and we'd burn 6068efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// CPU from the overhead of transfering small amounts of data at once. Too large 6168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// and the amount of data remaining in the buffer right before refilling it 6268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// would be a buffer underflow risk. We set it to half of the buffer size. 632550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.orgconst uint32_t WEBRTC_PA_PLAYBACK_REQUEST_FACTOR = 2; 6468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 6568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// Capture. 6668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 6768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// For capture, low latency is not a buffer overflow risk, but it makes us burn 6868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// CPU from the overhead of transfering small amounts of data at once, so we set 6968efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// a recommended value that we use for the kLowLatency constant (but if the user 7068efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// explicitly requests something lower then we will honour it). 7168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// 1ms takes about 6-7% CPU. 5ms takes about 5%. 10ms takes about 4.x%. 722550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.orgconst uint32_t WEBRTC_PA_LOW_CAPTURE_LATENCY_MSECS = 10; 7368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 7468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// There is a round-trip delay to ack the data to the server, so the 7568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// server-side buffer needs extra space to prevent buffer overflow. 20ms is 7668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// sufficient, but there is no penalty to making it bigger, so we make it huge. 7768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// (750ms is libpulse's default value for the _total_ buffer size in the 7868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// kNoLatencyRequirements case.) 792550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.orgconst uint32_t WEBRTC_PA_CAPTURE_BUFFER_EXTRA_MSECS = 750; 8068efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 812550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.orgconst uint32_t WEBRTC_PA_MSECS_PER_SEC = 1000; 8268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 8368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// Init _configuredLatencyRec/Play to this value to disable latency requirements 842550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.orgconst int32_t WEBRTC_PA_NO_LATENCY_REQUIREMENTS = -1; 8568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 8668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com// Set this const to 1 to account for peeked and used data in latency calculation 872550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.orgconst uint32_t WEBRTC_PA_CAPTURE_BUFFER_LATENCY_ADJUSTMENT = 0; 8868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 8968efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.comnamespace webrtc 9068efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com{ 9168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.comclass EventWrapper; 9268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 9368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.comclass AudioDeviceLinuxPulse: public AudioDeviceGeneric 9468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com{ 9568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.compublic: 962550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org AudioDeviceLinuxPulse(const int32_t id); 97096515b0702aaa00dc561cd7cf20df8b826f97c4pbos@webrtc.org virtual ~AudioDeviceLinuxPulse(); 9868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 9968efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // Retrieve the currently utilized audio layer 10014665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t ActiveAudioLayer( 10114665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org AudioDeviceModule::AudioLayer& audioLayer) const override; 10268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 10368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // Main initializaton and termination 10414665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t Init() override; 10514665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t Terminate() override; 10614665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org bool Initialized() const override; 10768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 10868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // Device enumeration 10914665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int16_t PlayoutDevices() override; 11014665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int16_t RecordingDevices() override; 11114665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t PlayoutDeviceName(uint16_t index, 11214665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org char name[kAdmMaxDeviceNameSize], 11314665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org char guid[kAdmMaxGuidSize]) override; 11414665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t RecordingDeviceName(uint16_t index, 11514665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org char name[kAdmMaxDeviceNameSize], 11614665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org char guid[kAdmMaxGuidSize]) override; 11768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 11868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // Device selection 11914665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SetPlayoutDevice(uint16_t index) override; 12014665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SetPlayoutDevice( 12114665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org AudioDeviceModule::WindowsDeviceType device) override; 12214665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SetRecordingDevice(uint16_t index) override; 12314665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SetRecordingDevice( 12414665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org AudioDeviceModule::WindowsDeviceType device) override; 12568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 12668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // Audio transport initialization 12714665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t PlayoutIsAvailable(bool& available) override; 12814665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t InitPlayout() override; 12914665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org bool PlayoutIsInitialized() const override; 13014665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t RecordingIsAvailable(bool& available) override; 13114665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t InitRecording() override; 13214665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org bool RecordingIsInitialized() const override; 13368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 13468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // Audio transport control 13514665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t StartPlayout() override; 13614665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t StopPlayout() override; 13714665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org bool Playing() const override; 13814665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t StartRecording() override; 13914665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t StopRecording() override; 14014665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org bool Recording() const override; 14168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 14268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // Microphone Automatic Gain Control (AGC) 14314665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SetAGC(bool enable) override; 14414665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org bool AGC() const override; 14568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 14668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // Volume control based on the Windows Wave API (Windows only) 14714665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SetWaveOutVolume(uint16_t volumeLeft, 14814665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org uint16_t volumeRight) override; 14914665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t WaveOutVolume(uint16_t& volumeLeft, 15014665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org uint16_t& volumeRight) const override; 15168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 15268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // Audio mixer initialization 15314665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t InitSpeaker() override; 15414665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org bool SpeakerIsInitialized() const override; 15514665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t InitMicrophone() override; 15614665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org bool MicrophoneIsInitialized() const override; 15768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 15868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // Speaker volume controls 15914665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SpeakerVolumeIsAvailable(bool& available) override; 16014665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SetSpeakerVolume(uint32_t volume) override; 16114665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SpeakerVolume(uint32_t& volume) const override; 16214665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t MaxSpeakerVolume(uint32_t& maxVolume) const override; 16314665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t MinSpeakerVolume(uint32_t& minVolume) const override; 16414665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SpeakerVolumeStepSize(uint16_t& stepSize) const override; 16568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 16668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // Microphone volume controls 16714665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t MicrophoneVolumeIsAvailable(bool& available) override; 16814665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SetMicrophoneVolume(uint32_t volume) override; 16914665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t MicrophoneVolume(uint32_t& volume) const override; 17014665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t MaxMicrophoneVolume(uint32_t& maxVolume) const override; 17114665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t MinMicrophoneVolume(uint32_t& minVolume) const override; 17214665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t MicrophoneVolumeStepSize(uint16_t& stepSize) const override; 17368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 17468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // Speaker mute control 17514665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SpeakerMuteIsAvailable(bool& available) override; 17614665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SetSpeakerMute(bool enable) override; 17714665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SpeakerMute(bool& enabled) const override; 17868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 17968efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // Microphone mute control 18014665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t MicrophoneMuteIsAvailable(bool& available) override; 18114665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SetMicrophoneMute(bool enable) override; 18214665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t MicrophoneMute(bool& enabled) const override; 18368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 18468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // Microphone boost control 18514665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t MicrophoneBoostIsAvailable(bool& available) override; 18614665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SetMicrophoneBoost(bool enable) override; 18714665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t MicrophoneBoost(bool& enabled) const override; 18868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 18968efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // Stereo support 19014665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t StereoPlayoutIsAvailable(bool& available) override; 19114665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SetStereoPlayout(bool enable) override; 19214665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t StereoPlayout(bool& enabled) const override; 19314665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t StereoRecordingIsAvailable(bool& available) override; 19414665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SetStereoRecording(bool enable) override; 19514665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t StereoRecording(bool& enabled) const override; 19668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 19768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // Delay information and control 19814665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t SetPlayoutBuffer(const AudioDeviceModule::BufferType type, 19914665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org uint16_t sizeMS) override; 20014665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t PlayoutBuffer(AudioDeviceModule::BufferType& type, 20114665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org uint16_t& sizeMS) const override; 20214665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t PlayoutDelay(uint16_t& delayMS) const override; 20314665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t RecordingDelay(uint16_t& delayMS) const override; 20468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 20568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // CPU load 20614665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org int32_t CPULoad(uint16_t& load) const override; 20768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 2081a07a1e8252daf088d1b94b56cce5e9a3e7cae67Brave Yao bool PlayoutWarning() const override; 2091a07a1e8252daf088d1b94b56cce5e9a3e7cae67Brave Yao bool PlayoutError() const override; 2101a07a1e8252daf088d1b94b56cce5e9a3e7cae67Brave Yao bool RecordingWarning() const override; 2111a07a1e8252daf088d1b94b56cce5e9a3e7cae67Brave Yao bool RecordingError() const override; 2121a07a1e8252daf088d1b94b56cce5e9a3e7cae67Brave Yao void ClearPlayoutWarning() override; 2131a07a1e8252daf088d1b94b56cce5e9a3e7cae67Brave Yao void ClearPlayoutError() override; 2141a07a1e8252daf088d1b94b56cce5e9a3e7cae67Brave Yao void ClearRecordingWarning() override; 2151a07a1e8252daf088d1b94b56cce5e9a3e7cae67Brave Yao void ClearRecordingError() override; 21668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 2171a07a1e8252daf088d1b94b56cce5e9a3e7cae67Brave Yao void AttachAudioBuffer(AudioDeviceBuffer* audioBuffer) override; 21868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 21968efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.comprivate: 2207fb75ecbd4226ca3fccdb7e64ce19850059c8c13andresp@webrtc.org void Lock() EXCLUSIVE_LOCK_FUNCTION(_critSect) { 22168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com _critSect.Enter(); 22268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com } 2237fb75ecbd4226ca3fccdb7e64ce19850059c8c13andresp@webrtc.org void UnLock() UNLOCK_FUNCTION(_critSect) { 22468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com _critSect.Leave(); 22568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com } 22668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void WaitForOperationCompletion(pa_operation* paOperation) const; 22768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void WaitForSuccess(pa_operation* paOperation) const; 22868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 229e2a800644c25cccff782096e69f432bbc78336fbniklas.enbom@webrtc.org bool KeyPressed() const; 230e2a800644c25cccff782096e69f432bbc78336fbniklas.enbom@webrtc.org 23168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com static void PaContextStateCallback(pa_context *c, void *pThis); 23268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com static void PaSinkInfoCallback(pa_context *c, const pa_sink_info *i, 23368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com int eol, void *pThis); 23468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com static void PaSourceInfoCallback(pa_context *c, const pa_source_info *i, 23568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com int eol, void *pThis); 23668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com static void PaServerInfoCallback(pa_context *c, const pa_server_info *i, 23768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void *pThis); 23868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com static void PaStreamStateCallback(pa_stream *p, void *pThis); 23968efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void PaContextStateCallbackHandler(pa_context *c); 24068efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void PaSinkInfoCallbackHandler(const pa_sink_info *i, int eol); 24168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void PaSourceInfoCallbackHandler(const pa_source_info *i, int eol); 24268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void PaServerInfoCallbackHandler(const pa_server_info *i); 24368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void PaStreamStateCallbackHandler(pa_stream *p); 24468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 24568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void EnableWriteCallback(); 24668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void DisableWriteCallback(); 24768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com static void PaStreamWriteCallback(pa_stream *unused, size_t buffer_space, 24868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void *pThis); 24968efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void PaStreamWriteCallbackHandler(size_t buffer_space); 25068efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com static void PaStreamUnderflowCallback(pa_stream *unused, void *pThis); 25168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void PaStreamUnderflowCallbackHandler(); 25268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void EnableReadCallback(); 25368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void DisableReadCallback(); 25468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com static void PaStreamReadCallback(pa_stream *unused1, size_t unused2, 25568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void *pThis); 25668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void PaStreamReadCallbackHandler(); 25768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com static void PaStreamOverflowCallback(pa_stream *unused, void *pThis); 25868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void PaStreamOverflowCallbackHandler(); 2592550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org int32_t LatencyUsecs(pa_stream *stream); 2602550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org int32_t ReadRecordedData(const void* bufferData, size_t bufferSize); 2612550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org int32_t ProcessRecordedData(int8_t *bufferData, 2622550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org uint32_t bufferSizeInSamples, 2632550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org uint32_t recDelay); 2642550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org 2652550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org int32_t CheckPulseAudioVersion(); 2662550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org int32_t InitSamplingFrequency(); 2672550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org int32_t GetDefaultDeviceInfo(bool recDevice, char* name, uint16_t& index); 2682550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org int32_t InitPulseAudio(); 2692550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org int32_t TerminatePulseAudio(); 27068efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 27168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void PaLock(); 27268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com void PaUnLock(); 27368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 27468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com static bool RecThreadFunc(void*); 27568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com static bool PlayThreadFunc(void*); 27668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com bool RecThreadProcess(); 27768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com bool PlayThreadProcess(); 27868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 27968efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com AudioDeviceBuffer* _ptrAudioBuffer; 28068efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 28168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com CriticalSectionWrapper& _critSect; 28268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com EventWrapper& _timeEventRec; 28368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com EventWrapper& _timeEventPlay; 28468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com EventWrapper& _recStartEvent; 28568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com EventWrapper& _playStartEvent; 28668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 2878c38e8b9b96d72317d6ce94c1442113b4e385dcbPeter Boström // TODO(pbos): Remove scoped_ptr and use directly without resetting. 2888c38e8b9b96d72317d6ce94c1442113b4e385dcbPeter Boström rtc::scoped_ptr<rtc::PlatformThread> _ptrThreadPlay; 2898c38e8b9b96d72317d6ce94c1442113b4e385dcbPeter Boström rtc::scoped_ptr<rtc::PlatformThread> _ptrThreadRec; 2902550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org int32_t _id; 29168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 29268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com AudioMixerManagerLinuxPulse _mixerManager; 29368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 2942550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org uint16_t _inputDeviceIndex; 2952550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org uint16_t _outputDeviceIndex; 29668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com bool _inputDeviceIsSpecified; 29768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com bool _outputDeviceIsSpecified; 29868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 299a31c428307bee721c825d46d2c1f18e813f00fcfandrew@webrtc.org int sample_rate_hz_; 3002550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org uint8_t _recChannels; 3012550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org uint8_t _playChannels; 30268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 30368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com AudioDeviceModule::BufferType _playBufType; 30468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 3051a07a1e8252daf088d1b94b56cce5e9a3e7cae67Brave Yao // Stores thread ID in constructor. 3061a07a1e8252daf088d1b94b56cce5e9a3e7cae67Brave Yao // We can then use ThreadChecker::CalledOnValidThread() to ensure that 3071a07a1e8252daf088d1b94b56cce5e9a3e7cae67Brave Yao // other methods are called from the same thread. 30891d6edef35e7275879c30ce16ecb8b6dc73c6e4ahenrikg // Currently only does RTC_DCHECK(thread_checker_.CalledOnValidThread()). 3091a07a1e8252daf088d1b94b56cce5e9a3e7cae67Brave Yao rtc::ThreadChecker thread_checker_; 3101a07a1e8252daf088d1b94b56cce5e9a3e7cae67Brave Yao 31168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com bool _initialized; 31268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com bool _recording; 31368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com bool _playing; 31468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com bool _recIsInitialized; 31568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com bool _playIsInitialized; 31668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com bool _startRec; 31768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com bool _stopRec; 31868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com bool _startPlay; 31968efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com bool _stopPlay; 32068efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com bool _AGC; 321589673f1cbef93921900a835de52d05ad4f3a0e2andrew@webrtc.org bool update_speaker_volume_at_startup_; 32268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 3232550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org uint16_t _playBufDelayFixed; // fixed playback delay 32468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 3252550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org uint32_t _sndCardPlayDelay; 3262550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org uint32_t _sndCardRecDelay; 32768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 3282550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org int32_t _writeErrors; 3292550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org uint16_t _playWarning; 3302550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org uint16_t _playError; 3312550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org uint16_t _recWarning; 3322550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org uint16_t _recError; 33368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 3342550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org uint16_t _deviceIndex; 3352550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org int16_t _numPlayDevices; 3362550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org int16_t _numRecDevices; 33728f3913ca95de8bd489ce3f6afd891864e8779cbleozwang@webrtc.org char* _playDeviceName; 33828f3913ca95de8bd489ce3f6afd891864e8779cbleozwang@webrtc.org char* _recDeviceName; 33928f3913ca95de8bd489ce3f6afd891864e8779cbleozwang@webrtc.org char* _playDisplayDeviceName; 34028f3913ca95de8bd489ce3f6afd891864e8779cbleozwang@webrtc.org char* _recDisplayDeviceName; 34128f3913ca95de8bd489ce3f6afd891864e8779cbleozwang@webrtc.org char _paServerVersion[32]; 34268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 3432550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org int8_t* _playBuffer; 34468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com size_t _playbackBufferSize; 34568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com size_t _playbackBufferUnused; 34668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com size_t _tempBufferSpace; 3472550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org int8_t* _recBuffer; 34868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com size_t _recordBufferSize; 34968efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com size_t _recordBufferUsed; 35068efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com const void* _tempSampleData; 35168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com size_t _tempSampleDataSize; 3522550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org int32_t _configuredLatencyPlay; 3532550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org int32_t _configuredLatencyRec; 35468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 35568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com // PulseAudio 3562550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org uint16_t _paDeviceIndex; 35768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com bool _paStateChanged; 35868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 35968efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com pa_threaded_mainloop* _paMainloop; 36068efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com pa_mainloop_api* _paMainloopApi; 36168efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com pa_context* _paContext; 36268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 36368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com pa_stream* _recStream; 36468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com pa_stream* _playStream; 3652550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org uint32_t _recStreamFlags; 3662550988baaf3a50a2eb1a595c26bc7912ad99b30pbos@webrtc.org uint32_t _playStreamFlags; 36768efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com pa_buffer_attr _playBufferAttr; 36868efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com pa_buffer_attr _recBufferAttr; 369e2a800644c25cccff782096e69f432bbc78336fbniklas.enbom@webrtc.org 370e2a800644c25cccff782096e69f432bbc78336fbniklas.enbom@webrtc.org char _oldKeyState[32]; 371e2a800644c25cccff782096e69f432bbc78336fbniklas.enbom@webrtc.org Display* _XDisplay; 37268efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com}; 37368efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 37468efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com} 37568efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com 37668efa21abcae03939dd03ea6ec11fd6f510c8c47xians@google.com#endif // MODULES_AUDIO_DEVICE_MAIN_SOURCE_LINUX_AUDIO_DEVICE_PULSE_LINUX_H_ 377