如何测量计算着色器的时间性能?

How to measure time performance of a compute shader?

我需要测量计算着色器的时间。但这当然不是微不足道的。 从 OpenGL Wiki - Performance 我了解到,在着色器调用之前和之后使用 glFinish() 很有用。但他们也说使用它并不是那么好。是否有可能测量着色器的时间?无论如何有可能测量计算着色器的时间吗?

我的代码看起来像这样:

renderloop()
{
  //(1)
  //(2)
  if(updateFunction) //this is done just one time at the beginning
  {
    //update Texture with a compute shader
    //...
    glDispatchCompute();
    glMemoryBarrier(GL_ALL_BARRIER_BITS);
  }
  //(3)
  //(1)

  //use the texture to do some marching cubes rendering
}

我想我必须在 (1) 位置插入 glFinish() 并在 (2) 开始计时并在 (3) 停止计时。但我不确定它是否真的有效并且会产生正确的计时结果,因为在参考中他们正在谈论渲染并且计算着色器没有渲染,不是吗?

也有OpenGL Timer_Query,但我不确定它是如何工作的,也不知道它对我有没有用。这些东西对我来说是新的,我不确定我现在是否完全理解它。

here 的回答说几乎不可能精确测量代码的一部分。最好的方法是测量帧渲染时间,但为了我的目的,我只需要帧渲染时间的计算着色器部分。

您认为最好的选择是什么?测量整帧渲染时间就可以了?还是您使用其他测量方法获得了更好的体验?

计时器查询绝对是正确的选择。

一般原则是您创建 'query objects' 并在 GL 函数调用之间插入。

作为GPU运行异步,这些查询会被插入到GPU命令队列中,'filled'真正处理命令时

因此,在您的情况下,您需要使用 glGenQueries(1, &myQuery);

创建查询

然后,不是启动计时器,而是在 (2) 中使用 glBeginQuery(GL_TIME_ELAPSED, myQuery) 启动查询,并在 (3) 中使用 glEndQuery(GL_TIME_ELAPSED).[= 'stop' 启动查询15=]

要获得结果,您只需调用 glGetQueryObject 函数即可。

您可以在此处了解更多信息,例如:http://www.lighthouse3d.com/tutorials/opengl-short-tutorials/opengl-timer-query/

当然还有一些'traps' - 最主要的是你必须等待计时结果准备好 - 所以你可以让GPU和CPU同步,这会减慢你的应用程序(但仍然会给你很好的 GL 时间),或者有多个查询在进行中。