首页 专利交易 科技果 科技人才 科技服务 国际服务 商标交易 会员权益 IP管家助手 需求市场 关于龙图腾
 /  免费注册
到顶部 到底部
清空 搜索

一种基于INTEL AVX指令集的浮点峰值计算吞吐测试方法 

买专利卖专利找龙图腾,真高效! 查专利查商标用IPTOP,全免费!专利年费监控用IP管家,真方便!

申请/专利权人:青岛雷神科技股份有限公司

摘要:本发明公开了一种基于INTELAVX指令集的浮点峰值计算吞吐测试算法,包括以下步骤:步骤1:AVX128BitADDSub;步骤2:AVX128bitMul;步骤3:AVX128BitFMA;步骤4:AVX128BitADD+Mul;步骤5:AVX256BitADDSub;步骤6,AVX256BitMul;步骤7,AVX256BitFMA;步骤8,AVX256BitADD+Mul;步骤9,AVX512BitADDSub;步骤10,AVX512BitMul;步骤11,AVX512BitADD+Mul;步骤12,AVX512BitFMA;步骤13,计算过程自动迭代和纳秒级计时;步骤14,针对不同处理器架构;步骤15,单线程测试+多线程调用;步骤16,显示出测试结果。本发明在尽可能短的测试时间下,可针对目前主流X86处理器的向量计算能力做出评估,帮助研究人员快速确定该架构处理器在SIMD吞吐中的设计,找到其基本计算能力的侧重点和性能峰值点。

