使用glGetString()和linux下的pthreads进行分段错误

使用glGetString()和linux下的pthreads进行分段错误,第1张

概述我正在尝试在后台线程中加载纹理,以帮助加快我的应用程序. 我们使用的堆栈是Linux上的C/C++,使用gcc进行编译.我们正在使用OpenGL,GLUT和GLEW.我们一直在使用libSOIL进行纹理加载. 最终,使用libSOIL启动纹理加载失败,因为它遇到导致段错误的glGetString()调用.为了缩小问题范围,我编写了一个非常简单的OpenGL应用程序来重现行为.下面的代码示例不应该“ 我正在尝试在后台线程中加载纹理,以帮助加快我的应用程序.

我们使用的堆栈是Linux上的C/C++,使用gcc进行编译.我们正在使用OpenGL,gluT和GLEW.我们一直在使用libSOIL进行纹理加载.

最终,使用libSOIL启动纹理加载失败,因为它遇到导致段错误的glGetString()调用.为了缩小问题范围,我编写了一个非常简单的OpenGL应用程序来重现行为.下面的代码示例不应该“做任何事情”,但它也不应该是段错误.如果我知道它为什么会这样做,我理论上可以重写libSOIL,以便它在一个pthreaded环境中运行.

voID *glPthreadTest( voID* arg ) {  glGetString( GL_EXTENSIONS ); //SIGSEGV  return NulL;}int main( int argc,char **argv ) {  glutinit( &argc,argv );  glutinitdisplayMode( gluT_RGBA | gluT_DOUBLE | gluT_DEPTH );  glewInit();  glGetString( GL_EXTENSIONS ); // Does not cause SIGSEGV   pthread_t ID;  if (pthread_create( &ID,NulL,glPthreadTest,(voID*)NulL ) != 0)    fprintf( stderr,"phtread_create glPthreadTest Failed.\n" );  glutMainLoop();  return EXIT_SUCCESS;}

来自gdb的此应用程序的示例堆栈跟踪如下所示:

#0  0x00000038492f86e9 in glGetString () from /usr/lib64/nvIDia/libGL.so.1No symbol table info available.#1  0x0000000000404425 in glPthreadTest (arg=0x0) at sf.cpp:168No locals.#2  0x0000003148e07d15 in start_thread (arg=0x7ffff7b36700) at pthread_create.c:308        __res = <optimized out>        pd = 0x7ffff7b36700        Now = <optimized out>        unwind_buf = {cancel_jmp_buf = {{jmp_buf = {140737349117696,-5802871742031723458,1,211665686528,140737349117696,5802854601940796478,-5829171783283899330},mask_was_saved = 0}},priv = {pad = {0x0,0x0,0x0},data = {prev = 0x0,cleanup = 0x0,canceltype = 0}}}        not_first_call = 0        pagesize_m1 = <optimized out>        sp = <optimized out>        freesize = <optimized out>#3  0x00000031486f246d in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:114No locals.

您会注意到我正在使用nvIDia libGL实现,但这也与Ubuntu用于Intel HD显卡的mesa libgl相同.

可能出现问题的任何提示,或者如何进一步调查以了解发生了什么?

编辑:以下是我的示例测试的#includes和编译字符串:

#include <SOIL.h>#include <GL/glew.h>#include <GL/freeglut.h>#include <GL/freeglut_ext.h>#include <signal.h>#include <pthread.h>#include <cstdio>

g -Wall -pedantic -I /usr/include / SOIL -O0 -ggdb -o sf sf.cpp -lSOIL -pthread -lGL -lglu -lGLEW -lglut -lX11

解决方法 为了使任何OpenGL调用正常运行,它需要一个OpenGL上下文.使用窗口系统绑定调用(如wglCreateContext或类似的)创建上下文.在创建上下文之后,它需要“变为当前”,这意味着将上下文与当前执行线程相关联.这是通过另一个特定于窗口系统的调用来完成的(如用于Microsoft windows的wglMakeCurrent或用于X windows的glXMakeCurrent). gluT从您那里抽象出所有这些复杂性,在您调用glutCreateWindow时执行所有这些 *** 作.

现在,要知道的一个重要规则是,任何时候只有一个OpenGL上下文可以是当前执行线程的当前.因此,在OP的原始示例中,如果她/他可以在他们创建的Pthread中使上下文变为当前,那么上下文将在主线程中丢失.保持所有这些一致性的方法是仅在单个线程中使用单个上下文. (OpenGL上下文可以共享数据,但gluT既不公开,也不使用窗口系统上下文创建调用).

在您的情况下,gluT可能不允许访问您真正需要的内容(即OpenGL上下文),以使其在另一个线程中保持最新状态.您需要自己创建和管理OpenGL上下文.

总结

以上是内存溢出为你收集整理的使用glGetString()和linux下的pthreads进行分段错误全部内容,希望文章能够帮你解决使用glGetString()和linux下的pthreads进行分段错误所遇到的程序开发问题。

如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。

欢迎分享,转载请注明来源:内存溢出

原文地址:https://54852.com/yw/1027600.html

(0)
打赏 微信扫一扫微信扫一扫 支付宝扫一扫支付宝扫一扫
上一篇 2022-05-23
下一篇2022-05-23

发表评论

登录后才能评论

评论列表(0条)

    保存