关闭
尊敬的极客用户,您好!
感谢您一直关注并使用极客头条,为了给您带来良好的体验效果及性能,极客头条将于2018年04月27日关闭,您可以在 我的博客 中继续使用发布文章功能并看到已经发布成功的文章。
返回 登录
3

Unreal* Engine 4 VR应用的CPU性能优化和差异化:第二部分

作者:王文斓

虚拟现实(VR)能够带给用户前所未有的沉浸体验,但同时由于双目渲染、低延迟、高分辨率、强制垂直同步(vsync)等特性使VR对CPU渲染线程和逻辑线程,以及GPU的计算压力较大[1]。如何能有效分析VR应用的性能瓶颈,优化CPU线程提高工作的并行化程度,从而降低GPU等待时间提升利用率将成为VR应用是否流畅、会否眩晕、沉浸感是否足够的关键。Unreal* Engine 4 (UE4) 作为目前VR开发者主要使用的两大游戏引擎之一,了解UE4的CPU线程结构和相关优化工具能够帮助我们开发出更优质基于UE4的VR应用。本文将集中介绍UE4的CPU性能分析和调试指令、线程结构、优化方法和工具、以及如何在UE4里发挥闲置CPU核心的计算资源来增强VR内容的表现,为不同配置的玩家提供相应的视听表现和内容,优化VR的沉浸感。

UE4 VR应用的CPU优化技巧

当VR开发的过程中遇到CPU性能问题时,除了需要找出瓶颈所在,还要掌握UE4里能够帮助优化这些瓶颈的工具,熟知每个工具的用法、效果和差异才能选取最合适的优化策略,快速提高VR应用的性能。在这个章节我们会集中讲解和介绍UE4的这些优化工具。

渲染线程优化
由于性能、带宽和MSAA等考虑因素,目前VR应用多采用前向渲染(Forward Rendering)而非延迟渲染(Deferred Rendering)。但在UE4的前向渲染管线中,为了减少GPU overdraw,在basepass前的prepass阶段会强制使用early-z来生成depth buffer,导致basepass前的GPU工作量提交较少。加上目前主流的DirectX* 11基本上属于单线程渲染,多线程能力较差,一旦VR场景的drawcalls或者primitives数目较多,culling计算时间较长,基本上在basepass前的计算阶段就很可能因为渲染线程瓶颈而产生GPU闲置(GPU bubbles),降低了GPU利用率而引发掉帧,所以渲染线程的优化在VR开发中至关重要。

由于性能、带宽和MSAA等考虑因素,目前VR应用多采用前向渲染(Forward Rendering)而非延迟渲染(Deferred Rendering)。但在UE4的前向渲染管线中,为了减少GPU overdraw,在basepass前的prepass阶段会强制使用early-z来生成depth buffer,导致basepass前的GPU工作量提交较少。加上目前主流的DirectX* 11基本上属于单线程渲染,多线程能力较差,一旦VR场景的drawcalls或者primitives数目较多,culling计算时间较长,基本上在basepass前的计算阶段就很可能因为渲染线程瓶颈而产生GPU闲置(GPU bubbles),降低了GPU利用率而引发掉帧,所以渲染线程的优化在VR开发中至关重要。

如果我们用GPUView分析图3的场景,会得到图4的结果,图4中红色箭头指的位置就是CPU渲染线程开始的时间。由于running start,第一个红色箭头在垂直同步前3ms就开始计算,但显然到了垂直同步时GPU还没工作可以做,一直到3.5ms后GPU短暂工作了一下又闲置了1.2ms,然后CPU才把prepass工作提交到CPU context queue,prepass完成后又过了2ms basepass的工作才被提交到CPU context queue给GPU执行。图4中红圈圈起来的地方就是GPU闲置的时间段,加起来有接近7ms的GPU bubbles,直接导致GPU渲染无法在11.1ms内完成而掉帧,需要2个垂直同步周期才能完成这帧的工作,实际上我们可以结合Windows* Performance Analyzer(WPA)分析GPU bubbles期间的渲染线程调用堆栈并找出瓶颈是由哪些函数引起的[1]。另外第二个红色箭头指的位置是下一帧渲染线程开始的时间,由于这一帧出现掉帧,所以下一帧的渲染线程多了整整一个垂直同步周期作计算。等到下一帧的GPU在垂直同步后开始工作时,渲染线程已经把CPU context queue填满了,所以GPU有足够多的工作可以做而不会产生GPU bubbles,只要没有GPU bubbles一帧的渲染在9ms内就能完成,于是下一帧就不会掉帧。3个垂直同步周期完成2帧的渲染,这也是为什么平均帧率是60fps的原因。

从图4的分析结果可以发现在这例子中,GPU实际上并不是性能瓶颈,只要把真正的CPU渲染线程瓶颈解决,该VR游戏就能够达到90fps。而事实上我们发现大部分用UE4开发的VR应用都存在渲染线程瓶颈,因此熟练掌握下面几种UE4渲染线程优化工具可以大大提升VR应用的性能。图片描述

图 3.一个存在CPU渲染线程瓶颈的VR游戏例子,上面显示了SteamVR对每帧CPU和GPU消耗时间的统计。
图片描述
图 4.图3例子的GPUView时间视图,可以看到CPU渲染线程瓶颈导致了GPU闲置,从而引发掉帧。

实例化立体渲染(Instanced Stereo Rendering)

VR由于双目渲染的原因导致drawcall数目增加一倍,容易引发渲染线程瓶颈。实例化立体渲染只要对对象提交一次drawcall,然后由GPU分别对左右眼视角施加对应的变换矩阵,就能够把对象同时画到左右眼视角上,等于把这部分的CPU工作移到GPU处理,增加了GPU vertex shader的工作但可以节省一半drawcall。因此,除非VR场景的drawcall数目较低(< 500),否则实例化立体渲染一般能够降低渲染线程负载,为VR应用带来约20%的性能提升。实例化立体渲染可以在项目设置中选择打开或关闭。

可见性剔除(Visibility Culling)

在VR应用中渲染线程瓶颈通常由两大原因造成,一个是静态网格计算另一个是可见性剔除。静态网格计算可以通过合并drawcall或者mesh来优化,而可见性剔除则需要减少原语(primitives)或者动态遮挡剔除(dynamic occlusion culling)的数目。可见性剔除瓶颈在VR应用中尤其严重,因为VR为了减低延时强制每帧CPU渲染线程计算最多只能提前到垂直同步前3ms(running start/queue ahead),而UE4里InitViews(包括可见性剔除和设置动态阴影等)阶段是不会产生GPU工作的,一旦InitViews所花时间超过3ms,就必定会产生GPU bubbles而降低GPU利用率,容易造成掉帧,所以可见性剔除在VR里需要重点优化。
….
查看全文


了解更多相关内容,请关注CSDN英特尔开发专区

评论