Initial Import
[profile/ivi/alsa-lib.git] / src / pcm / pcm.c
1 /**
2  * \file pcm/pcm.c
3  * \ingroup PCM
4  * \brief PCM Interface
5  * \author Jaroslav Kysela <perex@perex.cz>
6  * \author Abramo Bagnara <abramo@alsa-project.org>
7  * \date 2000-2001
8  *
9  * PCM Interface is designed to write or read digital audio frames. A
10  * frame is the data unit converted into/from sound in one time unit
11  * (1/rate seconds), by example if you set your playback PCM rate to
12  * 44100 you'll hear 44100 frames per second. The size in bytes of a
13  * frame may be obtained from bits needed to store a sample and
14  * channels count.
15  *
16  * See the \ref pcm page for more details.
17  */
18 /*
19  *  PCM Interface - main file
20  *  Copyright (c) 1998 by Jaroslav Kysela <perex@perex.cz>
21  *  Copyright (c) 2000 by Abramo Bagnara <abramo@alsa-project.org>
22  *
23  *   This library is free software; you can redistribute it and/or modify
24  *   it under the terms of the GNU Lesser General Public License as
25  *   published by the Free Software Foundation; either version 2.1 of
26  *   the License, or (at your option) any later version.
27  *
28  *   This program is distributed in the hope that it will be useful,
29  *   but WITHOUT ANY WARRANTY; without even the implied warranty of
30  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
31  *   GNU Lesser General Public License for more details.
32  *
33  *   You should have received a copy of the GNU Lesser General Public
34  *   License along with this library; if not, write to the Free Software
35  *   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
36  *
37  */
38
39 /*! \page pcm PCM (digital audio) interface
40
41 <P>Although abbreviation PCM stands for Pulse Code Modulation, we are
42 understanding it as general digital audio processing with volume samples
43 generated in continuous time periods.</P>
44
45 <P>The analog signal is recorded via analog to digital converters (ADC).
46 The digital value (de-facto a volume at a specific time) obtained
47 from ADC can be further processed. The following picture shows a perfect
48 sinus waveform:</P>
49
50 <BR>
51 \image html wave1.gif
52
53 <P>Next image shows digitized representation:</P>
54
55 <BR>
56 \image html wave2.gif
57
58 <P>As you may see, the quality of digital audio signal depends on the time
59 (recording rate) and voltage resolution (usually in an linear integer
60 representation with basic unit one bit).</P>
61
62 <P>The stored digital signal can be converted back to voltage (analog)
63 representation via digital to analog converters (DAC).</P>
64
65 <P>One digital value is called sample. More samples are collected to frames
66 (frame is terminology for ALSA) depending on count of converters used at one
67 specific time. One frame might contain one sample (when only one converter is
68 used - mono) or more samples (for example: stereo has signals from two converters
69 recorded at same time). Digital audio stream contains collection of frames
70 recorded at boundaries of continuous time periods.</P>
71
72 \section pcm_general_overview General overview
73
74 ALSA uses the ring buffer to store outgoing (playback) and incoming (capture,
75 record) samples. There are two pointers being maintained to allow
76 a precise communication between application and device pointing to current
77 processed sample by hardware and last processed sample by application.
78 The modern audio chips allow to program the transfer time periods.
79 It means that the stream of samples is divided to small chunks. Device
80 acknowledges to application when the transfer of a chunk is complete.
81
82 \section pcm_transfer Transfer methods in UNIX environments
83
84 In the UNIX environment, data chunk acknowledges are received via standard I/O
85 calls or event waiting routines (poll or select function). To accomplish
86 this list, the asynchronous notification of acknowledges should be listed
87 here. The ALSA implementation for these methods is described in
88 the \ref alsa_transfers section.
89
90 \subsection pcm_transfer_io Standard I/O transfers
91
92 The standard I/O transfers are using the read (see 'man 2 read') and write
93 (see 'man 2 write') C functions. There are two basic behaviours of these
94 functions - blocked and non-blocked (see the O_NONBLOCK flag for the
95 standard C open function - see 'man 2 open'). In non-blocked behaviour,
96 these I/O functions never stops, they return -EAGAIN error code, when no
97 data can be transferred (the ring buffer is full in our case). In blocked
98 behaviour, these I/O functions stop and wait until there is a room in the
99 ring buffer (playback) or until there are a new samples (capture). The ALSA
100 implementation can be found in the \ref alsa_pcm_rw section.
101
102 \subsection pcm_transfer_event Event waiting routines
103
104 The poll or select functions (see 'man 2 poll' or 'man 2 select' for further
105 details) allows to receive requests/events from the device while
106 an application is waiting on events from other sources (like keyboard, screen,
107 network etc.), too. \ref snd_pcm_poll_descriptors can be used to get file
108 descriptors to poll or select on (note that wait direction might be diferent
109 than expected - do not use only returned file descriptors, but handle
110 events member as well - see \ref snd_pcm_poll_descriptors function
111 description for more details and \ref snd_pcm_poll_descriptors_revents for
112 events demangling). The implemented transfer routines can be found in
113 the \ref alsa_transfers section.
114
115 \subsection pcm_transfer_async Asynchronous notification
116
117 ALSA driver and library knows to handle the asynchronous notifications over
118 the SIGIO signal. This signal allows to interrupt application and transfer
119 data in the signal handler. For further details see the sigaction function
120 ('man 2 sigaction'). The section \ref pcm_async describes the ALSA API for
121 this extension. The implemented transfer routines can be found in the
122 \ref alsa_transfers section.
123
124 \section pcm_open_behaviour Blocked and non-blocked open
125
126 The ALSA PCM API uses a different behaviour when the device is opened
127 with blocked or non-blocked mode. The mode can be specified with
128 \a mode argument in #snd_pcm_open() function.
129 The blocked mode is the default (without #SND_PCM_NONBLOCK mode).
130 In this mode, the behaviour is that if the resources have already used
131 with another application, then it blocks the caller, until resources are
132 free. The non-blocked behaviour (with #SND_PCM_NONBLOCK)
133 doesn't block the caller in any way and returns -EBUSY error when the
134 resources are not available. Note that the mode also determines the
135 behaviour of standard I/O calls, returning -EAGAIN when non-blocked mode is
136 used and the ring buffer is full (playback) or empty (capture).
137 The operation mode for I/O calls can be changed later with
138 the #snd_pcm_nonblock() function.
139
140 \section pcm_async Asynchronous mode
141
142 There is also possibility to receive asynchronous notification after
143 specified time periods. You may see the #SND_PCM_ASYNC
144 mode for #snd_pcm_open() function and
145 #snd_async_add_pcm_handler() function for further details.
146
147 \section pcm_handshake Handshake between application and library
148
149 The ALSA PCM API design uses the states to determine the communication
150 phase between application and library. The actual state can be determined
151 using #snd_pcm_state() call. There are these states:
152
153 \par SND_PCM_STATE_OPEN
154 The PCM device is in the open state. After the #snd_pcm_open() open call,
155 the device is in this state. Also, when #snd_pcm_hw_params() call fails,
156 then this state is entered to force application calling 
157 #snd_pcm_hw_params() function to set right communication
158 parameters.
159
160 \par SND_PCM_STATE_SETUP
161 The PCM device has accepted communication parameters and it is waiting
162 for #snd_pcm_prepare() call to prepare the hardware for
163 selected operation (playback or capture).
164
165 \par SND_PCM_STATE_PREPARE
166 The PCM device is prepared for operation. Application can use
167 #snd_pcm_start() call, write or read data to start
168 the operation.
169
170 \par SND_PCM_STATE_RUNNING
171 The PCM device has been started and is running. It processes the samples. The stream can
172 be stopped using the #snd_pcm_drop() or
173 #snd_pcm_drain() calls.
174
175 \par SND_PCM_STATE_XRUN
176 The PCM device reached overrun (capture) or underrun (playback).
177 You can use the -EPIPE return code from I/O functions
178 (#snd_pcm_writei(), #snd_pcm_writen(), #snd_pcm_readi(), #snd_pcm_readn())
179 to determine this state without checking
180 the actual state via #snd_pcm_state() call. It is recommended to use
181 the helper function #snd_pcm_recover() to recover from this state, but you can also use #snd_pcm_prepare(),
182 #snd_pcm_drop() or #snd_pcm_drain() calls.
183
184 \par SND_PCM_STATE_DRAINING
185 The device is in this state when application using the capture mode
186 called #snd_pcm_drain() function. Until all data are
187 read from the internal ring buffer using I/O routines
188 (#snd_pcm_readi(), #snd_pcm_readn()),
189 then the device stays in this state.
190
191 \par SND_PCM_STATE_PAUSED
192 The device is in this state when application called
193 the #snd_pcm_pause() function until the pause is released.
194 Not all hardware supports this feature. Application should check the
195 capability with the #snd_pcm_hw_params_can_pause().
196
197 \par SND_PCM_STATE_SUSPENDED
198 The device is in the suspend state provoked with the power management
199 system. The stream can be resumed using #snd_pcm_resume()
200 call, but not all hardware supports this feature. Application should check
201 the capability with the #snd_pcm_hw_params_can_resume().
202 In other case, the calls #snd_pcm_prepare(),
203 #snd_pcm_drop(), #snd_pcm_drain() can be used
204 to leave this state.
205
206 \par SND_PCM_STATE_DISCONNECTED
207 The device is physicaly disconnected. It does not accept any I/O calls in this state.
208
209 \section pcm_formats PCM formats
210
211 The full list of formats present the #snd_pcm_format_t type.
212 The 24-bit linear samples uses 32-bit physical space, but the sample is
213 stored in low three bits. Some hardware does not support processing of full
214 range, thus you may get the significant bits for linear samples via
215 #snd_pcm_hw_params_get_sbits() function. The example: ICE1712
216 chips support 32-bit sample processing, but low byte is ignored (playback)
217 or zero (capture). The function snd_pcm_hw_params_get_sbits()
218 returns 24 in the case.
219
220 \section alsa_transfers ALSA transfers
221
222 There are two methods to transfer samples in application. The first method
223 is the standard read / write one. The second method, uses the direct audio
224 buffer to communicate with the device while ALSA library manages this space
225 itself. You can find examples of all communication schemes for playback
226 in \ref example_test_pcm "Sine-wave generator example". To complete the
227 list, we should note that #snd_pcm_wait() function contains
228 embedded poll waiting implementation.
229
230 \subsection alsa_pcm_rw Read / Write transfer
231
232 There are two versions of read / write routines. The first expects the
233 interleaved samples at input (#SND_PCM_ACCESS_RW_INTERLEAVED access method),
234 and the second one expects non-interleaved (samples in separated buffers -
235 #SND_PCM_ACCESS_RW_NONINTERLEAVED access method) at input. There are these
236 functions for interleaved transfers: #snd_pcm_writei()
237 #snd_pcm_readi(). For non-interleaved transfers, there are
238 these functions: #snd_pcm_writen() and #snd_pcm_readn().
239
240 \subsection alsa_mmap_rw Direct Read / Write transfer (via mmap'ed areas)
241
242 Three kinds of organization of ring buffer memory areas exist in ALSA API.
243 Access #SND_PCM_ACCESS_MMAP_INTERLEAVED has interleaved samples. Access
244 #SND_PCM_ACCESS_MMAP_NONINTERLEAVED expects continous sample areas for
245 one channel. Access #SND_PCM_ACCESS_MMAP_COMPLEX does not fit to interleaved
246 and non-interleaved ring buffer organization.
247
248 There are two functions for this kind of transfer. Application can get an
249 access to memory areas via #snd_pcm_mmap_begin() function.
250 This function returns the areas (single area is equal to a channel)
251 containing the direct pointers to memory and sample position description
252 in #snd_pcm_channel_area_t structure. After application
253 transfers the data in the memory areas, then it must be acknowledged
254 the end of transfer via #snd_pcm_mmap_commit() function
255 to allow the ALSA library update the pointers to ring buffer. This kind of
256 communication is also called "zero-copy", because the device does not require
257 to copy the samples from application to another place in system memory.
258
259 If you like to use the compatibility functions in mmap mode, there are
260 read / write routines equaling to standard read / write transfers. Using
261 these functions discards the benefits of direct access to memory region.
262 See the #snd_pcm_mmap_readi(),
263 #snd_pcm_writei(), #snd_pcm_readn()
264 and #snd_pcm_writen() functions.
265
266 \section pcm_errors Error codes
267
268 \par -EPIPE
269
270 This error means xrun (underrun for playback or overrun for capture).
271 The underrun can happen when an application does not feed new samples
272 in time to alsa-lib (due CPU usage). The overrun can happen when
273 an application does not take new captured samples in time from alsa-lib.
274
275 \par -ESTRPIPE
276
277 This error means that system has suspended drivers. The application
278 should wait in loop when snd_pcm_resume() != -EAGAIN and then
279 call snd_pcm_prepare() when snd_pcm_resume() return an error code.
280 If snd_pcm_resume() does not fail (a zero value is returned), driver
281 supports resume and the snd_pcm_prepare() call can be ommited.
282
283 \par -EBADFD
284
285 This error means that the device is in a bad state. It means that
286 the handskahe between application and alsa-lib is corrupted.
287
288 \par -ENOTTY, -ENODEV
289
290 This error can happen when device is physically removed (for example
291 some hotplug devices like USB or PCMCIA, CardBus or ExpressCard
292 can be removed on the fly).
293
294 \section pcm_params Managing parameters
295
296 The ALSA PCM device uses two groups of PCM related parameters. The hardware
297 parameters contains the stream description like format, rate, count of
298 channels, ring buffer size etc. The software parameters contains the
299 software (driver) related parameters. The communication behaviour can be
300 controlled via these parameters, like automatic start, automatic stop,
301 interrupting (chunk acknowledge) etc. The software parameters can be
302 modified at any time (when valid hardware parameters are set). It includes
303 the running state as well.
304
305 \subsection pcm_hw_params Hardware related parameters
306
307 The ALSA PCM devices use the parameter refining system for hardware
308 parameters - #snd_pcm_hw_params_t. It means, that
309 application choose the full-range of configurations at first and then
310 application sets single parameters until all parameters are elementary
311 (definite).
312
313 \par Access modes
314
315 ALSA knows about five access modes. The first three can be used for direct
316 communication. The access mode #SND_PCM_ACCESS_MMAP_INTERLEAVED
317 determines the direct memory area and interleaved sample organization.
318 Interleaved organization means, that samples from channels are mixed together.
319 The access mode #SND_PCM_ACCESS_MMAP_NONINTERLEAVED
320 determines the direct memory area and non-interleaved sample organization.
321 Each channel has a separate buffer in the case. The complex direct memory
322 organization represents the #SND_PCM_ACCESS_MMAP_COMPLEX
323 access mode. The sample organization does not fit the interleaved or
324 non-interleaved access modes in the case. The last two access modes
325 describes the read / write access methods.
326 The #SND_PCM_ACCESS_RW_INTERLEAVED access represents the read /
327 write interleaved access and the #SND_PCM_ACCESS_RW_NONINTERLEAVED
328 represents the non-interleaved access.
329
330 \par Formats
331
332 The full list of formats is available in #snd_pcm_format_t
333 enumeration.
334
335 \subsection pcm_sw_params Software related parameters
336
337 These parameters - #snd_pcm_sw_params_t can be modified at
338 any time including the running state.
339
340 \par Minimum available count of samples
341
342 This parameter controls the wakeup point. If the count of available samples
343 is equal or greater than this value, then application will be activated.
344
345 \par Timestamp mode
346
347 The timestamp mode specifies, if timestamps are activated. Currently, only
348 #SND_PCM_TSTAMP_NONE and #SND_PCM_TSTAMP_MMAP
349 modes are known. The mmap mode means that timestamp is taken
350 on every period time boundary. Corresponding position in the ring buffer
351 assigned to timestamp can be obtained using #snd_pcm_htimestamp() function.
352
353 \par Transfer align
354
355 The read / write transfers can be aligned to this sample count. The modulo
356 is ignored by device. Usually, this value is set to one (no align).
357
358 \par Start threshold
359
360 The start threshold parameter is used to determine the start point in
361 stream. For playback, if samples in ring buffer is equal or greater than
362 the start threshold parameters and the stream is not running, the stream will
363 be started automatically from the device. For capture, if the application wants
364 to read count of samples equal or greater then the stream will be started.
365 If you want to use explicit start (#snd_pcm_start), you can
366 set this value greater than ring buffer size (in samples), but use the
367 constant MAXINT is not a bad idea.
368
369 \par Stop threshold
370
371 Similarly, the stop threshold parameter is used to automatically stop
372 the running stream, when the available samples crosses this boundary.
373 It means, for playback, the empty samples in ring buffer and for capture,
374 the filled (used) samples in ring buffer.
375
376 \par Silence threshold
377
378 The silence threshold specifies count of samples filled with silence
379 ahead of the current application pointer for playback. It is usable
380 for applications when an overrun is possible (like tasks depending on
381 network I/O etc.). If application wants to manage the ahead samples itself,
382 the #snd_pcm_rewind() function allows to forget the last
383 samples in the stream.
384
385 \section pcm_status Obtaining stream status
386
387 The stream status is stored in #snd_pcm_status_t structure.
388 These parameters can be obtained: the current stream state -
389 #snd_pcm_status_get_state(), timestamp of trigger -
390 #snd_pcm_status_get_trigger_tstamp(), timestamp of last
391 pointer update #snd_pcm_status_get_tstamp(), delay in samples -
392 #snd_pcm_status_get_delay(), available count in samples -
393 #snd_pcm_status_get_avail(), maximum available samples -
394 #snd_pcm_status_get_avail_max(), ADC over-range count in
395 samples - #snd_pcm_status_get_overrange(). The last two
396 parameters - avail_max and overrange are reset to zero after the status
397 call.
398
399 \subsection pcm_status_fast Obtaining stream state fast and update r/w pointer
400
401 <p>
402 The function #snd_pcm_avail_update() updates the current
403 available count of samples for writing (playback) or filled samples for
404 reading (capture). This call is mandatory for updating actual r/w pointer.
405 Using standalone, it is a light method to obtain current stream position,
406 because it does not require the user <-> kernel context switch, but the value
407 is less accurate, because ring buffer pointers are updated in kernel drivers
408 only when an interrupt occurs. If you want to get accurate stream state,
409 use functions #snd_pcm_avail(), #snd_pcm_delay() or #snd_pcm_avail_delay().
410 </p>
411 <p>
412 The function #snd_pcm_avail() reads the current hardware pointer
413 in the ring buffer from hardware and calls #snd_pcm_avail_update() then.
414 </p>
415 <p>
416 The function #snd_pcm_delay() returns the delay in samples.
417 For playback, it means count of samples in the ring buffer before
418 the next sample will be sent to DAC. For capture, it means count of samples
419 in the ring buffer before the next sample will be captured from ADC. It works
420 only when the stream is in the running or draining (playback only) state.
421 Note that this function does not update the current r/w pointer for applications,
422 so the function #snd_pcm_avail_update() must be called afterwards
423 before any read/write begin+commit operations.
424 </p>
425 <p>
426 The function #snd_pcm_avail_delay() combines #snd_pcm_avail() and
427 #snd_pcm_delay() and returns both values in sync.
428 </p>
429
430 \section pcm_action Managing the stream state
431
432 The following functions directly and indirectly affect the stream state:
433
434 \par snd_pcm_hw_params
435 The #snd_pcm_hw_params() function brings the stream state
436 to #SND_PCM_STATE_SETUP
437 if successfully finishes, otherwise the state #SND_PCM_STATE_OPEN
438 is entered.
439 When it is brought to SETUP state, this function automatically
440 calls #snd_pcm_prepare() function to bring to the PREPARE state
441 as below.
442
443 \par snd_pcm_prepare
444 The #snd_pcm_prepare() function enters from #SND_PCM_STATE_SETUP
445 to the #SND_PCM_STATE_PREPARED after a successful finish.
446
447 \par snd_pcm_start
448 The #snd_pcm_start() function enters
449 the #SND_PCM_STATE_RUNNING after a successful finish.
450
451 \par snd_pcm_drop
452 The #snd_pcm_drop() function enters the
453 #SND_PCM_STATE_SETUP state.
454
455 \par snd_pcm_drain
456 The #snd_pcm_drain() function enters the
457 #SND_PCM_STATE_DRAINING, if
458 the capture device has some samples in the ring buffer otherwise
459 #SND_PCM_STATE_SETUP state is entered.
460
461 \par snd_pcm_pause
462 The #snd_pcm_pause() function enters the
463 #SND_PCM_STATE_PAUSED or #SND_PCM_STATE_RUNNING.
464
465 \par snd_pcm_writei, snd_pcm_writen
466 The #snd_pcm_writei() and #snd_pcm_writen()
467 functions can conditionally start the stream -
468 #SND_PCM_STATE_RUNNING. They depend on the start threshold
469 software parameter.
470
471 \par snd_pcm_readi, snd_pcm_readn
472 The #snd_pcm_readi() and #snd_pcm_readn()
473 functions can conditionally start the stream -
474 #SND_PCM_STATE_RUNNING. They depend on the start threshold
475 software parameter.
476
477 \section pcm_sync Streams synchronization
478
479 There are two functions allowing link multiple streams together. In the
480 case, the linking means that all operations are synchronized. Because the
481 drivers cannot guarantee the synchronization (sample resolution) on hardware
482 lacking this feature, the #snd_pcm_info_get_sync() function
483 returns synchronization ID - #snd_pcm_sync_id_t, which is equal
484 for hardware synchronized streams. When the #snd_pcm_link()
485 function is called, all operations managing the stream state for these two
486 streams are joined. The opposite function is #snd_pcm_unlink().
487
488 \section pcm_dev_names PCM naming conventions
489
490 The ALSA library uses a generic string representation for names of devices.
491 The devices might be virtual, physical or a mix of both. The generic string
492 is passed to #snd_pcm_open() or #snd_pcm_open_lconf().
493 It contains two parts: device name and arguments. Devices and arguments are described
494 in configuration files. The usual place for default definitions is at /usr/share/alsa/alsa.conf.
495 For detailed descriptions about integrated PCM plugins look to \ref pcm_plugins.
496
497 \subsection pcm_dev_names_default Default device
498
499 The default device is equal to plug plugin with hw plugin as slave. The defaults are
500 used:
501
502 \code
503 defaults.pcm.card 0
504 defaults.pcm.device 0
505 defaults.pcm.subdevice -1
506 \endcode
507
508 These defaults can be freely overwritten in local configuration files.
509
510 Example:
511
512 \code
513 default
514 \endcode
515
516 \subsection pcm_dev_names_hw HW device
517
518 The hw device description uses the hw plugin. The three arguments (in order: CARD,DEV,SUBDEV)
519 specify card number or identifier, device number and subdevice number (-1 means any).
520
521 Example:
522
523 \code
524 hw
525 hw:0
526 hw:0,0
527 hw:supersonic,1
528 hw:soundwave,1,2
529 hw:DEV=1,CARD=soundwave,SUBDEV=2
530 \endcode
531
532 \subsection pcm_dev_names_plughw Plug->HW device
533
534 The plughw device description uses the plug plugin and hw plugin as slave. The arguments
535 are same as for hw device.
536
537 Example:
538
539 \code
540 plughw
541 plughw:0
542 plughw:0,0
543 plughw:supersonic,1
544 plughw:soundwave,1,2
545 plughw:DEV=1,CARD=soundwave,SUBDEV=2
546 \endcode
547
548 \subsection pcm_dev_names_plug Plug device
549
550 The plug device uses the plug plugin. The one SLAVE argument specifies the slave plugin.
551
552 Example:
553
554 \code
555 plug:mypcmdef
556 plug:hw
557 plug:'hw:0,0'
558 plug:SLAVE=hw
559 \endcode
560
561 \subsection pcm_dev_names_shm Shared memory device
562
563 The shm device uses the shm plugin. The two arguments (in order: SOCKET,PCM) specify
564 UNIX socket name (for example /tmp/alsa.socket) for server communication and server's PCM name.
565
566 Example:
567
568 \code
569 shm:'/tmp/alsa.sock',default
570 shm:SOCKET='/tmp/alsa.sock',PCM=default
571 \endcode
572
573 \subsection pcm_dev_names_tee Tee device
574
575 The tee device stores contents of a stream to given file plus transfers it to given slave plugin.
576 The three arguments (in order: SLAVE,FILE,FORMAT) specify slave plugin, filename and file format.
577
578 Example:
579
580 \code
581 tee:hw,'/tmp/out.raw',raw
582 \endcode
583
584 \subsection pcm_dev_names_file File device
585
586 The file device is file plugin with null plugin as slave. The arguments (in order: FILE,FORMAT)
587 specify filename and file format.
588
589 Example:
590
591 \code
592 file:'/tmp/out.raw',raw
593 \endcode
594
595 \subsection pcm_dev_names_null Null device
596
597 The null device is null plugin. This device has not any arguments.
598
599
600 \section pcm_examples Examples
601
602 The full featured examples with cross-links can be found in Examples section
603 (see top of page):
604
605 \anchor example_test_pcm
606 \par Sine-wave generator
607 \par
608 alsa-lib/test/pcm.c example shows various transfer methods for the playback direction.
609
610 \par Minimalistic PCM playback code
611 \par
612 alsa-lib/test/pcm_min.c example shows the minimal code to produce a sound.
613
614 \par Latency measuring tool
615 \par
616 alsa-lib/test/latency.c example shows the measuring of minimal latency between capture and
617 playback devices.
618
619 */
620
621 /**
622 \example ../../test/pcm.c
623 */
624 /**
625 \example ../../test/pcm_min.c
626 */
627 /**
628 \example ../../test/latency.c
629 */
630
631 #include <stdio.h>
632 #include <string.h>
633 #include <malloc.h>
634 #include <stdarg.h>
635 #include <signal.h>
636 #include <sys/poll.h>
637 #include <sys/shm.h>
638 #include <sys/mman.h>
639 #include <limits.h>
640 #include "pcm_local.h"
641
642 /**
643  * \brief get identifier of PCM handle
644  * \param pcm PCM handle
645  * \return ascii identifier of PCM handle
646  *
647  * Returns the ASCII identifier of given PCM handle. It's the same
648  * identifier specified in snd_pcm_open().
649  */
650 const char *snd_pcm_name(snd_pcm_t *pcm)
651 {
652         assert(pcm);
653         return pcm->name;
654 }
655
656 /**
657  * \brief get type of PCM handle
658  * \param pcm PCM handle
659  * \return type of PCM handle
660  *
661  * Returns the type #snd_pcm_type_t of given PCM handle.
662  */
663 snd_pcm_type_t snd_pcm_type(snd_pcm_t *pcm)
664 {
665         assert(pcm);
666         return pcm->type;
667 }
668
669 /**
670  * \brief get stream for a PCM handle
671  * \param pcm PCM handle
672  * \return stream of PCM handle
673  *
674  * Returns the type #snd_pcm_stream_t of given PCM handle.
675  */
676 snd_pcm_stream_t snd_pcm_stream(snd_pcm_t *pcm)
677 {
678         assert(pcm);
679         return pcm->stream;
680 }
681
682 /**
683  * \brief close PCM handle
684  * \param pcm PCM handle
685  * \return 0 on success otherwise a negative error code
686  *
687  * Closes the specified PCM handle and frees all associated
688  * resources.
689  */
690 int snd_pcm_close(snd_pcm_t *pcm)
691 {
692         int res = 0, err;
693         assert(pcm);
694         if (pcm->setup && !pcm->donot_close) {
695                 snd_pcm_drop(pcm);
696                 err = snd_pcm_hw_free(pcm);
697                 if (err < 0)
698                         res = err;
699         }
700         if (pcm->mmap_channels)
701                 snd_pcm_munmap(pcm);
702         while (!list_empty(&pcm->async_handlers)) {
703                 snd_async_handler_t *h = list_entry(pcm->async_handlers.next, snd_async_handler_t, hlist);
704                 snd_async_del_handler(h);
705         }
706         err = pcm->ops->close(pcm->op_arg);
707         if (err < 0)
708                 res = err;
709         err = snd_pcm_free(pcm);
710         if (err < 0)
711                 res = err;
712         return res;
713 }       
714
715 /**
716  * \brief set nonblock mode
717  * \param pcm PCM handle
718  * \param nonblock 0 = block, 1 = nonblock mode
719  * \return 0 on success otherwise a negative error code
720  */
721 int snd_pcm_nonblock(snd_pcm_t *pcm, int nonblock)
722 {
723         int err;
724         assert(pcm);
725         if ((err = pcm->ops->nonblock(pcm->op_arg, nonblock)) < 0)
726                 return err;
727         if (nonblock)
728                 pcm->mode |= SND_PCM_NONBLOCK;
729         else {
730                 if (pcm->hw_flags & SND_PCM_HW_PARAMS_NO_PERIOD_WAKEUP)
731                         return -EINVAL;
732                 pcm->mode &= ~SND_PCM_NONBLOCK;
733         }
734         return 0;
735 }
736
737 #ifndef DOC_HIDDEN
738 /**
739  * \brief set async mode
740  * \param pcm PCM handle
741  * \param sig Signal to raise: < 0 disable, 0 default (SIGIO)
742  * \param pid Process ID to signal: 0 current
743  * \return 0 on success otherwise a negative error code
744  *
745  * A signal is raised every period.
746  */
747 int snd_pcm_async(snd_pcm_t *pcm, int sig, pid_t pid)
748 {
749         assert(pcm);
750         if (sig == 0)
751                 sig = SIGIO;
752         if (pid == 0)
753                 pid = getpid();
754         return pcm->ops->async(pcm->op_arg, sig, pid);
755 }
756 #endif
757
758 /**
759  * \brief Obtain general (static) information for PCM handle
760  * \param pcm PCM handle
761  * \param info Information container
762  * \return 0 on success otherwise a negative error code
763  */
764 int snd_pcm_info(snd_pcm_t *pcm, snd_pcm_info_t *info)
765 {
766         assert(pcm && info);
767         return pcm->ops->info(pcm->op_arg, info);
768 }
769
770 /** \brief Retreive current PCM hardware configuration chosen with #snd_pcm_hw_params
771  * \param pcm PCM handle
772  * \param params Configuration space definition container
773  * \return 0 on success otherwise a negative error code
774  */
775 int snd_pcm_hw_params_current(snd_pcm_t *pcm, snd_pcm_hw_params_t *params)
776 {
777         unsigned int frame_bits;
778
779         assert(pcm && params);
780         if (!pcm->setup)
781                 return -EBADFD;
782         memset(params, 0, snd_pcm_hw_params_sizeof());
783         params->flags = pcm->hw_flags;
784         snd_mask_set(&params->masks[SND_PCM_HW_PARAM_ACCESS - SND_PCM_HW_PARAM_FIRST_MASK], pcm->access);
785         snd_mask_set(&params->masks[SND_PCM_HW_PARAM_FORMAT - SND_PCM_HW_PARAM_FIRST_MASK], pcm->format);
786         snd_mask_set(&params->masks[SND_PCM_HW_PARAM_SUBFORMAT - SND_PCM_HW_PARAM_FIRST_MASK], pcm->subformat);
787         frame_bits = snd_pcm_format_physical_width(pcm->format) * pcm->channels;
788         snd_interval_set_value(&params->intervals[SND_PCM_HW_PARAM_FRAME_BITS - SND_PCM_HW_PARAM_FIRST_INTERVAL], frame_bits);
789         snd_interval_set_value(&params->intervals[SND_PCM_HW_PARAM_CHANNELS - SND_PCM_HW_PARAM_FIRST_INTERVAL], pcm->channels);
790         snd_interval_set_value(&params->intervals[SND_PCM_HW_PARAM_RATE - SND_PCM_HW_PARAM_FIRST_INTERVAL], pcm->rate);
791         snd_interval_set_value(&params->intervals[SND_PCM_HW_PARAM_PERIOD_TIME - SND_PCM_HW_PARAM_FIRST_INTERVAL], pcm->period_time);
792         snd_interval_set_value(&params->intervals[SND_PCM_HW_PARAM_PERIOD_SIZE - SND_PCM_HW_PARAM_FIRST_INTERVAL], pcm->period_size);
793         snd_interval_copy(&params->intervals[SND_PCM_HW_PARAM_PERIODS - SND_PCM_HW_PARAM_FIRST_INTERVAL], &pcm->periods);
794         snd_interval_copy(&params->intervals[SND_PCM_HW_PARAM_BUFFER_TIME - SND_PCM_HW_PARAM_FIRST_INTERVAL], &pcm->buffer_time);
795         snd_interval_set_value(&params->intervals[SND_PCM_HW_PARAM_BUFFER_SIZE - SND_PCM_HW_PARAM_FIRST_INTERVAL], pcm->buffer_size);
796         snd_interval_set_value(&params->intervals[SND_PCM_HW_PARAM_BUFFER_BYTES - SND_PCM_HW_PARAM_FIRST_INTERVAL], (pcm->buffer_size * frame_bits) / 8);
797         params->info = pcm->info;
798         params->msbits = pcm->msbits;
799         params->rate_num = pcm->rate_num;
800         params->rate_den = pcm->rate_den;
801         params->fifo_size = pcm->fifo_size;
802         return 0;
803
804
805 /** \brief Install one PCM hardware configuration chosen from a configuration space and #snd_pcm_prepare it
806  * \param pcm PCM handle
807  * \param params Configuration space definition container
808  * \return 0 on success otherwise a negative error code
809  *
810  * The configuration is chosen fixing single parameters in this order:
811  * first access, first format, first subformat, min channels, min rate, 
812  * min period time, max buffer size, min tick time. If no mutually
813  * compatible set of parameters can be chosen, a negative error code
814  * will be returned.
815  *
816  * After this call, #snd_pcm_prepare() is called automatically and
817  * the stream is brought to \c #SND_PCM_STATE_PREPARED state.
818  *
819  * The hardware parameters cannot be changed when the stream is
820  * running (active). The software parameters can be changed
821  * at any time.
822  *
823  * The configuration space will be updated to reflect the chosen
824  * parameters.
825  */
826 int snd_pcm_hw_params(snd_pcm_t *pcm, snd_pcm_hw_params_t *params)
827 {
828         int err;
829         assert(pcm && params);
830         err = _snd_pcm_hw_params(pcm, params);
831         if (err < 0)
832                 return err;
833         err = snd_pcm_prepare(pcm);
834         return err;
835 }
836
837 /** \brief Remove PCM hardware configuration and free associated resources
838  * \param pcm PCM handle
839  * \return 0 on success otherwise a negative error code
840  */
841 int snd_pcm_hw_free(snd_pcm_t *pcm)
842 {
843         int err;
844         if (! pcm->setup)
845                 return 0;
846         if (pcm->mmap_channels) {
847                 err = snd_pcm_munmap(pcm);
848                 if (err < 0)
849                         return err;
850         }
851         // assert(snd_pcm_state(pcm) == SND_PCM_STATE_SETUP ||
852         //        snd_pcm_state(pcm) == SND_PCM_STATE_PREPARED);
853         err = pcm->ops->hw_free(pcm->op_arg);
854         pcm->setup = 0;
855         if (err < 0)
856                 return err;
857         return 0;
858 }
859
860 /** \brief Install PCM software configuration defined by params
861  * \param pcm PCM handle
862  * \param params Configuration container
863  * \return 0 on success otherwise a negative error code
864  *
865  * The software parameters can be changed at any time.
866  * The hardware parameters cannot be changed when the stream is
867  * running (active).
868  */
869 int snd_pcm_sw_params(snd_pcm_t *pcm, snd_pcm_sw_params_t *params)
870 {
871         int err;
872         /* the hw_params must be set at first!!! */
873         if (CHECK_SANITY(! pcm->setup)) {
874                 SNDMSG("PCM not set up");
875                 return -EIO;
876         }
877         if (! params->avail_min) {
878                 SNDMSG("params->avail_min is 0");
879                 return -EINVAL;
880         }
881 #if 0
882         /* disable the check below - it looks too restrictive
883          * (start_threshold is basically independent from avail_min)
884          */
885         if (params->start_threshold <= pcm->buffer_size &&
886             params->start_threshold > (pcm->buffer_size / params->avail_min) * params->avail_min) {
887                 SNDMSG("params->avail_min problem for start_threshold");
888                 return -EINVAL;
889         }
890 #endif
891         err = pcm->ops->sw_params(pcm->op_arg, params);
892         if (err < 0)
893                 return err;
894         pcm->tstamp_mode = params->tstamp_mode;
895         pcm->period_step = params->period_step;
896         pcm->avail_min = params->avail_min;
897         pcm->period_event = params->period_event;
898         pcm->start_threshold = params->start_threshold;
899         pcm->stop_threshold = params->stop_threshold;
900         pcm->silence_threshold = params->silence_threshold;
901         pcm->silence_size = params->silence_size;
902         pcm->boundary = params->boundary;
903         return 0;
904 }
905
906 /**
907  * \brief Obtain status (runtime) information for PCM handle
908  * \param pcm PCM handle
909  * \param status Status container
910  * \return 0 on success otherwise a negative error code
911  */
912 int snd_pcm_status(snd_pcm_t *pcm, snd_pcm_status_t *status)
913 {
914         assert(pcm && status);
915         return pcm->fast_ops->status(pcm->fast_op_arg, status);
916 }
917
918 /**
919  * \brief Return PCM state
920  * \param pcm PCM handle
921  * \return PCM state #snd_pcm_state_t of given PCM handle
922  *
923  * This is a faster way to obtain only the PCM state without calling
924  * \link ::snd_pcm_status() \endlink.
925  */
926 snd_pcm_state_t snd_pcm_state(snd_pcm_t *pcm)
927 {
928         assert(pcm);
929         return pcm->fast_ops->state(pcm->fast_op_arg);
930 }
931
932 /**
933  * \brief (DEPRECATED) Synchronize stream position with hardware
934  * \param pcm PCM handle
935  * \return 0 on success otherwise a negative error code
936  *
937  * Note this function does not update the actual r/w pointer
938  * for applications. The function #snd_pcm_avail_update()
939  * have to be called before any mmap begin+commit operation.
940  */
941 int snd_pcm_hwsync(snd_pcm_t *pcm)
942 {
943         assert(pcm);
944         if (CHECK_SANITY(! pcm->setup)) {
945                 SNDMSG("PCM not set up");
946                 return -EIO;
947         }
948         return pcm->fast_ops->hwsync(pcm->fast_op_arg);
949 }
950 #ifndef DOC_HIDDEN
951 link_warning(snd_pcm_hwsync, "Warning: snd_pcm_hwsync() is deprecated, consider to use snd_pcm_avail()");
952 #endif
953
954 /**
955  * \brief Obtain delay for a running PCM handle
956  * \param pcm PCM handle
957  * \param delayp Returned delay in frames
958  * \return 0 on success otherwise a negative error code
959  *
960  * For playback the delay is defined as the time that a frame that is written
961  * to the PCM stream shortly after this call will take to be actually
962  * audible. It is as such the overall latency from the write call to the final
963  * DAC.
964  *
965  * For capture the delay is defined as the time that a frame that was
966  * digitized by the audio device takes until it can be read from the PCM
967  * stream shortly after this call returns. It is as such the overall latency
968  * from the initial ADC to the read call.
969  *
970  * Please note that hence in case of a playback underrun this value will not
971  * necessarily got down to 0.
972  *
973  * If the application is interested in the fill level of the playback buffer
974  * of the device, it should use #snd_pcm_avail*() functions. The
975  * value returned by that call is not directly related to the delay, since the
976  * latter might include some additional, fixed latencies the former does not.
977  *
978  * Note this function does not update the actual r/w pointer
979  * for applications. The function #snd_pcm_avail_update()
980  * have to be called before any begin+commit operation.
981  */
982 int snd_pcm_delay(snd_pcm_t *pcm, snd_pcm_sframes_t *delayp)
983 {
984         assert(pcm);
985         if (CHECK_SANITY(! pcm->setup)) {
986                 SNDMSG("PCM not set up");
987                 return -EIO;
988         }
989         return pcm->fast_ops->delay(pcm->fast_op_arg, delayp);
990 }
991
992 /**
993  * \brief Resume from suspend, no samples are lost
994  * \param pcm PCM handle
995  * \return 0 on success otherwise a negative error code
996  * \retval -EAGAIN resume can't be proceed immediately (audio hardware is probably still suspended)
997  * \retval -ENOSYS hardware doesn't support this feature
998  *
999  * This function can be used when the stream is in the suspend state
1000  * to do the fine resume from this state. Not all hardware supports
1001  * this feature, when an -ENOSYS error is returned, use the \link ::snd_pcm_prepare() \endlink
1002  * function to recovery.
1003  */
1004 int snd_pcm_resume(snd_pcm_t *pcm)
1005 {
1006         assert(pcm);
1007         if (CHECK_SANITY(! pcm->setup)) {
1008                 SNDMSG("PCM not set up");
1009                 return -EIO;
1010         }
1011         return pcm->fast_ops->resume(pcm->fast_op_arg);
1012 }
1013
1014 /**
1015  * \brief Obtain last position update hi-res timestamp
1016  * \param pcm PCM handle
1017  * \param avail Number of available frames when timestamp was grabbed
1018  * \param tstamp Hi-res timestamp
1019  * \return 0 on success otherwise a negative error code
1020  *
1021  * Note this function does not update the actual r/w pointer
1022  * for applications.
1023  */
1024 int snd_pcm_htimestamp(snd_pcm_t *pcm, snd_pcm_uframes_t *avail, snd_htimestamp_t *tstamp)
1025 {
1026         assert(pcm);
1027         if (CHECK_SANITY(! pcm->setup)) {
1028                 SNDMSG("PCM not set up");
1029                 return -EIO;
1030         }
1031         return pcm->fast_ops->htimestamp(pcm->fast_op_arg, avail, tstamp);
1032 }
1033
1034 /**
1035  * \brief Prepare PCM for use
1036  * \param pcm PCM handle
1037  * \return 0 on success otherwise a negative error code
1038  */
1039 int snd_pcm_prepare(snd_pcm_t *pcm)
1040 {
1041         assert(pcm);
1042         if (CHECK_SANITY(! pcm->setup)) {
1043                 SNDMSG("PCM not set up");
1044                 return -EIO;
1045         }
1046         return pcm->fast_ops->prepare(pcm->fast_op_arg);
1047 }
1048
1049 /**
1050  * \brief Reset PCM position
1051  * \param pcm PCM handle
1052  * \return 0 on success otherwise a negative error code
1053  *
1054  * Reduce PCM delay to 0.
1055  */
1056 int snd_pcm_reset(snd_pcm_t *pcm)
1057 {
1058         assert(pcm);
1059         if (CHECK_SANITY(! pcm->setup)) {
1060                 SNDMSG("PCM not set up");
1061                 return -EIO;
1062         }
1063         return pcm->fast_ops->reset(pcm->fast_op_arg);
1064 }
1065
1066 /**
1067  * \brief Start a PCM
1068  * \param pcm PCM handle
1069  * \return 0 on success otherwise a negative error code
1070  */
1071 int snd_pcm_start(snd_pcm_t *pcm)
1072 {
1073         assert(pcm);
1074         if (CHECK_SANITY(! pcm->setup)) {
1075                 SNDMSG("PCM not set up");
1076                 return -EIO;
1077         }
1078         return pcm->fast_ops->start(pcm->fast_op_arg);
1079 }
1080
1081 /**
1082  * \brief Stop a PCM dropping pending frames
1083  * \param pcm PCM handle
1084  * \return 0 on success otherwise a negative error code
1085  *
1086  * This function stops the PCM <i>immediately</i>.
1087  * The pending samples on the buffer are ignored.
1088  *
1089  * For processing all pending samples, use \link ::snd_pcm_drain() \endlink
1090  * instead.
1091  */
1092 int snd_pcm_drop(snd_pcm_t *pcm)
1093 {
1094         assert(pcm);
1095         if (CHECK_SANITY(! pcm->setup)) {
1096                 SNDMSG("PCM not set up");
1097                 return -EIO;
1098         }
1099         return pcm->fast_ops->drop(pcm->fast_op_arg);
1100 }
1101
1102 /**
1103  * \brief Stop a PCM preserving pending frames
1104  * \param pcm PCM handle
1105  * \return 0 on success otherwise a negative error code
1106  * \retval -ESTRPIPE a suspend event occurred
1107  *
1108  * For playback wait for all pending frames to be played and then stop
1109  * the PCM.
1110  * For capture stop PCM permitting to retrieve residual frames.
1111  *
1112  * For stopping the PCM stream immediately, use \link ::snd_pcm_drop() \endlink
1113  * instead.
1114  */
1115 int snd_pcm_drain(snd_pcm_t *pcm)
1116 {
1117         assert(pcm);
1118         if (CHECK_SANITY(! pcm->setup)) {
1119                 SNDMSG("PCM not set up");
1120                 return -EIO;
1121         }
1122         return pcm->fast_ops->drain(pcm->fast_op_arg);
1123 }
1124
1125 /**
1126  * \brief Pause/resume PCM
1127  * \param pcm PCM handle
1128  * \param enable 0 = resume, 1 = pause
1129  * \return 0 on success otherwise a negative error code
1130  *
1131  * Note that this function works only on the hardware which supports
1132  * pause feature.  You can check it via \link ::snd_pcm_hw_params_can_pause() \endlink
1133  * function.
1134  */
1135 int snd_pcm_pause(snd_pcm_t *pcm, int enable)
1136 {
1137         assert(pcm);
1138         if (CHECK_SANITY(! pcm->setup)) {
1139                 SNDMSG("PCM not set up");
1140                 return -EIO;
1141         }
1142         return pcm->fast_ops->pause(pcm->fast_op_arg, enable);
1143 }
1144
1145 /**
1146  * \brief Get safe count of frames which can be rewinded
1147  * \param pcm PCM handle
1148  * \return a positive number of frames or negative error code
1149  *
1150  * Note: The snd_pcm_rewind() can accept bigger value than returned
1151  * by this function. But it is not guaranteed that output stream
1152  * will be consistent with bigger value.
1153  */
1154 snd_pcm_sframes_t snd_pcm_rewindable(snd_pcm_t *pcm)
1155 {
1156         assert(pcm);
1157         if (CHECK_SANITY(! pcm->setup)) {
1158                 SNDMSG("PCM not set up");
1159                 return -EIO;
1160         }
1161         return pcm->fast_ops->rewindable(pcm->fast_op_arg);
1162 }
1163
1164 /**
1165  * \brief Move application frame position backward
1166  * \param pcm PCM handle
1167  * \param frames wanted displacement in frames
1168  * \return a positive number for actual displacement otherwise a
1169  * negative error code
1170  */
1171 snd_pcm_sframes_t snd_pcm_rewind(snd_pcm_t *pcm, snd_pcm_uframes_t frames)
1172 {
1173         assert(pcm);
1174         if (CHECK_SANITY(! pcm->setup)) {
1175                 SNDMSG("PCM not set up");
1176                 return -EIO;
1177         }
1178         if (frames == 0)
1179                 return 0;
1180         return pcm->fast_ops->rewind(pcm->fast_op_arg, frames);
1181 }
1182
1183 /**
1184  * \brief Get safe count of frames which can be forwarded
1185  * \param pcm PCM handle
1186  * \return a positive number of frames or negative error code
1187  *
1188  * Note: The snd_pcm_forward() can accept bigger value than returned
1189  * by this function. But it is not guaranteed that output stream
1190  * will be consistent with bigger value.
1191  */
1192 snd_pcm_sframes_t snd_pcm_forwardable(snd_pcm_t *pcm)
1193 {
1194         assert(pcm);
1195         if (CHECK_SANITY(! pcm->setup)) {
1196                 SNDMSG("PCM not set up");
1197                 return -EIO;
1198         }
1199         return pcm->fast_ops->forwardable(pcm->fast_op_arg);
1200 }
1201
1202 /**
1203  * \brief Move application frame position forward
1204  * \param pcm PCM handle
1205  * \param frames wanted skip in frames
1206  * \return a positive number for actual skip otherwise a negative error code
1207  * \retval 0 means no action
1208  */
1209 #ifndef DOXYGEN
1210 snd_pcm_sframes_t INTERNAL(snd_pcm_forward)(snd_pcm_t *pcm, snd_pcm_uframes_t frames)
1211 #else
1212 snd_pcm_sframes_t snd_pcm_forward(snd_pcm_t *pcm, snd_pcm_uframes_t frames)
1213 #endif
1214 {
1215         assert(pcm);
1216         if (CHECK_SANITY(! pcm->setup)) {
1217                 SNDMSG("PCM not set up");
1218                 return -EIO;
1219         }
1220         if (frames == 0)
1221                 return 0;
1222         return pcm->fast_ops->forward(pcm->fast_op_arg, frames);
1223 }
1224 use_default_symbol_version(__snd_pcm_forward, snd_pcm_forward, ALSA_0.9.0rc8);
1225
1226 /**
1227  * \brief Write interleaved frames to a PCM
1228  * \param pcm PCM handle
1229  * \param buffer frames containing buffer
1230  * \param size frames to be written
1231  * \return a positive number of frames actually written otherwise a
1232  * negative error code
1233  * \retval -EBADFD PCM is not in the right state (#SND_PCM_STATE_PREPARED or #SND_PCM_STATE_RUNNING)
1234  * \retval -EPIPE an underrun occurred
1235  * \retval -ESTRPIPE a suspend event occurred (stream is suspended and waiting for an application recovery)
1236  *
1237  * If the blocking behaviour is selected and it is running, then routine waits until
1238  * all requested frames are played or put to the playback ring buffer.
1239  * The returned number of frames can be less only if a signal or underrun occurred.
1240  *
1241  * If the non-blocking behaviour is selected, then routine doesn't wait at all.
1242  */ 
1243 snd_pcm_sframes_t snd_pcm_writei(snd_pcm_t *pcm, const void *buffer, snd_pcm_uframes_t size)
1244 {
1245         assert(pcm);
1246         assert(size == 0 || buffer);
1247         if (CHECK_SANITY(! pcm->setup)) {
1248                 SNDMSG("PCM not set up");
1249                 return -EIO;
1250         }
1251         if (pcm->access != SND_PCM_ACCESS_RW_INTERLEAVED) {
1252                 SNDMSG("invalid access type %s", snd_pcm_access_name(pcm->access));
1253                 return -EINVAL;
1254         }
1255         return _snd_pcm_writei(pcm, buffer, size);
1256 }
1257
1258 /**
1259  * \brief Write non interleaved frames to a PCM
1260  * \param pcm PCM handle
1261  * \param bufs frames containing buffers (one for each channel)
1262  * \param size frames to be written
1263  * \return a positive number of frames actually written otherwise a
1264  * negative error code
1265  * \retval -EBADFD PCM is not in the right state (#SND_PCM_STATE_PREPARED or #SND_PCM_STATE_RUNNING)
1266  * \retval -EPIPE an underrun occurred
1267  * \retval -ESTRPIPE a suspend event occurred (stream is suspended and waiting for an application recovery)
1268  *
1269  * If the blocking behaviour is selected and it is running, then routine waits until
1270  * all requested frames are played or put to the playback ring buffer.
1271  * The returned number of frames can be less only if a signal or underrun occurred.
1272  *
1273  * If the non-blocking behaviour is selected, then routine doesn't wait at all.
1274  */ 
1275 snd_pcm_sframes_t snd_pcm_writen(snd_pcm_t *pcm, void **bufs, snd_pcm_uframes_t size)
1276 {
1277         assert(pcm);
1278         assert(size == 0 || bufs);
1279         if (CHECK_SANITY(! pcm->setup)) {
1280                 SNDMSG("PCM not set up");
1281                 return -EIO;
1282         }
1283         if (pcm->access != SND_PCM_ACCESS_RW_NONINTERLEAVED) {
1284                 SNDMSG("invalid access type %s", snd_pcm_access_name(pcm->access));
1285                 return -EINVAL;
1286         }
1287         return _snd_pcm_writen(pcm, bufs, size);
1288 }
1289
1290 /**
1291  * \brief Read interleaved frames from a PCM
1292  * \param pcm PCM handle
1293  * \param buffer frames containing buffer
1294  * \param size frames to be read
1295  * \return a positive number of frames actually read otherwise a
1296  * negative error code
1297  * \retval -EBADFD PCM is not in the right state (#SND_PCM_STATE_PREPARED or #SND_PCM_STATE_RUNNING)
1298  * \retval -EPIPE an overrun occurred
1299  * \retval -ESTRPIPE a suspend event occurred (stream is suspended and waiting for an application recovery)
1300  *
1301  * If the blocking behaviour was selected and it is running, then routine waits until
1302  * all requested frames are filled. The returned number of frames can be less only
1303  * if a signal or underrun occurred.
1304  *
1305  * If the non-blocking behaviour is selected, then routine doesn't wait at all.
1306  */ 
1307 snd_pcm_sframes_t snd_pcm_readi(snd_pcm_t *pcm, void *buffer, snd_pcm_uframes_t size)
1308 {
1309         assert(pcm);
1310         assert(size == 0 || buffer);
1311         if (CHECK_SANITY(! pcm->setup)) {
1312                 SNDMSG("PCM not set up");
1313                 return -EIO;
1314         }
1315         if (pcm->access != SND_PCM_ACCESS_RW_INTERLEAVED) {
1316                 SNDMSG("invalid access type %s", snd_pcm_access_name(pcm->access));
1317                 return -EINVAL;
1318         }
1319         return _snd_pcm_readi(pcm, buffer, size);
1320 }
1321
1322 /**
1323  * \brief Read non interleaved frames to a PCM
1324  * \param pcm PCM handle
1325  * \param bufs frames containing buffers (one for each channel)
1326  * \param size frames to be read
1327  * \return a positive number of frames actually read otherwise a
1328  * negative error code
1329  * \retval -EBADFD PCM is not in the right state (#SND_PCM_STATE_PREPARED or #SND_PCM_STATE_RUNNING)
1330  * \retval -EPIPE an overrun occurred
1331  * \retval -ESTRPIPE a suspend event occurred (stream is suspended and waiting for an application recovery)
1332  *
1333  * If the blocking behaviour was selected and it is running, then routine waits until
1334  * all requested frames are filled. The returned number of frames can be less only
1335  * if a signal or underrun occurred.
1336  *
1337  * If the non-blocking behaviour is selected, then routine doesn't wait at all.
1338  */ 
1339 snd_pcm_sframes_t snd_pcm_readn(snd_pcm_t *pcm, void **bufs, snd_pcm_uframes_t size)
1340 {
1341         assert(pcm);
1342         assert(size == 0 || bufs);
1343         if (CHECK_SANITY(! pcm->setup)) {
1344                 SNDMSG("PCM not set up");
1345                 return -EIO;
1346         }
1347         if (pcm->access != SND_PCM_ACCESS_RW_NONINTERLEAVED) {
1348                 SNDMSG("invalid access type %s", snd_pcm_access_name(pcm->access));
1349                 return -EINVAL;
1350         }
1351         return _snd_pcm_readn(pcm, bufs, size);
1352 }
1353
1354 /**
1355  * \brief Link two PCMs
1356  * \param pcm1 first PCM handle
1357  * \param pcm2 first PCM handle
1358  * \return 0 on success otherwise a negative error code
1359  *
1360  * The two PCMs will start/stop/prepare in sync.
1361  */ 
1362 int snd_pcm_link(snd_pcm_t *pcm1, snd_pcm_t *pcm2)
1363 {
1364         assert(pcm1);
1365         assert(pcm2);
1366         if (pcm1->fast_ops->link)
1367                 return pcm1->fast_ops->link(pcm1, pcm2);
1368         return -ENOSYS;
1369 }
1370
1371 /**
1372  * \brief Remove a PCM from a linked group
1373  * \param pcm PCM handle
1374  * \return 0 on success otherwise a negative error code
1375  */
1376 int snd_pcm_unlink(snd_pcm_t *pcm)
1377 {
1378         assert(pcm);
1379         if (pcm->fast_ops->unlink)
1380                 return pcm->fast_ops->unlink(pcm);
1381         return -ENOSYS;
1382 }
1383
1384 /**
1385  * \brief get count of poll descriptors for PCM handle
1386  * \param pcm PCM handle
1387  * \return count of poll descriptors
1388  */
1389 int snd_pcm_poll_descriptors_count(snd_pcm_t *pcm)
1390 {
1391         assert(pcm);
1392         if (pcm->fast_ops->poll_descriptors_count)
1393                 return pcm->fast_ops->poll_descriptors_count(pcm->fast_op_arg);
1394         return pcm->poll_fd_count;
1395 }
1396
1397
1398 /**
1399  * \brief get poll descriptors
1400  * \param pcm PCM handle
1401  * \param pfds array of poll descriptors
1402  * \param space space in the poll descriptor array
1403  * \return count of filled descriptors
1404  *
1405  * This function fills the given poll descriptor structs for the specified
1406  * PCM handle.  The poll desctiptor array should have the size returned by
1407  * \link ::snd_pcm_poll_descriptors_count() \endlink function.
1408  *
1409  * The result is intended for direct use with the poll() syscall.
1410  *
1411  * For reading the returned events of poll descriptor after poll() system
1412  * call, use \link ::snd_pcm_poll_descriptors_revents() \endlink function.
1413  * The field values in pollfd structs may be bogus regarding the stream
1414  * direction from the application perspective (POLLIN might not imply read
1415  * direction and POLLOUT might not imply write), but
1416  * the \link ::snd_pcm_poll_descriptors_revents() \endlink function
1417  * does the right "demangling".
1418  *
1419  * You can use output from this function as arguments for the select()
1420  * syscall, too. Do not forget to translate POLLIN and POLLOUT events to
1421  * corresponding FD_SET arrays and demangle events using
1422  * \link ::snd_pcm_poll_descriptors_revents() \endlink .
1423  */
1424 int snd_pcm_poll_descriptors(snd_pcm_t *pcm, struct pollfd *pfds, unsigned int space)
1425 {
1426         assert(pcm && pfds);
1427         if (pcm->fast_ops->poll_descriptors)
1428                 return pcm->fast_ops->poll_descriptors(pcm->fast_op_arg, pfds, space);
1429         if (pcm->poll_fd < 0) {
1430                 SNDMSG("poll_fd < 0");
1431                 return -EIO;
1432         }
1433         if (space >= 1 && pfds) {
1434                 pfds->fd = pcm->poll_fd;
1435                 pfds->events = pcm->poll_events | POLLERR | POLLNVAL;
1436         } else {
1437                 return 0;
1438         }
1439         return 1;
1440 }
1441
1442 /**
1443  * \brief get returned events from poll descriptors
1444  * \param pcm PCM handle
1445  * \param pfds array of poll descriptors
1446  * \param nfds count of poll descriptors
1447  * \param revents pointer to the returned (single) event
1448  * \return zero if success, otherwise a negative error code
1449  *
1450  * This function does "demangling" of the revents mask returned from
1451  * the poll() syscall to correct semantics (POLLIN = read, POLLOUT = write).
1452  *
1453  * Note: The null event also exists. Even if poll() or select()
1454  * syscall returned that some events are waiting, this function might
1455  * return empty set of events. In this case, application should
1456  * do next event waiting using poll() or select().
1457  *
1458  * Note: Even if multiple poll descriptors are used (i.e. pfds > 1),
1459  * this function returns only a single event.
1460  */
1461 int snd_pcm_poll_descriptors_revents(snd_pcm_t *pcm, struct pollfd *pfds, unsigned int nfds, unsigned short *revents)
1462 {
1463         assert(pcm && pfds && revents);
1464         if (pcm->fast_ops->poll_revents)
1465                 return pcm->fast_ops->poll_revents(pcm->fast_op_arg, pfds, nfds, revents);
1466         if (nfds == 1) {
1467                 *revents = pfds->revents;
1468                 return 0;
1469         }
1470         return -EINVAL;
1471 }
1472
1473 #ifndef DOC_HIDDEN
1474 #define PCMTYPE(v) [SND_PCM_TYPE_##v] = #v
1475 #define STATE(v) [SND_PCM_STATE_##v] = #v
1476 #define STREAM(v) [SND_PCM_STREAM_##v] = #v
1477 #define READY(v) [SND_PCM_READY_##v] = #v
1478 #define XRUN(v) [SND_PCM_XRUN_##v] = #v
1479 #define SILENCE(v) [SND_PCM_SILENCE_##v] = #v
1480 #define TSTAMP(v) [SND_PCM_TSTAMP_##v] = #v
1481 #define ACCESS(v) [SND_PCM_ACCESS_##v] = #v
1482 #define START(v) [SND_PCM_START_##v] = #v
1483 #define HW_PARAM(v) [SND_PCM_HW_PARAM_##v] = #v
1484 #define SW_PARAM(v) [SND_PCM_SW_PARAM_##v] = #v
1485 #define FORMAT(v) [SND_PCM_FORMAT_##v] = #v
1486 #define SUBFORMAT(v) [SND_PCM_SUBFORMAT_##v] = #v 
1487
1488 #define FORMATD(v, d) [SND_PCM_FORMAT_##v] = d
1489 #define SUBFORMATD(v, d) [SND_PCM_SUBFORMAT_##v] = d 
1490
1491
1492 static const char *const snd_pcm_stream_names[] = {
1493         STREAM(PLAYBACK),
1494         STREAM(CAPTURE),
1495 };
1496
1497 static const char *const snd_pcm_state_names[] = {
1498         STATE(OPEN),
1499         STATE(SETUP),
1500         STATE(PREPARED),
1501         STATE(RUNNING),
1502         STATE(XRUN),
1503         STATE(DRAINING),
1504         STATE(PAUSED),
1505         STATE(SUSPENDED),
1506         STATE(DISCONNECTED),
1507 };
1508
1509 static const char *const snd_pcm_access_names[] = {
1510         ACCESS(MMAP_INTERLEAVED), 
1511         ACCESS(MMAP_NONINTERLEAVED),
1512         ACCESS(MMAP_COMPLEX),
1513         ACCESS(RW_INTERLEAVED),
1514         ACCESS(RW_NONINTERLEAVED),
1515 };
1516
1517 static const char *const snd_pcm_format_names[] = {
1518         FORMAT(S8),
1519         FORMAT(U8),
1520         FORMAT(S16_LE),
1521         FORMAT(S16_BE),
1522         FORMAT(U16_LE),
1523         FORMAT(U16_BE),
1524         FORMAT(S24_LE),
1525         FORMAT(S24_BE),
1526         FORMAT(U24_LE),
1527         FORMAT(U24_BE),
1528         FORMAT(S32_LE),
1529         FORMAT(S32_BE),
1530         FORMAT(U32_LE),
1531         FORMAT(U32_BE),
1532         FORMAT(FLOAT_LE),
1533         FORMAT(FLOAT_BE),
1534         FORMAT(FLOAT64_LE),
1535         FORMAT(FLOAT64_BE),
1536         FORMAT(IEC958_SUBFRAME_LE),
1537         FORMAT(IEC958_SUBFRAME_BE),
1538         FORMAT(MU_LAW),
1539         FORMAT(A_LAW),
1540         FORMAT(IMA_ADPCM),
1541         FORMAT(MPEG),
1542         FORMAT(GSM),
1543         FORMAT(SPECIAL),
1544         FORMAT(S24_3LE),
1545         FORMAT(S24_3BE),
1546         FORMAT(U24_3LE),
1547         FORMAT(U24_3BE),
1548         FORMAT(S20_3LE),
1549         FORMAT(S20_3BE),
1550         FORMAT(U20_3LE),
1551         FORMAT(U20_3BE),
1552         FORMAT(S18_3LE),
1553         FORMAT(S18_3BE),
1554         FORMAT(U18_3LE),
1555         FORMAT(U18_3BE),
1556 };
1557
1558 static const char *const snd_pcm_format_aliases[SND_PCM_FORMAT_LAST+1] = {
1559         FORMAT(S16),
1560         FORMAT(U16),
1561         FORMAT(S24),
1562         FORMAT(U24),
1563         FORMAT(S32),
1564         FORMAT(U32),
1565         FORMAT(FLOAT),
1566         FORMAT(FLOAT64),
1567         FORMAT(IEC958_SUBFRAME),
1568 };
1569
1570 static const char *const snd_pcm_format_descriptions[] = {
1571         FORMATD(S8, "Signed 8 bit"), 
1572         FORMATD(U8, "Unsigned 8 bit"),
1573         FORMATD(S16_LE, "Signed 16 bit Little Endian"),
1574         FORMATD(S16_BE, "Signed 16 bit Big Endian"),
1575         FORMATD(U16_LE, "Unsigned 16 bit Little Endian"),
1576         FORMATD(U16_BE, "Unsigned 16 bit Big Endian"),
1577         FORMATD(S24_LE, "Signed 24 bit Little Endian"),
1578         FORMATD(S24_BE, "Signed 24 bit Big Endian"),
1579         FORMATD(U24_LE, "Unsigned 24 bit Little Endian"),
1580         FORMATD(U24_BE, "Unsigned 24 bit Big Endian"),
1581         FORMATD(S32_LE, "Signed 32 bit Little Endian"),
1582         FORMATD(S32_BE, "Signed 32 bit Big Endian"),
1583         FORMATD(U32_LE, "Unsigned 32 bit Little Endian"),
1584         FORMATD(U32_BE, "Unsigned 32 bit Big Endian"),
1585         FORMATD(FLOAT_LE, "Float 32 bit Little Endian"),
1586         FORMATD(FLOAT_BE, "Float 32 bit Big Endian"),
1587         FORMATD(FLOAT64_LE, "Float 64 bit Little Endian"),
1588         FORMATD(FLOAT64_BE, "Float 64 bit Big Endian"),
1589         FORMATD(IEC958_SUBFRAME_LE, "IEC-958 Little Endian"),
1590         FORMATD(IEC958_SUBFRAME_BE, "IEC-958 Big Endian"),
1591         FORMATD(MU_LAW, "Mu-Law"),
1592         FORMATD(A_LAW, "A-Law"),
1593         FORMATD(IMA_ADPCM, "Ima-ADPCM"),
1594         FORMATD(MPEG, "MPEG"),
1595         FORMATD(GSM, "GSM"),
1596         FORMATD(SPECIAL, "Special"),
1597         FORMATD(S24_3LE, "Signed 24 bit Little Endian in 3bytes"),
1598         FORMATD(S24_3BE, "Signed 24 bit Big Endian in 3bytes"),
1599         FORMATD(U24_3LE, "Unsigned 24 bit Little Endian in 3bytes"),
1600         FORMATD(U24_3BE, "Unsigned 24 bit Big Endian in 3bytes"),
1601         FORMATD(S20_3LE, "Signed 20 bit Little Endian in 3bytes"),
1602         FORMATD(S20_3BE, "Signed 20 bit Big Endian in 3bytes"),
1603         FORMATD(U20_3LE, "Unsigned 20 bit Little Endian in 3bytes"),
1604         FORMATD(U20_3BE, "Unsigned 20 bit Big Endian in 3bytes"),
1605         FORMATD(S18_3LE, "Signed 18 bit Little Endian in 3bytes"),
1606         FORMATD(S18_3BE, "Signed 18 bit Big Endian in 3bytes"),
1607         FORMATD(U18_3LE, "Unsigned 18 bit Little Endian in 3bytes"),
1608         FORMATD(U18_3BE, "Unsigned 18 bit Big Endian in 3bytes"),
1609 };
1610
1611 static const char *const snd_pcm_type_names[] = {
1612         PCMTYPE(HW), 
1613         PCMTYPE(HOOKS), 
1614         PCMTYPE(MULTI), 
1615         PCMTYPE(FILE), 
1616         PCMTYPE(NULL), 
1617         PCMTYPE(SHM), 
1618         PCMTYPE(INET), 
1619         PCMTYPE(COPY), 
1620         PCMTYPE(LINEAR), 
1621         PCMTYPE(ALAW), 
1622         PCMTYPE(MULAW), 
1623         PCMTYPE(ADPCM), 
1624         PCMTYPE(RATE), 
1625         PCMTYPE(ROUTE), 
1626         PCMTYPE(PLUG), 
1627         PCMTYPE(SHARE), 
1628         PCMTYPE(METER), 
1629         PCMTYPE(MIX), 
1630         PCMTYPE(DROUTE), 
1631         PCMTYPE(LBSERVER), 
1632         PCMTYPE(LINEAR_FLOAT), 
1633         PCMTYPE(LADSPA), 
1634         PCMTYPE(DMIX), 
1635         PCMTYPE(JACK),
1636         PCMTYPE(DSNOOP),
1637         PCMTYPE(IEC958),
1638         PCMTYPE(SOFTVOL),
1639         PCMTYPE(IOPLUG),
1640         PCMTYPE(EXTPLUG),
1641         PCMTYPE(MMAP_EMUL),
1642 };
1643
1644 static const char *const snd_pcm_subformat_names[] = {
1645         SUBFORMAT(STD), 
1646 };
1647
1648 static const char *const snd_pcm_subformat_descriptions[] = {
1649         SUBFORMATD(STD, "Standard"), 
1650 };
1651
1652 static const char *const snd_pcm_start_mode_names[] = {
1653         START(EXPLICIT),
1654         START(DATA),
1655 };
1656
1657 static const char *const snd_pcm_xrun_mode_names[] = {
1658         XRUN(NONE),
1659         XRUN(STOP),
1660 };
1661
1662 static const char *const snd_pcm_tstamp_mode_names[] = {
1663         TSTAMP(NONE),
1664         TSTAMP(ENABLE),
1665 };
1666 #endif
1667
1668 /**
1669  * \brief get name of PCM stream type
1670  * \param stream PCM stream type
1671  * \return ascii name of PCM stream type
1672  */
1673 const char *snd_pcm_stream_name(snd_pcm_stream_t stream)
1674 {
1675         if (stream > SND_PCM_STREAM_LAST)
1676                 return NULL;
1677         return snd_pcm_stream_names[stream];
1678 }
1679
1680 /**
1681  * \brief get name of PCM access type
1682  * \param acc PCM access type
1683  * \return ascii name of PCM access type
1684  */
1685 const char *snd_pcm_access_name(snd_pcm_access_t acc)
1686 {
1687         if (acc > SND_PCM_ACCESS_LAST)
1688                 return NULL;
1689         return snd_pcm_access_names[acc];
1690 }
1691
1692 /**
1693  * \brief get name of PCM sample format
1694  * \param format PCM sample format
1695  * \return ascii name of PCM sample format
1696  */
1697 const char *snd_pcm_format_name(snd_pcm_format_t format)
1698 {
1699         if (format > SND_PCM_FORMAT_LAST)
1700                 return NULL;
1701         return snd_pcm_format_names[format];
1702 }
1703
1704 /**
1705  * \brief get description of PCM sample format
1706  * \param format PCM sample format
1707  * \return ascii description of PCM sample format
1708  */
1709 const char *snd_pcm_format_description(snd_pcm_format_t format)
1710 {
1711         if (format > SND_PCM_FORMAT_LAST)
1712                 return NULL;
1713         return snd_pcm_format_descriptions[format];
1714 }
1715
1716 /**
1717  * \brief get PCM sample format from name
1718  * \param name PCM sample format name (case insensitive)
1719  * \return PCM sample format
1720  */
1721 snd_pcm_format_t snd_pcm_format_value(const char* name)
1722 {
1723         snd_pcm_format_t format;
1724         for (format = 0; format <= SND_PCM_FORMAT_LAST; format++) {
1725                 if (snd_pcm_format_names[format] &&
1726                     strcasecmp(name, snd_pcm_format_names[format]) == 0) {
1727                         return format;
1728                 }
1729                 if (snd_pcm_format_aliases[format] &&
1730                     strcasecmp(name, snd_pcm_format_aliases[format]) == 0) {
1731                         return format;
1732                 }
1733         }
1734         for (format = 0; format <= SND_PCM_FORMAT_LAST; format++) {
1735                 if (snd_pcm_format_descriptions[format] &&
1736                     strcasecmp(name, snd_pcm_format_descriptions[format]) == 0) {
1737                         return format;
1738                 }
1739         }
1740         return SND_PCM_FORMAT_UNKNOWN;
1741 }
1742
1743 /**
1744  * \brief get name of PCM sample subformat
1745  * \param subformat PCM sample subformat
1746  * \return ascii name of PCM sample subformat
1747  */
1748 const char *snd_pcm_subformat_name(snd_pcm_subformat_t subformat)
1749 {
1750         if (subformat > SND_PCM_SUBFORMAT_LAST)
1751                 return NULL;
1752         return snd_pcm_subformat_names[subformat];
1753 }
1754
1755 /**
1756  * \brief get description of PCM sample subformat
1757  * \param subformat PCM sample subformat
1758  * \return ascii description of PCM sample subformat
1759  */
1760 const char *snd_pcm_subformat_description(snd_pcm_subformat_t subformat)
1761 {
1762         if (subformat > SND_PCM_SUBFORMAT_LAST)
1763                 return NULL;
1764         return snd_pcm_subformat_descriptions[subformat];
1765 }
1766
1767 /**
1768  * \brief (DEPRECATED) get name of PCM start mode setting
1769  * \param mode PCM start mode
1770  * \return ascii name of PCM start mode setting
1771  */
1772 const char *snd_pcm_start_mode_name(snd_pcm_start_t mode)
1773 {
1774         if (mode > SND_PCM_START_LAST)
1775                 return NULL;
1776         return snd_pcm_start_mode_names[mode];
1777 }
1778
1779 #ifndef DOC_HIDDEN
1780 link_warning(snd_pcm_start_mode_name, "Warning: start_mode is deprecated, consider to use start_threshold");
1781 #endif
1782
1783 /**
1784  * \brief (DEPRECATED) get name of PCM xrun mode setting
1785  * \param mode PCM xrun mode
1786  * \return ascii name of PCM xrun mode setting
1787  */
1788 const char *snd_pcm_xrun_mode_name(snd_pcm_xrun_t mode)
1789 {
1790         if (mode > SND_PCM_XRUN_LAST)
1791                 return NULL;
1792         return snd_pcm_xrun_mode_names[mode];
1793 }
1794
1795 #ifndef DOC_HIDDEN
1796 link_warning(snd_pcm_xrun_mode_name, "Warning: xrun_mode is deprecated, consider to use stop_threshold");
1797 #endif
1798
1799 /**
1800  * \brief get name of PCM tstamp mode setting
1801  * \param mode PCM tstamp mode
1802  * \return ascii name of PCM tstamp mode setting
1803  */
1804 const char *snd_pcm_tstamp_mode_name(snd_pcm_tstamp_t mode)
1805 {
1806         if (mode > SND_PCM_TSTAMP_LAST)
1807                 return NULL;
1808         return snd_pcm_tstamp_mode_names[mode];
1809 }
1810
1811 /**
1812  * \brief get name of PCM state
1813  * \param state PCM state
1814  * \return ascii name of PCM state
1815  */
1816 const char *snd_pcm_state_name(snd_pcm_state_t state)
1817 {
1818         if (state > SND_PCM_STATE_LAST)
1819                 return NULL;
1820         return snd_pcm_state_names[state];
1821 }
1822
1823 /**
1824  * \brief get name of PCM type
1825  * \param type PCM type
1826  * \return ascii name of PCM type
1827  */
1828 #ifndef DOXYGEN
1829 const char *INTERNAL(snd_pcm_type_name)(snd_pcm_type_t type)
1830 #else
1831 const char *snd_pcm_type_name(snd_pcm_type_t type)
1832 #endif
1833 {
1834         if (type > SND_PCM_TYPE_LAST)
1835                 return NULL;
1836         return snd_pcm_type_names[type];
1837 }
1838 use_default_symbol_version(__snd_pcm_type_name, snd_pcm_type_name, ALSA_0.9.0);
1839
1840 /**
1841  * \brief Dump current hardware setup for PCM
1842  * \param pcm PCM handle
1843  * \param out Output handle
1844  * \return 0 on success otherwise a negative error code
1845  */
1846 int snd_pcm_dump_hw_setup(snd_pcm_t *pcm, snd_output_t *out)
1847 {
1848         assert(pcm);
1849         assert(out);
1850         if (CHECK_SANITY(! pcm->setup)) {
1851                 SNDMSG("PCM not set up");
1852                 return -EIO;
1853         }
1854         snd_output_printf(out, "  stream       : %s\n", snd_pcm_stream_name(pcm->stream));
1855         snd_output_printf(out, "  access       : %s\n", snd_pcm_access_name(pcm->access));
1856         snd_output_printf(out, "  format       : %s\n", snd_pcm_format_name(pcm->format));
1857         snd_output_printf(out, "  subformat    : %s\n", snd_pcm_subformat_name(pcm->subformat));
1858         snd_output_printf(out, "  channels     : %u\n", pcm->channels);
1859         snd_output_printf(out, "  rate         : %u\n", pcm->rate);
1860         snd_output_printf(out, "  exact rate   : %g (%u/%u)\n",
1861                           (pcm->rate_den ? ((double) pcm->rate_num / pcm->rate_den) : 0.0),
1862                           pcm->rate_num, pcm->rate_den);
1863         snd_output_printf(out, "  msbits       : %u\n", pcm->msbits);
1864         snd_output_printf(out, "  buffer_size  : %lu\n", pcm->buffer_size);
1865         snd_output_printf(out, "  period_size  : %lu\n", pcm->period_size);
1866         snd_output_printf(out, "  period_time  : %u\n", pcm->period_time);
1867         return 0;
1868 }
1869
1870 /**
1871  * \brief Dump current software setup for PCM
1872  * \param pcm PCM handle
1873  * \param out Output handle
1874  * \return 0 on success otherwise a negative error code
1875  */
1876 int snd_pcm_dump_sw_setup(snd_pcm_t *pcm, snd_output_t *out)
1877 {
1878         assert(pcm);
1879         assert(out);
1880         if (CHECK_SANITY(! pcm->setup)) {
1881                 SNDMSG("PCM not set up");
1882                 return -EIO;
1883         }
1884         snd_output_printf(out, "  tstamp_mode  : %s\n", snd_pcm_tstamp_mode_name(pcm->tstamp_mode));
1885         snd_output_printf(out, "  period_step  : %d\n", pcm->period_step);
1886         snd_output_printf(out, "  avail_min    : %ld\n", pcm->avail_min);
1887         snd_output_printf(out, "  period_event : %i\n", pcm->period_event);
1888         snd_output_printf(out, "  start_threshold  : %ld\n", pcm->start_threshold);
1889         snd_output_printf(out, "  stop_threshold   : %ld\n", pcm->stop_threshold);
1890         snd_output_printf(out, "  silence_threshold: %ld\n", pcm->silence_threshold);
1891         snd_output_printf(out, "  silence_size : %ld\n", pcm->silence_size);
1892         snd_output_printf(out, "  boundary     : %ld\n", pcm->boundary);
1893         return 0;
1894 }
1895
1896 /**
1897  * \brief Dump current setup (hardware and software) for PCM
1898  * \param pcm PCM handle
1899  * \param out Output handle
1900  * \return 0 on success otherwise a negative error code
1901  */
1902 int snd_pcm_dump_setup(snd_pcm_t *pcm, snd_output_t *out)
1903 {
1904         snd_pcm_dump_hw_setup(pcm, out);
1905         snd_pcm_dump_sw_setup(pcm, out);
1906         return 0;
1907 }
1908
1909 /**
1910  * \brief Dump status
1911  * \param status Status container
1912  * \param out Output handle
1913  * \return 0 on success otherwise a negative error code
1914  */
1915 int snd_pcm_status_dump(snd_pcm_status_t *status, snd_output_t *out)
1916 {
1917         assert(status);
1918         snd_output_printf(out, "  state       : %s\n", snd_pcm_state_name((snd_pcm_state_t) status->state));
1919         snd_output_printf(out, "  trigger_time: %ld.%06ld\n",
1920                 status->trigger_tstamp.tv_sec, status->trigger_tstamp.tv_nsec);
1921         snd_output_printf(out, "  tstamp      : %ld.%06ld\n",
1922                 status->tstamp.tv_sec, status->tstamp.tv_nsec);
1923         snd_output_printf(out, "  delay       : %ld\n", (long)status->delay);
1924         snd_output_printf(out, "  avail       : %ld\n", (long)status->avail);
1925         snd_output_printf(out, "  avail_max   : %ld\n", (long)status->avail_max);
1926         return 0;
1927 }
1928
1929 /**
1930  * \brief Dump PCM info
1931  * \param pcm PCM handle
1932  * \param out Output handle
1933  * \return 0 on success otherwise a negative error code
1934  */
1935 int snd_pcm_dump(snd_pcm_t *pcm, snd_output_t *out)
1936 {
1937         assert(pcm);
1938         assert(out);
1939         pcm->ops->dump(pcm->op_arg, out);
1940         return 0;
1941 }
1942
1943 /**
1944  * \brief Convert bytes in frames for a PCM
1945  * \param pcm PCM handle
1946  * \param bytes quantity in bytes
1947  * \return quantity expressed in frames
1948  */
1949 snd_pcm_sframes_t snd_pcm_bytes_to_frames(snd_pcm_t *pcm, ssize_t bytes)
1950 {
1951         assert(pcm);
1952         if (CHECK_SANITY(! pcm->setup)) {
1953                 SNDMSG("PCM not set up");
1954                 return -EIO;
1955         }
1956         return bytes * 8 / pcm->frame_bits;
1957 }
1958
1959 /**
1960  * \brief Convert frames in bytes for a PCM
1961  * \param pcm PCM handle
1962  * \param frames quantity in frames
1963  * \return quantity expressed in bytes
1964  */
1965 ssize_t snd_pcm_frames_to_bytes(snd_pcm_t *pcm, snd_pcm_sframes_t frames)
1966 {
1967         assert(pcm);
1968         if (CHECK_SANITY(! pcm->setup)) {
1969                 SNDMSG("PCM not set up");
1970                 return -EIO;
1971         }
1972         return frames * pcm->frame_bits / 8;
1973 }
1974
1975 /**
1976  * \brief Convert bytes in samples for a PCM
1977  * \param pcm PCM handle
1978  * \param bytes quantity in bytes
1979  * \return quantity expressed in samples
1980  */
1981 long snd_pcm_bytes_to_samples(snd_pcm_t *pcm, ssize_t bytes)
1982 {
1983         assert(pcm);
1984         if (CHECK_SANITY(! pcm->setup)) {
1985                 SNDMSG("PCM not set up");
1986                 return -EIO;
1987         }
1988         return bytes * 8 / pcm->sample_bits;
1989 }
1990
1991 /**
1992  * \brief Convert samples in bytes for a PCM
1993  * \param pcm PCM handle
1994  * \param samples quantity in samples
1995  * \return quantity expressed in bytes
1996  */
1997 ssize_t snd_pcm_samples_to_bytes(snd_pcm_t *pcm, long samples)
1998 {
1999         assert(pcm);
2000         if (CHECK_SANITY(! pcm->setup)) {
2001                 SNDMSG("PCM not set up");
2002                 return -EIO;
2003         }
2004         return samples * pcm->sample_bits / 8;
2005 }
2006
2007 /**
2008  * \brief Add an async handler for a PCM
2009  * \param handler Returned handler handle
2010  * \param pcm PCM handle
2011  * \param callback Callback function
2012  * \param private_data Callback private data
2013  * \return 0 otherwise a negative error code on failure
2014  *
2015  * The asynchronous callback is called when period boundary elapses.
2016  */
2017 int snd_async_add_pcm_handler(snd_async_handler_t **handler, snd_pcm_t *pcm, 
2018                               snd_async_callback_t callback, void *private_data)
2019 {
2020         int err;
2021         int was_empty;
2022         snd_async_handler_t *h;
2023         err = snd_async_add_handler(&h, _snd_pcm_async_descriptor(pcm),
2024                                     callback, private_data);
2025         if (err < 0)
2026                 return err;
2027         h->type = SND_ASYNC_HANDLER_PCM;
2028         h->u.pcm = pcm;
2029         was_empty = list_empty(&pcm->async_handlers);
2030         list_add_tail(&h->hlist, &pcm->async_handlers);
2031         if (was_empty) {
2032                 err = snd_pcm_async(pcm, snd_async_handler_get_signo(h), getpid());
2033                 if (err < 0) {
2034                         snd_async_del_handler(h);
2035                         return err;
2036                 }
2037         }
2038         *handler = h;
2039         return 0;
2040 }
2041
2042 /**
2043  * \brief Return PCM handle related to an async handler
2044  * \param handler Async handler handle
2045  * \return PCM handle
2046  */
2047 snd_pcm_t *snd_async_handler_get_pcm(snd_async_handler_t *handler)
2048 {
2049         if (handler->type != SND_ASYNC_HANDLER_PCM) {
2050                 SNDMSG("invalid handler type %d", handler->type);
2051                 return NULL;
2052         }
2053         return handler->u.pcm;
2054 }
2055
2056 static const char *const build_in_pcms[] = {
2057         "adpcm", "alaw", "copy", "dmix", "file", "hooks", "hw", "ladspa", "lfloat",
2058         "linear", "meter", "mulaw", "multi", "null", "empty", "plug", "rate", "route", "share",
2059         "shm", "dsnoop", "dshare", "asym", "iec958", "softvol", "mmap_emul",
2060         NULL
2061 };
2062
2063 static int snd_pcm_open_conf(snd_pcm_t **pcmp, const char *name,
2064                              snd_config_t *pcm_root, snd_config_t *pcm_conf,
2065                              snd_pcm_stream_t stream, int mode)
2066 {
2067         const char *str;
2068         char *buf = NULL, *buf1 = NULL;
2069         int err;
2070         snd_config_t *conf, *type_conf = NULL, *tmp;
2071         snd_config_iterator_t i, next;
2072         const char *id;
2073         const char *lib = NULL, *open_name = NULL;
2074         int (*open_func)(snd_pcm_t **, const char *, 
2075                          snd_config_t *, snd_config_t *, 
2076                          snd_pcm_stream_t, int) = NULL;
2077 #ifndef PIC
2078         extern void *snd_pcm_open_symbols(void);
2079 #endif
2080         if (snd_config_get_type(pcm_conf) != SND_CONFIG_TYPE_COMPOUND) {
2081                 char *val;
2082                 id = NULL;
2083                 snd_config_get_id(pcm_conf, &id);
2084                 val = NULL;
2085                 snd_config_get_ascii(pcm_conf, &val);
2086                 SNDERR("Invalid type for PCM %s%sdefinition (id: %s, value: %s)", name ? name : "", name ? " " : "", id, val);
2087                 free(val);
2088                 return -EINVAL;
2089         }
2090         err = snd_config_search(pcm_conf, "type", &conf);
2091         if (err < 0) {
2092                 SNDERR("type is not defined");
2093                 return err;
2094         }
2095         err = snd_config_get_id(conf, &id);
2096         if (err < 0) {
2097                 SNDERR("unable to get id");
2098                 return err;
2099         }
2100         err = snd_config_get_string(conf, &str);
2101         if (err < 0) {
2102                 SNDERR("Invalid type for %s", id);
2103                 return err;
2104         }
2105         err = snd_config_search_definition(pcm_root, "pcm_type", str, &type_conf);
2106         if (err >= 0) {
2107                 if (snd_config_get_type(type_conf) != SND_CONFIG_TYPE_COMPOUND) {
2108                         SNDERR("Invalid type for PCM type %s definition", str);
2109                         goto _err;
2110                 }
2111                 snd_config_for_each(i, next, type_conf) {
2112                         snd_config_t *n = snd_config_iterator_entry(i);
2113                         const char *id;
2114                         if (snd_config_get_id(n, &id) < 0)
2115                                 continue;
2116                         if (strcmp(id, "comment") == 0)
2117                                 continue;
2118                         if (strcmp(id, "lib") == 0) {
2119                                 err = snd_config_get_string(n, &lib);
2120                                 if (err < 0) {
2121                                         SNDERR("Invalid type for %s", id);
2122                                         goto _err;
2123                                 }
2124                                 continue;
2125                         }
2126                         if (strcmp(id, "open") == 0) {
2127                                 err = snd_config_get_string(n, &open_name);
2128                                 if (err < 0) {
2129                                         SNDERR("Invalid type for %s", id);
2130                                         goto _err;
2131                                 }
2132                                 continue;
2133                         }
2134                         SNDERR("Unknown field %s", id);
2135                         err = -EINVAL;
2136                         goto _err;
2137                 }
2138         }
2139         if (!open_name) {
2140                 buf = malloc(strlen(str) + 32);
2141                 if (buf == NULL) {
2142                         err = -ENOMEM;
2143                         goto _err;
2144                 }
2145                 open_name = buf;
2146                 sprintf(buf, "_snd_pcm_%s_open", str);
2147         }
2148         if (!lib) {
2149                 const char *const *build_in = build_in_pcms;
2150                 while (*build_in) {
2151                         if (!strcmp(*build_in, str))
2152                                 break;
2153                         build_in++;
2154                 }
2155                 if (*build_in == NULL) {
2156                         buf1 = malloc(strlen(str) + sizeof(ALSA_PLUGIN_DIR) + 32);
2157                         if (buf1 == NULL) {
2158                                 err = -ENOMEM;
2159                                 goto _err;
2160                         }
2161                         lib = buf1;
2162                         sprintf(buf1, "%s/libasound_module_pcm_%s.so", ALSA_PLUGIN_DIR, str);
2163                 }
2164         }
2165 #ifndef PIC
2166         snd_pcm_open_symbols(); /* this call is for static linking only */
2167 #endif
2168         open_func = snd_dlobj_cache_get(lib, open_name,
2169                         SND_DLSYM_VERSION(SND_PCM_DLSYM_VERSION), 1);
2170         if (open_func) {
2171                 err = open_func(pcmp, name, pcm_root, pcm_conf, stream, mode);
2172                 if (err >= 0) {
2173                         (*pcmp)->open_func = open_func;
2174                         err = 0;
2175                 } else {
2176                         snd_dlobj_cache_put(open_func);
2177                 }
2178         } else {
2179                 err = -ENXIO;
2180         }
2181         if (err >= 0) {
2182                 err = snd_config_search(pcm_root, "defaults.pcm.compat", &tmp);
2183                 if (err >= 0) {
2184                         long i;
2185                         if (snd_config_get_integer(tmp, &i) >= 0) {
2186                                 if (i > 0)
2187                                         (*pcmp)->compat = 1;
2188                         }
2189                 } else {
2190                         char *str = getenv("LIBASOUND_COMPAT");
2191                         if (str && *str)
2192                                 (*pcmp)->compat = 1;
2193                 }
2194                 err = snd_config_search(pcm_root, "defaults.pcm.minperiodtime", &tmp);
2195                 if (err >= 0)
2196                         snd_config_get_integer(tmp, &(*pcmp)->minperiodtime);
2197                 err = 0;
2198         }
2199        _err:
2200         if (type_conf)
2201                 snd_config_delete(type_conf);
2202         free(buf);
2203         free(buf1);
2204         return err;
2205 }
2206
2207 static int snd_pcm_open_noupdate(snd_pcm_t **pcmp, snd_config_t *root,
2208                                  const char *name, snd_pcm_stream_t stream,
2209                                  int mode, int hop)
2210 {
2211         int err;
2212         snd_config_t *pcm_conf;
2213         const char *str;
2214
2215         err = snd_config_search_definition(root, "pcm", name, &pcm_conf);
2216         if (err < 0) {
2217                 SNDERR("Unknown PCM %s", name);
2218                 return err;
2219         }
2220         if (snd_config_get_string(pcm_conf, &str) >= 0)
2221                 err = snd_pcm_open_noupdate(pcmp, root, str, stream, mode,
2222                                             hop + 1);
2223         else {
2224                 snd_config_set_hop(pcm_conf, hop);
2225                 err = snd_pcm_open_conf(pcmp, name, root, pcm_conf, stream, mode);
2226         }
2227         snd_config_delete(pcm_conf);
2228         return err;
2229 }
2230
2231 /**
2232  * \brief Opens a PCM
2233  * \param pcmp Returned PCM handle
2234  * \param name ASCII identifier of the PCM handle
2235  * \param stream Wanted stream
2236  * \param mode Open mode (see #SND_PCM_NONBLOCK, #SND_PCM_ASYNC)
2237  * \return 0 on success otherwise a negative error code
2238  */
2239 int snd_pcm_open(snd_pcm_t **pcmp, const char *name, 
2240                  snd_pcm_stream_t stream, int mode)
2241 {
2242         int err;
2243         assert(pcmp && name);
2244         err = snd_config_update();
2245         if (err < 0)
2246                 return err;
2247         return snd_pcm_open_noupdate(pcmp, snd_config, name, stream, mode, 0);
2248 }
2249
2250 /**
2251  * \brief Opens a PCM using local configuration
2252  * \param pcmp Returned PCM handle
2253  * \param name ASCII identifier of the PCM handle
2254  * \param stream Wanted stream
2255  * \param mode Open mode (see #SND_PCM_NONBLOCK, #SND_PCM_ASYNC)
2256  * \param lconf Local configuration
2257  * \return 0 on success otherwise a negative error code
2258  */
2259 int snd_pcm_open_lconf(snd_pcm_t **pcmp, const char *name, 
2260                        snd_pcm_stream_t stream, int mode,
2261                        snd_config_t *lconf)
2262 {
2263         assert(pcmp && name && lconf);
2264         return snd_pcm_open_noupdate(pcmp, lconf, name, stream, mode, 0);
2265 }
2266
2267 /**
2268  * \brief Opens a fallback PCM
2269  * \param pcmp Returned PCM handle
2270  * \param root Configuration root
2271  * \param name ASCII identifier of the PCM handle
2272  * \param orig_name The original ASCII name
2273  * \param stream Wanted stream
2274  * \param mode Open mode (see #SND_PCM_NONBLOCK, #SND_PCM_ASYNC)
2275  * \return 0 on success otherwise a negative error code
2276  */
2277 int snd_pcm_open_fallback(snd_pcm_t **pcmp, snd_config_t *root,
2278                           const char *name, const char *orig_name,
2279                           snd_pcm_stream_t stream, int mode)
2280 {
2281         int err;
2282         assert(pcmp && name && root);
2283         err = snd_pcm_open_noupdate(pcmp, root, name, stream, mode, 0);
2284         if (err >= 0) {
2285                 free((*pcmp)->name);
2286                 (*pcmp)->name = orig_name ? strdup(orig_name) : NULL;
2287         }
2288         return err;
2289 }
2290
2291 #ifndef DOC_HIDDEN
2292 int snd_pcm_new(snd_pcm_t **pcmp, snd_pcm_type_t type, const char *name,
2293                 snd_pcm_stream_t stream, int mode)
2294 {
2295         snd_pcm_t *pcm;
2296         pcm = calloc(1, sizeof(*pcm));
2297         if (!pcm)
2298                 return -ENOMEM;
2299         pcm->type = type;
2300         if (name)
2301                 pcm->name = strdup(name);
2302         pcm->stream = stream;
2303         pcm->mode = mode;
2304         pcm->poll_fd_count = 1;
2305         pcm->poll_fd = -1;
2306         pcm->op_arg = pcm;
2307         pcm->fast_op_arg = pcm;
2308         INIT_LIST_HEAD(&pcm->async_handlers);
2309         *pcmp = pcm;
2310         return 0;
2311 }
2312
2313 int snd_pcm_free(snd_pcm_t *pcm)
2314 {
2315         assert(pcm);
2316         free(pcm->name);
2317         free(pcm->hw.link_dst);
2318         free(pcm->appl.link_dst);
2319         snd_dlobj_cache_put(pcm->open_func);
2320         free(pcm);
2321         return 0;
2322 }
2323
2324 int snd_pcm_open_named_slave(snd_pcm_t **pcmp, const char *name,
2325                              snd_config_t *root,
2326                              snd_config_t *conf, snd_pcm_stream_t stream,
2327                              int mode, snd_config_t *parent_conf)
2328 {
2329         const char *str;
2330         int hop;
2331
2332         if ((hop = snd_config_check_hop(parent_conf)) < 0)
2333                 return hop;
2334         if (snd_config_get_string(conf, &str) >= 0)
2335                 return snd_pcm_open_noupdate(pcmp, root, str, stream, mode,
2336                                              hop + 1);
2337         return snd_pcm_open_conf(pcmp, name, root, conf, stream, mode);
2338 }
2339 #endif
2340
2341 /**
2342  * \brief Wait for a PCM to become ready
2343  * \param pcm PCM handle
2344  * \param timeout maximum time in milliseconds to wait,
2345  *        a negative value means infinity
2346  * \return a positive value on success otherwise a negative error code
2347  *         (-EPIPE for the xrun and -ESTRPIPE for the suspended status,
2348  *          others for general errors) 
2349  * \retval 0 timeout occurred
2350  * \retval 1 PCM stream is ready for I/O
2351  */
2352 int snd_pcm_wait(snd_pcm_t *pcm, int timeout)
2353 {
2354         if (snd_pcm_mmap_avail(pcm) >= pcm->avail_min) {
2355                 /* check more precisely */
2356                 switch (snd_pcm_state(pcm)) {
2357                 case SND_PCM_STATE_XRUN:
2358                         return -EPIPE;
2359                 case SND_PCM_STATE_SUSPENDED:
2360                         return -ESTRPIPE;
2361                 case SND_PCM_STATE_DISCONNECTED:
2362                         return -ENODEV;
2363                 default:
2364                         return 1;
2365                 }
2366         }
2367         return snd_pcm_wait_nocheck(pcm, timeout);
2368 }
2369
2370 #ifndef DOC_HIDDEN
2371 /* 
2372  * like snd_pcm_wait() but doesn't check mmap_avail before calling poll()
2373  *
2374  * used in drain code in some plugins
2375  */
2376 int snd_pcm_wait_nocheck(snd_pcm_t *pcm, int timeout)
2377 {
2378         struct pollfd *pfd;
2379         unsigned short revents = 0;
2380         int npfds, err, err_poll;
2381         
2382         npfds = snd_pcm_poll_descriptors_count(pcm);
2383         if (npfds <= 0 || npfds >= 16) {
2384                 SNDERR("Invalid poll_fds %d\n", npfds);
2385                 return -EIO;
2386         }
2387         pfd = alloca(sizeof(*pfd) * npfds);
2388         err = snd_pcm_poll_descriptors(pcm, pfd, npfds);
2389         if (err < 0)
2390                 return err;
2391         if (err != npfds) {
2392                 SNDMSG("invalid poll descriptors %d\n", err);
2393                 return -EIO;
2394         }
2395         do {
2396                 err_poll = poll(pfd, npfds, timeout);
2397                 if (err_poll < 0) {
2398                         if (errno == EINTR)
2399                                 continue;
2400                         return -errno;
2401                 }
2402                 if (! err_poll)
2403                         break;
2404                 err = snd_pcm_poll_descriptors_revents(pcm, pfd, npfds, &revents);
2405                 if (err < 0)
2406                         return err;
2407                 if (revents & (POLLERR | POLLNVAL)) {
2408                         /* check more precisely */
2409                         switch (snd_pcm_state(pcm)) {
2410                         case SND_PCM_STATE_XRUN:
2411                                 return -EPIPE;
2412                         case SND_PCM_STATE_SUSPENDED:
2413                                 return -ESTRPIPE;
2414                         case SND_PCM_STATE_DISCONNECTED:
2415                                 return -ENODEV;
2416                         default:
2417                                 return -EIO;
2418                         }
2419                 }
2420         } while (!(revents & (POLLIN | POLLOUT)));
2421 #if 0 /* very useful code to test poll related problems */
2422         {
2423                 snd_pcm_sframes_t avail_update;
2424                 snd_pcm_hwsync(pcm);
2425                 avail_update = snd_pcm_avail_update(pcm);
2426                 if (avail_update < (snd_pcm_sframes_t)pcm->avail_min) {
2427                         printf("*** snd_pcm_wait() FATAL ERROR!!!\n");
2428                         printf("avail_min = %li, avail_update = %li\n", pcm->avail_min, avail_update);
2429                 }
2430         }
2431 #endif
2432         return err_poll > 0 ? 1 : 0;
2433 }
2434 #endif
2435
2436 /**
2437  * \brief Return number of frames ready to be read (capture) / written (playback)
2438  * \param pcm PCM handle
2439  * \return a positive number of frames ready otherwise a negative
2440  * error code
2441  *
2442  * On capture does all the actions needed to transport to application
2443  * level all the ready frames across underlying layers.
2444  *
2445  * The position is not synced with hardware (driver) position in the sound
2446  * ring buffer in this function. This function is a light version of
2447  * #snd_pcm_avail() .
2448  *
2449  * Using this function is ideal after poll() or select() when audio
2450  * file descriptor made the event and when application expects just period
2451  * timing.
2452  *
2453  * Also this function might be called after #snd_pcm_delay() or
2454  * #snd_pcm_hwsync() functions to move private ring buffer pointers
2455  * in alsa-lib (the internal plugin chain).
2456  */
2457 snd_pcm_sframes_t snd_pcm_avail_update(snd_pcm_t *pcm)
2458 {
2459         return pcm->fast_ops->avail_update(pcm->fast_op_arg);
2460 }
2461
2462 /**
2463  * \brief Return number of frames ready to be read (capture) / written (playback)
2464  * \param pcm PCM handle
2465  * \return a positive number of frames ready otherwise a negative
2466  * error code
2467  *
2468  * On capture does all the actions needed to transport to application
2469  * level all the ready frames across underlying layers.
2470  *
2471  * The position is synced with hardware (driver) position in the sound
2472  * ring buffer in this functions.
2473  */
2474 snd_pcm_sframes_t snd_pcm_avail(snd_pcm_t *pcm)
2475 {
2476         int err;
2477
2478         assert(pcm);
2479         if (CHECK_SANITY(! pcm->setup)) {
2480                 SNDMSG("PCM not set up");
2481                 return -EIO;
2482         }
2483         err = pcm->fast_ops->hwsync(pcm->fast_op_arg);
2484         if (err < 0)
2485                 return err;
2486         return pcm->fast_ops->avail_update(pcm->fast_op_arg);
2487 }
2488
2489 /**
2490  * \brief Combine snd_pcm_avail and snd_pcm_delay functions
2491  * \param pcm PCM handle
2492  * \param availp Number of available frames in the ring buffer
2493  * \param delayp Total I/O latency in frames
2494  * \return zero on success otherwise a negative error code
2495  *
2496  * The avail and delay values retuned are in sync.
2497  */
2498 int snd_pcm_avail_delay(snd_pcm_t *pcm,
2499                         snd_pcm_sframes_t *availp,
2500                         snd_pcm_sframes_t *delayp)
2501 {
2502         snd_pcm_sframes_t sf;
2503         int err;
2504
2505         assert(pcm && availp && delayp);
2506         if (CHECK_SANITY(! pcm->setup)) {
2507                 SNDMSG("PCM not set up");
2508                 return -EIO;
2509         }
2510         err = pcm->fast_ops->hwsync(pcm->fast_op_arg);
2511         if (err < 0)
2512                 return err;
2513         sf = pcm->fast_ops->avail_update(pcm->fast_op_arg);
2514         if (sf < 0)
2515                 return (int)sf;
2516         err = pcm->fast_ops->delay(pcm->fast_op_arg, delayp);
2517         if (err < 0)
2518                 return err;
2519         *availp = sf;
2520         return 0;
2521 }
2522
2523 /**
2524  * \brief Silence an area
2525  * \param dst_area area specification
2526  * \param dst_offset offset in frames inside area
2527  * \param samples samples to silence
2528  * \param format PCM sample format
2529  * \return 0 on success otherwise a negative error code
2530  */
2531 int snd_pcm_area_silence(const snd_pcm_channel_area_t *dst_area, snd_pcm_uframes_t dst_offset,
2532                          unsigned int samples, snd_pcm_format_t format)
2533 {
2534         /* FIXME: sub byte resolution and odd dst_offset */
2535         char *dst;
2536         unsigned int dst_step;
2537         int width;
2538         u_int64_t silence;
2539         if (!dst_area->addr)
2540                 return 0;
2541         dst = snd_pcm_channel_area_addr(dst_area, dst_offset);
2542         width = snd_pcm_format_physical_width(format);
2543         silence = snd_pcm_format_silence_64(format);
2544         if (dst_area->step == (unsigned int) width) {
2545                 unsigned int dwords = samples * width / 64;
2546                 u_int64_t *dstp = (u_int64_t *)dst;
2547                 samples -= dwords * 64 / width;
2548                 while (dwords-- > 0)
2549                         *dstp++ = silence;
2550                 if (samples == 0)
2551                         return 0;
2552         }
2553         dst_step = dst_area->step / 8;
2554         switch (width) {
2555         case 4: {
2556                 u_int8_t s0 = silence & 0xf0;
2557                 u_int8_t s1 = silence & 0x0f;
2558                 int dstbit = dst_area->first % 8;
2559                 int dstbit_step = dst_area->step % 8;
2560                 while (samples-- > 0) {
2561                         if (dstbit) {
2562                                 *dst &= 0xf0;
2563                                 *dst |= s1;
2564                         } else {
2565                                 *dst &= 0x0f;
2566                                 *dst |= s0;
2567                         }
2568                         dst += dst_step;
2569                         dstbit += dstbit_step;
2570                         if (dstbit == 8) {
2571                                 dst++;
2572                                 dstbit = 0;
2573                         }
2574                 }
2575                 break;
2576         }
2577         case 8: {
2578                 u_int8_t sil = silence;
2579                 while (samples-- > 0) {
2580                         *dst = sil;
2581                         dst += dst_step;
2582                 }
2583                 break;
2584         }
2585         case 16: {
2586                 u_int16_t sil = silence;
2587                 while (samples-- > 0) {
2588                         *(u_int16_t*)dst = sil;
2589                         dst += dst_step;
2590                 }
2591                 break;
2592         }
2593         case 24:
2594 #ifdef SNDRV_LITTLE_ENDIAN
2595                 *(dst + 0) = silence >> 0;
2596                 *(dst + 1) = silence >> 8;
2597                 *(dst + 2) = silence >> 16;
2598 #else
2599                 *(dst + 2) = silence >> 0;
2600                 *(dst + 1) = silence >> 8;
2601                 *(dst + 0) = silence >> 16;
2602 #endif
2603                 break;
2604         case 32: {
2605                 u_int32_t sil = silence;
2606                 while (samples-- > 0) {
2607                         *(u_int32_t*)dst = sil;
2608                         dst += dst_step;
2609                 }
2610                 break;
2611         }
2612         case 64: {
2613                 while (samples-- > 0) {
2614                         *(u_int64_t*)dst = silence;
2615                         dst += dst_step;
2616                 }
2617                 break;
2618         }
2619         default:
2620                 SNDMSG("invalid format width %d", width);
2621                 return -EINVAL;
2622         }
2623         return 0;
2624 }
2625
2626 /**
2627  * \brief Silence one or more areas
2628  * \param dst_areas areas specification (one for each channel)
2629  * \param dst_offset offset in frames inside area
2630  * \param channels channels count
2631  * \param frames frames to silence
2632  * \param format PCM sample format
2633  * \return 0 on success otherwise a negative error code
2634  */
2635 int snd_pcm_areas_silence(const snd_pcm_channel_area_t *dst_areas, snd_pcm_uframes_t dst_offset,
2636                           unsigned int channels, snd_pcm_uframes_t frames, snd_pcm_format_t format)
2637 {
2638         int width = snd_pcm_format_physical_width(format);
2639         while (channels > 0) {
2640                 void *addr = dst_areas->addr;
2641                 unsigned int step = dst_areas->step;
2642                 const snd_pcm_channel_area_t *begin = dst_areas;
2643                 int channels1 = channels;
2644                 unsigned int chns = 0;
2645                 int err;
2646                 while (1) {
2647                         channels1--;
2648                         chns++;
2649                         dst_areas++;
2650                         if (channels1 == 0 ||
2651                             dst_areas->addr != addr ||
2652                             dst_areas->step != step ||
2653                             dst_areas->first != dst_areas[-1].first + width)
2654                                 break;
2655                 }
2656                 if (chns > 1 && chns * width == step) {
2657                         /* Collapse the areas */
2658                         snd_pcm_channel_area_t d;
2659                         d.addr = begin->addr;
2660                         d.first = begin->first;
2661                         d.step = width;
2662                         err = snd_pcm_area_silence(&d, dst_offset * chns, frames * chns, format);
2663                         channels -= chns;
2664                 } else {
2665                         err = snd_pcm_area_silence(begin, dst_offset, frames, format);
2666                         dst_areas = begin + 1;
2667                         channels--;
2668                 }
2669                 if (err < 0)
2670                         return err;
2671         }
2672         return 0;
2673 }
2674
2675
2676 /**
2677  * \brief Copy an area
2678  * \param dst_area destination area specification
2679  * \param dst_offset offset in frames inside destination area
2680  * \param src_area source area specification
2681  * \param src_offset offset in frames inside source area
2682  * \param samples samples to copy
2683  * \param format PCM sample format
2684  * \return 0 on success otherwise a negative error code
2685  */
2686 int snd_pcm_area_copy(const snd_pcm_channel_area_t *dst_area, snd_pcm_uframes_t dst_offset,
2687                       const snd_pcm_channel_area_t *src_area, snd_pcm_uframes_t src_offset,
2688                       unsigned int samples, snd_pcm_format_t format)
2689 {
2690         /* FIXME: sub byte resolution and odd dst_offset */
2691         const char *src;
2692         char *dst;
2693         int width;
2694         int src_step, dst_step;
2695         if (dst_area == src_area && dst_offset == src_offset)
2696                 return 0;
2697         if (!src_area->addr)
2698                 return snd_pcm_area_silence(dst_area, dst_offset, samples, format);
2699         src = snd_pcm_channel_area_addr(src_area, src_offset);
2700         if (!dst_area->addr)
2701                 return 0;
2702         dst = snd_pcm_channel_area_addr(dst_area, dst_offset);
2703         width = snd_pcm_format_physical_width(format);
2704         if (src_area->step == (unsigned int) width &&
2705             dst_area->step == (unsigned int) width) {
2706                 size_t bytes = samples * width / 8;
2707                 samples -= bytes * 8 / width;
2708                 memcpy(dst, src, bytes);
2709                 if (samples == 0)
2710                         return 0;
2711         }
2712         src_step = src_area->step / 8;
2713         dst_step = dst_area->step / 8;
2714         switch (width) {
2715         case 4: {
2716                 int srcbit = src_area->first % 8;
2717                 int srcbit_step = src_area->step % 8;
2718                 int dstbit = dst_area->first % 8;
2719                 int dstbit_step = dst_area->step % 8;
2720                 while (samples-- > 0) {
2721                         unsigned char srcval;
2722                         if (srcbit)
2723                                 srcval = *src & 0x0f;
2724                         else
2725                                 srcval = *src & 0xf0;
2726                         if (dstbit)
2727                                 *dst &= 0xf0;
2728                         else
2729                                 *dst &= 0x0f;
2730                         *dst |= srcval;
2731                         src += src_step;
2732                         srcbit += srcbit_step;
2733                         if (srcbit == 8) {
2734                                 src++;
2735                                 srcbit = 0;
2736                         }
2737                         dst += dst_step;
2738                         dstbit += dstbit_step;
2739                         if (dstbit == 8) {
2740                                 dst++;
2741                                 dstbit = 0;
2742                         }
2743                 }
2744                 break;
2745         }
2746         case 8: {
2747                 while (samples-- > 0) {
2748                         *dst = *src;
2749                         src += src_step;
2750                         dst += dst_step;
2751                 }
2752                 break;
2753         }
2754         case 16: {
2755                 while (samples-- > 0) {
2756                         *(u_int16_t*)dst = *(const u_int16_t*)src;
2757                         src += src_step;
2758                         dst += dst_step;
2759                 }
2760                 break;
2761         }
2762         case 24:
2763                 while (samples-- > 0) {
2764                         *(dst + 0) = *(src + 0);
2765                         *(dst + 1) = *(src + 1);
2766                         *(dst + 2) = *(src + 2);
2767                         src += src_step;
2768                         dst += dst_step;
2769                 }
2770                 break;
2771         case 32: {
2772                 while (samples-- > 0) {
2773                         *(u_int32_t*)dst = *(const u_int32_t*)src;
2774                         src += src_step;
2775                         dst += dst_step;
2776                 }
2777                 break;
2778         }
2779         case 64: {
2780                 while (samples-- > 0) {
2781                         *(u_int64_t*)dst = *(const u_int64_t*)src;
2782                         src += src_step;
2783                         dst += dst_step;
2784                 }
2785                 break;
2786         }
2787         default:
2788                 SNDMSG("invalid format width %d", width);
2789                 return -EINVAL;
2790         }
2791         return 0;
2792 }
2793
2794 /**
2795  * \brief Copy one or more areas
2796  * \param dst_areas destination areas specification (one for each channel)
2797  * \param dst_offset offset in frames inside destination area
2798  * \param src_areas source areas specification (one for each channel)
2799  * \param src_offset offset in frames inside source area
2800  * \param channels channels count
2801  * \param frames frames to copy
2802  * \param format PCM sample format
2803  * \return 0 on success otherwise a negative error code
2804  */
2805 int snd_pcm_areas_copy(const snd_pcm_channel_area_t *dst_areas, snd_pcm_uframes_t dst_offset,
2806                        const snd_pcm_channel_area_t *src_areas, snd_pcm_uframes_t src_offset,
2807                        unsigned int channels, snd_pcm_uframes_t frames, snd_pcm_format_t format)
2808 {
2809         int width = snd_pcm_format_physical_width(format);
2810         assert(dst_areas);
2811         assert(src_areas);
2812         if (! channels) {
2813                 SNDMSG("invalid channels %d", channels);
2814                 return -EINVAL;
2815         }
2816         if (! frames) {
2817                 SNDMSG("invalid frames %ld", frames);
2818                 return -EINVAL;
2819         }
2820         while (channels > 0) {
2821                 unsigned int step = src_areas->step;
2822                 void *src_addr = src_areas->addr;
2823                 const snd_pcm_channel_area_t *src_start = src_areas;
2824                 void *dst_addr = dst_areas->addr;
2825                 const snd_pcm_channel_area_t *dst_start = dst_areas;
2826                 int channels1 = channels;
2827                 unsigned int chns = 0;
2828                 while (dst_areas->step == step) {
2829                         channels1--;
2830                         chns++;
2831                         src_areas++;
2832                         dst_areas++;
2833                         if (channels1 == 0 ||
2834                             src_areas->step != step ||
2835                             src_areas->addr != src_addr ||
2836                             dst_areas->addr != dst_addr ||
2837                             src_areas->first != src_areas[-1].first + width ||
2838                             dst_areas->first != dst_areas[-1].first + width)
2839                                 break;
2840                 }
2841                 if (chns > 1 && chns * width == step) {
2842                         /* Collapse the areas */
2843                         snd_pcm_channel_area_t s, d;
2844                         s.addr = src_start->addr;
2845                         s.first = src_start->first;
2846                         s.step = width;
2847                         d.addr = dst_start->addr;
2848                         d.first = dst_start->first;
2849                         d.step = width;
2850                         snd_pcm_area_copy(&d, dst_offset * chns,
2851                                           &s, src_offset * chns, 
2852                                           frames * chns, format);
2853                         channels -= chns;
2854                 } else {
2855                         snd_pcm_area_copy(dst_start, dst_offset,
2856                                           src_start, src_offset,
2857                                           frames, format);
2858                         src_areas = src_start + 1;
2859                         dst_areas = dst_start + 1;
2860                         channels--;
2861                 }
2862         }
2863         return 0;
2864 }
2865
2866 static void dump_one_param(snd_pcm_hw_params_t *params, unsigned int k, snd_output_t *out)
2867 {
2868         snd_output_printf(out, "%s: ", snd_pcm_hw_param_name(k));
2869         snd_pcm_hw_param_dump(params, k, out);
2870         snd_output_putc(out, '\n');
2871 }
2872
2873 /**
2874  * \brief Dump a PCM hardware configuration space
2875  * \param params Configuration space
2876  * \param out Output handle
2877  * \return 0 on success otherwise a negative error code
2878  */
2879 int snd_pcm_hw_params_dump(snd_pcm_hw_params_t *params, snd_output_t *out)
2880 {
2881         unsigned int k;
2882         for (k = SND_PCM_HW_PARAM_FIRST_MASK; k <= SND_PCM_HW_PARAM_LAST_MASK; k++)
2883                 dump_one_param(params, k, out);
2884         for (k = SND_PCM_HW_PARAM_FIRST_INTERVAL; k <= SND_PCM_HW_PARAM_LAST_INTERVAL; k++)
2885                 dump_one_param(params, k, out);
2886         return 0;
2887 }
2888
2889 /**
2890  * \brief Check if hardware supports sample-resolution mmap for given configuration
2891  * \param params Configuration space
2892  * \retval 0 Hardware doesn't support sample-resolution mmap
2893  * \retval 1 Hardware supports sample-resolution mmap
2894  *
2895  * This function should only be called when the configuration space
2896  * contains a single configuration. Call #snd_pcm_hw_params to choose
2897  * a single configuration from the configuration space.
2898  */
2899 int snd_pcm_hw_params_can_mmap_sample_resolution(const snd_pcm_hw_params_t *params)
2900 {
2901         assert(params);
2902         if (CHECK_SANITY(params->info == ~0U)) {
2903                 SNDMSG("invalid PCM info field");
2904                 return 0; /* FIXME: should be a negative error? */
2905         }
2906         return !!(params->info & SNDRV_PCM_INFO_MMAP_VALID);
2907 }
2908
2909 /**
2910  * \brief Check if hardware does double buffering for start/stop for given configuration
2911  * \param params Configuration space
2912  * \retval 0 Hardware doesn't do double buffering for start/stop
2913  * \retval 1 Hardware does double buffering for start/stop
2914  *
2915  * This function should only be called when the configuration space
2916  * contains a single configuration. Call #snd_pcm_hw_params to choose
2917  * a single configuration from the configuration space.
2918  */
2919 int snd_pcm_hw_params_is_double(const snd_pcm_hw_params_t *params)
2920 {
2921         assert(params);
2922         if (CHECK_SANITY(params->info == ~0U)) {
2923                 SNDMSG("invalid PCM info field");
2924                 return 0; /* FIXME: should be a negative error? */
2925         }
2926         return !!(params->info & SNDRV_PCM_INFO_DOUBLE);
2927 }
2928
2929 /**
2930  * \brief Check if hardware does double buffering for data transfers for given configuration
2931  * \param params Configuration space
2932  * \retval 0 Hardware doesn't do double buffering for data transfers
2933  * \retval 1 Hardware does double buffering for data transfers
2934  *
2935  * This function should only be called when the configuration space
2936  * contains a single configuration. Call #snd_pcm_hw_params to choose
2937  * a single configuration from the configuration space.
2938  */
2939 int snd_pcm_hw_params_is_batch(const snd_pcm_hw_params_t *params)
2940 {
2941         assert(params);
2942         if (CHECK_SANITY(params->info == ~0U)) {
2943                 SNDMSG("invalid PCM info field");
2944                 return 0; /* FIXME: should be a negative error? */
2945         }
2946         return !!(params->info & SNDRV_PCM_INFO_BATCH);
2947 }
2948
2949 /**
2950  * \brief Check if hardware does block transfers for samples for given configuration
2951  * \param params Configuration space
2952  * \retval 0 Hardware doesn't block transfers
2953  * \retval 1 Hardware does block transfers
2954  *
2955  * This function should only be called when the configuration space
2956  * contains a single configuration. Call #snd_pcm_hw_params to choose
2957  * a single configuration from the configuration space.
2958  */
2959 int snd_pcm_hw_params_is_block_transfer(const snd_pcm_hw_params_t *params)
2960 {
2961         assert(params);
2962         if (CHECK_SANITY(params->info == ~0U)) {
2963                 SNDMSG("invalid PCM info field");
2964                 return 0; /* FIXME: should be a negative error? */
2965         }
2966         return !!(params->info & SNDRV_PCM_INFO_BLOCK_TRANSFER);
2967 }
2968
2969 /**
2970  * \brief Check if timestamps are monotonic for given configuration
2971  * \param params Configuration space
2972  * \retval 0 Device doesn't do monotomic timestamps
2973  * \retval 1 Device does monotonic timestamps
2974  *
2975  * This function should only be called when the configuration space
2976  * contains a single configuration. Call #snd_pcm_hw_params to choose
2977  * a single configuration from the configuration space.
2978  */
2979 int snd_pcm_hw_params_is_monotonic(const snd_pcm_hw_params_t *params)
2980 {
2981         assert(params);
2982         if (CHECK_SANITY(params->info == ~0U)) {
2983                 SNDMSG("invalid PCM info field");
2984                 return 0; /* FIXME: should be a negative error? */
2985         }
2986         return !!(params->info & SND_PCM_INFO_MONOTONIC);
2987 }
2988
2989 /**
2990  * \brief Check if hardware supports overrange detection
2991  * \param params Configuration space
2992  * \retval 0 Hardware doesn't support overrange detection
2993  * \retval 1 Hardware supports overrange detection
2994  *
2995  * This function should only be called when the configuration space
2996  * contains a single configuration. Call #snd_pcm_hw_params to choose
2997  * a single configuration from the configuration space.
2998  */
2999 int snd_pcm_hw_params_can_overrange(const snd_pcm_hw_params_t *params)
3000 {
3001         assert(params);
3002         if (CHECK_SANITY(params->info == ~0U)) {
3003                 SNDMSG("invalid PCM info field");
3004                 return 0; /* FIXME: should be a negative error? */
3005         }
3006         return !!(params->info & SNDRV_PCM_INFO_OVERRANGE);
3007 }
3008
3009 /**
3010  * \brief Check if hardware supports pause
3011  * \param params Configuration space
3012  * \retval 0 Hardware doesn't support pause
3013  * \retval 1 Hardware supports pause
3014  *
3015  * This function should only be called when the configuration space
3016  * contains a single configuration. Call #snd_pcm_hw_params to choose
3017  * a single configuration from the configuration space.
3018  */
3019 int snd_pcm_hw_params_can_pause(const snd_pcm_hw_params_t *params)
3020 {
3021         assert(params);
3022         if (CHECK_SANITY(params->info == ~0U)) {
3023                 SNDMSG("invalid PCM info field");
3024                 return 0; /* FIXME: should be a negative error? */
3025         }
3026         return !!(params->info & SNDRV_PCM_INFO_PAUSE);
3027 }
3028
3029 /**
3030  * \brief Check if hardware supports resume
3031  * \param params Configuration space
3032  * \retval 0 Hardware doesn't support resume
3033  * \retval 1 Hardware supports resume
3034  *
3035  * This function should only be called when the configuration space
3036  * contains a single configuration. Call #snd_pcm_hw_params to choose
3037  * a single configuration from the configuration space.
3038  */
3039 int snd_pcm_hw_params_can_resume(const snd_pcm_hw_params_t *params)
3040 {
3041         assert(params);
3042         if (CHECK_SANITY(params->info == ~0U)) {
3043                 SNDMSG("invalid PCM info field");
3044                 return 0; /* FIXME: should be a negative error? */
3045         }
3046         return !!(params->info & SNDRV_PCM_INFO_RESUME);
3047 }
3048
3049 /**
3050  * \brief Check if hardware does half-duplex only
3051  * \param params Configuration space
3052  * \retval 0 Hardware doesn't do half-duplex
3053  * \retval 1 Hardware does half-duplex
3054  *
3055  * This function should only be called when the configuration space
3056  * contains a single configuration. Call #snd_pcm_hw_params to choose
3057  * a single configuration from the configuration space.
3058  */
3059 int snd_pcm_hw_params_is_half_duplex(const snd_pcm_hw_params_t *params)
3060 {
3061         assert(params);
3062         if (CHECK_SANITY(params->info == ~0U)) {
3063                 SNDMSG("invalid PCM info field");
3064                 return 0; /* FIXME: should be a negative error? */
3065         }
3066         return !!(params->info & SNDRV_PCM_INFO_HALF_DUPLEX);
3067 }
3068
3069 /**
3070  * \brief Check if hardware does joint-duplex (playback and capture are somewhat correlated)
3071  * \param params Configuration space
3072  * \retval 0 Hardware doesn't do joint-duplex
3073  * \retval 1 Hardware does joint-duplex
3074  *
3075  * This function should only be called when the configuration space
3076  * contains a single configuration. Call #snd_pcm_hw_params to choose
3077  * a single configuration from the configuration space.
3078  */
3079 int snd_pcm_hw_params_is_joint_duplex(const snd_pcm_hw_params_t *params)
3080 {
3081         assert(params);
3082         if (CHECK_SANITY(params->info == ~0U)) {
3083                 SNDMSG("invalid PCM info field");
3084                 return 0; /* FIXME: should be a negative error? */
3085         }
3086         return !!(params->info & SNDRV_PCM_INFO_JOINT_DUPLEX);
3087 }
3088
3089 /**
3090  * \brief Check if hardware supports synchronized start with sample resolution
3091  * \param params Configuration space
3092  * \retval 0 Hardware doesn't support synchronized start
3093  * \retval 1 Hardware supports synchronized start
3094  *
3095  * This function should only be called when the configuration space
3096  * contains a single configuration. Call #snd_pcm_hw_params to choose
3097  * a single configuration from the configuration space.
3098  */
3099 int snd_pcm_hw_params_can_sync_start(const snd_pcm_hw_params_t *params)
3100 {
3101         assert(params);
3102         if (CHECK_SANITY(params->info == ~0U)) {
3103                 SNDMSG("invalid PCM info field");
3104                 return 0; /* FIXME: should be a negative error? */
3105         }
3106         return !!(params->info & SNDRV_PCM_INFO_SYNC_START);
3107 }
3108
3109 /**
3110  * \brief Check if hardware can disable period wakeups
3111  * \param params Configuration space
3112  * \retval 0 Hardware cannot disable period wakeups
3113  * \retval 1 Hardware can disable period wakeups
3114  */
3115 int snd_pcm_hw_params_can_disable_period_wakeup(const snd_pcm_hw_params_t *params)
3116 {
3117         assert(params);
3118         if (CHECK_SANITY(params->info == ~0U)) {
3119                 SNDMSG("invalid PCM info field");
3120                 return 0; /* FIXME: should be a negative error? */
3121         }
3122         return !!(params->info & SNDRV_PCM_INFO_NO_PERIOD_WAKEUP);
3123 }
3124
3125 /**
3126  * \brief Get rate exact info from a configuration space
3127  * \param params Configuration space
3128  * \param rate_num Pointer to returned rate numerator
3129  * \param rate_den Pointer to returned rate denominator
3130  * \return 0 otherwise a negative error code if the info is not available
3131  *
3132  * This function should only be called when the configuration space
3133  * contains a single configuration. Call #snd_pcm_hw_params to choose
3134  * a single configuration from the configuration space.
3135  */
3136 int snd_pcm_hw_params_get_rate_numden(const snd_pcm_hw_params_t *params,
3137                                       unsigned int *rate_num, unsigned int *rate_den)
3138 {
3139         assert(params);
3140         if (CHECK_SANITY(params->rate_den == 0)) {
3141                 SNDMSG("invalid rate_den value");
3142                 return -EINVAL;
3143         }
3144         *rate_num = params->rate_num;
3145         *rate_den = params->rate_den;
3146         return 0;
3147 }
3148
3149 /**
3150  * \brief Get sample resolution info from a configuration space
3151  * \param params Configuration space
3152  * \return signification bits in sample otherwise a negative error code if the info is not available
3153  *
3154  * This function should only be called when the configuration space
3155  * contains a single configuration. Call #snd_pcm_hw_params to choose
3156  * a single configuration from the configuration space.
3157  */
3158 int snd_pcm_hw_params_get_sbits(const snd_pcm_hw_params_t *params)
3159 {
3160         assert(params);
3161         if (CHECK_SANITY(params->msbits == 0)) {
3162                 SNDMSG("invalid msbits value");
3163                 return -EINVAL;
3164         }
3165         return params->msbits;
3166 }
3167
3168 /**
3169  * \brief Get hardware FIFO size info from a configuration space
3170  * \param params Configuration space
3171  * \return FIFO size in frames otherwise a negative error code if the info is not available
3172  *
3173  * This function should only be called when the configuration space
3174  * contains a single configuration. Call #snd_pcm_hw_params to choose
3175  * a single configuration from the configuration space.
3176  */
3177 int snd_pcm_hw_params_get_fifo_size(const snd_pcm_hw_params_t *params)
3178 {
3179         assert(params);
3180         if (CHECK_SANITY(params->info == ~0U)) {
3181                 SNDMSG("invalid PCM info field");
3182                 return -EINVAL;
3183         }
3184         return params->fifo_size;
3185 }
3186
3187 /**
3188  * \brief Fill params with a full configuration space for a PCM
3189  * \param pcm PCM handle
3190  * \param params Configuration space
3191  *
3192  * The configuration space will be filled with all possible ranges
3193  * for the PCM device.
3194  */
3195 int snd_pcm_hw_params_any(snd_pcm_t *pcm, snd_pcm_hw_params_t *params)
3196 {
3197         _snd_pcm_hw_params_any(params);
3198         return snd_pcm_hw_refine(pcm, params);
3199 }
3200
3201 /**
3202  * \brief get size of #snd_pcm_access_mask_t
3203  * \return size in bytes
3204  */
3205 size_t snd_pcm_access_mask_sizeof()
3206 {
3207         return sizeof(snd_pcm_access_mask_t);
3208 }
3209
3210 /**
3211  * \brief allocate an empty #snd_pcm_access_mask_t using standard malloc
3212  * \param ptr returned pointer
3213  * \return 0 on success otherwise negative error code
3214  */
3215 int snd_pcm_access_mask_malloc(snd_pcm_access_mask_t **ptr)
3216 {
3217         assert(ptr);
3218         *ptr = calloc(1, sizeof(snd_pcm_access_mask_t));
3219         if (!*ptr)
3220                 return -ENOMEM;
3221         return 0;
3222 }
3223
3224 /**
3225  * \brief frees a previously allocated #snd_pcm_access_mask_t
3226  * \param obj pointer to object to free
3227  */
3228 void snd_pcm_access_mask_free(snd_pcm_access_mask_t *obj)
3229 {
3230         free(obj);
3231 }
3232
3233 /**
3234  * \brief copy one #snd_pcm_access_mask_t to another
3235  * \param dst pointer to destination
3236  * \param src pointer to source
3237  */
3238 void snd_pcm_access_mask_copy(snd_pcm_access_mask_t *dst, const snd_pcm_access_mask_t *src)
3239 {
3240         assert(dst && src);
3241         *dst = *src;
3242 }
3243
3244 /**
3245  * \brief reset all bits in a #snd_pcm_access_mask_t
3246  * \param mask pointer to mask
3247  */
3248 void snd_pcm_access_mask_none(snd_pcm_access_mask_t *mask)
3249 {
3250         snd_mask_none((snd_mask_t *) mask);
3251 }
3252
3253 /**
3254  * \brief set all bits in a #snd_pcm_access_mask_t
3255  * \param mask pointer to mask
3256  */
3257 void snd_pcm_access_mask_any(snd_pcm_access_mask_t *mask)
3258 {
3259         snd_mask_any((snd_mask_t *) mask);
3260 }
3261
3262 /**
3263  * \brief test the presence of an access type in a #snd_pcm_access_mask_t
3264  * \param mask pointer to mask
3265  * \param val access type
3266  */
3267 int snd_pcm_access_mask_test(const snd_pcm_access_mask_t *mask, snd_pcm_access_t val)
3268 {
3269         return snd_mask_test((const snd_mask_t *) mask, (unsigned long) val);
3270 }
3271
3272 /**
3273  * \brief test, if given a #snd_pcm_access_mask_t is empty
3274  * \param mask pointer to mask
3275  * \retval 0 not empty
3276  * \retval 1 empty
3277  */
3278 int snd_pcm_access_mask_empty(const snd_pcm_access_mask_t *mask)
3279 {
3280         return snd_mask_empty((const snd_mask_t *) mask);
3281 }
3282
3283 /**
3284  * \brief make an access type present in a #snd_pcm_access_mask_t
3285  * \param mask pointer to mask
3286  * \param val access type
3287  */
3288 void snd_pcm_access_mask_set(snd_pcm_access_mask_t *mask, snd_pcm_access_t val)
3289 {
3290         snd_mask_set((snd_mask_t *) mask, (unsigned long) val);
3291 }
3292
3293 /**
3294  * \brief make an access type missing from a #snd_pcm_access_mask_t
3295  * \param mask pointer to mask
3296  * \param val access type
3297  */
3298 void snd_pcm_access_mask_reset(snd_pcm_access_mask_t *mask, snd_pcm_access_t val)
3299 {
3300         snd_mask_reset((snd_mask_t *) mask, (unsigned long) val);
3301 }
3302
3303 /**
3304  * \brief get size of #snd_pcm_format_mask_t
3305  * \return size in bytes
3306  */
3307 size_t snd_pcm_format_mask_sizeof()
3308 {
3309         return sizeof(snd_pcm_format_mask_t);
3310 }
3311
3312 /**
3313  * \brief allocate an empty #snd_pcm_format_mask_t using standard malloc
3314  * \param ptr returned pointer
3315  * \return 0 on success otherwise negative error code
3316  */
3317 int snd_pcm_format_mask_malloc(snd_pcm_format_mask_t **ptr)
3318 {
3319         assert(ptr);
3320         *ptr = calloc(1, sizeof(snd_pcm_format_mask_t));
3321         if (!*ptr)
3322                 return -ENOMEM;
3323         return 0;
3324 }
3325
3326 /**
3327  * \brief frees a previously allocated #snd_pcm_format_mask_t
3328  * \param obj pointer to object to free
3329  */
3330 void snd_pcm_format_mask_free(snd_pcm_format_mask_t *obj)
3331 {
3332         free(obj);
3333 }
3334
3335 /**
3336  * \brief copy one #snd_pcm_format_mask_t to another
3337  * \param dst pointer to destination
3338  * \param src pointer to source
3339  */
3340 void snd_pcm_format_mask_copy(snd_pcm_format_mask_t *dst, const snd_pcm_format_mask_t *src)
3341 {
3342         assert(dst && src);
3343         *dst = *src;
3344 }
3345
3346 /**
3347  * \brief reset all bits in a #snd_pcm_format_mask_t
3348  * \param mask pointer to mask
3349  */
3350 void snd_pcm_format_mask_none(snd_pcm_format_mask_t *mask)
3351 {
3352         snd_mask_none((snd_mask_t *) mask);
3353 }
3354
3355 /**
3356  * \brief set all bits in a #snd_pcm_format_mask_t
3357  * \param mask pointer to mask
3358  */
3359 void snd_pcm_format_mask_any(snd_pcm_format_mask_t *mask)
3360 {
3361         snd_mask_any((snd_mask_t *) mask);
3362 }
3363
3364 /**
3365  * \brief test the presence of a format in a #snd_pcm_format_mask_t
3366  * \param mask pointer to mask
3367  * \param val format
3368  */
3369 int snd_pcm_format_mask_test(const snd_pcm_format_mask_t *mask, snd_pcm_format_t val)
3370 {
3371         return snd_mask_test((const snd_mask_t *) mask, (unsigned long) val);
3372 }
3373
3374 /**
3375  * \brief test, if given a #snd_pcm_format_mask_t is empty
3376  * \param mask pointer to mask
3377  * \retval 0 not empty
3378  * \retval 1 empty
3379  */
3380 int snd_pcm_format_mask_empty(const snd_pcm_format_mask_t *mask)
3381 {
3382         return snd_mask_empty((const snd_mask_t *) mask);
3383 }
3384
3385 /**
3386  * \brief make a format present in a #snd_pcm_format_mask_t
3387  * \param mask pointer to mask
3388  * \param val format
3389  */
3390 void snd_pcm_format_mask_set(snd_pcm_format_mask_t *mask, snd_pcm_format_t val)
3391 {
3392         snd_mask_set((snd_mask_t *) mask, (unsigned long) val);
3393 }
3394
3395 /**
3396  * \brief make a format missing from a #snd_pcm_format_mask_t
3397  * \param mask pointer to mask
3398  * \param val format
3399  */
3400 void snd_pcm_format_mask_reset(snd_pcm_format_mask_t *mask, snd_pcm_format_t val)
3401 {
3402         snd_mask_reset((snd_mask_t *) mask, (unsigned long) val);
3403 }
3404
3405
3406 /**
3407  * \brief get size of #snd_pcm_subformat_mask_t
3408  * \return size in bytes
3409  */
3410 size_t snd_pcm_subformat_mask_sizeof()
3411 {
3412         return sizeof(snd_pcm_subformat_mask_t);
3413 }
3414
3415 /**
3416  * \brief allocate an empty #snd_pcm_subformat_mask_t using standard malloc
3417  * \param ptr returned pointer
3418  * \return 0 on success otherwise negative error code
3419  */
3420 int snd_pcm_subformat_mask_malloc(snd_pcm_subformat_mask_t **ptr)
3421 {
3422         assert(ptr);
3423         *ptr = calloc(1, sizeof(snd_pcm_subformat_mask_t));
3424         if (!*ptr)
3425                 return -ENOMEM;
3426         return 0;
3427 }
3428
3429 /**
3430  * \brief frees a previously allocated #snd_pcm_subformat_mask_t
3431  * \param obj pointer to object to free
3432  */
3433 void snd_pcm_subformat_mask_free(snd_pcm_subformat_mask_t *obj)
3434 {
3435         free(obj);
3436 }
3437
3438 /**
3439  * \brief copy one #snd_pcm_subformat_mask_t to another
3440  * \param dst pointer to destination
3441  * \param src pointer to source
3442  */
3443 void snd_pcm_subformat_mask_copy(snd_pcm_subformat_mask_t *dst, const snd_pcm_subformat_mask_t *src)
3444 {
3445         assert(dst && src);
3446         *dst = *src;
3447 }
3448
3449 /**
3450  * \brief reset all bits in a #snd_pcm_subformat_mask_t
3451  * \param mask pointer to mask
3452  */
3453 void snd_pcm_subformat_mask_none(snd_pcm_subformat_mask_t *mask)
3454 {
3455         snd_mask_none((snd_mask_t *) mask);
3456 }
3457
3458 /**
3459  * \brief set all bits in a #snd_pcm_subformat_mask_t
3460  * \param mask pointer to mask
3461  */
3462 void snd_pcm_subformat_mask_any(snd_pcm_subformat_mask_t *mask)
3463 {
3464         snd_mask_any((snd_mask_t *) mask);
3465 }
3466
3467 /**
3468  * \brief test the presence of a subformat in a #snd_pcm_subformat_mask_t
3469  * \param mask pointer to mask
3470  * \param val subformat
3471  */
3472 int snd_pcm_subformat_mask_test(const snd_pcm_subformat_mask_t *mask, snd_pcm_subformat_t val)
3473 {
3474         return snd_mask_test((const snd_mask_t *) mask, (unsigned long) val);
3475 }
3476
3477 /**
3478  * \brief test, if given a #snd_pcm_subformat_mask_t is empty
3479  * \param mask pointer to mask
3480  * \retval 0 not empty
3481  * \retval 1 empty
3482  */
3483 int snd_pcm_subformat_mask_empty(const snd_pcm_subformat_mask_t *mask)
3484 {
3485         return snd_mask_empty((const snd_mask_t *) mask);
3486 }
3487
3488 /**
3489  * \brief make a subformat present in a #snd_pcm_subformat_mask_t
3490  * \param mask pointer to mask
3491  * \param val subformat
3492  */
3493 void snd_pcm_subformat_mask_set(snd_pcm_subformat_mask_t *mask, snd_pcm_subformat_t val)
3494 {
3495         snd_mask_set((snd_mask_t *) mask, (unsigned long) val);
3496 }
3497
3498 /**
3499  * \brief make a subformat missing from a #snd_pcm_subformat_mask_t
3500  * \param mask pointer to mask
3501  * \param val subformat
3502  */
3503 void snd_pcm_subformat_mask_reset(snd_pcm_subformat_mask_t *mask, snd_pcm_subformat_t val)
3504 {
3505         snd_mask_reset((snd_mask_t *) mask, (unsigned long) val);
3506 }
3507
3508
3509 /**
3510  * \brief get size of #snd_pcm_hw_params_t
3511  * \return size in bytes
3512  */
3513 size_t snd_pcm_hw_params_sizeof()
3514 {
3515         return sizeof(snd_pcm_hw_params_t);
3516 }
3517
3518 /**
3519  * \brief allocate an invalid #snd_pcm_hw_params_t using standard malloc
3520  * \param ptr returned pointer
3521  * \return 0 on success otherwise negative error code
3522  */
3523 int snd_pcm_hw_params_malloc(snd_pcm_hw_params_t **ptr)
3524 {
3525         assert(ptr);
3526         *ptr = calloc(1, sizeof(snd_pcm_hw_params_t));
3527         if (!*ptr)
3528                 return -ENOMEM;
3529         return 0;
3530 }
3531
3532 /**
3533  * \brief frees a previously allocated #snd_pcm_hw_params_t
3534  * \param obj pointer to object to free
3535  */
3536 void snd_pcm_hw_params_free(snd_pcm_hw_params_t *obj)
3537 {
3538         free(obj);
3539 }
3540
3541 /**
3542  * \brief copy one #snd_pcm_hw_params_t to another
3543  * \param dst pointer to destination
3544  * \param src pointer to source
3545  */
3546 void snd_pcm_hw_params_copy(snd_pcm_hw_params_t *dst, const snd_pcm_hw_params_t *src)
3547 {
3548         assert(dst && src);
3549         *dst = *src;
3550 }
3551
3552
3553 /**
3554  * \brief Extract access type from a configuration space
3555  * \param params Configuration space
3556  * \param access Returned value
3557  * \return access type otherwise a negative error code if the configuration space does not contain a single value
3558  */
3559 #ifndef DOXYGEN
3560 int INTERNAL(snd_pcm_hw_params_get_access)(const snd_pcm_hw_params_t *params, snd_pcm_access_t *access)
3561 #else
3562 int snd_pcm_hw_params_get_access(const snd_pcm_hw_params_t *params, snd_pcm_access_t *access)
3563 #endif
3564 {
3565         unsigned int _val;
3566         int err = snd_pcm_hw_param_get(params, SND_PCM_HW_PARAM_ACCESS, &_val, NULL);
3567         if (err >= 0)
3568                 *access = _val;
3569         return err;
3570 }
3571
3572 /**
3573  * \brief Verify if an access type is available inside a configuration space for a PCM
3574  * \param pcm PCM handle
3575  * \param params Configuration space
3576  * \param access access type
3577  * \return 0 if available a negative error code otherwise
3578  */
3579 int snd_pcm_hw_params_test_access(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_access_t access)
3580 {
3581         return snd_pcm_hw_param_set(pcm, params, SND_TEST, SND_PCM_HW_PARAM_ACCESS, access, 0);
3582 }
3583
3584 /**
3585  * \brief Restrict a configuration space to contain only one access type
3586  * \param pcm PCM handle
3587  * \param params Configuration space
3588  * \param access access type
3589  * \return 0 otherwise a negative error code if configuration space would become empty
3590  */
3591 int snd_pcm_hw_params_set_access(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_access_t access)
3592 {
3593         return snd_pcm_hw_param_set(pcm, params, SND_TRY, SND_PCM_HW_PARAM_ACCESS, access, 0);
3594 }
3595
3596 /**
3597  * \brief Restrict a configuration space to contain only its first access type
3598  * \param pcm PCM handle
3599  * \param params Configuration space
3600  * \param access Returned first access type
3601  * \return 0 otherwise a negative error code
3602  */
3603 #ifndef DOXYGEN
3604 int INTERNAL(snd_pcm_hw_params_set_access_first)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_access_t *access)
3605 #else
3606 int snd_pcm_hw_params_set_access_first(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_access_t *access)
3607 #endif
3608 {
3609         return snd_pcm_hw_param_set_first(pcm, params, SND_PCM_HW_PARAM_ACCESS, access, NULL);
3610 }
3611
3612 /**
3613  * \brief Restrict a configuration space to contain only its last access type
3614  * \param pcm PCM handle
3615  * \param params Configuration space
3616  * \param access Returned last access type
3617  * \return 0 otherwise a negative error code
3618  */
3619 #ifndef DOXYGEN
3620 int INTERNAL(snd_pcm_hw_params_set_access_last)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_access_t *access)
3621 #else
3622 int snd_pcm_hw_params_set_access_last(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_access_t *access)
3623 #endif
3624 {
3625         return snd_pcm_hw_param_set_last(pcm, params, SND_PCM_HW_PARAM_ACCESS, access, NULL);
3626 }
3627
3628 /**
3629  * \brief Restrict a configuration space to contain only a set of access types
3630  * \param pcm PCM handle
3631  * \param params Configuration space
3632  * \param mask Access mask
3633  * \return 0 otherwise a negative error code
3634  */
3635 int snd_pcm_hw_params_set_access_mask(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_access_mask_t *mask)
3636 {
3637         return snd_pcm_hw_param_set_mask(pcm, params, SND_TRY, SND_PCM_HW_PARAM_ACCESS, (snd_mask_t *) mask);
3638 }
3639
3640 /**
3641  * \brief Get access mask from a configuration space
3642  * \param params Configuration space
3643  * \param mask Returned Access mask
3644  */
3645 int snd_pcm_hw_params_get_access_mask(snd_pcm_hw_params_t *params, snd_pcm_access_mask_t *mask)
3646 {
3647         if (params == NULL || mask == NULL)
3648                 return -EINVAL;
3649         snd_pcm_access_mask_copy(mask, snd_pcm_hw_param_get_mask(params, SND_PCM_HW_PARAM_ACCESS));
3650         return 0;
3651 }
3652
3653
3654 /**
3655  * \brief Extract format from a configuration space
3656  * \param params Configuration space
3657  * \param format returned format
3658  * \return format otherwise a negative error code if the configuration space does not contain a single value
3659  */
3660 #ifndef DOXYGEN
3661 int INTERNAL(snd_pcm_hw_params_get_format)(const snd_pcm_hw_params_t *params, snd_pcm_format_t *format)
3662 #else
3663 int snd_pcm_hw_params_get_format(const snd_pcm_hw_params_t *params, snd_pcm_format_t *format)
3664 #endif
3665 {
3666         return snd_pcm_hw_param_get(params, SND_PCM_HW_PARAM_FORMAT, (unsigned int *)format, NULL);
3667 }
3668
3669 /**
3670  * \brief Verify if a format is available inside a configuration space for a PCM
3671  * \param pcm PCM handle
3672  * \param params Configuration space
3673  * \param format format
3674  * \return 0 if available a negative error code otherwise
3675  */
3676 int snd_pcm_hw_params_test_format(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_format_t format)
3677 {
3678         return snd_pcm_hw_param_set(pcm, params, SND_TEST, SND_PCM_HW_PARAM_FORMAT, format, 0);
3679 }
3680
3681 /**
3682  * \brief Restrict a configuration space to contain only one format
3683  * \param pcm PCM handle
3684  * \param params Configuration space
3685  * \param format format
3686  * \return 0 otherwise a negative error code
3687  */
3688 int snd_pcm_hw_params_set_format(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_format_t format)
3689 {
3690         return snd_pcm_hw_param_set(pcm, params, SND_TRY, SND_PCM_HW_PARAM_FORMAT, format, 0);
3691 }
3692
3693 /**
3694  * \brief Restrict a configuration space to contain only its first format
3695  * \param pcm PCM handle
3696  * \param params Configuration space
3697  * \param format Returned first format
3698  * \return 0 otherwise a negative error code
3699  */
3700 #ifndef DOXYGEN
3701 int INTERNAL(snd_pcm_hw_params_set_format_first)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_format_t *format)
3702 #else
3703 int snd_pcm_hw_params_set_format_first(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_format_t *format)
3704 #endif
3705 {
3706         return snd_pcm_hw_param_set_first(pcm, params, SND_PCM_HW_PARAM_FORMAT, (unsigned int *)format, NULL);
3707 }
3708
3709 /**
3710  * \brief Restrict a configuration space to contain only its last format
3711  * \param pcm PCM handle
3712  * \param params Configuration space
3713  * \param format Returned last format
3714  * \return 0 otherwise a negative error code
3715  */
3716 #ifndef DOXYGEN
3717 int INTERNAL(snd_pcm_hw_params_set_format_last)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_format_t *format)
3718 #else
3719 int snd_pcm_hw_params_set_format_last(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_format_t *format)
3720 #endif
3721 {
3722         return snd_pcm_hw_param_set_last(pcm, params, SND_PCM_HW_PARAM_FORMAT, (unsigned int *)format, NULL);
3723 }
3724
3725 /**
3726  * \brief Restrict a configuration space to contain only a set of formats
3727  * \param pcm PCM handle
3728  * \param params Configuration space
3729  * \param mask Format mask
3730  * \return 0 otherwise a negative error code
3731  */
3732 int snd_pcm_hw_params_set_format_mask(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_format_mask_t *mask)
3733 {
3734         return snd_pcm_hw_param_set_mask(pcm, params, SND_TRY, SND_PCM_HW_PARAM_FORMAT, (snd_mask_t *) mask);
3735 }
3736
3737 /**
3738  * \brief Get format mask from a configuration space
3739  * \param params Configuration space
3740  * \param mask Returned Format mask
3741  */
3742 void snd_pcm_hw_params_get_format_mask(snd_pcm_hw_params_t *params, snd_pcm_format_mask_t *mask)
3743 {
3744         snd_pcm_format_mask_copy(mask, snd_pcm_hw_param_get_mask(params, SND_PCM_HW_PARAM_FORMAT));
3745 }
3746
3747
3748 /**
3749  * \brief Extract subformat from a configuration space
3750  * \param params Configuration space
3751  * \param subformat Returned subformat value
3752  * \return subformat otherwise a negative error code if the configuration space does not contain a single value
3753  */
3754 #ifndef DOXYGEN
3755 int INTERNAL(snd_pcm_hw_params_get_subformat)(const snd_pcm_hw_params_t *params, snd_pcm_subformat_t *subformat)
3756 #else
3757 int snd_pcm_hw_params_get_subformat(const snd_pcm_hw_params_t *params, snd_pcm_subformat_t *subformat)
3758 #endif
3759 {
3760         return snd_pcm_hw_param_get(params, SND_PCM_HW_PARAM_SUBFORMAT, subformat, NULL);
3761 }
3762
3763 /**
3764  * \brief Verify if a subformat is available inside a configuration space for a PCM
3765  * \param pcm PCM handle
3766  * \param params Configuration space
3767  * \param subformat subformat value
3768  * \return 0 if available a negative error code otherwise
3769  */
3770 int snd_pcm_hw_params_test_subformat(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_subformat_t subformat)
3771 {
3772         return snd_pcm_hw_param_set(pcm, params, SND_TEST, SND_PCM_HW_PARAM_SUBFORMAT, subformat, 0);
3773 }
3774
3775 /**
3776  * \brief Restrict a configuration space to contain only one subformat
3777  * \param pcm PCM handle
3778  * \param params Configuration space
3779  * \param subformat subformat value
3780  * \return 0 otherwise a negative error code if configuration space would become empty
3781  */
3782 int snd_pcm_hw_params_set_subformat(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_subformat_t subformat)
3783 {
3784         return snd_pcm_hw_param_set(pcm, params, SND_TRY, SND_PCM_HW_PARAM_SUBFORMAT, subformat, 0);
3785 }
3786
3787 /**
3788  * \brief Restrict a configuration space to contain only its first subformat
3789  * \param pcm PCM handle
3790  * \param params Configuration space
3791  * \param subformat Returned subformat
3792  * \return 0 otherwise a negative error code
3793  */
3794 #ifndef DOXYGEN
3795 int INTERNAL(snd_pcm_hw_params_set_subformat_first)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_subformat_t *subformat)
3796 #else
3797 int snd_pcm_hw_params_set_subformat_first(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_subformat_t *subformat)
3798 #endif
3799 {
3800         return snd_pcm_hw_param_set_first(pcm, params, SND_PCM_HW_PARAM_SUBFORMAT, subformat, NULL);
3801 }
3802
3803 /**
3804  * \brief Restrict a configuration space to contain only its last subformat
3805  * \param pcm PCM handle
3806  * \param params Configuration space
3807  * \param subformat Returned subformat
3808  * \return 0 otherwise a negative error code
3809  */
3810 #ifndef DOXYGEN
3811 int INTERNAL(snd_pcm_hw_params_set_subformat_last)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_subformat_t *subformat)
3812 #else
3813 int snd_pcm_hw_params_set_subformat_last(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_subformat_t *subformat)
3814 #endif
3815 {
3816         return snd_pcm_hw_param_set_last(pcm, params, SND_PCM_HW_PARAM_SUBFORMAT, subformat, NULL);
3817 }
3818
3819 /**
3820  * \brief Restrict a configuration space to contain only a set of subformats
3821  * \param pcm PCM handle
3822  * \param params Configuration space
3823  * \param mask Subformat mask
3824  * \return 0 otherwise a negative error code
3825  */
3826 int snd_pcm_hw_params_set_subformat_mask(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_subformat_mask_t *mask)
3827 {
3828         return snd_pcm_hw_param_set_mask(pcm, params, SND_TRY, SND_PCM_HW_PARAM_SUBFORMAT, (snd_mask_t *) mask);
3829 }
3830
3831 /**
3832  * \brief Get subformat mask from a configuration space
3833  * \param params Configuration space
3834  * \param mask Returned Subformat mask
3835  */
3836 void snd_pcm_hw_params_get_subformat_mask(snd_pcm_hw_params_t *params, snd_pcm_subformat_mask_t *mask)
3837 {
3838         snd_pcm_subformat_mask_copy(mask, snd_pcm_hw_param_get_mask(params, SND_PCM_HW_PARAM_SUBFORMAT));
3839 }
3840
3841
3842 /**
3843  * \brief Extract channels from a configuration space
3844  * \param params Configuration space
3845  * \param val Returned channels count
3846  * \return 0 otherwise a negative error code if the configuration space does not contain a single value
3847  */
3848 #ifndef DOXYGEN
3849 int INTERNAL(snd_pcm_hw_params_get_channels)(const snd_pcm_hw_params_t *params, unsigned int *val)
3850 #else
3851 int snd_pcm_hw_params_get_channels(const snd_pcm_hw_params_t *params, unsigned int *val)
3852 #endif
3853 {
3854         return snd_pcm_hw_param_get(params, SND_PCM_HW_PARAM_CHANNELS, val, NULL);
3855 }
3856
3857 /**
3858  * \brief Extract minimum channels count from a configuration space
3859  * \param params Configuration space
3860  * \param val minimum channels count
3861  * \return 0 otherwise a negative error code
3862  */
3863 #ifndef DOXYGEN
3864 int INTERNAL(snd_pcm_hw_params_get_channels_min)(const snd_pcm_hw_params_t *params, unsigned int *val)
3865 #else
3866 int snd_pcm_hw_params_get_channels_min(const snd_pcm_hw_params_t *params, unsigned int *val)
3867 #endif
3868 {
3869         return snd_pcm_hw_param_get_min(params, SND_PCM_HW_PARAM_CHANNELS, val, NULL);
3870 }
3871
3872 /**
3873  * \brief Extract maximum channels count from a configuration space
3874  * \param params Configuration space
3875  * \param val maximum channels count
3876  * \return 0 otherwise a negative error code
3877  */
3878 #ifndef DOXYGEN
3879 int INTERNAL(snd_pcm_hw_params_get_channels_max)(const snd_pcm_hw_params_t *params, unsigned int *val)
3880 #else
3881 int snd_pcm_hw_params_get_channels_max(const snd_pcm_hw_params_t *params, unsigned int *val)
3882 #endif
3883 {
3884         return snd_pcm_hw_param_get_max(params, SND_PCM_HW_PARAM_CHANNELS, val, NULL);
3885 }
3886
3887 /**
3888  * \brief Verify if a channels count is available inside a configuration space for a PCM
3889  * \param pcm PCM handle
3890  * \param params Configuration space
3891  * \param val channels count
3892  * \return 0 if available a negative error code otherwise
3893  */
3894 int snd_pcm_hw_params_test_channels(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int val)
3895 {
3896         return snd_pcm_hw_param_set(pcm, params, SND_TEST, SND_PCM_HW_PARAM_CHANNELS, val, 0);
3897 }
3898
3899 /**
3900  * \brief Restrict a configuration space to contain only one channels count
3901  * \param pcm PCM handle
3902  * \param params Configuration space
3903  * \param val channels count
3904  * \return 0 otherwise a negative error code if configuration space would become empty
3905  */
3906 int snd_pcm_hw_params_set_channels(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int val)
3907 {
3908         return snd_pcm_hw_param_set(pcm, params, SND_TRY, SND_PCM_HW_PARAM_CHANNELS, val, 0);
3909 }
3910
3911 /**
3912  * \brief Restrict a configuration space with a minimum channels count
3913  * \param pcm PCM handle
3914  * \param params Configuration space
3915  * \param val minimum channels count (on return filled with actual minimum)
3916  * \return 0 otherwise a negative error code if configuration space would become empty
3917  */
3918 int snd_pcm_hw_params_set_channels_min(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val)
3919 {
3920         return snd_pcm_hw_param_set_min(pcm, params, SND_TRY, SND_PCM_HW_PARAM_CHANNELS, val, NULL);
3921 }
3922
3923 /**
3924  * \brief Restrict a configuration space with a maximum channels count
3925  * \param pcm PCM handle
3926  * \param params Configuration space
3927  * \param val maximum channels count (on return filled with actual maximum)
3928  * \return 0 otherwise a negative error code if configuration space would become empty
3929  */
3930 int snd_pcm_hw_params_set_channels_max(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val)
3931 {
3932         return snd_pcm_hw_param_set_max(pcm, params, SND_TRY, SND_PCM_HW_PARAM_CHANNELS, val, NULL);
3933 }
3934
3935 /**
3936  * \brief Restrict a configuration space to have channels counts in a given range
3937  * \param pcm PCM handle
3938  * \param params Configuration space
3939  * \param min minimum channels count (on return filled with actual minimum)
3940  * \param max maximum channels count (on return filled with actual maximum)
3941  * \return 0 otherwise a negative error code if configuration space would become empty
3942  */
3943 int snd_pcm_hw_params_set_channels_minmax(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *min, unsigned int *max)
3944 {
3945         return snd_pcm_hw_param_set_minmax(pcm, params, SND_TRY, SND_PCM_HW_PARAM_CHANNELS, min, NULL, max, NULL);
3946 }
3947
3948 /**
3949  * \brief Restrict a configuration space to have channels count nearest to a target
3950  * \param pcm PCM handle
3951  * \param params Configuration space
3952  * \param val target channels count, returned chosen channels count
3953  * \return 0 otherwise a negative error code if configuration space is empty
3954  */
3955 #ifndef DOXYGEN
3956 int INTERNAL(snd_pcm_hw_params_set_channels_near)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val)
3957 #else
3958 int snd_pcm_hw_params_set_channels_near(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val)
3959 #endif
3960 {
3961         return snd_pcm_hw_param_set_near(pcm, params, SND_PCM_HW_PARAM_CHANNELS, val, NULL);
3962 }
3963
3964 /**
3965  * \brief Restrict a configuration space to contain only its minimum channels count
3966  * \param pcm PCM handle
3967  * \param params Configuration space
3968  * \param val minimum channels count
3969  * \return 0 otherwise a negative error code
3970  */
3971 #ifndef DOXYGEN
3972 int INTERNAL(snd_pcm_hw_params_set_channels_first)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val)
3973 #else
3974 int snd_pcm_hw_params_set_channels_first(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val)
3975 #endif
3976 {
3977         return snd_pcm_hw_param_set_first(pcm, params, SND_PCM_HW_PARAM_CHANNELS, val, NULL);
3978 }
3979
3980 /**
3981  * \brief Restrict a configuration space to contain only its maximum channels count
3982  * \param pcm PCM handle
3983  * \param params Configuration space
3984  * \param val maximum channels count
3985  * \return 0 otherwise a negative error code
3986  */
3987 #ifndef DOXYGEN
3988 int INTERNAL(snd_pcm_hw_params_set_channels_last)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val)
3989 #else
3990 int snd_pcm_hw_params_set_channels_last(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val)
3991 #endif
3992 {
3993         return snd_pcm_hw_param_set_last(pcm, params, SND_PCM_HW_PARAM_CHANNELS, val, NULL);
3994 }
3995
3996
3997 /**
3998  * \brief Extract rate from a configuration space
3999  * \param params Configuration space
4000  * \param val Returned approximate rate
4001  * \param dir Sub unit direction
4002  * \return 0 otherwise a negative error code if the configuration space does not contain a single value
4003  *
4004  * Actual exact value is <,=,> the approximate one following dir (-1, 0, 1)
4005  */
4006 #ifndef DOXYGEN
4007 int INTERNAL(snd_pcm_hw_params_get_rate)(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4008 #else
4009 int snd_pcm_hw_params_get_rate(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4010 #endif
4011 {
4012         return snd_pcm_hw_param_get(params, SND_PCM_HW_PARAM_RATE, val, dir);
4013 }
4014
4015 /**
4016  * \brief Extract minimum rate from a configuration space
4017  * \param params Configuration space
4018  * \param val Returned approximate minimum rate
4019  * \param dir Sub unit direction
4020  * \return 0 otherwise a negative error code
4021  *
4022  * Exact value is <,=,> the returned one following dir (-1,0,1)
4023  */
4024 #ifndef DOXYGEN
4025 int INTERNAL(snd_pcm_hw_params_get_rate_min)(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4026 #else
4027 int snd_pcm_hw_params_get_rate_min(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4028 #endif
4029 {
4030         return snd_pcm_hw_param_get_min(params, SND_PCM_HW_PARAM_RATE, val, dir);
4031 }
4032
4033 /**
4034  * \brief Extract maximum rate from a configuration space
4035  * \param params Configuration space
4036  * \param val Returned approximate maximum rate
4037  * \param dir Sub unit direction
4038  * \return 0 otherwise a negative error code
4039  *
4040  * Exact value is <,=,> the returned one following dir (-1,0,1)
4041  */
4042 #ifndef DOXYGEN
4043 int INTERNAL(snd_pcm_hw_params_get_rate_max)(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4044 #else
4045 int snd_pcm_hw_params_get_rate_max(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4046 #endif
4047 {
4048         return snd_pcm_hw_param_get_max(params, SND_PCM_HW_PARAM_RATE, val, dir);
4049 }
4050
4051 /**
4052  * \brief Verify if a rate is available inside a configuration space for a PCM
4053  * \param pcm PCM handle
4054  * \param params Configuration space
4055  * \param val approximate rate
4056  * \param dir Sub unit direction
4057  * \return 0 if available a negative error code otherwise
4058  *
4059  * Wanted exact value is <,=,> val following dir (-1,0,1)
4060  */
4061 int snd_pcm_hw_params_test_rate(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int val, int dir)
4062 {
4063         return snd_pcm_hw_param_set(pcm, params, SND_TEST, SND_PCM_HW_PARAM_RATE, val, dir);
4064 }
4065
4066 /**
4067  * \brief Restrict a configuration space to contain only one rate
4068  * \param pcm PCM handle
4069  * \param params Configuration space
4070  * \param val approximate rate
4071  * \param dir Sub unit direction
4072  * \return 0 otherwise a negative error code if configuration space would become empty
4073  *
4074  * Wanted exact value is <,=,> val following dir (-1,0,1)
4075  */
4076 int snd_pcm_hw_params_set_rate(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int val, int dir)
4077 {
4078         return snd_pcm_hw_param_set(pcm, params, SND_TRY, SND_PCM_HW_PARAM_RATE, val, dir);
4079 }
4080
4081 /**
4082  * \brief Restrict a configuration space with a minimum rate
4083  * \param pcm PCM handle
4084  * \param params Configuration space
4085  * \param val approximate minimum rate (on return filled with actual minimum)
4086  * \param dir Sub unit direction (on return filled with actual direction)
4087  * \return 0 otherwise a negative error code if configuration space would become empty
4088  *
4089  * Wanted/actual exact minimum is <,=,> val following dir (-1,0,1)
4090  */
4091 int snd_pcm_hw_params_set_rate_min(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4092 {
4093         return snd_pcm_hw_param_set_min(pcm, params, SND_TRY, SND_PCM_HW_PARAM_RATE, val, dir);
4094 }
4095
4096 /**
4097  * \brief Restrict a configuration space with a maximum rate
4098  * \param pcm PCM handle
4099  * \param params Configuration space
4100  * \param val approximate maximum rate (on return filled with actual maximum)
4101  * \param dir Sub unit direction (on return filled with actual direction)
4102  * \return 0 otherwise a negative error code if configuration space would become empty
4103  *
4104  * Wanted/actual exact maximum is <,=,> val following dir (-1,0,1)
4105  */
4106 int snd_pcm_hw_params_set_rate_max(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4107 {
4108         return snd_pcm_hw_param_set_max(pcm, params, SND_TRY, SND_PCM_HW_PARAM_RATE, val, dir);
4109 }
4110
4111 /**
4112  * \brief Restrict a configuration space to have rates in a given range
4113  * \param pcm PCM handle
4114  * \param params Configuration space
4115  * \param min approximate minimum rate (on return filled with actual minimum)
4116  * \param mindir Sub unit direction for minimum (on return filled with actual direction)
4117  * \param max approximate maximum rate (on return filled with actual maximum)
4118  * \param maxdir Sub unit direction for maximum (on return filled with actual direction)
4119  * \return 0 otherwise a negative error code if configuration space would become empty
4120  *
4121  * Wanted/actual exact min/max is <,=,> val following dir (-1,0,1)
4122  */
4123 int snd_pcm_hw_params_set_rate_minmax(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *min, int *mindir, unsigned int *max, int *maxdir)
4124 {
4125         return snd_pcm_hw_param_set_minmax(pcm, params, SND_TRY, SND_PCM_HW_PARAM_RATE, min, mindir, max, maxdir);
4126 }
4127
4128 /**
4129  * \brief Restrict a configuration space to have rate nearest to a target
4130  * \param pcm PCM handle
4131  * \param params Configuration space
4132  * \param val approximate target rate / returned approximate set rate
4133  * \param dir Sub unit direction
4134  * \return 0 otherwise a negative error code if configuration space is empty
4135  *
4136  * target/chosen exact value is <,=,> val following dir (-1,0,1)
4137  */
4138 #ifndef DOXYGEN
4139 int INTERNAL(snd_pcm_hw_params_set_rate_near)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4140 #else
4141 int snd_pcm_hw_params_set_rate_near(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4142 #endif
4143 {
4144         return snd_pcm_hw_param_set_near(pcm, params, SND_PCM_HW_PARAM_RATE, val, dir);
4145 }
4146
4147 /**
4148  * \brief Restrict a configuration space to contain only its minimum rate
4149  * \param pcm PCM handle
4150  * \param params Configuration space
4151  * \param val Returned minimum approximate rate
4152  * \param dir Sub unit direction
4153  * \return 0 otherwise a negative error code
4154  *
4155  * Actual exact value is <,=,> the approximate one following dir (-1, 0, 1)
4156  */
4157 #ifndef DOXYGEN
4158 int INTERNAL(snd_pcm_hw_params_set_rate_first)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4159 #else
4160 int snd_pcm_hw_params_set_rate_first(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4161 #endif
4162 {
4163         return snd_pcm_hw_param_set_first(pcm, params, SND_PCM_HW_PARAM_RATE, val, dir);
4164 }
4165
4166 /**
4167  * \brief Restrict a configuration space to contain only its maximum rate
4168  * \param pcm PCM handle
4169  * \param params Configuration space
4170  * \param val Returned maximum approximate rate
4171  * \param dir Sub unit direction
4172  * \return 0 otherwise a negative error code
4173  *
4174  * Actual exact value is <,=,> the approximate one following dir (-1, 0, 1)
4175  */
4176 #ifndef DOXYGEN
4177 int INTERNAL(snd_pcm_hw_params_set_rate_last)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4178 #else
4179 int snd_pcm_hw_params_set_rate_last(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4180 #endif
4181 {
4182         return snd_pcm_hw_param_set_last(pcm, params, SND_PCM_HW_PARAM_RATE, val, dir);
4183 }
4184
4185 /**
4186  * \brief Restrict a configuration space to contain only real hardware rates
4187  * \param pcm PCM handle
4188  * \param params Configuration space
4189  * \param val 0 = disable, 1 = enable (default) rate resampling
4190  * \return 0 otherwise a negative error code
4191  */
4192 int snd_pcm_hw_params_set_rate_resample(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int val)
4193 {
4194         assert(pcm && params);
4195         if (!val)
4196                 params->flags |= SND_PCM_HW_PARAMS_NORESAMPLE;
4197         else
4198                 params->flags &= ~SND_PCM_HW_PARAMS_NORESAMPLE;
4199         params->rmask = ~0;
4200         return snd_pcm_hw_refine(pcm, params);
4201 }
4202
4203 /**
4204  * \brief Extract resample state from a configuration space
4205  * \param pcm PCM handle
4206  * \param params Configuration space
4207  * \param val 0 = disable, 1 = enable rate resampling
4208  * \return 0 otherwise a negative error code
4209  */
4210 int snd_pcm_hw_params_get_rate_resample(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val)
4211 {
4212         assert(pcm && params && val);
4213         *val = params->flags & SND_PCM_HW_PARAMS_NORESAMPLE ? 0 : 1;
4214         return 0;
4215 }
4216
4217 /**
4218  * \brief Restrict a configuration space to allow the buffer to be accessible from outside
4219  * \param pcm PCM handle
4220  * \param params Configuration space
4221  * \param val 0 = disable, 1 = enable (default) exporting buffer
4222  * \return 0 otherwise a negative error code
4223  */
4224 int snd_pcm_hw_params_set_export_buffer(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int val)
4225 {
4226         assert(pcm && params);
4227         if (val)
4228                 params->flags |= SND_PCM_HW_PARAMS_EXPORT_BUFFER;
4229         else
4230                 params->flags &= ~SND_PCM_HW_PARAMS_EXPORT_BUFFER;
4231         params->rmask = ~0;
4232         return snd_pcm_hw_refine(pcm, params);
4233 }
4234
4235 /**
4236  * \brief Extract buffer accessibility from a configuration space
4237  * \param pcm PCM handle
4238  * \param params Configuration space
4239  * \param val 0 = disable, 1 = enable exporting buffer
4240  * \return 0 otherwise a negative error code
4241  */
4242 int snd_pcm_hw_params_get_export_buffer(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val)
4243 {
4244         assert(pcm && params && val);
4245         *val = params->flags & SND_PCM_HW_PARAMS_EXPORT_BUFFER ? 1 : 0;
4246         return 0;
4247 }
4248
4249 /**
4250  * \brief Restrict a configuration space to settings without period wakeups
4251  * \param pcm PCM handle
4252  * \param params Configuration space
4253  * \param val 0 = disable, 1 = enable (default) period wakeup
4254  * \return Zero on success, otherwise a negative error code.
4255  *
4256  * This function must be called only on devices where non-blocking mode is
4257  * enabled.
4258  *
4259  * To check whether the hardware does support disabling period wakeups, call
4260  * #snd_pcm_hw_params_can_disable_period_wakeup(). If the hardware does not
4261  * support this mode, standard period wakeups will be generated.
4262  *
4263  * Even with disabled period wakeups, the period size/time/count parameters
4264  * are valid; it is suggested to use #snd_pcm_hw_params_set_period_size_last().
4265  *
4266  * When period wakeups are disabled, the application must not use any functions
4267  * that could block on this device. The use of poll should be limited to error
4268  * cases. The application needs to use an external event or a timer to
4269  * check the state of the ring buffer and refill it apropriately.
4270  */
4271 int snd_pcm_hw_params_set_period_wakeup(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int val)
4272 {
4273         assert(pcm && params);
4274
4275         if (!val) {
4276                 if (!(pcm->mode & SND_PCM_NONBLOCK))
4277                         return -EINVAL;
4278                 params->flags |= SND_PCM_HW_PARAMS_NO_PERIOD_WAKEUP;
4279         } else
4280                 params->flags &= ~SND_PCM_HW_PARAMS_NO_PERIOD_WAKEUP;
4281         params->rmask = ~0;
4282
4283         return snd_pcm_hw_refine(pcm, params);
4284 }
4285
4286 /**
4287  * \brief Extract period wakeup flag from a configuration space
4288  * \param pcm PCM handle
4289  * \param params Configuration space
4290  * \param val 0 = disabled, 1 = enabled period wakeups
4291  * \return Zero on success, otherwise a negative error code.
4292  */
4293 int snd_pcm_hw_params_get_period_wakeup(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val)
4294 {
4295         assert(pcm && params && val);
4296         *val = params->flags & SND_PCM_HW_PARAMS_NO_PERIOD_WAKEUP ? 0 : 1;
4297         return 0;
4298 }
4299
4300 /**
4301  * \brief Extract period time from a configuration space
4302  * \param params Configuration space
4303  * \param val Returned approximate period duration in us
4304  * \param dir Sub unit direction
4305  * \return 0 otherwise a negative error code if the configuration space does not contain a single value
4306  *
4307  * Actual exact value is <,=,> the approximate one following dir (-1, 0, 1)
4308  */
4309 #ifndef DOXYGEN
4310 int INTERNAL(snd_pcm_hw_params_get_period_time)(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4311 #else
4312 int snd_pcm_hw_params_get_period_time(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4313 #endif
4314 {
4315         return snd_pcm_hw_param_get(params, SND_PCM_HW_PARAM_PERIOD_TIME, val, dir);
4316 }
4317
4318 /**
4319  * \brief Extract minimum period time from a configuration space
4320  * \param params Configuration space
4321  * \param val approximate minimum period duration in us
4322  * \param dir Sub unit direction
4323  * \return 0 otherwise a negative error code
4324  *
4325  * Exact value is <,=,> the returned one following dir (-1,0,1)
4326  */
4327 #ifndef DOXYGEN
4328 int INTERNAL(snd_pcm_hw_params_get_period_time_min)(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4329 #else
4330 int snd_pcm_hw_params_get_period_time_min(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4331 #endif
4332 {
4333         return snd_pcm_hw_param_get_min(params, SND_PCM_HW_PARAM_PERIOD_TIME, val, dir);
4334 }
4335
4336 /**
4337  * \brief Extract maximum period time from a configuration space
4338  * \param params Configuration space
4339  * \param val approximate maximum period duration in us
4340  * \param dir Sub unit direction
4341  * \return 0 otherwise a negative error code
4342  *
4343  * Exact value is <,=,> the returned one following dir (-1,0,1)
4344  */
4345 #ifndef DOXYGEN
4346 int INTERNAL(snd_pcm_hw_params_get_period_time_max)(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4347 #else
4348 int snd_pcm_hw_params_get_period_time_max(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4349 #endif
4350 {
4351         return snd_pcm_hw_param_get_max(params, SND_PCM_HW_PARAM_PERIOD_TIME, val, dir);
4352 }
4353
4354 /**
4355  * \brief Verify if a period time is available inside a configuration space for a PCM
4356  * \param pcm PCM handle
4357  * \param params Configuration space
4358  * \param val approximate period duration in us
4359  * \param dir Sub unit direction
4360  * \return 0 if available a negative error code otherwise
4361  *
4362  * Wanted exact value is <,=,> val following dir (-1,0,1)
4363  */
4364 int snd_pcm_hw_params_test_period_time(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int val, int dir)
4365 {
4366         return snd_pcm_hw_param_set(pcm, params, SND_TEST, SND_PCM_HW_PARAM_PERIOD_TIME, val, dir);
4367 }
4368
4369 /**
4370  * \brief Restrict a configuration space to contain only one period time
4371  * \param pcm PCM handle
4372  * \param params Configuration space
4373  * \param val approximate period duration in us
4374  * \param dir Sub unit direction
4375  * \return 0 otherwise a negative error code if configuration space would become empty
4376  *
4377  * Wanted exact value is <,=,> val following dir (-1,0,1)
4378  */
4379 int snd_pcm_hw_params_set_period_time(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int val, int dir)
4380 {
4381         return snd_pcm_hw_param_set(pcm, params, SND_TRY, SND_PCM_HW_PARAM_PERIOD_TIME, val, dir);
4382 }
4383
4384
4385 /**
4386  * \brief Restrict a configuration space with a minimum period time
4387  * \param pcm PCM handle
4388  * \param params Configuration space
4389  * \param val approximate minimum period duration in us (on return filled with actual minimum)
4390  * \param dir Sub unit direction (on return filled with actual direction)
4391  * \return 0 otherwise a negative error code if configuration space would become empty
4392  *
4393  * Wanted/actual exact minimum is <,=,> val following dir (-1,0,1)
4394  */
4395 int snd_pcm_hw_params_set_period_time_min(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4396 {
4397         return snd_pcm_hw_param_set_min(pcm, params, SND_TRY, SND_PCM_HW_PARAM_PERIOD_TIME, val, dir);
4398 }
4399
4400 /**
4401  * \brief Restrict a configuration space with a maximum period time
4402  * \param pcm PCM handle
4403  * \param params Configuration space
4404  * \param val approximate maximum period duration in us (on return filled with actual maximum)
4405  * \param dir Sub unit direction (on return filled with actual direction)
4406  * \return 0 otherwise a negative error code if configuration space would become empty
4407  *
4408  * Wanted/actual exact maximum is <,=,> val following dir (-1,0,1)
4409  */
4410 int snd_pcm_hw_params_set_period_time_max(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4411 {
4412         return snd_pcm_hw_param_set_max(pcm, params, SND_TRY, SND_PCM_HW_PARAM_PERIOD_TIME, val, dir);
4413 }
4414
4415 /**
4416  * \brief Restrict a configuration space to have period times in a given range
4417  * \param pcm PCM handle
4418  * \param params Configuration space
4419  * \param min approximate minimum period duration in us (on return filled with actual minimum)
4420  * \param mindir Sub unit direction for minimum (on return filled with actual direction)
4421  * \param max approximate maximum period duration in us (on return filled with actual maximum)
4422  * \param maxdir Sub unit direction for maximum (on return filled with actual direction)
4423  * \return 0 otherwise a negative error code if configuration space would become empty
4424  *
4425  * Wanted/actual exact min/max is <,=,> val following dir (-1,0,1)
4426  */
4427 int snd_pcm_hw_params_set_period_time_minmax(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *min, int *mindir, unsigned int *max, int *maxdir)
4428 {
4429         return snd_pcm_hw_param_set_minmax(pcm, params, SND_TRY, SND_PCM_HW_PARAM_PERIOD_TIME, min, mindir, max, maxdir);
4430 }
4431
4432 /**
4433  * \brief Restrict a configuration space to have period time nearest to a target
4434  * \param pcm PCM handle
4435  * \param params Configuration space
4436  * \param val approximate target period duration in us / returned chosen approximate target period duration
4437  * \param dir Sub unit direction
4438  * \return 0 otherwise a negative error code if configuration space is empty
4439  *
4440  * target/chosen exact value is <,=,> val following dir (-1,0,1)
4441  */
4442 #ifndef DOXYGEN
4443 int INTERNAL(snd_pcm_hw_params_set_period_time_near)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4444 #else
4445 int snd_pcm_hw_params_set_period_time_near(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4446 #endif
4447 {
4448         return snd_pcm_hw_param_set_near(pcm, params, SND_PCM_HW_PARAM_PERIOD_TIME, val, dir);
4449 }
4450
4451 /**
4452  * \brief Restrict a configuration space to contain only its minimum period time
4453  * \param pcm PCM handle
4454  * \param params Configuration space
4455  * \param val Returned approximate period duration in us
4456  * \param dir Sub unit direction
4457  * \return 0 otherwise a negative error code
4458  *
4459  * Actual exact value is <,=,> the approximate one following dir (-1, 0, 1)
4460  */
4461 #ifndef DOXYGEN
4462 int INTERNAL(snd_pcm_hw_params_set_period_time_first)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4463 #else
4464 int snd_pcm_hw_params_set_period_time_first(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4465 #endif
4466 {
4467         return snd_pcm_hw_param_set_first(pcm, params, SND_PCM_HW_PARAM_PERIOD_TIME, val, dir);
4468 }
4469
4470 /**
4471  * \brief Restrict a configuration space to contain only its maximum period time
4472  * \param pcm PCM handle
4473  * \param params Configuration space
4474  * \param val Returned maximum approximate period time
4475  * \param dir Sub unit direction
4476  * \return approximate period duration in us
4477  */
4478 #ifndef DOXYGEN
4479 int INTERNAL(snd_pcm_hw_params_set_period_time_last)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4480 #else
4481 int snd_pcm_hw_params_set_period_time_last(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4482 #endif
4483 {
4484         return snd_pcm_hw_param_set_last(pcm, params, SND_PCM_HW_PARAM_PERIOD_TIME, val, dir);
4485 }
4486
4487
4488 /**
4489  * \brief Extract period size from a configuration space
4490  * \param params Configuration space
4491  * \param val Returned approximate period size in frames
4492  * \param dir Sub unit direction
4493  * \return 0 otherwise a negative error code if the configuration space does not contain a single value
4494  *
4495  * Actual exact value is <,=,> the approximate one following dir (-1, 0, 1)
4496  */
4497 #ifndef DOXYGEN
4498 int INTERNAL(snd_pcm_hw_params_get_period_size)(const snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val, int *dir)
4499 #else
4500 int snd_pcm_hw_params_get_period_size(const snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val, int *dir)
4501 #endif
4502 {
4503         unsigned int _val;
4504         int err = snd_pcm_hw_param_get(params, SND_PCM_HW_PARAM_PERIOD_SIZE, &_val, dir);
4505         if (err >= 0)
4506                 *val = _val;
4507         return err;
4508 }
4509
4510 /**
4511  * \brief Extract minimum period size from a configuration space
4512  * \param params Configuration space
4513  * \param val approximate minimum period size in frames
4514  * \param dir Sub unit direction
4515  * \return 0 otherwise a negative error code
4516  *
4517  * Exact value is <,=,> the returned one following dir (-1,0,1)
4518  */
4519 #ifndef DOXYGEN
4520 int INTERNAL(snd_pcm_hw_params_get_period_size_min)(const snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val, int *dir)
4521 #else
4522 int snd_pcm_hw_params_get_period_size_min(const snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val, int *dir)
4523 #endif
4524 {
4525         unsigned int _val = *val;
4526         int err = snd_pcm_hw_param_get_min(params, SND_PCM_HW_PARAM_PERIOD_SIZE, &_val, dir);
4527         if (err >= 0)
4528                 *val = _val;
4529         return err;
4530 }
4531
4532 /**
4533  * \brief Extract maximum period size from a configuration space
4534  * \param params Configuration space
4535  * \param val approximate minimum period size in frames
4536  * \param dir Sub unit direction
4537  * \return 0 otherwise a negative error code
4538  *
4539  * Exact value is <,=,> the returned one following dir (-1,0,1)
4540  */
4541 #ifndef DOXYGEN
4542 int INTERNAL(snd_pcm_hw_params_get_period_size_max)(const snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val, int *dir)
4543 #else
4544 int snd_pcm_hw_params_get_period_size_max(const snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val, int *dir)
4545 #endif
4546 {
4547         unsigned int _val = *val;
4548         int err = snd_pcm_hw_param_get_max(params, SND_PCM_HW_PARAM_PERIOD_SIZE, &_val, dir);
4549         if (err >= 0)
4550                 *val = _val;
4551         return err;
4552 }
4553
4554 /**
4555  * \brief Verify if a period size is available inside a configuration space for a PCM
4556  * \param pcm PCM handle
4557  * \param params Configuration space
4558  * \param val approximate period size in frames
4559  * \param dir Sub unit direction
4560  * \return 0 if available a negative error code otherwise
4561  *
4562  * Wanted exact value is <,=,> val following dir (-1,0,1)
4563  */
4564 int snd_pcm_hw_params_test_period_size(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t val, int dir)
4565 {
4566         return snd_pcm_hw_param_set(pcm, params, SND_TEST, SND_PCM_HW_PARAM_PERIOD_SIZE, val, dir);
4567 }
4568
4569 /**
4570  * \brief Restrict a configuration space to contain only one period size
4571  * \param pcm PCM handle
4572  * \param params Configuration space
4573  * \param val approximate period size in frames
4574  * \param dir Sub unit direction
4575  * \return 0 otherwise a negative error code if configuration space would become empty
4576  *
4577  * Wanted exact value is <,=,> val following dir (-1,0,1)
4578  */
4579 int snd_pcm_hw_params_set_period_size(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t val, int dir)
4580 {
4581         return snd_pcm_hw_param_set(pcm, params, SND_TRY, SND_PCM_HW_PARAM_PERIOD_SIZE, val, dir);
4582 }
4583
4584 /**
4585  * \brief Restrict a configuration space with a minimum period size
4586  * \param pcm PCM handle
4587  * \param params Configuration space
4588  * \param val approximate minimum period size in frames (on return filled with actual minimum)
4589  * \param dir Sub unit direction (on return filled with actual direction)
4590  * \return 0 otherwise a negative error code if configuration space would become empty
4591  *
4592  * Wanted/actual exact minimum is <,=,> val following dir (-1,0,1)
4593  */
4594 int snd_pcm_hw_params_set_period_size_min(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val, int *dir)
4595 {
4596         unsigned int _val = *val;
4597         int err = snd_pcm_hw_param_set_min(pcm, params, SND_TRY, SND_PCM_HW_PARAM_PERIOD_SIZE, &_val, dir);
4598         if (err >= 0)
4599                 *val = _val;
4600         return err;
4601 }
4602
4603 /**
4604  * \brief Restrict a configuration space with a maximum period size
4605  * \param pcm PCM handle
4606  * \param params Configuration space
4607  * \param val approximate maximum period size in frames (on return filled with actual maximum)
4608  * \param dir Sub unit direction (on return filled with actual direction)
4609  * \return 0 otherwise a negative error code if configuration space would become empty
4610  *
4611  * Wanted/actual exact minimum is <,=,> val following dir (-1,0,1)
4612  */
4613 int snd_pcm_hw_params_set_period_size_max(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val, int *dir)
4614 {
4615         unsigned int _val = *val;
4616         int err = snd_pcm_hw_param_set_max(pcm, params, SND_TRY, SND_PCM_HW_PARAM_PERIOD_SIZE, &_val, dir);
4617         if (err >= 0)
4618                 *val = _val;
4619         return err;
4620 }
4621
4622 /**
4623  * \brief Restrict a configuration space to have period sizes in a given range
4624  * \param pcm PCM handle
4625  * \param params Configuration space
4626  * \param min approximate minimum period size in frames (on return filled with actual minimum)
4627  * \param mindir Sub unit direction for minimum (on return filled with actual direction)
4628  * \param max approximate maximum period size in frames (on return filled with actual maximum)
4629  * \param maxdir Sub unit direction for maximum (on return filled with actual direction)
4630  * \return 0 otherwise a negative error code if configuration space would become empty
4631  *
4632  * Wanted/actual exact min/max is <,=,> val following dir (-1,0,1)
4633  */
4634 int snd_pcm_hw_params_set_period_size_minmax(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *min, int *mindir, snd_pcm_uframes_t *max, int *maxdir)
4635 {
4636         unsigned int _min = *min;
4637         unsigned int _max = *max;
4638         int err = snd_pcm_hw_param_set_minmax(pcm, params, SND_TRY, SND_PCM_HW_PARAM_PERIOD_SIZE, &_min, mindir, &_max, maxdir);
4639         *min = _min;
4640         *max = _max;
4641         return err;
4642 }
4643
4644 /**
4645  * \brief Restrict a configuration space to have period size nearest to a target
4646  * \param pcm PCM handle
4647  * \param params Configuration space
4648  * \param val approximate target period size in frames / returned chosen approximate target period size
4649  * \param dir Sub unit direction
4650  * \return 0 otherwise a negative error code if configuration space is empty
4651  *
4652  * target/chosen exact value is <,=,> val following dir (-1,0,1)
4653  */
4654 #ifndef DOXYGEN
4655 int INTERNAL(snd_pcm_hw_params_set_period_size_near)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val, int *dir)
4656 #else
4657 int snd_pcm_hw_params_set_period_size_near(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val, int *dir)
4658 #endif
4659 {
4660         unsigned int _val = *val;
4661         int err = snd_pcm_hw_param_set_near(pcm, params, SND_PCM_HW_PARAM_PERIOD_SIZE, &_val, dir);
4662         if (err >= 0)
4663                 *val = _val;
4664         return err;
4665 }
4666
4667 /**
4668  * \brief Restrict a configuration space to contain only its minimum period size
4669  * \param pcm PCM handle
4670  * \param params Configuration space
4671  * \param val Returned maximum approximate period size in frames
4672  * \param dir Sub unit direction
4673  * \return 0 otherwise a negative error code
4674  *
4675  * Actual exact value is <,=,> the approximate one following dir (-1, 0, 1)
4676  */
4677 #ifndef DOXYGEN
4678 int INTERNAL(snd_pcm_hw_params_set_period_size_first)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val, int *dir)
4679 #else
4680 int snd_pcm_hw_params_set_period_size_first(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val, int *dir)
4681 #endif
4682 {
4683         unsigned int _val;
4684         int err = snd_pcm_hw_param_set_first(pcm, params, SND_PCM_HW_PARAM_PERIOD_SIZE, &_val, dir);
4685         if (err >= 0)
4686                 *val = _val;
4687         return err;
4688 }
4689
4690 /**
4691  * \brief Restrict a configuration space to contain only its maximum period size
4692  * \param pcm PCM handle
4693  * \param params Configuration space
4694  * \param val Returned maximum approximate period size in frames
4695  * \param dir Sub unit direction
4696  * \return 0 otherwise a negative error code
4697  *
4698  * Actual exact value is <,=,> the approximate one following dir (-1, 0, 1)
4699  */
4700 #ifndef DOXYGEN
4701 int INTERNAL(snd_pcm_hw_params_set_period_size_last)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val, int *dir)
4702 #else
4703 int snd_pcm_hw_params_set_period_size_last(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val, int *dir)
4704 #endif
4705 {
4706         unsigned int _val;
4707         int err = snd_pcm_hw_param_set_last(pcm, params, SND_PCM_HW_PARAM_PERIOD_SIZE, &_val, dir);
4708         if (err >= 0)
4709                 *val = _val;
4710         return err;
4711 }
4712
4713 /**
4714  * \brief Restrict a configuration space to contain only integer period sizes
4715  * \param pcm PCM handle
4716  * \param params Configuration space
4717  * \return 0 otherwise a negative error code if configuration space would become empty
4718  */
4719 int snd_pcm_hw_params_set_period_size_integer(snd_pcm_t *pcm, snd_pcm_hw_params_t *params)
4720 {
4721         return snd_pcm_hw_param_set_integer(pcm, params, SND_TRY, SND_PCM_HW_PARAM_PERIOD_SIZE);
4722 }
4723
4724
4725 /**
4726  * \brief Extract periods from a configuration space
4727  * \param params Configuration space
4728  * \param val approximate periods per buffer
4729  * \param dir Sub unit direction
4730  * \return 0 otherwise a negative error code if the configuration space does not contain a single value
4731  *
4732  * Actual exact value is <,=,> the approximate one following dir (-1, 0, 1)
4733  */
4734 #ifndef DOXYGEN
4735 int INTERNAL(snd_pcm_hw_params_get_periods)(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4736 #else
4737 int snd_pcm_hw_params_get_periods(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4738 #endif
4739 {
4740         return snd_pcm_hw_param_get(params, SND_PCM_HW_PARAM_PERIODS, val, dir);
4741 }
4742
4743 /**
4744  * \brief Extract minimum periods count from a configuration space
4745  * \param params Configuration space
4746  * \param val approximate minimum periods per buffer
4747  * \param dir Sub unit direction
4748  * \return 0 otherwise a negative error code
4749  *
4750  * Exact value is <,=,> the returned one following dir (-1,0,1)
4751  */
4752 #ifndef DOXYGEN
4753 int INTERNAL(snd_pcm_hw_params_get_periods_min)(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4754 #else
4755 int snd_pcm_hw_params_get_periods_min(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4756 #endif
4757 {
4758         return snd_pcm_hw_param_get_min(params, SND_PCM_HW_PARAM_PERIODS, val, dir);
4759 }
4760
4761 /**
4762  * \brief Extract maximum periods count from a configuration space
4763  * \param params Configuration space
4764  * \param val approximate maximum periods per buffer
4765  * \param dir Sub unit direction
4766  * \return 0 otherwise a negative error code
4767  *
4768  * Exact value is <,=,> the returned one following dir (-1,0,1)
4769  */
4770 #ifndef DOXYGEN
4771 int INTERNAL(snd_pcm_hw_params_get_periods_max)(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4772 #else
4773 int snd_pcm_hw_params_get_periods_max(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4774 #endif
4775 {
4776         return snd_pcm_hw_param_get_max(params, SND_PCM_HW_PARAM_PERIODS, val, dir);
4777 }
4778
4779 /**
4780  * \brief Verify if a periods count is available inside a configuration space for a PCM
4781  * \param pcm PCM handle
4782  * \param params Configuration space
4783  * \param val approximate periods per buffer
4784  * \param dir Sub unit direction
4785  * \return 0 if available a negative error code otherwise
4786  *
4787  * Wanted exact value is <,=,> val following dir (-1,0,1)
4788  */
4789 int snd_pcm_hw_params_test_periods(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int val, int dir)
4790 {
4791         return snd_pcm_hw_param_set(pcm, params, SND_TEST, SND_PCM_HW_PARAM_PERIODS, val, dir);
4792 }
4793
4794 /**
4795  * \brief Restrict a configuration space to contain only one periods count
4796  * \param pcm PCM handle
4797  * \param params Configuration space
4798  * \param val approximate periods per buffer
4799  * \param dir Sub unit direction
4800  * \return 0 otherwise a negative error code if configuration space would become empty
4801  *
4802  * Wanted exact value is <,=,> val following dir (-1,0,1)
4803  */
4804 int snd_pcm_hw_params_set_periods(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int val, int dir)
4805 {
4806         return snd_pcm_hw_param_set(pcm, params, SND_TRY, SND_PCM_HW_PARAM_PERIODS, val, dir);
4807 }
4808
4809 /**
4810  * \brief Restrict a configuration space with a minimum periods count
4811  * \param pcm PCM handle
4812  * \param params Configuration space
4813  * \param val approximate minimum periods per buffer (on return filled with actual minimum)
4814  * \param dir Sub unit direction (on return filled with actual direction)
4815  * \return 0 otherwise a negative error code if configuration space would become empty
4816  *
4817  * Wanted/actual exact minimum is <,=,> val following dir (-1,0,1)
4818  */
4819 int snd_pcm_hw_params_set_periods_min(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4820 {
4821         return snd_pcm_hw_param_set_min(pcm, params, SND_TRY, SND_PCM_HW_PARAM_PERIODS, val, dir);
4822 }
4823
4824 /**
4825  * \brief Restrict a configuration space with a maximum periods count
4826  * \param pcm PCM handle
4827  * \param params Configuration space
4828  * \param val approximate maximum periods per buffer (on return filled with actual maximum)
4829  * \param dir Sub unit direction (on return filled with actual direction)
4830  * \return 0 otherwise a negative error code if configuration space would become empty
4831  *
4832  * Wanted/actual exact maximum is <,=,> val following dir (-1,0,1)
4833  */
4834 int snd_pcm_hw_params_set_periods_max(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4835 {
4836         return snd_pcm_hw_param_set_max(pcm, params, SND_TRY, SND_PCM_HW_PARAM_PERIODS, val, dir);
4837 }
4838
4839 /**
4840  * \brief Restrict a configuration space to have periods counts in a given range
4841  * \param pcm PCM handle
4842  * \param params Configuration space
4843  * \param min approximate minimum periods per buffer (on return filled with actual minimum)
4844  * \param mindir Sub unit direction for minimum (on return filled with actual direction)
4845  * \param max approximate maximum periods per buffer (on return filled with actual maximum)
4846  * \param maxdir Sub unit direction for maximum (on return filled with actual direction)
4847  * \return 0 otherwise a negative error code if configuration space would become empty
4848  *
4849  * Wanted/actual exact min/max is <,=,> val following dir (-1,0,1)
4850  */
4851 int snd_pcm_hw_params_set_periods_minmax(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *min, int *mindir, unsigned int *max, int *maxdir)
4852 {
4853         return snd_pcm_hw_param_set_minmax(pcm, params, SND_TRY, SND_PCM_HW_PARAM_PERIODS, min, mindir, max, maxdir);
4854 }
4855
4856 /**
4857  * \brief Restrict a configuration space to have periods count nearest to a target
4858  * \param pcm PCM handle
4859  * \param params Configuration space
4860  * \param val approximate target periods per buffer / returned chosen approximate target periods per buffer
4861  * \param dir Sub unit direction
4862  * \return 0 otherwise a negative error code if configuration space is empty
4863  *
4864  * target/chosen exact value is <,=,> val following dir (-1,0,1)
4865  */
4866 #ifndef DOXYGEN
4867 int INTERNAL(snd_pcm_hw_params_set_periods_near)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4868 #else
4869 int snd_pcm_hw_params_set_periods_near(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4870 #endif
4871 {
4872         return snd_pcm_hw_param_set_near(pcm, params, SND_PCM_HW_PARAM_PERIODS, val, dir);
4873 }
4874
4875 /**
4876  * \brief Restrict a configuration space to contain only its minimum periods count
4877  * \param pcm PCM handle
4878  * \param params Configuration space
4879  * \param val Returned approximate minimum periods per buffer
4880  * \param dir Sub unit direction
4881  * \return 0 otherwise a negative error code
4882  *
4883  * Actual exact value is <,=,> the approximate one following dir (-1, 0, 1)
4884  */
4885 #ifndef DOXYGEN
4886 int INTERNAL(snd_pcm_hw_params_set_periods_first)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4887 #else
4888 int snd_pcm_hw_params_set_periods_first(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4889 #endif
4890 {
4891         return snd_pcm_hw_param_set_first(pcm, params, SND_PCM_HW_PARAM_PERIODS, val, dir);
4892 }
4893
4894 /**
4895  * \brief Restrict a configuration space to contain only its maximum periods count
4896  * \param pcm PCM handle
4897  * \param params Configuration space
4898  * \param val Returned approximate maximum periods per buffer
4899  * \param dir Sub unit direction
4900  * \return 0 otherwise a negative error code
4901  *
4902  * Actual exact value is <,=,> the approximate one following dir (-1, 0, 1)
4903  */
4904 #ifndef DOXYGEN
4905 int INTERNAL(snd_pcm_hw_params_set_periods_last)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4906 #else
4907 int snd_pcm_hw_params_set_periods_last(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4908 #endif
4909 {
4910         return snd_pcm_hw_param_set_last(pcm, params, SND_PCM_HW_PARAM_PERIODS, val, dir);
4911 }
4912
4913 /**
4914  * \brief Restrict a configuration space to contain only integer periods counts
4915  * \param pcm PCM handle
4916  * \param params Configuration space
4917  * \return 0 otherwise a negative error code if configuration space would become empty
4918  */
4919 int snd_pcm_hw_params_set_periods_integer(snd_pcm_t *pcm, snd_pcm_hw_params_t *params)
4920 {
4921         return snd_pcm_hw_param_set_integer(pcm, params, SND_TRY, SND_PCM_HW_PARAM_PERIODS);
4922 }
4923
4924
4925 /**
4926  * \brief Extract buffer time from a configuration space
4927  * \param params Configuration space
4928  * \param val Returned buffer time in us
4929  * \param dir Sub unit direction
4930  * \return 0 otherwise a negative error code if the configuration space does not contain a single value
4931  *
4932  * Actual exact value is <,=,> the approximate one following dir (-1, 0, 1)
4933  */
4934 #ifndef DOXYGEN
4935 int INTERNAL(snd_pcm_hw_params_get_buffer_time)(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4936 #else
4937 int snd_pcm_hw_params_get_buffer_time(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4938 #endif
4939 {
4940         return snd_pcm_hw_param_get(params, SND_PCM_HW_PARAM_BUFFER_TIME, val, dir);
4941 }
4942
4943 /**
4944  * \brief Extract minimum buffer time from a configuration space
4945  * \param params Configuration space
4946  * \param val approximate minimum buffer duration in us
4947  * \param dir Sub unit direction
4948  * \return 0 otherwise a negative error code
4949  *
4950  * Exact value is <,=,> the returned one following dir (-1,0,1)
4951  */
4952 #ifndef DOXYGEN
4953 int INTERNAL(snd_pcm_hw_params_get_buffer_time_min)(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4954 #else
4955 int snd_pcm_hw_params_get_buffer_time_min(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4956 #endif
4957 {
4958         return snd_pcm_hw_param_get_min(params, SND_PCM_HW_PARAM_BUFFER_TIME, val, dir);
4959 }
4960
4961 /**
4962  * \brief Extract maximum buffer time from a configuration space
4963  * \param params Configuration space
4964  * \param val approximate maximum buffer duration in us
4965  * \param dir Sub unit direction
4966  * \return 0 otherwise a negative error code
4967  *
4968  * Exact value is <,=,> the returned one following dir (-1,0,1)
4969  */
4970 #ifndef DOXYGEN
4971 int INTERNAL(snd_pcm_hw_params_get_buffer_time_max)(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4972 #else
4973 int snd_pcm_hw_params_get_buffer_time_max(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
4974 #endif
4975 {
4976         return snd_pcm_hw_param_get_max(params, SND_PCM_HW_PARAM_BUFFER_TIME, val, dir);
4977 }
4978
4979 /**
4980  * \brief Verify if a buffer time is available inside a configuration space for a PCM
4981  * \param pcm PCM handle
4982  * \param params Configuration space
4983  * \param val approximate buffer duration in us
4984  * \param dir Sub unit direction
4985  * \return 0 if available a negative error code otherwise
4986  *
4987  * Wanted exact value is <,=,> val following dir (-1,0,1)
4988  */
4989 int snd_pcm_hw_params_test_buffer_time(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int val, int dir)
4990 {
4991         return snd_pcm_hw_param_set(pcm, params, SND_TEST, SND_PCM_HW_PARAM_BUFFER_TIME, val, dir);
4992 }
4993
4994 /**
4995  * \brief Restrict a configuration space to contain only one buffer time
4996  * \param pcm PCM handle
4997  * \param params Configuration space
4998  * \param val approximate buffer duration in us
4999  * \param dir Sub unit direction
5000  * \return 0 otherwise a negative error code if configuration space would become empty
5001  *
5002  * Wanted exact value is <,=,> val following dir (-1,0,1)
5003  */
5004 int snd_pcm_hw_params_set_buffer_time(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int val, int dir)
5005 {
5006         return snd_pcm_hw_param_set(pcm, params, SND_TRY, SND_PCM_HW_PARAM_BUFFER_TIME, val, dir);
5007 }
5008
5009 /**
5010  * \brief Restrict a configuration space with a minimum buffer time
5011  * \param pcm PCM handle
5012  * \param params Configuration space
5013  * \param val approximate minimum buffer duration in us (on return filled with actual minimum)
5014  * \param dir Sub unit direction (on return filled with actual direction)
5015  * \return 0 otherwise a negative error code if configuration space would become empty
5016  *
5017  * Wanted/actual exact minimum is <,=,> val following dir (-1,0,1)
5018  */
5019 int snd_pcm_hw_params_set_buffer_time_min(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
5020 {
5021         return snd_pcm_hw_param_set_min(pcm, params, SND_TRY, SND_PCM_HW_PARAM_BUFFER_TIME, val, dir);
5022 }
5023
5024 /**
5025  * \brief Restrict a configuration space with a maximum buffer time
5026  * \param pcm PCM handle
5027  * \param params Configuration space
5028  * \param val approximate maximum buffer duration in us (on return filled with actual maximum)
5029  * \param dir Sub unit direction (on return filled with actual direction)
5030  * \return 0 otherwise a negative error code if configuration space would become empty
5031  *
5032  * Wanted/actual exact maximum is <,=,> val following dir (-1,0,1)
5033  */
5034 int snd_pcm_hw_params_set_buffer_time_max(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
5035 {
5036         return snd_pcm_hw_param_set_max(pcm, params, SND_TRY, SND_PCM_HW_PARAM_BUFFER_TIME, val, dir);
5037 }
5038
5039 /**
5040  * \brief Restrict a configuration space to have buffer times in a given range
5041  * \param pcm PCM handle
5042  * \param params Configuration space
5043  * \param min approximate minimum buffer duration in us (on return filled with actual minimum)
5044  * \param mindir Sub unit direction for minimum (on return filled with actual direction)
5045  * \param max approximate maximum buffer duration in us (on return filled with actual maximum)
5046  * \param maxdir Sub unit direction for maximum (on return filled with actual direction)
5047  * \return 0 otherwise a negative error code if configuration space would become empty
5048  *
5049  * Wanted/actual exact min/max is <,=,> val following dir (-1,0,1)
5050  */
5051 int snd_pcm_hw_params_set_buffer_time_minmax(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *min, int *mindir, unsigned int *max, int *maxdir)
5052 {
5053         return snd_pcm_hw_param_set_minmax(pcm, params, SND_TRY, SND_PCM_HW_PARAM_BUFFER_TIME, min, mindir, max, maxdir);
5054 }
5055
5056 /**
5057  * \brief Restrict a configuration space to have buffer time nearest to a target
5058  * \param pcm PCM handle
5059  * \param params Configuration space
5060  * \param val approximate target buffer duration in us / returned chosen approximate target buffer duration
5061  * \param dir Sub unit direction
5062  * \return 0 otherwise a negative error code if configuration space is empty
5063  *
5064  * target/chosen exact value is <,=,> val following dir (-1,0,1)
5065  */
5066 #ifndef DOXYGEN
5067 int INTERNAL(snd_pcm_hw_params_set_buffer_time_near)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
5068 #else
5069 int snd_pcm_hw_params_set_buffer_time_near(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
5070 #endif
5071 {
5072         return snd_pcm_hw_param_set_near(pcm, params, SND_PCM_HW_PARAM_BUFFER_TIME, val, dir);
5073 }
5074
5075 /**
5076  * \brief Restrict a configuration space to contain only its minimum buffer time
5077  * \param pcm PCM handle
5078  * \param params Configuration space
5079  * \param val Returned approximate minimum buffer duration in us
5080  * \param dir Sub unit direction
5081  * \return 0 otherwise a negative error code
5082  *
5083  * Actual exact value is <,=,> the approximate one following dir (-1, 0, 1)
5084  */
5085 #ifndef DOXYGEN
5086 int INTERNAL(snd_pcm_hw_params_set_buffer_time_first)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
5087 #else
5088 int snd_pcm_hw_params_set_buffer_time_first(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
5089 #endif
5090 {
5091         return snd_pcm_hw_param_set_first(pcm, params, SND_PCM_HW_PARAM_BUFFER_TIME, val, dir);
5092 }
5093
5094 /**
5095  * \brief Restrict a configuration space to contain only its maximum buffered time
5096  * \param pcm PCM handle
5097  * \param params Configuration space
5098  * \param val Returned approximate maximum buffer duration in us
5099  * \param dir Sub unit direction
5100  * \return 0 otherwise a negative error code
5101  *
5102  * Actual exact value is <,=,> the approximate one following dir (-1, 0, 1)
5103  */
5104 #ifndef DOXYGEN
5105 int INTERNAL(snd_pcm_hw_params_set_buffer_time_last)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
5106 #else
5107 int snd_pcm_hw_params_set_buffer_time_last(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
5108 #endif
5109 {
5110         return snd_pcm_hw_param_set_last(pcm, params, SND_PCM_HW_PARAM_BUFFER_TIME, val, dir);
5111 }
5112
5113
5114 /**
5115  * \brief Extract buffer size from a configuration space
5116  * \param params Configuration space
5117  * \param val Returned buffer size in frames
5118  * \return 0 otherwise a negative error code if the configuration space does not contain a single value
5119  */
5120 #ifndef DOXYGEN
5121 int INTERNAL(snd_pcm_hw_params_get_buffer_size)(const snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val)
5122 #else
5123 int snd_pcm_hw_params_get_buffer_size(const snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val)
5124 #endif
5125 {
5126         unsigned int _val;
5127         int err = snd_pcm_hw_param_get(params, SND_PCM_HW_PARAM_BUFFER_SIZE, &_val, NULL);
5128         if (err >= 0)
5129                 *val = _val;
5130         return err;
5131 }
5132
5133 /**
5134  * \brief Extract minimum buffer size from a configuration space
5135  * \param params Configuration space
5136  * \param val Returned approximate minimum buffer size in frames
5137  * \return 0 otherwise a negative error code
5138  */
5139 #ifndef DOXYGEN
5140 int INTERNAL(snd_pcm_hw_params_get_buffer_size_min)(const snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val)
5141 #else
5142 int snd_pcm_hw_params_get_buffer_size_min(const snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val)
5143 #endif
5144 {
5145         unsigned int _val;
5146         int err = snd_pcm_hw_param_get_min(params, SND_PCM_HW_PARAM_BUFFER_SIZE, &_val, NULL);
5147         if (err >= 0)
5148                 *val = _val;
5149         return err;
5150 }
5151
5152 /**
5153  * \brief Extract maximum buffer size from a configuration space
5154  * \param params Configuration space
5155  * \param val Returned approximate maximum buffer size in frames
5156  * \return 0 otherwise a negative error code
5157  *
5158  * Exact value is <,=,> the returned one following dir (-1,0,1)
5159  */
5160 #ifndef DOXYGEN
5161 int INTERNAL(snd_pcm_hw_params_get_buffer_size_max)(const snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val)
5162 #else
5163 int snd_pcm_hw_params_get_buffer_size_max(const snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val)
5164 #endif
5165 {
5166         unsigned int _val;
5167         int err = snd_pcm_hw_param_get_max(params, SND_PCM_HW_PARAM_BUFFER_SIZE, &_val, NULL);
5168         if (err >= 0)
5169                 *val = _val;
5170         return err;
5171 }
5172
5173 /**
5174  * \brief Verify if a buffer size is available inside a configuration space for a PCM
5175  * \param pcm PCM handle
5176  * \param params Configuration space
5177  * \param val buffer size in frames
5178  * \return 0 if available a negative error code otherwise
5179  *
5180  * Wanted exact value is <,=,> val following dir (-1,0,1)
5181  */
5182 int snd_pcm_hw_params_test_buffer_size(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t val)
5183 {
5184         return snd_pcm_hw_param_set(pcm, params, SND_TEST, SND_PCM_HW_PARAM_BUFFER_SIZE, val, 0);
5185 }
5186
5187 /**
5188  * \brief Restrict a configuration space to contain only one buffer size
5189  * \param pcm PCM handle
5190  * \param params Configuration space
5191  * \param val buffer size in frames
5192  * \return 0 otherwise a negative error code if configuration space would become empty
5193  *
5194  * Wanted exact value is <,=,> val following dir (-1,0,1)
5195  */
5196 int snd_pcm_hw_params_set_buffer_size(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t val)
5197 {
5198         return snd_pcm_hw_param_set(pcm, params, SND_TRY, SND_PCM_HW_PARAM_BUFFER_SIZE, val, 0);
5199 }
5200
5201 /**
5202  * \brief Restrict a configuration space with a minimum buffer size
5203  * \param pcm PCM handle
5204  * \param params Configuration space
5205  * \param val approximate minimum buffer size in frames (on return filled with actual minimum)
5206  * \return 0 otherwise a negative error code if configuration space would become empty
5207  */
5208 int snd_pcm_hw_params_set_buffer_size_min(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val)
5209 {
5210         unsigned int _val = *val;
5211         int err = snd_pcm_hw_param_set_min(pcm, params, SND_TRY, SND_PCM_HW_PARAM_BUFFER_SIZE, &_val, NULL);
5212         if (err >= 0)
5213                 *val = _val;
5214         return err;
5215 }
5216
5217 /**
5218  * \brief Restrict a configuration space with a maximum buffer size
5219  * \param pcm PCM handle
5220  * \param params Configuration space
5221  * \param val approximate maximum buffer size in frames (on return filled with actual maximum)
5222  * \return 0 otherwise a negative error code if configuration space would become empty
5223  */
5224 int snd_pcm_hw_params_set_buffer_size_max(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val)
5225 {
5226         unsigned int _val = *val;
5227         int err = snd_pcm_hw_param_set_max(pcm, params, SND_TRY, SND_PCM_HW_PARAM_BUFFER_SIZE, &_val, NULL);
5228         if (err >= 0)
5229                 *val = _val;
5230         return err;
5231 }
5232
5233 /**
5234  * \brief Restrict a configuration space to have buffer sizes in a given range
5235  * \param pcm PCM handle
5236  * \param params Configuration space
5237  * \param min approximate minimum buffer size in frames (on return filled with actual minimum)
5238  * \param max approximate maximum buffer size in frames (on return filled with actual maximum)
5239  * \return 0 otherwise a negative error code if configuration space would become empty
5240  */
5241 int snd_pcm_hw_params_set_buffer_size_minmax(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *min, snd_pcm_uframes_t *max)
5242 {
5243         unsigned int _min = *min;
5244         unsigned int _max = *max;
5245         int err = snd_pcm_hw_param_set_minmax(pcm, params, SND_TRY, SND_PCM_HW_PARAM_BUFFER_SIZE, &_min, NULL, &_max, NULL);
5246         *min = _min;
5247         *max = _max;
5248         return err;
5249 }
5250
5251 /**
5252  * \brief Restrict a configuration space to have buffer size nearest to a target
5253  * \param pcm PCM handle
5254  * \param params Configuration space
5255  * \param val approximate target buffer size in frames / returned chosen approximate target buffer size in frames
5256  * \return 0 otherwise a negative error code if configuration space is empty
5257  */
5258 #ifndef DOXYGEN
5259 int INTERNAL(snd_pcm_hw_params_set_buffer_size_near)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val)
5260 #else
5261 int snd_pcm_hw_params_set_buffer_size_near(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val)
5262 #endif
5263 {
5264         unsigned int _val = *val;
5265         int err = snd_pcm_hw_param_set_near(pcm, params, SND_PCM_HW_PARAM_BUFFER_SIZE, &_val, NULL);
5266         if (err >= 0)
5267                 *val = _val;
5268         return err;
5269 }
5270
5271 /**
5272  * \brief Restrict a configuration space to contain only its minimum buffer size
5273  * \param pcm PCM handle
5274  * \param params Configuration space
5275  * \param val Returned minimum buffer size in frames
5276  * \return buffer size in frames
5277  */
5278 #ifndef DOXYGEN
5279 int INTERNAL(snd_pcm_hw_params_set_buffer_size_first)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val)
5280 #else
5281 int snd_pcm_hw_params_set_buffer_size_first(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val)
5282 #endif
5283 {
5284         unsigned int _val;
5285         int err = snd_pcm_hw_param_set_first(pcm, params, SND_PCM_HW_PARAM_BUFFER_SIZE, &_val, NULL);
5286         if (err >= 0)
5287                 *val = _val;
5288         return err;
5289 }
5290
5291 /**
5292  * \brief Restrict a configuration space to contain only its maximum buffer size
5293  * \param pcm PCM handle
5294  * \param params Configuration space
5295  * \param val Returned maximum buffer size in frames
5296  * \return 0 otherwise a negative error code
5297  */
5298 #ifndef DOXYGEN
5299 int INTERNAL(snd_pcm_hw_params_set_buffer_size_last)(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val)
5300 #else
5301 int snd_pcm_hw_params_set_buffer_size_last(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val)
5302 #endif
5303 {
5304         unsigned int _val;
5305         int err = snd_pcm_hw_param_set_last(pcm, params, SND_PCM_HW_PARAM_BUFFER_SIZE, &_val, NULL);
5306         if (err >= 0)
5307                 *val = _val;
5308         return err;
5309 }
5310
5311
5312 /**
5313  * \brief (DEPRECATED) Extract tick time from a configuration space
5314  * \param params Configuration space
5315  * \param val Returned approximate tick duration in us
5316  * \param dir Sub unit direction
5317  * \return 0 otherwise a negative error code if the configuration space does not contain a single value
5318  *
5319  * Actual exact value is <,=,> the approximate one following dir (-1, 0, 1)
5320  */
5321 #ifndef DOXYGEN
5322 int INTERNAL(snd_pcm_hw_params_get_tick_time)(const snd_pcm_hw_params_t *params ATTRIBUTE_UNUSED, unsigned int *val, int *dir ATTRIBUTE_UNUSED)
5323 #else
5324 int snd_pcm_hw_params_get_tick_time(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
5325 #endif
5326 {
5327         *val = 0;
5328         return 0;
5329 }
5330
5331 /**
5332  * \brief (DEPRECATED) Extract minimum tick time from a configuration space
5333  * \param params Configuration space
5334  * \param val Returned approximate minimum tick duration in us
5335  * \param dir Sub unit direction
5336  * \return 0 otherwise a negative error code
5337  *
5338  * Exact value is <,=,> the returned one following dir (-1,0,1)
5339  */
5340 #ifndef DOXYGEN
5341 int INTERNAL(snd_pcm_hw_params_get_tick_time_min)(const snd_pcm_hw_params_t *params ATTRIBUTE_UNUSED, unsigned int *val, int *dir ATTRIBUTE_UNUSED)
5342 #else
5343 int snd_pcm_hw_params_get_tick_time_min(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
5344 #endif
5345 {
5346         *val = 0;
5347         return 0;
5348 }
5349
5350 /**
5351  * \brief (DEPRECATED) Extract maximum tick time from a configuration space
5352  * \param params Configuration space
5353  * \param val Returned approximate maximum tick duration in us
5354  * \param dir Sub unit direction
5355  * \return 0 otherwise a negative error code
5356  *
5357  * Exact value is <,=,> the returned one following dir (-1,0,1)
5358  */
5359 #ifndef DOXYGEN
5360 int INTERNAL(snd_pcm_hw_params_get_tick_time_max)(const snd_pcm_hw_params_t *params ATTRIBUTE_UNUSED, unsigned int *val, int *dir ATTRIBUTE_UNUSED)
5361 #else
5362 int snd_pcm_hw_params_get_tick_time_max(const snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
5363 #endif
5364 {
5365         *val = 0;
5366         return 0;
5367 }
5368
5369 /**
5370  * \brief (DEPRECATED) Verify if a tick time is available inside a configuration space for a PCM
5371  * \param pcm PCM handle
5372  * \param params Configuration space
5373  * \param val approximate tick duration in us
5374  * \param dir Sub unit direction
5375  * \return 0 if available a negative error code otherwise
5376  *
5377  * Wanted exact value is <,=,> val following dir (-1,0,1)
5378  */
5379 int snd_pcm_hw_params_test_tick_time(snd_pcm_t *pcm ATTRIBUTE_UNUSED, snd_pcm_hw_params_t *params ATTRIBUTE_UNUSED, unsigned int val, int dir ATTRIBUTE_UNUSED)
5380 {
5381         return val ? -EINVAL : 0;
5382 }
5383
5384 /**
5385  * \brief (DEPRECATED) Restrict a configuration space to contain only one tick time
5386  * \param pcm PCM handle
5387  * \param params Configuration space
5388  * \param val approximate tick duration in us
5389  * \param dir Sub unit direction
5390  * \return 0 otherwise a negative error code if configuration space would become empty
5391  *
5392  * Wanted exact value is <,=,> val following dir (-1,0,1)
5393  */
5394 int snd_pcm_hw_params_set_tick_time(snd_pcm_t *pcm ATTRIBUTE_UNUSED, snd_pcm_hw_params_t *params ATTRIBUTE_UNUSED, unsigned int val ATTRIBUTE_UNUSED, int dir ATTRIBUTE_UNUSED)
5395 {
5396         return 0;
5397 }
5398
5399 /**
5400  * \brief (DEPRECATED) Restrict a configuration space with a minimum tick time
5401  * \param pcm PCM handle
5402  * \param params Configuration space
5403  * \param val approximate minimum tick duration in us (on return filled with actual minimum)
5404  * \param dir Sub unit direction (on return filled with actual direction)
5405  * \return 0 otherwise a negative error code if configuration space would become empty
5406  *
5407  * Wanted/actual exact minimum is <,=,> val following dir (-1,0,1)
5408  */
5409 int snd_pcm_hw_params_set_tick_time_min(snd_pcm_t *pcm ATTRIBUTE_UNUSED, snd_pcm_hw_params_t *params ATTRIBUTE_UNUSED, unsigned int *val ATTRIBUTE_UNUSED, int *dir ATTRIBUTE_UNUSED)
5410 {
5411         return 0;
5412 }
5413
5414 /**
5415  * \brief (DEPRECATED) Restrict a configuration space with a maximum tick time
5416  * \param pcm PCM handle
5417  * \param params Configuration space
5418  * \param val approximate maximum tick duration in us (on return filled with actual maximum)
5419  * \param dir Sub unit direction (on return filled with actual direction)
5420  * \return 0 otherwise a negative error code if configuration space would become empty
5421  *
5422  * Wanted/actual exact maximum is <,=,> val following dir (-1,0,1)
5423  */
5424 int snd_pcm_hw_params_set_tick_time_max(snd_pcm_t *pcm ATTRIBUTE_UNUSED, snd_pcm_hw_params_t *params ATTRIBUTE_UNUSED, unsigned int *val ATTRIBUTE_UNUSED, int *dir ATTRIBUTE_UNUSED)
5425 {
5426         return 0;
5427 }
5428
5429 /**
5430  * \brief (DEPRECATED) Restrict a configuration space to have tick times in a given range
5431  * \param pcm PCM handle
5432  * \param params Configuration space
5433  * \param min approximate minimum tick duration in us (on return filled with actual minimum)
5434  * \param mindir Sub unit direction for minimum (on return filled with actual direction)
5435  * \param max approximate maximum tick duration in us (on return filled with actual maximum)
5436  * \param maxdir Sub unit direction for maximum (on return filled with actual direction)
5437  * \return 0 otherwise a negative error code if configuration space would become empty
5438  *
5439  * Wanted/actual exact min/max is <,=,> val following dir (-1,0,1)
5440  */
5441 int snd_pcm_hw_params_set_tick_time_minmax(snd_pcm_t *pcm ATTRIBUTE_UNUSED, snd_pcm_hw_params_t *params ATTRIBUTE_UNUSED, unsigned int *min ATTRIBUTE_UNUSED, int *mindir ATTRIBUTE_UNUSED, unsigned int *max ATTRIBUTE_UNUSED, int *maxdir ATTRIBUTE_UNUSED)
5442 {
5443         return 0;
5444 }
5445
5446 /**
5447  * \brief (DEPRECATED) Restrict a configuration space to have tick time nearest to a target
5448  * \param pcm PCM handle
5449  * \param params Configuration space
5450  * \param val approximate target tick duration in us / returned chosen approximate target tick duration in us
5451  * \param dir Sub unit direction
5452  * \return 0 otherwise a negative error code if configuration space is empty
5453  *
5454  * target/chosen exact value is <,=,> val following dir (-1,0,1)
5455  */
5456 #ifndef DOXYGEN
5457 int INTERNAL(snd_pcm_hw_params_set_tick_time_near)(snd_pcm_t *pcm ATTRIBUTE_UNUSED, snd_pcm_hw_params_t *params ATTRIBUTE_UNUSED, unsigned int *val ATTRIBUTE_UNUSED, int *dir ATTRIBUTE_UNUSED)
5458 #else
5459 int snd_pcm_hw_params_set_tick_time_near(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
5460 #endif
5461 {
5462         return 0;
5463 }
5464
5465 /**
5466  * \brief (DEPRECATED) Restrict a configuration space to contain only its minimum tick time
5467  * \param pcm PCM handle
5468  * \param params Configuration space
5469  * \param val Returned approximate minimum tick duration in us
5470  * \param dir Sub unit direction
5471  * \return 0 otherwise a negative error code
5472  *
5473  * Actual exact value is <,=,> the approximate one following dir (-1, 0, 1)
5474  */
5475 #ifndef DOXYGEN
5476 int INTERNAL(snd_pcm_hw_params_set_tick_time_first)(snd_pcm_t *pcm ATTRIBUTE_UNUSED, snd_pcm_hw_params_t *params ATTRIBUTE_UNUSED, unsigned int *val ATTRIBUTE_UNUSED, int *dir ATTRIBUTE_UNUSED)
5477 #else
5478 int snd_pcm_hw_params_set_tick_time_first(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
5479 #endif
5480 {
5481         return 0;
5482 }
5483
5484 /**
5485  * \brief (DEPRECATED) Restrict a configuration space to contain only its maximum tick time
5486  * \param pcm PCM handle
5487  * \param params Configuration space
5488  * \param val Returned approximate maximum tick duration in us
5489  * \param dir Sub unit direction
5490  * \return 0 otherwise a negative error code
5491  *
5492  * Actual exact value is <,=,> the approximate one following dir (-1, 0, 1)
5493  */
5494 #ifndef DOXYGEN
5495 int INTERNAL(snd_pcm_hw_params_set_tick_time_last)(snd_pcm_t *pcm ATTRIBUTE_UNUSED, snd_pcm_hw_params_t *params ATTRIBUTE_UNUSED, unsigned int *val ATTRIBUTE_UNUSED, int *dir ATTRIBUTE_UNUSED)
5496 #else
5497 int snd_pcm_hw_params_set_tick_time_last(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, unsigned int *val, int *dir)
5498 #endif
5499 {
5500         return 0;
5501 }
5502
5503 /**
5504  * \brief Get the minimum transfer align value in samples
5505  * \param params Configuration space
5506  * \param val Returned minimum align value
5507  * \return 0 otherwise a negative error code if the configuration space does not contain a single value
5508  */
5509 int snd_pcm_hw_params_get_min_align(const snd_pcm_hw_params_t *params, snd_pcm_uframes_t *val)
5510 {
5511         unsigned int format, channels, fb, min_align;
5512         int err;
5513
5514         err = snd_pcm_hw_param_get(params, SND_PCM_HW_PARAM_FORMAT, &format, NULL);
5515         if (err < 0)
5516                 return err;
5517         err = snd_pcm_hw_param_get(params, SND_PCM_HW_PARAM_CHANNELS, &channels, NULL);
5518         if (err < 0)
5519                 return err;
5520         // compute frame bits
5521         fb = snd_pcm_format_physical_width((snd_pcm_format_t)format) * channels;
5522         min_align = 1;
5523         while (fb % 8) {
5524                 fb *= 2;
5525                 min_align *= 2;
5526         }
5527         if (val)
5528                 *val = min_align;
5529         return 0;
5530 }
5531
5532 /**
5533  * \brief Return current software configuration for a PCM
5534  * \param pcm PCM handle
5535  * \param params Software configuration container
5536  * \return 0 on success otherwise a negative error code
5537  */
5538 int snd_pcm_sw_params_current(snd_pcm_t *pcm, snd_pcm_sw_params_t *params)
5539 {
5540         assert(pcm && params);
5541         if (CHECK_SANITY(! pcm->setup)) {
5542                 SNDMSG("PCM not set up");
5543                 return -EIO;
5544         }
5545         params->tstamp_mode = pcm->tstamp_mode;
5546         params->period_step = pcm->period_step;
5547         params->sleep_min = 0;
5548         params->avail_min = pcm->avail_min;
5549         params->period_event = pcm->period_event;
5550         params->xfer_align = 1;
5551         params->start_threshold = pcm->start_threshold;
5552         params->stop_threshold = pcm->stop_threshold;
5553         params->silence_threshold = pcm->silence_threshold;
5554         params->silence_size = pcm->silence_size;
5555         params->boundary = pcm->boundary;
5556         return 0;
5557 }
5558
5559 /**
5560  * \brief Dump a software configuration
5561  * \param params Software configuration container
5562  * \param out Output handle
5563  * \return 0 on success otherwise a negative error code
5564  */
5565 int snd_pcm_sw_params_dump(snd_pcm_sw_params_t *params, snd_output_t *out)
5566 {
5567         snd_output_printf(out, "tstamp_mode: %s\n", snd_pcm_tstamp_mode_name(params->tstamp_mode));
5568         snd_output_printf(out, "period_step: %u\n", params->period_step);
5569         snd_output_printf(out, "avail_min: %lu\n", params->avail_min);
5570         snd_output_printf(out, "start_threshold: %ld\n", params->start_threshold);
5571         snd_output_printf(out, "stop_threshold: %ld\n", params->stop_threshold);
5572         snd_output_printf(out, "silence_threshold: %lu\n", params->silence_threshold);
5573         snd_output_printf(out, "silence_size: %lu\n", params->silence_size);
5574         snd_output_printf(out, "boundary: %lu\n", params->boundary);
5575         return 0;
5576 }
5577
5578 /**
5579  * \brief get size of #snd_pcm_sw_params_t
5580  * \return size in bytes
5581  */
5582 size_t snd_pcm_sw_params_sizeof()
5583 {
5584         return sizeof(snd_pcm_sw_params_t);
5585 }
5586
5587 /**
5588  * \brief allocate an invalid #snd_pcm_sw_params_t using standard malloc
5589  * \param ptr returned pointer
5590  * \return 0 on success otherwise negative error code
5591  */
5592 int snd_pcm_sw_params_malloc(snd_pcm_sw_params_t **ptr)
5593 {
5594         assert(ptr);
5595         *ptr = calloc(1, sizeof(snd_pcm_sw_params_t));
5596         if (!*ptr)
5597                 return -ENOMEM;
5598         return 0;
5599 }
5600
5601 /**
5602  * \brief frees a previously allocated #snd_pcm_sw_params_t
5603  * \param obj pointer to object to free
5604  */
5605 void snd_pcm_sw_params_free(snd_pcm_sw_params_t *obj)
5606 {
5607         free(obj);
5608 }
5609
5610 /**
5611  * \brief copy one #snd_pcm_sw_params_t to another
5612  * \param dst pointer to destination
5613  * \param src pointer to source
5614  */
5615 void snd_pcm_sw_params_copy(snd_pcm_sw_params_t *dst, const snd_pcm_sw_params_t *src)
5616 {
5617         assert(dst && src);
5618         *dst = *src;
5619 }
5620
5621 /**
5622  * \brief Get boundary for ring pointers from a software configuration container
5623  * \param params Software configuration container
5624  * \param val Returned boundary in frames
5625  * \return 0 otherwise a negative error code
5626  */
5627 int snd_pcm_sw_params_get_boundary(const snd_pcm_sw_params_t *params, snd_pcm_uframes_t *val)
5628 {
5629         assert(params);
5630         *val = params->boundary;
5631         return 0;
5632 }
5633
5634 /**
5635  * \brief (DEPRECATED) Set start mode inside a software configuration container
5636  * \param pcm PCM handle
5637  * \param params Software configuration container
5638  * \param val Start mode
5639  * \return 0 otherwise a negative error code
5640  */
5641 int snd_pcm_sw_params_set_start_mode(snd_pcm_t *pcm, snd_pcm_sw_params_t *params, snd_pcm_start_t val)
5642 {
5643         assert(pcm && params);
5644         switch (val) {
5645         case SND_PCM_START_DATA:
5646                 params->start_threshold = 1;
5647                 break;
5648         case SND_PCM_START_EXPLICIT:
5649                 params->start_threshold = pcm->boundary;
5650                 break;
5651         default:
5652                 SNDMSG("invalid start mode value %d\n", val);
5653                 return -EINVAL;
5654         }
5655         return 0;
5656 }
5657
5658 #ifndef DOC_HIDDEN
5659 link_warning(snd_pcm_sw_params_set_start_mode, "Warning: start_mode is deprecated, consider to use start_threshold");
5660 #endif
5661
5662 /**
5663  * \brief (DEPRECATED) Get start mode from a software configuration container
5664  * \param params Software configuration container
5665  * \return start mode
5666  */
5667 snd_pcm_start_t snd_pcm_sw_params_get_start_mode(const snd_pcm_sw_params_t *params)
5668 {
5669         assert(params);
5670         /* FIXME: Ugly */
5671         return params->start_threshold > 1024 * 1024 ? SND_PCM_START_EXPLICIT : SND_PCM_START_DATA;
5672 }
5673
5674 #ifndef DOC_HIDDEN
5675 link_warning(snd_pcm_sw_params_get_start_mode, "Warning: start_mode is deprecated, consider to use start_threshold");
5676 #endif
5677
5678 /**
5679  * \brief (DEPRECATED) Set xrun mode inside a software configuration container
5680  * \param pcm PCM handle
5681  * \param params Software configuration container
5682  * \param val Xrun mode
5683  * \return 0 otherwise a negative error code
5684  */
5685 #ifndef DOXYGEN
5686 int snd_pcm_sw_params_set_xrun_mode(snd_pcm_t *pcm ATTRIBUTE_UNUSED, snd_pcm_sw_params_t *params, snd_pcm_xrun_t val)
5687 #else
5688 int snd_pcm_sw_params_set_xrun_mode(snd_pcm_t *pcm, snd_pcm_sw_params_t *params, snd_pcm_xrun_t val)
5689 #endif
5690 {
5691         assert(pcm && params);
5692         switch (val) {
5693         case SND_PCM_XRUN_STOP:
5694                 params->stop_threshold = pcm->buffer_size;
5695                 break;
5696         case SND_PCM_XRUN_NONE:
5697                 params->stop_threshold = pcm->boundary;
5698                 break;
5699         default:
5700                 SNDMSG("invalid xrun mode value %d\n", val);
5701                 return -EINVAL;
5702         }
5703         return 0;
5704 }
5705
5706 #ifndef DOC_HIDDEN
5707 link_warning(snd_pcm_sw_params_set_xrun_mode, "Warning: xrun_mode is deprecated, consider to use stop_threshold");
5708 #endif
5709
5710 /**
5711  * \brief (DEPRECATED) Get xrun mode from a software configuration container
5712  * \param params Software configuration container
5713  * \return xrun mode
5714  */
5715 snd_pcm_xrun_t snd_pcm_sw_params_get_xrun_mode(const snd_pcm_sw_params_t *params)
5716 {
5717         assert(params);
5718         /* FIXME: Ugly */
5719         return params->stop_threshold > 1024 * 1024 ? SND_PCM_XRUN_NONE : SND_PCM_XRUN_STOP;
5720 }
5721
5722 #ifndef DOC_HIDDEN
5723 link_warning(snd_pcm_sw_params_get_xrun_mode, "Warning: xrun_mode is deprecated, consider to use stop_threshold");
5724 #endif
5725
5726 /**
5727  * \brief Set timestamp mode inside a software configuration container
5728  * \param pcm PCM handle
5729  * \param params Software configuration container
5730  * \param val Timestamp mode
5731  * \return 0 otherwise a negative error code
5732  */
5733 #ifndef DOXYGEN
5734 int snd_pcm_sw_params_set_tstamp_mode(snd_pcm_t *pcm ATTRIBUTE_UNUSED, snd_pcm_sw_params_t *params, snd_pcm_tstamp_t val)
5735 #else
5736 int snd_pcm_sw_params_set_tstamp_mode(snd_pcm_t *pcm, snd_pcm_sw_params_t *params, snd_pcm_tstamp_t val)
5737 #endif
5738 {
5739         assert(pcm && params);
5740         if (CHECK_SANITY(val > SND_PCM_TSTAMP_LAST)) {
5741                 SNDMSG("invalid tstamp_mode value %d", val);
5742                 return -EINVAL;
5743         }
5744         params->tstamp_mode = val;
5745         return 0;
5746 }
5747
5748 /**
5749  * \brief Get timestamp mode from a software configuration container
5750  * \param params Software configuration container
5751  * \param val Returned timestamp
5752  * \return 0 otherwise a negative error code
5753  */
5754 #ifndef DOXYGEN
5755 int INTERNAL(snd_pcm_sw_params_get_tstamp_mode)(const snd_pcm_sw_params_t *params, snd_pcm_tstamp_t *val)
5756 #else
5757 int snd_pcm_sw_params_get_tstamp_mode(const snd_pcm_sw_params_t *params, snd_pcm_tstamp_t *val)
5758 #endif
5759 {
5760         assert(params && val);
5761         *val = params->tstamp_mode;
5762         return 0;
5763 }
5764
5765 /**
5766  * \brief (DEPRECATED) Set minimum number of ticks to sleep inside a software configuration container
5767  * \param pcm PCM handle
5768  * \param params Software configuration container
5769  * \param val Minimum ticks to sleep or 0 to disable the use of tick timer
5770  * \return 0 otherwise a negative error code
5771  */
5772 #ifndef DOXYGEN
5773 int snd_pcm_sw_params_set_sleep_min(snd_pcm_t *pcm ATTRIBUTE_UNUSED, snd_pcm_sw_params_t *params ATTRIBUTE_UNUSED, unsigned int val ATTRIBUTE_UNUSED)
5774 #else
5775 int snd_pcm_sw_params_set_sleep_min(snd_pcm_t *pcm, snd_pcm_sw_params_t *params, unsigned int val)
5776 #endif
5777 {
5778         return 0;
5779 }
5780
5781 /**
5782  * \brief (DEPRECATED) Get minimum numbers of ticks to sleep from a software configuration container
5783  * \param params Software configuration container
5784  * \param val returned minimum number of ticks to sleep or 0 if tick timer is disabled
5785  * \return 0 otherwise a negative error code
5786  */
5787 #ifndef DOXYGEN
5788 int INTERNAL(snd_pcm_sw_params_get_sleep_min)(const snd_pcm_sw_params_t *params ATTRIBUTE_UNUSED, unsigned int *val)
5789 #else
5790 int snd_pcm_sw_params_get_sleep_min(const snd_pcm_sw_params_t *params, unsigned int *val)
5791 #endif
5792 {
5793         *val = 0;
5794         return 0;
5795 }
5796
5797 /**
5798  * \brief Set avail min inside a software configuration container
5799  * \param pcm PCM handle
5800  * \param params Software configuration container
5801  * \param val Minimum avail frames to consider PCM ready
5802  * \return 0 otherwise a negative error code
5803  *
5804  * Note: This is similar to setting an OSS wakeup point.  The valid
5805  * values for 'val' are determined by the specific hardware.  Most PC
5806  * sound cards can only accept power of 2 frame counts (i.e. 512,
5807  * 1024, 2048).  You cannot use this as a high resolution timer - it
5808  * is limited to how often the sound card hardware raises an
5809  * interrupt.
5810  */
5811 #ifndef DOXYGEN
5812 int snd_pcm_sw_params_set_avail_min(snd_pcm_t *pcm ATTRIBUTE_UNUSED, snd_pcm_sw_params_t *params, snd_pcm_uframes_t val)
5813 #else
5814 int snd_pcm_sw_params_set_avail_min(snd_pcm_t *pcm, snd_pcm_sw_params_t *params, snd_pcm_uframes_t val)
5815 #endif
5816 {
5817         assert(pcm && params);
5818         /* Fix avail_min if it's below period size.  The period_size
5819          * defines the minimal wake-up timing accuracy, so it doesn't
5820          * make sense to set below that.
5821          */
5822         if (val < pcm->period_size)
5823                 val = pcm->period_size;
5824         params->avail_min = val;
5825         return 0;
5826 }
5827
5828 /**
5829  * \brief Get avail min from a software configuration container
5830  * \param params Software configuration container
5831  * \param val returned minimum available frames to consider PCM ready
5832  * \return 0 otherwise a negative error code
5833  */
5834 #ifndef DOXYGEN
5835 int INTERNAL(snd_pcm_sw_params_get_avail_min)(const snd_pcm_sw_params_t *params, snd_pcm_uframes_t *val)
5836 #else
5837 int snd_pcm_sw_params_get_avail_min(const snd_pcm_sw_params_t *params, snd_pcm_uframes_t *val)
5838 #endif
5839 {
5840         assert(params && val);
5841         *val = params->avail_min;
5842         return 0;
5843 }
5844
5845 /**
5846  * \brief Set period event inside a software configuration container
5847  * \param pcm PCM handle
5848  * \param params Software configuration container
5849  * \param val 0 = disable period event, 1 = enable period event
5850  * \return 0 otherwise a negative error code
5851  *
5852  * An poll (select) wakeup event is raised if enabled.
5853  */
5854 int snd_pcm_sw_params_set_period_event(snd_pcm_t *pcm, snd_pcm_sw_params_t *params, int val)
5855 {
5856         assert(pcm && params);
5857         params->period_event = val;
5858         return 0;
5859 }
5860
5861 /**
5862  * \brief Get period event from a software configuration container
5863  * \param params Software configuration container
5864  * \param val returned period event state
5865  * \return 0 otherwise a negative error code
5866  */
5867 int snd_pcm_sw_params_get_period_event(const snd_pcm_sw_params_t *params, int *val)
5868 {
5869         assert(params && val);
5870         *val = params->period_event;
5871         return 0;
5872 }
5873
5874 /**
5875  * \brief (DEPRECATED) Set xfer align inside a software configuration container
5876  * \param pcm PCM handle
5877  * \param params Software configuration container
5878  * \param val Chunk size (frames are attempted to be transferred in chunks)
5879  * \return 0 otherwise a negative error code
5880  */
5881 #ifndef DOXYGEN
5882 int snd_pcm_sw_params_set_xfer_align(snd_pcm_t *pcm ATTRIBUTE_UNUSED, snd_pcm_sw_params_t *params ATTRIBUTE_UNUSED, snd_pcm_uframes_t val ATTRIBUTE_UNUSED)
5883 #else
5884 int snd_pcm_sw_params_set_xfer_align(snd_pcm_t *pcm, snd_pcm_sw_params_t *params, snd_pcm_uframes_t val)
5885 #endif
5886 {
5887         return 0;
5888 }
5889
5890 /**
5891  * \brief (DEPRECATED) Get xfer align from a software configuration container
5892  * \param params Software configuration container
5893  * \param val returned chunk size (frames are attempted to be transferred in chunks)
5894  * \return 0 otherwise a negative error code
5895  */
5896 #ifndef DOXYGEN
5897 int INTERNAL(snd_pcm_sw_params_get_xfer_align)(const snd_pcm_sw_params_t *params ATTRIBUTE_UNUSED, snd_pcm_uframes_t *val)
5898 #else
5899 int snd_pcm_sw_params_get_xfer_align(const snd_pcm_sw_params_t *params, snd_pcm_uframes_t *val)
5900 #endif
5901 {
5902         *val = 1;
5903         return 0;
5904 }
5905
5906 /**
5907  * \brief Set start threshold inside a software configuration container
5908  * \param pcm PCM handle
5909  * \param params Software configuration container
5910  * \param val Start threshold in frames
5911  * \return 0 otherwise a negative error code
5912  *
5913  * PCM is automatically started when playback frames available to PCM 
5914  * are >= threshold or when requested capture frames are >= threshold
5915  */
5916 #ifndef DOXYGEN
5917 int snd_pcm_sw_params_set_start_threshold(snd_pcm_t *pcm ATTRIBUTE_UNUSED, snd_pcm_sw_params_t *params, snd_pcm_uframes_t val)
5918 #else
5919 int snd_pcm_sw_params_set_start_threshold(snd_pcm_t *pcm, snd_pcm_sw_params_t *params, snd_pcm_uframes_t val)
5920 #endif
5921 {
5922         assert(pcm && params);
5923         params->start_threshold = val;
5924         return 0;
5925 }
5926
5927 /**
5928  * \brief Get start threshold from a software configuration container
5929  * \param params Software configuration container
5930  * \param val Returned start threshold in frames
5931  * \return 0 otherwise a negative error code
5932  *
5933  * PCM is automatically started when playback frames available to PCM 
5934  * are >= threshold or when requested capture frames are >= threshold
5935  */
5936 #ifndef DOXYGEN
5937 int INTERNAL(snd_pcm_sw_params_get_start_threshold)(const snd_pcm_sw_params_t *params, snd_pcm_uframes_t *val)
5938 #else
5939 int snd_pcm_sw_params_get_start_threshold(const snd_pcm_sw_params_t *params, snd_pcm_uframes_t *val)
5940 #endif
5941 {
5942         assert(params);
5943         *val = params->start_threshold;
5944         return 0;
5945 }
5946
5947
5948 /**
5949  * \brief Set stop threshold inside a software configuration container
5950  * \param pcm PCM handle
5951  * \param params Software configuration container
5952  * \param val Stop threshold in frames
5953  * \return 0 otherwise a negative error code
5954  *
5955  * PCM is automatically stopped in #SND_PCM_STATE_XRUN state when available
5956  * frames is >= threshold. If the stop threshold is equal to boundary (also
5957  * software parameter - sw_param) then automatic stop will be disabled
5958  * (thus device will do the endless loop in the ring buffer).
5959  */
5960 #ifndef DOXYGEN
5961 int snd_pcm_sw_params_set_stop_threshold(snd_pcm_t *pcm ATTRIBUTE_UNUSED, snd_pcm_sw_params_t *params, snd_pcm_uframes_t val)
5962 #else
5963 int snd_pcm_sw_params_set_stop_threshold(snd_pcm_t *pcm, snd_pcm_sw_params_t *params, snd_pcm_uframes_t val)
5964 #endif
5965 {
5966         assert(pcm && params);
5967         params->stop_threshold = val;
5968         return 0;
5969 }
5970
5971 /**
5972  * \brief Get stop threshold from a software configuration container
5973  * \param params Software configuration container
5974  * \param val Returned stop threshold in frames
5975  * \return 0 otherwise a negative error code
5976  *
5977  * PCM is automatically stopped in #SND_PCM_STATE_XRUN state when available
5978  * frames is >= threshold. If the stop threshold is equal to boundary (also
5979  * software parameter - sw_param) then automatic stop will be disabled
5980  * (thus device will do the endless loop in the ring buffer).
5981  */
5982 #ifndef DOXYGEN
5983 int INTERNAL(snd_pcm_sw_params_get_stop_threshold)(const snd_pcm_sw_params_t *params, snd_pcm_uframes_t *val)
5984 #else
5985 int snd_pcm_sw_params_get_stop_threshold(const snd_pcm_sw_params_t *params, snd_pcm_uframes_t *val)
5986 #endif
5987 {
5988         assert(params);
5989         *val = params->stop_threshold;
5990         return 0;
5991 }
5992
5993
5994 /**
5995  * \brief Set silence threshold inside a software configuration container
5996  * \param pcm PCM handle
5997  * \param params Software configuration container
5998  * \param val Silence threshold in frames 
5999  * \return 0 otherwise a negative error code
6000  *
6001  * A portion of playback buffer is overwritten with silence (see 
6002  * #snd_pcm_sw_params_set_silence_size) when playback underrun is nearer
6003  * than silence threshold.
6004  */
6005 #ifndef DOXYGEN
6006 int snd_pcm_sw_params_set_silence_threshold(snd_pcm_t *pcm ATTRIBUTE_UNUSED, snd_pcm_sw_params_t *params, snd_pcm_uframes_t val)
6007 #else
6008 int snd_pcm_sw_params_set_silence_threshold(snd_pcm_t *pcm, snd_pcm_sw_params_t *params, snd_pcm_uframes_t val)
6009 #endif
6010 {
6011         assert(pcm && params);
6012         if (CHECK_SANITY(val >= pcm->buffer_size)) {
6013                 SNDMSG("invalid silent_threshold value %ld (buffer_size = %ld)",
6014                        val, pcm->buffer_size);
6015                 return -EINVAL;
6016         }
6017         params->silence_threshold = val;
6018         return 0;
6019 }
6020
6021 /**
6022  * \brief Get silence threshold from a software configuration container
6023  * \param params Software configuration container
6024  * \param val Returned silence threshold in frames
6025  * \return 0 otherwise a negative error value
6026  *
6027  * A portion of playback buffer is overwritten with silence (see 
6028  * #snd_pcm_sw_params_set_silence_size) when playback underrun is nearer
6029  * than silence threshold.
6030  */
6031 #ifndef DOXYGEN
6032 int INTERNAL(snd_pcm_sw_params_get_silence_threshold)(const snd_pcm_sw_params_t *params, snd_pcm_uframes_t *val)
6033 #else
6034 int snd_pcm_sw_params_get_silence_threshold(const snd_pcm_sw_params_t *params, snd_pcm_uframes_t *val)
6035 #endif
6036 {
6037         assert(params && val);
6038         *val = params->silence_threshold;
6039         return 0;
6040 }
6041
6042
6043 /**
6044  * \brief Set silence size inside a software configuration container
6045  * \param pcm PCM handle
6046  * \param params Software configuration container
6047  * \param val Silence size in frames (0 for disabled)
6048  * \return 0 otherwise a negative error code
6049  *
6050  * A portion of playback buffer is overwritten with silence when playback
6051  * underrun is nearer than silence threshold (see 
6052  * #snd_pcm_sw_params_set_silence_threshold)
6053  *
6054  * The special case is when silence size value is equal or greater than
6055  * boundary. The unused portion of the ring buffer (initial written samples
6056  * are untouched) is filled with silence at start. Later, only just processed
6057  * sample area is filled with silence. Note: silence_threshold must be set to zero.
6058  */
6059 #ifndef DOXYGEN
6060 int snd_pcm_sw_params_set_silence_size(snd_pcm_t *pcm ATTRIBUTE_UNUSED, snd_pcm_sw_params_t *params, snd_pcm_uframes_t val)
6061 #else
6062 int snd_pcm_sw_params_set_silence_size(snd_pcm_t *pcm, snd_pcm_sw_params_t *params, snd_pcm_uframes_t val)
6063 #endif
6064 {
6065         assert(pcm && params);
6066         if (CHECK_SANITY(val < pcm->boundary && val > pcm->buffer_size)) {
6067                 SNDMSG("invalid silence_size %ld (boundary %ld, buffer_size %ld)",
6068                        val, pcm->boundary, pcm->buffer_size);
6069                 return -EINVAL;
6070         }
6071         params->silence_size = val;
6072         return 0;
6073 }
6074
6075 /**
6076  * \brief Get silence size from a software configuration container
6077  * \param params Software configuration container
6078  * \param val Returned silence size in frames (0 for disabled)
6079  * \return 0 otherwise a negative error code
6080  *
6081  * A portion of playback buffer is overwritten with silence when playback
6082  * underrun is nearer than silence threshold (see 
6083  * #snd_pcm_sw_params_set_silence_threshold)
6084  */
6085 #ifndef DOXYGEN
6086 int INTERNAL(snd_pcm_sw_params_get_silence_size)(const snd_pcm_sw_params_t *params, snd_pcm_uframes_t *val)
6087 #else
6088 int snd_pcm_sw_params_get_silence_size(const snd_pcm_sw_params_t *params, snd_pcm_uframes_t *val)
6089 #endif
6090 {
6091         assert(params);
6092         *val = params->silence_size;
6093         return 0;
6094 }
6095
6096
6097 /**
6098  * \brief get size of #snd_pcm_status_t
6099  * \return size in bytes
6100  */
6101 size_t snd_pcm_status_sizeof()
6102 {
6103         return sizeof(snd_pcm_status_t);
6104 }
6105
6106 /**
6107  * \brief allocate an invalid #snd_pcm_status_t using standard malloc
6108  * \param ptr returned pointer
6109  * \return 0 on success otherwise negative error code
6110  */
6111 int snd_pcm_status_malloc(snd_pcm_status_t **ptr)
6112 {
6113         assert(ptr);
6114         *ptr = calloc(1, sizeof(snd_pcm_status_t));
6115         if (!*ptr)
6116                 return -ENOMEM;
6117         return 0;
6118 }
6119
6120 /**
6121  * \brief frees a previously allocated #snd_pcm_status_t
6122  * \param obj pointer to object to free
6123  */
6124 void snd_pcm_status_free(snd_pcm_status_t *obj)
6125 {
6126         free(obj);
6127 }
6128
6129 /**
6130  * \brief copy one #snd_pcm_status_t to another
6131  * \param dst pointer to destination
6132  * \param src pointer to source
6133  */
6134 void snd_pcm_status_copy(snd_pcm_status_t *dst, const snd_pcm_status_t *src)
6135 {
6136         assert(dst && src);
6137         *dst = *src;
6138 }
6139
6140 /** 
6141  * \brief Get state from a PCM status container (see #snd_pcm_state)
6142  * \param obj #snd_pcm_status_t pointer
6143  * \return PCM state
6144  */
6145 snd_pcm_state_t snd_pcm_status_get_state(const snd_pcm_status_t *obj)
6146 {
6147         assert(obj);
6148         return obj->state;
6149 }
6150
6151 /** 
6152  * \brief Get trigger timestamp from a PCM status container
6153  * \param obj #snd_pcm_status_t pointer
6154  * \param ptr Pointer to returned timestamp
6155  *
6156  * Trigger means a PCM state transition (from stopped to running or
6157  * versa vice). It applies also to pause and suspend. In other words,
6158  * timestamp contains time when stream started or when it was stopped.
6159  */
6160 void snd_pcm_status_get_trigger_tstamp(const snd_pcm_status_t *obj, snd_timestamp_t *ptr)
6161 {
6162         assert(obj && ptr);
6163         ptr->tv_sec = obj->trigger_tstamp.tv_sec;
6164         ptr->tv_usec = obj->trigger_tstamp.tv_nsec / 1000L;
6165 }
6166
6167 /** 
6168  * \brief Get trigger hi-res timestamp from a PCM status container
6169  * \param obj #snd_pcm_status_t pointer
6170  * \param ptr Pointer to returned timestamp
6171  *
6172  * Trigger means a PCM state transition (from stopped to running or
6173  * versa vice). It applies also to pause and suspend. In other words,
6174  * timestamp contains time when stream started or when it was stopped.
6175  */
6176 #ifndef DOXYGEN
6177 void INTERNAL(snd_pcm_status_get_trigger_htstamp)(const snd_pcm_status_t *obj, snd_htimestamp_t *ptr)
6178 #else
6179 void snd_pcm_status_get_trigger_htstamp(const snd_pcm_status_t *obj, snd_htimestamp_t *ptr)
6180 #endif
6181 {
6182         assert(obj && ptr);
6183         *ptr = obj->trigger_tstamp;
6184 }
6185 use_default_symbol_version(__snd_pcm_status_get_trigger_htstamp, snd_pcm_status_get_trigger_htstamp, ALSA_0.9.0rc8);
6186
6187 /** 
6188  * \brief Get "now" timestamp from a PCM status container
6189  * \param obj #snd_pcm_status_t pointer
6190  * \param ptr Pointer to returned timestamp
6191  */
6192 void snd_pcm_status_get_tstamp(const snd_pcm_status_t *obj, snd_timestamp_t *ptr)
6193 {
6194         assert(obj && ptr);
6195         ptr->tv_sec = obj->tstamp.tv_sec;
6196         ptr->tv_usec = obj->tstamp.tv_nsec / 1000L;
6197 }
6198
6199 /** 
6200  * \brief Get "now" hi-res timestamp from a PCM status container
6201  * \param obj pointer to #snd_pcm_status_t
6202  * \param ptr Pointer to returned timestamp
6203  */
6204 #ifndef DOXYGEN
6205 void INTERNAL(snd_pcm_status_get_htstamp)(const snd_pcm_status_t *obj, snd_htimestamp_t *ptr)
6206 #else
6207 void snd_pcm_status_get_htstamp(const snd_pcm_status_t *obj, snd_htimestamp_t *ptr)
6208 #endif
6209 {
6210         assert(obj && ptr);
6211         *ptr = obj->tstamp;
6212 }
6213 use_default_symbol_version(__snd_pcm_status_get_htstamp, snd_pcm_status_get_htstamp, ALSA_0.9.0rc8);
6214
6215 /** 
6216  * \brief Get delay from a PCM status container (see #snd_pcm_delay)
6217  * \return Delay in frames
6218  *
6219  * Delay is distance between current application frame position and
6220  * sound frame position.
6221  * It's positive and less than buffer size in normal situation,
6222  * negative on playback underrun and greater than buffer size on
6223  * capture overrun.
6224  */
6225 snd_pcm_sframes_t snd_pcm_status_get_delay(const snd_pcm_status_t *obj)
6226 {
6227         assert(obj);
6228         return obj->delay;
6229 }
6230
6231 /** 
6232  * \brief Get number of frames available from a PCM status container (see #snd_pcm_avail_update)
6233  * \return Number of frames ready to be read/written
6234  */
6235 snd_pcm_uframes_t snd_pcm_status_get_avail(const snd_pcm_status_t *obj)
6236 {
6237         assert(obj);
6238         return obj->avail;
6239 }
6240
6241 /** 
6242  * \brief Get maximum number of frames available from a PCM status container after last #snd_pcm_status call
6243  * \return Maximum number of frames ready to be read/written
6244  */
6245 snd_pcm_uframes_t snd_pcm_status_get_avail_max(const snd_pcm_status_t *obj)
6246 {
6247         assert(obj);
6248         return obj->avail_max;
6249 }
6250
6251 /** 
6252  * \brief Get count of ADC overrange detections since last call
6253  * \return Count of ADC overrange detections
6254  */
6255 snd_pcm_uframes_t snd_pcm_status_get_overrange(const snd_pcm_status_t *obj)
6256 {
6257         assert(obj);
6258         return obj->overrange;
6259 }
6260
6261 /**
6262  * \brief get size of #snd_pcm_info_t
6263  * \return size in bytes
6264  */
6265 size_t snd_pcm_info_sizeof()
6266 {
6267         return sizeof(snd_pcm_info_t);
6268 }
6269
6270 /**
6271  * \brief allocate an invalid #snd_pcm_info_t using standard malloc
6272  * \param ptr returned pointer
6273  * \return 0 on success otherwise negative error code
6274  */
6275 int snd_pcm_info_malloc(snd_pcm_info_t **ptr)
6276 {
6277         assert(ptr);
6278         *ptr = calloc(1, sizeof(snd_pcm_info_t));
6279         if (!*ptr)
6280                 return -ENOMEM;
6281         return 0;
6282 }
6283
6284 /**
6285  * \brief frees a previously allocated #snd_pcm_info_t
6286  * \param obj pointer to object to free
6287  */
6288 void snd_pcm_info_free(snd_pcm_info_t *obj)
6289 {
6290         free(obj);
6291 }
6292
6293 /**
6294  * \brief copy one #snd_pcm_info_t to another
6295  * \param dst pointer to destination
6296  * \param src pointer to source
6297  */
6298 void snd_pcm_info_copy(snd_pcm_info_t *dst, const snd_pcm_info_t *src)
6299 {
6300         assert(dst && src);
6301         *dst = *src;
6302 }
6303
6304 /**
6305  * \brief Get device from a PCM info container
6306  * \param obj PCM info container
6307  * \return device number
6308  */
6309 unsigned int snd_pcm_info_get_device(const snd_pcm_info_t *obj)
6310 {
6311         assert(obj);
6312         return obj->device;
6313 }
6314
6315 /**
6316  * \brief Get subdevice from a PCM info container
6317  * \param obj PCM info container
6318  * \return subdevice number
6319  */
6320 unsigned int snd_pcm_info_get_subdevice(const snd_pcm_info_t *obj)
6321 {
6322         assert(obj);
6323         return obj->subdevice;
6324 }
6325
6326 /**
6327  * \brief Get stream (direction) from a PCM info container
6328  * \param obj PCM info container
6329  * \return stream
6330  */
6331 snd_pcm_stream_t snd_pcm_info_get_stream(const snd_pcm_info_t *obj)
6332 {
6333         assert(obj);
6334         return obj->stream;
6335 }
6336
6337 /**
6338  * \brief Get card from a PCM info container
6339  * \param obj PCM info container
6340  * \return card number otherwise a negative error code if not associable to a card
6341  */
6342 int snd_pcm_info_get_card(const snd_pcm_info_t *obj)
6343 {
6344         assert(obj);
6345         return obj->card;
6346 }
6347
6348 /**
6349  * \brief Get id from a PCM info container
6350  * \param obj PCM info container
6351  * \return short id of PCM
6352  */
6353 const char *snd_pcm_info_get_id(const snd_pcm_info_t *obj)
6354 {
6355         assert(obj);
6356         return (const char *)obj->id;
6357 }
6358
6359 /**
6360  * \brief Get name from a PCM info container
6361  * \param obj PCM info container
6362  * \return name of PCM
6363  */
6364 const char *snd_pcm_info_get_name(const snd_pcm_info_t *obj)
6365 {
6366         assert(obj);
6367         return (const char *)obj->name;
6368 }
6369
6370 /**
6371  * \brief Get subdevice name from a PCM info container
6372  * \param obj PCM info container
6373  * \return name of used PCM subdevice
6374  */
6375 const char *snd_pcm_info_get_subdevice_name(const snd_pcm_info_t *obj)
6376 {
6377         assert(obj);
6378         return (const char *)obj->subname;
6379 }
6380
6381 /**
6382  * \brief Get class from a PCM info container
6383  * \param obj PCM info container
6384  * \return class of PCM
6385  */
6386 snd_pcm_class_t snd_pcm_info_get_class(const snd_pcm_info_t *obj)
6387 {
6388         assert(obj);
6389         return obj->dev_class;
6390 }
6391
6392 /**
6393  * \brief Get subclass from a PCM info container
6394  * \param obj PCM info container
6395  * \return subclass of PCM
6396  */
6397 snd_pcm_subclass_t snd_pcm_info_get_subclass(const snd_pcm_info_t *obj)
6398 {
6399         assert(obj);
6400         return obj->dev_subclass;
6401 }
6402
6403 /**
6404  * \brief Get subdevices count from a PCM info container
6405  * \param obj PCM info container
6406  * \return subdevices total count of PCM
6407  */
6408 unsigned int snd_pcm_info_get_subdevices_count(const snd_pcm_info_t *obj)
6409 {
6410         assert(obj);
6411         return obj->subdevices_count;
6412 }
6413
6414 /**
6415  * \brief Get available subdevices count from a PCM info container
6416  * \param obj PCM info container
6417  * \return available subdevices count of PCM
6418  */
6419 unsigned int snd_pcm_info_get_subdevices_avail(const snd_pcm_info_t *obj)
6420 {
6421         assert(obj);
6422         return obj->subdevices_avail;
6423 }
6424
6425 /**
6426  * \brief Get hardware synchronization ID from a PCM info container
6427  * \param obj PCM info container
6428  * \return hardware synchronization ID
6429  */
6430 snd_pcm_sync_id_t snd_pcm_info_get_sync(const snd_pcm_info_t *obj)
6431 {
6432         snd_pcm_sync_id_t res;
6433         assert(obj);
6434         memcpy(&res, &obj->sync, sizeof(res));
6435         return res;
6436 }
6437
6438 /**
6439  * \brief Set wanted device inside a PCM info container (see #snd_ctl_pcm_info)
6440  * \param obj PCM info container
6441  * \param val Device number
6442  */
6443 void snd_pcm_info_set_device(snd_pcm_info_t *obj, unsigned int val)
6444 {
6445         assert(obj);
6446         obj->device = val;
6447 }
6448
6449 /**
6450  * \brief Set wanted subdevice inside a PCM info container (see #snd_ctl_pcm_info)
6451  * \param obj PCM info container
6452  * \param val Subdevice number
6453  */
6454 void snd_pcm_info_set_subdevice(snd_pcm_info_t *obj, unsigned int val)
6455 {
6456         assert(obj);
6457         obj->subdevice = val;
6458 }
6459
6460 /**
6461  * \brief Set wanted stream inside a PCM info container (see #snd_ctl_pcm_info)
6462  * \param obj PCM info container
6463  * \param val Stream
6464  */
6465 void snd_pcm_info_set_stream(snd_pcm_info_t *obj, snd_pcm_stream_t val)
6466 {
6467         assert(obj);
6468         obj->stream = val;
6469 }
6470
6471 /**
6472  * \brief Application request to access a portion of direct (mmap) area
6473  * \param pcm PCM handle 
6474  * \param areas Returned mmap channel areas
6475  * \param offset Returned mmap area offset in area steps (== frames)
6476  * \param frames mmap area portion size in frames (wanted on entry, contiguous available on exit)
6477  * \return 0 on success otherwise a negative error code
6478  *
6479  * It is necessary to call the snd_pcm_avail_update() function directly before
6480  * this call. Otherwise, this function can return a wrong count of available frames.
6481  *
6482  * The function should be called before a sample-direct area can be accessed.
6483  * The resulting size parameter is always less or equal to the input count of frames
6484  * and can be zero, if no frames can be processed (the ring buffer is full).
6485  *
6486  * See the snd_pcm_mmap_commit() function to finish the frame processing in
6487  * the direct areas.
6488  */
6489 int snd_pcm_mmap_begin(snd_pcm_t *pcm,
6490                        const snd_pcm_channel_area_t **areas,
6491                        snd_pcm_uframes_t *offset,
6492                        snd_pcm_uframes_t *frames)
6493 {
6494         snd_pcm_uframes_t cont;
6495         snd_pcm_uframes_t f;
6496         snd_pcm_uframes_t avail;
6497         const snd_pcm_channel_area_t *xareas;
6498         assert(pcm && areas && offset && frames);
6499         xareas = snd_pcm_mmap_areas(pcm);
6500         if (xareas == NULL)
6501                 return -EBADFD;
6502         *areas = xareas;
6503         *offset = *pcm->appl.ptr % pcm->buffer_size;
6504         avail = snd_pcm_mmap_avail(pcm);
6505         if (avail > pcm->buffer_size)
6506                 avail = pcm->buffer_size;
6507         cont = pcm->buffer_size - *offset;
6508         f = *frames;
6509         if (f > avail)
6510                 f = avail;
6511         if (f > cont)
6512                 f = cont;
6513         *frames = f;
6514         return 0;
6515 }
6516
6517 /**
6518  * \brief Application has completed the access to area requested with #snd_pcm_mmap_begin
6519  * \param pcm PCM handle
6520  * \param offset area offset in area steps (== frames)
6521  * \param frames area portion size in frames
6522  * \return count of transferred frames otherwise a negative error code
6523  *
6524  * You should pass this function the offset value that
6525  * snd_pcm_mmap_begin() returned. The frames parameter should hold the
6526  * number of frames you have written or read to/from the audio
6527  * buffer. The frames parameter must never exceed the contiguous frames
6528  * count that snd_pcm_mmap_begin() returned. Each call to snd_pcm_mmap_begin()
6529  * must be followed by a call to snd_pcm_mmap_commit().
6530  *
6531  * Example:
6532 \code
6533   double phase = 0;
6534   const snd_pcm_area_t *areas;
6535   snd_pcm_sframes_t avail, size, commitres;
6536   snd_pcm_uframes_t offset, frames;
6537   int err;
6538
6539   avail = snd_pcm_avail_update(pcm);
6540   if (avail < 0)
6541     error(avail);
6542   // at this point, we can transfer at least 'avail' frames
6543   
6544   // we want to process frames in chunks (period_size)
6545   if (avail < period_size)
6546     goto _skip;
6547   size = period_size;
6548   // it is possible that contiguous areas are smaller, thus we use a loop
6549   while (size > 0) {
6550     frames = size;
6551
6552     err = snd_pcm_mmap_begin(pcm_handle, &areas, &offset, &frames);
6553     if (err < 0)
6554       error(err);
6555     // this function fills the areas from offset with count of frames
6556     generate_sine(areas, offset, frames, &phase);
6557     commitres = snd_pcm_mmap_commit(pcm_handle, offset, frames);
6558     if (commitres < 0 || commitres != frames)
6559       error(commitres >= 0 ? -EPIPE : commitres);
6560       
6561     size -= frames;
6562   }
6563  _skip:
6564 \endcode
6565  *
6566  * Look to the \ref example_test_pcm "Sine-wave generator" example
6567  * for more details about the generate_sine function.
6568  */
6569 snd_pcm_sframes_t snd_pcm_mmap_commit(snd_pcm_t *pcm,
6570                                       snd_pcm_uframes_t offset,
6571                                       snd_pcm_uframes_t frames)
6572 {
6573         assert(pcm);
6574         if (CHECK_SANITY(offset != *pcm->appl.ptr % pcm->buffer_size)) {
6575                 SNDMSG("commit offset (%ld) doesn't match with appl_ptr (%ld) %% buf_size (%ld)",
6576                        offset, *pcm->appl.ptr, pcm->buffer_size);
6577                 return -EPIPE;
6578         }
6579         if (CHECK_SANITY(frames > snd_pcm_mmap_avail(pcm))) {
6580                 SNDMSG("commit frames (%ld) overflow (avail = %ld)", frames,
6581                        snd_pcm_mmap_avail(pcm));
6582                 return -EPIPE;
6583         }
6584         return pcm->fast_ops->mmap_commit(pcm->fast_op_arg, offset, frames);
6585 }
6586
6587 #ifndef DOC_HIDDEN
6588
6589 int _snd_pcm_poll_descriptor(snd_pcm_t *pcm)
6590 {
6591         assert(pcm);
6592         return pcm->poll_fd;
6593 }
6594
6595 void snd_pcm_areas_from_buf(snd_pcm_t *pcm, snd_pcm_channel_area_t *areas, 
6596                             void *buf)
6597 {
6598         unsigned int channel;
6599         unsigned int channels = pcm->channels;
6600         for (channel = 0; channel < channels; ++channel, ++areas) {
6601                 areas->addr = buf;
6602                 areas->first = channel * pcm->sample_bits;
6603                 areas->step = pcm->frame_bits;
6604         }
6605 }
6606
6607 void snd_pcm_areas_from_bufs(snd_pcm_t *pcm, snd_pcm_channel_area_t *areas, 
6608                              void **bufs)
6609 {
6610         unsigned int channel;
6611         unsigned int channels = pcm->channels;
6612         for (channel = 0; channel < channels; ++channel, ++areas, ++bufs) {
6613                 areas->addr = *bufs;
6614                 areas->first = 0;
6615                 areas->step = pcm->sample_bits;
6616         }
6617 }
6618
6619 snd_pcm_sframes_t snd_pcm_read_areas(snd_pcm_t *pcm, const snd_pcm_channel_area_t *areas,
6620                                      snd_pcm_uframes_t offset, snd_pcm_uframes_t size,
6621                                      snd_pcm_xfer_areas_func_t func)
6622 {
6623         snd_pcm_uframes_t xfer = 0;
6624         snd_pcm_sframes_t err = 0;
6625         snd_pcm_state_t state;
6626
6627         if (size == 0)
6628                 return 0;
6629
6630         while (size > 0) {
6631                 snd_pcm_uframes_t frames;
6632                 snd_pcm_sframes_t avail;
6633         _again:
6634                 state = snd_pcm_state(pcm);
6635                 switch (state) {
6636                 case SND_PCM_STATE_PREPARED:
6637                         err = snd_pcm_start(pcm);
6638                         if (err < 0)
6639                                 goto _end;
6640                         break;
6641                 case SND_PCM_STATE_RUNNING:
6642                         err = snd_pcm_hwsync(pcm);
6643                         if (err < 0)
6644                                 goto _end;
6645                         break;
6646                 case SND_PCM_STATE_DRAINING:
6647                 case SND_PCM_STATE_PAUSED:
6648                         break;
6649                 case SND_PCM_STATE_XRUN:
6650                         err = -EPIPE;
6651                         goto _end;
6652                 case SND_PCM_STATE_SUSPENDED:
6653                         err = -ESTRPIPE;
6654                         goto _end;
6655                 case SND_PCM_STATE_DISCONNECTED:
6656                         err = -ENODEV;
6657                         goto _end;
6658                 default:
6659                         err = -EBADFD;
6660                         goto _end;
6661                 }
6662                 avail = snd_pcm_avail_update(pcm);
6663                 if (avail < 0) {
6664                         err = avail;
6665                         goto _end;
6666                 }
6667                 if (avail == 0) {
6668                         if (state == SND_PCM_STATE_DRAINING)
6669                                 goto _end;
6670                         if (pcm->mode & SND_PCM_NONBLOCK) {
6671                                 err = -EAGAIN;
6672                                 goto _end;
6673                         }
6674
6675                         err = snd_pcm_wait(pcm, -1);
6676                         if (err < 0)
6677                                 break;
6678                         goto _again;
6679                         
6680                 }
6681                 frames = size;
6682                 if (frames > (snd_pcm_uframes_t) avail)
6683                         frames = avail;
6684                 if (! frames)
6685                         break;
6686                 err = func(pcm, areas, offset, frames);
6687                 if (err < 0)
6688                         break;
6689                 frames = err;
6690                 offset += frames;
6691                 size -= frames;
6692                 xfer += frames;
6693         }
6694  _end:
6695         return xfer > 0 ? (snd_pcm_sframes_t) xfer : snd_pcm_check_error(pcm, err);
6696 }
6697
6698 snd_pcm_sframes_t snd_pcm_write_areas(snd_pcm_t *pcm, const snd_pcm_channel_area_t *areas,
6699                                       snd_pcm_uframes_t offset, snd_pcm_uframes_t size,
6700                                       snd_pcm_xfer_areas_func_t func)
6701 {
6702         snd_pcm_uframes_t xfer = 0;
6703         snd_pcm_sframes_t err = 0;
6704         snd_pcm_state_t state;
6705
6706         if (size == 0)
6707                 return 0;
6708
6709         while (size > 0) {
6710                 snd_pcm_uframes_t frames;
6711                 snd_pcm_sframes_t avail;
6712         _again:
6713                 state = snd_pcm_state(pcm);
6714                 switch (state) {
6715                 case SND_PCM_STATE_PREPARED:
6716                 case SND_PCM_STATE_PAUSED:
6717                         break;
6718                 case SND_PCM_STATE_RUNNING:
6719                         err = snd_pcm_hwsync(pcm);
6720                         if (err < 0)
6721                                 goto _end;
6722                         break;
6723                 case SND_PCM_STATE_XRUN:
6724                         err = -EPIPE;
6725                         goto _end;
6726                 case SND_PCM_STATE_SUSPENDED:
6727                         err = -ESTRPIPE;
6728                         goto _end;
6729                 case SND_PCM_STATE_DISCONNECTED:
6730                         err = -ENODEV;
6731                         goto _end;
6732                 default:
6733                         err = -EBADFD;
6734                         goto _end;
6735                 }
6736                 avail = snd_pcm_avail_update(pcm);
6737                 if (avail < 0) {
6738                         err = avail;
6739                         goto _end;
6740                 }
6741                 if ((state == SND_PCM_STATE_RUNNING &&
6742                      (snd_pcm_uframes_t)avail < pcm->avail_min &&
6743                      size > (snd_pcm_uframes_t)avail)) {
6744                         if (pcm->mode & SND_PCM_NONBLOCK) {
6745                                 err = -EAGAIN;
6746                                 goto _end;
6747                         }
6748
6749                         err = snd_pcm_wait(pcm, -1);
6750                         if (err < 0)
6751                                 break;
6752                         goto _again;                    
6753                 }
6754                 frames = size;
6755                 if (frames > (snd_pcm_uframes_t) avail)
6756                         frames = avail;
6757                 if (! frames)
6758                         break;
6759                 err = func(pcm, areas, offset, frames);
6760                 if (err < 0)
6761                         break;
6762                 frames = err;
6763                 if (state == SND_PCM_STATE_PREPARED) {
6764                         snd_pcm_sframes_t hw_avail = pcm->buffer_size - avail;
6765                         hw_avail += frames;
6766                         /* some plugins might automatically start the stream */
6767                         state = snd_pcm_state(pcm);
6768                         if (state == SND_PCM_STATE_PREPARED &&
6769                             hw_avail >= (snd_pcm_sframes_t) pcm->start_threshold) {
6770                                 err = snd_pcm_start(pcm);
6771                                 if (err < 0)
6772                                         goto _end;
6773                         }
6774                 }
6775                 offset += frames;
6776                 size -= frames;
6777                 xfer += frames;
6778         }
6779  _end:
6780         return xfer > 0 ? (snd_pcm_sframes_t) xfer : snd_pcm_check_error(pcm, err);
6781 }
6782
6783 snd_pcm_uframes_t _snd_pcm_mmap_hw_ptr(snd_pcm_t *pcm)
6784 {
6785         return *pcm->hw.ptr;
6786 }
6787
6788 snd_pcm_uframes_t _snd_pcm_boundary(snd_pcm_t *pcm)
6789 {
6790         return pcm->boundary;
6791 }
6792
6793 #ifndef DOC_HIDDEN
6794 link_warning(_snd_pcm_mmap_hw_ptr, "Warning: _snd_pcm_mmap_hw_ptr() is deprecated, consider to not use this function");
6795 link_warning(_snd_pcm_boundary, "Warning: _snd_pcm_boundary() is deprecated, consider to use snd_pcm_sw_params_current()");
6796 #endif
6797
6798 static const char *const names[SND_PCM_HW_PARAM_LAST_INTERVAL + 1] = {
6799         [SND_PCM_HW_PARAM_FORMAT] = "format",
6800         [SND_PCM_HW_PARAM_CHANNELS] = "channels",
6801         [SND_PCM_HW_PARAM_RATE] = "rate",
6802         [SND_PCM_HW_PARAM_PERIOD_TIME] = "period_time",
6803         [SND_PCM_HW_PARAM_PERIOD_SIZE] = "period_size",
6804         [SND_PCM_HW_PARAM_BUFFER_TIME] = "buffer_time",
6805         [SND_PCM_HW_PARAM_BUFFER_SIZE] = "buffer_size",
6806         [SND_PCM_HW_PARAM_PERIODS] = "periods"
6807 };
6808
6809 int snd_pcm_slave_conf(snd_config_t *root, snd_config_t *conf,
6810                        snd_config_t **_pcm_conf, unsigned int count, ...)
6811 {
6812         snd_config_iterator_t i, next;
6813         const char *str;
6814         struct {
6815                 unsigned int index;
6816                 int flags;
6817                 void *ptr;
6818                 int present;
6819         } fields[count];
6820         unsigned int k;
6821         snd_config_t *pcm_conf = NULL;
6822         int err;
6823         int to_free = 0;
6824         va_list args;
6825         assert(root);
6826         assert(conf);
6827         assert(_pcm_conf);
6828         if (snd_config_get_string(conf, &str) >= 0) {
6829                 err = snd_config_search_definition(root, "pcm_slave", str, &conf);
6830                 if (err < 0) {
6831                         SNDERR("Invalid slave definition");
6832                         return -EINVAL;
6833                 }
6834                 to_free = 1;
6835         }
6836         if (snd_config_get_type(conf) != SND_CONFIG_TYPE_COMPOUND) {
6837                 SNDERR("Invalid slave definition");
6838                 err = -EINVAL;
6839                 goto _err;
6840         }
6841         va_start(args, count);
6842         for (k = 0; k < count; ++k) {
6843                 fields[k].index = va_arg(args, int);
6844                 fields[k].flags = va_arg(args, int);
6845                 fields[k].ptr = va_arg(args, void *);
6846                 fields[k].present = 0;
6847         }
6848         va_end(args);
6849         snd_config_for_each(i, next, conf) {
6850                 snd_config_t *n = snd_config_iterator_entry(i);
6851                 const char *id;
6852                 if (snd_config_get_id(n, &id) < 0)
6853                         continue;
6854                 if (strcmp(id, "comment") == 0)
6855                         continue;
6856                 if (strcmp(id, "pcm") == 0) {
6857                         if (pcm_conf != NULL)
6858                                 snd_config_delete(pcm_conf);
6859                         if ((err = snd_config_copy(&pcm_conf, n)) < 0)
6860                                 goto _err;
6861                         continue;
6862                 }
6863                 for (k = 0; k < count; ++k) {
6864                         unsigned int idx = fields[k].index;
6865                         long v;
6866                         assert(idx < SND_PCM_HW_PARAM_LAST_INTERVAL);
6867                         assert(names[idx]);
6868                         if (strcmp(id, names[idx]) != 0)
6869                                 continue;
6870                         switch (idx) {
6871                         case SND_PCM_HW_PARAM_FORMAT:
6872                         {
6873                                 snd_pcm_format_t f;
6874                                 err = snd_config_get_string(n, &str);
6875                                 if (err < 0) {
6876                                 _invalid:
6877                                         SNDERR("invalid type for %s", id);
6878                                         goto _err;
6879                                 }
6880                                 if ((fields[k].flags & SCONF_UNCHANGED) &&
6881                                     strcasecmp(str, "unchanged") == 0) {
6882                                         *(snd_pcm_format_t*)fields[k].ptr = (snd_pcm_format_t) -2;
6883                                         break;
6884                                 }
6885                                 f = snd_pcm_format_value(str);
6886                                 if (f == SND_PCM_FORMAT_UNKNOWN) {
6887                                         SNDERR("unknown format %s", str);
6888                                         err = -EINVAL;
6889                                         goto _err;
6890                                 }
6891                                 *(snd_pcm_format_t*)fields[k].ptr = f;
6892                                 break;
6893                         }
6894                         default:
6895                                 if ((fields[k].flags & SCONF_UNCHANGED)) {
6896                                         err = snd_config_get_string(n, &str);
6897                                         if (err >= 0 &&
6898                                             strcasecmp(str, "unchanged") == 0) {
6899                                                 *(int*)fields[k].ptr = -2;
6900                                                 break;
6901                                         }
6902                                 }
6903                                 err = snd_config_get_integer(n, &v);
6904                                 if (err < 0)
6905                                         goto _invalid;
6906                                 *(int*)fields[k].ptr = v;
6907                                 break;
6908                         }
6909                         fields[k].present = 1;
6910                         break;
6911                 }
6912                 if (k < count)
6913                         continue;
6914                 SNDERR("Unknown field %s", id);
6915                 err = -EINVAL;
6916                 goto _err;
6917         }
6918         if (!pcm_conf) {
6919                 SNDERR("missing field pcm");
6920                 err = -EINVAL;
6921                 goto _err;
6922         }
6923         for (k = 0; k < count; ++k) {
6924                 if ((fields[k].flags & SCONF_MANDATORY) && !fields[k].present) {
6925                         SNDERR("missing field %s", names[fields[k].index]);
6926                         err = -EINVAL;
6927                         goto _err;
6928                 }
6929         }
6930         *_pcm_conf = pcm_conf;
6931         pcm_conf = NULL;
6932         err = 0;
6933  _err:
6934         if (pcm_conf)
6935                 snd_config_delete(pcm_conf);
6936         if (to_free)
6937                 snd_config_delete(conf);
6938         return err;
6939 }
6940                 
6941
6942 int snd_pcm_conf_generic_id(const char *id)
6943 {
6944         static const char ids[3][8] = { "comment", "type", "hint" };
6945         unsigned int k;
6946         for (k = 0; k < sizeof(ids) / sizeof(ids[0]); ++k) {
6947                 if (strcmp(id, ids[k]) == 0)
6948                         return 1;
6949         }
6950         return 0;
6951 }
6952
6953 static void snd_pcm_set_ptr(snd_pcm_t *pcm, snd_pcm_rbptr_t *rbptr,
6954                             volatile snd_pcm_uframes_t *hw_ptr, int fd, off_t offset)
6955 {
6956         rbptr->master = NULL;   /* I'm master */
6957         rbptr->ptr = hw_ptr;
6958         rbptr->fd = fd;
6959         rbptr->offset = offset;
6960         if (rbptr->changed)
6961                 rbptr->changed(pcm, NULL);
6962 }
6963
6964 void snd_pcm_set_hw_ptr(snd_pcm_t *pcm, volatile snd_pcm_uframes_t *hw_ptr, int fd, off_t offset)
6965 {
6966         assert(pcm);
6967         assert(hw_ptr);
6968         snd_pcm_set_ptr(pcm, &pcm->hw, hw_ptr, fd, offset);
6969 }
6970
6971 void snd_pcm_set_appl_ptr(snd_pcm_t *pcm, volatile snd_pcm_uframes_t *appl_ptr, int fd, off_t offset)
6972 {
6973         assert(pcm);
6974         assert(appl_ptr);
6975         snd_pcm_set_ptr(pcm, &pcm->appl, appl_ptr, fd, offset);
6976 }
6977
6978 static void snd_pcm_link_ptr(snd_pcm_t *pcm, snd_pcm_rbptr_t *pcm_rbptr,
6979                              snd_pcm_t *slave, snd_pcm_rbptr_t *slave_rbptr)
6980 {
6981         snd_pcm_t **a;
6982         int idx;
6983         
6984         a = slave_rbptr->link_dst;
6985         for (idx = 0; idx < slave_rbptr->link_dst_count; idx++)
6986                 if (a[idx] == NULL) {
6987                         a[idx] = pcm;
6988                         goto __found_free_place;
6989                 }
6990         a = realloc(a, sizeof(snd_pcm_t *) * (slave_rbptr->link_dst_count + 1));
6991         if (a == NULL) {
6992                 pcm_rbptr->ptr = NULL;
6993                 pcm_rbptr->fd = -1;
6994                 pcm_rbptr->offset = 0UL;
6995                 return;
6996         }
6997         a[slave_rbptr->link_dst_count++] = pcm;
6998       __found_free_place:
6999         pcm_rbptr->master = slave_rbptr->master ? slave_rbptr->master : slave;
7000         pcm_rbptr->ptr = slave_rbptr->ptr;
7001         pcm_rbptr->fd = slave_rbptr->fd;
7002         pcm_rbptr->offset = slave_rbptr->offset;
7003         slave_rbptr->link_dst = a;
7004         if (pcm_rbptr->changed)
7005                 pcm_rbptr->changed(pcm, slave);
7006 }
7007
7008 static void snd_pcm_unlink_ptr(snd_pcm_t *pcm, snd_pcm_rbptr_t *pcm_rbptr,
7009                                snd_pcm_t *slave, snd_pcm_rbptr_t *slave_rbptr)
7010 {
7011         snd_pcm_t **a;
7012         int idx;
7013
7014         a = slave_rbptr->link_dst;
7015         for (idx = 0; idx < slave_rbptr->link_dst_count; idx++) {
7016                 if (a[idx] == pcm) {
7017                         a[idx] = NULL;
7018                         goto __found;
7019                 }
7020         }
7021         /* assert(0); */
7022         return;
7023
7024       __found:
7025         pcm_rbptr->master = NULL;
7026         pcm_rbptr->ptr = NULL;
7027         pcm_rbptr->fd = -1;
7028         pcm_rbptr->offset = 0UL;
7029         if (pcm_rbptr->changed)
7030                 pcm_rbptr->changed(pcm, slave);
7031 }
7032
7033 void snd_pcm_link_hw_ptr(snd_pcm_t *pcm, snd_pcm_t *slave)
7034 {
7035         assert(pcm);
7036         assert(slave);
7037         snd_pcm_link_ptr(pcm, &pcm->hw, slave, &slave->hw);
7038 }
7039
7040 void snd_pcm_link_appl_ptr(snd_pcm_t *pcm, snd_pcm_t *slave)
7041 {
7042         assert(pcm);
7043         assert(slave);
7044         snd_pcm_link_ptr(pcm, &pcm->appl, slave, &slave->appl);
7045 }
7046
7047 void snd_pcm_unlink_hw_ptr(snd_pcm_t *pcm, snd_pcm_t *slave)
7048 {
7049         assert(pcm);
7050         assert(slave);
7051         snd_pcm_unlink_ptr(pcm, &pcm->hw, slave, &slave->hw);
7052 }
7053
7054 void snd_pcm_unlink_appl_ptr(snd_pcm_t *pcm, snd_pcm_t *slave)
7055 {
7056         assert(pcm);
7057         assert(slave);
7058         snd_pcm_unlink_ptr(pcm, &pcm->appl, slave, &slave->appl);
7059 }
7060
7061 #endif /* DOC_HIDDEN */
7062
7063 /*
7064  *
7065  */
7066
7067 #ifndef DOC_HIDDEN
7068
7069 #ifdef USE_VERSIONED_SYMBOLS
7070
7071 #define OBSOLETE1(name, what, new) \
7072   default_symbol_version(__##name, name, new); \
7073   symbol_version(__old_##name, name, what);
7074
7075 #else
7076
7077 #define OBSOLETE1(name, what, new) \
7078   use_default_symbol_version(__##name, name, new);
7079
7080 #endif /* USE_VERSIONED_SYMBOLS */
7081
7082 #define __P_OLD_GET(pfx, name, val_type, ret_type) \
7083 ret_type pfx##name(const snd_pcm_hw_params_t *params) \
7084 { \
7085         val_type val; \
7086         if (INTERNAL(name)(params, &val) < 0) \
7087                 return 0; \
7088         return (ret_type)val; \
7089 }
7090
7091 #define __P_OLD_GET1(pfx, name, val_type, ret_type) \
7092 ret_type pfx##name(const snd_pcm_hw_params_t *params, int *dir) \
7093 { \
7094         val_type val; \
7095         if (INTERNAL(name)(params, &val, dir) < 0) \
7096                 return 0; \
7097         return (ret_type)val; \
7098 }
7099
7100 #define __OLD_GET(name, val_type, ret_type) __P_OLD_GET(__old_, name, val_type, ret_type)
7101 #define __OLD_GET1(name, val_type, ret_type) __P_OLD_GET1(__old_, name, val_type, ret_type)
7102
7103 __OLD_GET(snd_pcm_hw_params_get_access, snd_pcm_access_t, int);
7104 __OLD_GET(snd_pcm_hw_params_get_format, snd_pcm_format_t, int);
7105 __OLD_GET(snd_pcm_hw_params_get_subformat, snd_pcm_subformat_t, int);
7106 __OLD_GET(snd_pcm_hw_params_get_channels, unsigned int, int);
7107 __OLD_GET1(snd_pcm_hw_params_get_rate, unsigned int, int);
7108 __OLD_GET1(snd_pcm_hw_params_get_period_time, unsigned int, int);
7109 __OLD_GET1(snd_pcm_hw_params_get_period_size, snd_pcm_uframes_t, snd_pcm_sframes_t);
7110 __OLD_GET1(snd_pcm_hw_params_get_periods, unsigned int, int);
7111 __OLD_GET1(snd_pcm_hw_params_get_buffer_time, unsigned int, int);
7112 __OLD_GET(snd_pcm_hw_params_get_buffer_size, snd_pcm_uframes_t, snd_pcm_sframes_t);
7113 __OLD_GET1(snd_pcm_hw_params_get_tick_time, unsigned int, int);
7114
7115 __OLD_GET(snd_pcm_hw_params_get_channels_min, unsigned int, unsigned int);
7116 __OLD_GET1(snd_pcm_hw_params_get_rate_min, unsigned int, unsigned int);
7117 __OLD_GET1(snd_pcm_hw_params_get_period_time_min, unsigned int, unsigned int);
7118 __OLD_GET1(snd_pcm_hw_params_get_period_size_min, snd_pcm_uframes_t, snd_pcm_uframes_t);
7119 __OLD_GET1(snd_pcm_hw_params_get_periods_min, unsigned int, unsigned int);
7120 __OLD_GET1(snd_pcm_hw_params_get_buffer_time_min, unsigned int, unsigned int);
7121 __OLD_GET(snd_pcm_hw_params_get_buffer_size_min, snd_pcm_uframes_t, snd_pcm_uframes_t);
7122 __OLD_GET1(snd_pcm_hw_params_get_tick_time_min, unsigned int, unsigned int);
7123
7124 __OLD_GET(snd_pcm_hw_params_get_channels_max, unsigned int, unsigned int);
7125 __OLD_GET1(snd_pcm_hw_params_get_rate_max, unsigned int, unsigned int);
7126 __OLD_GET1(snd_pcm_hw_params_get_period_time_max, unsigned int, unsigned int);
7127 __OLD_GET1(snd_pcm_hw_params_get_period_size_max, snd_pcm_uframes_t, snd_pcm_uframes_t);
7128 __OLD_GET1(snd_pcm_hw_params_get_periods_max, unsigned int, unsigned int);
7129 __OLD_GET1(snd_pcm_hw_params_get_buffer_time_max, unsigned int, unsigned int);
7130 __OLD_GET(snd_pcm_hw_params_get_buffer_size_max, snd_pcm_uframes_t, snd_pcm_uframes_t);
7131 __OLD_GET1(snd_pcm_hw_params_get_tick_time_max, unsigned int, unsigned int);
7132
7133 #define __P_OLD_NEAR(pfx, name, ret_type) \
7134 ret_type pfx##name(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, ret_type val) \
7135 { \
7136         if (INTERNAL(name)(pcm, params, &val) < 0) \
7137                 return 0; \
7138         return (ret_type)val; \
7139 }
7140
7141 #define __P_OLD_NEAR1(pfx, name, ret_type) \
7142 ret_type pfx##name(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, ret_type val, int *dir) \
7143 { \
7144         if (INTERNAL(name)(pcm, params, &val, dir) < 0) \
7145                 return 0; \
7146         return (ret_type)val; \
7147 }
7148
7149 #define __OLD_NEAR(name, ret_type) __P_OLD_NEAR(__old_, name, ret_type)
7150 #define __OLD_NEAR1(name, ret_type) __P_OLD_NEAR1(__old_, name, ret_type)
7151
7152 __OLD_NEAR(snd_pcm_hw_params_set_channels_near, unsigned int);
7153 __OLD_NEAR1(snd_pcm_hw_params_set_rate_near, unsigned int);
7154 __OLD_NEAR1(snd_pcm_hw_params_set_period_time_near, unsigned int);
7155 __OLD_NEAR1(snd_pcm_hw_params_set_period_size_near, snd_pcm_uframes_t);
7156 __OLD_NEAR1(snd_pcm_hw_params_set_periods_near, unsigned int);
7157 __OLD_NEAR1(snd_pcm_hw_params_set_buffer_time_near, unsigned int);
7158 __OLD_NEAR(snd_pcm_hw_params_set_buffer_size_near, snd_pcm_uframes_t);
7159 __OLD_NEAR1(snd_pcm_hw_params_set_tick_time_near, unsigned int);
7160
7161 #define __P_OLD_SET_FL(pfx, name, ret_type) \
7162 ret_type pfx##name(snd_pcm_t *pcm, snd_pcm_hw_params_t *params) \
7163 { \
7164         ret_type val; \
7165         if (INTERNAL(name)(pcm, params, &val) < 0) \
7166                 return 0; \
7167         return (ret_type)val; \
7168 }
7169
7170 #define __P_OLD_SET_FL1(pfx, name, ret_type) \
7171 ret_type pfx##name(snd_pcm_t *pcm, snd_pcm_hw_params_t *params, int *dir) \
7172 { \
7173         ret_type val; \
7174         if (INTERNAL(name)(pcm, params, &val, dir) < 0) \
7175                 return 0; \
7176         return (ret_type)val; \
7177 }
7178
7179 #define __OLD_SET_FL(name, ret_type) __P_OLD_SET_FL(__old_, name, ret_type)
7180 #define __OLD_SET_FL1(name, ret_type) __P_OLD_SET_FL1(__old_, name, ret_type)
7181
7182 __OLD_SET_FL(snd_pcm_hw_params_set_access_first, snd_pcm_access_t);
7183 __OLD_SET_FL(snd_pcm_hw_params_set_format_first, snd_pcm_format_t);
7184 __OLD_SET_FL(snd_pcm_hw_params_set_subformat_first, snd_pcm_subformat_t);
7185 __OLD_SET_FL(snd_pcm_hw_params_set_channels_first, unsigned int);
7186 __OLD_SET_FL1(snd_pcm_hw_params_set_rate_first, unsigned int);
7187 __OLD_SET_FL1(snd_pcm_hw_params_set_period_time_first, unsigned int);
7188 __OLD_SET_FL1(snd_pcm_hw_params_set_period_size_first, snd_pcm_uframes_t);
7189 __OLD_SET_FL1(snd_pcm_hw_params_set_periods_first, unsigned int);
7190 __OLD_SET_FL1(snd_pcm_hw_params_set_buffer_time_first, unsigned int);
7191 __OLD_SET_FL(snd_pcm_hw_params_set_buffer_size_first, snd_pcm_uframes_t);
7192 __OLD_SET_FL1(snd_pcm_hw_params_set_tick_time_first, unsigned int);
7193
7194 __OLD_SET_FL(snd_pcm_hw_params_set_access_last, snd_pcm_access_t);
7195 __OLD_SET_FL(snd_pcm_hw_params_set_format_last, snd_pcm_format_t);
7196 __OLD_SET_FL(snd_pcm_hw_params_set_subformat_last, snd_pcm_subformat_t);
7197 __OLD_SET_FL(snd_pcm_hw_params_set_channels_last, unsigned int);
7198 __OLD_SET_FL1(snd_pcm_hw_params_set_rate_last, unsigned int);
7199 __OLD_SET_FL1(snd_pcm_hw_params_set_period_time_last, unsigned int);
7200 __OLD_SET_FL1(snd_pcm_hw_params_set_period_size_last, snd_pcm_uframes_t);
7201 __OLD_SET_FL1(snd_pcm_hw_params_set_periods_last, unsigned int);
7202 __OLD_SET_FL1(snd_pcm_hw_params_set_buffer_time_last, unsigned int);
7203 __OLD_SET_FL(snd_pcm_hw_params_set_buffer_size_last, snd_pcm_uframes_t);
7204 __OLD_SET_FL1(snd_pcm_hw_params_set_tick_time_last, unsigned int);
7205
7206 #define __P_OLD_GET_SW(pfx, name, ret_type) \
7207 ret_type pfx##name(snd_pcm_sw_params_t *params) \
7208 { \
7209         ret_type val; \
7210         if (INTERNAL(name)(params, &val) < 0) \
7211                 return 0; \
7212         return (ret_type)val; \
7213 }
7214
7215 #define __OLD_GET_SW(name, ret_type) __P_OLD_GET_SW(__old_, name, ret_type)
7216
7217 __OLD_GET_SW(snd_pcm_sw_params_get_tstamp_mode, snd_pcm_tstamp_t);
7218 __OLD_GET_SW(snd_pcm_sw_params_get_sleep_min, unsigned int);
7219 __OLD_GET_SW(snd_pcm_sw_params_get_avail_min, snd_pcm_uframes_t);
7220 __OLD_GET_SW(snd_pcm_sw_params_get_xfer_align, snd_pcm_uframes_t);
7221 __OLD_GET_SW(snd_pcm_sw_params_get_start_threshold, snd_pcm_uframes_t);
7222 __OLD_GET_SW(snd_pcm_sw_params_get_stop_threshold, snd_pcm_uframes_t);
7223 __OLD_GET_SW(snd_pcm_sw_params_get_silence_threshold, snd_pcm_uframes_t);
7224 __OLD_GET_SW(snd_pcm_sw_params_get_silence_size, snd_pcm_uframes_t);
7225
7226 OBSOLETE1(snd_pcm_hw_params_get_access, ALSA_0.9, ALSA_0.9.0rc4);
7227 OBSOLETE1(snd_pcm_hw_params_set_access_first, ALSA_0.9, ALSA_0.9.0rc4);
7228 OBSOLETE1(snd_pcm_hw_params_set_access_last, ALSA_0.9, ALSA_0.9.0rc4);
7229
7230 OBSOLETE1(snd_pcm_hw_params_get_format, ALSA_0.9, ALSA_0.9.0rc4);
7231 OBSOLETE1(snd_pcm_hw_params_set_format_first, ALSA_0.9, ALSA_0.9.0rc4);
7232 OBSOLETE1(snd_pcm_hw_params_set_format_last, ALSA_0.9, ALSA_0.9.0rc4);
7233
7234 OBSOLETE1(snd_pcm_hw_params_get_subformat, ALSA_0.9, ALSA_0.9.0rc4);
7235 OBSOLETE1(snd_pcm_hw_params_set_subformat_first, ALSA_0.9, ALSA_0.9.0rc4);
7236 OBSOLETE1(snd_pcm_hw_params_set_subformat_last, ALSA_0.9, ALSA_0.9.0rc4);
7237
7238 OBSOLETE1(snd_pcm_hw_params_get_channels, ALSA_0.9, ALSA_0.9.0rc4);
7239 OBSOLETE1(snd_pcm_hw_params_get_channels_min, ALSA_0.9, ALSA_0.9.0rc4);
7240 OBSOLETE1(snd_pcm_hw_params_get_channels_max, ALSA_0.9, ALSA_0.9.0rc4);
7241 OBSOLETE1(snd_pcm_hw_params_set_channels_near, ALSA_0.9, ALSA_0.9.0rc4);
7242 OBSOLETE1(snd_pcm_hw_params_set_channels_first, ALSA_0.9, ALSA_0.9.0rc4);
7243 OBSOLETE1(snd_pcm_hw_params_set_channels_last, ALSA_0.9, ALSA_0.9.0rc4);
7244
7245 OBSOLETE1(snd_pcm_hw_params_get_rate, ALSA_0.9, ALSA_0.9.0rc4);
7246 OBSOLETE1(snd_pcm_hw_params_get_rate_min, ALSA_0.9, ALSA_0.9.0rc4);
7247 OBSOLETE1(snd_pcm_hw_params_get_rate_max, ALSA_0.9, ALSA_0.9.0rc4);
7248 OBSOLETE1(snd_pcm_hw_params_set_rate_near, ALSA_0.9, ALSA_0.9.0rc4);
7249 OBSOLETE1(snd_pcm_hw_params_set_rate_first, ALSA_0.9, ALSA_0.9.0rc4);
7250 OBSOLETE1(snd_pcm_hw_params_set_rate_last, ALSA_0.9, ALSA_0.9.0rc4);
7251
7252 OBSOLETE1(snd_pcm_hw_params_get_period_time, ALSA_0.9, ALSA_0.9.0rc4);
7253 OBSOLETE1(snd_pcm_hw_params_get_period_time_min, ALSA_0.9, ALSA_0.9.0rc4);
7254 OBSOLETE1(snd_pcm_hw_params_get_period_time_max, ALSA_0.9, ALSA_0.9.0rc4);
7255 OBSOLETE1(snd_pcm_hw_params_set_period_time_near, ALSA_0.9, ALSA_0.9.0rc4);
7256 OBSOLETE1(snd_pcm_hw_params_set_period_time_first, ALSA_0.9, ALSA_0.9.0rc4);
7257 OBSOLETE1(snd_pcm_hw_params_set_period_time_last, ALSA_0.9, ALSA_0.9.0rc4);
7258
7259 OBSOLETE1(snd_pcm_hw_params_get_period_size, ALSA_0.9, ALSA_0.9.0rc4);
7260 OBSOLETE1(snd_pcm_hw_params_get_period_size_min, ALSA_0.9, ALSA_0.9.0rc4);
7261 OBSOLETE1(snd_pcm_hw_params_get_period_size_max, ALSA_0.9, ALSA_0.9.0rc4);
7262 OBSOLETE1(snd_pcm_hw_params_set_period_size_near, ALSA_0.9, ALSA_0.9.0rc4);
7263 OBSOLETE1(snd_pcm_hw_params_set_period_size_first, ALSA_0.9, ALSA_0.9.0rc4);
7264 OBSOLETE1(snd_pcm_hw_params_set_period_size_last, ALSA_0.9, ALSA_0.9.0rc4);
7265
7266 OBSOLETE1(snd_pcm_hw_params_get_periods, ALSA_0.9, ALSA_0.9.0rc4);
7267 OBSOLETE1(snd_pcm_hw_params_get_periods_min, ALSA_0.9, ALSA_0.9.0rc4);
7268 OBSOLETE1(snd_pcm_hw_params_get_periods_max, ALSA_0.9, ALSA_0.9.0rc4);
7269 OBSOLETE1(snd_pcm_hw_params_set_periods_near, ALSA_0.9, ALSA_0.9.0rc4);
7270 OBSOLETE1(snd_pcm_hw_params_set_periods_first, ALSA_0.9, ALSA_0.9.0rc4);
7271 OBSOLETE1(snd_pcm_hw_params_set_periods_last, ALSA_0.9, ALSA_0.9.0rc4);
7272
7273 OBSOLETE1(snd_pcm_hw_params_get_buffer_time, ALSA_0.9, ALSA_0.9.0rc4);
7274 OBSOLETE1(snd_pcm_hw_params_get_buffer_time_min, ALSA_0.9, ALSA_0.9.0rc4);
7275 OBSOLETE1(snd_pcm_hw_params_get_buffer_time_max, ALSA_0.9, ALSA_0.9.0rc4);
7276 OBSOLETE1(snd_pcm_hw_params_set_buffer_time_near, ALSA_0.9, ALSA_0.9.0rc4);
7277 OBSOLETE1(snd_pcm_hw_params_set_buffer_time_first, ALSA_0.9, ALSA_0.9.0rc4);
7278 OBSOLETE1(snd_pcm_hw_params_set_buffer_time_last, ALSA_0.9, ALSA_0.9.0rc4);
7279
7280 OBSOLETE1(snd_pcm_hw_params_get_buffer_size, ALSA_0.9, ALSA_0.9.0rc4);
7281 OBSOLETE1(snd_pcm_hw_params_get_buffer_size_min, ALSA_0.9, ALSA_0.9.0rc4);
7282 OBSOLETE1(snd_pcm_hw_params_get_buffer_size_max, ALSA_0.9, ALSA_0.9.0rc4);
7283 OBSOLETE1(snd_pcm_hw_params_set_buffer_size_near, ALSA_0.9, ALSA_0.9.0rc4);
7284 OBSOLETE1(snd_pcm_hw_params_set_buffer_size_first, ALSA_0.9, ALSA_0.9.0rc4);
7285 OBSOLETE1(snd_pcm_hw_params_set_buffer_size_last, ALSA_0.9, ALSA_0.9.0rc4);
7286
7287 OBSOLETE1(snd_pcm_hw_params_get_tick_time, ALSA_0.9, ALSA_0.9.0rc4);
7288 OBSOLETE1(snd_pcm_hw_params_get_tick_time_min, ALSA_0.9, ALSA_0.9.0rc4);
7289 OBSOLETE1(snd_pcm_hw_params_get_tick_time_max, ALSA_0.9, ALSA_0.9.0rc4);
7290 OBSOLETE1(snd_pcm_hw_params_set_tick_time_near, ALSA_0.9, ALSA_0.9.0rc4);
7291 OBSOLETE1(snd_pcm_hw_params_set_tick_time_first, ALSA_0.9, ALSA_0.9.0rc4);
7292 OBSOLETE1(snd_pcm_hw_params_set_tick_time_last, ALSA_0.9, ALSA_0.9.0rc4);
7293
7294 OBSOLETE1(snd_pcm_sw_params_get_tstamp_mode, ALSA_0.9, ALSA_0.9.0rc4);
7295 OBSOLETE1(snd_pcm_sw_params_get_sleep_min, ALSA_0.9, ALSA_0.9.0rc4);
7296 OBSOLETE1(snd_pcm_sw_params_get_avail_min, ALSA_0.9, ALSA_0.9.0rc4);
7297 OBSOLETE1(snd_pcm_sw_params_get_xfer_align, ALSA_0.9, ALSA_0.9.0rc4);
7298 OBSOLETE1(snd_pcm_sw_params_get_start_threshold, ALSA_0.9, ALSA_0.9.0rc4);
7299 OBSOLETE1(snd_pcm_sw_params_get_stop_threshold, ALSA_0.9, ALSA_0.9.0rc4);
7300 OBSOLETE1(snd_pcm_sw_params_get_silence_threshold, ALSA_0.9, ALSA_0.9.0rc4);
7301 OBSOLETE1(snd_pcm_sw_params_get_silence_size, ALSA_0.9, ALSA_0.9.0rc4);
7302
7303 #endif /* DOC_HIDDEN */
7304
7305 /*
7306  * basic helpers
7307  */
7308  
7309  
7310 /**
7311  * \brief Recover the stream state from an error or suspend
7312  * \param pcm PCM handle
7313  * \param err error number
7314  * \param silent do not print error reason
7315  * \return 0 when error code was handled successfuly, otherwise a negative error code
7316  *
7317  * This a high-level helper function building on other functions.
7318  *
7319  * This functions handles -EINTR (interrupted system call),
7320  * -EPIPE (overrun or underrun) and -ESTRPIPE (stream is suspended)
7321  * error codes trying to prepare given stream for next I/O.
7322  *
7323  * Note that this function returs the original error code when it is not
7324  * handled inside this function (for example -EAGAIN is returned back).
7325  */
7326 int snd_pcm_recover(snd_pcm_t *pcm, int err, int silent)
7327 {
7328         if (err > 0)
7329                 err = -err;
7330         if (err == -EINTR)      /* nothing to do, continue */
7331                 return 0;
7332         if (err == -EPIPE) {
7333                 const char *s;
7334                 if (snd_pcm_stream(pcm) == SND_PCM_STREAM_PLAYBACK)
7335                         s = "underrun";
7336                 else
7337                         s = "overrun";
7338                 if (!silent)
7339                         SNDERR("%s occurred", s);
7340                 err = snd_pcm_prepare(pcm);
7341                 if (err < 0) {
7342                         SNDERR("cannot recovery from %s, prepare failed: %s", s, snd_strerror(err));
7343                         return err;
7344                 }
7345                 return 0;
7346         }
7347         if (err == -ESTRPIPE) {
7348                 while ((err = snd_pcm_resume(pcm)) == -EAGAIN)
7349                         /* wait until suspend flag is released */
7350                         poll(NULL, 0, 1000);
7351                 if (err < 0) {
7352                         err = snd_pcm_prepare(pcm);
7353                         if (err < 0) {
7354                                 SNDERR("cannot recovery from suspend, prepare failed: %s", snd_strerror(err));
7355                                 return err;
7356                         }
7357                 }
7358                 return 0;
7359         }
7360         return err;
7361 }
7362
7363 /**
7364  * \brief Set the hardware and software parameters in a simple way
7365  * \param pcm PCM handle
7366  * \param format required PCM format
7367  * \param access required PCM access
7368  * \param channels required PCM channels
7369  * \param rate required sample rate in Hz
7370  * \param soft_resample 0 = disallow alsa-lib resample stream, 1 = allow resampling
7371  * \param latency required overall latency in us
7372  * \return 0 on success otherwise a negative error code
7373  */
7374 int snd_pcm_set_params(snd_pcm_t *pcm,
7375                        snd_pcm_format_t format,
7376                        snd_pcm_access_t access,
7377                        unsigned int channels,
7378                        unsigned int rate,
7379                        int soft_resample,
7380                        unsigned int latency)
7381 {
7382         snd_pcm_hw_params_t *params;
7383         snd_pcm_sw_params_t *swparams;
7384         const char *s = snd_pcm_stream_name(snd_pcm_stream(pcm));
7385         snd_pcm_uframes_t buffer_size, period_size;
7386         unsigned int rrate, period_time;
7387         int err;
7388
7389         snd_pcm_hw_params_alloca(&params);
7390         snd_pcm_sw_params_alloca(&swparams);
7391
7392         assert(pcm);
7393         /* choose all parameters */
7394         err = snd_pcm_hw_params_any(pcm, params);
7395         if (err < 0) {
7396                 SNDERR("Broken configuration for %s: no configurations available", s);
7397                 return err;
7398         }
7399         /* set software resampling */
7400         err = snd_pcm_hw_params_set_rate_resample(pcm, params, soft_resample);
7401         if (err < 0) {
7402                 SNDERR("Resampling setup failed for %s: %s", s, snd_strerror(err));
7403                 return err;
7404         }
7405         /* set the selected read/write format */
7406         err = snd_pcm_hw_params_set_access(pcm, params, access);
7407         if (err < 0) {
7408                 SNDERR("Access type not available for %s: %s", s, snd_strerror(err));
7409                 return err;
7410         }
7411         /* set the sample format */
7412         err = snd_pcm_hw_params_set_format(pcm, params, format);
7413         if (err < 0) {
7414                 SNDERR("Sample format not available for %s: %s", s, snd_strerror(err));
7415                 return err;
7416         }
7417         /* set the count of channels */
7418         err = snd_pcm_hw_params_set_channels(pcm, params, channels);
7419         if (err < 0) {
7420                 SNDERR("Channels count (%i) not available for %s: %s", channels, s, snd_strerror(err));
7421                 return err;
7422         }
7423         /* set the stream rate */
7424         rrate = rate;
7425         err = INTERNAL(snd_pcm_hw_params_set_rate_near)(pcm, params, &rrate, 0);
7426         if (err < 0) {
7427                 SNDERR("Rate %iHz not available for playback: %s", rate, snd_strerror(err));
7428                 return err;
7429         }
7430         if (rrate != rate) {
7431                 SNDERR("Rate doesn't match (requested %iHz, get %iHz)", rate, err);
7432                 return -EINVAL;
7433         }
7434         /* set the buffer time */
7435         err = INTERNAL(snd_pcm_hw_params_set_buffer_time_near)(pcm, params, &latency, NULL);
7436         if (err < 0) {
7437                 /* error path -> set period size as first */
7438                 /* set the period time */
7439                 period_time = latency / 4;
7440                 err = INTERNAL(snd_pcm_hw_params_set_period_time_near)(pcm, params, &period_time, NULL);
7441                 if (err < 0) {
7442                         SNDERR("Unable to set period time %i for %s: %s", period_time, s, snd_strerror(err));
7443                         return err;
7444                 }
7445                 err = INTERNAL(snd_pcm_hw_params_get_period_size)(params, &period_size, NULL);
7446                 if (err < 0) {
7447                         SNDERR("Unable to get period size for %s: %s", s, snd_strerror(err));
7448                         return err;
7449                 }
7450                 buffer_size = period_size * 4;
7451                 err = INTERNAL(snd_pcm_hw_params_set_buffer_size_near)(pcm, params, &buffer_size);
7452                 if (err < 0) {
7453                         SNDERR("Unable to set buffer size %lu %s: %s", buffer_size, s, snd_strerror(err));
7454                         return err;
7455                 }
7456                 err = INTERNAL(snd_pcm_hw_params_get_buffer_size)(params, &buffer_size);
7457                 if (err < 0) {
7458                         SNDERR("Unable to get buffer size for %s: %s", s, snd_strerror(err));
7459                         return err;
7460                 }
7461         } else {
7462                 /* standard configuration buffer_time -> periods */
7463                 err = INTERNAL(snd_pcm_hw_params_get_buffer_size)(params, &buffer_size);
7464                 if (err < 0) {
7465                         SNDERR("Unable to get buffer size for %s: %s", s, snd_strerror(err));
7466                         return err;
7467                 }
7468                 err = INTERNAL(snd_pcm_hw_params_get_buffer_time)(params, &latency, NULL);
7469                 if (err < 0) {
7470                         SNDERR("Unable to get buffer time (latency) for %s: %s", s, snd_strerror(err));
7471                         return err;
7472                 }
7473                 /* set the period time */
7474                 period_time = latency / 4;
7475                 err = INTERNAL(snd_pcm_hw_params_set_period_time_near)(pcm, params, &period_time, NULL);
7476                 if (err < 0) {
7477                         SNDERR("Unable to set period time %i for %s: %s", period_time, s, snd_strerror(err));
7478                         return err;
7479                 }
7480                 err = INTERNAL(snd_pcm_hw_params_get_period_size)(params, &period_size, NULL);
7481                 if (err < 0) {
7482                         SNDERR("Unable to get period size for %s: %s", s, snd_strerror(err));
7483                         return err;
7484                 }
7485         }
7486         /* write the parameters to device */
7487         err = snd_pcm_hw_params(pcm, params);
7488         if (err < 0) {
7489                 SNDERR("Unable to set hw params for %s: %s", s, snd_strerror(err));
7490                 return err;
7491         }
7492
7493         /* get the current swparams */
7494         err = snd_pcm_sw_params_current(pcm, swparams);
7495         if (err < 0) {
7496                 SNDERR("Unable to determine current swparams for %s: %s", s, snd_strerror(err));
7497                 return err;
7498         }
7499         /* start the transfer when the buffer is almost full: */
7500         /* (buffer_size / avail_min) * avail_min */
7501         err = snd_pcm_sw_params_set_start_threshold(pcm, swparams, (buffer_size / period_size) * period_size);
7502         if (err < 0) {
7503                 SNDERR("Unable to set start threshold mode for %s: %s", s, snd_strerror(err));
7504                 return err;
7505         }
7506         /* allow the transfer when at least period_size samples can be processed */
7507         err = snd_pcm_sw_params_set_avail_min(pcm, swparams, period_size);
7508         if (err < 0) {
7509                 SNDERR("Unable to set avail min for %s: %s", s, snd_strerror(err));
7510                 return err;
7511         }
7512         /* write the parameters to the playback device */
7513         err = snd_pcm_sw_params(pcm, swparams);
7514         if (err < 0) {
7515                 SNDERR("Unable to set sw params for %s: %s", s, snd_strerror(err));
7516                 return err;
7517         }
7518         return 0;
7519 }
7520
7521 /**
7522  * \brief Get the transfer size parameters in a simple way
7523  * \param pcm PCM handle
7524  * \param buffer_size PCM ring buffer size in frames
7525  * \param period_size PCM period size in frames
7526  * \return 0 on success otherwise a negative error code
7527  */
7528 int snd_pcm_get_params(snd_pcm_t *pcm,
7529                        snd_pcm_uframes_t *buffer_size,
7530                        snd_pcm_uframes_t *period_size)
7531 {
7532         snd_pcm_hw_params_t *hw;
7533         int err;
7534
7535         assert(pcm);
7536         snd_pcm_hw_params_alloca(&hw);
7537         err = snd_pcm_hw_params_current(pcm, hw);
7538         if (err < 0)
7539                 return err;
7540         err = INTERNAL(snd_pcm_hw_params_get_buffer_size)(hw, buffer_size);
7541         if (err < 0)
7542                 return err;
7543         err = INTERNAL(snd_pcm_hw_params_get_period_size)(hw, period_size, NULL);
7544         if (err < 0)
7545                 return err;
7546         return 0;
7547 }