了解framebuffer driver,skeletonfb.c有著一個framebuffer基本的架構,值得參考。筆記如下:
顯卡可支援多螢幕,因此可能有多個display。而每個display可有自己的data,因此每個display都是一個framebuffer device,意即各有其fb_info。fb_info中的par是硬體相關的state,硬體只有一份,因此這些state對每個display來說是共享的。任一個display做了改變 (如resolution,var->xres和var->yres),其他的display都可得知此狀況。以下是framebuffer driver需要或不需要實作的function:
int xxxfb_init(void):
在linux kernel 2.6後引入platform的概念,讓driver更加容易實作。這個function的功能是向platform註冊這支driver,即執行platform_driver_register()。如int __init s3c2410fb_init(void)
static int xxxfb_open(struct fb_info *info, int user) / static int xxxfb_release(struct fb_info *info, int user):
Optional。在framebuffer device open/close時執行,通常不需實作。
static int xxxfb_check_var(struct fb_var_screeninfo *var, struct fb_info *info):
Optional。檢查硬體是否支援傳入的struct var所指定的狀態。這個function並不改變hardware state,意即fb_info和par不變。值的部份,會做round up。爆掉的話就發-EINVAL。此處是driver註冊後,調整var的唯一地方。意即在其他的function改變var的內容是錯的。
static int xxxfb_set_par(struct fb_info *info):
Optional。利用fb_info裡的fb_var_screeninfo,可改變frmebuffer的resolution,pclk等hardware status。此 function將改變par和fb_fix_screeninfo。var是不變的,而是利用其狀態來做硬體設定。在呼叫xxxfb_set_par前應呼叫xxxfb_check_var以確保參數正確。如果resolution不能改,那這個function就不需實作。然而,還是可以透過這個function來讓硬體回到working state,也是一種recover的機制。
static int xxxfb_pan_display(struct fb_var_screeninfo *var, struct fb_info *info)
Not required。主要是平移的功能。不是很確定,但看起來像vitual resolution。virtual大於visible,因此就有xoffset和yoffset。根據傳入的var裡所指定的xoffset和yoffset來決定display要平移多少。
static int xxxfb_blank(int blank_mode, struct fb_info *info):
Not required。清空display。
/* ------------ Accelerated Functions --------------------- */
以下為加速的function,會depend on硬體有無此功能。不然則使用generic unaccelerated function。
void xxxfb_fillrect(struct fb_info *p, const struct fb_fillrect *region):
在screent上畫一矩形。
void xxxfb_copyarea(struct fb_info *p, const struct fb_copyarea *area):
Required。copy矩形從一個區域到另一個。
void xxxfb_imageblit(struct fb_info *p, const struct fb_image *image):
Required。複製image,從memory到screen。
int xxxfb_cursor(struct fb_info *info, struct fb_cursor *cursor)"
Optional。如果有hardware cursor,就不需要。
void xxxfb_rotate(struct fb_info *info, int angle):
Not required。如果硬體提供此功能,可在此hook。
int xxxfb_sync(struct fb_info *info):
Not required。使用硬體加速,可能需要sync。
/*
* Frame buffer operations
*/
static struct fb_ops xxxfb_ops = {
.owner = THIS_MODULE,
.fb_open = xxxfb_open,
.fb_read = xxxfb_read,
.fb_write = xxxfb_write,
.fb_release = xxxfb_release,
.fb_check_var = xxxfb_check_var,
.fb_set_par = xxxfb_set_par,
.fb_setcolreg = xxxfb_setcolreg,
.fb_blank = xxxfb_blank,
.fb_pan_display = xxxfb_pan_display,
.fb_fillrect = xxxfb_fillrect, /* Needed !!! */
.fb_copyarea = xxxfb_copyarea, /* Needed !!! */
.fb_imageblit = xxxfb_imageblit, /* Needed !!! */
.fb_cursor = xxxfb_cursor, /* Optional !!! */
.fb_rotate = xxxfb_rotate,
.fb_sync = xxxfb_sync,
.fb_ioctl = xxxfb_ioctl,
.fb_mmap = xxxfb_mmap,
};
static int __devinit xxxfb_probe(struct pci_dev *dev, const struct pci_device_id *ent):
這是主要的功能了,包括:
設定fb_info,其中包括註冊所需要的fb_ops
設定fb_var_screeninfo,這是console要用的
向系統要求memory address space: request_mem_region()
最後,register_framebuffer():向fbmem.c層註冊。
留言列表