我正在尝试将OpenCL与OpenGL互操作一起使用。在GPU上计算路径跟踪算法,然后将GL纹理绘制为四边形。在Intel CPU上可以正常工作,但是当我尝试在GTX 970上运行时,在解锁该GL纹理时会出现段错误。 Dunno(如果是原因)或内核正在运行。我让代码说明一切。我正在使用OpenCL C++包装器btw。

GL纹理创建

glGenTextures(1, &texture);
glBindTexture(GL_TEXTURE_2D, texture);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, framebuffer);
glBindTexture(GL_TEXTURE_2D, 0); //Unbind texture

CL纹理分配
m_textureCL = cl::ImageGL(m_context,
        CL_MEM_READ_WRITE,
        GL_TEXTURE_2D,
        0,
        texture,
        &errCode);

RunKernel函数
//-----------------------------------------------------------------------------
//  Lock texture
//-----------------------------------------------------------------------------
std::vector<cl::Memory> glObjects; //Create vector of GL objects to lock
glObjects.push_back(m_textureCL); //Add created CL texture buffer
glFlush(); //Flush GL queue

errCode = m_cmdQueue.enqueueAcquireGLObjects(&glObjects, NULL, NULL);
if(errCode != CL_SUCCESS) {
    std::cerr << "Error locking texture" << errCode << std::endl;
    return errCode;
}
//-----------------------------------------------------------------------------

//-----------------------------------------------------------------------------
//  Run queue
//-----------------------------------------------------------------------------
errCode = m_cmdQueue.enqueueNDRangeKernel(
        m_kernel,
        cl::NullRange,
        cl::NDRange(height*width),
        cl::NullRange,
        NULL,
        NULL);
if(errCode != CL_SUCCESS) {
    std::cerr << "Error running queue: " << errCode << std::endl;
    return errCode;
}
//---------------------------------------


//-----------------------------------------------------------------------------
//  Unlock
//-----------------------------------------------------------------------------
errCode = m_cmdQueue.enqueueReleaseGLObjects(&glObjects, NULL, NULL);
if(errCode != CL_SUCCESS) {
    std::cerr << "Error unlocking texture: " << errCode << std::endl;
    return errCode;
} <<------ Here's where segfault occurs, can't get past this point

内核功能定义
__kernel void RadianceGPU (
    __write_only image2d_t texture,
    other_stuff...)

在内核中写入纹理
write_imagef(
        texture,
        (int2)(x, height-y-1),
        (float4)(
            clamp(framebuffer[id].x, 0.0f, 1.0f),
            clamp(framebuffer[id].y, 0.0f, 1.0f),
            clamp(framebuffer[id].z, 0.0f, 1.0f),
            1.0f) * 1.0f);

有趣的是,尽管纹理为UNSIGNED_BYTE,但write_imagef()仍然有效。

编辑:
因此,我终于弄清楚是什么原因导致了问题。创建CL属性时设置了错误的显示。我刚刚从GLFW粘贴了窗口,这在Nvidia驱动程序上引起了问题。您需要使用glxGetCurrentDisplay或glfwGetX11Display。这样可以修复段错误。

最佳答案

我不确定这是否是您的问题,但是无论如何我都会试一试。

您尚未以可移植的方式同步对glObjects的访问。从OpenCL 1.1:



基本上,glFinish是便携式行为所必需的。

在下面已引用的段落中,可能有更多有趣的信息:



这是引用来自以下文件的链接:https://www.khronos.org/registry/cl/specs/opencl-1.1.pdf#nameddest=section-9.8.6

关于c++ - OpenCL/OpenGL互操作性纹理段,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/36827145/

10-16 16:43