是否可以运行设备端CUDA代码来了解为正在运行的内核网格的每个块分配了多少(静态和/或动态)共享内存?
在主机端,您知道启动的内核拥有(或将拥有)共享内存的数量,因为您自己设置了该值;但是设备方面怎么样?在上限中编译该大小很容易,但该信息不可用(除非明确传递)到设备。是否有用于获取它的GPU上机制? CUDA C Programming Guide似乎没有讨论这个问题(在共享内存部分之内或之外)。
答案 0 :(得分:2)
有可能:该信息可用于特殊寄存器中的内核代码:%dynamic_smem_size
和%total_smem_size
。
通常,当我们编写内核代码时,我们不需要知道特定的寄存器(特殊或其他) - 我们编写C / C ++代码。即使我们使用这些寄存器,CUDA编译器也会通过保存其值的函数或结构来隐藏它。例如,当我们使用值%tid.x
时,我们实际上访问了特殊寄存器%
,它对块中的每个线程设置不同。当您查看已编译的PTX代码时,您可以看到这些寄存器“正在运行”。 ArrayFire撰写了一篇很棒的博客文章,其中包含一些有用的例子:Demystifying PTX code。
但是如果CUDA编译器“隐藏”了我们的注册用法,那么我们如何才能在幕后实际坚持使用它们,用那些__forceinline__ __device__ unsigned dynamic_smem_size()
{
unsigned ret;
asm volatile ("mov.u32 %0, %dynamic_smem_size;" : "=r"(ret));
return ret;
}
- 前缀名称访问它们?嗯,这是如何:
%total_smem_size
和asm
的类似功能。此函数使编译器添加显式PTX指令,就像x = dynamic_smem_size();
可用于主机代码直接发出CPU汇编指令一样。此函数应始终内联,因此在分配
x
您实际上只是将特殊寄存器的值分配给preg_*
。