Android帧缓冲区(Frame Buffer)硬件抽象层(HAL)模块Gralloc的实现原理分析(5)

简介:
  3. fb设备的打开过程
        在Gralloc模块中,fb设备的ID值定义为GRALLOC_HARDWARE_FB0。GRALLOC_HARDWARE_FB0是一个宏,定义在文件hardware/libhardware/include/hardware/gralloc.h中, 如下所示:
  1. #define GRALLOC_HARDWARE_FB0 "fb0"  
 
       fb设备使用结构体framebuffer_device_t 来描述。结构体framebuffer_device_t是用来描述系统帧缓冲区的信息,它定义在文件hardware/libhardware/include/hardware/gralloc.h中, 如下所示:
  1. typedef struct framebuffer_device_t {  
  2.     struct hw_device_t common;  
  3.   
  4.     /* flags describing some attributes of the framebuffer */  
  5.     const uint32_t  flags;  
  6.   
  7.     /* dimensions of the framebuffer in pixels */  
  8.     const uint32_t  width;  
  9.     const uint32_t  height;  
  10.   
  11.     /* frambuffer stride in pixels */  
  12.     const int       stride;  
  13.   
  14.     /* framebuffer pixel format */  
  15.     const int       format;  
  16.   
  17.     /* resolution of the framebuffer's display panel in pixel per inch*/  
  18.     const float     xdpi;  
  19.     const float     ydpi;  
  20.   
  21.     /* framebuffer's display panel refresh rate in frames per second */  
  22.     const float     fps;  
  23.   
  24.     /* min swap interval supported by this framebuffer */  
  25.     const int       minSwapInterval;  
  26.   
  27.     /* max swap interval supported by this framebuffer */  
  28.     const int       maxSwapInterval;  
  29.   
  30.     int reserved[8];  
  31.   
  32.     int (*setSwapInterval)(struct framebuffer_device_t* window,  
  33.             int interval);  
  34.   
  35.     int (*setUpdateRect)(struct framebuffer_device_t* window,  
  36.             int left, int top, int width, int height);  
  37.   
  38.     int (*post)(struct framebuffer_device_t* dev, buffer_handle_t buffer);  
  39.   
  40.     int (*compositionComplete)(struct framebuffer_device_t* dev);  
  41.   
  42.     void* reserved_proc[8];  
  43.   
  44. } framebuffer_device_t;  

        成员变量flags用来记录系统帧缓冲区的标志,目前没有使用这成员变量,它的值被设置为0。
        成员变量width和height分别用来描述设备显示屏的宽度和高度,它们是以像素为单位的。
        成员变量stride用来描述设备显示屏的一行有多少个像素点。
        成员变量format用来描述系统帧缓冲区的像素格式,支持的像素格式主要有HAL_PIXEL_FORMAT_RGBX_8888和HAL_PIXEL_FORMAT_RGB_565两种。HAL_PIXEL_FORMAT_RGBX_8888表示一个像素使用32位来描述,R、G和B分别占8位,另外8位未使用。HAL_PIXEL_FORMAT_RGB_565表示一个像素使用16位来描述,R、G和B分别占5、6和5位。
        成员变量xdpi和ydpi分别用来描述设备显示屏在宽度和高度上的密度,即每英寸有多少个像素点。
        成员变量fps用来描述设备显示屏的刷新频率,它的单位是帧每秒。
        成员变量minSwapInterval和maxSwapInterval用来描述帧缓冲区交换前后两个图形缓冲区的最小和最大时间间隔。
        成员变量reserved是保留给将来使用的。
        成员函数setSwapInterval用来设置帧缓冲区交换前后两个图形缓冲区的最小和最大时间间隔。
        成员函数setUpdateRect用来设置帧缓冲区的更新区域。
        成员函数post用来将图形缓冲区buffer的内容渲染到帧缓冲区中去,即显示在设备的显示屏中去。
        成员函数compositionComplete用来通知fb设备device,图形缓冲区的组合工作已经完成,目前没有使用这个成员函数。
        成员变量reserved是一个函数指针数组,它们是保留给将来使用的。
        在结构体framebuffer_device_t的一系列成员函数中,post是最重要的一个成员函数,用户空间的应用程序通过调用这个成员函数就可以在设备的显示屏中渲染指定的画面,后面我们将详细这个函数的实现。
        Gralloc模块在在文件hardware/libhardware/include/hardware/gralloc.h中定义了一个帮助函数framebuffer_open,用来打开fb设备,如下所示:
  1. static inline int framebuffer_open(const struct hw_module_t* module,  
  2.         struct framebuffer_device_t** device) {  
  3.     return module->methods->open(module,  
  4.             GRALLOC_HARDWARE_FB0, (struct hw_device_t**)device);  
  5. }  
       参数module指向的是一个用来描述Gralloc模块的hw_module_t结构体,前面提到,它的成员变量methods所指向的一个hw_module_methods_t结构体的成员函数open指向了Gralloc模块中的函数gralloc_device_open,这个函数打开fb设备的代码段如下所示:
  1. int gralloc_device_open(const hw_module_t* module, const char* name,  
  2.         hw_device_t** device)  
  3. {  
  4.     int status = -EINVAL;  
  5.     if (!strcmp(name, GRALLOC_HARDWARE_GPU0)) {  
  6.         ......  
  7.     } else {  
  8.         status = fb_device_open(module, name, device);  
  9.     }  
  10.     return status;  
  11. }  
       参数name的值等于GRALLOC_HARDWARE_FB0,因此,函数gralloc_device_open接下来会调用另外一个函数fb_device_open来执行打开fb设备的操作。
 
       函数fb_device_open定义在文件hardware/libhardware/modules/gralloc/framebuffer.cpp中,如下所示:
  1. struct fb_context_t {  
  2.     framebuffer_device_t  device;  
  3. };  
  4.   
  5. ......  
  6.   
  7. int fb_device_open(hw_module_t const* module, const char* name,  
  8.         hw_device_t** device)  
  9. {  
  10.     int status = -EINVAL;  
  11.     if (!strcmp(name, GRALLOC_HARDWARE_FB0)) {  
  12.         alloc_device_t* gralloc_device;  
  13.         status = gralloc_open(module, &gralloc_device);  
  14.         if (status < 0)  
  15.             return status;  
  16.   
  17.         /* initialize our state here */  
  18.         fb_context_t *dev = (fb_context_t*)malloc(sizeof(*dev));  
  19.         memset(dev, 0, sizeof(*dev));  
  20.   
  21.         /* initialize the procs */  
  22.         dev->device.common.tag = HARDWARE_DEVICE_TAG;  
  23.         dev->device.common.version = 0;  
  24.         dev->device.common.module = const_cast<hw_module_t*>(module);  
  25.         dev->device.common.close = fb_close;  
  26.         dev->device.setSwapInterval = fb_setSwapInterval;  
  27.         dev->device.post            = fb_post;  
  28.         dev->device.setUpdateRect = 0;  
  29.   
  30.         private_module_t* m = (private_module_t*)module;  
  31.         status = mapFrameBuffer(m);  
  32.         if (status >= 0) {  
  33.             int stride = m->finfo.line_length / (m->info.bits_per_pixel >> 3);  
  34.             int format = (m->info.bits_per_pixel == 32)  
  35.                          ? HAL_PIXEL_FORMAT_RGBX_8888  
  36.                          : HAL_PIXEL_FORMAT_RGB_565;  
  37. #ifdef NO_32BPP  
  38.             format = HAL_PIXEL_FORMAT_RGB_565;  
  39. #endif  
  40.             const_cast<uint32_t&>(dev->device.flags) = 0;  
  41.             const_cast<uint32_t&>(dev->device.width) = m->info.xres;  
  42.             const_cast<uint32_t&>(dev->device.height) = m->info.yres;  
  43.             const_cast<int&>(dev->device.stride) = stride;  
  44.             const_cast<int&>(dev->device.format) = format;  
  45.             const_cast<float&>(dev->device.xdpi) = m->xdpi;  
  46.             const_cast<float&>(dev->device.ydpi) = m->ydpi;  
  47.             const_cast<float&>(dev->device.fps) = m->fps;  
  48.             const_cast<int&>(dev->device.minSwapInterval) = 1;  
  49.             const_cast<int&>(dev->device.maxSwapInterval) = 1;  
  50.             *device = &dev->device.common;  
  51.         }  
  52.     }  
  53.     return status;  
  54. }  
 
        这个函数主要是用来创建一个fb_context_t结构体,并且对它的成员变量device进行初始化。结构体fb_context_t的成员变量device的类型为framebuffer_device_t,前面提到,它是用来描述fb设备的。fb设备主要是用来渲染图形缓冲区的,这是通过调用它的成员函数post来实现的。从这里可以看出,函数fb_device_open所打开的fb设备的成员函数post被设置为Gralloc模块中的函数fb_post,后面我们再详细分析它的实现。