主权项:1.一种基于INTELAVX指令集的浮点峰值计算吞吐测试方法,其特征在于,包括以下步骤:步骤1:AVX128BitADDSub;使用AVX组合浮点计算,首先要对寄存器进行加载操作,将相应数据加载到相应寄存器,这里使用128bitSIMD指令将加法要做的数值加载:const__m128dadd0=_mm_set1_pd,vmovaps指令可把4个对准的单精度值传送到xmm寄存器或者内存,vmovupd可把4个不对准的单精度值传送到xmm寄存器或者内存,将数值送入128bitxmm寄存器后,便可使用加法与减法指令执行Add或者Sub;使用add_ps语句将add0的数值与r0-r7的数值进行加法计算r0=_mm_add_psr0,add0;r1=_mm_add_psr1,add0;r2=_mm_add_psr2,add0;r3=_mm_add_psr3,add0;r4=_mm_add_psr4,add0;r5=_mm_add_psr5,add0;r6=_mm_add_psr6,add0;r7=_mm_add_psr7,add0;使用sub_ps语句将sub0的数值与r0-r7的数值进行组合浮点减法计算r0=_mm_sub_psr0,sub0;r1=_mm_sub_psr1,sub0;r2=_mm_sub_psr2,sub0;r3=_mm_sub_psr3,sub0;r4=_mm_sub_psr4,sub0;r5=_mm_sub_psr5,sub0;r6=_mm_sub_psr6,sub0;r7=_mm_sub_psr7,sub0;编译器将使用SIMD模式编译为vaddpsxmm0,xmm6,xmm4的语句或者vsubpsxmm0,xmm6,xmm4的语句,这样就构成了AVX-128向量计算加法与减法的基本计算部分;步骤2:AVX128bitMul;Mul便是乘法计算的简写,在进行矢量乘法的时候,我们依旧要将数据装载入SIMD寄存器中,且保证对应的单精度和双精度占满SIMD寄存器,如计算32位单精度浮点数时,一个xmm寄存器需打包4个单精度浮点数和2个双精度浮点数乘法计算部分仍然为之前的数据加载,加载至mul0、mul1两个寄存器中,但计算部分调用12个寄存器,进行4组乘法计算,对mul0的两组,对mul1的两组r0=_mm_mul_psr0,mul0;r1=_mm_mul_psr1,mul0;r2=_mm_mul_psr2,mul0;r3=_mm_mul_psr3,mul0;r4=_mm_mul_psr4,mul0;r5=_mm_mul_psr5,mul0;r6=_mm_mul_psr6,mul0;r7=_mm_mul_psr7,mul0;r8=_mm_mul_psr8,mul0;r9=_mm_mul_psr9,mul0;rA=_mm_mul_psrA,mul0;rB=_mm_mul_psrB,mul0;r0=_mm_mul_psr0,mul1;r1=_mm_mul_psr1,mul1;r2=_mm_mul_psr2,mul1;r3=_mm_mul_psr3,mul1;r4=_mm_mul_psr4,mul1;r5=_mm_mul_psr5,mul1;r6=_mm_mul_psr6,mul1;r7=_mm_mul_psr7,mul1;r8=_mm_mul_psr8,mul1;r9=_mm_mul_psr9,mul1;rA=_mm_mul_psrA,mul1;rB=_mm_mul_psrB,mul1;r0=_mm_mul_psr0,mul0;r1=_mm_mul_psr1,mul0;r2=_mm_mul_psr2,mul0;r3=_mm_mul_psr3,mul0;r4=_mm_mul_psr4,mul0;r5=_mm_mul_psr5,mul0;r6=_mm_mul_psr6,mul0;r7=_mm_mul_psr7,mul0;r8=_mm_mul_psr8,mul0;r9=_mm_mul_psr9,mul0;rA=_mm_mul_psrA,mul0;rB=_mm_mul_psrB,mul0;r0=_mm_mul_psr0,mul1;r1=_mm_mul_psr1,mul1;r2=_mm_mul_psr2,mul1;r3=_mm_mul_psr3,mul1;r4=_mm_mul_psr4,mul1;r5=_mm_mul_psr5,mul1;r6=_mm_mul_psr6,mul1;r7=_mm_mul_psr7,mul1;r8=_mm_mul_psr8,mul1;r9=_mm_mul_psr9,mul1;rA=_mm_mul_psrA,mul1;rB=_mm_mul_psrB,mul1;编译器将使用SIMD模式编译为vmulpsxmm0,xmm6,xmm4的语句,这样就构成了AVX-128向量计算乘法的基本计算部分;步骤3:AVX128BitFMA;融合乘加指令集分两种,基于Intel处理器支持的为FMA3,基于AMDBulldozer和Piledriver架构处理器的为FMA4指令集,这两者之间的区别在于支持的操作数有不同,FMA3指令可实现三操作数的融合乘加指令,即完成单指令A=A+B*C的计算,四操作数的FMA4指令,即A=B+C*D的计算,这样在运作中一次调用的寄存器数量也不同;FMA3128bit同时FMA3主要有4种融合模式,即融合乘加Vfmadd,乘减融合Vfmsub,负的乘加融合Vfnmadd-a*b+c,负的乘减融合Vfnmsub-a*b-c针对三操作数的浮点计算算法,将融合乘加与负的融合乘加指令结合,让CPU执行基于FMA3指令集的融合乘加与负的融合乘加计算,同时加载命令不变,依旧是使用_mm_set1_ps指令,使用融合乘加FMA3需要同时执行三个操作数:r0=_mm_fmadd_psmul0,mul1,r0;r1=_mm_fmadd_psmul0,mul1,r1;r2=_mm_fmadd_psmul0,mul1,r2;r3=_mm_fmadd_psmul0,mul1,r3;r4=_mm_fmadd_psmul0,mul1,r4;r5=_mm_fmadd_psmul0,mul1,r5;r6=_mm_fmadd_psmul0,mul1,r6;r7=_mm_fmadd_psmul0,mul1,r7;r8=_mm_fmadd_psmul0,mul1,r8;r9=_mm_fmadd_psmul0,mul1,r9;rA=_mm_fmadd_psmul0,mul1,rA;rB=_mm_fmadd_psmul0,mul1,rB;这里Vfmaddps语句将mul0、mul1和寄存器r0的数据进行融合乘加等价于r0=mul0*mul1+r0将结果存入r0到rb一共12个寄存器中,加上原本mul0与mul1的两个寄存器,一共占用14个寄存器,另一部分使用负的融合乘加指令Vfnmadd替换Vfmadd即可;FMA4128bitFMA4指令的代码不同于FMA3的Vfmaddps这类语句,而是_mm_nmacc_ps和_mm_macc_ps这样的语句来执行融合乘加和负的融合乘加操作;步骤4:AVX128BitADD+Mul;本步骤采用上述的乘法和加法的部分;步骤5:AVX256BitADDSub;const__m256mul0=_mm256_set1_psconst__m256mul1=_mm256_set1_ps,定义装载256位寄存器,同时计算部分要使用256bit定义,加法语句为:r0=_mm256_add_psr0,add0;步骤6,AVX256BitMul;同AVX128BitMul内容,需在_mm_mul前加入256进行定义即可;步骤7,AVX256BitFMA;同AVX128BitFMA内容,需在_mm_fmadd_ps前加入256进行定义即可;步骤8,AVX256BitADD+Mul;同AVX128BitADD与Mul内容,需在_mm_add_ps和_mm_sub_ps前加入256进行定义即可;步骤9,AVX512BitADDSub;采用512位定义的AVX512C++语言模式,即_mm512_add_ps和_mm512_sub_ps;步骤10,AVX512BitMul;采用512位定义的AVX512C++语言模式,即_mm512_mul_ps;步骤11,AVX512BitADD+Mul;使用乘法与加法结合的形式,乘法和加法都分别计算,使用_mm512_add_ps和_mm512_mul_ps指令执行;步骤12,AVX512BitFMA;将步骤11的Mul、ADD乘法加法指令分别执行,改用FMA指令执行,即_mm512_fmadd_ps;步骤13,计算过程自动迭代和纳秒级计时;从pentium开始,很多80x86微处理器都引入TSC,一个用于时间戳计数器的64位的寄存器,它在每个时钟信号到来时加一;计算部分需要while—iterations循环迭代,迭代上十亿次,定义struct结构体关键字,results是定义的结果,具体声明了拥有2个成员的结构体,分别为双精度的flops值和sum总和,flops值即浮点操作次数,定义相应的类名:benchmark,即测试结果,最终表示为Gflops每秒,在固定的时间内即可,voidrun将执行线程和时间的值输入,同时每次迭代会有多个block进行计算,各个线程同时记录返回值,最终浮点操作次数=iterations*flops_per_iteration*block_sizeseconds,iterations为迭代次数,flops_per_iteration为每次迭代的浮点操作次数,block_size为数据块大小,seconds为秒,以上为测试线程的定义,确定计算的量和flops的结果,将结果除以10亿即为Gflops;步骤14,针对不同处理器架构:由于不同时代的处理器支持的指令集不同,所以应当选择合适的指令集编译文件进行测试,以防运行出错,所以针对目前主流CPU,主要分为7个大类:Core2-SSE128bit体系Sandybridge-AVX体系Haswell-AVX2FMA3体系AMDBulldozerAVXFMA4体系AMDPiledriverAVX2FMA4体系IntelpurleyAVX512FMA3体系AMDZenAVX2FMA3体系验证处理器是否支持相应指令集才可运行,运行CPUID识别程序即可,识别是否支持AVX-AVX2-FMA3-FMA4-AVX512指令集,CPU信息现在存储于EAX寄存器,检测AVX和FMA指令集;通过读取EAX寄存器相应地址,获取返回值后识别,若不支持相应指令集,则不运行该指令集的浮点计算测试;步骤15,单线程测试+多线程调用:该计算程序的执行默认将执行单线程运算,C++11新标准中引入C++11新标准中引入四个头文件来支持多线程编程,他们分别是atomic,thread,mutex,condition_variable和future;语句std::thread::hardware_concurrency,返回实现支持的并发线程数;当确认支持的线程并发数之后,需要使用std::threadt[num_threads];建立相应数量的线程;步骤16,显示出测试结果:当某个计算步骤迭代完成后,将由相应的计算次数与计算的时间进行除法,输出对应的浮点计算次数。

