4. 图形绘制流水的基本原理和实践 (3)

Vulkan 同步原语

image.png
image.png

Fence

CPU 代码执行前等待,GPU 所有代码执行后触发

image.png

Event

CommandBuffer 执行到中途等待和触发

image.png

Semaphore 信号量

一个提交执行完后进行触发,执行前等待

image.png

Barrier 内存屏障 CommandBuffer 中的各个 cmb 之间等待和触发 优化的话需要通过排布渲染顺序减少 Barrier 的使用

image.png

简单的多线程渲染,没有资源同步

  1. 开启多线程创建多个 command buffer,

  2. 等待所有线程执行完成,获取所有 command buffer ,再用一个 primary command buffer 去执行这些所有 secondary command buffer

image.png

没有资源竞争,同步,调度 线程之间不要共享 pool ,可写数据 image.png

FrameGraph

用 FrameGraph 处理资源竞争 简单的 Differed FrameGraph 可以知道资源的生命周期,当 Image 或 Buffer 不需要使用的时候,可以作为另外的 Pass 的输出 image.png

AO 流程的资源访问

image.png

可以将 AO 步骤进行异步执行,他们的资源读写不与主线程发生冲突。 这个多线程调度算法是

  1. 先将每个 Pass 做成一个 Submit

  2. 利用 FrameGraph + Semaphore 来进行 Submit 调度

可以参考 Filament 的 FrameGraph

image.png
image.png

Vulkan 优化

参考 Arm 和高通的最佳实践

移动端常见优化

一般要从带宽上优化,计算性能已经很高了

不需要做 pre depth,因为 Tile-base 会收集所有指令,并没有绘制顺序的区别?

避免破坏 early z

直接画 UI 中的图像来避免 Alpha blend image.png

减少通用寄存器使用

  • 两个 vec2 合成一个 vec4

  • 展开写循环 image.png

灯光渲染 传统两种方式的优缺点 使用 Vulkan 的 Subpass 也没法很好的解决 Deferred lighting 在移动端的带宽瓶颈

image.png

混合使用,来优化 Forward 带阴影的灯光用传统的方法着色,双重循环 mesh 和 Light。 不带阴影的灯光 for 循环统一在一个 Pass 计算,上限 6 个

image.png

灯光再多,用 claster lighting

最后更新于

这有帮助吗?