调用cudaMemcpyAsync时,何时可以安全地重用CPU缓冲区?
我的项目将有多个线程,每个线程在不同的cudaStreams上执行内核。其他一些线程将使用将存储在队列中的结果。此处有一些伪代码:调用cudaMemcpyAsync时,何时可以安全地重用CPU缓冲区?,cuda,Cuda,我的项目将有多个线程,每个线程在不同的cudaStreams上执行内核。其他一些线程将使用将存储在队列中的结果。此处有一些伪代码: while(true) { cudaMemcpyAsync(d_mem, h_mem, some_stream) kernel_launch(some_stream) cudaMemcpyAsync(h_queue_results[i++], d_result, some_stream) } 在第一个cudaMemcpyAsync返回后重新使用h_m
while(true) {
cudaMemcpyAsync(d_mem, h_mem, some_stream)
kernel_launch(some_stream)
cudaMemcpyAsync(h_queue_results[i++], d_result, some_stream)
}
在第一个cudaMemcpyAsync返回后重新使用h_mem是否安全?或者我应该使用N个主机缓冲区来发布gpu计算
如何知道h_mem何时可以重用?我应该使用cudaevents进行一些同步吗
顺便说一句,h_mem是主机固定的。如果它是可分页的,我可以在中间重用h_mem吗?从我在这里读到的内容来看,似乎我可以在memcpyasync返回后在中间重用,对吗
异步的
对于从可分页主机内存到设备内存的传输,主机内存
立即复制到暂存缓冲区(无设备同步
(已执行)。一旦可分页缓冲区恢复,该函数将返回
已复制到暂存内存。DMA传输到最终
目标可能尚未完成。用于固定主机之间的传输
内存和设备内存,功能完全异步。对于
从设备内存到可分页主机内存的传输
将仅在副本完成后返回。对于所有其他转让,
该函数是完全异步的。如果必须首先设置可分页内存
暂存到固定内存时,将使用
工作线程。对于从任何主机内存到任何主机内存的传输,
该功能与主机完全同步
谢谢 为了获得复制/计算重叠,必须使用固定内存。原因在你摘录的段落中。假设您采用多流方法的全部原因是复制/计算重叠,因此我认为正确的答案不是切换到使用可分页内存缓冲区 关于您的问题,假设
h_mem
仅用作此处显示的伪代码的源缓冲区(即其中的数据仅参与一个cudaMemcpyAsync
调用),那么一旦该流中的下一个cuda操作开始,就不再需要h_mem缓冲区。因此,如果您的kernel\u启动
是一个实际的内核(…)
,那么一旦kernel
开始,您就可以确信前面的cudaMemcpyAsync
已经完成
您可以将cudaEvents与
CUDAEventsSynchronize()
或cudaStreamWaitEvent()
一起使用,也可以直接在流中使用cudaStreamSynchronize()
。例如,如果您在显示的流伪代码中有一个cudaStreamSynchronize()
调用,并且是在cudaMemcpyAsync
调用之后,那么cudaStreamSynchronize()
调用之后的任何代码都保证在cudaMemcpyAsync()
调用完成之后执行。我引用的所有调用都记录在。中,因此我必须确保在重用主机内存缓冲区(h_mem)之前memcpyasync已经结束,我可以通过在cudamemcpyasync调用之后放置一个事件来完成同步,但是,然后我应该让一个线程等待此事件。。。所以我想我可以看看这个博客上的“流回调”:顺便说一句。从我摘录的段落中,我看到当主机内存被复制到没有任何设备同步的staging缓冲区时,memcpyasync将返回。所以我想我可以使用一个没有固定内存的memcpyAsync作为第一个拷贝,使用一个有固定内存的memcpyAsync作为第二个拷贝(结果)。