FrameBuffer之register_framebuffer
来源:互联网 发布:淘宝卖店铺 编辑:程序博客网 时间:2024/06/06 07:02
我们知道在各个平台上注册自己的fb驱动到kernel中都是通过register_framebuffer来实现的,下面来分析register_framebuffer的实现:
/** * register_framebuffer - registers a frame buffer device * @fb_info: frame buffer info structure * * Registers a frame buffer device @fb_info. * * Returns negative errno on error, or zero for success. * */intregister_framebuffer(struct fb_info *fb_info){ int ret; mutex_lock(®istration_lock); ret = do_register_framebuffer(fb_info); mutex_unlock(®istration_lock); return ret;}EXPORT_SYMBOL(register_framebuffer);
这里就是kernl提供给驱动注册的接口,这里的实现还是通过do_register_framebuffer来继续实现的:
static int do_register_framebuffer(struct fb_info *fb_info){ int i, ret; struct fb_event event; struct fb_videomode mode; if (fb_check_foreignness(fb_info)) return -ENOSYS; ret = do_remove_conflicting_framebuffers(fb_info->apertures, fb_info->fix.id, fb_is_primary_device(fb_info)); if (ret) return ret; if (num_registered_fb == FB_MAX) return -ENXIO; num_registered_fb++; for (i = 0 ; i < FB_MAX; i++) if (!registered_fb[i]) break; fb_info->node = i; atomic_set(&fb_info->count, 1); mutex_init(&fb_info->lock); mutex_init(&fb_info->mm_lock); fb_info->dev = device_create(fb_class, fb_info->device, MKDEV(FB_MAJOR, i), NULL, "fb%d", i); if (IS_ERR(fb_info->dev)) { /* Not fatal */ printk(KERN_WARNING "Unable to create device for framebuffer %d; errno = %ld\n", i, PTR_ERR(fb_info->dev)); fb_info->dev = NULL; } else fb_init_device(fb_info); if (fb_info->pixmap.addr == NULL) { fb_info->pixmap.addr = kmalloc(FBPIXMAPSIZE, GFP_KERNEL); if (fb_info->pixmap.addr) { fb_info->pixmap.size = FBPIXMAPSIZE; fb_info->pixmap.buf_align = 1; fb_info->pixmap.scan_align = 1; fb_info->pixmap.access_align = 32; fb_info->pixmap.flags = FB_PIXMAP_DEFAULT; } } fb_info->pixmap.offset = 0; if (!fb_info->pixmap.blit_x) fb_info->pixmap.blit_x = ~(u32)0; if (!fb_info->pixmap.blit_y) fb_info->pixmap.blit_y = ~(u32)0; if (!fb_info->modelist.prev || !fb_info->modelist.next) INIT_LIST_HEAD(&fb_info->modelist); if (fb_info->skip_vt_switch) pm_vt_switch_required(fb_info->dev, false); else pm_vt_switch_required(fb_info->dev, true); fb_var_to_videomode(&mode, &fb_info->var); fb_add_videomode(&mode, &fb_info->modelist); registered_fb[i] = fb_info; event.info = fb_info; if (!lockless_register_fb) console_lock(); if (!lock_fb_info(fb_info)) { if (!lockless_register_fb) console_unlock(); return -ENODEV; } fb_notifier_call_chain(FB_EVENT_FB_REGISTERED, &event); unlock_fb_info(fb_info); if (!lockless_register_fb) console_unlock(); return 0;}
接下来需要好好分析一下这段代码的含义:
1> 根据当前注册的fb_info的apertures属性从FrameBuffer驱动数组registered_fb中查询是否存在冲突
2> 判断已注册的驱动是否超过32个FrameBuffer驱动,如果不超过的话,则增加注册驱动的个数方便后面检查
3> 从数组registered_fb中查找空闲元素,用于存储当前注册的fb_info,然后将找到的位置赋值给fb_info->node
4> 初始化当前注册的fb_info的成员信息
5> 通过device_create接口在/dev目录下创建一个fbx的设备文件,次设备号就是该fb_info在数组registered_fb中的索引
6> 初始化fb_info结构体
7> 将初始化好的fb_info注册到registered_fb数组中
8> 使用Linux事件通知机制发送一个FrameBuffer注册事件FB_EVENT_FB_REGISTERED
总结一下这个过程就是将设备输出化的fb_info保存到registered_fb数组中,所以在注册fb_info的时候,其实就是先要构造一个fb_info然后初始化这个结构体,其实这个结构体就是描述的一个Framebuffer驱动。
阅读全文
0 0
- FrameBuffer之register_framebuffer
- FrameBuffer 之 fb_fix_screeninfo 、fb_var_screeninfo
- framebuffer[转之]
- FrameBuffer 之 fb_fix_screeninfo 、fb_var_screeninfo
- FrameBuffer 之 fb_fix_screeninfo 、fb_var_screeninfo
- FrameBuffer 之 fb_fix_screeninfo 、fb_var_screeninfo
- FrameBuffer系列 之 介绍
- framebuffer之s3cfb_probe分析
- FrameBuffer系列 之 简单编程
- FrameBuffer系列 之 显示图片
- FrameBuffer系列 之 一点资源
- (转)FrameBuffer 之 fb_fix_screeninfo 、fb_var_screeninfo
- Linux设备驱动之Framebuffer
- Linux之Framebuffer学习总结
- FrameBuffer
- FrameBuffer
- FrameBuffer
- Framebuffer
- Struts2中获得Request,Response的几种方法
- 常用shell(1):shell获取系统当前时间戳
- 【寒江雪】C++内存对齐原则
- POJ1988 Cube Stacking(并查集的应用)
- Retrofit 中设置 OkHttp 拦截器,保存和添加 Cookie
- FrameBuffer之register_framebuffer
- COJ1978-LXX的图论题
- C++/CLI 窗体程序通过空间的name操纵控件
- spring AOP
- Codeforces 839C Journey(dfs+概率)
- Hadoop系列之初识MapReduce(1)
- 徒手撸个http 服务器(二) ----epoll系列函数
- leetcode[Minimum Absolute Difference in BST]//待整理多种解法
- 一个诡异的Java问题