Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/sockets/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
调用cudaMemcpyAsync时,何时可以安全地重用CPU缓冲区?_Cuda - Fatal编程技术网

调用cudaMemcpyAsync时,何时可以安全地重用CPU缓冲区?

调用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

我的项目将有多个线程,每个线程在不同的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_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作为第二个拷贝(结果)。