alsa架构分析

目录

1.    Abstract

2.    Introduction

3.    音频驱动框架介绍

3.1      音频设备的注册

3.2     音频驱动的注册

3.2.1       Probe函数的调用

3.2.2       Soc_probe函数

4.    通常的使用流程的分析

4.1.1       open过程介绍

4.1.2       snd_pcm_hw_params流程分析

4.1.3       prepare流程分析

4.1.4       write的流程

4.1.5       使用流程的总结t

5.    Amixer调用的相关逻辑

5.1.1       Amixer调用的上层逻辑

5.1.2       Amixer的内核流程

6.    总结

7.    未讨论

1.               Abstract

主要是讲2.6.21内核里面的alsa驱动的架构,以及在我们的平台上需要注意的东西。.

2.               Introduction

分成几个部分:

驱动整体框架,一个简单的播放流程介绍,以及我们的平台需要注意的地方;

3.               音频驱动框架介绍

3.1               音频设备的注册

Alsa驱动分析(转) - wilson - Wilsons blog

这就是设备的注册了,设备本身非常简单,复杂的是这个设备的drvdatadrvdata里面包含了三部分,关于machine的,关于platform的,关于codec的,从大体上说machine主要是关于cpu这边的也可以说是关于ssp本身设置的,而platform是关于平台级别的,就是说这个平台本身实现相关的,而codec就是与我们所用的音频codec相关的;基本上这里就可以看出整个音频驱动的架构特点,就是从alsa层进入——>内核alsa层接口->core层,这里再调用上面说的三个方面的函数来处理,先是cpu级别的,再是platform的,再是codec级别的,这几层做完了,工作也就做得差不多了,后面会详细讲讲,当然这个执行顺序不是固定的(不知道是不是marvel写代码不专业导致的),但多半都包括了这三部分的工作;

3.2            音频驱动的注册

3.2.1          Probe函数的调用      

                  Alsa驱动分析(转) - wilson - Wilsons blog

                   前面讲了设备的注册,里面的设备的名字就是”soc-audio”,而这里的driver的注册时名字也是 soc-audio”,对于platform的设备匹配的原则是根据名字的,所以将会匹配成功,成功后就会执行audio驱动提供的probe函数soc_probe;

3.2.2          Soc_probe函数

这个函数本身架构很简单,和前面说的逻辑一样,先调用了cpu级别的probe,再是codec级别的,最后是platform的(这里三个的顺序就不一样),但是因为cpu级别的和platform级别的都为空,最后都调用了codec级别的probe函数,也就是micco_soc_probe,这个函数基本上就完成了所有应该完成的音频驱动的初始化了;简单的划分,分成两部分,对上和对下:对上主要是注册设备节点,以及这些设备节点对应的流的创建;对下主要是读写函数的设置,codec本身的dai设置,初始化寄存器的设置,最重要的就是后面的control的创建和门的创建了,如下图所示:

Alsa驱动分析(转) - wilson - Wilsons blog这里面的第一部分就是负责初始化的;

 

第二部分就是创建卡和流,对于alsa驱动来说,是先分成卡0,卡1…,然后对于每一个卡的每一个cpu支持的daidigit audio interface)也就是pcm接口 或者i2S接口等都要建立对应的流,一个dai有可能包含两个流,一个是录的一个是play的,但在我们的平台上对于i2Sdai是没有录音功能的,所以我们的平台只有一个卡,三个流,pcm的录和playi2Splay;流的创建还是更多的考虑为上层服务的,它所提供的接口都是soc层的,这里非常重要的地方在于驱动的一个典型做法那就是如何把关键的内核数据结构和export到外部的/dev下的设备节点实现关联,比如:

 

关键数据结构struct snd_pcm,是根据cpu所固有的dai创建的,而对于每一个struct  snd_pcm又可能用到两个substream(它们实现具体的流的播放等),它们之间的链接是通过它的内部数据成员struct snd_pcm_str streams[2];来连接的,而这个snd_pcm类型的指针是在函数snd_device_new里面通过device_data放到设备里面的,这个设备会在snd_device_register_all

的时候注册到/dev下面,并且调用dev_set_drvdata(preg->dev, private_data);来把这个指针放到设备的私有数据里面;而在需要使用的时候通过snd_pcm_playback_open里面的snd_lookup_minor_data函数取得其私有数据并返回的,这样就实现了设备节点和对应的驱动的数据结构的关联,这是一种非常普遍的做法;有了这个数据结构它就可以根据一定的原则取得对应于这个需求的substream,于是一切的操作都可以交给这个substream

 

第三部分就是control的创建,这个函数比较简单,就是把表micco_snd_controls里面已经定义好的controls模板创建controls,然后加入到cardcontrols列表中去;本身功能很清晰,但是对于我们平台来说,需要非常小心,因为这里决定了各个controls的序号,而这个序号是audio_controller访问硬件的索引,所以千万要小心尽量要维持目前的controls的序号,如果要额外添加新的controls一定要记得要放在micco_add_widgets后面来做,这样可以做到兼容,否则audio_controller的工作量就大了

 

第四部分就是门的创建了,这个函数也是很清楚,就是把codec对应的门都加入到codec->dapm_widgets列表中去(这里的门的概念可以简单的理解为水管与水管之间的连接的地方,声音数据像水一样从水管里面流出来,源头可以是CPU了,也可以是modem,然后通过不同的门,流向不同的地方,比如speaker,比如蓝牙耳机等等),然后根据micco_audio_map把所有可能连在一起的门连接起来,这个表micco_audio_map的意思是{目的名字,控制点名字,源头名字},然后函数snd_soc_dapm_connect_input会根据这些名字去查表codec->dapm_widgets(先前已经把所有的门都加入了)找到它们再根据不同的类型做不同的连接,比如是mux之间的连接,muxpga之间的连接等等,注意这里的连接其实只不过是说找到连接的可能性,它对于不同的门,找到其可能的sourcesink,加入到对应的列表中去,具体细节如下:

首先,扫描整个codec所拥有的所有的门,如果它的名字和传入的sink的名字相同,则认为它就是这个路径的sink,如果它的名字和传入的source名字相同,则认为它是这个路径的source,如果源头或者sink没有找到都返回错误;然后分配一个struct snd_soc_dapm_path,这个数据结构的主要成分包括名字,source门,sink门,这条路径的control,这个源头和sink是否已经连接,是否已经走过(用在后面),这个数据结构会被挂在三个链表里面,一个是source的就是这个门会在很多的路径中,把它在这个路径中做sourcepath都连在一起,一个是sink的就是把这个门在所有这些由它做sinkpath都连接在一起,一个是把所有的路径都需要连接在一起的这个是通过codecdapm_paths来访问的;

list_add(&path->list, &codec->dapm_paths);

list_add(&path->list_sink, &wsink->sources);

list_add(&path->list_source, &wsource->sinks);

需要注意的时候,这里把路径的list_sink加入到了wsink门的sources列表里面,而把路径的list_source加入到wsourcesinks列表里面,所以当访问的时候从wsink门的sources出发就可以找到连接这个门作为sink的所有的路径,而从wsourcesinks列表出发就可以找到所有以这个门作为source的路径;

