PortAudio 2.0
pa_linux_pulseaudio_internal.h
Go to the documentation of this file.
1
2/*
3 * PulseAudio host to play natively in Linux based systems without
4 * ALSA emulation
5 *
6 * Copyright (c) 2014-2023 Tuukka Pasanen <tuukka.pasanen@ilmi.fi>
7 * Copyright (c) 2016 Sqweek
8 *
9 * Based on the Open Source API proposed by Ross Bencina
10 * Copyright (c) 1999-2002 Ross Bencina, Phil Burk
11 *
12 * Permission is hereby granted, free of charge, to any person obtaining
13 * a copy of this software and associated documentation files
14 * (the "Software"), to deal in the Software without restriction,
15 * including without limitation the rights to use, copy, modify, merge,
16 * publish, distribute, sublicense, and/or sell copies of the Software,
17 * and to permit persons to whom the Software is furnished to do so,
18 * subject to the following conditions:
19 *
20 * The above copyright notice and this permission notice shall be
21 * included in all copies or substantial portions of the Software.
22 *
23 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
24 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
25 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
26 * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR
27 * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF
28 * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
29 * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
30 */
31
32/*
33 * The text above constitutes the entire PortAudio license; however,
34 * the PortAudio community also makes the following non-binding requests:
35 *
36 * Any person wishing to distribute modifications to the Software is
37 * requested to send the modifications to the original developer so that
38 * they can be incorporated into the canonical version. It is also
39 * requested that these non-binding requests be included along with the
40 * license above.
41 */
42
43#ifndef _PA_HOSTAPI_PULSEAUDIO_H_
44#define _PA_HOSTAPI_PULSEAUDIO_H_
45
46#include "pa_util.h"
47#include "pa_allocation.h"
48#include "pa_hostapi.h"
49#include "pa_stream.h"
50#include "pa_cpuload.h"
51#include "pa_process.h"
52
53#include "pa_unix_util.h"
54#include "pa_ringbuffer.h"
55#include "pa_debugprint.h"
56
57/* PulseAudio headers */
58#include <stdio.h>
59#include <string.h>
60#include <pulse/pulseaudio.h>
61
62#ifdef __cplusplus
63extern "C"
64{
65#endif /* __cplusplus */
66
67/* prototypes for functions declared in this file */
68
69#define PA_PULSEAUDIO_SET_LAST_HOST_ERROR(errorCode, errorText) \
70 PaUtil_SetLastHostErrorInfo(paInDevelopment, errorCode, errorText)
71
72#define PAPULSEAUDIO_MAX_DEVICECOUNT 1024
73#define PAPULSEAUDIO_MAX_DEVICENAME 1024
74
75/* Default latency values to expose. Chosen by trial and error to be reasonable. */
76#define PA_PULSEAUDIO_DEFAULT_MIN_LATENCY 0.010
77#define PA_PULSEAUDIO_DEFAULT_MAX_LATENCY 0.080
78
79/* Just some value that Pulseaudio can handle */
80#define PAPULSEAUDIO_FRAMESPERBUFFERUNSPEC 32
81
82/* Assuming of 2 seconds of 44100 Hz sample rate with FLOAT (4 bytes) and stereo channels (2 channels).
83 You should have pretty good size buffer with this. If output/intput doesn't happens in 2 second we
84 have more trouble than this buffer.
85 @todo change this to something more sophisticated */
86#define PULSEAUDIO_BUFFER_SIZE (96100 * 4 * 2)
87
109
110/* PaPulseAudio_Stream - a stream data structure specifically for this implementation */
111
113{
118
120 pa_threaded_mainloop *mainloop;
121 pa_context *context;
122 pa_sample_spec outputSampleSpec;
123 pa_sample_spec inputSampleSpec;
124 pa_stream *outputStream;
125 pa_stream *inputStream;
126 pa_buffer_attr outputBufferAttr;
127 pa_buffer_attr inputBufferAttr;
132
137
140
143
145
147
148 /* Used in communication between threads
149 *
150 * State machine works like this:
151 * When stream is wanted to start with Pa_StartStream
152 * then isActive is 1 if opening of devices goes well
153 * and isStopped is then 0.
154 *
155 * When requested to stop isStopped is 1 on isActive is 0
156 * and nothing should be written to ouput or read from input
157 * anymore
158 *
159 * Pulseaudio does not like this as it creates streams and they
160 * start when they are ready and it can be after we have
161 * exited Pa_StartStream or before if get's kicked up very fast
162 *
163 * pulseaudioIsActive and pulseaudioIsStopped are used to find if
164 * there is stream active or stopped in pulseaudio side. They
165 * live their own life besides isActive and isStopped to make sure
166 * that portaudio will have input and output available before
167 * reading or writing to stream.
168 */
169 volatile sig_atomic_t isActive;
170 volatile sig_atomic_t isStopped;
171 volatile sig_atomic_t pulseaudioIsActive;
172 volatile sig_atomic_t pulseaudioIsStopped;
173
174}
176
177/* PulseAudio Error checking macro */
178#define PA_PULSEAUDIO_IS_ERROR(pastream, errorCode) \
179 if( !(pastream) || \
180 !(pastream)->context || \
181 !PA_CONTEXT_IS_GOOD( pa_context_get_state( (pastream)->context ) ) || \
182 ( (pastream)->outputStream && \
183 !PA_STREAM_IS_GOOD( pa_stream_get_state( (pastream)->outputStream ) ) ) || \
184 ( (pastream)->inputStream && \
185 !PA_STREAM_IS_GOOD( pa_stream_get_state( (pastream)->inputStream ) ) ) ) \
186 { \
187 if( !(pastream) || \
188 ( (pastream)->context && \
189 pa_context_get_state( (pastream)->context ) == PA_CONTEXT_FAILED ) || \
190 ( (pastream)->outputStream && \
191 pa_stream_get_state( (pastream)->outputStream ) == PA_STREAM_FAILED ) || \
192 ( (pastream)->inputStream && \
193 pa_stream_get_state( (pastream)->inputStream ) == PA_STREAM_FAILED ) ) \
194 { \
195 return errorCode; \
196 } \
197 } \
198 if( !(pastream)->isActive || (pastream)->isStopped ) \
199 { \
200 return paStreamIsStopped; \
201 }
202
204 pa_operation **pulseaudioOperation);
205
206void PaPulseAudio_Lock( pa_threaded_mainloop *mainloop );
207
208void PaPulseAudio_UnLock( pa_threaded_mainloop *mainloop );
209
211 PaHostApiIndex index );
212
213void Terminate( struct PaUtilHostApiRepresentation *hostApi );
214
215
217 const PaStreamParameters * inputParameters,
218 const PaStreamParameters * outputParameters,
219 double sampleRate );
220
222 PaStream ** s,
223 const PaStreamParameters * inputParameters,
224 const PaStreamParameters * outputParameters,
225 double sampleRate,
226 unsigned long framesPerBuffer,
227 PaStreamFlags streamFlags,
228 PaStreamCallback * streamCallback,
229 void *userData );
230
233
234PaTime GetStreamTime( PaStream * stream );
235double GetStreamCpuLoad( PaStream * stream );
236
239
241
242void PaPulseAudio_CheckContextStateCb( pa_context * c,
243 void *userdata );
244void PaPulseAudio_ServerInfoCb( pa_context *c,
245 const pa_server_info *i,
246 void *userdata );
247
248void PaPulseAudio_SinkListCb( pa_context * c,
249 const pa_sink_info * l,
250 int eol,
251 void *userdata );
252
253void PaPulseAudio_SourceListCb( pa_context * c,
254 const pa_source_info * l,
255 int eol,
256 void *userdata );
257
258void PaPulseAudio_StreamStateCb( pa_stream * s,
259 void *userdata );
260
261void PaPulseAudio_StreamStartedCb( pa_stream * s,
262 void *userdata );
263
264void PaPulseAudio_StreamUnderflowCb( pa_stream * s,
265 void *userdata );
266
268 pa_sample_spec * pulseaudiosf
269);
270
271#ifdef __cplusplus
272}
273#endif /* __cplusplus */
274
275
276#endif
Allocation Group prototypes. An Allocation Group makes it easy to allocate multiple blocks of memory ...
Functions to assist in measuring the CPU utilization of a callback stream. Used to implement the Pa_G...
Interfaces and representation structures used by pa_front.c to manage and communicate with host API i...
void PaPulseAudio_SinkListCb(pa_context *c, const pa_sink_info *l, int eol, void *userdata)
Definition pa_linux_pulseaudio.c:367
void PaPulseAudio_UnLock(pa_threaded_mainloop *mainloop)
Definition pa_linux_pulseaudio_cb.c:170
void Terminate(struct PaUtilHostApiRepresentation *hostApi)
Definition pa_linux_pulseaudio.c:806
int PaPulseAudio_CheckConnection(PaPulseAudio_HostApiRepresentation *ptr)
Definition pa_linux_pulseaudio.c:67
PaError IsFormatSupported(struct PaUtilHostApiRepresentation *hostApi, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate)
Definition pa_linux_pulseaudio.c:819
PaError IsStreamActive(PaStream *stream)
Definition pa_linux_pulseaudio.c:1385
PaError OpenStream(struct PaUtilHostApiRepresentation *hostApi, PaStream **s, const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate, unsigned long framesPerBuffer, PaStreamFlags streamFlags, PaStreamCallback *streamCallback, void *userData)
Definition pa_linux_pulseaudio.c:999
void PaPulseAudio_Lock(pa_threaded_mainloop *mainloop)
Definition pa_linux_pulseaudio_cb.c:156
double GetStreamCpuLoad(PaStream *stream)
Definition pa_linux_pulseaudio.c:1425
void PaPulseAudio_ReleaseOperation(PaPulseAudio_HostApiRepresentation *hostapi, pa_operation **pulseaudioOperation)
Definition pa_linux_pulseaudio_cb.c:109
PaError PaPulseAudio_Initialize(PaUtilHostApiRepresentation **hostApi, PaHostApiIndex index)
Definition pa_linux_pulseaudio.c:561
void PaPulseAudio_StreamStateCb(pa_stream *s, void *userdata)
Definition pa_linux_pulseaudio.c:471
PaPulseAudio_HostApiRepresentation * PaPulseAudio_New(void)
Definition pa_linux_pulseaudio.c:141
void PaPulseAudio_StreamStartedCb(pa_stream *s, void *userdata)
Definition pa_linux_pulseaudio_cb.c:556
struct PaPulseAudio_Stream PaPulseAudio_Stream
void PaPulseAudio_StreamUnderflowCb(pa_stream *s, void *userdata)
Definition pa_linux_pulseaudio.c:535
PaError IsStreamStopped(PaStream *s)
Definition pa_linux_pulseaudio.c:1378
void PaPulseAudio_Free(PaPulseAudio_HostApiRepresentation *ptr)
Definition pa_linux_pulseaudio.c:206
PaError PaPulseAudio_ConvertPortaudioFormatToPaPulseAudio_(PaSampleFormat portaudiosf, pa_sample_spec *pulseaudiosf)
Definition pa_linux_pulseaudio.c:919
#define PAPULSEAUDIO_MAX_DEVICECOUNT
Definition pa_linux_pulseaudio_internal.h:72
void PaPulseAudio_CheckContextStateCb(pa_context *c, void *userdata)
Definition pa_linux_pulseaudio.c:257
void PaPulseAudio_ServerInfoCb(pa_context *c, const pa_server_info *i, void *userdata)
Definition pa_linux_pulseaudio.c:275
void PaPulseAudio_SourceListCb(pa_context *c, const pa_source_info *l, int eol, void *userdata)
Definition pa_linux_pulseaudio.c:419
PaTime GetStreamTime(PaStream *stream)
Definition pa_linux_pulseaudio.c:1392
Buffer Processor prototypes. A Buffer Processor performs buffer length adaption, coordinates sample f...
Single-reader single-writer lock-free ring buffer.
Stream interfaces, representation structures and helper functions used to interface between pa_front....
Prototypes for utility functions used by PortAudio implementations.
void PaStream
Definition portaudio.h:644
unsigned long PaStreamFlags
Definition portaudio.h:662
unsigned long PaSampleFormat
Definition portaudio.h:489
int PaError
Definition portaudio.h:122
int PaStreamCallback(const void *input, void *output, unsigned long frameCount, const PaStreamCallbackTimeInfo *timeInfo, PaStreamCallbackFlags statusFlags, void *userData)
Definition portaudio.h:839
int PaDeviceIndex
Definition portaudio.h:214
int PaHostApiIndex
Definition portaudio.h:240
double PaTime
Definition portaudio.h:465
Definition portaudio.h:506
Definition pa_linux_pulseaudio_internal.h:89
pa_context * context
Definition pa_linux_pulseaudio_internal.h:104
PaUtilStreamInterface callbackStreamInterface
Definition pa_linux_pulseaudio_internal.h:91
PaUtilStreamInterface blockingStreamInterface
Definition pa_linux_pulseaudio_internal.h:92
pa_time_event * timeEvent
Definition pa_linux_pulseaudio_internal.h:106
PaHostApiIndex hostApiIndex
Definition pa_linux_pulseaudio_internal.h:96
pa_mainloop_api * mainloopApi
Definition pa_linux_pulseaudio_internal.h:103
pa_sample_spec pulseaudioDefaultSampleSpec
Definition pa_linux_pulseaudio_internal.h:99
PaUtilAllocationGroup * allocations
Definition pa_linux_pulseaudio_internal.h:94
pa_threaded_mainloop * mainloop
Definition pa_linux_pulseaudio_internal.h:102
int deviceCount
Definition pa_linux_pulseaudio_internal.h:105
PaUtilHostApiRepresentation inheritedHostApiRep
Definition pa_linux_pulseaudio_internal.h:90
Definition pa_linux_pulseaudio_internal.h:113
volatile sig_atomic_t pulseaudioIsActive
Definition pa_linux_pulseaudio_internal.h:171
PaDeviceIndex inputDevice
Definition pa_linux_pulseaudio_internal.h:138
PaPulseAudio_HostApiRepresentation * hostapi
Definition pa_linux_pulseaudio_internal.h:117
unsigned int suggestedLatencyUSecs
Definition pa_linux_pulseaudio_internal.h:128
volatile sig_atomic_t isActive
Definition pa_linux_pulseaudio_internal.h:169
size_t missedBytes
Definition pa_linux_pulseaudio_internal.h:146
PaUtilBufferProcessor bufferProcessor
Definition pa_linux_pulseaudio_internal.h:116
pa_stream * inputStream
Definition pa_linux_pulseaudio_internal.h:125
PaUtilCpuLoadMeasurer cpuLoadMeasurer
Definition pa_linux_pulseaudio_internal.h:115
PaUtilStreamRepresentation streamRepresentation
Definition pa_linux_pulseaudio_internal.h:114
PaUtilRingBuffer inputRing
Definition pa_linux_pulseaudio_internal.h:144
pa_sample_spec outputSampleSpec
Definition pa_linux_pulseaudio_internal.h:122
pa_buffer_attr outputBufferAttr
Definition pa_linux_pulseaudio_internal.h:126
pa_stream * outputStream
Definition pa_linux_pulseaudio_internal.h:124
unsigned long framesPerHostCallback
Definition pa_linux_pulseaudio_internal.h:119
int inputFrameSize
Definition pa_linux_pulseaudio_internal.h:136
int outputChannelCount
Definition pa_linux_pulseaudio_internal.h:130
pa_context * context
Definition pa_linux_pulseaudio_internal.h:121
int inputChannelCount
Definition pa_linux_pulseaudio_internal.h:131
volatile sig_atomic_t isStopped
Definition pa_linux_pulseaudio_internal.h:170
volatile sig_atomic_t pulseaudioIsStopped
Definition pa_linux_pulseaudio_internal.h:172
PaDeviceIndex outputDevice
Definition pa_linux_pulseaudio_internal.h:139
pa_buffer_attr inputBufferAttr
Definition pa_linux_pulseaudio_internal.h:127
int outputFrameSize
Definition pa_linux_pulseaudio_internal.h:135
char * outputStreamName
Definition pa_linux_pulseaudio_internal.h:141
pa_sample_spec inputSampleSpec
Definition pa_linux_pulseaudio_internal.h:123
size_t maxFramesPerBuffer
Definition pa_linux_pulseaudio_internal.h:133
int outputUnderflows
Definition pa_linux_pulseaudio_internal.h:129
size_t maxFramesHostPerBuffer
Definition pa_linux_pulseaudio_internal.h:134
char * inputStreamName
Definition pa_linux_pulseaudio_internal.h:142
pa_threaded_mainloop * mainloop
Definition pa_linux_pulseaudio_internal.h:120
Definition portaudio.h:548
Definition pa_allocation.h:66
The main buffer processor data structure.
Definition pa_process.h:253
Definition pa_cpuload.h:56
Definition pa_hostapi.h:201
Definition pa_ringbuffer.h:94
Definition pa_stream.h:67
Definition pa_stream.h:147