上一节讲述了framebuffer驱动,一句话概述就是:
Linux系统下的显示驱动框架,每个显示屏被抽象为一个帧缓冲区,注册到FrameBuffer模块中,并在/dev/graphics目录下创建对应的fbX设备。
众所周知,Android的各子系统通常不会直接使用内核驱动,而是通过HAL层来间接引用底层架构。显示系统中也是如此--它借助于HAL层来操作帧缓冲区,Android系统在硬件抽象层中提供了一个Gralloc模块,封装了用户层对帧缓冲区的所有操作接口。
用户空间的应用程序在使用帧缓冲区之前,首先要加载Gralloc模块,然后打开帧缓冲设备,获取设备的各种参数并完成 gralloc 模块的初始化。
有了gralloc设备之后,用户空间中的应用程序就可以申请分配一块图形缓冲区,并且将这块图形缓冲区映射到应用程序的地址空间来,以便可以向里面写入要绘制的画面的内容。
最后,用户空间中的应用程序就通过fb设备来将已经准备好了的图形缓冲区渲染到帧缓冲区中去,即将图形缓冲区的内容绘制到显示屏中去。相应地,当用户空间中的应用程序不再需要使用一块图形缓冲区的时候,就可以通过gralloc设备来释放它,并且将它从地址空间中解除映射
gralloc分配framebuffer图形缓冲区
函数gralloc_alloc_framebuffer用来在系统帧缓冲区中分配图形缓冲区,而函数gralloc_alloc_buffer用来在内存中分配图形缓冲区,这里只讨论gralloc_alloc_framebuffer (hardware/libhardware/modules/gralloc/gralloc.cpp)
如上代码核心工作:
gralloc调用gralloc_alloc_framebuffer()分配framebuffer的内存,其核心是对fb设备/dev/graphics/fb或者/dev/fb执行mmap(),映射到用户空间,然后去操作
这里顺便说下mmap的作用:
mmap可以将某个设备或者文件映射到应用程序进程的内存空间中,mmap函数返回值为用户空间映射的这段内存,这样访问这段内存就相当于对设备/文件进行读写,而不用再通过read(),write()了,减少了数据拷贝的次数。
上述代码中的void* vaddr = mmap(0, fbSize, PROT_READ|PROT_WRITE, MAP_SHARED, fd, 0);
作用是将fd所对应的文件或者设备映射到用户进程,返回的用户进程内存起始地址为vaddr,大小为fbSize
参考文章
网友评论