glBufferData分配的内存何时释放? [英] When is the memory allocated by glBufferData freed?
问题描述
假设我为统一缓冲区分配内存,如下所示:
Let's say I allocate memory for a uniform buffer, like so:
GLuint length(0x1000);
GLuint myBuffer;
glGenBuffers(1, &myBuffer);
glBindBuffer(GL_UNIFORM_BUFFER, myBuffer);
glBufferData(GL_UNIFORM_BUFFER, length, NULL, GL_STATIC_DRAW);
使用完缓冲区后,我想确保该内存可再次用于其他缓冲区.调用glDeleteBuffers(1,&myBuffer)
是否足以实现这一目标?因为我的直觉告诉我应该为此呼叫glBufferData
(例如OpenGL 4中的glInvalidateBufferData
),但在glBufferData
的文档中完全没有提及任何类型的内容(
When I am done using the buffer, I would like to make sure that the memory is available again for other buffers. Is it sufficient to call glDeleteBuffers(1,&myBuffer)
to achieve that? Because my gut feeling tells me there should be a call symmetrical to glBufferData
for that
(like glInvalidateBufferData
in OpenGL 4), but nothing of the kind is mentioned in the documentation for glBufferData
at all (http://www.opengl.org/sdk/docs/man/xhtml/glBufferData.xml)
推荐答案
不是嗡嗡声,但是诸如顶点数组对象之类的容器对象使该讨论变得更加复杂.
Not to be a buzz kill, but container objects such as Vertex Array Objects significantly complicate this discussion.
通常,当您删除缓冲区对象时,会发生两个关键事件,从而可以回收内存:
Normally, when you delete a buffer object two key things happen that allow the memory to be reclaimed:
- 其名称(
GLuint
ID)被释放以立即重用 - 该对象已从 当前活动 上下文中解除绑定
- Its name (
GLuint
ID) is freed up for reuse immediately - The object is unbound from the currently active context
有一个需要注意的隐藏警告:
- 直到在 任何上下文 中没有没有剩余引用,该数据存储才真正释放.
- The data store is not actually freed until there are no remaining references to the object in any context.
There is a hidden caveat that needs to be observed:
当删除绑定到顶点数组对象"的顶点缓冲区"对象并且该顶点数组对象"当前未绑定时,不会出现在项目符号点2中讨论的行为.发生的事情是释放了名称,但是VAO继续引用名称(现在无效)和数据存储区(仍然存在).在删除此顶点数组对象"或更改绑定使其不再引用原始缓冲区对象之前,不会回收缓冲区对象的内存.
When you delete a Vertex Buffer Object that is bound to a Vertex Array Object and that Vertex Array Object is not currently bound, the behavior discussed in bullet point 2 does not occur. What happens is the name is freed up, but the VAO continues to reference both the name (which is now invalid) and the data store (which continues to exist). The memory for the buffer object will not be reclaimed until this Vertex Array Object is deleted, or the binding is changed so that it no longer references the original buffer object.
有关上述内容的更权威的解释,建议您阅读
For a more authoritative explanation of the above, I suggest you read Section 5.1.2 and Section 5.1.3 of the OpenGL 4.4 core spec. I will list the most relevant parts of both below.
删除缓冲区,纹理或渲染缓冲区对象后,该对象将不受其在当前上下文中绑定到的任何绑定点的绑定,并与绑定到当前上下文的容器对象的任何附件分离,如以下内容所述: DeleteBuffers,DeleteTextures和DeleteRenderbuffers.如果以其他相关状态(例如BindBufferRange中的缓冲区范围或FramebufferTexture或BindImageTexture中的选定级别和图层信息)建立了对象绑定,则该状态不受自动取消绑定的影响.在其他情况下的绑定点不受影响. 未绑定容器对象的附件(例如删除未绑定到上下文的顶点数组对象上附加的缓冲区的删除)不会受到影响,并继续充当已删除对象的引用,如接下来的部分.
When a buffer, texture, or renderbuffer object is deleted, it is unbound from any bind points it is bound to in the current context, and detached from any attachments of container objects that are bound to the current context, as described for DeleteBuffers, DeleteTextures, and DeleteRenderbuffers. If the object binding was established with other related state (such as a buffer range in BindBufferRange or selected level and layer information in FramebufferTexture or BindImageTexture), that state is not affected by the automatic unbind. Bind points in other contexts are not affected. Attachments to unbound container objects, such as deletion of a buffer attached to a vertex array object which is not bound to the context, are not affected and continue to act as references on the deleted object, as described in the following section.
5.1.3删除的对象和对象名称生存期
[...] GL将不会回收支持已删除对象的基础存储,直到 所有引用 从容器对象附着点,上下文绑定点到对象,或视图已删除.
[...] The underlying storage backing a deleted object will not be reclaimed by the GL until all references to the object from container object attachment points, context binding points, or views are removed.
注意::此行为适用于OpenGL中的所有容器对象,除非取消了对资源的所有引用,否则不会回收内存.从长远来看,熟悉要删除的参考文件的必要条件(请参阅: 5.1.2 ).
NOTE: This behavior applies to all container objects in OpenGL, memory is not reclaimed until all references to a resource are eliminated. Familiarizing yourself with the necessary conditions (see: 5.1.2) for references to be removed will serve you well in the long-run.
这篇关于glBufferData分配的内存何时释放?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!