第三步就是为这个数据结构赋值:sourcesink,初始化三个链表;第四步:如果control为空则把这个路径加入到相应的三个链表中去,并且路径设为已经连接,并返回;第五步:否则,根据sink的类型,如果是adcdacinputoutputmicbiasvmidprepost,则把路径加入到三个链表,设置已经连接的标志;如果是snd_soc_dapm_mux则调用dapm_connect_mux来处理;如果是mixerswitch则调用dapm_connect_mixer来处理,如果是hpmiclinespk,则把path加入到三个链表中去,但是设置成为连接的状态

大约就是这样的了。

也许您要问,为什么要这么做呢?

这个,我也有想过,甚至我认为在门比较少的时候,确实没什么必要,但是这么做的好处在于当要播放音乐的时候,它可以实现自动的寻找路径并且自动poweron那些门,不需要上层做任何的控制,因为它真的到达目的地的所有的路径,这样它可以自己选择走哪条路;如果不这么连接起来的话,就需要提供给上层连接的接口,完全由上层来决定该连接哪些门,也必须由上层来负责poweronoff这些门;

第五部分就是注册了,这里就是向 /dev 注册设备节点,因为这些设备节点会由 alsa 层来访问的,这些设备节点和驱动的连接我前面已经说了,主要是提供了对上的 alsa 接口,给 alsa 层调用。   

4.               通常的使用流程的分析

通常使用alsalib来播放声音包括以下几个步骤:

1,   open,这个和oss相同,对应于alsa就是snd_pcm_open

2,   param设置,这个就是snd_pcm_hw_params;

3,   上层的alsa在设置param的成功以后或者出错的时候恢复都需要调用snd_pcm_prepare;

4,   write函数;

现在一个个的来看;

4.1.1          open过程介绍

如下图所示:Alsa驱动分析(转) - wilson - Wilsons blog

         就是我先前说的分成三部分,先是cpu级别的,包括clockenabe,中断的申请,空间的申请;

         然后就是平台级别的包括DMA所需要的空间的分配等;

         不过这里codec级别的没有提供相关的函数,由machine提供了一些函数主要是设置channel,格式,频率范围等等;

4.1.2          snd_pcm_hw_params流程分析

Alsa驱动分析(转) - wilson - Wilsons blog

         流程就是这样,至于里面做的具体的事情,我觉得只需要对照spec看看就知道了,具体的寄存器设置下面有一点讲解,主要是格式的设置(采样率的设置会留到prepare的时候),至于中断上来的时候那个更新hw_ptr函数很有用,这样上层就可以知道数据到底写了多少或者说还有多少空间可以写;

 

4.1.3          prepare流程分析

 

alsa层调用snd_pcm_prepare的时候会触发驱动对应的prepare的函数执行,如下:

Alsa驱动分析(转) - wilson - Wilsons blog可以看出基本上还是分为了三段,一段是cpu级别的,主要是对于ssp port的设置,具体设置如下:

对于voice通道,littleton_micco_voice_prepare的设置:

the sscr0 0xc0163f,sscr1 0xf01dc0,sspsp 0x800085

其中对于pcmssp地址是:

#define SSCR0_P4        __REG(0x41A00000)  /* SSP Port 4 Control Register 0 */

#define SSCR1_P4        __REG(0x41A00004)  /* SSP Port 4 Control Register 1 */

#define SSPSP_P4        __REG(0x41A0002C)  /* SSP Port 4 Programmable Serial Protocol */

所以结果就相当于:

 SSCR0_P4 0x41A000000xc0163f ——00000000110000000001011000111111

对于这个地址高8位为0

31 MOD-0:普通模式;30ACS-0:时钟选择是由NCSECS位绝决定,看后面;

29FPCKE-0FIFO packing mode disabled28()-0reserved

2752MM-013mbps模式;2624FRDC-0:每帧的时隙数

23TIM->1:表示禁止传输fifo underrun中断;22RIM-1:表示禁止接收fifo overrun中断

21NCS->0:表示时钟选择由ECS决定;20EDSS-0:表示前面填充DSS来达到8-16

198SCR-0x16:决定串口bit率,=sspx clock/(scr+1)???;7SSE-0:表示disable port

6ECS-0:表示片内的时钟用来计算serial clock rate54FRF-0b11:表示psp模式用来模拟I2S协议

30DSS-0b1111:表示16bit数据(EDSS0

 

SSCR1_P4 0x41A00004:  0xf01dc0——00000000111100000001110111000000

对于这个地址高8位也为0

31TTELP-0:表示最后一个bit传输(LSB)传完后有半个时钟处于高阻(三态)状态;

30(TTE)-0:表示传输信号不是三态的;29EBCEI-0bit传输错误不产生中断

28SCFR-0:表示SSPSCLK的时钟信号需要连续的工作,主模式ignore27ECRA-0:表示禁止其它ssp向它发起始终请求

26ECRB-0:表示同2725SCLKDIR-0:表示主模式,SSP端口,驱动SSPSCLK

24SFRMDIR-0:表示主模式,SSP端口,驱动SSPSFRM信号;

23RWOT-1:表示只接收不传输???;22TRAIL-1:表示trailing bytes dma burst来处理;

21TSRE-1:表示传输DMA sevice request enabled20RSRE-1:表示接收DMA service request允许

19TINTE-0:表示接收超时中断disable18PINTE-0:表示外设trail byte 中断disable

17:保留;16IFS->0:表示帧的极性由PSP的极性位决定;

15STRF-0:表示传输FIFO(读,写)由SSDR_X来决定;14EFWR-0:表示FIFO读写特别函数disable

1310RFT-0b0111:表示到达什么级别rxfifo断言中断;96TFT-0111:表示TXFIFO断言中断级别

5:保留;4SPH-0:表示在每一个帧开始之前要等一个时钟,结束后要等0.5个时钟;

3SPO-0:表示SSPSCLKinactive的时候是低电平;2LBM-0:表示非循环模式

1RIE-0:表示RXFIFO门槛到达的中断disable0RIE)->0:表示接收FIFO门槛到达中断disable

 

 

SSPSP_P4 0x41A0002C:  0x800085-00000000100000000000000010000101

这个地址的高8位为0

31reverved3028EDMYSTOP-0extended dummy stop

2726EDMYSTART-0extended dummy start25FSRT-0:下一帧的开始由前面的扩展STOP决定;

2423DMYSTOP-0b01:表示最后一bit传输完毕后保持activeclock1clock的延迟;22:保留

2116SFRMWDTH-0:表示最小位帧宽度;159SFRMDLY-0serial frame dealy

87DMYSTRT-0b01:表示1clock的延迟在开始的时候;64STRTDLY-0start delay

3ETDS-0:表示结束时的传输状态为low2SFRMP-1serial frame的极性;

10SCMODE-0b01data driven 上升沿,数据采样下降沿,idle状态,低;

 

对于littleton_micco_hifi_prepare的设置:

 The sscr0 e1c0003f,sscr1 701dc0,sspsp 40200004,sstsa 3,ssrsa 3,ssacd 60,ssacdd 6590040

其中对于I2sspp地址是:

#define SSCR0_P3  __REG(0x41900000)  /* SSP Port 3 Control Register 0 */

#define SSCR1_P3  __REG(0x41900004)  /* SSP Port 3 Control Register 1 */

#define SSPSP_P3  __REG(0x4190002C)  /* SSP Port 3 Programmable Serial Protocol */

#define SSTSA_P3  __REG(0x41900030)  /* SSP Port 3 Tx Timeslot Active */

#define SSRSA_P3  __REG(0x41900034)  /* SSP Port 3 Rx Timeslot Active */

#define SSACD_P3 __REG(0x4190003C)  /* SSP Port 3 Audio Clock Divider */

