android graphic(16)—fence(简化)


前面一篇文章以代码分析了fence的产生和传递过程,这里将过程简化为上层和下层两幅图。其中图中橘黄色的fence为release fence,而绿色的fence为acquire fence。

上层绘图

这里写图片描述

a, Surface dequeue buffer,Buffer Queue传递给Surface一个release fence,然后wait等待这个release fence触发。触发后,开始绘图。

b, 绘图完成后queue buffer,同时设置一个acquire fence, Layer对应的消费者acquire到这个buffer。

c, 该layer有两种合成方式,overlay合成和opengl合成。如果使用opengl合成,会调用doGLFenceWaitLocked()等到上层绘图的完成,然后执行Opengl合成,如果是overlay,surfaceflinger不做过多处理。

d, 在下个vsync信号处理期间,首先为上次合成时的buffer,即buffer1利用sycnForReleaseLocked()函数创建一个release fence,然后再将该buffer release,还给BufferQueue。
注意,一般在acquire buffer的时候,都会先将上次vsync使用的buffer release到BufferQueue。

下层合成

这里写图片描述

a, surfaceflinger完成HWC_FRAMEBUFFER相关layer的合成后,会将合成的buffer设置到HWC_FRAMEBUFFER_TARGET layer。在eglSwapBuffers()时DisplayDevice会去queue该buffer到对应的BufferQueue,同时设置一个acquire fence。FramebufferSurface首先acquire到该buffer,同时包括该acquire fence,然后交给hwcomposer处理。

b, 对overlay的layer的合成,在上层已经设置了acquire fence,这里直接交给hwcomposer处理。

c, hwcomposer在处理HWC_FRAMEBUFFER_TARGET layer时(buffer1),会为其设置一个release fence(fence2)。在下次vsync信号处理期间,该buffer会被release到BufferQueue中,同时附带hwcomposer设置的release fence。

d, hwcomposer在处理overlay layer时(buffer3),会为其设置一个release fence(fence4)。在下次vsync信号处理期间,该buffer会被release到BufferQueue中,同时附带hwcomposer设置的release fence。

安卓系统的`releaseBuffer`机制主要用于管理图形缓冲区(Graphic Buffer),特别是在渲染过程中释放不再需要的缓冲区资源。下面我会尽量清晰地描述其工作原理和代码流程: ### 1. `releaseBuffer`的作用 当应用程序完成对某个图形缓冲区的操作并将其提交给SurfaceFlinger进行合成时,该缓冲区将从应用进程转移到SurfaceFlinger进程中处理。此时,在应用层面上这个缓冲区已经可以被标记为“已发布”,意味着它可以被新的帧数据覆盖或者完全释放掉以节省内存。 ### 2. 工作流程概述 #### a) 缓冲队列 (BufferQueue) 这是连接生产者(如GLRenderer、Canvas等) 和消费者(SurfaceFlinger) 的桥梁,它负责传递图像帧,并维护了一个环形缓冲池来存储待使用的framebuffer对象。每个buffer都有一个状态机用于跟踪它们所处的状态变化。 #### b) 生产者的视角 - 应用程序通过调用`dequeueBuffer()`请求获取空闲缓冲; - 经过绘制操作后再次调用`queueBuffer()`把含有新内容的 buffer 发送给 SurfaceFlinger 进行显示; - 当一帧结束之后,则会触发一次 release 操作 (`releaseBuffer`) ,通知 BufferQueue 将对应 slot 置为空闲状态以便后续复用。 #### c) 消费者的视角 - SurfaceFlinger 一旦接收到 queue 上来的 frame 数据包就会把它加入到等待呈现列表里;而当屏幕刷新周期到来并且有足够的时间间隔可供展示下一个画面时便开始执行实际的画面合成任务——即真正意义上向物理显示屏推送像素信息的动作。与此同时对于那些已经被完整播放过的旧帧而言自然也就失去了继续存在的意义所以会被立即销毁回收进而腾出空间供将来使用。 ### 3. 具体函数调用路径 由于 Android 版本更新频繁且各版本间存在差异,因此具体的 API 实现细节可能会有所不同,但大致上涉及到的主要类包括但不限于: - **IGraphicBufferProducer** / **BpGraphicBufferProducer**: 提供给客户端侧的应用程序接口。 - **BufferQueue::Core**: 核心逻辑所在之处,控制着整个 buffers 生命周期及流转过程中的各项事务处理。 - **SF (SurfaceFlinger)**: 负责最终渲染输出的核心服务组件之一。 ```cpp // 示例伪码表示部分关键步骤 void GraphicBufferProducer::requestRelease(int slot){ // 更新slot状态 mSlots[slot].mState = SLOT_STATE_FREE; } void SurfaceFlinger::onFrameAvailable(const sp<Fence>& fence) { // 处理可用的新帧... // 假设这里我们完成了当前帧的所有工作, // 那么接下来就可以安全地释放之前分配好的 buffer了 graphicBuffer->unlock(); } ``` 请注意这只是一个简化版的概念图示,真实环境中还需要考虑更多因素比如同步信号量(`fences`)、跨进程通信(IPC)等问题才能保证所有参与者之间协调一致运作良好。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值