数据科学

统一虚拟内存利用 RAPIDS cuDF 为 pandas 提供强力支持

上一篇文章 中介绍的 cuDF-pandas 是一个 GPU 加速库,可加速 pandas 以实现显著的性能提升,速度最高可提升至原来的 50 倍,而无需对现有代码进行任何更改。作为 NVIDIA RAPIDS 生态系统的一部分,cuDF-pandas 充当代理层,尽可能在 GPU 上执行运算,必要时 (通过 pandas) 回退至 CPU。这可确保与完整的 pandas API 和第三方库兼容,同时利用 GPU 加速加快数据处理速度。只需加载 cuDF-pandas,用户即可维护熟悉的 pandas 工作流程,同时获得统一的 CPU/GPU 体验。

在幕后,cuDF-pandas 默认使用托管内存池,使其能够处理超过 GPU 物理内存的数据集。这是通过 CUDA Unified Virtual Memory (UVM) 实现的,可提供跨主机 (CPU) 和设备 (GPU) 内存的统一地址空间。UVM 允许 cuDF-pandas 超额订阅 GPU 内存,根据需要自动在主机和设备之间迁移数据。

这篇博文将介绍为什么需要 UVM 及其优势。

为什么 cuDF-pandas 使用 UVM 

统一虚拟内存对于解决 GPU 加速数据处理中的两个关键挑战至关重要:

  1. GPU 显存有限:许多 GPU (尤其是消费级型号) 的显存明显少于现代数据集。UVM 支持超额认购,允许工作负载利用系统内存扩展到物理 GPU 显存之外。
  2. 易用性:UVM 可自动处理 CPU 和 GPU 之间的数据迁移,从而简化内存管理。这降低了编程的复杂性,并确保用户可以专注于自己的工作流程,而无需担心显式内存传输。

有关 UVM 的详细信息 

CUDA 6.0 中引入的 Unified Virtual Memory (UVM)可创建 CPU 和 GPU 之间共享的单个虚拟地址空间,从而简化开发者的内存管理。UVM 根据访问模式以页面粒度透明迁移数据:

  • 当 GPU 访问驻留在主机内存中的数据时,它会触发页错误,促使数据迁移到 GPU 内存。
  • 相反,当 GPU 显存已满时,使用较少的页面会被逐回主机内存。

虽然 UVM 通过消除显式内存传输的需求来扩展内存容量并简化编程,但由于页面错误和迁移开销,它可能会引入性能瓶颈。为缓解这些问题,我们采用了优化措施,如预取(例如,使用 cudaMemPrefetchAsync),以便在执行内核之前主动将数据迁移到 GPU。以下是 nsys 配置文件图,其中显示了在执行 libcudf 内核之前对 CUDA API 层中 cudaMemPrefetchAsync 的多次调用:

An nsys-profile showing calls to cudaMemPrefetchAsync being made before execution of libcudf kernels.
图 1. 一个 nsys-profile,显示在执行 libcudf 核函数之前对 cudaMemPrefetchAsync 的调用。

如需更深入地了解 Unified Memory,包括其优势以及预取和内存建议 (cudaMemAdvise) 等优化实例,请参阅技术博客 《面向 CUDA 初学者的 Unified Memory》(Unified Memory for CUDA Beginners)。该博客解释了 UVM 在不同 GPU 架构中的工作原理,并提供了在实际应用中更大限度提高性能的技巧。

cuDF-pandas 如何利用 UVM 

cuDF-pandas 中,UVM 在实现高性能数据处理方面发挥着关键作用:

  1. 托管内存池:默认情况下,cuDF-pandas 使用由 UVM 支持的托管内存池。此池可减少分配开销,并确保有效利用主机和设备内存。
  2. 预取优化:预取可确保在内核访问数据之前将数据迁移到 GPU,从而减少运行时页错误。例如,在需要大量数据的 I/O 操作或连接期间,预取可通过主动将数据移动到设备内存来确保更流畅的执行。如前所述,这些预取调用发生在 libcudf 层中,用于特定内核,如 哈希连接

示例:Google Colab 上的大型连接和写入 Parquet

考虑对两个非常大的表执行 合并/连接操作 ,即在 Google Colab 的有限 GPU memory 中执行 cuDF-pandas

  • 如果没有 UVM,此操作将因设备内存不足而失败。
  • 启用 UVM 后,数据集将在主机内存和设备内存之间进行分割。随着连接的进行,系统仅会将所需的数据部分迁移到 GPU。
  • 预取可确保在计算之前将相关数据引入设备内存,从而进一步优化此过程。

用户可以利用 GPU 处理超过 GPU 显存的更大数据集,而无需更改代码。使用 Unified Virtual Memory (UVM)时,速度提升因操作而异,但在保持稳定性的同时,仍可显著提升端到端应用的性能。

A plot comparing time taken by pandas and cuDF-pandas to merge. Pandas takes 28.2 s whereas cuDF-pandas takes 2.19s.
图 2、表格 pandas 与 cuDF-pandas 的合并持续时间比较。 CPU 硬件:Intel(R) Xeon(R) Gold 6130 CPU @ 2.10GHz,GPU 硬件:NVIDIA T4

写入 Parquet 文件也是如此。原本使用 cudf 运行到 MemoryError 的内容,现在使用 cuDF-pandas 成功完成,甚至比 pandas 更快。

A plot comparing time taken by pandas and cuDF-pandas for writing a large table to parquet. Pandas takes 28.1 s whereas cuDF-pandas takes 14.4s.
图 3、根据 pandas 与 cuDF-pandas 的拼接持续时间编写大型表格。 CPU 硬件:Intel(R) Xeon(R) Gold 6130 CPU @ 2.10GHz,GPU 硬件:NVIDIA T4

结束语 

统一虚拟内存是 cuDF-pandas 的基石,使其能够高效处理大型数据集,同时保持与低端 GPU 的兼容性。通过利用托管内存池和预取等功能,cuDF-pandas 可在受限硬件上为 pandas 工作流提供性能和稳定性。这使其成为扩展数据科学工作流的理想选择,而无需牺牲可用性或修改大量代码。

试用此 Google Colab notebook ,了解大于 GPU 内存的数据集的实际执行能力。

 

标签