對於一維情況,我非常瞭解CUDA中全局內存的整合訪問需求。CUDA聯合訪問二維塊
但是我對二維情況(即我們有一個2D網格,由2D塊組成)有點卡住了。
假設我有一個向量in_vector
,並且在我的內核中,我想以合併的方式訪問它。像這樣:
__global__ void my_kernel(float* out_matrix, float* in_vector, int size)
{
int i = blockIdx.x * blockDim.x + threadIdx.x;
int j = blockIdx.y * blockDim.y + threadIdx.y;
// ...
float vx = in_vector[i]; // This is good. Here we have coalesced access
float vy = in_vector[j]; // Not sure about this. All threads in my warp access the same global address. (See explanation)
// ...
// Do some calculations... Obtain result
}
在我對這種2D情況的理解中,塊內的線程以列主要方式「排列」。例如:假設一(threadIdx.x,threadIdx.y)表示法:
- 第一經線將是:(0,0),(1,0),(2,0),...,( (0,1),(1,1),(2,1),...,(31,1),
- 等等。
在這種情況下,調用in_vector[i]
給了我們一個合併訪問,因爲同一warp中的每個連續線程都將訪問連續的地址。然而,調用in_vector[j]
似乎是一個壞主意,因爲每個連續的線程將訪問全局內存中的相同地址(例如warp 0中的所有線程將訪問in_vector [0],這會給我們32個不同的全局內存請求)
我對此有正確的理解嗎?如果是這樣,我怎樣才能使用in_vector[j]
聯合訪問全局內存?
非常感謝您提供非常豐富的答案。這正是我正在尋找的。 – Iam