||
本文不详细分析lcd的每行代码 ,只是做简单的构架分析, 要详细的分析可以参考http://www.cnitblog.com/luofuchong/archive/2007/10/30/35570.html,里面虽然是多2410的分析,但都大同小异。
LCD驱动是用了device 和driver架构,首先看arch/arm/mach-s3c6410/mach-smdk6410.c文件,在353行有这样一个数组
static struct platform_device *smdk6410_devices[] __initdata = {
……………………
&s3c_device_lcd,
……………………
}
我们在进里面了解详情,在arch/arm/palt-s3c64xx/devs.c文件里有s3c_device_lcd变量的定义
static struct resource s3c_lcd_resource[] = {
[0] = {
.start = S3C64XX_PA_LCD, //lcd寄存器的起始地址
.end = S3C64XX_PA_LCD + SZ_1M - 1, //lcd寄存器的结束地址,
.flags = IORESOURCE_MEM,
},
[1] = {
.start = IRQ_LCD_VSYNC, //lcd中断寄存器起始地址,在s3cfb_probe用
.end = IRQ_LCD_SYSTEM,
.flags = IORESOURCE_IRQ,
}
};
static u64 s3c_device_lcd_dmamask = 0xffffffffUL;
struct platform_device s3c_device_lcd = {
.name = "s3c-lcd", //这个会和driver中的name一样,driver
//根据这个进行匹配
.id = -1,
.num_resources = ARRAY_SIZE(s3c_lcd_resource),
.resource = s3c_lcd_resource,
.dev = {
.dma_mask = &s3c_device_lcd_dmamask,
.coherent_dma_mask = 0xffffffffUL
}
};
在arch/arm/mach-s3c6410/mach-smdk6410.c文件的
static void __init smdk6410_machine_init(void)函数中有这么一句话
platform_add_devices(smdk6410_devices, ARRAY_SIZE(smdk6410_devices));
这个就是对device设备进行注册,在注册driver驱动时,会根据name找到相应的device进行匹配,然后会调用probe。
下面分析driver,在drivers/video/samsung/s3cfb.c文件的最下面有这样的一段代码
static struct platform_driver s3cfb_driver = {
.probe = s3cfb_probe, //匹配的话会调用这个函数
.remove = s3cfb_remove,
.suspend = s3cfb_suspend,
.resume = s3cfb_resume,
.driver = {
.name = "s3c-lcd", //上面说的,内核会根据这个来找到相应的device
.owner = THIS_MODULE,
},
};
int __devinit s3cfb_init(void)
{
return platform_driver_register(&s3cfb_driver);//进行drive注册
}
匹配后会掉用s3cfb_probe();
这个函数里面对fbinfo进行初始化,对相关寄存器进行初始化,在6410lcd驱动中,主要要修改的几个文件是:drivers/video/samsung目录下的s3cfb.c,假设你在配置的时候即用make menuconfig命令,在里面选择的是480WV,他对应的文件时s3cfb_lte480wv.c,s3cfb_lte480wv.c是和屏参数相关的文件。还有个要改的文件是s3cfb_fimd4x.c,这个文件主要是涉及寄存器的一些参数的配置。
主要几个重点:对构架的分析,理清楚各个文件的关系。s3cfb.c中的s3cfb_probe主要是在根据s3cfb_fimd4x.c和s3cfb_lte480wv.c文件来初始fbinfo,并且写相关LCD寄存器。s3cfb_lte480wv.c主要是记录屏的参数,在这里进行修改来满足不同的lcd屏。s3cfb_fimd4x.c是对寄存器的值进行初始化,比如各个窗口的显示模式、颜色表寄存器的模式、各个窗口的控制寄存器,此文件还包含6410对于lcd的特殊功能,用ioctl来进行实现的。fbmem.c这个是fb字符设备驱动,每个窗口都是一个字符设备,在s3cfb_probe中通过调用register_buffer进行注册,注意,里面有一个fb_notifier_call_chain,他最终会调用drivers/video/console/fbcon.c中的fbcon_init,里面会有对logo的调用;fbmem.c文件里还有通用的ioctl功能调用,适合所有带lcd控制器的处理器,这个文件时通用的,每个处理器的fbmem都是一样的,做成了和硬件无关。
lcd驱动简单构架图