/
//Author:Mercury Xu
//Date:2008-12-08
//Descrption:聲音作為WinCE系統中一個比較基礎的配置大家已經都不會陌生。
//           本文主要是總結下作者在調試WM9715聲卡驅動芯片
//           過程中遇到的一些問題
//OS:WinCE5.0
/
正文
好了。以下是Segment II,跳过来的朋友和读过来的朋友都要准备好了。我们要开始耍WM9715了。

首先我们还是来热身下,热身我们要准备以下两个东西

1.应用层的一些小知识。
2.WM9715 datasheet。

我们先来看第一个,做流式驱动调用的时候我们知道,有一个XXX_IOCONTROL之类的函数一般在最后,我们再WM9715的WAV驱动的地方也有个。 WAV_IOControl。我们在应用层怎么去调用他呢?
其实很简单。大家先看看MSDN的这个文档:
http://msdn.microsoft.com/en-us/library/aa363216(VS.85).aspx

BOOL WINAPI DeviceIoControl(  __in         HANDLE hDevice, //句柄一个,定义一个HANDLE的句柄,在初始化的时候就好了  __in         DWORD dwIoControlCode,//这个一般无关痛痒,Null掉了  __in_opt     LPVOID lpInBuffer,//这个就比较重要了,输入数据的接口,要和你定义好的case数值匹配好哦!  __in         DWORD nInBufferSize,//这个长度一般都直接用sizeof处理掉了。  __out_opt    LPVOID lpOutBuffer,//这个也是比较重要的,返回值,在上一篇文章里面case最后有个比较精彩的程序段,                                  //给了这个变量值,大家可以回头过去看看。      __in         DWORD nOutBufferSize,//这个也直接sizeof了。  __out_opt    LPDWORD lpBytesReturned,//这个我们都Null  __inout_opt  LPOVERLAPPED lpOverlapped ///这个也NULL了);

好了。不多说了,看懂了吧。这里再提醒下,case的值一定不能搞错了,搞错了怎么样都是出不了的。

接下来还有个难度稍微大一点点的。我们再上一篇文章应该有看到在try的里面有个很长的结构体,叫PMMDRV_MESSAGE_PARAMS
这个结构体再APP不管你用EVC还是VS2005都是没有给出初始化定义的。所以,接下来我们给出他的定义

  1. BOOL WAV_IOControl(DWORD  dwOpenData,
  2. DWORD  dwCode,
  3. PBYTE  pBufIn,
  4. DWORD  dwLenIn,
  5. PBYTE  pBufOut,
  6. DWORD  dwLenOut,
  7. PDWORD pdwActualOut)
  8. You can use pBufIn pass its parameter, and pBufIn is defined with
  9. typedef struct {
  10. UINT uDeviceId;
  11. UINT uMsg;
  12. DWORD dwUser;
  13. DWORD dwParam1;
  14. DWORD dwParam2;
  15. } MMDRV_MESSAGE_PARAMS, *PMMDRV_MESSAGE_PARAMS;
  16. and you can use pBufOut to get return value, it is definded with
  17. (DWORD *)
  18. (PMMDRV_MESSAGE_PARAMS)pBufIn, (DWORD *)pBufOut
  19. WRITE REGISTER
  20. dwCode:   IOCTL_WAV_MESSAGE
  21. uMsg:     WODM_WRITE_AC97
  22. dwParam1: AC97 register's ID, it should be even, please read AC'97 specification
  23. dwParam2: pass value(write), the value shoud be an 16-bits
  24. number.
  25. READ REGISTER
  26. dwCode:   IOCTL_WAV_MESSAGE
  27. uMsg:     WIDM_READ_AC97
  28. dwParam1: AC97 register's ID, it should be even, please read AC'97 specification
  29. pBufOut:  RETURN VALUE

这下眼前一亮了吧。我顺带将9715的两个东东也带出来了。关于9715的操作我们接下来就开始给大家说说,刺激的地方要开始了。

下面我们开始比较刺激的地方了。看看WM9715的结构以及驱动的地方怎么去处理。

对于芯片的操作,无非就是两个,读寄存器,写寄存器,首先我们看看WM9715的datasheet

http://www.wolfsonmicro.jp/uploads/documents/cn/WM9715L_Rev3.9.pdf

我们先看下他的功能

rel="File-List" href="file:///C:%5CDOCUME%7E1%5CMERCUR%7E1%5CLOCALS%7E1%5CTemp%5Cmsohtml1%5C01%5Cclip_filelist.xml">

AC’97 Rev 2.2 compatible stereo codec

AC’97 Rev2.2 兼容立体声解码

- DAC SNR 90dB, THD –86dB

- ADC SNR 88dB, THD –88dB

- Variable Rate Audio, supports all WinCE sample rates

多频率音频,支持所有WinCE采样率

- Tone Control, Bass Boost and 3D Enhancement

音调控制,重音控制以及3D环绕控制

• On-chip 45mW headphone driver

片载45毫瓦耳机驱动

• On-chip 400mW mono speaker driver

片载400毫瓦单声道喇叭驱动

• Stereo, mono or differential microphone input

立体声,单声道或者混合麦克风输入

- Automatic Level Control (ALC)

自动等级控制

• Auxiliary mono DAC (ring tone or DC level generation)

辅助单DAC

• Seamless interface to wireless chipset

无线连接接口

• Resistive touchpanel interface

电阻丝触摸板接口

- Supports 4-wire and 5-wire panels

支持4线和5线触摸板

- 12-bit resolution, INL ±3 LSBs (<0.5 pixels)

12位协议,INL ±LSBs (<0.5 pixels)

- X, Y and touch-pressure (Z) measurement

X,Y以及触摸压力测量

- Pen-down detection supported in Sleep Mode

休眠模式下触摸笔下压侦测

• 2 comparator inputs for battery monitoring

2个电源侦测比较输入端口

• Up to 4 auxiliary ADC inputs

4个辅助ADC输入

• 1.8V to 3.6V supplies

1.8V 到 3.6v 电压支持

• 7x7mm QFN

7* 7mm QFN封装

好了,如果你还是不放心,看到

- Variable Rate Audio, supports all WinCE sample rates

多频率音频,支持所有WinCE采样率

这句话你应该可以放心大胆的来玩这颗芯片了。

首先,我们需要知道,系统的声音是一个数据音频,所有,系统走的方式是通过I2S来的。这一块一般再BSP包中都会有写好了。大家都不用去修改。直接用就好了

其次,其他的声音输入采用的方式基本上是通过9715的几个音频输入口,比如MIC LINEIN这几个来实现的。首先你要检查下硬件上都是OK,输入一些音频的模拟信号进去,确认已经进入到了芯片里。

最后我们开始来看这个DATASHEET里面的最神奇的图。Audio paths overview。。。大概在14页图片1

这个图太神奇了。。想起了小时玩红白机三国志里面选角色的情景,走线路判断后选人。怀念啊。。。。
这里我们就拿LINEINL这一路来看PIN23蓝色的线走下去。

1.我们先碰到了10H这个寄存器他是控制输入音量的,我们先要使能,然后选择最大音量,这里有个小尝试,+的dB是音量最大啊!!!(众人,地球人都知道。。。)
2.接下来我们看到了个MIXER.不鸟他
3.然后我们看到我们要使能的寄存位了10H:15我们很开心的把它做成1,使能了。
4.headphone mix是个大关,混合了下音以后送出来
5.接下来有个选择器,我们直接过去,上面有个转向器,我们也不用鸟他了02H的转向器
6.最后一个BOSS来了02H首先你要他处于可以放的状态,也就是非MUTE状态,我们仔细一看,02H:7.好了。我们很开心的把它弄成了1.
7.最后的最后我们来弄个音量,也弄个最大音量就好了。

以上就是一套路线打通的方法,其他路线打通的方法大同小异。大家一路跟下去就OK了。

至于如可写寄存器如何读寄存器,下面我们简单说下,因为不同的ARM可能对这个处理的方式不太一样。但是总体上是类似。

上面我们很开心的将一些寄存器位设计为高,我们通过写寄存器的方式实现。下面我给一个参考给大家

  1. BOOL WriteAC97Reg(USHORT RegIndex, USHORT RegValue)
  2. {
  3. ULONG timeout = 0;
  4. GRABMUTEX();
  5. IOW_REG_SET(struct ac97Ctrl1Bits, &v_pCodecReg->ac97ctrl1, (RegValue << 16) | ((RegIndex & 0x7f) << 8));        //  CODEC_AC97_CMD = (RegValue << 16) | RegIndex;
  6. IOW_REG_OR(struct ac97Ctrl0Bits, &v_pCodecReg->ac97ctrl0, 0xe000);      //  CODEC_AC97_CTRL |= 0xe000;
  7. while ((v_pCodecReg->ac97ctrl0.ac97_write_tagh & AC97_WRITE_SLOT1_VALID) && (timeout++ < TIMEOUT_LOOPS));
  8. if(timeout >= TIMEOUT_LOOPS)
  9. {
  10. RETAILMSG(1, (TEXT("Timeout in write ac97")));
  11. }
  12. usWait(5);
  13. RELEASEMUTEX();
  14. return (timeout < TIMEOUT_LOOPS);
  15. }
  1. // AC97_CONTROL_0 -0X01C R/W
  2. struct ac97Ctrl0Bits {
  3. unsigned da_channel        :2;// da channel enable, bit1 left channel, bit0 right channel; 1= channel enable;0=channel disable
  4. unsigned ad_channel        :2;// ad channel enable
  5. unsigned warm_wake        :1;// Warm wake codec 1= warm wake   0= exit warm wake-up mode.
  6. unsigned ac97_start        :1;// ac97 interface start 1= ac97 interface start  0= stop
  7. unsigned rsvd0            :5;// reserved
  8. unsigned ac97_write_tagh    :5;// AC-link output frame tag setting
  9. unsigned rsvd1            :16;// reserved
  10. };
  11. // AC97_STATUS_0 -0X024 R
  12. struct ac97Status0Bits {
  13. unsigned ac97_slot_rq        :8;    // ac97 slot request
  14. unsigned ac97_read_tagh        :8;  // ac97 input frame status bit15 codec ready, bit14 solt1 valid, bit13 slot2....
  15. unsigned rsvd0            :16;
  16. };

1.IOW_REG_SET和 IOW_REG_OR这两个函数大家根据自己的芯片进行定义就好了,其他都是很常用的。在这里就不多说了。
2. ac97Ctrl1Bits和0是对WM9715你自身ARM控制的一些操作。这个你按照你自己的来就好了。
3.最后两个是赋值了。

基本的思路是上面的。大家还是要根据不同的芯片来不同处理。
那今天驱动部分我们就介绍完了。关于应用层,明天我们再聊。

關於基於WinCE下的聲音系統調試的一些經驗總結之驱动程式部分(二)相关推荐

  1. java 修改wav文件头_使用Java聲音API從WAV文件中修剪開頭和結尾

    我有製作的基礎知識.但是,輸出文件一遍又一遍地重複WAV標頭字節.生成的文件大小合適,但是它與垃圾一起提交.使用Java聲音API從WAV文件中修剪開頭和結尾 我想使用一個擴展AudioInputSt ...

  2. 关于wince 下LCD 控制器设置成RGB888 24bit 的相关问题

    在论坛找了一个topic ,自己也来分析一下. http://bbs.csdn.net/topics/350122995?page=1#post-392888121 -- 100分:开帖讨论WINCE ...

  3. linux下复制catalog信息指令,基於Linux下catalog方式的 Oracle 備份策略(RMAN)

    --********************************** --基於Linux下 Oracle備份策略(RMAN) --********************************* ...

  4. mt7601的linux驱动下载,mt7601u,基於 Linux mac80211 MT7601U USB bgn無線dongle驅動程序,下載mt7601u的源碼_GitHub_開發99...

    這是一款用於 MT7601U USB dongle的Linux驅動程序. 它是基於供應商gpl驅動程序從頭開始編寫的. 供應商驅動程序不同,這個驅動程序使用現代的Linux WiFi基礎設施,並且應該 ...

  5. 基於IIS的WCF的分布式多層架構開發實現

    曾用.NET Remoting,基於IIS,為公司實現過分布式多層架構,客戶端采用Web Browser瀏覽,當時,公司領導告訴我可能會有多臺中間服務器用於系統,又不想每臺電腦的去安裝程序,所以,我最 ...

  6. 基於tiny4412的Linux內核移植--- 中斷和GPIO學習(2)

    作者 彭東林 pengdonglin137@163.com 平臺 tiny4412 ADK Linux-4.4.4 u-boot使用的U-Boot 2010.12,是友善自帶的,爲支持設備樹和uIma ...

  7. python笑傲江湖统计字数_基於Python的tf-idf算法实现:以《笑傲江湖》为例

    连结Jasonnor/tf-idf-python​github.com 简介 tf-idf(term frequency-inverse document frequency)是一种用於信息检索与文字 ...

  8. php complex,PHP復雜的基於角色的訪問控制列表

    I have already made the database and the php code needed to implement this customized ACL system. No ...

  9. OpenCV學習筆記(6)基於 VC+OpenCV+DirectShow 的多個攝像頭同步工作

    http://blog.csdn.net/chenyusiyuan/article/details/4643313 因項目需要采集2個攝像頭的數據進行雙目檢測,一開始采用以下代碼來測試: #inclu ...

最新文章

  1. Spring cloud 微服务docker容器化最佳实践
  2. 为何 Windows 10X 无法延续 Windows 的成功?
  3. php ecos,php
  4. poj1192 最优连通子集(树形dp)
  5. 自己动手用C扩展PHP(三)
  6. python做excel表格代码_[宜配屋]听图阁
  7. ANDROID笔记:Activity之间的传值
  8. 3. LAMP 安装与配置
  9. python策略模式包含角色_Python 之策略模式
  10. dosbox使用教程创建masm5
  11. Ipsec phase1 and phase2
  12. python怎么让矩阵内所有元素自己平方_python numpy库中矩阵用法指南
  13. 实验一:交换机和路由器的基本配置
  14. Spring Boot学习笔记(二十一)Spring boot 数据校验 @Validated、@Valid用法详解
  15. SDOI2019R2翻车记
  16. 手机内存卡照片删了怎么恢复
  17. 使用Adobe Acrobat XI Pro进行pdf裁剪
  18. org.quartz.JobPersistenceException:Couldn‘t retrieve job because a required class was not found
  19. 金海佳学C++primer 练习9.4/9.5
  20. Facebook等使用苹果源生分享

热门文章

  1. php 系统平均负载,深入理解liunx平均负载
  2. Google DFP广告管理系统简介:下订单
  3. #ifndef、#define、#endif作用
  4. 【微信小程序】小程序自定义随机分享图片
  5. php实现数组值遍历连接成一串字符串
  6. “声”来震撼 乐在途中·飞利浦汽车音响震撼上市
  7. 糯米团—重制“iPhone团购信息客户端”(二)
  8. 阿里国际站买家取消金标蓝标–上线优质买家(L1+)
  9. frp内网穿透服务器搭建及免费frp服务器提供
  10. 从0开始学c语言-终篇41-练习、学习分享