在代码中过度使用__syncthread

时间:2014-01-12 14:45:37

标签: cuda gpgpu

我理解__syncthreads()的目的,但我有时会发现它在某些代码中被过度使用。

例如,在以下代码中取自NVIDIA备注,每个主要计算s_data[tx]-s_data[tx-1]。每个线程需要从全局内存中读取的数据以及由其相邻线程读取的数据。两个线程将处于相同的warp中,因此应完成从全局内存中检索其数据并安排同时执行。

我相信代码在没有__syncthread()的情况下仍然可以正常工作,但显然NVIDIA的说明不然。有什么评论吗?

// Example – shared variables
// optimized version of adjacent difference
__global__ void adj_diff(int *result, int *input)
{
    // shorthand for threadIdx.x
    int tx = threadIdx.x;
    // allocate a __shared__ array, one element per thread
    __shared__ int s_data[BLOCK_SIZE];
    // each thread reads one element to s_data
    unsigned int i = blockDim.x * blockIdx.x + tx;
    s_data[tx] = input[i];
    // avoid race condition: ensure all loads
    // complete before continuing
    __syncthreads();

    if(tx > 0)
        result[i] = s_data[tx] – s_data[tx–1];
    else if(i > 0)
    {
        // handle thread block boundary
        result[i] = s_data[tx] – input[i-1];
    }
}

1 个答案:

答案 0 :(得分:5)

如果你在“Nvidia笔记”中包含一个链接到哪里,那就好了。

  

两个线程将处于相同的warp

不,他们不会,至少在所有情况下都不会。 tx = 32时会发生什么?那么对应tx的线程属于块中的warp 1,对应tx-1的线程属于块中的warp 0。

无法保证warp 0在warp 1之前执行,因此代码可能会失败而不调用__synchtreads()(因为没有它,s_data[tx-1]的值可能无效,因为warp 0没有运行,因此尚未加载它。)