日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

NEON技术粗浅认识

發布時間:2023/12/8 编程问答 40 豆豆
生活随笔 收集整理的這篇文章主要介紹了 NEON技术粗浅认识 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

1、簡介

???????? 微處理器處理數據主要分為以下幾種:

Single instruction single data—SISD

Single instruction multiple data(vectormode)—SIMD

Single instruction multiple data(packeddata mode)—SIMD

(1)SISD

???????? 一次指令操作一個數據。如下例子4次指令操作才完成8個寄存器相加:

addro, r5

add r1,r6

addr2, r7

addr3, r8

?

(2)SIMD(vector mode)

???????? 一次指令可以處理多個數據,但是每個數據處理是順序執行,如下:

VADD.F32S24, S8, S16

//S24=S8+S16

//S25=S9+S17

//S26=S10+S18

//S27=S11+S19

一個指令,但是數據相加是順序執行。在ARM上這個也叫Vector Floating Point(VFP)。

(3)SIMD(packed data mode)

???????? 一次指令可以處理多個數據,由于使用大寄存器方式可以同時進行,如下:

VADD.I16Q10, Q8, Q9

一個指令將兩個64-bit寄存相加,I16表示數據類型int16,64-bit= 4 * 16,每個寄存器里4個16-bit lanes獨立相加,但是同時完成,如圖:

在ARM上這個叫做增強型SIMD技術或NEON技術。

2、寄存器信息

???????? 在armv7-A和armv7-R的體系架構上基本采用了neon技術,armv8也支持并與armv7兼容。VFP和NEON共用協處理器CP10和CP11的指令空間和寄存器,并成為ARM/Thumb指令集的一部分。

???????? NEON寄存器就會是由相同數據類型組成的元素向量,一個寄存器(即一個向量)劃分為多個管道,每個管道包含一個數據元素。每個neon指令就是這些管道元素并行操作,且互相不影響。Neon劃分為兩種向量:64-bit NEON vectors(doubleword簡稱D寄存器)和128-bit NEON vectors(quadword簡稱Q寄存器)。

64-bit NEON vectors包含:

8個8-bit elements(即8個管道,每個管道可以包含8bit的數據元素)

4個16-bit elements

2個32-bit elements

1個64-bit elements

128-bit NEONvectors包含:

16個8-bit elements

8個16-bit elments

4個32-bit elements

2個64-bit elements

???????? 這樣劃分就可以neon用在不同場景:像素處理8-bit,顏色處理16-bit等。

管道lane和元素element關系

執行neon指令:VADD.I16 Q0, Q1, Q2,Q代表128-bit寄存器,I16代表16-bit,這句話就是8個16-bit lanes的128-bit向量寄存器相加,如圖所示:

???????? VFP和NEON是共享寄存器空間,因此寄存器存是重疊的,如圖所示:

Neon 寄存器單元:

16個128-bit Q 寄存器,Q0~Q15

32個64-bit D寄存器,D0~D31

VFPv3-D32:

32個64-bit D寄存器,D0~D31

VFPv2或VFPv3-16:

16個64-bit D寄存器,D0~D15

VFP:

16個32-bit S寄存器

neon單元可以訪問Q0寄存器作為一個128-bit寄存器

neon單元可以訪問Q0寄存器作為兩個64-bit寄存器D0和D1

neon不能范圍32-bit的S寄存器,但VFP可以訪問32-bit

???????? 下表是neon支持的數據類型:

?

3、neon使用方法

(1)匯編

???????? 通過匯編直接時鐘neon指令:

.text

.arm

.global double_elements

double_elements:

vadd.i32 q0,q0,q0

bx? lr

.end

arm-hisiv300-linux-as -mfloat-abi=softfp-mfpu=neon-vfpv4 neon_as.S

m-hisiv300-linux-as -mfloat-abi=softfp-mfpu=neon-vfpv4 neon_as.S

該種方式效率最高,但是難度大,移植性差

?

(2)使用arm提供的Intrinsics函數

???????? 可以認為是內聯函數,但是在編譯時編譯器會將函數轉化為neon指令。調用該函數需要包含頭文件arm_neon.h,該頭文件包含了neon各種操作函數,具體可以該頭文件arm-hisiv300-linux/lib/gcc/arm-hisiv300-linux-uclibcgnueabi/4.8.3/include/arm_neon.h或參考文檔《neon_programmers_guide.pdf》附錄D。

簡單例子:

#include <arm_neon.h>

uint32x4_t double_elements(uint32x4_tinput)

{

???????? return(vaddq_u32(input,input));

}

arm-hisiv300-linux-gcc -mfloat-abi=softfp-mfpu=neon-vfpv4 -c neon_in.c

匯編結果如下:

?

(3)自動化向量(實際驗證未通過)

