Apalis-imx8 audio devices cannot listed with PortAudio

Hi,

this issue is similar to Apalis-imx8 SGTL5000 codec issues.
But our application requires to use hardware device directly via PortAudio.
I’ve tried the pa_devs example from Portaudio to list the available devices.
Compiled PortAudio with ‘–enable-debug-output’ the output of pa_devs for the analog audio device and the hdmi device is:

FillInDevInfo: Filling device info for: apalis-imx8qm-sgtl5000: - (hw:1,0)
GropeDevice: collecting info ..
Expression 'alsa_snd_pcm_hw_params_set_buffer_size_near( pcm, hwParams, &alsaBufferFrames )' failed in '../portaudio/src/hostapi/alsa/pa_linux_alsa.c', line: 922
Host error description: Invalid argument
FillInDevInfo: Failed groping hw:1,0 for capture
FillInDevInfo: Filling device info for: imx-audio-hdmi-tx: - (hw:2,0)
GropeDevice: collecting info ..
Expression 'alsa_snd_pcm_hw_params_set_buffer_size_near( pcm, hwParams, &alsaBufferFrames )' failed in '../portaudio/src/hostapi/alsa/pa_linux_alsa.c', line: 922
Host error description: Invalid argument
FillInDevInfo: Failed groping hw:2,0 for playback

Can you give me any tips for further investigation?
The OS is based on the yocto 5.6.0-devel Reference Image.

Best regards,
Jonas

@daniel_m.tx

Hi @jonas-licht ,

Were you able to advance on this issue?

It’s a bit hard to say what is exactly the problem, it seems that the code is failing at this line, but it’s hard to say on which param the code is finding an invalid argument.

In my opinion, the best approach to solve this issue is to compile an image with debugging enabled as displayed on this article and then debug the code running gdbserver.

Best regards,
Daniel Morais

Hi @daniel_m.tx ,

after some debugging in user space I think it’s a kernel Problem.
I’ve wrote this simple test program (inspired by alsa_snd_pcm_hw_params() on Ubuntu 20.04 started returning an unexpected -ENOMEM · Issue #125 · alsa-project/alsa-lib · GitHub), which simply try to set any hw params to the alsa device and it already fails.

#include <stdio.h>
#include <stdlib.h>

#include <alsa/asoundlib.h>

int main()
{
    snd_output_t *logger;
    snd_pcm_t *handle;
    snd_pcm_hw_params_t *hw_params;
    unsigned int rate;
    int err;

    err = snd_output_stdio_attach(&logger, stderr, 0);
    if (err < 0)
        return EXIT_FAILURE;

    err = snd_pcm_open(&handle, "hw:1,0", SND_PCM_STREAM_PLAYBACK, SND_PCM_NONBLOCK);
    if (err < 0)
        goto error_logger;

    snd_pcm_hw_params_alloca(&hw_params);
    err = snd_pcm_hw_params_any(handle, hw_params);
    if (err < 0)
        goto error_handle;

    fprintf(stderr, "Before:\n");
    snd_pcm_hw_params_dump(hw_params, logger);

    err = snd_pcm_hw_params(handle, hw_params);
    if (err < 0)
        fprintf(stderr, "snd_pcm_hw_params(): %d\n", err);

    fprintf(stderr, "After:\n");
    snd_pcm_hw_params_dump(hw_params, logger);

    if (err < 0)
        goto error_handle;

    snd_pcm_close(handle);

    return EXIT_SUCCESS;
error_handle:
    snd_pcm_close(handle);
error_logger:
    snd_output_close(logger);
    return EXIT_FAILURE;
}

You can compile it with gcc test.c -lasound -ggdb
The output on my side is:

Before:
ACCESS:  MMAP_INTERLEAVED RW_INTERLEAVED
FORMAT:  S16_LE S24_LE S32_LE
SUBFORMAT:  STD
SAMPLE_BITS: [16 32]
FRAME_BITS: [16 64]
CHANNELS: [1 2]
RATE: [8000 96000]
PERIOD_TIME: (187 2047500]
PERIOD_SIZE: [18 16380]
PERIOD_BYTES: [128 65532]
PERIODS: [2 255]
BUFFER_TIME: [375 4096000]
BUFFER_SIZE: [36 32768]
BUFFER_BYTES: [128 65536]
TICK_TIME: ALL
snd_pcm_hw_params(): -22
After:
ACCESS:  MMAP_INTERLEAVED
FORMAT:  S16_LE
SUBFORMAT:  STD
SAMPLE_BITS: 16
FRAME_BITS: 16
CHANNELS: 1
RATE: 8000
PERIOD_TIME: [8250 2047500]
PERIOD_SIZE: [66 16380]
PERIOD_BYTES: [132 32760]
PERIODS: [2 255]
BUFFER_TIME: [16500 4096000]
BUFFER_SIZE: 32768
BUFFER_BYTES: [264 65536]
TICK_TIME: ALL

I will now try to continue to debug the kernel code.

Best regards,
Jonas

@daniel_m.tx

Hi @jonas-licht ,

Sorry for the delay.

Debugging the code step by step, did you check the arguments passed to the snd_pcm_hw_params() function? Which one is returning an invalid argument?

Best regards,
Daniel Morais

Hi @daniel_m.tx ,

what did you mean with checking the arguments if snd_pcm_hw_params ?
In my understanding you give the function a struct which includes all parameters.
This function calls ioctl and then everything happens in the kernel.

Best regards,
Jonas

Hi @jonas-licht ,

Yes, you are correct, but seeing the -22 (invalid argument) error it seems that some of these parameters inside the struct are not being configured correctly, because of this I believe that checking the struct might provide a hint for the issue.

Are you still stuck on the same step on this issue?

Best regards,
Daniel Morais