使用GPU设备OpenCL程序执行失败

时间:2013-12-03 13:16:48

标签: opencl

我是OpenCL的初学者。为了学习库的基础知识,我尝试在以下URL执行第一个程序:

https://www.olcf.ornl.gov/tutorials/opencl-vector-addition/

我以前链接了来自 NVIDIA GPU计算SDK 的openCL include和库,当然编译程序还可以。但是,如果我运行它,则clCreateContext函数内的执行失败。

// Bind to platform
err = clGetPlatformIDs(1, &cpPlatform, NULL);

// Get ID for the device
err = clGetDeviceIDs(cpPlatform, CL_DEVICE_TYPE_GPU, 1, &device_id, NULL);

// Create a context  
context = clCreateContext(0, 1, &device_id, NULL, NULL, &err);

问题来自上一个方法clGetDeviceIDs,它似乎感觉不到device_id变量(如果clGetDeviceIDs中的CL_DEVICE_TYPE_GPU标记为CL_DEVICE_TYPE_CPU的替换{{1}}该程序完美无缺)。不过,我的显卡驱动程序已更新。根据执行情况,我的计算机上似乎没有任何GPU设备。这很奇怪。你认为我的驱动程序不正确并且缺少依赖关系吗?我真的迷路了。有人能帮帮我吗?

非常感谢您的帮助。

2 个答案:

答案 0 :(得分:3)

您是否检查过以确保只定义了1个平台?

cl_uint nPlatforms;
cl_uint err = CL_SUCCESS;
err = clGetPlatformIDs(1, NULL, &nPlatforms);

如果有多个平台,您可以这样做:

cl_platform_id* platformID_Array;
platformID_Array = (cl_platform_id *)malloc(sizeof(cl_platform_id)*nPlatforms);
err = CL_SUCCESS;
err = clGetPlatformIDs(nPlatforms, platformID_Array, NULL);

然后检查姓名:

for (cl_uint i = 0; i < nPlatforms; i++) {
    size_t vendorSize;
    char* vendorCstring;
    err = clGetPlatformInfo(platformID_Array[i], CL_PLATFORM_VENDOR, 0, NULL, &vendorSize);
    vendorCstring = (char*)malloc(sizeof(char)*vendorSize);
    err = clGetPlatformInfo(platformID_Array[i], CL_PLATFORM_VENDOR, vendorSize, vendorCstring, NULL);
    printf("Platform name = %s\n",vendorCstring);
}

您也可以尝试:

err = clGetDeviceIDs(NULL, CL_DEVICE_TYPE_GPU, 1, &device_id, NULL); 

注意平台ID的NULL参数。在这种情况下,行为是实现定义的,因此您可以看到支持哪个设备。我怀疑你会得到一个CPU设备,但值得检查。

答案 1 :(得分:2)

如果您说,选项CL_DEVICE_TYPE_CPU适合您,则您获得的平台没有GPU设备。

您应该尝试其他平台,因为英特尔和nVIDIA设备位于不同的平台上。

您可以尝试err = clGetPlatformIDs(2, &cpPlatform, NULL);并获得两个平台而不是1,或者使用另一个更聪明的算法来查找所有可用平台上的有效GPU。

当然,这不是链接或编译问题,因为方法可以正常工作。

我会这样做:

// Num of platforms
int numplat;
err = clGetPlatformIDs(0, NULL, &numplat);

// Num of platforms
int cpPlat[numplat];
err = clGetPlatformIDs(numplat, &cpPlat, NULL);

// Get ID for the device
for(int i=0; i<numplat; i++){
    err = clGetDeviceIDs(cpPlatform[i], CL_DEVICE_TYPE_GPU, 1, &device_id, NULL);
    if (err == CL_SUCCESS )
       break;
}

// Create a context  
context = clCreateContext(0, 1, &device_id, NULL, NULL, &err);