我遇到了一个更大的内核问题,但它似乎要反映到以下代码,内核永远不会返回。有人可以解释一下为什么会出现无限循环吗?
__global__ void infinite_while_kernel(void)
{
int index = 0;
while (index >= threadIdx.x) {
index--;
}
return;
}
int main(void) {
infinite_while_kernel<<<1, 1>>>();
cudaDeviceSynchronize();
return 0;
}
另外,下面的内核也会卡住:
__global__ void not_infinite_while_kernel(void)
{
int index = 0;
while (index >= (unsigned int) 0u*threadIdx.x) {
index--;
}
return;
}
在原始内核中用threadIdx.x
替换0
将返回,如预期的那样。我正在使用v5.5工具包,并使用-arch=sm_20 -O0
标志进行编译。在特斯拉M2090上运行。我目前无法访问任何其他硬件,也无法访问工具包版本(这不是我的系统)。
答案 0 :(得分:3)
这段代码也挂在普通的C ++中(试一试):
int main(){
int index = 0;
while (index >= 0U){
index--;
}
return 0;
}
将有符号值与无符号值进行比较时,compiler converts the signed value to unsigned。
threadIdx.x
是无符号值。代码中没有标记的0
常量不是。
作为无符号比较,您的测试始终为true,因此while循环永远不会退出。
另请注意,您的__global__
功能应使用void
进行修饰。
最后,在内核启动后代码中没有cudaDeviceSynchronize()
或其他障碍,无论如何,即使内核挂起,程序也会“正常”退出。
所以我认为您发布的代码实际上并不会重现您所描述的问题,但如果您添加cudaDeviceSynchronize()
它将会发生。