#gcc -O -fopenmp -O2 stream.c -o stream
重要编译参数调节:
STREAM_ARRAY_SIZE
调节array大小,设置方法100M的方法:
gcc -O -DSTREAM_ARRAY_SIZE=100000000
stream.c -o stream.100M
NTIMES
调节stream在每个kernel的运行次数,输出最好的一次。
设置7次的方法。可通过-DNTIMES=7调节
多核支持
多核情况下,通过 -O -fopenmp 增加多核OpenMP支持
mtune=native -march=native
针对CPU指令的优化,此处由于编译机即运⾏机器。故采用native的优化⽅法。
-O3
编译器编译优化级别。
–fopenmp
适应多处理器环境。开启后,程序默认线程为CPU线程数,也可以运行时也可以动态指定运行的进程数,12为自定义的要使用的处理器数。
export OMP_NUM_THREADS=12
-mcmodel=medium
当单个Memory Array Size ⼤于2GB时需要设置此参数。
-DNTIMES=200
计算次数为200次。
-DSTREAM_ARRAY_SIZE=700000000
指定测试数组a[],b[],c[]的大小(成员个数)。
推荐计算公式1:A102410241024=38N,N= A102410241024/3/8。A值取值不超过内存单条容量的50%,算出N值为DSTREAM_ARRAY_SIZE。
解释:由于stream.c源码推荐设置至少4倍最高级缓存,且STREAM_ARRAY_SIZE为double类型=8 bit。所以公式为:最高级缓存(单位:Byte)×4.1倍×CPU路数/8
例如:测试机器是双路CPU,最高级缓存32MB,则计算值为32×1024×1024×4.1×2/8≈34393292
推荐计算公式2:{最高级缓存X MB}×1024×1024×4.1×CPU路数/8,结果取整数
stream.c -o stream.o
生成stream.o文件
完整示例:
gcc -O -fopenmp -DSTREAM_ARRAY_SIZE=100000000
-DNTIME=20 stream.c -o stream
结果说明
Copy操作:它先访问一个内存单元读出其中的值,
再将值写入到另一个内存单元
Scale操作:先从内存单元读出其中的值,作一个乘法运算,
再将结果写入到另一个内存单元
Add操作:先从内存单元读出两个值,做加法运算,
再将结果写入到另一个内存单元
Triad :将以上三个组合起来,在本测试中表示的意思是将Copy、Scale、Add
三种操作组合起来进行测试。具体操作方式是:先从内存单元中中读两个值a、b,
对其进行乘加混合运算(a + 因子 * b ) ,将运算结果写入到另一个内存单元。
测试命令脚本:
stream1:gcc -fopenmp -D_OPENMP stream.c -o stream &&export OMP_NUM_THREADS=1&&export GOMP_CPU_AFFINITY=0&&./stream
stream64:gcc -fopenmp -O3 -DSTREAM_ARRAY_SIZE=2000000000 -DNTIMES=80 -mcmodel=large stream.c -o stream &&export OMP_NUM_THREADS=64&&export GOMP_CPU_AFFINITY=0-63&&./stream
stream4:gcc -fopenmp -O3 -DSTREAM_ARRAY_SIZE=2000000000 -DNTIMES=80 stream.c -o stream &&export OMP_NUM_THREADS=4&&export GOMP_CPU_AFFINITY=0-3&&./stream
调优:修改stream.c里defind N 值 define N =L3乘以1024乘以(4.1/8 )取整数
内存带宽=搬运的内存大小/耗时。STREAM在计算时跳过第一次的结果,避免系统冷启动时的误差,取三次值求平均较好