#define     SSACDD_P3   __REG(0x41900040)  /* SSP Port 3 Audio Clock Dither Divider Register */

 

SSCR0_P3==__REG(0x41900000):e1c0003f——11100001110000000000000000111111

31 MOD-1:网络模式;30ACS-1:时钟选择是audio clockaudio clock divider决定,由ssacd寄存器决定;

29FPCKE-1FIFO packing mode enabled28()-0reserved

2752MM-013mbps模式;2624FRDC-1:每帧的时隙数

23TIM->1:表示禁止传输fifo underrun中断;22RIM-1:表示禁止接收fifo overrun中断

21NCS->0:这里ignore,由ACS决定了(为1);20EDSS-0:表示前面填充DSS来达到8-16

198SCR-0:ACS那里决定;7SSE-0:表示disable port,工作时应为1

6ECS-0:表示片内的时钟用来计算serial clock rate54FRF-0b11:表示psp模式用来模拟I2S协议

30DSS-0b1111:表示16bit数据(EDSS0

 

SSCR1_P3==__REG(0x41900004):701dc0——00000000011100000001110111000000

31TTELP-0:表示最后一个bit传输(LSB)传完后有半个时钟处于高阻(三态)状态;

30(TTE)-0:表示传输信号不是三态的;29EBCEI-0bit传输错误不产生中断

28SCFR-0:表示SSPSCLK的时钟信号需要连续的工作,主模式ignore27ECRA-0:表示禁止其它ssp向它发起始终请求

26ECRB-0:表示同2725SCLKDIR-0:表示主模式,SSP端口,驱动SSPSCLK

24SFRMDIR-0:表示主模式,SSP端口,驱动SSPSFRM信号;

23RWOT-0:接收和传输都可以;22TRAIL-1:表示trailing bytes dma burst来处理;

21TSRE-1:表示传输DMA sevice request enabled20RSRE-1:表示接收DMA service request允许

19TINTE-0:表示接收超时中断disable18PINTE-0:表示外设trail byte 中断disable

17:保留;16IFS->0:表示帧的极性由PSP的极性位决定;

15STRF-0:表示传输FIFO(读,写)由SSDR_X来决定;14EFWR-0:表示FIFO读写特别函数disable

1310RFT-0b0111:表示到达什么级别rxfifo断言中断;96TFT-0111:表示TXFIFO断言中断级别

5:保留;4SPH-0:表示在每一个帧开始之前要等一个时钟,结束后要等0.5个时钟;

3SPO-0:表示SSPSCLKinactive的时候是低电平;2LBM-0:表示非循环模式

1RIE-0:表示RXFIFO门槛到达的中断disable0RIE)->0:表示接收FIFO门槛到达中断disable

 

SSPSP_P3==__REG(0x4190002C):40200004——01000000001000000000000000000100

31reverved3028EDMYSTOP-4extended dummy stop

2726EDMYSTART-0extended dummy start25FSRT-0:下一帧的开始由前面的扩展STOP决定;

2423DMYSTOP-0b00:表示最后一bit传输完毕后保持activeclock数的延迟;22:保留

2116SFRMWDTH-0b20:表示最小位帧宽度;159SFRMDLY-0serial frame dealy

87DMYSTRT-0b00:表示0clock的延迟在开始的时候;64STRTDLY-0start delay

3ETDS-0:表示结束时的传输状态为low2SFRMP-1serial frame的极性;

10SCMODE-0b00data driven 下降沿,数据采样上升沿,idle状态,低;

 

SSTSA_P3==__REG(0x41900030):3——0011

318->0:reserved;7:0TTSA->0b0011:表示在那个time slot里面是传输数据的0,不传输,1传输;

SSRSA_P3==__REG(0x41900034):3——0011

31reserved70RTSA-0:表示在那个slot里面接收数据,0,不接受,接收;

SSACD_P3==__REG(0x4190003C):60——01100000

318reserved7SCDX8-0sysclk/4产生内部audio clock1sysclk/8产生audio clock

64ACPS-0b110:PLL输出时钟由Audio clock dither Divider register value决定;

3SCDB-0:如果SCDX80scdx8决定,为1,则sysclk不分频;

20ACDS-0:表示clock divider select /1

SSACDD_P3==__REG(0x41900040):6590040——00000110010110010000000001000000

31reserved3016NUM-1625;除数(0x659

1512reserved110DEN-64:被除数

比如我们的板子上是这样计算这些值的:

比如,在我们的机子上的一个实例是这样的,

那么第一步取得采样率:48K,它也就是Sync clock

第二步球的bit率:48X64=3.072M

第三步求的sysclk:这个根据scdx8决定是X4还是X8,在我们的例子中是4,所以:3.072X4=12.288

第四步求得我们要的dither divider y,公式为:

624*(y)/2=12.288

算出y=0.039384615384615384615384615384615

所以查可能的分子和分母表,得出,分子是:

64,分母是1625

如下图所示:

Alsa驱动分析(转) - wilson - Wilsons blog

当然更加详细的请参阅spec

 

第二段是平台级别的,主要是对于DMA的初始化;

第三段是codec级别的,这里主要是对codec本身的设置,通过i2c接口对codec的寄存器操作,比如采样率等等;

最后面还有一个poweron的函数,这个函数前面有提到,但是没有详细分析,这里分析一下:

首先根据事件类型,决定是关闭门序列,还是启动门序列,我只分析启动过程;

得到启动序列,就开始遍历整个序列,对于这个序列的每一个类型,查找所有的门的序列,直到有一个门的类型和当前启动序列的类型相同,然后再根据不同的类型做不同的检查和power

1,如果是snd_soc_dapm_vmid则继续,不做任何处理;

2

A)如果是snd_soc_dapm_adc,并且其active1,这个active在上一步已经分析过了,必须要包含这个流的名字的sname的门才会被激活,假设我们现在讨论的是用pcm通道播放声音,那么流的名字就是“Voice Playback”,所以,将dac3active被设成1,这样就避免了power on dac1dac2,和adc了。如果这两个条件都满足,那么必然是“Voice Capture”了,因为只有这时候,我们才会用到adc,现在看看,如果用了adc将会启动什么,于是调用函数is_connected_input_ep,这是一个通用递归函数,从名字上来说就是看是否是已经连接了输入的门,我们只考虑adc的情况,其余的情况待会再讨论,对于adc,在is_connected_input_ep函数里面,是通过遍历所有以这个门作为sinksource门(list_for_each_entry(path, &widget->sources, list_sink),可以看到,这里的最后一个参数是list_sink,而第二个参数却是widget->sources,这个原因我在门连接分析页里面已经分析过了,总之sources就表示这个门的sources列表,而sinks就是这个门的sink列表),通过递归调用is_connected_input_ep来查看这些source门是否其中有一个是连通的,返回的是所有是否连通的和(联通为1,否则为0),所以返回的结果可能是大于1的数,表示不只一个源是联通的。

B)如果这个函数返回为真则表示此adc是联通的,于是调用dapm_update_bits来处理,这个函数过对mux(它的reg<0)inputoutputmichplinespk,不做任何处理就返回了;过了这一关,开始查是否menrevert为真,如果为真,则把power取反,原来为真现在变假,于是调用snd_soc_readmicco_soc_read)开始读这个寄存器的值(注意,这里读的值是可能和物理上的这个寄存器的值不一样的,这里读的值是cache里面的值),读出来后强制把1<<shift后的位置为1,比较新旧值是否有变化,如果有,则调用snd_soc_write(codec, widget->reg, new)把值写到cache里面(实际负责写的是micco_soc_write,而且,它对于0x70+0x15以下包含0x15的值是直接写到寄存器的地址的,否则只是些到数组cache里面去)好对于adc的情况我们就分析完了。

