Android VSYNC双Buffer与三Buffer渲染线程RenderThread(5)

Android VSYNC双Buffer与三Buffer渲染线程RenderThread(5)

 

手机自带的卡顿丢帧分析工具,柱状图:

3a9de541702343d18babd00f84e99a79.png

7a64713140ea47d1b71f0507118f1796.png

 

 

帧的大体绘制过程:

fc3f615e7cd843a3a1fa12a5cfc34278.png

帧绘制中的重要概念:BufferQueue
首先看一下 BufferQueue,BufferQueue 是一个生产者(Producer)-消费者(Consumer)模型中的数据结构,一般来说,消费者(Consumer) 创建 BufferQueue,而生产者(Producer) 一般不和 BufferQueue 在同一个进程里面

当生产者(Producer) 需要 Buffer 时,它通过调用 dequeueBuffer()并指定 Buffer 的宽度,高度,像素格式和使用标志,从 BufferQueue 请求释放 Buffer
生产者(Producer) 将填充缓冲区,并通过调用 queueBuffer()将缓冲区返回到队列。
消费者(Consumer) 使用 acquireBuffer()获取 Buffer 并消费 Buffer 的内容
使用完成后,消费者(Consumer)将通过调用 releaseBuffer()将 Buffer 返回到队列
 

在 Android App 的渲染流程里面,App 就是个生产者(Producer) ,而 SurfaceFlinger 是一个消费者(Consumer),所以上面的流程就可以翻译为

当 App 需要 Buffer 时,它通过调用 dequeueBuffer()并指定 Buffer 的宽度,高度,像素格式和使用标志,从 BufferQueue 请求释放 Buffer
App 可以用 cpu 进行渲染也可以调用用 gpu 来进行渲染,渲染完成后,通过调用 queueBuffer()将缓冲区返回到 App 对应的 BufferQueue(如果是 gpu 渲染的话,这里还有个 gpu 处理的过程)
SurfaceFlinger 在收到 Vsync 信号之后,开始准备合成,使用 acquireBuffer()获取 App 对应的 BufferQueue 中的 Buffer 并进行合成操作
合成结束后,SurfaceFlinger 将通过调用 releaseBuffer()将 Buffer 返回到 App 对应的 BufferQueue

 

单缓存
单 Buffer 情况,因为只有一个 Buffer 可用,这个 Buffer 既要用来做合成显示,又要被应用拿去做渲染。

d3007f8ba2cc4dc69e47e3dfdc9e0246.jpeg
理想情况下,单 Buffer 也是可以完成任务不卡顿丢帧的。
1、App 收到 Vsync 信号,获取 Buffer 开始渲染;
2、间隔 Vsync-Offset 时间后,SurfaceFlinger 收到 Vsync 信号,开始合成;
3、屏幕刷新,我们看到合成后的画面。

4c9a6e3ba7904faf989780d373b99ad5.jpeg

但很不幸,理想情况也就想一想,任何一个环节,如果 App 渲染或者 SurfaceFlinger 合成,在屏幕显示刷新之前还没完成,那么屏幕刷新时候,拿到的 Buffer 就是不完整的,用户看来,就有撕裂的视觉效果。

 

双缓冲

两个缓存区: Back Buffer 、 Frame Buffer。当写入下一帧时,GPU会先填充 Back Buffer 中,当刷新屏幕时,屏幕从 Frame Buffer 中读数据。VSYNC 主要是完成帧的复制,开始下一帧的渲染。

a6fa2a3afb0f4a9e940e877763bda4a5.webp
 

 

Choreographer主要是配合 Vsync ,给上层 App 的渲染提供稳定的 Message 处理的时机,Vsync 到来时候 ,系统通过对 Vsync 信号周期的调整,控制每1帧绘制时机。Vsync 周期如果是 16.6ms (60 fps) ,是因为手机屏幕是 60Hz 的刷新率,也就是 16.6ms 刷新1次,系统为了配合屏幕刷新频率,将 Vsync 的周期也设置为 16.6 ms,每隔 16.6 ms ,Vsync 信号到来唤醒 Choreographer 来做 App 的绘制操作 ,如果每个 Vsync 周期应用都能渲染完成,那么应用的 fps 就是 60 ,用户的感觉就是非常流畅,这就是引入 Choreographer 的主要作用。

