【问题标题】:Operation not Permitted on ALSA get hw parameters functionsALSA 上不允许操作获取硬件参数函数
【发布时间】:2014-05-14 20:42:42
【问题描述】:

我正在尝试播放从服务器接收的 pcm 音频缓冲区。我下载了一个示例 alsa 播放文件,将记录的文件作为输入,它工作正常,但我在 SIP 客户端应用程序中添加的相同代码出现了 Operation not allowed 错误。打开设备并为设备设置配置都可以,但尝试获取我配置的参数给了我Operation not permitted error。 谁能告诉我这个错误的原因?

/* Open the PCM device in playback mode */
    if (pcm = snd_pcm_open(&pcm_handle, PCM_DEVICE,
                                    SND_PCM_STREAM_PLAYBACK, 0) < 0)
            printf("ERROR: Can't open \"%s\" PCM device. %s\n",
                                    PCM_DEVICE, snd_strerror(pcm));

    /* Allocate parameters object and fill it with default values*/
    snd_pcm_hw_params_alloca(&params);

    snd_pcm_hw_params_any(pcm_handle, params);

    /* Set parameters */
    if (pcm = snd_pcm_hw_params_set_access(pcm_handle, params,
                                    SND_PCM_ACCESS_RW_INTERLEAVED) < 0)
            printf("ERROR: Can't set interleaved mode. %s\n", snd_strerror(pcm));

    if (pcm = snd_pcm_hw_params_set_format(pcm_handle, params,
                                            //SND_PCM_FORMAT_S16_LE) < 0) 
                                            SND_PCM_FORMAT_MU_LAW) < 0)
            printf("ERROR: Can't set format. %s\n", snd_strerror(pcm));

    if (pcm = snd_pcm_hw_params_set_channels(pcm_handle, params, channels) < 0)
            printf("ERROR: Can't set channels number. %s\n", snd_strerror(pcm));

    if (pcm = snd_pcm_hw_params_set_rate_near(pcm_handle, params, &rate, 0) < 0)
            printf("ERROR: Can't set rate. %s\n", snd_strerror(pcm));

    /* Write parameters */
    if (pcm = snd_pcm_hw_params(pcm_handle, params) < 0)
            printf("ERROR: Can't set harware parameters. %s\n", snd_strerror(pcm));

   /* Resume information */
    printf("PCM name: '%s'\n", snd_pcm_name(pcm_handle));

    printf("PCM state: %s\n", snd_pcm_state_name(snd_pcm_state(pcm_handle)));

    pcm =  snd_pcm_hw_params_get_channels(params, &tmp);
    printf("channels: %i  %d", tmp, pcm);

    if (tmp == 1)
            printf("(mono)\n");
    else if (tmp == 2)
            printf("(stereo)\n");

    snd_pcm_hw_params_get_rate(params, &tmp, 0);
    printf("rate: %d bps\n", tmp);

    printf("seconds: %d\n", seconds);

    /* Allocate buffer to hold single period */
    snd_pcm_hw_params_get_period_size(params, &frames, 0);

    buff_size = frames * channels * 2 /* 2 -> sample size */;
    buff = (char *) malloc(buff_size);

    printf("buffsize: %d\n", buff_size);
    snd_pcm_hw_params_get_period_time(params, &tmp, NULL);

【问题讨论】:

  • 您应该检查所有函数调用的返回值。无论如何,哪个功能失败了?
  • 感谢回复 snd_pcm_hw_params_get_channels、snd_pcm_hw_params_get_rate 和 snd_pcm_hw_params_get_period_size 所有上述函数都在获取 Operation not allowed 且返回值为 0

标签: c alsa


【解决方案1】:

你所有的错误检查都是错误的。

&lt; 运算符的绑定比= 强,所以在这样的一行中:

if (err = snd_something(...) < 0)

将函数的返回值与零进行比较,并将比较的结果(假或真,0 或 1)分配给变量。

要使其正常工作,您必须在作业周围添加括号:

if ((err = snd_something(...)) < 0)

但最好不要尝试将所有内容都放在一个表达式中:

err = snd_something(...);
if (err < 0)

【讨论】:

  • snd_pcm_hw_params_get_channels(params,&tmp) snd_pcm_hw_params_get_rate(params, &tmp, 0);返回成功(0),参数必须获得我必须设置的值,即 8000 和 1,但两个函数值都设置为 1 并且操作不允许错误
  • "Operation not allowed" 是代码 1 的错误。我解释了为什么这不是真正的错误代码。
  • 当我将它作为单独的代码运行时,我得到了我配置的参数(采样率和通道)。当我的 sip 客户端中包含相同的代码时,我遇到了这个问题,并且当我在上写入音频缓冲区时没有声音阿尔萨设备。你能告诉我做错了什么吗?
  • 您真的阅读并理解了我的回答吗?如果您进行这些更改,您将获得正确的错误代码。
  • 我按照你说的修改了我的代码,得到了返回值 1。有什么办法可以解决这个问题吗?
猜你喜欢
  • 2017-07-07
  • 1970-01-01
  • 2020-05-25
  • 1970-01-01
  • 1970-01-01
  • 2023-03-27
  • 2011-08-16
  • 1970-01-01
相关资源
最近更新 更多