Android CameraServer GrallocBuffer架构理解2
Gralloc Buffer 设计与实现知识库源码路径:frameworks/native/libs/ui/include/ui/+frameworks/native/libs/ui/第一章 总体架构1.1 系统定位Gralloc(Graphics Allocation)是 Android 图形子系统的内存管理层,负责图形缓冲区的分配、映射、锁定和跨进程传输。位于 HAL 层之上、SurfaceFlinger/图形管线之下。┌─────────────────────────────────────────────────┐ │ 应用层 (Surface/ANativeWindow) │ ├─────────────────────────────────────────────────┤ │ GraphicBuffer (核心对象) │ │ ┌──────────────────┬────────────────────┐ │ │ │ GraphicBufferAllocator │ GraphicBufferMapper │ │ │ (分配/释放) │ (映射/锁定/元数据) │ │ └──────────┬───────────┴─────────┬──────────┘ │ │ │ │ │ │ ┌──────────┴─────────────────────┴──────────┐ │ │ │ GrallocAllocator / GrallocMapper │ │ │ │ (抽象接口层 Gralloc.h) │ │ │ └──────────┬─────────────────────┬──────────┘ │ │ │ │ │ │ ┌──────────┴───────┐ ┌───────────┴──────────┐ │ │ │ Gralloc2/3/4/5 │ │ Gralloc2/3/4/5 │ │ │ │ Allocator │ │ Mapper │ │ │ │ (HAL分配器) │ │ (HAL映射器) │ │ │ └──────────────────┘ └──────────────────────┘ │ ├─────────────────────────────────────────────────┤ │ HAL层 (厂商实现: IAllocator / IMapper) │ └─────────────────────────────────────────────────┘1.2 核心设计原则Allocator/Mapper 分离: 分配与映射由不同 HAL 服务提供,可独立升级版本自适应: 运行时探测可用的最高 Gralloc 版本(5→4→3→2),逐级降级单例模式: Allocator 和 Mapper 全局唯一,通过 Singleton 管理跨进程安全: 通过 Flattenable 协议实现 GraphicBuffer 的序列化/反序列化第二章 核心类详解2.1 GraphicBuffer — 图形缓冲区核心对象文件:GraphicBuffer.h/GraphicBuffer.cpp继承关系:ANativeWindowBuffer (C结构体, 定义 width/height/format/usage/handle) └── ANativeObjectBaseANativeWindowBuffer, GraphicBuffer, RefBase └── GraphicBuffer + FlattenableGraphicBuffer关键成员成员类型说明width/heightint缓冲区尺寸strideint行步长(像素),可能大于 widthformatPixelFormat像素格式 (RGBA_8888 等)usageuint64_t64位使用标志 (HW_TEXTURE|SW_READ 等)layerCountuint32_t层数 (array texture)handlebuffer_handle_t底层 native_handle 指针mIduint64_t唯一ID = PID32 | 递增计数mOwneruint8_t所有权: ownNone/ownHandle/ownDatamBufferMapperGraphicBufferMapperMapper 引用mDeathCallbacksvectorpaircallback, context销毁回调 (用于跨进程缓存)mDependencyMonitorDependencyMonitor依赖监控 (调试用)构造方式// 1. 空构造(用于 unflatten 反序列化)GraphicBuffer();// 2. 分配新缓冲区(最常用)GraphicBuffer(uint32_twidth,uint32_theight,PixelFormat format,uint32_tlayerCount,uint64_tusage,std::string requestorName);// 3. 从已有 handle 包装(4种模式)GraphicBuffer(constnative_handle_t*handle,HandleWrapMethod method,...);// - WRAP_HANDLE: 直接引用,不拥有所有权// - TAKE_HANDLE: 接管已注册 handle 的所有权// - TAKE_UNREGISTERED_HANDLE: 接管未注册 handle,先 import// - CLONE_HANDLE: 克隆 handle,先 import// 4. 通过 AllocationRequest (支持附加选项)GraphicBuffer(constGraphicBufferAllocator::AllocationRequestrequest);锁定 API// 同步锁定 - 获取 CPU 可访问的虚拟地址status_tlock(uint32_tusage,void**vaddr,...);status_tlock(uint32_tusage,constRectrect,void**vaddr,...);// 异步锁定 - 支持 acquire fencestatus_tlockAsync(uint32_tusage,void**vaddr,intfenceFd,...);status_tlockAsync(uint64_tproducerUsage,uint64_tconsumerUsage,constRectrect,void**vaddr,intfenceFd,...);// YCbCr 格式锁定 (YUV 平面)status_tlockYCbCr(uint32_tusage,android_ycbcr*ycbcr);status_tlockAsyncYCbCr(uint32_tusage,android_ycbcr*ycbcr,intfenceFd);// 解锁 - 返回 release fencestatus_tunlock();status_tunlockAsync(int*fenceFd);跨进程传输 (Flattenable)flatten() 序列化格式 (13个int32_t + handle数据): ┌────────────┬────────┬─────────┬────────┬─────────┬─────────────┬───────────────────┐ │ 'GB01'标记 │ width │ height │ stride │ format │ layerCount │ usage (低32位) │ ├────────────┼────────┼─────────┼────────┼─────────┼─────────────┼───────────────────┤ │ mId高32位 │ mId低32位│ genNum │ numFds │ numInts │ usage (高32位)│ handle data... │ └────────────┴────────┴─────────┴────────┴─────────┴─────────────┴───────────────────┘GB01: 64位 usage 的新版本GBFR: 旧版本(32位 usage)handle 的 fd 和 int 数据直接追加在固定头部之后销毁回调机制// 用于跨进程 layer 缓存:// 1. App 进程持有 spGraphicBuffer,SurfaceFlinger 也持有 sp// 2. App 释放最后一个 sp → 析构函数触发 death callbacks// 3. 回调通知客户端缓存清除该 buffer,并通知 SF 释放其 spstd::vectorstd::pairGraphicBufferDeathCallback,void*mDeathCallbacks;2.2 GraphicBufferAllocator — 缓冲区分配器文件:GraphicBufferAllocator.h/GraphicBufferAllocator.cppSingletonGraphicBufferAllocator └── GraphicBufferAllocator核心职责调用底层 GrallocAllocator 执行实际分配维护分配记录列表sAllocList(用于调试和 dump)ATrace 追踪分配计数和详情分配请求结构structAllocationRequest{boolimportBuffer;// 是否立即 import(默认 true)uint32_twidth,height;PixelFormat format;uint32_tlayerCount;uint64_tusage;std::string requestorName;std::vectorAdditionalOptionsextras;// Gralloc5 扩展选项};structAllocationResult{status_t status;buffer_handle_t handle;uint32_tstride;};分配流程GraphicBuffer 构造 → GraphicBufferAllocator::allocate() → 参数校验 (width/height 非零, bpp 溢出检查, layerCount = 1) → mAllocator-allocate(request) // 尝试新接口 → 若返回 UNKNOWN_TRANSACTION: → 若有 extras → 报错(版本不匹配) → 否则降级到旧 allocate(requestorName, width, height, ...) → 计算 bufSize = stride * height * bpp → 记录到 sAllocList (加锁) → ATrace 记录初始化(版本探测)GraphicBufferAllocator::GraphicBufferAllocator():mMapper(GraphicBufferMapper::get()){switch(mMapper.getMapperVersion()){caseGRALLOC_5:mAllocator=make_uniqueGralloc5Allocator(...);break;caseGRALLOC_4:mAllocator=make_uniqueGralloc4Allocator(...);break;caseGRALLOC_3:mAllocator=make_uniqueGralloc3Allocator(...);break;caseGRALLOC_2:mAllocator=make_uniqueGralloc2Allocator(...);break;}}2.3 GraphicBufferMapper — 缓冲区映射器文件:GraphicBufferMapper.h/GraphicBufferMapper.cpp核心职责import: 将跨进程传递的 raw handle 转为本进程可用的 buffer_handle_tlock/unlock: 将缓冲区映射到 CPU 虚拟地址空间元数据查询/设置: 查询/修改 buffer 的各种属性(dataspace、HDR 信息等)validateBufferSize: 验证 buffer 参数是否匹配版本枚举enumVersion{GRALLOC_2=2,GRALLOC_3,GRALLOC_4,GRALLOC_5,};初始化(版本探测,优先级 5→4→3→2)GraphicBufferMapper::GraphicBufferMapper(){mMapper=make_uniqueGralloc5Mapper();// 先试 5if(mMapper-isLoaded()){mMapperVersion=GRALLOC_5;return;}mMapper=make_uniqueGralloc4Mapper();// 再试 4if(mMapper-isLoaded()){mMapperVersion=GRALLOC_4;return;}if(!requireMapper4()){// API 36 才允许 3/2mMapper=make_uniqueGralloc3Mapper();if(mMapper-isLoaded()){mMapperVersion=GRALLOC_3;return;}mMapper=make_uniqueGralloc2Mapper();if(mMapper-isLoaded()){mMapperVersion=GRALLOC_2;return;}}LOG_ALWAYS_FATAL("gralloc-mapper is missing");}注意: API level = 36 且require_gralloc4_or_newerflag 开启时,不再加载 Gralloc2/3。Lock 流程GraphicBufferMapper::lock(handle, usage, bounds, acquireFence) → mMapper-lock(handle, usage, bounds, fence, address, bpp, bps) → 返回 LockResult { address, bytesPerPixel, bytesPerStride }元数据 API (Gralloc4+)// 查询类getBufferId(handle,id)getName(handle,name)getWidth(handle,w)/getHeight(handle,h)getPixelFormatRequested(handle,fmt)/getPixelFormatFourCC(handle,fourcc)getUsage(handle,usage)getAllocationSize(handle,size)getPlaneLayouts(handle,layouts)// 平面布局信息getDataspace(handle,dataspace)getSmpte2086(handle,smpte)// HDR 色彩信息getCta861_3(handle,cta)// HDR 亮度信息getSmpte2094_40/10/50(handle,data)// �态 HDR 元数据// 设置类setDataspace(handle,dataspace)setSmpte2086(handle,smpte)setCta861_3(handle,cta)setSmpte2094_40/10/50(handle,data)第三章 Gralloc HAL 版本演进3.1 抽象基类 (Gralloc.h)// GrallocMapper — IMapper 包装classGrallocMapper{virtualstatus_timportBuffer(rawHandle,outBufferHandle)=0;virtualvoidfreeBuffer(bufferHandle)=0;virtualstatus_tvalidateBufferSize(...)=0;virtualstatus_tlock(bufferHandle,usage,bounds,acquireFence,outData,...)=0;virtualintunlock(bufferHandle)=0;// 30+ 个可选元数据查询/设置虚函数 (默认返回 INVALID_OPERATION)};// GrallocAllocator — IAllocator 包装class