And two more small changes

On Thu, 2017-08-17 at 19:05 +0300, Paul Kocialkowski wrote:
> This introduces an ALSA library, with dedicated helpers for handling
> playback and capture. It handles ALSA device identification and
> configuration as well as a run loop with callback mechanisms for
> feeding
> output data and handling input data.
> 
> This library paves the way for testing audio going through display
> connectors, such as HDMI.
> 
> Signed-off-by: Paul Kocialkowski <[email protected]>
> ---
>  configure.ac                                       |   3 +
>  .../intel-gpu-tools/intel-gpu-tools-docs.xml       |   1 +
>  lib/Makefile.am                                    |   7 +
>  lib/igt.h                                          |   1 +
>  lib/igt_alsa.c                                     | 624
> +++++++++++++++++++++
>  lib/igt_alsa.h                                     |  60 ++
>  6 files changed, 696 insertions(+)
>  create mode 100644 lib/igt_alsa.c
>  create mode 100644 lib/igt_alsa.h
> 
> diff --git a/configure.ac b/configure.ac
> index 50aa86b5..e66273a4 100644
> --- a/configure.ac
> +++ b/configure.ac
> @@ -219,6 +219,9 @@ if test "x$enable_chamelium" = xyes; then
>       AC_DEFINE(HAVE_CHAMELIUM, 1, [Enable Chamelium support])
>  fi
>  
> +PKG_CHECK_MODULES(ALSA, [alsa], [alsa=yes], [alsa=no])
> +AM_CONDITIONAL(HAVE_ALSA, [test "x$alsa" = xyes])
> +
>  # ------------------------------------------------------------------
> -----------
>  #                    Configuration options
>  # ------------------------------------------------------------------
> -----------
> diff --git a/docs/reference/intel-gpu-tools/intel-gpu-tools-docs.xml
> b/docs/reference/intel-gpu-tools/intel-gpu-tools-docs.xml
> index c77159cf..0c34e4a5 100644
> --- a/docs/reference/intel-gpu-tools/intel-gpu-tools-docs.xml
> +++ b/docs/reference/intel-gpu-tools/intel-gpu-tools-docs.xml
> @@ -16,6 +16,7 @@
>    <chapter>
>      <title>API Reference</title>
>      <xi:include href="xml/drmtest.xml"/>
> +    <xi:include href="xml/igt_alsa.xml"/>
>      <xi:include href="xml/igt_audio.xml"/>
>      <xi:include href="xml/igt_aux.xml"/>
>      <xi:include href="xml/igt_chamelium.xml"/>
> diff --git a/lib/Makefile.am b/lib/Makefile.am
> index 5ea08314..3ff14f66 100644
> --- a/lib/Makefile.am
> +++ b/lib/Makefile.am
> @@ -38,6 +38,13 @@ lib_source_list +=         \
>       $(NULL)
>  endif
>  
> +if HAVE_ALSA
> +lib_source_list +=           \
> +     igt_alsa.c              \
> +     igt_alsa.h              \
> +     $(NULL)
> +endif
> +
>  AM_CPPFLAGS = -I$(top_srcdir)
>  AM_CFLAGS = \
>           $(CWARNFLAGS) \
> diff --git a/lib/igt.h b/lib/igt.h
> index a75d2db7..ebf92349 100644
> --- a/lib/igt.h
> +++ b/lib/igt.h
> @@ -35,6 +35,7 @@
>  #include "igt_dummyload.h"
>  #include "igt_fb.h"
>  #include "igt_frame.h"
> +#include "igt_alsa.h"
>  #include "igt_audio.h"
>  #include "igt_gt.h"
>  #include "igt_kms.h"
> diff --git a/lib/igt_alsa.c b/lib/igt_alsa.c
> new file mode 100644
> index 00000000..d8bd0873
> --- /dev/null
> +++ b/lib/igt_alsa.c
> @@ -0,0 +1,624 @@
> +/*
> + * Copyright © 2017 Intel Corporation
> + *
> + * Permission is hereby granted, free of charge, to any person
> obtaining a
> + * copy of this software and associated documentation files (the
> "Software"),
> + * to deal in the Software without restriction, including without
> limitation
> + * the rights to use, copy, modify, merge, publish, distribute,
> sublicense,
> + * and/or sell copies of the Software, and to permit persons to whom
> the
> + * Software is furnished to do so, subject to the following
> conditions:
> + *
> + * The above copyright notice and this permission notice (including
> the next
> + * paragraph) shall be included in all copies or substantial
> portions of the
> + * Software.
> + *
> + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
> EXPRESS OR
> + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
> MERCHANTABILITY,
> + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO
> EVENT SHALL
> + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES
> OR OTHER
> + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
> ARISING
> + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
> OTHER DEALINGS
> + * IN THE SOFTWARE.
> + *
> + * Authors:
> + *  Paul Kocialkowski <[email protected]>
> + */
> +
> +#include "config.h"
> +
> +#include <alsa/asoundlib.h>
> +
> +#include "igt.h"
> +
> +#define HANDLES_MAX  8
> +
> +/**
> + * SECTION:igt_alsa
> + * @short_description: Library with ALSA helpers
> + * @title: ALSA
> + * @include: igt_alsa.h
> + *
> + * This library contains helpers for ALSA playback and capture.
> + */
> +
> +struct alsa {
> +     snd_pcm_t *output_handles[HANDLES_MAX];
> +     int output_handles_count;
> +     int output_sampling_rate;
> +     int output_channels;
> +
> +     int (*output_callback)(void *data, short *buffer, int
> samples);
> +     void *output_callback_data;
> +     int output_samples_trigger;
> +
> +     snd_pcm_t *input_handle;
> +     int input_sampling_rate;
> +     int input_channels;
> +
> +     int (*input_callback)(void *data, short *buffer, int
> samples);
> +     void *input_callback_data;
> +     int input_samples_trigger;
> +};
> +
> +static void alsa_error_handler(const char *file, int line, const
> char *function,
> +                            int err, const char *fmt, ...)
> +{
> +     if (err)
> +             igt_debug("[ALSA] %s: %s\n", function,
> snd_strerror(err));
> +}

