一台设备有多个CUDA上下文-有意义吗



我以为我已经掌握了这一点,但显然我没有:)我需要从编码器不接受的任何格式的帧中使用NVENC执行并行H.264流编码,因此我有以下代码管道:

  • 调用一个通知新帧已到达的回调
  • 我将帧复制到CUDA内存并执行所需的颜色空间转换(只有第一个cuMemcpy是同步的,所以我可以从回调返回,所有挂起的操作都被推送到专用流中)
  • 我把一个事件推到流上,让另一个线程等待它,一旦它被设置好,我就把CUDA内存指针和正确颜色空间中的帧一起送到解码器

出于某种原因,我假设如果我在并行线程中执行此管道,则需要为每个线程提供一个专用上下文。代码很慢,经过一番阅读,我明白上下文切换实际上很昂贵,然后我得出的结论是,这毫无意义,因为在上下文中拥有整个GPU,所以我锁定了其他转码器线程的任何并行处理。

问题1:在这种情况下,我是否擅长为执行上述管道的每个线程使用单个上下文和在此上下文上创建的显式流?

问题2:有人能告诉我CUDA设备上下文的唯一目的是什么吗?我认为这在多GPU场景中是有意义的,但在任何情况下,我都想为一个GPU创建多个上下文吗?

问题1:在这种情况下,我是否擅长为执行上述管道的每个线程使用单个上下文和在此上下文上创建的显式流?

您应该可以处理单个上下文。

问题2:有人能告诉我CUDA设备上下文的唯一目的是什么吗?我认为这在多GPU场景中是有意义的,但在任何情况下,我都想为一个GPU创建多个上下文吗?

编程指南中讨论了CUDA设备上下文。它表示与特定进程相关的所有状态(内存映射、分配、内核定义和其他状态相关信息)(即与该特定进程对GPU的使用相关)。单独的进程通常具有单独的上下文(单独的设备也是如此),因为这些进程具有独立的GPU使用和独立的内存映射。

如果你有一个GPU的多进程使用,你通常会在该GPU上创建多个上下文。正如您所发现的,可以从一个过程中创建多个上下文,但通常不是必需的。

是的,当你有多个上下文时,在这些上下文中启动的内核将需要上下文切换,从一个上下文中的一个内核切换到另一个上下文的另一个内核。这些内核不能同时运行。

CUDA运行时API使用情况为您管理上下文。使用运行时API时,通常不会显式地与CUDA上下文交互。然而,在驱动程序API的使用中,上下文是显式创建和管理的。

显然几年过去了,但NVENC/NVDEC现在似乎从视频编解码器SDK的9.1版本(大约2019年9月)开始支持CUstream:https://developer.nvidia.com/nvidia-video-codec-sdk/download

9.1新增-Encode:NVENC中的CUStream支持,增强了CUDA预处理和NVENC编码之间的并行性

我对CUDA非常陌生,但我的基本理解是,CUcontexts允许多个进程使用GPU(通过进行中断彼此工作的上下文交换),而CUstreams允许在单个进程内协调共享GPU的资源。

最新更新