Android双Buffer与三Buffer丢帧卡顿对比

92b71164f9f54daa99480b5ec6f3aeb4.png

双buffer下,主线程连续超时,开始丢帧。三buffer减轻丢帧情况,从原先丢2帧减轻到丢1帧。

主线程有时要等待 SurfaceFlinger释放Buffer后,才能获取 Buffer 进行生产,但大部分情况下, SurfaceFlinger 和应用主线程 同时收到 Vsync 信号,如果应用主线程等待SurfaceFlinger释放 Buffer,那会让应用主线程执行时间延后。

双 Buffer 时候,App生产的 Buffer 必须要及时拿去让 GPU 渲染,然后 SurfaceFlinger 才能进行合成,一旦 GPU 超时,就容易出现 SurfaceFlinger 无法及时合成而导致掉帧;在三 Buffer 轮转时候,App 生产的 Buffer 可及早进入 BufferQueue,让 GPU 去进行渲染(因为不需等待),当 SurfaceFlinger 本身负载比较大,三个 Buffer 轮转也会有效降低 dequeueBuffer 等待时间。

App 与 SurfaceFlinger 的交互主要集中在三点

  1. Vsync 信号的接收和处理
  2. RenderThread 的 dequeueBuffer
  3. RenderThread 的 queueBuffer

RenderThread 的 dequeueBuffer

dequeue 有出队的意思,dequeueBuffer 顾名思义,就是从队列中拿出一个 Buffer,这个队列就是 SurfaceFlinger 中的 BufferQueue。如下图,应用开始渲染前,首先需要通过 Binder 调用从 SurfaceFlinger 的 BufferQueue 中获取一个 Buffer。

  1. dequeue(生产者发起) : 当生产者需要缓冲区时,它会通过调用 dequeueBuffer() 从 BufferQueue 请求一个可用的缓冲区,并指定缓冲区的宽度、高度、像素格式和使用标记。
  2. queue(生产者发起):生产者填充缓冲区并通过调用 queueBuffer() 将缓冲区返回到队列。
  3. acquire(消费者发起) :消费者通过 acquireBuffer() 获取该缓冲区并使用该缓冲区的内容
  4. release(消费者发起) :当消费者操作完成后,它会通过调用 releaseBuffer() 将该缓冲区返回到队列

当 VSYNC 信号到达时,SurfaceFlinger 会遍历它的层列表,以寻找新的缓冲区。如果找到新的缓冲区,它会获取该缓冲区;否则,它会继续使用以前获取的缓冲区。SurfaceFlinger 必须始终显示内容,因此它会保留一个缓冲区。如果在某个层上没有提交缓冲区,则该层会被忽略。SurfaceFlinger 在收集可见层的所有缓冲区之后,便会询问 Hardware Composer 应如何进行合成。

这里丢帧了(Jank),丢1帧:

f9820bda816f45c9a5e2cdbf090c9505.png

 

从SurfaceFlinger端才能真正认定丢帧:

212fbf201835403e8095f5db93ad5d27.jpeg

 

 

 

 

