简介FrameBuffer 在Android中并不像在其它GUI那样直观,抽象的层次比较多,加上GUI的更新是通过OpenGLES来做的。所以让人很难搞清GUI更新的整个流程,最近要准备一个讲稿,所以花了一些去研究,这里做点笔记供大家参考,源代码是基于高通平台的,这些代码在网上都可以下载。 FrameBuffer 的相关组件如下图所示:
mNativeWindow = new FramebufferNativeWindow();
framebuffer_device_t const * fbDev = mNativeWindow->getDevice();
if (hw_get_module(OVERLAY_HARDWARE_MODULE_ID, &module) == 0) {
overlay_control_open(module, &mOverlayEngine);
}
surface = eglCreateWindowSurface(display, config, mNativeWindow.get(), NULL);
eglMakeCurrent(display, surface, surface, context);
这两个函数由eglSwapBuffers调过来,调到: egl_window_surface_v2_t::swapBuffers:
nativeWindow->queueBuffer(nativeWindow, buffer);
nativeWindow->dequeueBuffer(nativeWindow, &buffer);
OverlayControlChannel用于设置参数,比如设置Overlay的位置,宽度和高度: bool OverlayControlChannel::setPosition(int x, int y, uint32_t w, uint32_t h) {
ov.dst_rect.x = x;
ov.dst_rect.y = y;
ov.dst_rect.w = w;
ov.dst_rect.h = h;
ioctl(mFD, MSMFB_OVERLAY_SET, &ov);
}
OverlayDataChannel用于显示Overlay,其中最重要的函数就是queueBuffer: bool OverlayDataChannel::queueBuffer(uint32_t offset) {
mOvData.data.offset = offset;
ioctl(mFD, MSMFB_OVERLAY_PLAY, odPtr))
}
framebuffer只是/dev/graphic/fb0的包装,Surface的Buffer则是对/dev/pmem、ashmem和GPU内存(msm_hw3dm)的包装,它的目标主要是方便硬件加速,因为 DMA传输使用物理地址,要求内存在物理地址上连续。
#define MSM_PMEM_MDP_SIZE 0x1B76000 #define MSM_PMEM_ADSP_SIZE 0xB71000 #define MSM_PMEM_AUDIO_SIZE 0x5B000 #define MSM_FB_SIZE 0x177000 #define MSM_GPU_PHYS_SIZE SZ_2M #define PMEM_KERNEL_EBI1_SIZE 0x1C000 msm_msm7x2x_allocate_memory_regions分配几大块内存用于给pmem做二次分配。
Kernel Graphics System Layer (KGSL),3D图形加速驱动程序,源代码drivers/gpu/msm目录下,它是对GPU的包装,给OpenGLES 2.0提供抽象的接口。
这个我在内核中没有找到相关代码。
msm_fb.c: framebuffer, overlay和blit的用户接口。 mdp_dma.c: 对具体显示设备的包装,提供两种framebuffer更新的方式: mdp_refresh_screen: 定时更新。 mdp_dma_pan_update: 通过pan display主动更新。 mdp_dma_lcdc.c:针对LCD实现的显示设备,mdp_lcdc_update用更新framebuffer。 SeeAlso |
作者: 李先静 xianjimli@gmail.com
日期: 2010-01-14
本文介绍了 Android 的 framebuffer 的整体架构,图文并茂,比较清晰。文章转自 http://www.limodev.cn/blog


浙公网安备 33010602011771号