这是 CUDA SDK (2.3) matrixMultiply 内核的一部分:
for (int a = aBegin, b = bBegin;
a <= aEnd;
a += aStep, b += bStep) {
__shared__ float As[BLOCK_SIZE][BLOCK_SIZE];
__shared__ float Bs[BLOCK_SIZE][BLOCK_SIZE];
int XI=wA * ty + tx;
int XII=wB * ty + tx;
////////////////////
// PREFETCH BLOCK //
////////////////////
AS(ty, tx) = A[a + XI];
BS(ty, tx) = B[b + XII];
__syncthreads();
for (int k = 0; k < BLOCK_SIZE; ++k)
Csub += AS(ty, k) * BS(k, tx);
__syncthreads();
}
此版本的矩阵乘法将切片带入共享内存并在共享内存带宽上执行计算。我想通过将下一次迭代的数据预取到 L1 缓存中来提高性能。我按照这里的建议使用预取内在函数,并将以下命令插入到PREFETCH BLOCK
上面:
long long int k,kk;
k=((long long int)A+aStep); if(k<=aEnd) prefetch_l1(k+XI);
kk=((long long int)B+bStep); if(kk<=aEnd) prefetch_l1(kk+XII);
经过测试,两个版本(有或没有预取)执行非常相似(平均 3 次运行):
没有预取: 6434.866211(毫秒)
预取: 6480.041016(毫秒)
问题:
我希望看到预取的一些加速,但我对结果感到困惑。任何机构都有理由说明为什么这两个实现非常接近?也许我正在执行错误的预取。
先感谢您。
更多信息:
显卡:特斯拉 C2050
CUDA 版本:4.0
inline __device__ void prefetch_l1 (unsigned int addr)
{
asm(" prefetch.global.L1 [ %1 ];": "=r"(addr) : "r"(addr));
}