opengl - 无法释放共享上下文创建的纹理

标签 opengl textures shared

我在使用共享上下文时遇到了问题:

我有两个线程,每个线程都有一个上下文,例如 Thr1(thread1) 与 Ctx1(Context1) 以及 Thr2 和 Ctx2。 Ctx2 是与 Ctx1 共享创建的。

然后,在 Thr2 中,我使用 Ctx2 作为当前上下文创建一些纹理,并进行一些渲染。之后,我销毁 Ctx2 并完成 Thr2。

现在问题出现了:在我销毁Ctx2之后,在Ctx2下创建的纹理没有被释放(是部分纹理,不是全部)。我使用 gDebugger 来分析我的程序,发现这些纹理没有被释放,并列在 Ctx1 下。

当我重复创建 Thr2/Ctx2 并创建纹理并销毁 Thr2/Ctx2 时,纹理越来越多,内存也越来越多。

我尝试过:

在销毁Ctx2之前删除Thr2中的纹理;

在 Thr2 中,将 Ctx1 设置为当前状态,并在 Ctx2 销毁之前尝试删除纹理;

最佳答案

这听起来像是预期的行为。

为了解释具有多个上下文的对象的生命周期,我将使用“池”一词来描述纹理的集合。我认为这个概念没有通用的术语,所以这已经是最好的了。

虽然您通常可能认为纹理由上下文拥有,但它们实际上由池拥有。只要你只有一个背景,那就是学术差异。上下文拥有该​​池,该池拥有在上下文中创建的所有纹理。当上下文被破坏时,池也会随之消失,这反过来又会破坏池中的所有纹理。

现在,有了两个共享上下文,事情就变得更有趣了。您仍然拥有一个池,两个上下文都共享该池的所有权。当您在两个上下文中的任何一个中创建纹理时,该纹理都归共享池所有。当上下文被删除时,它放弃了它对池的共享所有权。只要至少一个上下文处于事件状态,池(包括池中的所有纹理)就会保持不变。

在您的场景中,上下文 2 创建纹理。该纹理被添加到上下文 1 和上下文 2 共享的池中。然后删除上下文 2。创建的纹理保留在池中。池本身仍然处于事件状态,因为上下文 1(仍然存在)共享池的所有权。这意味着纹理也仍然存在。上下文 2 创建纹理是无关紧要的,因为纹理由池拥有,而不是上下文 2。

因此,如果您确实想要删除纹理,则必须进行 glDeleteTexture() 调用。无论您是在上下文 1 还是上下文 2 中进行此调用都没有关系。

删除共享纹理时存在一些微妙的方面,例如与作为 FBO 附件的纹理有关,或者在一个上下文中删除纹理而在另一个上下文中绑定(bind)的纹理。但由于这不是这个问题的核心,而且有点复杂,我将引用规范了解详细信息(例如,请参见 OpenGL 3.3 规范第 337 页的 D.1.2 节)。

关于opengl - 无法释放共享上下文创建的纹理,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29813500/

相关文章:

ios - 是否可以平铺纹理 SKShapeNode

php - 哪个 php 框架适合共享主机?

c++ - 在 Windows 上同时使用 .so 和 .dll

c++ - 我的 C++ 软件是太多 exe 的集合,我该如何管理它

c++ - OpenGL 着色器与 CUDA

Python OpenGL 如何正确渲染离屏

android - 使用 ANativeWindow 的 SurfaceTexture/Surface 映射

opengl - 如何计算法线矩阵?

opengl - 什么是正确的 Gamma 校正函数?

android - 你如何将opengl纹理转换回android中的位图?