编写基于ARM的uClinux下自设备驱动

定义:
HOST PC:目标机,即在它上面编写、生成驱动程序,一般用PC。我在目标机上装的是Fedora 3操作系统。
使用硬件:CPU: S3C44B0X01(ARM7)
一、需要的软件
1.1:uClinx源码包。如uClinux-040408-hzh.tar.bz2。例如解压缩到/home/uClinux-040408目录,那它的一级目录下应该有linux-2.4.x源码树目录(具体的可能有点不一样)。
1.2: 针对目标板的ARM交叉编译工具。如arm-elf-tools-20030314.sh。在命令行下:执行sh arm-elf-tools-20030314.sh后,的HOST PC上会多出一个/usr/local/bin目录,当中会有arm-elf-gcc(在种样条件下,具体名称的前缀——arm-elf-,会有不一样, 为叙说方便,以下就以arm-elf-为前缀)等可执行文件。相应的,/usr/local/bin也被自动添加到环境变量PATH中。
二、编写驱动程序
/*                                                    
 * $ hello.c $
*/                                                   
#include <linux/config.h>
#include <linux/version.h>
#include <linux/module.h>
#include <linux/init.h>
#include <linux/fs.h>
                                                         
static int __init hello_init_module(void)
{ printk("<1>Hello, world/n"); return 0; }
static void __exit hello_cleanup_module(void)
{ printk("<1>Goodbye cruel world/n"); }
module_init(hello_init_module);
module_exit(hello_cleanup_module);
三、编译、链接驱动程序
这当中需注意几点:
3.1:编译、链接使用的实用程序。要用/usr/local/bin目录下的以arm-elf-为前缀的实用程序。因为/usr/local/bin目录已被放PATH环境变量,不必为这几个应用程序专门指定目录。
3.2:编译、链几个相对重要的选项:
3.2.1:-D__KERNEL__:这是一个内核模块。必选
3.2.2:-DMODULE:如果编译出的模块要支持可加载功能,即支持insmod和rmmod,要选。如果你是准备把模块编译进zImage的,不必选。
3.2.3:-D__linux__:功能我不太清楚,但必选,否则会出现类似于以下的报错:
In file included from /home/uClinux-040408/linux-2.4.x/include/linux/coda_fs_i.h:14,
                 from /home/uClinux-040408/linux-2.4.x/include/linux/fs.h:310,
                 from ov511.c:42:
/home/uClinux-040408/linux-2.4.x/include/linux/coda.h:259: parse error before `u_quad_t'
/home/uClinux-040408/linux-2.4.x/include/linux/coda.h:259: warning: no semicolon at end of struct or union
/home/uClinux-040408/linux-2.4.x/include/linux/coda.h:267: parse error before `va_bytes'
/home/uClinux-040408/linux-2.4.x/include/linux/coda.h:267: warning: type defaults to `int' in declaration of `va_bytes'
/home/uClinux-040408/linux-2.4.x/include/linux/coda.h:267: warning: data definition has no type or storage class
/home/uClinux-040408/linux-2.4.x/include/linux/coda.h:268: parse error before `va_filerev'
/home/uClinux-040408/linux-2.4.x/include/linux/coda.h:268: warning: type defaults to `int' in declaration of `va_filerev'
/home/uClinux-040408/linux-2.4.x/include/linux/coda.h:268: warning: data definition has no type or storage class
/home/uClinux-040408/linux-2.4.x/include/linux/coda.h:435: field `attr' has incomplete type
/home/uClinux-040408/linux-2.4.x/include/linux/coda.h:443: field `attr' has incomplete type
/home/uClinux-040408/linux-2.4.x/include/linux/coda.h:485: field `attr' has incomplete type
/home/uClinux-040408/linux-2.4.x/include/linux/coda.h:494: field `attr' has incomplete type
/home/uClinux-040408/linux-2.4.x/include/linux/coda.h:539: field `attr' has incomplete type
/home/uClinux-040408/linux-2.4.x/include/linux/coda.h:546: field `attr' has incomplete type
/home/uClinux-040408/linux-2.4.x/include/linux/coda.h:566: field `attr' has incomplete type
make: *** [all] Error 1
-DEXPORT_SYMTAB:定义输出符号,如果在源代码中有类似于EXPORT_SYMBOL(ov511_register_decomp_module)的代码,则必选;否则可以忽略。
3.2.4:-I/home/uClinux-040408/linux-2.4.x/include:设定搜索路径。必选。
3.2.5:-fno-builtin:告诉gcc不要使用内建的一些函数,像memcpy,如果该选项不选,会出类似于以下的警告:
In file included from /home/uClinux-040408/linux-2.4.x/include/linux/string.h:19,
                 from /home/uClinux-040408/linux-2.4.x/include/linux/fs.h:23,
                 from ov511.c:42:
/home/uClinux-040408/linux-2.4.x/include/asm/string.h:16: warning: conflicting types for built-in function `memcpy'
/home/uClinux-040408/linux-2.4.x/include/asm/string.h:26: warning: conflicting types for built-in function `memset'
In file included from /home/uClinux-040408/linux-2.4.x/include/linux/fs.h:23,
                 from ov511.c:42:
/home/uClinux-040408/linux-2.4.x/include/linux/string.h:79: warning: conflicting types for built-in function `memcmp'
-------------这结果,是由于gcc内建函数,以上就是memcpy和memset,和string.h中定的函数原型不一致而造成
3.3:一个命令实例:
arm-elf-gcc -D__KERNEL__ -DMODULE -I/home/uClinux-040408/linux-2.4.x/include -Wall  -O2 -nostdinc -iwithprefix include -fno-builtin -D__linux__  -DNO_MM -DEXPORT_SYMTAB -c hello.c
3.3.1:相应的Makefile文件:
#
# makefile for module
#
PRE = arm-elf-
CC = $(PRE)gcc
LD = $(PRE)gcc
AR = $(PRE)ar
# CFLAGS = -I/usr/src/linux/include -Wall -O2 -g -mcpu=i586
KERNELDIR = /home/uClinux-040408/linux-2.4.x
#KERNELDIR = /usr/local/arm-elf
INCLUDEDIR = $(KERNELDIR)/include
CFLAGS += -D__KERNEL__
CFLAGS += -DMODULE
CFLAGS += -I$(INCLUDEDIR)
CFLAGS += -Wall
CFLAGS += -O2
CFLAGS += -nostdinc
CFLAGS += -iwithprefix include
CFLAGS += -fno-builtin
CFLAGS += -D__linux__
CFLAGS += -DNO_MM
all :
 $(CC) $(CFLAGS) -c hello.c
clean:
 rm -rf *.o *~ core .depend .*.cmd *.ko *.mod.c .tmp_versions
四、加载驱动程序
4.1:因为ARM板上的存贮载体不同于PC,而此时你必须把编译出的模块,例如上面的hello.o,加入到内核 中,就必须建立可写的系统。我对linux系统并不是很懂,一些介绍的方法用来用去还是不行,以下就说我测试下来能用的,当然我不敢肯定这方法别的板上能 不能用。在超级终端中输入:
# cd /dev
# mknod mtdblock1 b 30 1
# mount -t yaffs /dev/mtdblock1 /mnt
接下就可以在/mnt目录下进行读写了。
4.2:下载驱动文件hello.o到ARM板上。我用是通过网络的反线方式,然后用ftp;不知道怎么通过串口下载文件。
4.3:执行命令insmod hello.o加载驱动模块到内核。
五、卸载驱动程序
5.1:执行命令rmmod hello.o,丛内核中卸载驱动。
  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值