1:定义方法
创建一个cudaStream_t对象,并在启动内核和进行memcpy时将流对象作为参数传入。
2:运行时API实现
1 //创建了两个流,并在pinned memory中分配了float型的数组hostPtr 2 cudaStream_t stream[2]; 3 for(int i = 0;i < 2;i++) 4 cudaStreamCreate(&stream[i]); 5 6 float* hostPtr; 7 cudaMallocHost((void**)&hostPtr,2*size); 8 9 //将每个流定义为由host到device的内存拷贝/kernel启动以及device到host的内存拷贝三个操作组成的序列,允许一个流的内存拷贝与另一个流的kernel执行同时进行--同步执行 10 for(int i =0 ;i < 2;i++) 11 cudamemcpyasync(inputdevptr+i*size/sizeof(float),hostptr+i*size/izeof(float),size,cudamemcpyhosttodevice,stream[i]); 12 13 for(int i = 0;i < 2;i++) 14 mykernel<<<100,512,0,stream[i]>>>(outputdevptr+i*size,inputptr+i*size,size); 15 16 for(int i = 0;i < 2;i++) 17 cudamemcpyasync(hostptr+i*size/sizeof(float),outputdevptr+i*size/sizeof(float),size,cudamemcpydevicetohost,strea[i]); 18 19 cudathreadsynchronize();//保证进行下一步操作前两个流都已经运行完毕 20 //cudaStreamSynchronize()用于主机与特定流的同步,同时又允许其他流继续在设备上执行 21 22 //流的释放 23 for(int i = 0;i < 2;i++) 24 cudaStreamDestroy(stream[i]);
A:执行参数中没有流参数或使用0作为流参数时,不会创建流。此时为异步执行方式
B:以下函数会进行轮询,占大量CPU资源,最好只在计时或分隔失败的kernel启动或内存拷贝时调用这些函数。
cudaStreamQuery()-----查询一个流中的位置前的所有操作是否均已完成
cudaStreamSynchronize()----显示强制CUDA运行时等待流中所有操作完成
cudaThreadSynchronize()---强制CUDA运行时进行等待知道调用位置之前所有流中的所有任务完成才能往下进行
cudaStreamSynchroniz0----等待直到所有与主机线程相关的命令执行完。
cudaStreamWaitEvent0----
cudaStreamDestroy()----一直等待,直到所在流中的任务都结束,才会销毁流,并返回主机线程;
cudaStreamAddCallback()---当设备端出现异常时,主机端自动返回
3:stream priorities
cudaStreamCreateWithPriority()-----设置优先级
cudaDeviceGetStreamPriorityRange()---获取优先级[height,low];
4:驱动API实现
1 CUstream stream[2]; 2 for(int i = 0;i < 2;i++) 3 cuStreamCreate(&stream[i],0); 4 5 float* hostPtr; 6 cuMemAllocHost((void**)&hostPtr,2*size); 7 8 for(int i = 0;i < 2;i++) 9 cuMemcpyHostToDAsync(inputDevptr+i*size,hostPtr+i*size,size,stream[i]); 10 11 for(int i = 0;i < 2;i++) 12 { 13 int offset = 0; 14 cuParamSeti(cuFunction,offset,outputDevPtr); 15 offset += sizeof(int); 16 cuParamSeti(cuFunction,offset,inputDevPtr); 17 offset += sizeof(int); 18 cuParamSeti(cuFunction,offset,size); 19 offset += sizeof(int); 20 cuParamSetSize(cuFunction,offset); 21 22 cuFuncSetBlockShape(cuFunction,512,1,1); 23 cuLaunchGridAsync(cuFunction,100,1,stream[i]); 24 } 25 26 for(int i = 0;i < 2;i++) 27 cuMemcpyDtoHAsync(hostPtr+i*size,outputDevPtr+i*size,size,stream[i]); 28 29 cuCtxSynchronize(); 30 31 for(int i = 0;i < 2;i++) 32 cuStreamDestroy(&stream[i]);