全文数据:一种基于INTELAVX指令集的浮点峰值计算吞吐测试算法技术领域[0001]本发明涉及浮点算法领域,具体为一种基于INTELAVX指令集的浮点峰值计算吞吐测试算法。背景技术[0002]过去,主流CPU通过提高每秒指令执行次数来提高CPU在单位时间内的计算能力,通常每个时钟周期执行一条指令完成一次计算,但随着计算的复杂度增加,CPU内部引入了流水线执行的方式,即将一个完整的指令执行步骤拆分成多个步骤,由各个寄存器按流水线的形式分别完成,每个时钟周期同样完成一次操作,只要流水线能稳定运行下去,依旧可以做到近似一个时钟周期有一条指令完成,这种一个时钟周期完成一条指令的形式,也被称为标量处理器。[0003]但随着CPU每秒时钟周期数不断提高,也就是CPU主频不断提高,要想继续提升主频就相当困难了,于是在CPU内加入多个指令执行流水线,做到同时有多个流水线在几乎同时进行指令执行的流水工作,在受到缓存缺失,分支预测失败等情况的影响下,依旧能实现每个时钟周期平均执行超过一条指令的微处理器,也被称为超标量流水线架构。[0004]标量或是超标量处理器,都没有解决一个问题,那就是仍然是一条计算指令实现一次数值计算,但随着单纯增加执行单元对功耗发热的影响越来越大,CPU的计算性能发展为多线程并发与SMD并行两种思路,多线程仍然没有改变指令层面的执行,仍旧是提高单位时间内指令执行的数量,而SIMD则改变了过去指令执行的基本思想,引入了向量矢量)计算的概念。[0005]过去无论计算8位16位32位抑或其他数据类型的计算,一次指令执行往往就是一组数值的计算,如1+1,2X2,1.00001X1.000001等,而SMD指令集则提供了一条指令同时执行多组数值计算的可能,如定义数据类型为32位浮点单精度浮点)。[0006]而有4组数值计算,如A+B,C+D,E+F,G+H,分别将A,C,E,G装入一个128bitSMD寄存器,B,D,F,H装入另一个128bitSMD寄存器,然后这两个寄存器相加的指令操作就完成了4次32位浮点计算,也就大大提高了计算效率,如图1所示。[0007]随着CPU的发展,如今向量指令集的位宽也在不断增大,支持的直接指令操作也在不断增加,不同数据类型之间的数据对齐支持,浮点数与整数数据的转换都越来越方便,X86CPU上从MMX到SSE再到AVX,如今AVX512指令集可支持512bit寄存器,同时打包8个64位双精度浮点浮点数和16个32位单精度浮点数),同时为应对一些混合计算如乘法加法并存的计算,引入了FMAFusedmultiplyAdd融合乘加指令,如FMA3指令可实现三操作数的融合乘加指令,即完成单指令A=A+B*C的计算A,B,C三个操作数),抑或四操作数的FMA4指令,S卩A=B+C*D的计算A,B,C,D为四个操作数)。[0008]但是向量化指令对计算并行度要求也相当高,由于大量软件依旧使用较老的SIMD指令体系编译或专门的高度向量化编译的软件常人难以接触,使得最新处理器的峰值性能往往被人忽视,同时为了确定在不同处理器中,因为指令体系,寄存器,流水线的一些限制,也会使得在进行不同计算时吞吐量有所不同,如可能因为FMA单元和AddMul单元的设计不同,进行乘法,加法,或者乘法加法混合计算以及FM融合计算下的吞吐量是不同的,甚至在某些SIMD寄存器中,整数计算和浮点计算可以占用的位宽也是不同的,所以通过编写相应计算程序,并调用最新指令集,尽可能将数据关联性降低,提高并行性和降低分支预测难度,通过精确的计时测算就可以计算出处理器的加法减法乘法或混合计算以及融合乘加计算下的最大峰值,也可通过不同矢量位宽指令的运用,计算出在128256512bitSHffi指令集寄存器的浮点计算峰值。[0009]同时由于当代CPU多核多线程已成为主流,对CPU浮点峰值的计量不仅仅需要考虑SMD向量指令集的充分利用,还要考虑多线程并发的实现,使其成为高并发,高并行,高向量化的可执行程序。[0010]同时,针对AVX512浮点计算的benchmark,由于为最新的SIMD指令集,需要参照Intel64andIA_32ArchitecturesSoftwareDeveloper’sManual以及IntelC++编译器ICC编译器的向量化操作得以实现。发明内容[0011]本发明的目的在于提供一种基于INTELAVX指令集的浮点峰值计算吞吐测试算法,在拿到一颗支持向量化指令集的CPU时,可以快速通过该算法软件迅速测的其在加法减法,乘法或使用融合乘加指令下的浮点计算峰值,并且最大化使用最新向量指令集进行计算,从而准确计算出该CPU能达到的浮点计算峰值,分析CPU在进行矢量计算情况下的基本性能,以及运行类似浮点密集计算的基本运行情况。[0012]为实现上述目的,本发明提供如下技术方案:一种基于INTELAVX指令集的浮点峰值计算吞吐测试算法,包括以下步骤:[0013]步骤1:AVX128BitADDSub;[0014]使用AVX组合浮点计算,首先要对寄存器进行加载操作,将相应数据加载到相应寄存器,这里使用128bitSIMD指令将加法要做的数值加载:const__ml28daddO=_mm_setl_pd,vmovaps指令可把4个对准的单精度值传送到xmm寄存器或者内存,vmovupd可把4个不对准的单精度值传送到xmm寄存器或者内存,将数值送入128bitXMM寄存器后,便可使用加法与减法指令执行Add或者Sub;[0015]使用add_ps语句将addO的数值与r〇-r7的数值进行加法计算[0024]使用sub_ps语句将subO的数值与r〇-r7的数值进行组合浮点减法计算[0033]编译器将使用SIMD模式编译为vaddpsxmm0,xmm6,xmm4的语句或者vsubpsxmmO,xmm6,xmm4的语句,[0034]这样就构成了AVX-128向量计算加法与减法的基本计算部分;[0035]步骤2:AVX128bitMul;[0036]Mui便是乘法计算的简写,在进行矢量乘法的时候,我们依旧要将数据装载入snro寄存器中,且保证对应的单精度和双精度占满snro寄存器,如计算32位单精度浮点数时,一个XMM寄存器需打包4个单精度浮点数和2个双精度浮点数乘法计算部分仍然为之前的数据加载,加载至muio.mull两个寄存器中,但计算部分调用12个寄存器,进行4组乘法计算,对mulO的两组,对mull的两组;[0085]编译器将使用SIMD模式编译为vmulpsxmmO,xmm6,xmm4的语句,这样就构成了AVX-128向量计算乘法的基本计算部分;[0086]步骤3:AVX128BitFMA;[0087]融合乘加指令集分两种,基于Intel处理器支持的为FMA3,基于AMDBulldozer和Piledriver架构处理器的为FMA4指令集,这两者之间的区别在于支持的操作数有不同,FMA3指令可实现三操作数的融合乘加指令,即完成单指令A=A+B*C的计算,四操作数的FMA4指令,S卩A=B+C*D的计算,这样在运作中一次调用的寄存器数量也不同;[0088]FMA3128bit[0089]同时FMA3主要有4种融合模式,即融合乘加Vfmadd,乘减融合Vfmsub,负的乘加融合Vfnmadd_axb+c,负的乘减融合Vfnmsub_axb-c[0090]针对三操作数的浮点计算算法,将融合乘加与负的融合乘加指令结合,让CPU执行基于FMA3指令集的融合乘加与负的融合乘加计算,同时加载命令不变,依旧是使用_mm_setl_ps指令,使用融合乘加FMA3需要同时执行三个操作数:[0103]这里fmaddps语句将mul0,mull和寄存器rO的数据进行融合乘加等价于r0=mul0xmull+rO将结果存入rO到rb—共12个寄存器中,加上原本mulO与mull的两个寄存器,一共占用14个寄存器,另一部分使用负的融合乘加指令fnmadd替换fmadd即可;[0104]FMA4128bit[0105]FMA4指令的代码不同于FMA3的Vfmaddps这类语句,而是_mm_nmacc_ps*_mm_macc_ps这样的语句来执行融合乘加和负的融合乘加操作;[0106]步骤4:AVX128BitADD+Mul;[0107]本步骤采用上述的乘法和加法的部分;[0108]步骤5:AVX256BitADDSub;[0110]const_m256mulI=_mm256_setl_ps,定义装载256位寄存器,同时计算部分要使用256bit定义,加法语句为:[0112]步骤6,AVX256BitMul;[0113]同AVX128BitMul内容,需在前加入256进行定义即可;[0114]步骤7,AVX256BitFMA;[0115]同AVX128BitFMA内容,需在_mm_fmaddps前加入256进行定义即可;[0116]步骤8,AVX256BitADD+Mul;[0117]同AVX128Bitadd与mul内容,需在_mm_addps*_mm_subps前加入256进行定义即可;[0118]步骤9,八¥父5128优八0051*[0119]同上一步骤;[0120]步骤l〇,AVX512BitMul[0121]同上一步骤;[0122]步骤11,八¥父5128^八00+]«111[0123]同上一步骤;[0124]步骤12,八¥父5128优卩嫩[0125]同上一步骤,但AVX512指令集支持需集成ICC编译器支持,才能将C++语句编译为AVX512汇编语句;[0126]步骤13,计算过程自动迭代和纳秒级计时;[0127]从Pentium开始,很多80x86微处理器都引入TSC,一个用于时间戳计数器的64位的寄存器,它在每个时钟信号到来时加一;[0128]计算部分需要while—iterations循环迭代,迭代最好上十亿次,IG次[0131]以上为测试线程的定义,确定计算的量和flops的结果[0132]将结果除以10亿,单位为Gflops;[0133]步骤14,针对不同处理器架构[0134]由于不同时代的处理器支持的指令集不同,所以应当选择合适的指令集编译文件进行测试,以防运行出错,所以针对目前主流CPU,主要分为7个大类:[0135]Core2-SSE128bit体系[0136]Sandybridge-AVX体系[0137]Haswell_AVX2FMA3体系[0138]AMDBulldozerAVXFMA4体系[0139]AMDPiledriverAVX2FMA4体系[0140]IntelpurleyAVX512FMA3体系[0141]AMDZenAVX2FMA3体系[0142]验证处理器是否支持相应指令集才可运行,运行CPUID识别程序即可,识别是否支持AVX-AVX2-FMA3-FMA4-AVX512指令集,CPU信息现在存储于EAX寄存器,检测AVX和FMA指令集;通过读取EAX寄存器相应地址,获取返回值后识别,若不支持相应指令集,则不运行该指令集的浮点计算测试;[0143]步骤15,单线程测试+多线程调用:[0144]该计算程序的执行默认将执行单线程运算,C++11新标准中引入C++11新标准中引入四个头文件来支持多线程编程,他们分别是〈atomic〉,〈thread〉,〈mutex〉,〈condition_variable〉和〈future〉;语句std::thread::hardware_concurrency,返回实现支持的并发线程数;当确认支持的线程并发数之后,需要使用std::threadt[num_threads];建立相应数量的线程;[0145]步骤16,显示出测试结果:[0146]当某个计算步骤迭代完成后,将由相应的计算次数与计算的时间进行除法,输出对应的浮点计算次数。[0147]与现有技术相比,本发明的有益效果是:本发明在尽可能短的测试时间下,可针对目前主流X86处理器的向量计算能力做出评估,包含SSEAVX128位矢量256位矢量和512位矢量指令集下的乘加计算能力,实际测试结果可接近理论硬件吞吐峰值,帮助研究人员快速确定该架构处理器在SIMD吞吐中的设计,找到其基本计算能力的侧重点和性能峰值点。附图说明[0148]图1为4次32位浮点计算流程图;[0149]图2为本发明流程图。具体实施方式[0150]下面将结合本发明实施例中的附图,对本发明实施例中的技术方案进行清楚、完整地描述,显然,所描述的实施例仅仅是本发明一部分实施例,而不是全部的实施例。基于本发明中的实施例,本领域普通技术人员在没有做出创造性劳动前提下所获得的所有其他实施例,都属于本发明保护的范围。[0151]请参阅图2,本发明提供一种技术方案:一种基于INTELAVX指令集的浮点峰值计算吞吐测试算法,包括以下步骤:进行此类程序编写,需明确需求,要实现的效果是测试CPU的SMD峰值浮点性能,而还要考虑加法器,乘法器以及FMA融合乘加的吞吐量,同时基于AVX指令集来实现浮点峰值的计算,由于要追求较快速和精确的测试数据,需要对程序执行过程中的实际运行部分进行计时,将最终的浮点计算结果显示出来,单位flops。[0152]首先是计算部分程序的编写,由于要测试矢量化的浮点计算性能,所以我们按先加减,后乘除,最后FM融合乘加三大计算部分来进行计算,从而得到浮点计算值。[0153]步骤1,AVX128BitADDSub,加减:[0154]使用AVX组合浮点计算,首先要对寄存器进行加载操作,将相应数据加载到相应寄存器,这里使用128bitSIMD指令将加法要做的数值加载:const__ml28daddO=_mm_setl_pdx浮点数)(对应汇编语句vmovupsvmovaps指令),将要进行减计算的初始值装入到另一个128bitSIMD寄存器中:const_ml28dsub0=_mm_setl_pdy浮点数),vmovaps指令可把4个对准的单精度值传送到xmm寄存器或者内存,vmovupd可把4个不对准的单精度值传送到xmm寄存器或者内存,将数值送入128bitXMM寄存器后,便可使用加法与减法指令执行Add或者Sub。[0155]使用add_ps语句将addO的数值与r〇-r7的数值进行加法计算[0164]使用sub_ps语句将subO的数值与r〇-r7的数值进行组合浮点减法计算[0173]编译器将使用SIMD模式编译为vaddpsxmm0,xmm6,xmm4这样的语句加法组合计算,XMM为128bit寄存器或者vsubpsxmm0,xmm6,xmm4减法组合计算)的语句[0174]这样就构成了AVX-128向量计算加法与减法的基本计算部分[0175]步骤2,AVX128bitMul,乘;[0176]MuI便是乘法计算的简写,在进行矢量乘法的时候,我们依旧要将数据装载入snro寄存器中,且保证对应的单精度和双精度占满Snro寄存器,如计算32位单精度浮点数时,一个XMM寄存器需打包4个单精度浮点数和2个双精度浮点数乘法计算部分仍然为之前的数据加载,加载至mulO.mull两个寄存器中,但计算部分调用12个寄存器,进行4组乘法计算相当于48次128bit乘法),对muIO的两组,对mu11的两组[0225]编译器将使用SMD模式编译为vmulpsxmm0,xmm6,xmm4这样的语句乘法组合计算,XMM为128bit寄存器这样就构成了AVX-128向量计算乘法的基本计算部分[0226]步骤3,AVX128BitFMA,融合乘加;[0227]融合乘加指令集分两种,基于Intel处理器支持的为FMA3,基于AMDBulldozer和Piledriver架构处理器的为FMA4指令集,这两者之间的区别在于支持的操作数有不同,FMA3指令可实现三操作数的融合乘加指令,即完成单指令A=A+B*C的计算A,B,C三个操作数),四操作数的FMA4指令,S卩A=B+C*D的计算A,B,C,D为四个操作数),这样在运作中一次调用的寄存器数量也不同。[0228]FMA3128bit[0229]同时FMA3主要有4种融合模式,即融合乘加Vfmadd,乘减融合Vfmsub,负的乘加融合Vfnmadd_axb+c,负的乘减融合Vfnmsub_axb-c[0230]针对三操作数的浮点计算算法,可以选择全部为融合乘法加法的模式,也可分不同模式。如融合乘加与融合乘减结合,我们将融合乘加与负的融合乘加指令结合,让CPU执行基于FMA3指令集的融合乘加与负的融合乘加计算,同时加载命令不变,依旧是使用_mm_setl_ps指令,但使用融合乘加FMA3需要同时执行三个操作数[0243]这里fmaddps语句将mul0,mull和寄存器rO的数据进行融合乘加等价于r0=mul0xmull+rO将结果存入rO到rb—共12个寄存器中,加上原本mulO与mull的两个寄存器,一共占用14个寄存器,同理另一部分使用负的融合乘加指令fnmadd替换fmadd即可[0244]FMA4128bit[0245]FMA4指令的代码不同于FMA3的Vfmaddps这类语句,而是_mm_nmacc_ps*_mm_maCC_ps这样的语句来执行融合乘加和负的融合乘加操作代码格式类似于FMA3操作,[0248]步骤4,AVX128BitADD+Mul[0249]这里可参考上文乘法和加法的部分;[0250]步骤5,AVX256BitADDSub加减)[0251]const_m256mul0=_mm256_setl_ps[0252]const_m256mull=_mm256_setl_ps,定义装载256位寄存器,同时计算部分要使用256bit定义,如加法语句应该为:[0253]r0=_mm256_add_psr0,add0;[0254]步骤6,AVX256BitMul乘)[0255]参考AVX128BitMul内容,仅需在前加入256进行定义即可[0256]步骤7,AVX256BitFMA融合乘加)[0257]参考AVX128BitFMA内容,仅需在_mm_fmaddps前加入256进行定义即可[0258]步骤8,AVX256BitADD+Mul[0259]参考AVX128Bitadd与mul内容,仅需在_!11111_1^8和_1]1111_8油口8前加入256进行定义即可[0260]步骤9,AVX512BitADDSub[0261]以此类推;[0262]步骤1〇,八¥父5128优]«111[0263]以此类推;[0264]步骤11,AVX512BitADD+Mul[0265]以此类推;[0266]步骤12,AVX512BitFMA[0267]以此类推,但AVX512指令集支持需集成ICC编译器支持,才能将C++语句编译为AVX512汇编语句;[0268]步骤13,计算过程自动迭代和纳秒级计时[0269]从pentium开始,很多80x86微处理器都引入TSC,一个用于时间戳计数器的64位的寄存器,它在每个时钟信号CLK,CLK是微处理器中一条用于接收外部振荡器的时钟信号输入引线到来时加一。[0270]通过它可以计算CPU的主频,比如:如果微处理器的主频是IMHZ的话,那么TSC就会在1秒内增加1000000。除了计算CHJ的主频外,还可以通过TSC来测试微处理器其他处理单元的运算速度。[0271]那么如何获取TSC的值呢?可以使用rdtsc,一条读取TSC的指令,它把TSC的低32位存放在EAX寄存器中,把TSC的高32位存放在EDX中,通过获取主频确定CPU执行的时间和周期,由于CPU每周期时间都以纳秒以下计,所以能将时间计数精确到纳秒级[0272]计算部分需要while—iterations循环迭代,迭代最好上十亿次,IG次[0275]以上为测试线程的定义,确定计算的量和fIops的结果[0276];将结果除以10亿,单位为Gflops[0277]步骤14,针对不同处理器架构;[0278]由于不同时代的处理器支持的指令集不同,所以应当选择合适的指令集编译文件进行测试,以防运行出错,所以针对目前主流CPU,主要分为7个大类[0279]Core2-SSE128bit体系[0280]Sandybridge-AVX体系[0281]Haswell_AVX2FMA3体系[0282]AMDBulldozerAVXFMA4体系[0283]AMDPiledriverAVX2FMA4体系[0284]IntelpurleyAVX512FMA3体系[0285]AMDZenAVX2FMA3体系[0286]需验证处理器是否支持相应指令集才可运行,运行CPUID识别程序即可,识别是否支持AVX-AVX2-FMA3-FMA4-AVX512指令集,CPU信息现在存储于EAX寄存器,检测AVX和FMA指令集。需通过读取EAX寄存器相应地址,获取返回值后才能识别,若不支持相应指令集,则不能运行该指令集的浮点计算测试[0287]步骤15,单线程测试+多线程调用;[0288]—般计算机程序是默认串行计算的,所以,该计算程序的执行默认将执行单线程运算,但这是远远不够的,C++11新标准中引入C++11新标准中引入了四个头文件来支持多线程编程,他们分别是〈atomic〉,〈thread〉,〈mutex〉,〈condition_variable和〈future〉。语句std::thread::hardware_concurrency,返回实现支持的并发线程数。该值应该被认为只是一个提示。当确认支持的线程并发数之后,需要使用std::threadt[num_threads];建立相应数量的线程[0289]步骤16,显示出测试结果;[0290]当某个计算步骤迭代完成后,将由相应的计算次数(需要计算的计算总量是固定值与计算的时间进行除法,输出对应的浮点计算次数,实测结果大约为理论值98%以上,由于使用顺序重复数值计算,CPU几乎不需考虑分支预测和缓存映射,能直接表现出几乎全部计算能力。[0291]本发明在尽可能短的测试时间下,可针对目前主流X86处理器的向量计算能力做出评估,包含SSEAVX128位矢量256位矢量和512位矢量指令集下的乘加计算能力,实际测试结果可接近理论硬件吞吐峰值,帮助研究人员快速确定该架构处理器在snro吞吐中的设计,找到其基本计算能力的侧重点和性能峰值点。[0292]尽管已经示出和描述了本发明的实施例,对于本领域的普通技术人员而言,可以理解在不脱离本发明的原理和精神的情况下可以对这些实施例进行多种变化、修改、替换和变型,本发明的范围由所附权利要求及其等同物限定。

权利要求:1.一种基于INTELAVX指令集的浮点峰值计算吞吐测试算法,其特征在于,包括以下步骤:步骤1:AVX128BitADDSub;使用AVX组合浮点计算,首先要对寄存器进行加载操作,将相应数据加载到相应寄存器,这里使用128bitSIMD指令将加法要做的数值加载:const__ml28daddO=_mm_setl_pd,vmovaps指令可把4个对准的单精度值传送到xmm寄存器或者内存,vmovupd可把4个不对准的单精度值传送到xmm寄存器或者内存,将数值送入128bitXMM寄存器后,便可使用加法与减法指令执行Add或者Sub;使用add_ps语句将addO的数值与r〇-r7的数值进行加法计算使用sub_ps语句将subO的数值与r〇-r7的数值进行组合浮点减法计算编译器将使用SIMD模式编译为vaddpsxmm0,xmm6,xmm4的语句或者vsubpsxmmO,xmm6,xmm4的语句,这样就构成了AVX-128向量计算加法与减法的基本计算部分;步骤2:AVX128bitMul;Mul便是乘法计算的简写,在进行矢量乘法的时候,我们依旧要将数据装载入SMD寄存器中,且保证对应的单精度和双精度占满SIMD寄存器,如计算32位单精度浮点数时,一个XMM寄存器需打包4个单精度浮点数和2个双精度浮点数乘法计算部分仍然为之前的数据加载,加载至mulO.mull两个寄存器中,但计算部分调用12个寄存器,进行4组乘法计算,对mulO的两组,对mull的两组编译器将使用SIMD模式编译为vmuIpsxmmO,xmm6,xmm4的语句,这样就构成了AVX-128向量计算乘法的基本计算部分;步骤3:AVX128BitFMA;融合乘加指令集分两种,基于Intel处理器支持的为FMA3,基于AMDBu11dozer和Piledriver架构处理器的为FMA4指令集,这两者之间的区别在于支持的操作数有不同,FMA3指令可实现三操作数的融合乘加指令,即完成单指令A=A+B*C的计算,四操作数的FMA4指令,S卩A=B+C*D的计算,这样在运作中一次调用的寄存器数量也不同;FMA3128bit同时FMA3主要有4种融合模式,即融合乘加Vfmadd,乘减融合Vfmsub,负的乘加融合Vfnmadd_axb+c,负的乘减融合Vfnmsub_axb-c针对三操作数的浮点计算算法,将融合乘加与负的融合乘加指令结合,让CHJ执行基于FMA3指令集的融合乘加与负的融合乘加计算,同时加载命令不变,依旧是使用_mm_setl_ps指令,使用融合乘加FMA3需要同时执行三个操作数:这里fmaddps语句将mulO,mull和寄存器rO的数据进行融合乘加等价于rO=mulOxmull+rO将结果存入rO到rb—共12个寄存器中,加上原本mulO与mull的两个寄存器,一共占用14个寄存器,另一部分使用负的融合乘加指令fnmadd替换fmadd即可;FMA4128bit?1\^4指令的代码不同于?]\^3的\^1]11^8这类语句,而是_1]1111_111]1^_卩8和_1]1111_1]1^_口8这样的语句来执行融合乘加和负的融合乘加操作;步骤4:AVX128BitADD+Mul;本步骤采用上述的乘法和加法的部分;步骤5:AVX256BitADDSub;const—m256mul0=_mm256_setl_psconst__m256mull=_mm256_setl_ps,定义装载256位寄存器,同时计算部分要使用256bit定义,加法语句为:r0=_mm256_add_psrO,addO;步骤6,AVX256BitMul;同AVX128BitMul内容,需在前加入256进行定义即可;步骤7,AVX256BitFMA;同AVX128BitFMA内容,需在_mm_fmaddps前加入256进行定义即可;步骤8,AVX256BitADD+Mul;同AVX128Bitadd与mul内容,需在_mm_addps*_mm_subps前加入256进行定义即可;步骤9,AVX512BitADDSub同上一步骤;步骤104¥乂5128^]«111同上一步骤;步骤114¥父5128优厶00+]«111同上一步骤;步骤124¥乂5128优卩嫩同上一步骤,但AVX512指令集支持需集成ICC编译器支持,才能将C++语句编译为AVX512汇编语句;步骤13,计算过程自动迭代和纳秒级计时;从Pentium开始,很多80x86微处理器都引入TSC,一个用于时间戳计数器的64位的寄存器,它在每个时钟信号到来时加一;计算部分需要while—iterations循环迭代,迭代最好上十亿次,IG次以上为测试线程的定义,确定计算的量和flops的结果将结果除以10亿,单位为Gflops;步骤14,针对不同处理器架构由于不同时代的处理器支持的指令集不同,所以应当选择合适的指令集编译文件进行测试,以防运行出错,所以针对目前主流CPU,主要分为7个大类:Core2-SSE128bit体系Sandybridge-AVX体系Haswel1-AVX2FMA3体系AMDBulldozerAVXFMA4体系AMDPiledriverAVX2FMA4体系IntelpurleyAVX512FMA3体系AMDZenAVX2FMA3体系验证处理器是否支持相应指令集才可运行,运行CPUID识别程序即可,识别是否支持AVX-AVX2-FMA3-FMA4-AVX512指令集,CPU信息现在存储于EAX寄存器,检测AVX和FMA指令集;通过读取EAX寄存器相应地址,获取返回值后识别,若不支持相应指令集,则不运行该指令集的浮点计算测试;步骤15,单线程测试+多线程调用:该计算程序的执行默认将执行单线程运算,C++11新标准中引入C++11新标准中引入四个头文件来支持多线程编程,他们分别是〈atomic〉,〈thread〉,〈mutex〉,〈condition_variable〉和〈future〉;语句std::thread::hardware_concurrency,返回实现支持的并发线程数;当确认支持的线程并发数之后,需要使用std::threadt[num_threads];建立相应数量的线程;步骤16,显示出测试结果:当某个计算步骤迭代完成后,将由相应的计算次数与计算的时间进行除法,输出对应的浮点计算次数。

百度查询: 青岛雷神科技股份有限公司 一种基于INTEL AVX指令集的浮点峰值计算吞吐测试方法

免责声明
1、本报告根据公开、合法渠道获得相关数据和信息,力求客观、公正,但并不保证数据的最终完整性和准确性。
2、报告中的分析和结论仅反映本公司于发布本报告当日的职业理解,仅供参考使用,不能作为本公司承担任何法律责任的依据或者凭证。