游戏卡顿白皮书 › L1 客户端游戏进程
主线程同步加载/Shader 编译 Synchronous asset load, shader compile
原因 ID cg-sync-load · 主责 研发团队·客户端开发
在含图示和实验的完整版中打开此卡片 →
第一次绘制没见过的区域、怪物、特效之前,要先读文件、生成 Shader,画面因此卡住。
起因 进入新区域,首次出现的技能、装备、怪物 → 结果 主线程等待文件读取和 Shader 编译 → 画面表现 只在第一次卡住 0.1~1 秒,第二次起就正常
- 症状
- 卡住, 一卡一卡
- 因素
- 停顿
- 谁会遇到
- 只有我
- 何时出现
- 移动中/切换地图时, 做特定操作时
- 负责方
- 主责 研发团队·客户端开发
- 研发团队要做的事
- 异步加载,提前加载(预热),在加载界面或首次启动时预编译 Shader,利用好加载界面。
- 数值参考
- 编译一个 Shader 要几十 ms,长的超过 100 ms。纹理加载视存储设备速度需要几十到几百 ms。
- 监控图上
- 开服/维护后激增 · 帧尖峰次数(版本更新、驱动更新后)
- 查看位置
- 用 PresentMon 把同一路线录两遍,对比第一次和第二次经过。开发版本中,Unreal 开启 r.PSOPrecache.Validation,查看 stat PSOPrecache 和日志中的“PSO PRECACHING MISS”;Unity 在 Profiler 的 Timeline 中查看冲高帧里的加载、Shader 区段
- 确认依据
- 只在第一次去的地方、第一次用的技能上冲高 0.1~1 秒,第二次就消失。版本更新或显卡驱动更新后反馈集中出现,随后减少
- 排除依据
- 同一地点每次都冲高,就不是 Shader 缓存问题。只在存储设备慢的 PC 上每次移动都重复出现,看“存储设备过慢导致资源流式加载滞后”;专用显存占满,看“显存(VRAM)不足”
- 确认手段
- 需要游戏服务器/客户端的日志和指标
- 深入了解
- 在 PC 上,显卡驱动会把编译好的 Shader 存进 Shader 缓存,之后重复使用。所以显卡驱动更新或游戏版本更新刚发布时,这份缓存会失效,原本流畅的玩家也会有一段时间重新一卡一卡。“版本更新后每到一个新地方就顿一下”是典型的反馈。
出处
- Shader loading Unity
首次使用某个 Shader 变体时,显卡驱动要为 GPU 生成它,可能明显停顿;生成过的会被缓存,不会再停顿 - Optimizing Rendering With PSO Caches in Unreal Engine Epic Games
在需要的那一刻才创建管线状态(PSO),可能耗时 100 ms 以上,所以要提前创建 - Direct3D 12 Return Codes Microsoft
D3D12_ERROR_DRIVER_VERSION_MISMATCH:其他驱动版本生成的 PSO 缓存不能复用(驱动更新后需重新编译) - PresentMon Capture Application (README-CaptureApplication.md) Intel
用 FrameTime(帧与帧之间的 CPU 时间)录制每帧耗时 - PSO Precaching for Unreal Engine Epic Games
开启 r.PSOPrecache.Validation 后,可用 stat PSOPrecache 查看漏掉的 PSO 统计,日志中会记录“PSO PRECACHING MISS”;运行时创建 PSO 超过默认的 20 ms 即记为 hitch
相关原因
同一层:L1 客户端游戏进程
其他层中同样导致“卡住”的原因
查看含图示和实验的原卡片