Would be a good idea to add an __attribute__((printf)) here
> +
> +/**
> + * alsa_init:
> + * Allocate and initialize an alsa structure and configure the error
> handler.
> + *
> + * Returns: A newly-allocated alsa structure
> + */
> +struct alsa *alsa_init(void)
> +{
> +     struct alsa *alsa;
> +
> +     alsa = malloc(sizeof(struct alsa));
> +     memset(alsa, 0, sizeof(struct alsa));
> +
> +     /* Redirect errors to igt_debug instead of stderr. */
> +     snd_lib_error_set_handler(alsa_error_handler);
> +
> +     return alsa;
> +}
> +
> +static char *alsa_resolve_indentifier(const char *device_name, int
> skip)
> +{
> +     snd_ctl_card_info_t *card_info;
> +     snd_pcm_info_t *pcm_info;
> +     snd_ctl_t *handle = NULL;
> +     const char *pcm_name;
> +     char *identifier = NULL;
> +     char name[32];
> +     int card;
> +     int dev;
> +     int ret;
> +
> +     snd_ctl_card_info_alloca(&card_info);
> +     snd_pcm_info_alloca(&pcm_info);
> +
> +     card = -1;
Just set card = -1 at it's declaration
> +
> +     /* First try to open the device as-is. */
> +     if (!skip) {
> +             ret = snd_ctl_open(&handle, device_name, 0);
> +             if (!ret) {
> +                     identifier = strdup(device_name);
> +                     goto resolved;
> +             }
> +     }
> +
> +     do {
> +             ret = snd_card_next(&card);
> +             if (ret < 0 || card < 0)
> +                     break;
> +
> +             snprintf(name, sizeof(name), "hw:%d", card);
> +
> +             ret = snd_ctl_open(&handle, name, 0);
> +             if (ret < 0)
> +                     continue;
> +
> +             ret = snd_ctl_card_info(handle, card_info);
> +             if (ret < 0) {
> +                     snd_ctl_close(handle);
> +                     handle = NULL;
> +                     continue;
> +             }
> +
> +             dev = -1;
> +
> +             do {
> +                     ret = snd_ctl_pcm_next_device(handle, &dev);
> +                     if (ret < 0 || dev < 0)
> +                             break;
> +
> +                     snd_pcm_info_set_device(pcm_info, dev);
> +                     snd_pcm_info_set_subdevice(pcm_info, 0);
> +
> +                     ret = snd_ctl_pcm_info(handle, pcm_info);
> +                     if (ret < 0)
> +                             continue;
> +
> +                     pcm_name = snd_pcm_info_get_name(pcm_info);
> +                     if (!pcm_name)
> +                             continue;
> +
> +                     ret = strncmp(device_name, pcm_name,
> +                                   strlen(device_name));
> +
> +                     if (ret == 0) {
> +                             if (skip > 0) {
> +                                     skip--;
> +                                     continue;
> +                             }
> +
> +                             snprintf(name, sizeof(name),
> "hw:%d,%d", card,
> +                                      dev);
> +
> +                             identifier = strdup(name);
> +                             goto resolved;
> +                     }
> +             } while (dev >= 0);
> +
> +             snd_ctl_close(handle);
> +             handle = NULL;
> +     } while (card >= 0);
> +
> +resolved:
> +     if (handle)
> +             snd_ctl_close(handle);
> +
> +     return identifier;
> +}
> +
> +/**
> + * alsa_open_output:
> + * @alsa: The target alsa structure
> + * @device_name: The name prefix of the output device(s) to open
> + *
> + * Open ALSA output devices whose name prefixes match the provided
> name prefix.
> + *
> + * Returns: An integer equal to zero for success and negative for
> failure
> + */
> +int alsa_open_output(struct alsa *alsa, const char *device_name)
> +{
> +     snd_pcm_t *handle;
> +     char *identifier;
> +     int skip;
> +     int index;
> +     int ret;
> +
> +     skip = alsa->output_handles_count;
> +     index = alsa->output_handles_count;
> +
> +     while (index < HANDLES_MAX) {
> +             identifier = alsa_resolve_indentifier(device_name,
> skip++);
> +             if (!identifier)
> +                     break;
> +
> +             ret = snd_pcm_open(&handle, identifier,
> SND_PCM_STREAM_PLAYBACK,
> +                                SND_PCM_NONBLOCK);
> +             if (ret < 0) {
> +                     free(identifier);
> +                     continue;
> +             }
> +
> +             igt_debug("Opened output %s\n", identifier);
> +
> +             alsa->output_handles[index++] = handle;
> +             free(identifier);
> +     }
> +
> +     if (index == 0)
> +             return -1;
> +
> +     alsa->output_handles_count = index;
> +
> +     return 0;
> +}
> +
> +/**
> + * alsa_open_input:
> + * @alsa: The target alsa structure
> + * @device_name: The name of the input device to open
> + *
> + * Open the ALSA input device whose name matches the provided name
> prefix.
> + *
> + * Returns: An integer equal to zero for success and negative for
> failure
> + */
> +int alsa_open_input(struct alsa *alsa, const char *device_name)
> +{
> +     snd_pcm_t *handle;
> +     char *identifier;
> +     int ret;
> +
> +     identifier = alsa_resolve_indentifier(device_name, 0);
> +
> +     ret = snd_pcm_open(&handle, device_name,
> SND_PCM_STREAM_CAPTURE,
> +                        SND_PCM_NONBLOCK);
> +     if (ret < 0)
> +             goto complete;
> +
> +     igt_debug("Opened input %s\n", identifier);
> +
> +     alsa->input_handle = handle;
> +
> +     ret = 0;
> +
> +complete:
> +     free(identifier);
> +
> +     return ret;
> +}
> +
> +/**
> + * alsa_close_output:
> + * @alsa: The target alsa structure
> + *
> + * Close all the open ALSA outputs.
> + */
> +void alsa_close_output(struct alsa *alsa)
> +{
> +     snd_pcm_t *handle;
> +     int i;
> +
> +     for (i = 0; i < alsa->output_handles_count; i++) {
> +             handle = alsa->output_handles[i];
> +             if (!handle)
> +                     continue;
> +
> +             snd_pcm_close(handle);
> +             alsa->output_handles[i] = NULL;
> +     }
> +
> +     alsa->output_handles_count = 0;
> +}
> +
> +/**
> + * alsa_close_output:
> + * @alsa: The target alsa structure
> + *
> + * Close the open ALSA input.
> + */
> +void alsa_close_input(struct alsa *alsa)
> +{
> +     snd_pcm_t *handle = alsa->input_handle;
> +     if (!handle)
> +             return;
> +
> +     snd_pcm_close(handle);
> +     alsa->input_handle = NULL;
> +}
> +
> +static bool alsa_test_configuration(snd_pcm_t *handle, int channels,
> +                          int sampling_rate)
> +{
> +     snd_pcm_hw_params_t *params;
> +     int ret;
> +
> +     snd_pcm_hw_params_alloca(&params);
> +
> +     ret = snd_pcm_hw_params_any(handle, params);
> +     if (ret < 0)
> +             return false;
> +
> +     ret = snd_pcm_hw_params_test_rate(handle, params,
> sampling_rate, 0);
> +     if (ret < 0)
> +             return false;
> +
> +     ret = snd_pcm_hw_params_test_channels(handle, params,
> channels);
> +     if (ret < 0)
> +             return false;
> +
> +     return true;
> +}
> +
> +/**
> + * alsa_test_output_configuration:
> + * @alsa: The target alsa structure
> + * @channels: The number of channels to test
> + * @sampling_rate: The sampling rate to test
> + *
> + * Test the output configuration specified by @channels and
> @sampling_rate
> + * for the output devices.
> + *
> + * Returns: A boolean indicating whether the test succeeded
> + */
> +bool alsa_test_output_configuration(struct alsa *alsa, int channels,
> +                                 int sampling_rate)
> +{
> +     snd_pcm_t *handle;
> +     bool ret;
> +     int i;
> +
> +     for (i = 0; i < alsa->output_handles_count; i++) {
> +             handle = alsa->output_handles[i];
> +
> +             ret = alsa_test_configuration(handle, channels,
> sampling_rate);
> +             if (!ret)
> +                     return false;
> +     }
> +
> +     return true;
> +}
> +
> +/**
> + * alsa_test_input_configuration:
> + * @alsa: The target alsa structure
> + * @channels: The number of channels to test
> + * @sampling_rate: The sampling rate to test
> + *
> + * Test the input configuration specified by @channels and
> @sampling_rate
> + * for the input device.
> + *
> + * Returns: A boolean indicating whether the test succeeded
> + */
> +bool alsa_test_input_configuration(struct alsa *alsa, int channels,
> +                                int sampling_rate)
> +{
> +     return alsa_test_configuration(alsa->input_handle, channels,
> +                                    sampling_rate);
> +}
> +
> +/**
> + * alsa_configure_output:
> + * @alsa: The target alsa structure
> + * @channels: The number of channels to test
> + * @sampling_rate: The sampling rate to test
> + *
> + * Configure the output devices with the configuration specified by
> @channels
> + * and @sampling_rate.
> + */
> +void alsa_configure_output(struct alsa *alsa, int channels,
> +                        int sampling_rate)
> +{
> +     snd_pcm_t *handle;
> +     int ret;
> +     int i;
> +
> +     for (i = 0; i < alsa->output_handles_count; i++) {
> +             handle = alsa->output_handles[i];
> +
> +             ret = snd_pcm_set_params(handle,
> SND_PCM_FORMAT_S16_LE,
> +                                      SND_PCM_ACCESS_RW_INTERLEAV
> ED,
> +                                      channels, sampling_rate, 0,
> 0);
> +             igt_assert(ret >= 0);
> +     }
> +
> +     alsa->output_channels = channels;
> +     alsa->output_sampling_rate = sampling_rate;
> +}
> +
> +/**
> + * alsa_configure_input:
> + * @alsa: The target alsa structure
> + * @channels: The number of channels to test
> + * @sampling_rate: The sampling rate to test
> + *
> + * Configure the input device with the configuration specified by
> @channels
> + * and @sampling_rate.
> + */
> +void alsa_configure_input(struct alsa *alsa, int channels,
> +                       int sampling_rate)
> +{
> +     snd_pcm_t *handle;
> +     int ret;
> +
> +     handle = alsa->input_handle;
> +
> +     ret = snd_pcm_set_params(handle, SND_PCM_FORMAT_S16_LE,
> +                              SND_PCM_ACCESS_RW_INTERLEAVED,
> channels,
> +                              sampling_rate, 0, 0);
> +     igt_assert(ret >= 0);
> +
> +     alsa->input_channels = channels;
> +     alsa->input_sampling_rate = sampling_rate;
> +
> +}
> +
> +/**
> + * alsa_register_output_callback:
> + * @alsa: The target alsa structure
> + * @callback: The callback function to call to fill output data
> + * @callback_data: The data pointer to pass to the callback function
> + * @samples_trigger: The required number of samples to trigger the
> callback
> + *
> + * Register a callback function to be called to fill output data
> during a run.
> + * The callback is called when @samples_trigger samples are
> required.
> + *
> + * The callback should return an integer equal to zero for success
> and negative
> + * for failure.
> + */
> +void alsa_register_output_callback(struct alsa *alsa,
> +                                int (*callback)(void *data, short
> *buffer, int samples),
> +                                void *callback_data, int
> samples_trigger)
> +{
> +     alsa->output_callback = callback;
> +     alsa->output_callback_data = callback_data;
> +     alsa->output_samples_trigger = samples_trigger;
> +}
> +
> +/**
> + * alsa_register_input_callback:
> + * @alsa: The target alsa structure
> + * @callback: The callback function to call when input data is
> available
> + * @callback_data: The data pointer to pass to the callback function
> + * @samples_trigger: The required number of samples to trigger the
> callback
> + *
> + * Register a callback function to be called when input data is
> available during
> + * a run. The callback is called when @samples_trigger samples are
> available.
> + *
> + * The callback should return an integer equal to zero for success,
> negative for
> + * failure and positive to indicate that the run should stop.
> + */
> +void alsa_register_input_callback(struct alsa *alsa,
> +                               int (*callback)(void *data, short
> *buffer, int samples),
> +                               void *callback_data, int
> samples_trigger)
> +{
> +     alsa->input_callback = callback;
> +     alsa->input_callback_data = callback_data;
> +     alsa->input_samples_trigger = samples_trigger;
> +}
> +
> +/**
> + * alsa_run:
> + * @alsa: The target alsa structure
> + * @duration_ms: The maximum duration of the run in milliseconds
> + *
> + * Run ALSA playback and capture on the input and output devices for
> at
> + * most @duration_ms milliseconds, calling the registered callbacks
> when needed.
> + *
> + * Returns: An integer equal to zero for success, positive for a
> stop caused
> + * by the input callback and negative for failure
> + */
> +int alsa_run(struct alsa *alsa, int duration_ms)
> +{
> +     snd_pcm_t *handle;
> +     short *output_buffer = NULL;
> +     short *input_buffer = NULL;
> +     int output_limit;
> +     int output_total = 0;
> +     int output_counts[alsa->output_handles_count];
> +     bool output_ready = false;
> +     int output_channels;
> +     int output_trigger;
> +     int input_limit;
> +     int input_total = 0;
> +     int input_count = 0;
> +     int input_channels;
> +     int input_trigger;
> +     bool reached;
> +     int index;
> +     int count;
> +     int avail;
> +     int i;
> +     int ret;
> +
> +     output_limit = alsa->output_sampling_rate * duration_ms /
> 1000;
> +     output_channels = alsa->output_channels;
> +     output_trigger = alsa->output_samples_trigger;
> +     output_buffer = malloc(sizeof(short) * output_channels *
> +                            output_trigger);
> +
> +     if (alsa->input_callback) {
> +             input_limit = alsa->input_sampling_rate *
> duration_ms / 1000;
> +             input_trigger = alsa->input_samples_trigger;
> +             input_channels = alsa->input_channels;
> +             input_buffer = malloc(sizeof(short) * input_channels
> *
> +                                   input_trigger);
> +     }
> +
> +     do {
> +             reached = true;
> +
> +             if (output_total < output_limit) {
> +                     reached = false;
> +
> +                     if (!output_ready) {
> +                             output_ready = true;
> +
> +                             for (i = 0; i < alsa-
> >output_handles_count; i++)
> +                                     output_counts[i] = 0;
> +
> +                             ret = alsa->output_callback(alsa-
> >output_callback_data,
> +                                                         output_b
> uffer,
> +                                                         output_t
> rigger);
> +                             if (ret < 0)
> +                                     goto complete;
> +                     }
> +
> +                     for (i = 0; i < alsa->output_handles_count;
> i++) {
> +                             handle = alsa->output_handles[i];
> +
> +                             if (output_counts[i] <
> output_trigger &&
> +                                 snd_pcm_avail(handle) > 0) {
> +                                     index = output_counts[i] *
> +                                             output_channels;
> +                                     count = output_trigger -
> +                                             output_counts[i];
> +                                     avail =
> snd_pcm_avail(handle);
> +
> +                                     count = avail < count ?
> avail : count;
> +
> +                                     ret = snd_pcm_writei(handle,
> +                                                          &output
> _buffer[index],
> +                                                          count);
> +                                     if (ret < 0) {
> +                                             ret =
> snd_pcm_recover(handle,
> +                                                                 
>   count, 0);
> +                                             if (ret < 0)
> +                                                     goto
> complete;
> +                                     }
> +
> +                                     output_counts[i] += ret;
> +                             }
> +                     }
> +
> +                     output_ready = false;
> +
> +                     for (i = 0; i < alsa->output_handles_count;
> i++)
> +                             if (output_counts[i] <
> output_trigger)
> +                                     output_ready = true;
> +
> +                     if (!output_ready)
> +                             output_total += output_trigger;
> +
> +             }
> +
> +             if (alsa->input_callback && input_total <
> input_limit) {
> +                     reached = false;
> +
> +                     if (input_count == input_trigger) {
> +                             input_count = 0;
> +
> +                             ret = alsa->input_callback(alsa-
> >input_callback_data,
> +                                                        input_buf
> fer,
> +                                                        input_tri
> gger);
> +                             if (ret != 0)
> +                                     goto complete;
> +                     }
> +
> +                     handle = alsa->input_handle;
> +
> +                     if (input_count < input_trigger &&
> +                         (snd_pcm_avail(handle) > 0 ||
> input_total == 0)) {
> +                             index = input_count *
> input_channels;
> +                             count = input_trigger - input_count;
> +                             avail = snd_pcm_avail(handle);
> +
> +                             count = avail > 0 && avail < count ?
> avail :
> +                                     count;
> +
> +                             ret = snd_pcm_readi(handle,
> +                                                 &input_buffer[in
> dex],
> +                                                 count);
> +                             if (ret == -EAGAIN) {
> +                                     ret = 0;
> +                             } else if (ret < 0) {
> +                                     ret =
> snd_pcm_recover(handle, count, 0);
> +                                     if (ret < 0)
> +                                             goto complete;
> +                             }
> +
> +                             input_count += ret;
> +                             input_total += ret;
> +                     }
> +             }
> +     } while (!reached);
> +
> +     ret = 0;
> +
> +complete:
> +     if (output_buffer)
> +             free(output_buffer);
> +
> +     if (input_buffer)
> +             free(input_buffer);
> +
> +     return ret;
> +}
> diff --git a/lib/igt_alsa.h b/lib/igt_alsa.h
> new file mode 100644
> index 00000000..9911ddde
> --- /dev/null
> +++ b/lib/igt_alsa.h
> @@ -0,0 +1,60 @@
> +/*
> + * Copyright © 2017 Intel Corporation
> + *
> + * Permission is hereby granted, free of charge, to any person
> obtaining a
> + * copy of this software and associated documentation files (the
> "Software"),
> + * to deal in the Software without restriction, including without
> limitation
> + * the rights to use, copy, modify, merge, publish, distribute,
> sublicense,
> + * and/or sell copies of the Software, and to permit persons to whom
> the
> + * Software is furnished to do so, subject to the following
> conditions:
> + *
> + * The above copyright notice and this permission notice (including
> the next
> + * paragraph) shall be included in all copies or substantial
> portions of the
> + * Software.
> + *
> + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
> EXPRESS OR
> + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
> MERCHANTABILITY,
> + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO
> EVENT SHALL
> + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES
> OR OTHER
> + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
> ARISING
> + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
> OTHER DEALINGS
> + * IN THE SOFTWARE.
> + *
> + * Authors:
> + *  Paul Kocialkowski <[email protected]>
> + */
> +
> +#ifndef IGT_ALSA_H
> +#define IGT_ALSA_H
> +
> +#ifdef HAVE_CONFIG_H
> +#include "config.h"
> +#endif
> +
> +#include "igt.h"
> +#include <stdbool.h>
> +
> +struct alsa;
> +
> +struct alsa *alsa_init(void);
> +int alsa_open_output(struct alsa *alsa, const char *device_name);
> +int alsa_open_input(struct alsa *alsa, const char *device_name);
> +void alsa_close_output(struct alsa *alsa);
> +void alsa_close_input(struct alsa *alsa);
> +bool alsa_test_output_configuration(struct alsa *alsa, int channels,
> +                                 int sampling_rate);
> +bool alsa_test_input_configuration(struct alsa *alsa, int channels,
> +                                int sampling_rate);
> +void alsa_configure_output(struct alsa *alsa, int channels,
> +                        int sampling_rate);
> +void alsa_configure_input(struct alsa *alsa, int channels,
> +                       int sampling_rate);
> +void alsa_register_output_callback(struct alsa *alsa,
> +                                int (*callback)(void *data, short
> *buffer, int samples),
> +                                void *callback_data, int
> samples_trigger);
> +void alsa_register_input_callback(struct alsa *alsa,
> +                               int (*callback)(void *data, short
> *buffer, int samples),
> +                               void *callback_data, int
> samples_trigger);
> +int alsa_run(struct alsa *alsa, int duration_ms);
> +
> +#endif
_______________________________________________
Intel-gfx mailing list
[email protected]
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

Reply via email to