GPU 高性能编程 CUDA : CUDA C 简介


先编写一个 hello world 和 C 没有什么区别

我们将 CPU 以及系统的内存称为主机,将 GPU 及其内存称为设备,hello world 示例程序不考虑主机之外的任何计算设备

核函数的调用

__global__ void kernel ( void ) {

}

int main(){

kernel<<1,1>>();

}

kernel() 函数,并且带有修饰符 __global__,这个修饰符告诉编译器,函数应该在设备上而不是主机上运行,而 main 函数交给主机编译器

kernel() 的调用为什么需要尖括号和数值

CUDA C需要通过某种语法将一个函数标记为“设备代码”,表示将主机代码送到一个编译器,将设别代码送到另一个编译器。CUDA编译器负责运行时从主机代码调用设备代码

所以这个函数调用实际上表示调用设备代码,尖括号表示将一些参数传递给运行时系统,这些参数并不是传递给设备代码的参数,而是告诉运行时如何启动设备代码,传递给设备代码的参数是放在圆括号中的

参数传递给核函数的过程中没有任何特别之处,除了尖括号语法,核函数外表和标准 C 中任何的函数调用一个样,运行时,系统负责处理将参数从主机传递给设备的所有过程

当设备执行任何有用的操作时,都需要分配内存,例如将计算值返回给主机,通过 cudaMalloc() 来分配内存,这个函数告诉 CUDA 运行时在设备上分配内存,第一个参数是一个指针,指向用于保存新分配内存地址的指针,第二个参数是分配内存的大小。除了分配内存的指针不是作为函数的返回值外,这个函数的行为和 malloc() 是相同的,并且返回 void*


dev_c是主机上的一个指针,即保存这个指针的地址为主机上的,这个指针指向设备上的一个分配的地址,语句 *c=a+b 代表将参数 a 和 b 的值加起来,结果保存在 c 指向的内存中


不可以在主机代码中对 cudaMalloc() 返回的指针进行解引用,可以对这个指针进行参数传递,对其执行算术运算,就是不可以用和这个指针来读取或者写入内存

cudaMemcpy() 进行内存的复制,类似于 C 中的 memcpy() ,只不过多了一个参数用来指定设备内存指针究竟是源指针还是目标指针,cudaMemcpyDevicesToHost,源指针是设备指针,目标指针是主机指针,参数一为什么用变量的地址,而不是指针

使用设备指针的限制如下:

将 cudaMalloc() 分配的指针传递给在设备上执行的函数

在设备代码中使用 cudaMalloc() 分配的指针进行内存的读/写操作

将 cudaMalloc() 分配的指针传递给在主机上执行的函数

不能在主机代码中使用 cudaMalloc() 分配的指针进行内存的读/写操作

使用 cudaFree() 来释放cudaMalloc() 分配的内存

设备的查询

int count;
cudaGetDeviceCount(&count)

返回设备的个数

cudaDeviceProp prop;
cudaGetDevicesPropertise(&prop,0)

返回第零个设备的属性







 
 

猜你喜欢

转载自blog.csdn.net/xxiaozr/article/details/80072748