内存带宽计算方法如下:
带宽=内存核心频率×内存总线位数×倍增系数
理论读写带宽 = 频率*位宽/8bits
下面举例说明内存带宽计算:
DDR4 2133MHz内存的读写带宽:2133Mbit/s✖64bit➗8bit = 17064MB/s
DDR4 2666MHz内存的读写带宽:2666Mbit/s✖64bit➗8bit = 21328MB/s
测试到内存带宽的性能,主要是进行下面四种数组运算:
1、数组的复制(copy)
2、数组的尺度变换(scale)
3、数组的矢量求和(add)
4、数组的复合矢量求和(triad)
stream测试使用如下算法:
Memory:stream_array a[];stream_array b[];stream_array c[]
CPU运算方法:
数组的复制(copy):c[j]=a[j]
数组的尺度变换(scale) : b[j]=scalar*c[j]
数组的矢量求和(add) : c[j]=a[j]+b[j]
数组的复合矢量求和(triad) : a[j]=b[j]+scalar*c[j]
将某个内存块之间的数据读取出来,经过简单的运算放入另一个内存块,所以内存带宽=搬运内存的大小/耗时
测试注意事项:
1、内存数组大小设置,必须要远大于L3 Cache的大小
2、内存实测带宽跟CPU的数量有关系
stream源码下载地址:https://www.cs.virginia.edu/stream/FTP/Code/stream.c
编译stream命令:
gcc -O3 -fopenmp -mcmodel=medium -DSTREAM_ARRAY_SIZE=100000000 stream.c -o stream
编译参数解释:
-O3:编译器编译优化级别
-mcmodel=medium:单个Memory Array Size大于2GB需要设置此参数
-fopenmp:适应多处理器环境,开启后,程序默认线程为CPU线程数,运行时也可以动态指定运行的进程数 :export OMP_NUM_THREADS=12
-DSTREAM_ARRAY_SIZE=100000000:指定计算中a[] b[] c[]数组的大小
示例:如果CPU的L3缓存是35M,double 64bit=8byte
STREAM_ARRAY_SIZE=35M*4*2(两颗CPU)*1000*1000/8=35000000,可以大于此值
-DNTIMES=30:执行次数,并且从这些结果中选取最优值
-DOFFSET=4096:数组的偏移,一般不定义
测试结果实例: