2015-04-23 135 views
4

创建不能释放纹理我遇到使用共享上下文的问题。 Ctx2创建与Ctx1共享。通过共享上下文

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

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

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

我曾尝试:

删除纹理THR2之前摧毁Ctx2;

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

回答

5

这听起来像预期的行为。

为了解释具有多个上下文的对象的生命周期,我将使用“池”一词来描述一组纹理。我不认为这个概念有通用的术语,所以这和任何东西都一样好。

尽管您可能通常会对上下文拥有的纹理进行图片处理,但实际上它们都属于一个池。只要你有一个单一的背景,这是一个学术上的差异。上下文拥有该​​池,该池拥有在上下文中创建的所有纹理。当上下文被破坏时,游泳池就会消失,反过来会破坏游泳池中的所有纹理。

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

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

因此,如果您确实想要删除纹理,则必须调用glDeleteTexture()。如果在上下文1或上下文2中进行此调用,则无关紧要。

删除共享纹理时存在一些细微方面,例如与纹理为FBO附件有关的问题,或与绑定时在一个上下文中被删除的纹理在另一种情况下。但是由于这不是这个问题的核心,而且有点复杂,所以我会参考规范中的细节(例如参见OpenGL 3.3规范第337页的D.1.2部分)。

+0

非常感谢。对不起,我是新来的OpenGL。在我的场景中,如果Thr2在调用MakeCurrent(0,0,0)后调用glDeleteTextures,会发生什么?根据你所说的,似乎没有什么会发生。我对吗? – CurtisGuo

+0

是的,您需要在拥有当前上下文的情况下进行所有OpenGL调用。否则他们不会有任何效果。 –

+0

如果(在GLX扩展中)glXMakeCurrent(dpy,0,0)被调用,并且GLXDrawable被销毁。它是唯一的方法来删除我创建一个新的GLXDrawable的纹理,并调用glXMakeCurrent(dpy,Ctx2,drawable)并删除纹理? – CurtisGuo