如何调试CUDA错误码700(非法内存访问/Warp Illegal Address)?
CUDA error calling "cudaStreamSynchronize(0)", code is 700 an illegal memory access was encountered on 489
0# my_func(signed char const*, unsigned char const*, int*, int*, int, int) in libthing.so
以下是针对性的调试步骤:
用cuda-memcheck定位问题:直接运行
cuda-memcheck ./你的程序名,这个工具会追踪所有CUDA内存操作,精准指出非法访问的类型(越界读写、无效指针等)以及对应的调用栈,比单纯的错误提示更具体。核对内存分配与指针有效性:
- 检查
my_func中传递给CUDA内核的所有指针,确认是通过cudaMalloc分配的设备内存指针,而非主机内存指针直接传入。 - 确认内存没有在CUDA操作完成前被
cudaFree释放,尤其是异步操作场景下,别提前释放依赖的内存。
- 检查
编译时添加调试信息,用cuda-gdb单步调试:重新编译CUDA代码时加上
-G -lineinfo参数,生成带调试信息的可执行文件。然后用cuda-gdb ./你的程序名启动调试,在my_func或对应的CUDA内核上设置断点,单步执行就能找到触发非法访问的具体代码行。检查内核中的索引边界:排查CUDA内核里的循环索引、数组访问逻辑,确保所有索引都在分配的内存范围内,比如避免出现
idx >= array_length这类越界情况,尤其是动态计算维度时,要仔细校验计算逻辑。验证内存拷贝操作:逐一核对所有
cudaMemcpy、cudaMemcpyAsync调用,确认拷贝方向(cudaMemcpyHostToDevice/cudaMemcpyDeviceToHost)正确,拷贝的字节数和分配的内存大小完全匹配,避免因拷贝越界破坏内存结构。检查流操作的内存生命周期:错误触发在
cudaStreamSynchronize,说明流中之前的异步操作(内核或内存拷贝)存在内存问题。要确保提交到流的所有操作,其依赖的内存在同步完成前都处于有效状态,没有被提前释放或修改。
内容的提问来源于stack exchange,提问作者Richard