Android性能分析:卡顿丢帧基础CPU/GPU原理(4)-CSDN博客文章浏览阅读821次,点赞18次,收藏19次。产生 Jank 的那一帧的显示期间,GPU/CPU 在闲置的。CPU返回后,会直接将GraphicBuffer提交给SurfaceFlinger,告诉SurfaceFlinger进行合成,但是这个时候GPU可能并未完成之前的图像渲染,这时候就牵扯到一个同步,Android中,用的是Fence机制,SurfaceFlinger合成前会查询Fence,如果GPU渲染没有结束,则等待GPU渲染结束,GPU结束后,会通知SurfaceFlinger进行合成,SF合成后,提交显示,最终完成图像的渲染显示。https://blog.csdn.net/zhangphil/article/details/138804486

 Android GPU渲染屏幕绘制显示基础概念(1)-CSDN博客文章浏览阅读1k次,点赞30次,收藏18次。CPU返回后,会直接将GraphicBuffer提交给SurfaceFlinger,告诉SurfaceFlinger进行合成,但是这个时候GPU可能并未完成之前的图像渲染,这时候就牵扯到一个同步,Android中,用的是Fence机制,SurfaceFlinger合成前会查询Fence,如果GPU渲染没有结束,则等待GPU渲染结束,GPU结束后,会通知SurfaceFlinger进行合成,SF合成后,提交显示,最终完成图像的渲染显示。而对SF来说,只要有合成任务,它就得再去申请VSYNC-sf。https://blog.csdn.net/zhangphil/article/details/138585120Android GPU渲染SurfaceFlinger合成RenderThread的dequeueBuffer/queueBuffer与fence机制(2)-CSDN博客文章浏览阅读794次,点赞12次,收藏17次。t 时长,20s,20秒的trace文件。CPU返回后,会直接将GraphicBuffer提交给SurfaceFlinger,告诉SurfaceFlinger进行合成,但是这个时候GPU可能并未完成之前的图像渲染,这时候就牵扯到一个同步,Android中,用的是Fence机制,SurfaceFlinger合成前会查询Fence,如果GPU渲染没有结束,则等待GPU渲染结束,GPU结束后,会通知SurfaceFlinger进行合成,SF合成后,提交显示,最终完成图像的渲染显示。就是 Buffer。https://blog.csdn.net/zhangphil/article/details/138628225Android性能:SurfaceFlinger与BufferQueue(3)-CSDN博客文章浏览阅读757次,点赞25次,收藏24次。t 时长,20s,20秒的trace文件。CPU返回后,会直接将GraphicBuffer提交给SurfaceFlinger,告诉SurfaceFlinger进行合成,但是这个时候GPU可能并未完成之前的图像渲染,这时候就牵扯到一个同步,Android中,用的是Fence机制,SurfaceFlinger合成前会查询Fence,如果GPU渲染没有结束,则等待GPU渲染结束,GPU结束后,会通知SurfaceFlinger进行合成,SF合成后,提交显示,最终完成图像的渲染显示。就是 Buffer。https://blog.csdn.net/zhangphil/article/details/138631517

Android性能:Double Buffer双缓冲/Triple Buffer三缓冲丢帧Jank与无丢帧No Jank-CSDN博客文章浏览阅读842次,点赞6次,收藏13次。Android ADB调试真机设备Android ADB(Andorid Debug Bridge),是Android开发中有用的测试和调试工具。使用Android ADB调试设备,直接在Windows的dos命令窗口输入命名adb即可,如图:为什么执行adb命令后是这样?_android 抓trace。三Buffer轮转情况下,基本不会有这种情况的发生,渲染线程一般在 dequeueBuffer 时,都可以顺利拿到可用的 Buffer (如果 dequeueBuffer 本身耗时那就也会拉长时间)。https://zhangphil.blog.csdn.net/article/details/138213964

Android硬件加速hardwareAccelerated支持/不支持的绘图接口-CSDN博客文章浏览阅读262次,点赞3次,收藏14次。三Buffer轮转情况下,基本不会有这种情况的发生,渲染线程一般在 dequeueBuffer 时,都可以顺利拿到可用的 Buffer (如果 dequeueBuffer 本身耗时那就也会拉长时间)。在Android早期的版本,由于硬件制造商差异大,增加了这一开关,但随着Android系统版本的迭代,以及硬件技术水平提升,现有的绝大多数Android手机硬件层面均已支持硬件加速(GPU渲染),Android本身也只有有限几个接口不支持硬件加速。https://blog.csdn.net/zhangphil/article/details/138502494

Android adb shell命令捕获systemtrace_android 抓trace-CSDN博客文章浏览阅读1.7k次,点赞2次,收藏5次。Android ADB调试真机设备Android ADB(Andorid Debug Bridge),是Android开发中有用的测试和调试工具。使用Android ADB调试设备,直接在Windows的dos命令窗口输入命名adb即可,如图:为什么执行adb命令后是这样?Android ADB(Andorid Debug Bridge)调试真机设备_adb在线执行器_zhangphil的博客-CSDN博客。-t 时长,20s,20秒的trace文件。-o 保存文件路径。_android 抓tracehttps://blog.csdn.net/zhangphil/article/details/131249820

