gem5驗證數組的緩存優化

陸續寫些關於新書《自己動手寫CPU》的博客,本篇主要是講解 gem5驗證數組的緩存優化


軟件優化是提高cache命中率的十分有效的手段,cache的基本原理是利用程序局部性,而軟件優化可以通過提高程序局部性,從而提高cache命中率。舉一個例子如下:

程序A:

#include <stdio.h>

int main()
{
    int i=0,j=0;
    long count=0;
    long temp[51200][8];      
 
    for(i=0;i<51200;i++)
       for(j=0;j<8;j++)
           {
           temp[i][j]=i*j;   //  大約51200 次DCache缺失
           }
 
}
在C語言中,二維數組在內存中是按照行的次序在按照列的次序存放,也就是說,二維數組中同一行的數據在內存中是挨着的,但同一列的數據在內存中是分散的。

假設數據cache的line size是64,long類型是8個字節,那麼在程序A中,temp[i][0]-temp[i][7]剛好是64字節,佔用數據cache的一個line,所以在寫temp[i][0]將發生一次cache缺失,在寫temp[i][1]-temp[i][7]的時候,不會發生數據缺失,所以,一共發生51200次缺失。

程序B:

#include <stdio.h>

int main()
{

    int i=0,j=0;
    long count=0;
    long temp[51200][8];      

    for(i=0;i<8;i++)
       for(j=0;j<51200;j++)
           {
           temp[j][i]=i*j;   // 大約8*51200 次DCache缺失
           }
}
仍然假設數據cache的line size是64,long類型是8個字節,那麼在程序B中,是先按照列的次序訪問,在按照行的次序訪問,所以每次訪問都會發生數據cache缺失,一共發生8*51200=409600次缺失。

下面我們通過gem5仿真驗證上述分析是否正確。

還是以我的開發環境爲例,gem5安裝在/root/gem5/gem5-stable-50ff05095970/路徑下,修改tests/test-progs/hello/src目錄下的hello.c,如下:

#include <stdio.h>

int main()
{

    int i=0,j=0;
    long count=0;
    long temp[51200][8];      

}
使用如下命令編譯(需要在/root/gem5/gem5-stable-50ff05095970/tests/test-progs/hello/src目錄下執行下面的命令):

gcc --static hello.c -o hello
然後使用前幾次編譯得到的X86對應的gem5.opt運行hello,並且選擇CPU模型是Timing,也就是順序流水線模型,命令如下(需要在/root/gem5/gem5-stable-50ff05095970/路徑下執行下面的命令):
./build/X86/gem5.opt ./configs/example/se.py --cpu-type=timing --caches -c ./tests/test-progs/hello/src/hello
得到的統計結果在m5out/stats.txt中,找到其中的如下數據(分別是執行時間和數據cache寫操作的缺失數):

sim_seconds                                  0.000030                       # Number of seconds simulated
......
system.cpu.dcache.WriteReq_misses::cpu.data           90

修改hello.c的代碼爲程序A,然後編譯,並使用gem5.opt運行,再次打開stat.txt得到運行時間、數據cache的缺失數如下:

sim_seconds                                  0.013802
......
system.cpu.dcache.WriteReq_misses::cpu.data        51290
可見數據cache的缺失數增加了51200,符合我們前期的分析。

修改hello.c的代碼爲程序B,然後編譯,並使用gem5.opt運行,再次打開stat.txt得到運行時間、數據cache的缺失數如下:

sim_seconds                                  0.031548
......
system.cpu.dcache.WriteReq_misses::cpu.data       409688

可見數據cache的缺失數增加了409588,接近409600,基本符合預期。通過實驗可以更加深刻的瞭解到程序優化對緩存使用的影響。


上面的結果與預期有一定誤差,可能是數組的起始地址沒有64字節對齊,也可能是因爲循環賦值導致其餘部分代碼發生變化,從而引起數據cache訪問次數的變化。


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章