网上关于cubiboard的资料不是很多,本文简要分析其显示初始化过程,如有问题请指出,共同学习。
整个显示分为几个模块,包括disp、vga、hdmi、lcd,这些模块都是以字符设备驱动的形式体现,最终
会在/dev/目录下生成对应节点。
整个流程的开始是在insmod lcd.ko 时触发的,在drivers\video\sun7i\lcd\dev_lcd.c中
int __init lcd_module_init(void)
{
alloc_chrdev_region(&devid, 0, 1, "lcd");
...
device_create(lcd_class, NULL, devid, NULL, "lcd");
lcd_init();
return ret;
}
这里注册设备节点,然后调用了lcd_init(),其代码如下
int lcd_init(void)
{
DRV_DISP_Init();
Fb_Init(0);
return 0;
}
DRV_DISP_Init()函数会初始化一些全局变量以及一些硬件相关初始化。
Fb _Init(0)则是另一个文件中的接口,其主要工作就是完成framebuffer注册,下面看其具体实现过程。
在drivers\video\sun7i\disp\dev_fb.c中
__s32 Fb_Init(__u32 from)
{
if(from == 0)//call from lcd driver
{
for(i=0; i<8; i++)
{
g_fbi.fbinfo[i] = framebuffer_alloc(0, g_fbi.dev);
......
register_framebuffer(g_fbi.fbinfo[i]); //注册framebuffer,生成对应fb%d
}
}
//打开对应显示设备
......
fb_num = (g_fbi.disp_init.disp_mode==DISP_INIT_MODE_TWO_DIFF_SCREEN)?2:1;
for(i = 0; i<fb_num; i++)
{
Display_Fb_Request(i, &fb_para);
...
}
}
在Display_Fb_Request中申请显示内存,并把它设置到显示寄存器中
__s32 Display_Fb_Request(__u32 fb_id, __disp_fb_create_para_t *fb_para)
{
...
Fb_map_video_memory(info);//申请内存,并把地址保存起来,后面会传给mali驱动
...
var_to_disp_fb(&(layer_para.fb), &(info->var), &(info->fix));
layer_para.fb.addr[0] = (__u32)info->fix.smem_start;
BSP_disp_layer_set_para(sel, hdl, &layer_para);//根据提供的地址,设置显示寄存器中framebuffer地址,以后往这个地址写东西就相当于写到屏幕上
...
}
到这里已经可以看到如何把内存中的东西对应到屏幕上的,开机logo就是通过打开/dev/graphic/fb0来显示的。
粗浅分析,如有问题请见谅。