void OCLManagerMultiPlatform::configure(base::OCLOperationConfiguration &configuration, bool useConfiguration) { cl_int err; // determine number of available OpenCL platforms cl_uint platformCount; err = clGetPlatformIDs(0, nullptr, &platformCount); if (err != CL_SUCCESS) { std::stringstream errorString; errorString << "OCL Error: Unable to get number of OpenCL platforms. Error Code: " << err << std::endl; throw SGPP::base::operation_exception(errorString.str()); } if (verbose) { std::cout << "OCL Info: " << platformCount << " OpenCL platforms have been found" << std::endl; } // get available platforms std::vector<cl_platform_id> platformIds(platformCount); err = clGetPlatformIDs(platformCount, platformIds.data(), nullptr); if (err != CL_SUCCESS) { std::stringstream errorString; errorString << "OCL Error: Unable to get Platform ID. Error Code: " << err << std::endl; throw SGPP::base::operation_exception(errorString.str()); } for (size_t i = 0; i < platformCount; i++) { this->configurePlatform(platformIds[i], *parameters, useConfiguration); } }
platform_vector getPlatformsIDs() { const platform_vector::size_type maxPlatforms = 10; platform_vector platformIds(maxPlatforms); cl_uint numOfPlatforms = 0; cl_int ret = clGetPlatformIDs(maxPlatforms, platformIds.data(), &numOfPlatforms); if (ret != CL_SUCCESS) { std::cerr << "Failed to get platform ids." << std::endl; numOfPlatforms = 0; } platformIds.resize(numOfPlatforms); return platformIds; }
/// // functions for preparing create opencl program, contains CreateContext, CreateProgram, CreateCommandQueue, CreateMemBuffer, and Cleanup // Create an OpenCL context on the first available GPU platform. cl_context CreateContext() { cl_context context = NULL; cl_uint platformIdCount = 0; cl_int errNum; #ifndef POCL_HSA // get number of platforms clGetPlatformIDs (0, NULL, &platformIdCount); std::vector<cl_platform_id> platformIds(platformIdCount); clGetPlatformIDs (platformIdCount, platformIds.data(), NULL); // In this example, first platform is a CPU, the second one is a GPU. we just choose the first available device. cl_context_properties contextProperties[] = { CL_CONTEXT_PLATFORM, (cl_context_properties)platformIds[1], 0 }; context = clCreateContextFromType(contextProperties, CL_DEVICE_TYPE_GPU, NULL, NULL, &errNum); if (errNum != CL_SUCCESS) { std::cout << "Could not create GPU context, trying CPU..." << std::endl; context = clCreateContextFromType(contextProperties, CL_DEVICE_TYPE_CPU, NULL, NULL, &errNum); if (errNum != CL_SUCCESS) { std::cerr << "Failed to create an OpenCL GPU or CPU context." << std::endl; return NULL; } } #else context = poclu_create_any_context(); #endif return context; }
// Intitialize OpenCL //***************************************************************************** void createCLContext(int PLATFORM, int DEVICE) { cl_int error; cl_uint platformIdCount = 0; clGetPlatformIDs (0, NULL, &platformIdCount); std::vector<cl_platform_id> platformIds (platformIdCount); clGetPlatformIDs (platformIdCount, platformIds.data(), NULL); cpPlatform = platformIds[PLATFORM]; // Get the number of GPU devices available to the platform ciErrNum = clGetDeviceIDs(cpPlatform, CL_DEVICE_TYPE_GPU, 0, NULL, &uiDevCount); printf("Number of GPU devices is %i \n",uiDevCount); //oclCheckErrorEX(ciErrNum, CL_SUCCESS, pCleanup); // Create the device list unsigned int uiEndDev = uiDevCount - 1; cdDevices = new cl_device_id [uiDevCount]; ciErrNum = clGetDeviceIDs(cpPlatform, CL_DEVICE_TYPE_GPU, uiDevCount, cdDevices, NULL); // Get device name char* value; size_t valueSize; clGetDeviceInfo(cdDevices[DEVICE], CL_DEVICE_NAME, 0, NULL, &valueSize); value = (char*) malloc(valueSize); clGetDeviceInfo(cdDevices[DEVICE], CL_DEVICE_NAME, valueSize, value, NULL); printf("Devide name is %s \n",value); free(value); // Check if the requested device (or any of the devices if none requested) supports context sharing with OpenGL if(g_glInterop) { bool bSharingSupported = false; for (unsigned int i = uiDeviceUsed; (!bSharingSupported && (i <= uiEndDev)); ++i) { size_t extensionSize; ciErrNum = clGetDeviceInfo(cdDevices[i], CL_DEVICE_EXTENSIONS, 0, NULL, &extensionSize ); //oclCheckErrorEX(ciErrNum, CL_SUCCESS, pCleanup); if(extensionSize > 0) { char* extensions = (char*)malloc(extensionSize); ciErrNum = clGetDeviceInfo(cdDevices[i], CL_DEVICE_EXTENSIONS, extensionSize, extensions, &extensionSize); printf("Get device info error is %i \n",ciErrNum); //oclCheckErrorEX(ciErrNum, CL_SUCCESS, pCleanup); std::string stdDevString(extensions); free(extensions); size_t szOldPos = 0; size_t szSpacePos = stdDevString.find(' ', szOldPos); // extensions string is space delimited while (szSpacePos != stdDevString.npos) { if( strcmp(GL_SHARING_EXTENSION, stdDevString.substr(szOldPos, szSpacePos - szOldPos).c_str()) == 0 ) { // Device supports context sharing with OpenGL uiDeviceUsed = i; bSharingSupported = true; printf("Sharing supported!\n"); break; } do { szOldPos = szSpacePos + 1; szSpacePos = stdDevString.find(' ', szOldPos); } while (szSpacePos == szOldPos); } } } // Define OS-specific context properties and create the OpenCL context cl_context_properties props[] = { CL_GL_CONTEXT_KHR, (cl_context_properties)glXGetCurrentContext(), CL_GLX_DISPLAY_KHR, (cl_context_properties)glXGetCurrentDisplay(), CL_CONTEXT_PLATFORM, (cl_context_properties)cpPlatform, 0 }; cxGPUContext = clCreateContext(props, 1, &cdDevices[uiDeviceUsed], NULL, NULL, &ciErrNum); printf("Create context error is %i\n",ciErrNum); } else { // No GL interop cl_context_properties props[] = {CL_CONTEXT_PLATFORM, (cl_context_properties)PLATFORM, 0}; cxGPUContext = clCreateContext(props, 1, &cdDevices[uiDeviceUsed], NULL, NULL, &error); printf("Error 7 is %i \n",error); g_glInterop = false; } //oclCheckErrorEX(ciErrNum, CL_SUCCESS, pCleanup); }
cl_int cl_runner::init_cl() { if (m_bInitCL) return CL_SUCCESS; // Error code cl_int err_num = CL_SUCCESS; cl_uint num_platforms = 0; size_t i; // Get the number of PlatformIDs // /* Additional Error Codes */ // CL_PLATFORM_NOT_FOUND_KHR -1001 err_num = clGetPlatformIDs(0, 0, &num_platforms); if (err_num != CL_SUCCESS) { DOL_TRACE("cl_runner: Unable to get platforms \n"); //std::cerr << "Unable to get platforms" << endl; return err_num; } // Get the PlatformIDs std::vector<cl_platform_id> platformIds(num_platforms + 1); for (i = 0; i < num_platforms; ++i) platformIds[i] = NULL; // err_num = clGetPlatformIDs(num_platforms, &m_clPlatformId, &num_platforms); err_num = clGetPlatformIDs(num_platforms, &platformIds[0], &num_platforms); if (err_num != CL_SUCCESS) { DOL_TRACE("cl_runner: Error getting platform id \n"); return err_num; } if (num_platforms > 0) { char pbuf[256]; for (i = 0; i < num_platforms; ++i) { err_num = clGetPlatformInfo(platformIds[i], CL_PLATFORM_VENDOR, sizeof(pbuf), pbuf, NULL); if (err_num != CL_SUCCESS) { DOL_TRACE("Error getting platform vendor info \n"); return err_num; } m_clPlatformId = platformIds[i]; if (!strcmp(pbuf, "Advanced Micro Devices, Inc.")) { printf("cl_runner: Find platform: %s\n\n", pbuf); break; } else printf("cl_runner: Find unknown platform: %s\n\n", pbuf); } } else { printf("cl_runner: num_platforms = %d\n\n", num_platforms); } //m_clPlatformId = platformIds[0]; #if 0 cl_device_id deviceIDs[MAX_COPROC_INSTANCES] = { NULL }; size_t num_devices = 0; // Get the DeviceIDs // #define CL_DEVICE_NOT_FOUND -1 //err_num = clGetDeviceIDs(m_clPlatformId, CL_DEVICE_TYPE_GPU, 1, &m_clDeviceId, NULL); err_num = clGetDeviceIDs(m_clPlatformId, CL_DEVICE_TYPE_DEFAULT, 1, &m_clDeviceId, NULL); //err_num = clGetDeviceIDs(m_clPlatformId, CL_DEVICE_TYPE_ACCELERATOR, 1, &m_clDeviceId, NULL); //err_num = clGetDeviceIDs(m_clPlatformId, CL_DEVICE_TYPE_DEFAULT, MAX_COPROC_INSTANCES, deviceIDs, &num_devices); //m_clDeviceId = deviceIDs[0]; if (err_num != CL_SUCCESS) { DOL_TRACE("cl_runner: Error getting device ids \n"); return err_num; } // Create the Context m_clContext = clCreateContext(0, 1, &m_clDeviceId, NULL, NULL, &err_num); if (err_num != CL_SUCCESS) { DOL_TRACE("cl_runner: Error creating context \n"); return err_num; } #else /* * If we could find our platform, use it. * Otherwise use just available platform. */ cl_context_properties cps[3] = { CL_CONTEXT_PLATFORM, (cl_context_properties)m_clPlatformId, 0 }; // Create the Context m_clContext = clCreateContextFromType(cps, CL_DEVICE_TYPE_DEFAULT, //CL_DEVICE_TYPE_ALL, //CL_DEVICE_TYPE_CPU, //CL_DEVICE_TYPE_GPU, NULL, NULL, &err_num); if (err_num != CL_SUCCESS) { DOL_TRACE("cl_runner: Error creating context \n"); return err_num; } #endif // // Problems imstalling ATI Stream SDK on AT HD 4850 // // FindNumDevices(), From: http://devgurus.amd.com/thread/131594 // size_t num_devices, cb, cb_devices = 0; // Get number of contect devices - first step err_num = clGetContextInfo(m_clContext, CL_CONTEXT_DEVICES, 0, NULL, &cb_devices); if (err_num != CL_SUCCESS) { DOL_TRACE("cl_runner: Error getting context info \n"); return err_num; } num_devices = cb_devices / sizeof(cl_device_id); std::vector<cl_device_id> devices(num_devices + 1); for (i = 0; i <= num_devices; ++i) devices[i] = NULL; // Get number of contect devices - second step err_num = clGetContextInfo(m_clContext, CL_CONTEXT_DEVICES, cb_devices, &devices[0], 0); if (err_num != CL_SUCCESS) { DOL_TRACE("cl_runner: Error getting context info \n"); return err_num; } std::string dev_name; for (i = 0; i < num_devices; ++i) { cb = 0; // Get device name - first step err_num = clGetDeviceInfo(devices[i], CL_DEVICE_NAME, 0, NULL, &cb); if (err_num == CL_SUCCESS) { dev_name = ""; dev_name.resize(cb); // Get device name - second step err_num = clGetDeviceInfo(devices[i], CL_DEVICE_NAME, cb, &dev_name[0], 0); if (err_num == CL_SUCCESS) std::cout << "cl_runner: Device Name: " << dev_name.c_str() << endl; else std::cout << "cl_runner: Device Name: unknown device name." << endl; } } if (num_devices > 0) { m_clDeviceId = devices[0]; for (i = 1; i < num_devices; ++i) { cl_device_id deviceId = devices[i]; #if defined(CL_VERSION_1_1) || defined(CL_VERSION_1_2) if (deviceId) clReleaseDevice(deviceId); #endif } } else { DOL_TRACE1("cl_runner: num_devices = %d\n", num_devices); } // Create the command-queue m_clCmdQueue = clCreateCommandQueue(m_clContext, m_clDeviceId, 0, &err_num); if (err_num != CL_SUCCESS || m_clCmdQueue == NULL) { DOL_TRACE("cl_runner: Error creating command queue \n"); return err_num; } m_bInitCL = true; return CL_SUCCESS; }