我将GL_MAP_UNSYNCHRONIZED_BIT与glMapBufferRange一起使用以映射缓冲区对象。然后,我将返回的指针传递给工作线程以异步计算新顶点。该对象被加倍缓冲,因此我可以在写入另一个对象时渲染一个对象。使用GL_MAP_UNSYNCHRONIZED_BIT可为我带来显着更好的性能(主要是因为glUnmapBuffer更快返回),但我得到了一些视觉效果(尽管有双重缓冲)-因此,我假设GPU在DMA上传仍在进行时开始渲染,或者工作线程太早开始写入顶点。如果我正确理解glFenceSync,glWaitSync和glClientWaitSync,则应该以以下方式解决这些问题:
答:避免在DMA处理完成之前让GPU渲染缓冲区对象:在glUnmapBufferRange之后,直接在主线程上调用
GLsync uploadSync = glFenceSync(GL_SYNC_GPU_COMMANDS_COMPLETE, 0);
glFlush();
glWaitSync(uploadSync, 0, GL_TIMEOUT_IGNORED);
B:避免在GPU完成渲染之前从工作线程中写入缓冲区:在glDrawElements之后出现混淆,请在主线程上调用
GLsync renderSync = glFenceSync(GL_SYNC_GPU_COMMANDS_COMPLETE, 0);
在工作线程上,就在开始将数据写入到以前从glMapBufferRange返回的指针之前
glClientWaitSync(renderSync,0,100000000);
...start writing to the mapped pointer
1:我的显式同步方法正确吗?
2:如何处理第二种情况?我想在工作线程中等待(我不想使我的主线程停滞),但是我无法从工作线程发出glCommands。除了gl调用以外,还有另一种方法来检查是否已发出GLsync信号吗?
您可以做的是在辅助线程中创建一个OpenGL上下文,然后与主线程共享它。下一个:
在主线程上运行:
GLsync renderSync = glFenceSync(GL_SYNC_GPU_COMMANDS_COMPLETE, 0); glFlush();
然后
在工作线程上运行:
glClientWaitSync(renderSync,0,100000000);
在glFlush
主线程上是很重要的,否则你可以有无限的等待。另请参阅OpenGL文档:
4.1.2信令
脚注3:由SYNC_FLUSH_COMMANDS_BIT定义的简单刷新行为在等待另一个上下文的命令流中发出的fence命令完成时无济于事。在围篱同步对象上阻塞的应用程序必须采取其他步骤,以确保发出相应围篱命令的上下文已将该命令刷新到图形管道。
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句