我正在执行一个简单的testing,它比较从malloc()分配的数据的访问延迟和从主机(cpu执行访问)的cudaHostAlloc()分配的数据。 我注意到访问使用cudaHostAlloc()分配的数据比访问Jetson Tk1上malloc()分配的数据要慢得多。
对于独立GPU而言,情况并非如此,似乎只适用于TK1。 经过一番调查,我发现用cudaHostAlloc()分配的数据是映射到进程地址空间的/ dev / nvmap区域的映射(mmap)。 对于映射在进程堆上的普通malloc'd数据,情况并非如此。 我知道这个映射可能是必要的,以允许GPU访问数据,因为cudaHostAlloc的数据必须从主机和设备都可见。
我的问题是:从主机访问cudaHostAlloc'd数据的开销从哪里来的? 数据映射到/ dev / nvmap在CPUcaching上未caching?
我相信我找到了这个行为的原因。 经过进一步调查(使用Linux跟踪事件并查看nvmap驱动程序代码 )之后,我发现开销的来源是使用NVMAP_HANDLE_UNCACHEABLE
标志将使用cudaHostAlloc()
分配的数据标记为“uncacheable”。 调用pgprot_noncached()
是为了确保相关的PTE被标记为不可缓存的。
主机访问使用cudaMallocManaged()
分配的数据的行为是不同的。 数据将被缓存(使用标志NVMAP_HANDLE_CACHEABLE
)。 因此从主机访问这个数据就相当于malloc()'d
数据。 同样重要的是,CUDA运行时不允许设备(GPU)与主机同时访问与cudaMallocManaged()
一起分配的任何数据,并且这样的操作会生成段错误。 但是,运行时允许同时访问设备和主机上的cudaHostAlloc()'d
数据,我相信这是使cudaHostAlloc()'d
数据无法缓存的原因之一。