我在矩阵乘法基准测试中遇到了一个奇怪的性能问题(来自MOSBENCH套件的Metis中的matrix_mult ).基准进行了优化,瓦片中的数据,使得有源工作集是12KB(32×32整数3个砖)和将装配到L1高速缓存.长话短说,交换内部两个大多数循环在某些阵列输入大小(4096,8192)上的性能差异几乎是4倍,而在其他阵列输入大小上差异大约为30%.问题基本上归结为顺序访问元素而不是步幅模式.我认为某些数组大小创建了一个糟糕的步幅访问,产生了很多缓存线冲突.当从2路关联L1变为8路关联L1时,性能差异明显减小.
我的问题是为什么gcc不优化循环排序以最大化顺序内存访问?
下面是问题的简化版本(请注意,性能时间高度依赖于L1配置.下面显示的数字来自2.3 GHZ AMD系统,其中64K L1双向关联使用-O3编译).
N = ARRAY_SIZE // 1024
int* mat_A = (int*)malloc(N*N*sizeof(int));
int* mat_B = (int*)malloc(N*N*sizeof(int));
int* mat_C = (int*)malloc(N*N*sizeof(int));
// Elements of mat_B are accessed in a stride pattern of length N
// This takes 800 msec
for (int t = 0; t < 1000; t++)
for (int a = 0; a < 32; a++)
for (int b = 0; b < 32; b++)
for (int c = 0; c < 32; c++) …Run Code Online (Sandbox Code Playgroud)