Linux 2 6内核移植及驱动开发总结

发布 2019-06-16 00:22:35 阅读 6099

文档编号:wf

文档版本号:v1.0

linux2.6内核移植以及驱动开发。

总结文档。编制日期: 2006.10.31

审核日期。批准日期。

目录 21.引言 3

驱动 42.1cs8900a简介 4

2.2 cs8900a驱动移植 6

驱动 73.1 tl16c554驱动简介 7

3.2 tl16c554的中断共享 9

块设备驱动及s3c2410 sdi 驱动 12

4.1 linux2.6 下的sd/mmc驱动 13

4.2 s3c2410 sdi 控制器驱动 17

总线驱动 18

5.1 usb的拓扑结构 19

5.2usb主机驱动程序结构 20

5.3 usb大存储设备 22

buffer与s3c2410 lcd控制器驱动 25

6.1帧缓冲(frame buffer)设备驱动概述 25

6.2 s3c2410 lcd控制器驱动 29

7. i2c总线驱动 36

7.1 linux i2c总线驱动核心层概述 36

7.2编写i2c设备驱动程序模块的方法 41

8. nand flash 与yaffs文件系统 45

8.1 nand flash 45

8.2 linux mtd子系统 46

8.3 yaffs文件系统介绍 48

8.4 yaffs2 文件系统在linux2.6.18-rc2上的移植 52

文件系统 56

9.1设备驱动模型(device driver model)概述 56

9.2 udev 的配置和使用 62

2.6字符设备驱动程序开发 65

10.1 并发和竞争 65

10.2 使用udev自动创建字符设备的节点 67

11.小结 68

经过内核开发小组几个月的努力,linux2.6内核在s3c2410x系统平台上的移植工作终于基本完成。同时,根据linux2.

6新的特性,2.4下各驱动模块也陆续被移植或重新编写。随着内核以及驱动开发工作的进一步深入开展,深深地体会到规范文档的重要意义,因此内核开发小组组织编写了本文档,旨在总结过去工作中的经验和收获,同时期望对今后的工作起到积极的指导作用。

无论是对于企业服务器还是对于嵌入式系统,linux 2.6 都是一个巨大的进步。对高端的机器来说,新特性针对的是性能改进、可扩展性、吞吐率,以及对 smp 机器 numa 的支持。

对于嵌入式领域,添加了新的体系结构和处理器类型(包括对那些没有硬件控制的内存管理方案的 mmu-less 系统的支持),以及采用可抢占内核、更加有效的调度算法以及同步性的提高。对于linux2.6内核新特性的描述和分析,已经有很多**或文档见诸于各专业期刊或网络,因此本文档并不着重于2.

6内核性能的分析,而是把重点放在与设备驱动相关的内核子系统的描述上,分析了实际应用中常见设备的工作原理以及其驱动程序的实现。由于篇幅有限,文中并不会(也不需要)对各驱动模块作逐行的源码分析,而是选取关键部分加以重点讨论,旨在理解并学习其先进的设计思想和理念。

本文档基本覆盖目前各终端上使用的设备资源,主要讨论了cs8900a以太网控制器、tl16c554、sd/mmc块设备以及s3c2410 sdi控制器、usb总线和i2c总线、frame buffer和lcd控制器以及nand flash和yaffs文件系统,同时还讨论了udev文件系统以及linux2.6 下字符设备驱动程序开发的注意事项。

若不加特殊说明,文中所指的linux2.6内核版本为linux2.6.

18-rc2,linux2.4内核版本为linux2.4.

18。文档中所涉及的所有驱动模块都已经在wfet-2000s(mainboard v1.1)型终端下测试通过,对于其他类型或版本的终端也应该具有普适性。

cs8900a以太网控制器是一款功能强大、全双工的以太网接口芯片。cs8900a支持两种访问模式,即i/o模式和memory模式。在i/o模式下基地址是可配置的,默认为0300h。

使用memory模式时,占用4k字节的系统地址空间。i/o模式是cs8900a默认的工作模式,在linux2.6中,cs8900a驱动程序只支持i/o模式。

cs8900a内部寄存器和buffer的访问基于一种独特的、高效的架构,称为packetpage。在i/o模式下访问cs8900a内部寄存器时,程序首先要设置packetpage指针,即首先把目标寄存器的地址写入packetpage地址端口(pointer port,i/o base + 0x000ah),则目标寄存器将被映射到packetpage数据端口(data port,i/o base + 0x000ch)。例如,驱动程序可以使用如下的**访问内部寄存器:

#define pp_address 0x0a /*packetpage pointer port (section 4.10.10) *

#define pp_data0x0c /*packetpage data port (section 4.10.10) *

static inline u16 cs8900_read (struct net_device *dev,u16 reg)

outw (reg,dev->base_addr + pp_address);

return (inw (dev->base_addr + pp_data));

假设要读取rxstatus寄存器,则可以使用如下的**:

status = cs8900_read (dev,pp_rxstatus);

在linux 2.6网络驱动的架构下,cs8900a以太网控制器的驱动主要实现open(),stop()以及接收和发送函数,并向网络核心层注册这些函数,列出如下:

dev->opencs8900_start;

dev->stopcs8900_stop;

dev->hard_start_xmit = cs8900_send_start;

dev->get_statscs8900_get_stats;

dev->set_multicast_list = cs8900_set_receive_mode;

dev->tx_timeoutcs8900_transmit_timeout;

函数cs8900_start()设置cs8900a的几个控制寄存器,如接收配置寄存器rxcfg,接受控制寄存器rxctl,发送配置寄存器txcfg等等,同时设置cs8900a的所对应的cpu中断引脚为上升沿触发模式,并向内核注册中断服务子程序cs8900_interrupt。函数列出如下:

static int cs8900_start (struct net_device *dev)

int result;

#if defined(config_arch_smdk2410)

set_irq_type(dev->irq, irqt_rising);

//s3c_irqext_type(dev->irq, irqt_rising);

/* enable the ethernet controller */

cs8900_set (dev,pp_rxcfg,rxokie | buffercrc | crcerrorie | runtie | extradataie);