摘自《ARM Linux入门与实践》一书的P281页:
11.2.3 将驱动编译进内核
当在实际项目的量产中,不可能一台台的将一堆驱动一个个的安装,一定要将它们编译进内核。而且当为CRAMFS只读文件系统时,一掉电,刚安装的模块及驱动也就丢了,所以也必须要求编译进内核。
1.在内核配置选项中增加该驱动的选项
#cd /linuette/target/box/kernel
#vi ./drivers/char/Config.in
增加内容:
if [ “$CONFIG_ARCH_S3C2410” = “y” ]; then
tristate ‘S3C2410 LED Driver example’ CONFIG_S3C2410_LED
fi
#make menuconfig
选中“Character devices->S3C2410 LED Driver example”项。
2.在内核的Makefile中增加该驱动的编译内容
#vi ./driver/char/Makefile
增加内容:
obj-$(CONFIG_S3C2410_LED) += leds.o
将led.c复制到kernel/driver/char目录下,然后重新编译更新内核。
3.出现的问题
问题1:make zImage后出现__this_modules无定义的错误
原因:在驱动程序中有下述的定义项
#ifndef MODULE
#define MODULE
#endif
问题2:不能编译进内核,即/proc/devices文件和/dev目录下都没有出leds
原因:在驱动程序中有下述的定义项
#ifndef MODULE
#define MODULE
#endif
问题3:在/dev目录下找不到leds设备文件
解决方法:可以使用设备文件系统devfs。将原驱动程序中的初始化和退出程序修改成如下:
static devfs_handle_t devfs_handle;
static int __init leds_init(void){
int ret;
int i;
ret = register_chrdev(LED_MAJOR,DEVICE_NAME,&leds_fops);
if (ret < 0){
printk(DEVICE_NAME "can't register major number");
return ret;
}
devfs_handle = devfs_register(NULL,DEVICE_NAME,DEVFS_FL_DEFAULT,LED_MAJOR,0,S_IFCHR | S_IRUSR | S_IWUSR,&leds_fops,NULL);
for (i=0;i<4;i++){
set_gpio_ctrl(led_table[i] | GPIO_PULLUP_EN | GPIO_MODE_OUT);
write_gpio_bit(led_table[i],1);
}
printk(DEVICE_NAME "initialized\n");
return 0;
}
static void __exit leds_exit(void){
devfs_unregister(devfs_handle);
unregister_chrdev(LED_MAJOR,DEVICE_NAME);
} |