基於FPGA的深度卷積神經網路的加速器設計
翻譯:卜居
【0. 摘要】
CNN已經廣泛用於影象識別,因為它能模仿生物視覺神經的行為獲得很高識別準確率。最近,基於深度學習演算法的現代應用高速增長進一步改善了研究和實現。特別地,多種基於FPGA平臺的深度CNN加速器被提出,具有高效能、可重配置、快速開發週期等優勢。
儘管目前FPGA加速器已經展示了相比通用處理器更好的效能,加速器設計空間並沒有很好發掘。一個嚴重的問題是,一個FPGA平臺的計算吞吐並未很好匹配記憶體頻寬。因此,已有的方案要麼未充分利用邏輯資源,要麼未充分利用記憶體頻寬,都不能獲得最佳效能。同時,深度學習應用不斷增加的複雜度和可擴充套件性讓這個問題更加嚴重。
為了克服這個問題,我們利用roofline模型提出一種設計分析方法。對於任意CNN設計方案,我們量化分析它使用不同優化技術(迴圈分塊、變換)的計算吞吐和所需記憶體頻寬。在roofline模型幫助下,我們可以發現最好效能和最低FPGA資源需求的解決方案。
作為案例研究,我們在VC707 FPGA板卡上實現了一個CNN加速器,並將它與之前的方案對比。我們的實現在100MHz工作頻率下可獲得61.62GFLOPS的峰值處理能力,大大優於之前的方案。
【1. 簡介】
CNN是著名的深度學習架構,從人工神經網路擴充套件而來,它已經大量用於不同應用,包括視訊監控,移動機器人視覺,資料中心的影象搜尋引擎等【6】【7】【8】【10】【14】
受生物視覺神經行為的啟發,CNN用多層神經元相連處理資料,在影象識別中可獲得很高準確率。最近,基於深度學習演算法的現代應用快速增長進一步改善了DCNN的研究。
由於CNN的特殊計算模式,通用處理器實現CNN並不高效,所以很難滿足效能需求。於是,最近基於FPGA,GPU甚至ASIC的不同加速器被相繼提出【3】【4】【9】以提升CNN設計效能。在這些方案中,基於FPGA的加速器由於其更好的效能,高能效,快速開發週期以及可重配置能力吸引了越來越多研究者的注意【1】【2】【3】【6】【12】【14】。
對於任意CNN演算法實現,存在很多潛在解決方案,導致巨大的設計空間。在我們的實驗中,我們發現使用同樣FPGA邏輯資源的不同方案效能有最大90%差距。尋找最優解不無價值,尤其當考慮FPGA平臺計算資源和記憶體頻寬限制時。實際上,如果一個加速器結構並未仔細設計,它的計算吞吐與記憶體頻寬不匹配。未充分利用邏輯資源或記憶體頻寬都意味著效能下降。
不幸的是,FPGA技術進步和深度學習演算法同時將該問題複雜化了。一方面,當前FPGA平臺不斷提升的邏輯資源和記憶體頻寬擴大了設計空間,採取不同FPGA優化技術(如迴圈分塊、變換)會進一步擴大設計空間。另一方面,為了滿足現代應用需求,深度學習可擴充套件性和複雜性在持續增長。因此,在巨大的設計空間中尋找最優解就更加困難,亟需一種高效檢索基於FPGA的CNN設計空間的方法。
為了高效檢索設計空間,本文提出了分析設計的方法。我們的工作優於以前的方法,原因有二:
首先,【1,2,3,6,14】主要關注計算引擎優化,要麼忽視了外部儲存器操作,要麼直接將他們的加速器接入外部儲存器。我們的工作則考慮了緩衝區管理和頻寬優化。
其次,【12】通過資料重用減少了外部資料獲取從而獲得加速。但是這種方法不必導致最優全域性效能。另外他們的方法需要對每層重新配置,不太方便。我們的加速器無需重程式設計FPGA就能執行不同層的計算。
本文主要貢獻如下:
* 量化分析可能解決方案的計算吞吐和所需記憶體頻寬;
* 在計算資源和記憶體頻寬限制下,我們用roofline模型識別所有可能的解決方案,討論了不同層如何尋找最優解;
* 我們提出一種CNN加速器設計,對每層使用統一的迴圈展開因子;
* 實現了CNN加速器,獲得61.62GFLOPS處理效能,是目前最優的;
【2. 背景】
2.1 CNN基礎
CNN受神經科學研究的啟發,經過長達20多年的演變,CNN在計算機視覺、AI(【11】【9】)領域越來越突出。作為一種經典有監督學習演算法,CNN使用前饋處理用於識別,反饋用於訓練。在工業實踐中,很多應用設計者離線訓練CNN,然後用訓練好的CNN實現實時任務。因此,前饋計算速度是比較重要的。本文關注用基於FPGA的加速器設計前饋計算加速。
一個典型CNN由兩部分組成:特徵提取器 + 分類器。
特徵提取器用於過濾輸入影象,產生表示影象不同特徵的特徵圖。這些特徵可能包括拐角,線,圓弧等,對位置和形變不敏感。特徵提取器的輸出是包含這些特徵的低維向量。
該向量送入分類器(通常基於傳統的人工神經網路)分類器的目的是決定輸入屬於某個類別的可能性。
一個典型CNN包括多個計算層,例如,特徵提取器可能包括幾個卷積層和可選的下采樣層。圖1展示了卷積層的計算。
卷積層收到N個特徵圖作為輸入,每個輸入特徵圖被一個K * K的核卷積,產生一個輸出特徵圖的一個畫素。滑動窗的間隔為S,一般小於K。總共產生M個輸出特徵圖用於下一卷積層。卷積層的虛擬碼如下:
- for(row = 0; row < R; row ++)
- {
- for(col = 0; col < C; col ++)
- {
- for(to = 0; to < M; to ++)
- {
- for(ti = 0; ti < N; ti ++)
- {
- for(i = 0; i < K; i++)
- {
- for(j = 0; j < K; j++)
- {
- output_fm[to][row][col] += weights[to][ti][i][j] * input_fm[ti][S * row + i][S * col + j];
- }
- }
- }
- }
- }
- }
在前饋計算角度,之前的論文【5】證明卷及操作會佔據超過90%的總計算時間,所以本文我們關注加速卷積層。後面會考慮整合其他可選層,如下采樣層、最大池化層。
一個真實的CNN
圖2展示了一個真實CNN應用,摘自【9】。該CNN包括8層,前5層為卷積層,第6~8層為全連線人工神經網路。該演算法接收3通道224x224輸入影象(從原始256x256三通道RGB影象變換而來),輸出1000維向量表示1000個類別的可能性。
第一層輸入為3個224x224解析度的特徵圖,輸出96個55x55解析度的特徵圖,輸出分為兩個集,每個48組特徵圖。表1記錄了該CNN的配置。
2.2 Roofline模型
計算和通訊是系統吞吐優化的兩個基本限制。一個實現可能是計算受限的或訪存受限的。【15】開發了roofline效能模型來將系統性能同片外儲存頻寬、峰值計算效能相關聯。
公式(1)表示了特定硬體平臺的可達吞吐率,用GFLOPS作為評估指標。
一個應用實際GFLOPS不會高於這兩項中的最小值:第一項為所有可用計算資源提供的峰值計算能力(計算上限),第二項為給定計算-通訊比時系統訪存頻寬可支援的最大浮點效能(IO頻寬上限)。計算-通訊比,又稱每DRAM傳輸運算量,表示特定系統實現所需的DRAM訪問量。
圖3將roofline模型視覺化,分別展示了計算上限和IO頻寬上限。演算法2相比演算法1有更高計算-通訊比,或更好的資料重用.從圖中看到演算法2充分利用所有硬體計算資源,效能優於演算法1。
【3. 加速器設計探索】
本節首先提供了我們的加速器結構概覽,介紹了FPGA平臺上的幾個設計挑戰。為了克服這些挑戰,我們提出了相應的優化技術。
3.1 設計概覽
如圖4所示,一個CNN加速器設計包括:處理單元(PE),片上快取,外部儲存器以及片內外互聯。PE是卷積的基本計算單元。用於處理的所有資料放在外部儲存器。由於片上資源限制,資料首先快取到片上buffer,之後送入PE。這裡使用雙緩衝將傳輸時間掩蓋於計算時間。片上互聯用於PE和片上緩衝的通訊。
在FPGA平臺上有這樣幾個設計挑戰阻礙了高效的CNN加速器設計:首先,片上資料只有很小一部分,故迴圈分塊(loop tiling)是必要的,不合適的迴圈分塊可能降低資料重用和資料並行處理效率。
其次,PE和緩衝區組織及其互聯應仔細考慮,這樣能高效處理片上資料。第三,PE的資料處理吞吐應該匹配FPGA平臺的片外訪存頻寬。
本節我們從Code1開始優化,提供了連續步驟獲得最優處理效率。
使用了迴圈分塊的程式碼如下:
注意到迴圈變數i和j並未分塊,因為CNN中卷積層kernel尺寸K太小(3~11)。
第二,我們討論了計算引擎優化並將計算效能與分塊係數建立聯絡。
第三,我們使用資料重用技術減少外存訪問,建立了計算-訪存比和分塊係數的聯絡;
第四,利用上述兩個變數,我們定義了設計空間,在FPGA平臺上找最優解;
第五,我們討論了怎樣為多層CNN應用選擇最好的加速器。
3.2 計算優化
本節使用標準基於多面體的資料相關性分析【13】來通過迴圈排程和迴圈分塊尺寸窮舉法衍生出一系列等效CNN設計實現。
計算優化目標是使用有效的迴圈展開、流水線,將計算資源完全利用。本節假設所有需要的資料都在片上。片外儲存頻寬限制將在3.3節討論。
迴圈展開:用於增加海量計算資源利用率。在不同迴圈層次展開會產生不同實現。展開的執行單元是否共享資料以及共享到什麼程度會影響生成硬體的複雜性,最終影響展開的複製品數量和硬體執行頻率。某個迴圈維度中對一個數組的共享關係可以分為三種類型:
* 無關,如果迴圈變數i不出現在陣列A的任何訪問函式,則稱相應迴圈維度對陣列A是無關的;
* 獨立,如果陣列A沿著某個迴圈維度i是完全可分的,稱i對陣列A獨立;
* 相關,如果陣列A沿某個迴圈維度i不可分,稱i對陣列A依賴;
圖6顯示了不同資料共享關係時產生的硬體實現。
獨立資料共享關係:buffer和計算引擎直接連線;
無關:生成廣播式連線;
相關:產生帶多路開關的互聯;
對圖5中程式碼分析相關性,結論如下表:
最終,選擇too和tii兩個迴圈維度做迴圈展開,從而避免生成複雜硬體拓撲。我們需要將迴圈巢狀次序做修改,讓too和tii到最內層迴圈,簡化HLS程式碼生成。生成的硬體實現如圖7所示。
迴圈流水線: 是HLS裡一項重要優化技術,通過將不同迴圈層次操作執行交疊,可提高系統吞吐。可獲得的吞吐受資源和資料相關性限制。loop-carried相關性會導致迴圈不能完全流水線。
經過迴圈展開和流水線優化的程式碼如圖所示。
分塊尺寸選擇:將迴圈結構固定後,不同迴圈分塊尺寸變化會有巨大效能變化。程式碼3中有效的迴圈分塊尺寸由公式(2)確定:
(卜居注:後面4個條件是顯然的,第一個是由於迴圈展開、流水線的要求而必須加以限制,為了獲得高計算能力,必須付出增加硬體面積的代價)
給定特定分塊尺寸組合(Tm, Tn, Tr, Tc),計算效能(或roofline模型中的計算上限)可以由公式(3)計算得到。從公式中看到,計算上限是Tm和Tn的函式。
(卜居注:計算上限的單位是GFLOPS,也就是計算量除以耗時。公式分子為完成程式碼(1)的總乘、加計算量,分母為完成計算所需的時鐘週期,由於使用了迴圈分塊,所以括號內的時鐘週期數目為流水線從開始到結束的總週期,括號外為分塊外迴圈次數。)
3.3 訪存優化
在3.2節,我們討論瞭如何衍生設計變種使用不同計算上限,假設計算引擎所有資料訪問都是片上已經快取的。但是,當考慮記憶體頻寬限制時,高計算上限的設計變種不一定能達到更高計算上限。本節我們將展示如何通過高效資料重用降低所需通訊量。
圖9展示了一個CNN層的記憶體傳輸操作。輸入/輸出特徵圖和權值在計算引擎開始之前就已經載入,產生的輸出特徵圖寫回主存。
本地儲存提升:如果最內層迴圈的通訊部分(圖9迴圈變數為ti)與某個陣列是無關的,那麼該迴圈會有冗餘記憶體操作。本地儲存提升【13】可以用於降低冗餘操作。
在圖9中,最內層迴圈ti與output_fm是無關的,所以訪問output_fm的操作可以提升到外層迴圈。注意到提升操作可以一直執行,直到與迴圈變數相關。
利用該技術,對output_fm的訪存需求從降低至。
為了資料重用而實行迴圈變換:為了最大可能進行資料重用,我們使用基於多面體的優化框架來發現所有有效的迴圈變換。表3顯示了迴圈層次和陣列之間的資料共享關係。本地儲存提升方法用到每個可能的迴圈排程中,儘可能減少總通訊量。
計算-通訊比:用來描述每次訪存的計算操作。資料重用優化會降低總的訪存次數,進而提升計算-通訊比。
圖9程式碼的計算-通訊比可以由公式(4)計算:
裡面變數較多,分別表示如公式(5)~(11)
給定一個特定迴圈結構和分塊尺寸組(Tm, Tn, Tr, Tc),計算-通訊比可以通過上述公式計算得到。
3.4 設計空間探索
綜上所述,給定(Tm, Tn, Tr, Tc),可以計算該設計的計算能力上限和計算-通訊比。列舉所有可能的迴圈次序和分塊尺寸可以產生一系列計算效能和計算-通訊比對,圖8(a)顯示了例子CNN第5層在roofline模型中的所有有效解,X軸表示計算-通訊比,或者每DRAM位元組訪問的浮點處理效能。Y軸表示計算效能(GFLOPS)。任意點與原點(0, 0)的連線斜率表示該實現的最低訪存頻寬需求。
例如,設計P的最低訪存頻寬需求和P' 是相同的。
在圖8(b)中,頻寬上限線和計算上限是由特定平臺決定的。在頻寬上限線左側的點需要比平臺能提供的訪存頻寬更高,因此不可實現,即圖中雖然設計A取得了最高的計算效能,但平臺記憶體頻寬不能滿足該設計的需求,所以平臺上可以獲得的效能落到A' 位置。
平臺支援的設計定義為:位於頻寬上限線右側的集合。位於頻寬上限線的是左側點的投影。
我們探索平臺支援最優方案的策略如下:最高效能,最高計算-通訊比(這樣有最小的訪存需求)。該準則基於我們可以使用更少IO口,更少LUT和硬體連線,資料傳輸引擎有更低頻寬需求。因此,點C是CNN第5層的最終選擇,它的頻寬需求為2.2GB/s。
3.5 多層CNN加速器設計
前幾節我們討論瞭如何為每個卷積層尋找最優實現引數。在CNN應用中,這些引數可能在不同層之間變化。表4顯示了例子CNN中每層最優展開係數(Tm和Tn):
設計一個支援不同展開係數的多個卷積層的硬體加速器將會非常有挑戰性,因為需要設計複雜的硬體架構來支援重配置計算引擎和互聯。
一種替代方案是所有層都用同一套展開係數。我們枚舉了所有可行的解來選擇最優的全域性設計引數。使用統一展開係數易於設計實現,但對某些層是次優解。表4表明使用統一展開係數(64, 7),效能下降不超過5%。因此我們的實驗選擇了這個展開係數。
列舉空間大約98,000,使用普通筆記本大約10分鐘就能完成。
【4. 實現細節】
本節描述我們解決方案的具體實現。
4.1. 系統概述
圖10 顯示了我們的實現概述。
全部系統都放在了單個FPGA晶片,使用DDR3 DRAM用於外部儲存。
MicroBlaze是一個RISC處理器軟核,用於幫助CNN加速器啟動,與主機CPU通訊,以及計時。
AXI4lite匯流排用於傳輸命令,AXI4匯流排用於傳輸資料
CNN加速器作為AXI總線上一個IP。它從MicroBlaze接收命令和配置引數,與定製的資料傳輸引擎通過FIFO介面通訊,該資料傳輸引擎可以獲取通過AXI4匯流排外部儲存。
MicroBlaze和CNN加速器使用中斷機制來提供精確的計時。
4.2 計算引擎
圖11的計算引擎部分顯示了我們實現的模組圖。它們是基於第三節分析結果而設計的。
二級迴圈展開(圖2中的Tm和Tn)實現為並行執行計算引擎,使用了類似圖7的樹狀結構。對於最優的跨層設計(Tm, Tn)=(64,7),單個引擎接收來自輸入特徵圖的7個輸入,以及7個來自權值的輸入以及一個bias輸入。64個複製的結構用來展開Tm。
(卜居注:由於使用了64個相同的計算引擎,每個消耗35個dsp,有7個乘法器和7個加法器組成,每個加法器消耗2個dsp,每個乘法器消耗3個dsp)
4.3 儲存子系統
片上緩衝區是基於雙緩衝設計的,工作在乒乓模式來掩蓋資料傳輸時間到計算時間中。它們一共有4組,兩組用於輸入特徵圖、權值,兩組用於輸出特徵圖。我們先介紹每個緩衝區的組織,隨後介紹乒乓資料傳輸機制。
每個緩衝區包括幾個獨立的緩衝區bank,每個輸入緩衝區的bank數目等於Tn(input_fm的分塊尺寸)。輸出緩衝區的bank數目等於Tm(output_fm的分塊尺寸)。
雙緩衝用於實現乒乓操作。為了簡化討論,我們使用圖9的具體例子來展示乒乓操作機制。見圖9中的程式碼。“off-load”操作只有在[N/Tn]次“load”操作後才會發生一次。但每個output_fm傳輸的資料量大於input_fm,比例大約為Tm/Tn = 64/7 = 9.1,為了提高頻寬利用率,我們實現了兩套獨立通道,一個用於load操作,另一個用於off-load操作。
圖12顯示了計算和資料傳輸階段的時序圖。
第一個階段時,計算引擎處理輸入緩衝區0同時拷貝下一階段資料到輸入緩衝區1,下一階段做相反的操作。這是輸入特徵圖、權值的乒乓操作。
當[N/Tn]個階段之後,輸出特徵圖寫入DRAM,"off-load"操作會將位於輸出緩衝區0的結果寫回DRAM,直到輸出緩衝區1產生新的結果。這是輸出特徵圖的乒乓操作。注意這兩個獨立存取通道機制適用於該框架下任何其他資料重用的場景。
4.4 外部資料傳輸引擎
使用外部資料傳輸引擎的目的有兩個:(1)可以提供加速器和外部DRAM之間的資料傳輸;(2)可以隔離加速器和平臺、工具相關頻寬特性。
圖13展示了一個實驗,在Vivado 2013.4中的AXI4匯流排頻寬。
兩幅圖中,我們設定兩個引數,AXI匯流排到DRAM控制器的位寬,和DRAM控制器的外部頻寬,在它們最高配置下單改變IP-AXI介面數目和每個IP的位寬。
在圖13(a)中,增加IP-AXI介面位寬不影響頻寬(400MB/s在100MHz頻率下)。
在圖13(b)中,更多IP介面加入AXI匯流排,它的頻寬幾乎線性增長,最高頻寬大約4.5GB/s。
在我們CNN加速器設計中,最小頻寬需要1.55GB/s。根據圖13,4個IP介面足夠用於這個設計。我們使用兩個AXI-IP介面用於資料傳輸引擎0,兩個用於資料傳輸引擎1,如圖10所示。
【5. 評估】
本節首先介紹我們實驗環境設定,然後提供了全面的實驗結果。
5.1 實驗設定
加速器設計用Vivado HLS(v2013.4)實現。該工具允許用C語言實現加速器,並匯出RTL為一個Vivado IP核。CNN設計C程式碼通過增加HLS定義的編譯嚮導實現並行化,並行化版本通過時序分析工具進行了驗證。快速綜合前模擬使用該工具的C模擬和C/RTL聯合模擬完成。綜合前資源報告用於設計空間探索和效能估計。匯出的RTL使用Vivado v2013.4進行綜合、實現。
我們的實現基於VC707板卡,有一片Xilinx FPGA晶片Virtex 7 485t。它的工作頻率為100MHz,軟體實現執行在Intel Xeon CPU E5-2430(@2.2GHz),15MB Cache。
5.2 實驗結果
本小節我們先彙報資源佔用,之後對比軟體實現(CPU上)和我們的加速器實現(FPGA上)。最後,給出了我們的實現和已有FPGA實現的對比情況。
佈局佈線由Vivado工具集提供。之後,工具會彙報資源佔用情況,如表6所示。可以看出我們的CNN加速器已經差不多完全利用了FPGA的硬體資源。
我們的加速器和基於軟體的實現效能對比如表7所示。
我們選擇本文提出的跨層加速器作為對比。軟體在單執行緒和16執行緒使用gcc帶-O3優化選項實現。我們的FPGA實現相比單執行緒軟體實現獲得了17.42x加速比,同時相比16執行緒軟體實現獲得4.8x加速比。我們的加速器總效能達到61.62GFLOPS。
圖14顯示了我們板卡實現圖。
一個功率計用來測量執行時功率特性,大約18.6瓦特。CPU的熱設計功率為95瓦特。因此,我們可以粗略估計軟體和FPGA的功率。
表8顯示了能耗相差至少24.6倍,FPGA實現消耗更少能量。
在表5中列出了已有的不同基於FPGA的CNN加速器同我們實現的對比情況。
之前的方法是用GMACS,而我們用GFLOPS作為效能指標。我們首次將所有結果數字表示為GOPS,實現同等對比。注意每個乘加操作包括兩個整數操作。表5的第9行顯示,我們的加速器具有61.62GOPS吞吐,相比其他實現至少有3.62倍加速。
由於不同工作使用了不同並行策略和不同FPGA平臺,很難有一個直接對比。為了提供公平對比,我們進一步給出“效能密度”結果,定義為單位面積(每slice)的GOPS,可表示一個設計的效率而無需考慮所用的FPGA平臺,最終結果如表5最後一行所示,我們的設計獲得最高效能密度,比第二名高1.8倍。另外,如果使用定點計算引擎,我們的方法可以獲得更好效能和效能密度,因為定點處理單元使用更少的資源(如表9所示)。
(卜居注:定點評估有問題,加法器不需要DSP,乘法器所需資源不比浮點少)
【6. 相關工作】
本節,我們討論不同設計方法,參考其他之前的基於FPGA的CNN加速器設計工作。
首先,很多CNN應用加速器都聚焦在優化計算引擎上。實現【6】【14】【3】是三個代表。
最早的方法【6】主要用軟體搭起CNN應用,而是用一個硬體脈動結構加速器完成濾波卷積工作。這個設計省下大量硬體資源,用於自動駕駛機器人的嵌入式系統。
【14】【2】【3】在FPGA上實現了完整CNN應用,但採取了不同並行措施。【14】【2】主要利用了特徵圖內部卷積核的並行性。【3】使用了輸出內、輸出間的並行性。我們的並行方法類似,但他們並未使用片上緩衝區做資料重用,而是用很高頻寬和動態重配置來提高效能。我們的實現合理進行資料重用,平衡了頻寬限制和FPGA計算能力。
其次,【12】考慮了CNN的通訊問題,選擇最大化資料重用,將頻寬需求降至最低。但他們的方法並未考慮最大化計算效能,另外當換到下一層計算時他們需要為FPGA重程式設計(大約10秒),而我們的方案秩序消耗不到1us來配置幾個暫存器。
【7. 結論】
本文中,我們提出了基於roofline模型的CNN FPGA加速方法。首先優化CNN的計算和訪存,之後將所有可能涉及在roofline模型下建模,為每層尋找最優解。我們通過枚舉發現了最好的跨層設計。最終,我們在Xilinx VC707板卡上實現,效能優於以往的實現。
【8. 致謝】
【9. 參考文獻