关于opengl:现代图形管线有几帧深?

How many frames deep is a modern graphics pipeline?

假定管道已完全满:GPU等待vsync,GPU /驱动程序命令将所有缓冲区均已满,从而阻塞了用户程序。

(现代)管道中有多少帧有价值的数据?

例如:(4)

  • GPU前缓冲区中的帧
  • GPU后缓冲区中的帧
  • GPU命令缓冲区中的帧
  • CPU驱动程序命令缓冲区中的帧

  • 这取决于您所使用的图形卡以及所处的模式,但是通常来说,答案是1-3帧(如果要计算的是2-4帧,则为2-4帧)被作为帧推入缓冲区)。

    • 如果没有Vsync或任何其他类型的双缓冲策略,则没有必要在任何给定时间在内存中保留多于一帧的帧,一旦将新帧推入缓冲区,该帧就会被覆盖。
    • 启用VSync后,新的帧将被推入帧缓冲区的第二部分,并延迟将来执行的任何命令,直到触发"垂直同步"(因此,名称很明显),然后翻转这两个帧。
    • 第三种模式对于OpenGL不常见,但Vulkan和DirectX用户熟悉,称为"信箱模式",有时也称为"三重缓冲",它保留了两个"后缓冲区",总共三个缓冲区:

      • 保留一个后备缓冲区,以供垂直同步触发时使用。
      • 另一个后缓冲区直接接收完成的帧,没有延迟
      • 每当发生垂直同步时,就会切换这两个后备缓冲区的角色。

    请注意,使用三重缓冲,当缓冲区已满时,主机不会被阻塞。

    GPU可能会选择缓冲其他帧,例如在您的示例中,尽管这在OpenGL / DirectX11中比在Vulkan / DirectX12中更为常见,因为在那些后者的API中,主机在术语上更加明确GPU应该做什么的事,我无法想象一个程序员会故意扩展帧缓冲区。除了三重缓冲已经提供的好处外,还不清楚它会带来什么好处。


    对于传统的API(非命令缓冲区API),真正重要的是您使用了多少个缓冲区。图形流水线可以进行流水线处理,但是流水线的深度并不深,因此可以在同时处理多个完全独立的帧的过程中。因此,GPU的队列和GPU本身通常只会处理单个帧。

    并且由于这些API中没有真正的方法来为多个完整帧构建命令数据,因此,您可以使用的帧数将受到所使用的实际缓冲区数的限制。等待时间的帧数通常是缓冲区1的数量,代表您正在构建的帧。

    对于命令缓冲区API,帧数通常取决于您拥有的CPU内存量。缓冲区的数量提供了最低限度,但是从技术上讲,没有什么可以阻止您提前缓冲数十个或数百个帧。 CPU内存不足。

    当然,这假定您所有的每帧数据都位于CB中。如果这些数据中的任何一个位于GPU可访问的内存中(例如,矩阵数组等),或者您需要在帧之间更改描述符集,那么现在您需要缓冲另一组东西。这对事物的深度施加了额外的限制。