本文主要是介绍TFLite: neon基础知识,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!
neon介绍
Neon是适用于ARM Cortex-A系列处理器的一种SIMD(Single Instruction, Multiple Data)扩展结构。NEON有自己的执行管道和寄存器组,neon寄存器组包含32个64位的寄存器和16个128位的寄存器,它们分别被标识为(D0-D31),(Q0-Q15)。 实际上D寄存器和Q寄存器是重叠的,如下图所示。NEON 技术本质上是一种并行处理技术,通过并行处理可加速多媒体和信号处理算法(如视频编码/解码、2D/3D 图形等)。通过使用neon可极大的提高软件的性能。
Neon关键概念
1、数据类型
Neon寄存器可以存放大部分的基本数据类型,如int8、int16等。寄存器可以存放的数据个数跟寄存器大小和数据类型有关。比如64bit的寄存器可以存放8个int8类型数据。而128bit的寄存器则可以存放16个int8类型数据。
2、寄存器---向量(vector)
在neon中一个寄存器可以看作是一个向量。比如一个64bit的寄存器D0,当这个寄存器存放4个int16类型数据时,可以把它看作是一个向量,它包含了4个类型为int16的元素。
3、管道(lane)---元素
在上例中,当D0存放4个int16数据时,则此时D0有4个管道,管道0到管道3。管道0位于寄存器的低bit位。这个管道实际就对应了向量的元素概念。
4、Neon的数据装载顺序
假设一个uint16类型的数组为{0x0201,0x0403,0x0605,0x0807},则它在内存中低地址到高地址存放的顺序为0x01,0x02,0x03````0x08(小端模式)。内存中的数据装入neon寄存器时,是低地址内存数据放入neon寄存器的低地址上,高地址内存数据放入neon寄存器的高地址上。当neon寄存器数据装入内存中时,同样是neon寄存器的低地址数据放入的内存低地址上,neon寄存器的高地址数据放入的内存高地址上。所以内存中的数据经过neon处理后,数据的顺序是不会发生变化的。
如何使用Neon
1、intrinsics(内部函数)
使用intrinsics不如使用汇编优化效率高。但是使用intrinsics较为简单,且容易维护。这些函数在编译的时候会直接转化成Neon的汇编指令。为了支持这些内部函数必须要包含头文件arm_neon.h ,还要通过在编译的时候加入-mfloat-abi=softfp -mfpu=neon,同时需要打开-O2优化选项。使用intrinsics没法控制寄存器分配和内存对齐等。
如:
#include <arm_neon.h>
uint32x4_t double_elements(uint32x4_t input)
{
return(vaddq_u32(input, input));
}
2、开源库:
基于neon的开源库如Project Ne10、OpenMAX DL
3、汇编:
使用neon汇编优化的效果最好但是汇编移植性差,且难度较高。
4、自动向量化(Vectorizing Compilers):
通过添加一些编译选项来使能向量化编译,让编译器自动生成优化代码,但对于复杂算法就不行了。
Arm-neon网站:http://www.arm.com/zh/products/processors/technologies/neon.php
---------------------
作者:EmSoftEn
来源:CSDN
原文:https://blog.csdn.net/EmSoftEn/article/details/51834171?utm_source=copy
版权声明:本文为博主原创文章,转载请附上博文链接!
这篇关于TFLite: neon基础知识的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!