zoukankan      html  css  js  c++  java
  • imx6solo wm8960始终没有声音输出

    我尝试各种办法,wm8960始终不能得到声音输出。调试过程如下:

    首先,打开电源使能脚:

           ret=gpio_request(SABRESD_CODEC_PWR_EN,"audio_pwr_en");

           if (!ret){

                  printk("Turn on audio(wm8962)power!(1:enable) ");

                  gpio_direction_output(SABRESD_CODEC_PWR_EN,1);         // 0:enable, 1:disable  

                  gpio_free(SABRESD_CODEC_PWR_EN);

           }

    串口打印如下出错信息:

    wm8962 0-001a: Failed to get supply 'SPKVDD1':-19

    wm8962 0-001a: Failed to request supplies: -19

    wm8962 0-001a: asoc: failed to probe CODECwm8962.0-001a: -19

    asoc: failed toinstantiate card wm8962-audio: -19

    InitializeHDMI-audio failed. Load HDMI-video first!

    ALSA device list:

      No soundcards found.

    把imx6q_init_audio();后移几行,上面的错误就没有了。但出现下面错误 :

    wm8962 0-001a: Device is not a WM8962, ID 0 !=6243

    wm8962 0-001a: asoc: failed to probe CODECwm8962.0-001a: -22

    asoc: failed toinstantiate card wm8962-audio: -22

    把sound/soc/codec/下面的wm8962.c改用wm8960.c(修改Kconfig和Makefile)。

    wm8960_i2c_probe不调用。原因是:

           .driver = {

                  .name = "wm8960",

    而   {

                  I2C_BOARD_INFO("wm8962", 0x1a),

                  .platform_data =&wm8962_config_data,

           },

    linux driver是根据name来匹配的,如果匹配就调用。

    登记了snd_soc_register_codec后,codec的probe也不调用。

    原因是下面这个snd_dai_driver的name要一致才能调用。

    static struct snd_soc_dai_driver wm8960_dai = {

           .name = "wm8960",

    static structsnd_soc_dai_link imx_dai[] = {

           {

                  .name = "HiFi",

                  .stream_name = "HiFi",

                  .codec_dai_name       = "wm8960",

    调用后显示:

    wm8960 0-001a: wm8960 probed success!

    wm8960 0-001a: Failed to add routeHPOUTL->Headphone Jack

    asoc: wm8960<-> imx-ssi.1 mapping ok

    input:wm8960-audio DMIC as /devices/platform/soc-audio.5/sound/card0/input1

    input:wm8960-audio Ext Spk as /devices/platform/soc-audio.5/sound/card0/input2

    ALSA device list:

      #0: wm8960-audio

    root@imx6solo ~$find / -name *wm8960*

    /sys/devices/platform/imx-wm8960.0

    /sys/bus/platform/devices/imx-wm8960.0

    /sys/bus/platform/drivers/imx-wm8960

    /sys/bus/platform/drivers/imx-wm8960/imx-wm8960.0

    /sys/bus/i2c/drivers/wm8960

    /proc/asound/wm8960audio

    root@imx6solo ~$

    问题是/dev/下面并没有增加设备,无法使用/dev/pcm。

    root@imx6solo/usr/bin$ aplay -L                 

    null

        Discard all samples (playback) or generatezero samples (capture)

    root@imx6solo/usr/bin$ aplay -l

    **** List ofPLAYBACK Hardware Devices ****

    card 0:wm8960audio [wm8960-audio], device 0: HiFi wm8960-0 []

      Subdevices: 1/1

      Subdevice #0: subdevice #0

    root@imx6solo/usr/bin$

    现在应该是试试ALSA驱动程序是不是真能用的时候了. 接者就是使用它.

    查看声卡是否存在:

    root@imx6solo ~$cat /proc/asound/cards

     0 [wm8960audio    ]: wm8960-audio - wm8960-audio

                          wm8960-audio

    ALSA 驱动程序在 /dev/snd/ 目录下有自己的驱动程序。

    root@imx6solo ~$ ls /dev/snd/

    controlC0 pcmC0D0c   pcmC0D0p  timer

    http://www.alsa-project.org/main/index.php/Download上面下载alsa tester包括alsa-lib,alsa-utils。

    编译:./gitcompile CC=arm-linux-gcc --host=arm-linux

    现在进化到configure都从网络上临时下载的地步了,我有点out了。

    编译alsa-utils总是过不去。重新下载alsaplayer。

    ./configure--host=arm-linux CC=arm-linux-gcc --disable-oggvorbis

    然后make.

    对比了wm8960.c/wm8962.c,imx-wm8960.c/imx-wm8962.c,差别其实非常大。

    http://bbs.21ic.com/forum.php?mod=viewthread&tid=869393,从这个链接地址可以下载imx-wm8960.c。

    重新配置linux kernel,设备/dev/dsp和/dev/mixer出来,这是OSS接口的要求。

    root@imx6solo/test/audio$ ./wavplay test.wav

    -------------------------------------------------------------------->

    File Magic:         [RIFF]

    File Length:        [424636]

    File Type:          [WAVE]

    Fmt Magic:          [fmt ]

    Fmt Size:           [16]

    Fmt Format:         [PCM]

    Fmt Channels:       [2]

    FmtSample_rate:    [22050](HZ),22khz

    FmtBytes_p_second: [88200]

    FmtBlocks_align:   [4]

    FmtSample_length:  [16]

    Chunk Type:         [data]

    Chunk Length:       [424600]

    <--------------------------------------------------------------------

    Plug PCM: Rateconversion PCM (44100, sformat=S16_LE)

    Converter:linear-interpolation

    Protocol version:10002

    Its setup is:

      stream      : PLAYBACK

      access      : RW_INTERLEAVED

      format      : S16_LE

      subformat   : STD

      channels    : 2

      rate        : 22050

      exact rate  : 22050 (22050/1)

      msbits      : 16

      buffer_size : 8192

      period_size : 256

      period_time : 11609

      tstamp_mode : NONE

      period_step : 1

      avail_min   : 256

      period_event : 0

      start_threshold  : 1

      stop_threshold   : 8192

      silence_threshold: 0

      silence_size : 0

      boundary    : 536870912

    Slave: DirectStream Mixing PCM

    Its setup is:

      stream      : PLAYBACK

      access      : MMAP_INTERLEAVED

      format      : S16_LE

      subformat   : STD

      channels    : 2

      rate        : 44100         //44khz

      exact rate  : 44100 (44100/1)

      msbits      : 16

      buffer_size : 16384

      period_size : 512

      period_time : 11609

      tstamp_mode : NONE

      period_step : 1

      avail_min   : 512

      period_event : 0

      start_threshold  : 2

      stop_threshold   : 16384

      silence_threshold: 0

      silence_size : 0

      boundary    : 1073741824

    Hardware PCM card0 'wm8960-audio' device 0 subdevice 0

    Its setup is:

      stream      : PLAYBACK

      access      : MMAP_INTERLEAVED

      format      : S16_LE

      subformat   : STD

      channels    : 2

      rate        : 44100         //44khz

      exact rate  : 44100 (44100/1)

      msbits      : 16

      buffer_size : 16384

      period_size : 512

      period_time : 11609

      tstamp_mode : ENABLE

      period_step : 1

      avail_min   : 512

      period_event : 0

      start_threshold  : 1

      stop_threshold   : 1073741824

      silence_threshold: 0

      silence_size : 1073741824

      boundary    : 1073741824

      appl_ptr    : 0

      hw_ptr      : 0

    root@imx6solo/test/audio$ aplay test.wav

    Playing WAVE'test.wav' : Signed 16 bit Little Endian, Rate 22050 Hz, Stereo

    Aborted by signalInterrupt...

    root@imx6solo/test/audio$

    仍然是没有声音输出!!

    换了一个44khz采集率的wav文件,仍然没有声音输出!

    root@imx6solo/test/audio$ aplay xihuanni.wav

    Playing WAVE'xihuanni.wav' : Signed 16 bit Little Endian, Rate 44100 Hz, Stereo

    Aborted by signalInterrupt...

    再次检查了pin mux config,是正确的。但就是没有任何audio输出!

    如果直接用imx-wm8962.c,则有许多出错信息,如下:

    root@imx6solo/test/audio$ aplay xihuanni.wav

    WM8960 PLL:Unsupported N=3

    Failed to startFLL: -22

    Failed to setSYSCLK: -22

    asoc: machinehw_params failed

    Failed to setSYSCLK: -22

    ALSA libpcm_direct.c:980:(snd1_pFailed to set SYSCLK: -22

    cm_direct_initialize_slave)unable to install hw params

    ALSA libpcm_dmix.c:1030:(snd_pcm_dmix_open) unable to initialize slave

    aplay: main:660:audio open error: Invalid argument

    所以,要用imx-wm8962.c来修改的话,还有点麻烦,不会很容易。

    网上找了一个人交流,他用的是imx-wm8960.module,就是编译出来的.o

    ifneq ($(wildcardsound/soc/imx/imx-wm8960.c),)

    snd-soc-imx-wm8960-objs:= imx-wm8960.c

    else

    snd-soc-imx-wm8960-objs:= imx-wm8960.module

    endif

    我这样修改后,运行导致crash。

    register wm8960 I2C driver success!

    Unable to handlekernel paging request at virtual address f8f2fe18

    pgd = 80004000

    [f8f2fe18] *pgd=1bce9811, *pte=00000000,*ppte=00000000

    Internal error:Oops: 807 [#1] PREEMPT

    Modules linked in:

    CPU: 0    Not tainted (3.0.101-2790-gc248ed7 #274)

    先验证了i2c,示波器显示有输出,并且测了看device addr也是0x1A。

    alsamixer配置也是全部拉高,退出后重新进入,也是对的,可以保存和读出。

    i2s data仍然没有,数据线对地电阻也测了,并没有短路。

    仔细查了linux代码,没有i2s部分,应该是改成SSI了。

    ssi有两个,一个是在driver/mxc/ssi.c,这个是以前的。

    现在是sound/soc/imx/imx-ssi.c。

    imx6q_add_imx_ssi(1,&mx6_sabresd_ssi_pdata); 注册为platform device。

    加了一句打印:

    imx_ssi_probesuccessfully。证明probe是被调用了的。

    root@imx6solo/test/audio$ aplay xihuanni.wav

    snd_pcm_dmix_open()

    snd1_pcm_hw_open_fd()

    snd_pcm_plug_open()

    Playing WAVE'xihuanni.wav' : Signed 16 bit Little Endian, Rate 44100 Hz, Stereo

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    snd_pcm_mmap_writei

    然后挂起,ssi接口无输出,应该是mixer配置不正确。

    最终查明原因,是没有正确初始化wm8960导致的。
    在imx-wm8960.c的
    static int imx_hifi_hw_params(struct snd_pcm_substream *substream,
    struct snd_pcm_hw_params *params)函数中增加:
    ...
    wm8960_vendor_set(codec_dai);
    ...

    /* based on the result of dump */
    void wm8960_vendor_set(struct snd_soc_dai *codec_dai)
    {
    struct snd_soc_codec *codec = codec_dai->codec;

    snd_soc_write(codec, 0x19, 0xc0); /* power1, ok*/
    snd_soc_write(codec, 0x1a, 0x199); /* power2, ok*/

    snd_soc_write(codec, 0x31, 0xf7); /* classd1 : enable L&R, ok */
    snd_soc_write(codec, 0x33, 0x11b); /* classd3 : volume max, ok */

    snd_soc_write(codec, 0x28, 0x179); /* ok */
    snd_soc_write(codec, 0x29, 0x179); /* ok */

    snd_soc_write(codec, 0x22, 0x100); /* dac to mixer, ok */
    snd_soc_write(codec, 0x25, 0x100); /* dac to mixer, ok */

    snd_soc_write(codec, 0x2f, 0x0c); /* left & right output mixer enable, ok */
    snd_soc_write(codec, 0x05, 0x00); /* ok */
    }

  • 相关阅读:
    HttpURLConnection中使用代理(Proxy)及其验证(Authentication)
    Java获取随机数的几种方法
    史上最全的java随机数/字符串生成算法(转)
    httpClient中的三种超时设置小结
    几个性能测试工具
    硬件知识
    北风风hadoop课程体系
    IT大数据服务管理高级课程(IT服务,大数据,云计算,智能城市)
    .net framework client profile
    Resharper中注释代码的快捷键
  • 原文地址:https://www.cnblogs.com/subo_peng/p/5233915.html
Copyright © 2011-2022 走看看