diff --git a/sycl/source/detail/platform_impl.cpp b/sycl/source/detail/platform_impl.cpp index a60f20d5dd78e..a3c14d03f2bd9 100644 --- a/sycl/source/detail/platform_impl.cpp +++ b/sycl/source/detail/platform_impl.cpp @@ -88,33 +88,6 @@ context_impl &platform_impl::khr_get_default_context() { return *It->second; } -static bool IsBannedPlatform(platform Platform) { - // The NVIDIA OpenCL platform is currently not compatible with DPC++ - // since it is only 1.2 but gets selected by default in many systems - // There is also no support on the PTX backend for OpenCL consumption, - // and there have been some internal reports. - // To avoid problems on default users and deployment of DPC++ on platforms - // where CUDA is available, the OpenCL support is disabled. - // - // There is also no support for the AMD HSA backend for OpenCL consumption, - // as well as reported problems with device queries, so AMD OpenCL support - // is disabled as well. - // - auto IsMatchingOpenCL = [](platform Platform, const std::string_view name) { - const bool HasNameMatch = Platform.get_info().find( - name) != std::string::npos; - const auto Backend = detail::getSyclObjImpl(Platform)->getBackend(); - const bool IsMatchingOCL = (HasNameMatch && Backend == backend::opencl); - if (detail::ur::trace(detail::ur::TraceLevel::TRACE_ALL) && IsMatchingOCL) { - std::cout << "SYCL_UR_TRACE: " << name - << " OpenCL platform found but is not compatible." << std::endl; - } - return IsMatchingOCL; - }; - return IsMatchingOpenCL(Platform, "NVIDIA CUDA") || - IsMatchingOpenCL(Platform, "AMD Accelerated Parallel Processing"); -} - // Get the vector of platforms supported by a given UR adapter // replace uses of this with a helper in adapter object, the adapter // objects will own the ur adapter handles and they'll need to pass them to @@ -132,25 +105,13 @@ std::vector platform_impl::getAdapterPlatforms(adapter_impl &Adapter, for (const auto &UrPlatform : UrPlatforms) { platform Platform = detail::createSyclObjFromImpl( getOrMakePlatformImpl(UrPlatform, Adapter)); - const bool IsBanned = IsBannedPlatform(Platform); - bool HasAnyDevices = false; - - // Platform.get_devices() increments the device count for the platform - // and if the platform is banned (like OpenCL for AMD), it can cause - // incorrect device numbering, when used with ONEAPI_DEVICE_SELECTOR. - if (!IsBanned) - HasAnyDevices = !Platform.get_devices(info::device_type::all).empty(); + bool HasAnyDevices = !Platform.get_devices(info::device_type::all).empty(); if (!Supported) { - if (IsBanned || !HasAnyDevices) { + if (!HasAnyDevices) { Platforms.push_back(std::move(Platform)); } } else { - if (IsBanned) { - continue; // bail as early as possible, otherwise banned platforms may - // mess up device counting - } - // The SYCL spec says that a platform has one or more devices. ( SYCL // 2020 4.6.2 ) If we have an empty platform, we don't report it back // from platform::get_platforms(). diff --git a/unified-runtime/source/adapters/opencl/platform.cpp b/unified-runtime/source/adapters/opencl/platform.cpp index b1140aadd43c4..5bf14fa8b3a16 100644 --- a/unified-runtime/source/adapters/opencl/platform.cpp +++ b/unified-runtime/source/adapters/opencl/platform.cpp @@ -30,6 +30,50 @@ static cl_int mapURPlatformInfoToCL(ur_platform_info_t URPropName) { } } +static bool isBannedOpenCLPlatform(cl_platform_id platform) { + size_t nameSize = 0; + cl_int res = + clGetPlatformInfo(platform, CL_PLATFORM_NAME, 0, nullptr, &nameSize); + if (res != CL_SUCCESS || nameSize == 0) { + return false; + } + + std::string name(nameSize, '\0'); + res = clGetPlatformInfo(platform, CL_PLATFORM_NAME, nameSize, name.data(), + nullptr); + if (res != CL_SUCCESS) { + return false; + } + + // The NVIDIA OpenCL platform is currently not compatible with DPC++ + // since it is only 1.2 but gets selected by default in many systems. + // There is also no support on the PTX backend for OpenCL consumption. + // + // There is also no support for the AMD HSA backend for OpenCL consumption, + // as well as reported problems with device queries, so AMD OpenCL support + // is disabled as well. + bool isBanned = + name.find("NVIDIA CUDA") != std::string::npos || + name.find("AMD Accelerated Parallel Processing") != std::string::npos; + + return isBanned; +} + +static bool isBannedOpenCLDevice(cl_device_id device) { + cl_device_type deviceType = 0; + cl_int res = clGetDeviceInfo(device, CL_DEVICE_TYPE, sizeof(cl_device_type), + &deviceType, nullptr); + if (res != CL_SUCCESS) { + return false; + } + + // Filter out FPGA accelerator devices as their usage with OpenCL adapter is + // deprecated + bool isBanned = (deviceType & CL_DEVICE_TYPE_ACCELERATOR) != 0; + + return isBanned; +} + UR_DLLEXPORT ur_result_t UR_APICALL urPlatformGetInfo(ur_platform_handle_t hPlatform, ur_platform_info_t propName, size_t propSize, void *pPropValue, size_t *pSizeRet) { @@ -102,14 +146,26 @@ urPlatformGet(ur_adapter_handle_t, uint32_t NumEntries, CLPlatforms.data(), nullptr); CL_RETURN_ON_FAILURE(Res); + // Filter out banned platforms + std::vector FilteredPlatforms; + for (uint32_t i = 0; i < NumPlatforms; i++) { + if (!isBannedOpenCLPlatform(CLPlatforms[i])) { + FilteredPlatforms.push_back(CLPlatforms[i]); + } + } + try { - for (uint32_t i = 0; i < NumPlatforms; i++) { - auto URPlatform = - std::make_unique(CLPlatforms[i]); + for (auto &Platform : FilteredPlatforms) { + auto URPlatform = std::make_unique(Platform); UR_RETURN_ON_FAILURE(URPlatform->InitDevices()); - Adapter->URPlatforms.emplace_back(URPlatform.release()); + // Only add platforms that have devices, especially in case all + // devices are banned + if (!URPlatform->Devices.empty()) { + Adapter->URPlatforms.emplace_back(URPlatform.release()); + } } - Adapter->NumPlatforms = NumPlatforms; + Adapter->NumPlatforms = + static_cast(Adapter->URPlatforms.size()); } catch (std::bad_alloc &) { return UR_RESULT_ERROR_OUT_OF_RESOURCES; } catch (...) { @@ -217,11 +273,19 @@ ur_result_t ur_platform_handle_t_::InitDevices() { CL_RETURN_ON_FAILURE(Res); + // Filter out banned devices + std::vector FilteredDevices; + for (uint32_t i = 0; i < DeviceNum; i++) { + if (!isBannedOpenCLDevice(CLDevices[i])) { + FilteredDevices.push_back(CLDevices[i]); + } + } + try { - Devices.resize(DeviceNum); - for (size_t i = 0; i < DeviceNum; i++) { - Devices[i] = - std::make_unique(CLDevices[i], this, nullptr); + Devices.resize(FilteredDevices.size()); + for (size_t i = 0; i < FilteredDevices.size(); i++) { + Devices[i] = std::make_unique(FilteredDevices[i], + this, nullptr); } } catch (std::bad_alloc &) { return UR_RESULT_ERROR_OUT_OF_RESOURCES;