打算写一个矩阵转置分别在CPU和GPU平台的性能优化的系列,在最开始把测试环境等一些基本情况交代清楚,并在这里持续更新优化的结果。
机器配置
为了方便各位对比性能,介绍一下我的测试机器配置。
CPU Intel 9900k,程序主要与主频和缓存密切相关,参考如下:
公用函数
void TestTranspose(int i,int iAlign,int iVerify)
{
/*typedef*/ void (*Funcp[20])(unsigned char*, unsigned char*);
void (*TargetFunc)(unsigned char*, unsigned char*);
Funcp[0] = SimdTransposeBlock16;
Funcp[1] = SimdTransposeBlock16Pad;
Funcp[2] = SimdTransposeBlock8ColPad;
Funcp[3] = SimdTransposeBlock8RowPad;
Funcp[4] = SimdTransposeBlock16PadParallel;
Funcp[5] = SimdTransposeBlock8RowPadPrefetch;
Funcp[6] = SimdTransposeBlock8RowPPP;
Funcp[7] = IPPTranspose;
TargetFunc = Funcp[i];
unsigned char* pSource;
unsigned char* pTarget;
if (iAlign)
{
pSource = (unsigned char*)malloc(sizeof(unsigned char) * NSLICE);
for (int irow = 0; irow < NROW; ++irow)
{
memset(pSource + irow * NCOL, irow % 256, sizeof(unsigned char) * NCOL);//按照字节赋值
}
pTarget = (unsigned char*)malloc(sizeof(unsigned char) * NSLICE);
for (int irow = 0; irow < NROW; ++irow)
{
memset(pTarget + irow * NCOL, irow % 256, sizeof(unsigned char) * NCOL);//按照字节赋值
}
}
else
{
pSource = (unsigned char*)malloc(sizeof(unsigned char) * NREALCOL * NROW);
for (int irow = 0; irow < NROW; ++irow)
{
memset(pSource + irow * (NREALCOL), irow % 256, sizeof(unsigned char) * (NREALCOL));//按照字节赋值
}
pTarget = (unsigned char*)malloc(sizeof(unsigned char) * NSLICE);
for (int irow = 0; irow < NROW; ++irow)
{
memset(pTarget + irow * NCOL, irow % 256, sizeof(unsigned char) * NCOL);//按照字节赋值
}
}
TargetFunc(pSource, pTarget);
/*unsigned char* pNavi;
InitMem(pNavi);
if (iAlign)
{
NavTranspose(pSource, pNavi);
Verify(pNavi, pTarget);
}
else
{
NavTransposePad(pSource, pNavi);
Verify(pNavi, pTarget);
}
FreeMem(pNavi);*/
FreeMem(pTarget);
FreeMem(pSource);
}
优化情况
CPU平台上对元素为char类型,尺寸为1024 * 1024,内存1M的矩阵转置,分别从内存访问,向量化,多线程并行化三个角度优化,执行情况如下:
优化手段 | 执行时间(ms) |
---|---|
读内存连续 | 2.68945 |
写内存连续 | 1.5498 |
写内存连续+分块 | 0.605469 |
写内存连续+分块+内存填充 | 0.367188 |
写内存连续+分块+内存填充+多线程 | 0.105469 |
Intrinsic+写内存连续+分块+内存填充 | 0.0732422 |
Intrinsic+写内存连续+分块+内存填充+寄存器优化 | 0.0695312 |
Intrinsic+写内存连续+分块+内存填充+寄存器优化+预取 | 0.0669922 |
Intrinsic+写内存连续+分块+内存填充+寄存器优化+预取+多线程 | 0.0200195 |
单线程+IPP | 0.0822266 |
性能对比:
1.在CPU平台上原始转置方法执行时间:2.68945ms,最终优化转置方法执行时间:0.0200195ms,得到加速比约135倍。
2.单线程下与Intel IPP转置函数对比性能,其中IPP 0.0822266ms,Intrinsic最快达到0.0669922ms,速度快于IPP。获得加速比为1.227 。
传送门
CPU性能优化系列——矩阵转置(一)访问内存顺序带来的性能差异
CPU性能优化系列——矩阵转置(六)Intrinsic转置实现与Core Bound优化