Cuda 學習 - 基本定義
===
# Cuda 的資料使用流程如下
1. 從 CPU 做資料初始化
2. 將資料從 CPU 搬運至 GPU
3. Kernel 根據 Grid、Block 大小做資源分配
4. 將執行完的資料從 GPU 搬運回 CPU
5. 回收 CPU、GPU 的相關資源
# 名詞定義
* 程式上
* Host code : 在 CPU 上執行的程式
* Device code : 在 GPU 上執行的程式
* ```__global__```:在 GPU 上執行,由 CPU 呼叫,無返回值。
* ```__device__```:在 GPU 上執行,由其他 GPU 函數呼叫,可有返回值。
* ```__host__```:在 CPU 上執行,由 CPU 呼叫,可有返回值。
* 相關 element
* Thread
* 執行 GPU 運算的最小單位, 同常由 block 來分配須使用的 thread 數量
* 每個 thread 可以是 1~3 維, 視目標任務而定
* 可透過 threadIDx 來進行識別
* Block
* Block 低下含有若干個 thread, 並且由 grid 來分配須使用的 block 數量
* 在 Block 底下的 Thread 可共享記憶體, 每個 block可透過 blockIDx進行識別
* 每個 block 可以是 1~3 維, 視目標任務而定
* Grid
* 由多個 Block 組合而成根據任務分配 Block 所需的數量, 為用來啟動kernel function的最高級別
* 每個 grid 可以是 1~3 維, 視目標任務而定, 可透過 gridDim 來查詢維度大小

# 程式上的設置及範例
* ```kernel_name<<<num_of_block, thread_per_block>>>(argument)```
* kernel_name : 是我們要執行的 cuda 程式
* num_of_block : block 設定的數量
* thread_per_block : 每個 block 需要的thread
* num_of_block 跟 thread_per_block 均為 dim3 的變數, 識任務情況資料維度為1~3維
* 範例
* 在以下範里中我們設定了以下
* grid 含有2個 block
* 每個block 含有4個 thread
* 備註 : dim3可彈性的設定 例如 dim3 a(4)、b(2,5)、c(2,5,4)
* 將 grid 及 block 的設定帶入並啟用 kernel function -> hello_cuda_with_id
* 最後會輸出是由哪個 blockIDx 及 threadIDx 打印 Hello World
```cpp=
#include <cuda_runtime.h>
#include <device_launch_parameters.h>
#include <stdio.h>
__global__ void hello_cuda(){
printf("Hello CUDA world \n");
}
__global__ void hello_cuda_with_id(){
printf("Hello CUDA world with blockIDx.x %d, threadIDx %d \n", blockIdx.x, threadIdx.x);
}
int main(){
dim3 grid(2); // Set up the block size in a grid
dim3 block(4); // set up the thread size in a block
hello_cuda_with_id<<<grid, block>>>();
cudaDeviceSynchronize();
cudaDeviceReset();
return 0;
}
```

* ###### tags : `Cuda`