adb shell top -m 10 -s 1 -d 1 -o %CPU,%MEM,TIME+,PID,COMMAND,CMDLINE_adb shell top -m 10 -s cpu-CSDN博客文章浏览阅读390次。使用Android ADB调试设备,直接在Windows的dos命令窗口输入命名adb即可,如图:为什么执行adb命令后是这样?Android ADB(Andorid Debug Bridge)调试真机设备_adb在线执行器_zhangphil的博客-CSDN博客。Android adb shell dump当前手机设备的所有activity_dump当前activity_zhangphil的博客-CSDN博客。Android adb获取CPU信息_zhangphil的博客-CSDN博客。_adb shell top -m 10 -s cpuhttps://blog.csdn.net/zhangphil/article/details/131412814

 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/845083.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Visual Studio Code 开发esp8266流程2Arduino 配置 nodemcu

http://arduino.esp8266.com/stable/package_esp8266com_index.json Arduino: Library Manager

第二十五章CSS中的技巧(导航栏、下拉列表)

1.CSS精灵 1.什么是CSS精灵 英文叫法 CSS sprites,通常被解释为“CSS图像拼合”或“CSS贴图定位”;其实就是把网页中一些背景图片整合到一张图片文件中,再利用css“background-image”, “background-repeat”,“background-position”的组…

中国地质大学(武汉):23考研多专业接受调剂,24新增上机考试!中国地质大学(武汉)计算机考研考情分析!

中国地质大学(武汉)计算机学院成立于1985年,其前身为地矿部武汉计算站。经过近二十年的努力,计算机学院不断发展壮大。现设有计算机应用、计算机软件、网络与系统结构、信息安全四个教研室;拥有湖北省计算机应用技术重…

最大回撤概念与计算

一、最大回撤,是指的最大下跌的值: 1、即所有下跌趋势中,净值最低的点,与历史净值最高点直接的差值。 2、最大回撤取绝对值显示 二、如果有时间限制,则计算对应时间段内的最大回撤。 示意图如下: 三、举…

【Java面试】七、SpringMvc的执行流程、SpringBoot自动装配原理

文章目录 1、SpringMVC的执行流程1.1 视图阶段1.2 前后端分离阶段 2、SpringBoot自动配置原理3、框架常用的注解3.1 Spring的注解3.2 SpringMvc的注解3.3 SpringBoot的注解 4、面试 1、SpringMVC的执行流程 1.1 视图阶段 旧项目中,未前后端分离时,用到…

OAK相机如何将 YOLOv10 模型转换成 blob 格式?

编辑:OAK中国 首发:oakchina.cn 喜欢的话,请多多👍⭐️✍ 内容可能会不定期更新,官网内容都是最新的,请查看首发地址链接。 Hello,大家好,这里是OAK中国,我是Ashely。 专…

Microsoft Fabric 是什么?

最近半个月没有更新内容,原因是什么呢? 原因是花了两周的时间备考了一下"Microsoft Certified: Fabric Analytics Engineer Associate"的考试认证。 非常幸运考试通过了。 那什么是Microsoft Fabric 呢? Microsoft Fabric 是一个…

运筹学_4.整数规划

文章目录 引言4.1 分枝定界方法求解整数规划问题整数规划的分类整数规划解法概述分支定界法 4.2 0-1整数规划0-1整数规划的数学模型隐枚举法求解0-1规划问题 4.3 指派问题(分配问题)的匈牙利解法指派问题的数学模型指派问题的匈牙利解法 引言 规划中的决策变量(全部或部分)限制…

【备战蓝桥杯】蓝桥杯省一笔记:算法模板笔记(Java)

蓝桥杯 0、快读快写模板1、回文判定2、前缀和3、差分4、二分查找5、快速幂6、判断素数7、gcd&lcm8、进制转换9、位运算10、字符串常用API11、n的所有质因子12、n的质因子个数13、n的约数个数14、n阶乘的约数个数15、n的约数和16、阶乘 & 双阶乘17、自定义升序降序18、动…

