如何在多GPU系统中根据PCI供应商,设备和总线ID将OpenCL设备与特定GPU相匹配?

时间:2011-09-01 21:22:51

标签: opencl gpu pci

我希望能够在由PCI ID识别的多GPU系统上将OpenCL设备与系统中的GPU相匹配。

例如,如果我的系统有多个GPU,可能来自不同的供应商,我可以通过枚举PCI总线列出设备。这给了我PCI供应商,设备和总线ID。如果我根据某些选择标准选择其中一个(GPU)PCI设备用于OpenCL计算,我该如何将其与OpenCL设备匹配?

我可以使用 clGetDeviceIDs()在OpenCL中枚举GPU设备,但没有明显的方法可以将OpenCL设备与PCI设备相匹配。 OpenCL函数 clGetDeviceInfo()提供对PCI供应商ID和设备名称的访问,但不提供对PCI设备或总线ID的访问。我可以尝试将PCI设备名称与OpenCL设备名称匹配,但是您可能有多个相同类型的设备,并且名称并不总是相同。

为什么这有必要?假设我知道程序X在GPU A上运行CUDA或其他东西。我想避免使用GPU A进行OpenCL操作,因此我选择GPU B.然后我需要弄清楚哪个OpenCL设备是GPU A,哪个是GPU B. PCI ID似乎是识别GPU设备的唯一一致且跨平台的方式。

BTW,CUDA API确实为您提供了PCI,总线和插槽ID(CU_DEVICE_ATTRIBUTE_PCI_BUS_ID,CU_DEVICE_ATTRIBUTE_PCI_DEVICE_ID),但CUDA仅适用于NVidia设备。

理想情况下,我需要使用C或C ++的解决方案。

5 个答案:

答案 0 :(得分:7)

这样做的方法是使用两个特定于供应商的扩展。对于AMD,您必须使用适用于Windows和Linux的CL_DEVICE_TOPOLOGY_AMD并返回PCIe总线ID,这对GPU来说是唯一的。在NVIDIA上,查询设备的CL_DEVICE_PCI_BUS_ID_NV。另见:https://anteru.net/2014/08/01/2483/

答案 1 :(得分:1)

不幸的是,由于openCL的抽象性,你所寻找的答案并不漂亮。

我发现可靠的唯一方法是在openCL中为平台+设备ID分配苛刻的工作负载,然后通过AMD的ADL和Nvidia的NVML等工具监控流程使用情况。即使像cgminer这样的成熟应用程序也存在这方面的问题,并且经常将openCL工作负载与卡指标混淆,以至于他们分配配置变量以手动更正它(“gpu-map”)。

我希望现在有一个更好的答案,因为通过openCL知道哪个设备位于端点后面会很棒!这可能会在未来发生变化,因为AMD正在努力将这一层添加到openCL中,正如阿森所指出的那样。

答案 2 :(得分:1)

似乎Anteru的答案是正确的,但前提是你运行的是linux / mac。 经过一些测试后,似乎Windows无法识别这些特定于供应商的扩展。 (我已经在Geforce GTX Titan和ATI Radeon R9上测试了它)

我的解决方案是使用clGetGLContextInfoKHR()函数(自openCL规范1.1起可用)和" CL_CURRENT_DEVICE_FOR_GL_CONTEXT_KHR"参数,这将确保您获得一个openCL设备ID,该ID与执行渲染的GPU相同。

是的,那不会给你物理总线插槽,但这将确保呈现的GPU与计算的GPU相同!

此外,假设一个人使用Nvidia Quadro卡,那么他可以使用wgl_nv_gpu_affinity来确保openGL访问特定的GPU,然后使用GL上下文&从它获取openCL设备ID。

答案 3 :(得分:0)

最新的AMD版本在Linux上有cl_device_topology_amd扩展,它将CL_DEVICE_TOPOLOGY_AMD选项添加到clGetDeviceInfo(),但这是一个非常狭窄的解决方案。

答案 4 :(得分:0)

我开发了一个库来做到这一点:让OpenCL模拟不要踩到彼此的脚趾。

您可以在此处找到它:https://github.com/nbigaouette/oclutils/

它首先枚举机器上每个平台的所有平台和每个设备。您选择所需的平台,它将选择最好的设备。我在我的工作站上使用3个nvidia卡:两个用于OpenCL计算的GTX 580和一个用于显示器的GT 210。同时运行两个模拟将分别在两个GTX上运行。没有干预。

还有一个很好的类可以保持两个缓冲区同步:一个在主机上,一个在设备上。调用OpenCL_Array :: Host_to_Device()和OpenCL_Array :: Device_to_Host()可以简单地来回传输。

适用于这些平台:

  • nvidia(仅限GPU)
  • amd(CPU和/或GPU)
  • intel(仅限CPU)
  • apple(CPU和/或GPU)

请注意,它不会让您选择使用哪个设备,但请为您选择一个。如果一个程序的两个实例使用该库,他们将知道它并且不会在同一设备上运行(当然,如果你也有)。目前还无法检测视频卡是否用于显示器。但至少它是一个开始!