我已经使用EGL API编写了一个库。该库具有“ init”和“ deinit”功能。 在'init'函数中,用户传递的本机窗口ID使用该本机窗口ID创建了eglCreateWindowSurface。在'deinit'函数中,使用eglDestroySurface破坏表面。
现在,用户再次调用“ init”函数来创建另一个eglCreateWindowSurface,但是他传递了与先前相同的窗口ID(因为他尚未关闭窗口),此处eglCreateWindowSurface失败,错误为EGL_BAD_ALLOC。
我阅读了EGL规范
如果已经有与赢相关的EGLSurface(由于 先前的eglCreateWindowSurface调用),然后出现EGL_BAD_ALLOC错误 生成
当我已经使用eglDestroySurface破坏了曲面时,为什么没有使用相同的窗口ID再次创建曲面,所以我没有得到这个。
xserver重新使用先前关闭的窗口ID时会发生此问题吗?
答案 0 :(得分:0)
eglDestroySurface
是否返回EGL_TRUE值?
如果不是,则销毁可能失败。
请注意,如果没有足够的资源来分配新表面,也可能会生成EGL_BAD_ALLOC。
答案 1 :(得分:0)
即使EGLSurface
或eglDestroySurface
之后,您的eglTerminate
可能也不会被销毁。您可能称为eglMakeCurrent( display, surface... context)
-这将您的表面绑定到GL上下文的默认帧缓冲区。您需要取消绑定才能真正删除表面。调用eglMakeCurrent(display, EGL_NO_SURFACE... EGL_NO_CONTEXT)
-这导致活动线程释放上下文和表面。现在,您将发现EGL忘记/删除了表面,可以重用Window ID。 eglReleaseThread
应该做同样的事情。
eglMakeCurrent(display,EGL_NO_SURFACE,EGL_NO_SURFACE,EGL_NO_CONTEXT);将取消绑定表面并允许将其删除,这不是立即进行的,eglMakeCurrent将在该上下文上导致glFlush。因此,可能需要一点时间来完成已调用的绘制并将图像解析到缓冲区。否则,GPU可能会崩溃。在eglMakeCurrent之前调用glFinish()以确保完成,或创建fence并等待它。在eglMakeCurrent(... EGL_NO_SURFACE ...)之前或之后调用eglDeleteSurface都没有关系,但是所有gl命令必须在eglMakeCurrent(... EGL_NO_SURFACE ...,EGL_NO_CONTEXT)之前发生。因为这不会使上下文成为当前上下文,并且没有当前上下文也不会执行gl命令。
您可以尝试调用eglGetCurrentContext和eglGetCurrentSurface来检查表面是否仍然存在-您得到的不是EGL_NO_SURFACE句柄。但是在eglDeleteSurface之后,表面句柄绝对没有用。请参阅EGL规范1.5的3.7.4节-但正如我上面所说,它的存在仅是因为它绑定到当前上下文。参见第3.7.3节