3

A)如果此类型是snd_soc_dapm_dac并且active1,则调用is_connected_output_ep来取得是否要power,下面来看看函数is_connected_output_ep,这也是一个通用的判断是否有连接到输出的递归函数,我们只分析dac的情况,list_for_each_entry(path, &widget->sinks, list_source),上面已经讲过,这里实际上查的是这个门的所有的sink列表,通过递归调用is_connected_output_ep来看是否它的sink是联通的,只要有一条路是联通的,则power为真。

B)返回后调用dapm_update_bits来处理,上面已经分析过了,这个函数就是判断是否需要设置此门的寄存器的1<<shift位。

4,如果此类型是snd_soc_dapm_pga,则调用is_connected_input_ep来判断是否联通输入,再调用is_connected_output_ep判断是否联通输出,对于pga is_connected_input_ep函数的处理和adc是一样的,对于is_connected_output_epdac的处理是一样的,接着调用dapm_set_pga,根据power的值决定是mute pga还是启用pga,但是就我打印的结果来看,基本上这个函数所起的作用为0,因为对于pga的门似乎都没有设置相应的control,最后调用dapm_update_bits,设置power 位。

5,对于other widget,这里在我们的平台上多半是指mux,首先调用is_connected_input_ep判断是否连接输入,再调用is_connected_output_ep判断是否有输出,调用dapm_update_bits位设置power 位,最后调用w->eventdo_post_event)来进行后期处理,这里主要就是对mux进行寄存器设置,因为mux的寄存器的地址都是大于0x70+0x15的,所以它们的地址需要转化,这个函数就是根据mux的类型,访问不同的寄存器。

 

基本上prepare后,一切就都就绪了,只等一个trigger;而trigger的执行会在上层的alsalib调用write的函数触发;

4.1.4          write的流程

 

Alsa驱动分析(转) - wilson - Wilsons blog

用户层的write到内核里面都是通过ioctl来做的,这里面会触发trigger函数的执行,等trigger执行完以后,才会真正调用函数把用户层的东西copydma分配的空间;

这里面基本上只是画了最简单的逻辑,其实里面非常的复杂特别是函snd_pcm_lib_write1,这里面有同步的操作,也就是要等到有空余的空间的时候才允许写,否则就要等待,唤醒是通过函数snd_pcm_update_hw_ptr_post来做的,这个函数会在DMA传输完一帧的中断到来的时候被调用,用来更新缓冲区指针;

 

其中trigger的逻辑如下:

Alsa驱动分析(转) - wilson - Wilsons blog

 

简单的说就是启动DMAenable ssp口;

4.1.5          使用流程的总结t

         简单总结一下,用户的使用流程;

         A,调用snd_pcm_open打开设备节点对应的pcm流的substream也就是录音或者play

B,调用snd_pcm_hw_params设置硬件参数,包括格式,通道,采样率,DMA空间的分配,中断的申请等等,这里面会调用prepare函数使硬件准备好硬件,包括codec的寄存器设置,各种路径的建立,门的power on等;

C,调用write函数实现把数据写到设备里面去,这里会触发trigger函数也就是DMA的启动,SSP端口的启动等。

5.               Amixer调用的相关逻辑

我们的audio controller所调用的驱动的接口都是amixer csetcget,所以有必要分析一下它的逻辑:

5.1.1          Amixer调用的上层逻辑

Alsa驱动分析(转) - wilson - Wilsons blog

    也就是说通过/dev下面的设备节点调用相应的ioctl,然后进入到内核的范围;

5.1.2          Amixer的内核流程     

Alsa驱动分析(转) - wilson - Wilsons blog

这里只分析了控制函数为snd_soc_dapm_put_enum_double的处理逻辑,其它的都类似,而具体的应该是哪个处理函数来处理是在controlnew的时候就已经确立了的,对于我们的平台其实在表micco_dapm_widgets建立的时候就已经确立了;

为了方便后来者的调试,我这里把各个numid的对应的控制函数都列出来了,如下:

numid=112snd_soc_put_volsw

numid=1320snd_soc_dapm_put_enum_double

 

 

.

6.               总结

Alsa驱动的架构主要是分成对上为alsalib提供接口,对下实现硬件的管理,对上的内容基本都是在sound/core目录里面的文件来完成,而设计硬件的操作分成两部分一部分相关与cpu这边的是由sound/soc/pxa目录里面的文件来完成的,另外一部分设计codec是由sound/soc/codec来完成的,这部分主要就是对codec这边的寄存器的设置;简单示意如下:

Alsa驱动分析(转) - wilson - Wilsons blog

它复杂的地方在于用户态的alsa lib

7.               未讨论

还有一些地方没有讨论到,比如timer,不过留到以后补充吧

备注:

              内核版本:2.6.21+marvel patch

                硬件平台:pxa310+9034codec

 作者:wylhistory

转载请注明出处!

  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Linux操作系统下各项服务的解释 1、alsasound:Alsa声卡驱动程序支持。Alsa声卡驱动程序本来是为了一种声卡Gravis UltraSound(GUS)而写的,该程序被证 明很优秀,于是作者就开始为一般的声卡写驱动程序。Alsa和OSS/Free 及OSS/Linux兼容,但是有自己的接口,甚至比OSS优秀。   2、amd:运行automount精灵程序,该精灵在必要时自动安装一些本地设备和NFS文件系统。   3、apmd:apmd用来监视系统用电状态,并将相关信息通过syslogd 写入日志。也可以用来在电源不足时关机。   4、arpwatch:该程序主要用来维护以太网物理地址和IP地址的对应关系。   5、atalk:AppleTalk精灵程序。注意不要在后台运行该程序,该程序的数据结构必须在运行其他进程前先花一定时间初始化。   6、atd:运行用户用At命令调度的任务。也在系统负荷比较低时运行批处理任务。   7、autofs:当您需要时自动转载文件系统,而当您不需要时自动卸载。   8、bootparamd:该服务允许老的Sun工作站从Linux网络启动,它和rarp现在很少使用,基本上被bootp和dhcp取代了。   9、crond:cron是Unix下的一个传统程序,该程序周期地运行用户调度的任务。比起传统的Unix版本,Vixie版本添加了不少属性,而且更安全,配置更简单。   10、dhcpd:该精灵提供了对动态主机控制协议(Dynamic Host Control Protocol)的访问支持。