本文转自 Luoshengyang 51CTO博客,原文链接:http://blog.51cto.com/shyluo/967075,如需转载请自行联系原作者
目录
相关文章
|
24天前
|
安全 Android开发 数据安全/隐私保护
深入探讨iOS与Android系统安全性对比分析
在移动操作系统领域,iOS和Android无疑是两大巨头。本文从技术角度出发,对这两个系统的架构、安全机制以及用户隐私保护等方面进行了详细的比较分析。通过深入探讨,我们旨在揭示两个系统在安全性方面的差异,并为用户提供一些实用的安全建议。
|
2月前
|
缓存 Java Shell
Android 系统缓存扫描与清理方法分析
Android 系统缓存从原理探索到实现。
60 15
Android 系统缓存扫描与清理方法分析
|
2月前
|
存储 Linux Android开发
Android底层:通熟易懂分析binder:1.binder准备工作
本文详细介绍了Android Binder机制的准备工作,包括打开Binder驱动、内存映射(mmap)、启动Binder主线程等内容。通过分析系统调用和进程与驱动层的通信,解释了Binder如何实现进程间通信。文章还探讨了Binder主线程的启动流程及其在进程通信中的作用,最后总结了Binder准备工作的调用时机和重要性。
Android底层:通熟易懂分析binder:1.binder准备工作
|
3月前
|
安全 Android开发 数据安全/隐私保护
探索安卓与iOS的安全性差异:技术深度分析与实践建议
本文旨在深入探讨并比较Android和iOS两大移动操作系统在安全性方面的不同之处。通过详细的技术分析,揭示两者在架构设计、权限管理、应用生态及更新机制等方面的安全特性。同时,针对这些差异提出针对性的实践建议,旨在为开发者和用户提供增强移动设备安全性的参考。
143 3
|
2月前
|
开发工具 Android开发 Swift
安卓与iOS开发环境的差异性分析
【10月更文挑战第8天】 本文旨在探讨Android和iOS两大移动操作系统在开发环境上的不同,包括开发语言、工具、平台特性等方面。通过对这些差异性的分析,帮助开发者更好地理解两大平台,以便在项目开发中做出更合适的技术选择。
|
开发工具 Android开发
Android 7.1 使用mmm编译模块失败
Android 7.1 使用mmm编译模块失败
301 0
|
Android开发
Android不编译某个模块
Android 5.1 源码,编译相关的文件一般在build目录下build/target/product 放了很多mk文件;一般不同的产品会有不同的目录 假设我不想编译OpenWnn,在build目录下grep一下“OpenWnn”target/product/full_base.
1432 0
|
10天前
|
开发框架 前端开发 Android开发
安卓与iOS开发中的跨平台策略
在移动应用开发的战场上,安卓和iOS两大阵营各据一方。随着技术的演进,跨平台开发框架成为开发者的新宠,旨在实现一次编码、多平台部署的梦想。本文将探讨跨平台开发的优势与挑战,并分享实用的开发技巧,帮助开发者在安卓和iOS的世界中游刃有余。
|
15天前
|
搜索推荐 Android开发 开发者
探索安卓开发中的自定义视图:打造个性化UI组件
【10月更文挑战第39天】在安卓开发的世界中,自定义视图是实现独特界面设计的关键。本文将引导你理解自定义视图的概念、创建流程,以及如何通过它们增强应用的用户体验。我们将从基础出发,逐步深入,最终让你能够自信地设计和实现专属的UI组件。
|
1天前
|
Java 调度 Android开发
安卓与iOS开发中的线程管理差异解析
在移动应用开发的广阔天地中,安卓和iOS两大平台各自拥有独特的魅力。如同东西方文化的差异,它们在处理多线程任务时也展现出不同的哲学。本文将带你穿梭于这两个平台之间,比较它们在线程管理上的核心理念、实现方式及性能考量,助你成为跨平台的编程高手。