CUDA MPI 性能瓶颈

CUDA MPI performance bottleneck

我想澄清以下问题。我可以访问包含 Nvidia K40 GPU 和 Intel Xeon E5 processor.The 使用 lscpu 命令获得的处理器详细信息的单个节点如下:

Architecture:          x86_64
CPU op-mode(s):        32-bit, 64-bit
Byte Order:            Little Endian
CPU(s):                32
On-line CPU(s) list:   0-31
Thread(s) per core:    1
Core(s) per socket:    8
Socket(s):             4
NUMA node(s):          4
Vendor ID:             GenuineIntel
CPU family:            6
Model:                 62
Stepping:              4
CPU MHz:               2300.201
BogoMIPS:              4599.40
Virtualization:        VT-x
L1d cache:             32K
L1i cache:             32K
L2 cache:              256K
L3 cache:              16384K
NUMA node0 CPU(s):     0-7
NUMA node1 CPU(s):     8-15
NUMA node2 CPU(s):     16-23
NUMA node3 CPU(s):     24-31

我是 运行 一个 MPI 程序,它在处理器的 32 个内核之间分配工作。然后每个核心将一部分卸载到 GPU。在 运行 代码上,性能下降(执行时间增加)而不是下降?是不是因为内核对 GPU 的访问被序列化了?我只是想清楚地了解这个概念,因此我没有发布任何代码。我已经阅读了有关 CUDA aware MPI 的信息,但我认为它在这种情况下用处不大,因为它更适用于多节点情况。如果我错了,请纠正我。在这些情况下提高性能的可能方法是什么?

Is it because the the access to the GPU by the cores is getting serialized?

除非您采取特殊步骤,否则 GPU 上的序列化可能以某种方式对您观察​​到的内容有所贡献。 MPI 创建了多个 进程 。一种常见的策略是为每个 CPU 核心创建一个进程。来自不同进程(针对单个 GPU)的 CUDA activity 通常会在该 GPU 上序列化。

What are the possible ways to improve performance in situations like these?

CUDA MPS就是专门为这种情况设计的。它允许来自不同进程的 GPU activity 表现得好像它们都来自同一个进程。这可以有几种类型的效率优势(例如,GPU 上没有上下文切换,可以同时 运行 一些 GPU 内核,等等),但我不想夸大这个功能。它对您的情况是否有帮助以及有多大帮助只能通过尝试来确定。

如果您在 GPU 上投入大量工作(每个 MPI 级别),那么期望任意线性缩放当然是不合理的。一旦 GPU 工作饱和,如果 GPU 成为瓶颈,事情就不会变得更快,而且额外的 MPI 等级服务的额外开销实际上也可能减慢速度。

This presentation,从幻灯片 40 左右开始,在这种情况下提供了很多有关 MPS 的有用信息。

请注意,我在这里主要关注 GPU 方面。通常,当您将 MPI 等级计数从 1 缩放到系统上 "processors" 的总数时,MPI 代码可能不会显示线性缩放(并且甚至可能因 MPI 开销和其他因素而变慢)。这可能有很多与GPU无关的原因:

  1. 进程placement/affinity
  2. CPU
  3. 的内存带宽饱和
  4. 在 HPC 代码中使用 "hyperthreaded" 个核心通常没有任何好处或负面影响。

而且我相信还有很多其他的可能性。因此,您的性能下降实际上完全有可能与 GPU 无关(如果事实证明它不是瓶颈)并且是由于其他一些因素造成的。您可以使用分析工具对此有一些初步的想法,上面链接的演示文稿提供了一些想法。