首先接到这一个项目,说是要用mediastreamer2做一个网络电话。之前也是从来没有接触过。于是首先开始在百度中搜索一下需要哪些东西,以及那些步骤。最后大致了解了一下,做这个项目最终要的就是需要移植好多的库,每一个库都需要配置,最后在交叉编译好动态库,然后在执行mediastreamer2的时候去调用这些动态库和头文件就OK了。 1、首先meidastream2是基于ortp库的,那么首先就是下载源码,交叉编译。 交叉编译ortp 下载源码:http://savannah.c3sl.ufpr.br/linphone/ortp/sources/?C=S;O=A 我使用0.18.0版本 ortp-0.18.0.tar.gz 然后通过winshare(Windows和Linux的通信)把下载好的库文件拷贝到Linux下, 然后解压 tar zxvf ortp-0.18.0.tar.gz 注意这个时候可能会发生错误,是没有权限的问题,那么就在命令行前边加上sudo 然后配置 把下边这三行写成一个脚本 vim **.sh ./configure CC=arm-linux-gcc --host=arm-linux --target=arm-linux --prefix=/home/protocol_stack/install/ make make install 然后用chmod 777 **.sh 执行脚本./**.sh 这样子就完成了配置,编译,安装。(安装目录为/home/protocol_stack/install/,也就是最后生成的头文件,可执行文件,库文件都会在这个目录下) 2、因为项目是要用到SIP协议的,所以我们还需要移植sip的库 osip2和eXosip2协议,这两个协议对应两个库,osip是简单的osip协议,但是因为API少等一系列原因,增加了eXosip2对osip2的补充。 交叉编译osip2 下载源码:http://ftp.gnu.org/gnu/osip/ 我使用的版本是3.6.0 libosip2-3.6.0.tar.gz 然后通过winshare(Windows和Linux的通信)把下载好的库文件拷贝到Linux下, 然后解压 tar zxvf libosip2-3.6.0.tar.gz 注意这个时候可能会发生错误,是没有权限的问题,那么就在命令行前边加上sudo 然后配置 把下边这三行写成一个脚本 vim **.sh ./configure --host=arm-linux --target=arm-linux --prefix=/home/protocol_stack/install/ make make install 然后用chmod 777 **.sh 执行脚本./**.sh 交叉编译eXosip2 下载源码:http://ftp.gnu.org/gnu/osip/ 我使用的版本是3.6.0 libeXosip2-3.6.0.tar.gz 然后通过winshare(Windows和Linux的通信)把下载好的库文件拷贝到Linux下, 然后解压 tar zxvf libeXosip2-3.6.0.tar.gz 注意这个时候可能会发生错误,是没有权限的问题,那么就在命令行前边加上sudo 然后配置 把下边这三行写成一个脚本 vim **.sh ./configure --host=arm-linux --target=arm-linux --prefix=/home/protocol_stack/install/ PKG_CONFIG_PATH=/home/protocol_stack/install/lib/pkgconfig make make install 然后用chmod 777 **.sh 执行脚本./**.sh 接下来可以编译mediastreamer2了,不过ms2,依赖好多库:ogg、speex、pulseaudio。而pulseaudio又依赖许多库:alsa、json、libtool。 3、交叉编译ogg 下载源码:http://xiph.org/downloads/ 我使用1.3.1版本 libogg-1.3.3.tar.gz 然后通过winshare(Windows和Linux的通信)把下载好的库文件拷贝到Linux下, 然后解压 tar zxvf libogg-1.3.3.tar.gz 注意这个时候可能会发生错误,是没有权限的问题,那么就在命令行前边加上sudo 然后配置 把下边这三行写成一个脚本 vim **.sh ./configure CC=arm-linux-gcc --prefix=/home/protocol_stack/install/ --host=arm-linux make make install 然后用chmod 777 **.sh 执行脚本./**.sh 4、交叉编译speex 下载源码:http://www.speex.org/downloads/ 我使用1.2rc1版本 speex-1.2rc1.tar.gz 然后通过winshare(Windows和Linux的通信)把下载好的库文件拷贝到Linux下, 然后解压 tar zxvf speex-1.2rc1.tar.gz 注意这个时候可能会发生错误,是没有权限的问题,那么就在命令行前边加上sudo 然后配置 把下边这三行写成一个脚本 vim **.sh ./configure CC=arm-linux-gcc --prefix=/home/protocol_stack/install/ --with-ogg=/home/protocol_stack/install/ --enable-fixed-point --disable-float-api \ --host=arm-linux make make install 然后用chmod 777 **.sh 执行脚本./**.sh 5、交叉编译pulseaudio 下载源码:http://freedesktop.org/software/pulseaudio/releases/ 我使用1.0版本 pulseaudio-1.0.tar.gz 然后通过winshare(Windows和Linux的通信)把下载好的库文件拷贝到Linux下, 然后解压 tar zxvf pulseaudio-1.0.tar.gz 注意这个时候可能会发生错误,是没有权限的问题,那么就在命令行前边加上sudo 然后配置 把下边这三行写成一个脚本 vim **.sh ./configure CC=arm-linux-gcc CXX=arm-linux-g++ --prefix=/home/protocol_stack/install --host=arm-linux --disable-rpath --disable-nls --disable-dbus --disable-bluez --disable-samplerate --disable-solaris --disable-gconf --disable-avahi --disable-jack --disable-lirc --disable-glib2 --disable-gtk2 --disable-openssl --disable-ipv6 --disable-asyncns --disable-per-user-esound-socket --disable-oss-output --disable-oss-wrapper --disable-x11 --enable-neon-opt=no --with-database=simple PKG_CONFIG_PATH=/home/protocol_stack/install/lib/pkgconfig CPPFLAGS=-I/home/protocol_stack/install/include LDFLAGS=-L/home/protocol_stack/install/lib CFLAGS=-I/home/protocol_stack/install/include make make install 然后用chmod 777 **.sh 执行脚本./**.sh 错误1: checking for ltdl.h... no configure: error: Unable to find libltdl version 2. Makes sure you have libtool 2.4 or later installed. make: *** No targets specified and no makefile found. Stop. 分析;找不到libltdl。确保你有libtool 2.4及以上的版本。 下载libtool 2.4.2版本 这时需要交叉编译libtool 下载源码:ftp://ftp.gnu.org/gnu/libtool/ 我使用2.4.2版本 libtool-2.4.2.tar.gz 然后通过winshare(Windows和Linux的通信)把下载好的库文件拷贝到Linux下, 然后解压 tar zxvf libtool-2.4.2.tar.gz 注意这个时候可能会发生错误,是没有权限的问题,那么就在命令行前边加上sudo 然后配置 把下边这三行写成一个脚本 vim **.sh ./configure --host=arm-linux --prefix =/home/protocol_stack/install/ make make install 然后用chmod 777 **.sh 执行脚本./**.sh 交叉编译alsa: http://www.alsa-project.org/main/index.php/Main_Page 这个库的版本需要根据你嵌入式Linux内核中alsa的版本而定,可以使用命令查看内核中alsa的版本: # cat /proc/asound/version Advanced Linux Sound Architecture Driver Version 1.0.24. 可以到内核中alsa驱动版本是1.0.24,所以我选1.0.24版本 alsa-lib-1.0.24.1.tar.gz 然后通过winshare(Windows和Linux的通信)把下载好的库文件拷贝到Linux下, 然后解压 tar zxvf speex-1.2rc1.tar.gz 注意这个时候可能会发生错误,是没有权限的问题,那么就在命令行前边加上sudo 然后配置 把下边这三行写成一个脚本 vim **.sh ./configure --host=arm-linux --prefix =/home/protocol_stack/install/ make make install 然后用chmod 777 **.sh 执行脚本./**.sh 错误:configure: error: Package requirements ( sndfile >= 1.0.20 ) were not met: No package 'sndfile' found 分析:缺少库 libsndfile库,那么接下来再进行交叉编译libsndfile libsndfile-1.0.25.tar.gz http://www.linuxfromscratch.org/blfs/view/svn/multimedia/libsndfile.html 然后通过winshare(Windows和Linux的通信)把下载好的库文件拷贝到Linux下, 然后解压 tar zxvf libsndfile-1.0.25.tar.gz 注意这个时候可能会发生错误,是没有权限的问题,那么就在命令行前边加上sudo 然后配置 把下边这三行写成一个脚本 vim **.sh ./configure --host=arm-linux --prefix =/home/protocol_stack/install/ make make install 然后用chmod 777 **.sh 执行脚本./**.sh 7、最后编译mediastreamer2 下载源码:http://ftp.twaren.net/Unix/NonGNU//linphone/mediastreamer/ 我使用2.8版本 mediastreamer-2.8.0.tar.gz 然后通过winshare(Windows和Linux的通信)把下载好的库文件拷贝到Linux下, 然后解压 tar zxvf mediastreamer-2.8.0.tar.gz 注意这个时候可能会发生错误,是没有权限的问题,那么就在命令行前边加上sudo 然后配置 把下边这三行写成一个脚本 vim **.sh ./configure CC=arm-linux-gcc --prefix=/home/protocol_stack/install/ PKG_CONFIG_PATH=/home/protocol_stack/install/lib/pkgconfig --disable-gsm --enable-video=no --enable-macsnd=no --disable-static --disable-sdl --disable-x11 --disable-ffmpeg --host=arm-linux --target=arm-linux make make install 然后用chmod 777 **.sh 执行脚本./**.sh 上面的configure选项没有屏蔽v4l1和v4l2,所以还得交叉编译v4l 编译v4l libv4l-0.6.4.tar.gz 下载源码:http://pkgs.fedoraproject.org/repo/pkgs/libv4l/ 然后通过winshare(Windows和Linux的通信)把下载好的库文件拷贝到Linux下, 然后解压 tar zxvf libv4l-0.6.4.tar.gz 注意这个时候可能会发生错误,是没有权限的问题,那么就在命令行前边加上sudo 然后配置 我使用0.6.4版本 libv4l-0.6.4.tar.gz make clean make CC=arm-linux-gcc make install PREFIX=/home/protocol_stack/install 编译mediastreamer2出错:(1)checking for LIBCHECK... no checking for LIBJSON... no configure: error: Package requirements ( json >= 0.9 ) were not met: No package 'json' found 解决方法就是交叉编译json 下载源码:http://ftp.debian.org/debian/pool/main/j/json-c/ 分析:缺少json库,那么我们继续交叉编译json库 json-c_0.12.1.orig.tar.gz 然后通过winshare(Windows和Linux的通信)把下载好的库文件拷贝到Linux下, 然后解压 tar zxvf mediastreamer-2.8.0.tar.gz 注意这个时候可能会发生错误,是没有权限的问题,那么就在命令行前边加上sudo 然后配置 ./configure --host=linux-arm \ --prefix =/home/protocol_stack/install/ make && make install 好了,json库已经编译完成了。接下来我们继续编译mediastreamer2 。。。。。 但是还是有问题,怎么办呢?还是哪个问题还是找不到json库。 分析:在json的论坛中,找到了解决方案:把编译生成的/lib/pkgconfig/这个目录下生成了一个json-c.pc。最后mediastreamer2在调用的时候找的是json.pc。那么我们就把这个文件名改为json.pc #mv json-c.pc json.pc OK,这次这个是可以编译的过去了。接下来继续编译 。。。 又出现问题了 /home/protocol_stack/install/lib/libjson.so: undefined reference to `rpl_malloc' /home/protocol_stack/install/lib/libjson.so: undefined reference to `rpl_realloc' 问题分析: 这个错误的原因是因为没有定义 rpl_malloc 和 rpl_realloc 这两个变量。 那么我们应该怎么办么? 那么就在这个目录下进行查这两个变量是在哪里定义的? 于是:#grep "rpl_malloc" -nR * ....... 找到了,原来这两个变量是在这个config的文件中的。是一个宏开关 那么就好办了,我们就直接把这两个宏进行注释。 嗯嗯,继续。。。我们重新编译json库。。。嗯嗯编译好了,接下来继续来编译mediastreamer2 。。。。 又出错了,还是这个原因 /home/protocol_stack/install/lib/libjson.so: undefined reference to `rpl_malloc' /home/protocol_stack/install/lib/libjson.so: undefined reference to `rpl_realloc 嗯嗯,还是这个原因?究竟是为什么呢。再次来到json的目录下,再次看有没有把那两个宏开关给关闭? 嗯哼? 竟然没有关闭? 分析?明白了。原来是我把配置和编译同时执行了。这个宏开关是./configure ...生成的。 那么就只好,这样。把./configure。。。生成的config文件,再进行关闭宏开关。最后直接make && make install -j8 直接编译,安装,是不能再次进行配置的。因为以配置config文件就会再次生成,那么宏开关就又开了。 OK,安装好了,下来继续进行编译mediastreamer2.。。。。。。。。。。。 。。。。。。。。。。。。。。 又出现了问题? error: /user/include/python2.7/pyconfig.h:15:52: fatal error: arm-linux-gnueabi/python2.7/pyconfig.h: No such file or directory compilation terminated. 分析::找不到arm-linux-gnueabi/python2.7/pyconfig.h这文件。那就继续交叉编译python 好吧,继续下载python,然后再进行交叉编译,但是编译Python的时候出来一系列的问题。根本没有办法解决。 那么该怎么办呢?时候一个小时又一个小时的过去? 最后有一个大胆的想法,既然python都编译不下去。那就不要了。 于是,在mediastreamer2的./configure 中添上一项 --without-python 。 。。。再次配置编译。。。。。。。。。。。 error: /user/include/python2.7/pyconfig.h:15:52: fatal error: arm-linux-gnueabi/python2.7/pyconfig.h: No such file or directory compilation termiated. 嗯哼?还是一样的错误。怎么办呢? 于是乎就又在论坛上进行找灵感。。。。。 还是找不到。。。 又一结合前边几个库的配置编译,发现不使能一个模块还可以用另外一个--disable-python 。。。 于是乎 就把--without-python改为了--disable-python 继续编译。。。。 。。。。。。。。。。。。。。。。。。。。。 到了这个节骨眼上了,编译每跳一下,我的心就跟着逗一下。。。。心酸 。。。。。。 。。。。。。 。。。。。。 竟然编译成功了。。。。 哈哈。。。。。。。。。 于是,马上就把编译好的库,拷贝到了开发板。。。 嗯嗯,本来还想把编译好的库目录树拷贝下的,但是太多了,放不下。。。算了吧。。。。 找到编译好的库 在库中的/bin中找到arm-linux-mediastream 然后执行./arm-linux-mediastream 。。。。报错了 问题: error : while loading shared libraries: libmediastreamer.so.1: cannot open shared object file: No such file 答案:分析: 遇到这个问题就是,libmediastreamer.so.1这个动态库,在可执行文件armlinuxmediastreamer执行的时候,会调用这个动态库,但是环境变量中找不到这个动态库。那么我们就是要把我们编译好的动态链接库的目录加到环境变量中 LD_LIBRARY_PATH=$LD_LIBRARY_PATH://arm/lib/这个目录下就是放着我们编译好的所有的动态链接库(包括libmediastreamer.so.1) 执行步骤:LD_LIBRARY_PATH=$LD_LIBRARY_PATH://arm/lib export LD_LIBRARY_PATH ./arm-linux-mediastream mediastream --local --remote --payload [ --fmtp ] [ --jitter ] [ --width ] [ --height ] [ --bitrate ] [ --ec (enable echo canceller) ] [ --ec-tail ] [ --ec-delay ] [ --ec-framesize ] [ --agc (enable automatic gain control) ] [ --ng (enable noise gate)] [ --ng-threshold (noise gate threshold) ] [ --ng-floorgain (gain applied to the signal when its energy is below the threshold.) ] [ --capture-card ] [ --playback-card ] [ --infile <input wav file> specify a wav file to be used for input, instead of soundcard ] [ --outfile specify a wav file to write audio into, instead of soundcard ] [ --camera ] [ --el (enable echo limiter) ] [ --el-speed (gain changes are smoothed with a coefficent) ] [ --el-thres (Threshold above which the system becomes active) ] [ --el-force (The proportional coefficient controlling the mic attenuation) ] [ --el-sustain (Time in milliseconds for which the attenuation is kept unchanged after) ] [ --el-transmit-thres (TO BE DOCUMENTED) ] [ --rc (enable adaptive rate control) ] [ --zrtp (enable zrtp) ] [ --verbose (most verbose messages) ] [ --video-windows-id <video surface:preview surface>] [ --srtp (enable srtp, master key is generated if absent from comand line) [ --netsim-bandwidth (simulates a network download bandwidth limit) 于是按照第一种方式进行 参数添加 ./arm-linux-mediastream --local 8888 --remote 127.0.0.1:88 88 OK运行正常了 下面是运行信息。。。 ortp-message-audio_stream_process_rtcp: interarrival jitter=119 , lost packets percentage since last report=0.000000, round trip time=0.000000 seconds ortp-message-oRTP-stats: RTP stats : ortp-message- number of rtp packet sent=150 ortp-message- number of rtp bytes sent=25800 bytes ortp-message- number of rtp packet received=150 ortp-message- number of rtp bytes received=25800 bytes ortp-message- number of incoming rtp bytes successfully delivered to the application=25284 ortp-message- number of rtp packet lost=0 ortp-message- number of rtp packets received too late=0 ortp-message- number of bad formatted rtp packets=0 ortp-message- number of packet discarded because of queue overflow=0 ortp-message-Bandwidth usage: download=81.290281 kbits/sec, upload=81.288664 kbits/sec ortp-message-Receiving RTCP SR ortp-message-Receiving RTCP SDES ortp-message-Found CNAME=unknown@unknown ortp-message-Found TOOL=oRTP-0.18.0 ortp-message-Found NOTE=This is free sofware (LGPL) ! ortp-message-Quality indicator : 4.888437 运行正常了。。。。。。
mini2440 beer(通常称pwm或timer)驱动,注册为misc(杂项)设备, 挂载再platform bus上, 测试信息: U-Boot 2012.07 (Aug 30 2012 - 21:55:43) +++++++++++++++++++++++++++++++++++++++++++++++++++++++ +++ Welcome to my u-boot +++ +++ Liyong-zou +++ +++++++++++++++++++++++++++++++++++++++++++++++++++++++ CPUID: 32440001 FCLK: 400 MHz HCLK: 100 MHz PCLK: 50 MHz DRAM: 64 MiB WARNING: Caches not enabled NAND: 256 MiB In: serial Out: serial Err: serial Net: dm9000 Hit any key to stop autoboot: 5 \0x08\0x08\0x08 4 \0x08\0x08\0x08 3 \0x08\0x08\0x08 2 \0x08\0x08\0x08 1 \0x08\0x08\0x08 0 dm9000 i/o: 0x20000300, id: 0x90000a46 DM9000: running in 16 bit mode MAC: 00:01:02:03:04:05 could not establish link Using dm9000 device File transfer via NFS from server 192.168.1.30; our IP address is 192.168.1.20 Filename '/home/liyong-zou/nfs/kernel/uImage'. Load address: 0x30008000 Loading: *\0x08#######################################################T ########## \0x09 ################################################################# \0x09 #########################T ######################################## \0x09 ################################################################# \0x09 ################################################################# \0x09 ################################################################# \0x09 ###############T #######T ########### done Bytes transferred = 2164312 (210658 hex) ## Booting kernel from Legacy Image at 30008000 ... Image Name: Linux-2.6.39.4 Created: 2012-10-27 13:48:03 UTC Image Type: ARM Linux Kernel Image (uncompressed) Data Size: 2164248 Bytes = 2.1 MiB Load Address: 30008000 Entry Point: 30008040 Verifying Checksum ... OK XIP Kernel Image ... OK OK Starting kernel ... Uncompressing Linux... done, booting the kernel. Linux version 2.6.39.4 (liyong-zou@liyongzou-desktop) (gcc version 4.4.3 (ctng-1.6.1) ) #86 Sat Oct 27 21:47:46 CST 2012 CPU: ARM920T [41129200] revision 0 (ARMv4T), cr=00007177 CPU: VIVT data cache, VIVT instruction cache Machine: MINI2440 Memory policy: ECC disabled, Data cache writeback CPU S3C2440A (id 0x32440001) S3C24XX Clocks, Copyright 2004 Simtec Electronics S3C244X: core 400.000 MHz, memory 100.000 MHz, peripheral 50.000 MHz CLOCK: Slow mode (1.500 MHz), fast, MPLL on, UPLL on Built 1 zonelists in Zone order, mobility grouping on. Total pages: 16256 Kernel command line: noinitrd root=/dev/nfs nfsroot=192.168.1.30:/home/liyong-zou/nfs/rootfs ip=192.168.1.20:192.168.1.30:192.168.1.1:255.255.255.0::eth0:off console=ttySAC0,115200 PID hash table entries: 256 (order: -2, 1024 bytes) Dentry cache hash table entries: 8192 (order: 3, 32768 bytes) Inode-cache hash table entries: 4096 (order: 2, 16384 bytes) Memory: 64MB = 64MB total Memory: 60500k/60500k available, 5036k reserved, 0K highmem Virtual kernel memory layout: vector : 0xffff0000 - 0xffff1000 ( 4 kB) fixmap : 0xfff00000 - 0xfffe0000 ( 896 kB) DMA : 0xffc00000 - 0xffe00000 ( 2 MB) vmalloc : 0xc4800000 - 0xf6000000 ( 792 MB) lowmem : 0xc0000000 - 0xc4000000 ( 64 MB) modules : 0xbf000000 - 0xc0000000 ( 16 MB) .init : 0xc0008000 - 0xc002a000 ( 136 kB) .text : 0xc002a000 - 0xc03f3ea4 (3880 kB) .data : 0xc03f4000 - 0xc0418c40 ( 148 kB) SLUB: Genslabs=13, HWalign=32, Order=0-3, MinObjects=0, CPUs=1, Nodes=1 NR_IRQS:85 irq: clearing subpending status 00000002 Console: colour dummy device 80x30 console [ttySAC0] enabled Calibrating delay loop... 49.56 BogoMIPS (lpj=123904) pid_max: default: 32768 minimum: 301 Mount-cache hash table entries: 512 CPU: Testing write buffer coherency: ok gpiochip_add: gpios 288..303 (GPIOK) failed to register gpiochip_add: gpios 320..334 (GPIOL) failed to register gpiochip_add: gpios 352..353 (GPIOM) failed to register NET: Registered protocol family 16 MINI2440: Option string mini2440=0tb MINI2440: LCD [0:240x320] 1:800x480 2:1024x768 S3C2440: Initialising architecture S3C2440: IRQ Support S3C244X: Clock Support, DVS off bio: create slab <bio-0> at 0 usbcore: registered new interface driver usbfs usbcore: registered new interface driver hub usbcore: registered new device driver usb s3c-i2c s3c2440-i2c: slave address 0x10 s3c-i2c s3c2440-i2c: bus frequency set to 97 KHz s3c-i2c s3c2440-i2c: i2c-0: S3C I2C adapter Advanced Linux Sound Architecture Driver Version 1.0.24. NET: Registered protocol family 2 IP route cache hash table entries: 1024 (order: 0, 4096 bytes) TCP established hash table entries: 2048 (order: 2, 16384 bytes) TCP bind hash table entries: 2048 (order: 1, 8192 bytes) TCP: Hash tables configured (established 2048 bind 2048) TCP reno registered UDP hash table entries: 256 (order: 0, 4096 bytes) UDP-Lite hash table entries: 256 (order: 0, 4096 bytes) NET: Registered protocol family 1 RPC: Registered udp transport module. RPC: Registered tcp transport module. RPC: Registered tcp NFSv4.1 backchannel transport module. JFFS2 version 2.2. (NAND) \0xc2\0xa9 2001-2006 Red Hat, Inc. ROMFS MTD (C) 2007 Red Hat, Inc. msgmni has been set to 118 io scheduler noop registered io scheduler deadline registered io scheduler cfq registered (default) Console: switching to colour frame buffer device 60x53 fb0: s3c2410fb frame buffer device backlight initialized s3c2440-uart.0: ttySAC0 at MMIO 0x50000000 (irq = 70) is a S3C2440 s3c2440-uart.1: ttySAC1 at MMIO 0x50004000 (irq = 73) is a S3C2440 s3c2440-uart.2: ttySAC2 at MMIO 0x50008000 (irq = 76) is a S3C2440 brd: module loaded mini2440_beer# register OK s3c2440_adc# register W1 OK at24 0-0050: 1024 byte 24c08 EEPROM, writable, 16 bytes/write S3C24XX NAND Driver, (c) 2004 Simtec Electronics s3c24xx-nand s3c2440-nand: Tacls=1, 10ns Twrph0=3 30ns, Twrph1=2 20ns s3c24xx-nand s3c2440-nand: NAND soft ECC NAND device: Manufacturer ID: 0xec, Chip ID: 0xda (Samsung NAND 256MiB 3,3V 8-bit) Creating 5 MTD partitions on "nand": 0x000000000000-0x000000080000 : "u-boot" 0x000000080000-0x0000000a0000 : "u-boot-env" 0x0000000a0000-0x0000006a0000 : "kernel" 0x0000006a0000-0x0000046a0000 : "root" 0x0000046a0000-0x000010000000 : "extend" dm9000 Ethernet Driver, V1.31 eth0: dm9000e at c4872300,c4876304 IRQ 51 MAC: 00:01:02:03:04:05 (chip) ohci_hcd: USB 1.1 'Open' Host Controller (OHCI) Driver s3c2410-ohci s3c2410-ohci: S3C24XX OHCI s3c2410-ohci s3c2410-ohci: new USB bus registered, assigned bus number 1 s3c2410-ohci s3c2410-ohci: irq 42, io mem 0x49000000 hub 1-0:1.0: USB hub found hub 1-0:1.0: 2 ports detected usbcore: registered new interface driver libusual s3c2440-usbgadget s3c2440-usbgadget: S3C2440: increasing FIFO to 128 bytes mousedev: PS/2 mouse device common for all mice input: gpio-keys as /devices/platform/gpio-keys/input/input0 input: mini2440_ts as /devices/platform/mini2440_ts/input/input1 mini2440_ts# register OK S3C24XX RTC, (c) 2004,2006 Simtec Electronics s3c-rtc s3c2410-rtc: rtc disabled, re-enabling s3c-rtc s3c2410-rtc: rtc core: registered s3c as rtc0 i2c /dev entries driver S3C2410 Watchdog Timer, (c) 2004 Simtec Electronics s3c2410-wdt s3c2410-wdt: watchdog inactive, reset disabled, irq enabled cpuidle: using governor ladder sdhci: Secure Digital Host Controller Interface driver sdhci: Copyright(c) Pierre Ossman s3c-sdi s3c2440-sdi: powered down. s3c-sdi s3c2440-sdi: mmc0 - using pio, sw SDIO IRQ usbcore: registered new interface driver usbhid usbhid: USB HID core driver ALSA device list: No soundcards found. TCP cubic registered NET: Registered protocol family 17 Registering the dns_resolver key type s3c-rtc s3c2410-rtc: setting system clock to 2000-02-26 23:38:54 UTC (951608334) dm9000 dm9000: eth0: link down IP-Config: Complete: device=eth0, addr=192.168.1.20, mask=255.255.255.0, gw=192.168.1.1, host=192.168.1.20, domain=, nis-domain=(none), bootserver=192.168.1.30, rootserver=192.168.1.30, rootpath= dm9000 dm9000: eth0: link up, 100Mbps, full-duplex, lpa 0x4DE1 VFS: Mounted root (nfs filesystem) on device 0:14. Freeing init memory: 136K Please press Enter to activate this console. Liyong-zou [root@Liyong-zou /]#/home/test_beer please type operation: \0x09type 0 to exit \0x09type 1 to start beer \0x09type 22 to stop beer \0x09type 3 to set prescaler(1~256) \0x09type 4 to set divier(2/4/8/16) \0x09type 5 to set freq(20~20000) \0x09type 6 to set pwm(0~100) \0x09what are you want:1 please type operation: \0x09type 0 to exit \0x09type 1 to start beer \0x09type 22 to stop beer \0x09type 3 to set prescaler(1~256) \0x09type 4 to set divier(2/4/8/16) \0x09type 5 to set freq(20~20000) \0x09type 6 to set pwm(0~100) \0x09what are you want:6 and type the arg:100 please type operation: \0x09type 0 to exit \0x09type 1 to start beer \0x09type 22 to stop beer \0x09type 3 to set prescaler(1~256) \0x09type 4 to set divier(2/4/8/16) \0x09type 5 to set freq(20~20000) \0x09type 6 to set pwm(0~100) \0x09what are you want:6 and type the arg:99 please type operation: \0x09type 0 to exit \0x09type 1 to start beer \0x09type 22 to stop beer \0x09type 3 to set prescaler(1~256) \0x09type 4 to set divier(2/4/8/16) \0x09type 5 to set freq(20~20000) \0x09type 6 to set pwm(0~100) \0x09what are you want:22 please type operation: \0x09type 0 to exit \0x09type 1 to start beer \0x09type 22 to stop beer \0x09type 3 to set prescaler(1~256) \0x09type 4 to set divier(2/4/8/16) \0x09type 5 to set freq(20~20000) \0x09type 6 to set pwm(0~100) \0x09what are you want:1 please type operation: \0x09type 0 to exit \0x09type 1 to start beer \0x09type 22 to stop beer \0x09type 3 to set prescaler(1~256) \0x09type 4 to set divier(2/4/8/16) \0x09type 5 to set freq(20~20000) \0x09type 6 to set pwm(0~100) \0x09what are you want:6 and type the arg:50 please type operation: \0x09type 0 to exit \0x09type 1 to start beer \0x09type 22 to stop beer \0x09type 3 to set prescaler(1~256) \0x09type 4 to set divier(2/4/8/16) \0x09type 5 to set freq(20~20000) \0x09type 6 to set pwm(0~100) \0x09what are you want:0 [root@Liyong-zou /]#

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值