收音机驱动

来源:互联网 发布:linux php环境一键安装 编辑:程序博客网 时间:2024/04/30 18:57

今天拿板子过来一试,发现在DllMain函数的载入频繁调用,不知什么原因。

关于动态连接库入口点函数:

如果指定了入口点函数,系统在进程或线程载入或卸载DLL时就会调用入口点函数。

可以用来实现简单的初始化及清除任务。

进程载入DLL时:

对于使用了载入时动态连接的程序,DLL通过进程初始化来载入。

对于使用了运行时连接的程序,DLL在调用LoadLibraryLoadLibraryEx返回前载入。

进程卸载DLL时:

进程终止或者调用了FreeLibrary函数,同时引用计数为0,则DLL被卸载。

但如果进程作为TerminateProcessTerminateThread函数的结果终止,系统不会调用入口点函数。

 

至于为什么会一直创建线程和关闭线程,这就不得而知了。(现在认为是没有添加DisableThreadLibraryCalls函数)

流接口函数FMR_Init

使用LocalAlloc函数申请一段堆栈空间,接下来调用FMRadio_Init函数

 

关于FMRadio_Init函数

这个函数主要调用了两个函数CreateI2CFileFMRadioI2CWrite,看来所执行的初始化功能会在这两个函数里面。(现注:无非就是初始化一下I2C

 

关于CreateI2CFile函数

这函数使用了CreateFile,具体见代码和MSDN。只执行打开IIC的文件。

 

关于FMRadioI2CWrite函数

这函数似乎是对IIC的写?

这里用到i2c/i2c.h文件里面的一个结构体

I2CParam.chipAddr = FMRADIO_ADDR;   //IIC write address

I2CParam.readOrWrite = IIC_WRITE;

I2CParam.count = 1;

 

reg  = (BYTE)((val>>8)&0xff);   

data = (BYTE)(val & 0xff);

I2CParam.regAddr = reg;

I2CParam.pData = &data;

 

最后调用DeviceIoControl函数

i2c/i2c.h   #define IOCRL_I2CTRANSMIT  0x00008000

原来上面的I2CParam结构体赋值是为了这函数里面的一个参数,它的赋值方式可能和I2C的设置有关。看得还是晕晕的,特别是不知道这DeviceIoControl什么用,传输一个消息(数据什么的)给设备?(现注:没错,就是对设备的操作信息传输)

综上所述,这就是执行整个初始化所做的工作了。具体以后再作分析。

关于ReadSTO函数

到现在我还是不知道什么是STO,这函数所执行的过程和FMRadioI2CWrite有点类似,大可看为在读一个“STO”的东西。这里是读出data的值,打开设备失败或RMXG0,都属于失败的情况。

关于FMRadio_SetFreq函数

顾名思义是个设置频率的函数,里面有通过一个公式来计算PCNT(不大清楚是什么东西)。和FMRadio_SetPCNT函数有点类似,主要就差别于一个公式的计算,里面定有蹊跷。

就这函数而谈就是把频率写入寄存器,察看R1R2。(现注:应该就是换算成一个值,写进寄存器,以后就见多了。嗯,就像下面说的那样)

对于PCNT的理解:它是频率在寄存器上的设置,通过换算之后,就是频率在寄存器上的表现。

FMRadio_SetPCNT函数,没有通过公式计算,也就是说它的参数是经过计算之后的。

关于FMRadio_AutoSearch函数

这函数是里面最为复杂的一个函数,里面的流程是根据硬件介绍上的一个流程图来实现的。

(现注:当时记得是在数据手册上有个流程图)

当执行成功,返回值将是它的频率,如果查找失败,它的返回值将是-1

 

 

关于FMR_IOControl函数

今天总算认识了这一个函数,在DeviceIoControl被执行的时候,它就会被调用。这个函数就是执行我们对设备传送消息时,设备对消息的处理。具体的一些实现细节就在硬件说明书里面(比如识别的数据格式等)。

 

里面有一些宏定义在#include "../wavdev/2410/wavext.h"里面。上面还需要windev.h

 

收音机的传输是通过I2C,所以数据的一些格式全部都是以I2C的形式,它没有自己的一套格式(也可以说是和I2C一致)。对寄存器的直接操作。收音机的IO操作是间接通过I2CIO操作来实现的。

 

上面的驱动算是告一个段落。现在的主要任务就是测试驱动的功能,可能要通过应用程序来测试(也许有其他的方法,现在还不知道)。

测试的应用程序布局:

4个功能按钮:

按钮1play,用于启动收音机。首先应该打开文件,创造线程。

按钮2autosearch,自动选频。

按钮3locked,锁定频率。

按钮4cancel,退出收音机功能。

 

定义线程运行实现的功能函数。这作为一个线程实现功能的体现。

今天测试了一下,似乎流接口函数还是可以成功相应,但还是没看出做了一些什么实际的意义。也许是缺少一个可以用来运行的线程吧,现在要凭自己想象一下线程要如何安排:

首先,这个线程必须可以运行FMradio_read,(ReadFile)去读取那个芯片,但是单纯这样的读可以使喇叭发出电台的声音吗?看来还有很长的一段路要执行。其中是否要建立缓冲区?接收到缓冲区之后,如何处理这些数据?(传送到哪里?)

 

上面错误的解释:之前是不熟悉这些,现在有点明了。其实IIC只是传送个控制信号。对于音频的信号传输等方面它是不干涉的。是有另两条线接入芯片WM8753。目前音频的信号处理对我来说将是透明的。只要控制让收音机芯片运行起来就可以了。

 

关于IIC的流接口初始化函数I2C_Init(见I2C驱动文件)

原创粉丝点击