???????? 該方式需要對指針參數添加__restrict(用于限定和約束指針,表明指針是訪問一個數據對象的唯一且初始的方式)。簡單例子:

void add_ints(int * __restrictpa, int * __restrict pb, unsigned int n, int x)

{

???????? unsigned int i;

???????? for(i = 0; i < (n & ~3); i++)

?????????????????? pa[i] = pb[i] + x;

}

void add_floats(float *__restrict pa, float * __restrict pb, unsigned int n, float x)

{

??? unsigned int i;

??? for(i = 0; i < (n & ~3); i++)

??????? pa[i] = pb[i] + x;

}

arm-hisiv300-linux-gcc -mfloat-abi=softfp -mfpu=neon-vfpv4-ftree-vectorize?-ftree-vectorizer-verbose=1 -c neon_av.c

匯編如下:

???????? 該方法浮點運算會自動轉化為neon指令,而整型則不會。從第二小節可以知道neon支持整型操作,而實際圖像,顏色等都是整形數的,該方法對于這些操作就無法發揮neon指令優勢。

?

(4)使用第三方優化庫

???????? 以下列舉了已經用neon優化過的庫,編譯時加入neon參數,然后調用相應接口進行操作。

A.Ne10

官網:http://projectne10.github.com/Ne10/

git地址:https://github.com/projectNe10/Ne10

C接口函數提供了匯編和常用處理方法

?

B.OpenMAX DL

???????? 地址:http://www.khronos.org/openmax/ 網站無法打開

OpenMAX由Khronosgroup(也是open Gl制定者)制定的開放多媒體加速層,是一個不需要授權、跨平臺的軟件抽象層,以C語言實現的軟件接口,提供了一下系列處理音頻、視頻、靜態圖片的API。

OpenMAX自上而下分為三個層次:OpenMAX ALOpenMAXILOpenMAX DL

OpenMAX AL:Application Layer應用和多媒體中間層的標準接口,使得應用在多媒體接口上具有了可移植性

OpenMAX IL: Integration Layer,作為在嵌入式和移動設備中使用的audio,video,images codecs的底層接口。使得AP和多媒體框架可以以統一的方式訪問多媒體codec和支持組件。Codec可以是硬件和軟件的任意組合,對用戶透明。

OpenMAX DL: Development Layer,最底層使用neon進行了優化

?

C.ffmpeg

官網:http://ffmpeg.org/

git地址:https://github.com/FFmpeg/FFmpeg

???????? FFmpeg是一套可以用來記錄、轉換數字音頻、視頻,并能將其轉化為流的開源計算機程序。采用LGPLGPL許可證。它提供了錄制、轉換以及流化音視頻的完整解決方案。它包含了非常先進的音頻/視頻編解碼庫libavcodec,為了保證高可移植性和編解碼質量,libavcodec里很多code都是從頭開發的。

?????? 功能包括視頻采集功能、視頻格式轉換、視頻抓圖、給視頻加水印等。

?

DEigen3

?????? 官網:http://eigen.tuxfamily.org/

?????? Githubhttps://github.com/artsy/eigen

?????? Eigen是一個高層次的C ++庫,有效支持線性代數,矩陣和矢量運算,數值分析及其相關的算法

?

EPixman

?????? 官網:http://pixman.org/

?????? 2D圖形庫

?

Fx264

?????? 官網:http://www.videolan.org/developers/x264.html

?

GMath-neon

?????? 官網:http://code.google.com/p/math-neon/

??????

?

5hi3536 目前使用neon的方法

?????? 目前,我們只是編譯時添加了參數,未做其他處理:

CFLAGS +=-mfloat-abi=softfp -mfpu=neon-vfpv4 -mno-unaligned-access-fno-aggressive-loop-optimizations。簡單例子;

float sum1(floata, float b)

{

?????? return (a+b);

}

int sum2(int a,int b)

{

?????? return (a+b);

}

arm-hisiv300-linux-gcc -mfloat-abi=softfp -mfpu=neon-vfpv4-c neon.c

匯編如下:

也是對浮點進行了neon操作,而整型是保持不變的。

?????? 因此使用的是第三種自動化向量的方法。

?

4neon應用例子

?????? 在《neon_programmers_guide.pdf》文檔中舉了好多個neon使用的例子:

A.交換RGB顏色通道

B.處理非對齊數組

C.矩陣計算

D.向量積

E.轉換色彩深度

F.中值濾波

GFIR濾波

?

5、官方參考文檔

?????? Neon資料比價少,在arm官網上可以查到如下幾個資料,第一個是詳細說明。

neon_programmers_guide.pdf

introducing_neon.pdf

neon_support_in_compilation_tools.pdf

總結

以上是生活随笔為你收集整理的NEON技术粗浅认识的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。