2024盘古石初赛(服务器部分)

赛后总结 这次初赛就有20道服务器部分赛题,做的情况一般,错了5道题这样,主要原因就是出在第二个网站服务器没有重构起来 今天来复现一下 这次的服务器部分我直接用仿真仿起来就开找了 第一台IM前期配置 先把网配置好,然后ssh…

如此简单,一文带你玩转接口自动化上(Python + Pytest + Requests + Allure )

一. 前言 哈喽大伙们好,好久不见距离上次更新博客已经有一年之久了,这将近一年的时间小编主要的时间都花在了实习和24届校招上面了,最终也是收获满满,选择了一个还不错的offer,感谢一路走来的自己和身边朋友的帮助&…

基于Three.js实现的3D立方体动画

本文由ScriptEcho平台提供技术支持 项目地址:传送门 基于Three.js实现的3D立方体动画 应用场景 该代码段适用于需要在网页中创建交互式3D场景的场景。例如,可以用于展示产品、创建游戏或制作视觉效果。 基本功能 此代码段使用Three.js库创建了一个…

【机器学习】随机森林:深度解析与应用实践

🌈个人主页: 鑫宝Code 🔥热门专栏: 闲话杂谈| 炫酷HTML | JavaScript基础 ​💫个人格言: "如无必要,勿增实体" 文章目录 随机森林:深度解析与应用实践引言1. 随机森林基础1.1 什么是随机森林…

Android更新优化 - 增量更新是如何节省用户时间和流量的

增量更新和全量更新 我想玩过大型手游的人都知道,手游的安装包非常大,因为资源图片众多。而你每次更新都把所有文件都更新下来,是非常耗时的,对吧。耗时是一个方面,有些人在户外开的是移动网络,动不动就几…

计算机组成原理·海明编码及其实验

前言:海明编码这一块在刚开始的时候没有弄懂,后面通过做实验、复习慢慢摸清了门道。在学习计算机组成原理的过程中,实验实践是很重要的,它会让你去搞清楚事情背后的原理,逼着你学会你没听懂的东西。这篇文章会从海明码…

Check Point 安全网关任意文件读取漏洞复现(CVE-2024-24919)

Check Point 安全网关任意文件读取漏洞复现(CVE-2024-24919) 1.漏洞描述 Check Point Security Gateways 是 Check Point Sofware 提供的一系列 网络安全Q解决方案。这些解决方案包括下一代防火墙(NGFW)、数据中心安全网关和 A1驱动的量子网关,旨在为企业提供针对…

@Value 读取环境变量配置

在项目开发过程中,有必要使用一些灰色规则(即仅用于开发使用过程中的逻辑控制变量)。 比如,本地开发中,一些业务逻辑需要调用第三方代码,但又在本地调不通,怎么办。只能通过 if(本地开发) {mock…

【开源】渔具租赁系统 JAVA+Vue.js+SpringBoot+MySQL

目录 一、项目介绍 1.1渔具档案模块 1.2渔具租赁模块 1.3渔具归还模块 1.4在线留言模块 二、项目截图 三、核心代码 一、项目介绍 Vue.jsSpringBoot前后端分离新手入门项目《渔具租赁系统》,包括渔具档案模块、渔具租赁模块、渔具归还模块、在线留言模块和部…

当新媒体运营开始说真话,这些道理你真的懂么?沈阳新媒体运营培训

运营新人,尤其是刚毕业、啥都不会的大学生,一定要认清的现实就是:虽然新媒体运营这个岗位门槛比较低,薪资也比较香,但绝不是养老型的工作。 平时大家还是很忙的,所以一定要摒弃学生思维,千万别…

02--nginx代理缓存

前言:比较常用的用法反向代理,和缓存的一些操作,用虚拟环境复刻出来,里面参数不用详细记录,用作复习,使用时直接查找即可。环境搭建过程参考前一篇文章nginx基础。 1、基础环境 IP角色作用192.168.189.143…