陳業旺,吳林煌,楊俊偉
(1.福州大學 先進制造學院,福建 晉江 362200;2.福州大學 物理與信息工程學院,福建 福州 350108)
高效視頻編碼標準H.265/HEVC(High Efficiency Video Coding,HEVC)[1-2]提供了超高清視頻的壓縮編碼方案[3-5]。在壓縮相同質量視頻時,它比上一代編碼標準H.264提高了約50%的壓縮性能[6]。但同時,H.265標準相對H.264標準也增加了算法復雜度[7]。本文所述的編碼系統使用Zynq這種包 含 PL(Programmable Logic)與 PS(Processing System)的異構平臺實現,利用PL硬件的高度并行運算加速編碼過程,利用PS控制編碼器的編碼參數[8]。這使得編碼器既能加速編碼運算,又可向PS端CPU提供控制接口而不失靈活性。H.265硬編碼器要壓縮編碼更高清視頻,還需要解決一個重要的問題,即如何滿足其成倍增加的數據吞吐量,同時盡可能降低存取延時、減少存儲帶寬壓力。由于H.265標準中可在8×8至64×64范圍內動態劃分CTU,支持33種幀內預測模式[9-11],因此更增加了對內存空間訪問的需求。
文獻[12]將新型的非易失性存儲器如ReRAM、STT-RAM等與DRAM組成分層內存結構,有效地節約了總體存儲器面積、降低了編碼數據存取功耗。但該方案中,DRAM與非易失性存儲器需要不同的存儲控制器管理對內存的訪問,這無疑增加了硬件成本。文獻[13]采用現場可編程邏輯門陣列(Field Programmable Gate Array,FPGA)拓展的PCIE接口接收待編碼的視頻數據然后緩存至DDR中,再利用SRIO(Serial RapidIO)接口將FPGA預處理后的數據送至DSP芯片中,在DSP芯片上完成HEVC壓縮編碼。該方案硬件成本高,使用多個接口連接不同硬件電路,增加了系統的不穩定性,也增加了視頻編碼延時,傳輸帶寬利用率不高。文獻[14]設計了DDR-BRAM-LUT三級物理存儲結構,使用DDR進行幀緩存、用BRAM行緩存、用LUT緩存參考像素,在一定程度上緩解了片外存儲器的帶寬壓力,但沒有考慮CTU在內存中的存儲安排與DDR訪問效率的關系,數據存取效率不高。
綜合考慮上述問題,本文設計了一種可有效提升H.265編碼器數據存取效率的硬件架構。首先分析了DDR4訪問的特性、硬件結構特點以及H.265編碼的特性,從而設計了以64×64的CTU為單位、以DDR4內存頁對齊存儲、視頻幀乒乓結構讀寫,然后介紹了基于DDR-FIFO-BRAM結構的編碼數據存取方案,主要包括:待編碼圖像數據的存儲;重構圖像的存儲與滑動讀取重構圖像搜索框數據,并根據當前分辨率對重構圖像做填充,整個過程硬件流水實現;碼流緩存控制。最后介紹了系統整體設計流程,并對系統測試結果進行了分析。本文所述方案在Xilinx的Zynq UltraScale+ MPSOC 9EG平臺上得以實現,并通過搭建基于H.265硬編碼器的軟硬件協同工程驗證了本方案的可行性。
本設計使用Xilinx的ZCU102套件完成方案的測試驗證。ZCU102是面向視頻等應用設計的套件。其具有Xilinx 16nm可編程邏輯架構的Zynq UltraScale+ MPSOC器件,具備四核ARM Cortex A53、雙核Cortex R5F實時處理器、一個Mali -400 MP2 GPU以及HDMI等外設接口。其中,H.265編碼器在FPGA端運行;視頻數據從HDMI接口接收后輸出Native Video格式數據,再經分辨率檢測、色彩空間轉換及下采樣為YUV4∶2∶0格式后通過AXI_HP口存于PS端DDR4中;H.265編碼器讀寫DDR4中的像素數據,完成視頻編碼并實時輸出碼流,碼流經控制模塊緩存輸出至PS端DDR4中;Linux操作系統在PS端的ARM CortexA53核上運行,操作系統負責把碼流封包后通過以太網發送至目的IP,在目標設備上接收碼流并解碼顯示。系統整體框圖如圖1所示。

圖1 系統整體框圖
文獻[15]采用NAND flash作為編碼數據存儲單元,可實現掉電不丟失數據,但在實時視頻編碼過程中需要頻繁訪問存儲器。使用NAND flash會帶來更高功耗,同時相較于DDR其工作頻率也更低。本文所述方案中,編碼數據與PS端CPU操作系統使用同一DDR4,在保證存取效率的同時,也使DDR4存儲空間得到充分利用,降低了系統功耗。
Zynq芯片平臺有4個AXI_HP(High Performance)接口用于提供PL與PS存儲器之間的高吞吐量數據路徑。AXI_HP接口與存儲器之間的硬件結構如圖2所示。PL端的IP可通過4個AXI_HP接口向PS端DDR或OCM(on-chip RAM)存儲器快速傳輸數據。

圖2 AXI_HP與存儲器結構圖
為了使數據訪問更高效,本設計使用DMA傳輸的方法,無需CPU干預。在DDR4顆粒中,同一時間只能訪問同一bank group的一個bank,而且在此bank中只能訪問其中一行。DDR4內存頁大小為內存整列中一行對應的列可尋址范圍乘以DQ位數,內存頁大小如式(1)所示。

式中:SP為DDR4內存頁大小,C表示內存矩陣列地址的位數,O表示DDR4 DQ位數。如果要換行或bank訪問意味著存儲器需要額外的時鐘去做片選、使能控制,這會進一步降低存儲器的訪問效率。但值得注意的是,不同bank group之間可以獨立預取8位數據,同一時間不同bank group的數據預取互不影響。若將數據都存放在同一bank group中,DDR4的效率會嚴重降低。另外,DDRC總線的效率與突發讀寫長度相關,適當增加突發讀寫長度,可使存儲器訪問效率得以提升。
基于以上分析,本文把DDR存儲空間分為CPU操作系統核心使用部分和編碼數據緩存部分,進一步把編碼數據的兩個主要部分即待編碼圖像數據和重構圖像數據分別存放在兩個bank group中,以減少存取延時。為了避免數據的存儲與讀取發生沖突,本文將待編碼圖像數據與重構圖像數據都做了幀乒乓存取處理。DDR4內存空間劃分示意如圖3所示。

圖3 DDR4內存空間劃分
H.265硬編碼器在對高清視頻編碼時會產生大量的中間數據。這些數據需要暫存在DDR4中。如在幀內預測時,編碼器需要參考已編碼的塊去預測當前待編碼塊消除圖像空間冗余;同時把編碼器輸出的重構圖像寫入DDR4緩存,供幀間預測使用。本文針對待編碼圖像與重構圖像數據的編碼特性,設計了一套高效存取FPGA硬件框架。為了適應不同分辨率的編碼需求,首先在視頻輸入端正確識別出當前輸入的分辨率,然后將分辨率值輸出給編碼系統使用。在計算分辨率的同時,圖像幀的起、止信息也包含在此模塊中。為了節省資源,不再使用額外的邏輯資源去獲取幀的同步信息,本文將模塊的幀同步信息輸出給編碼器數據存取系統,用于控制存取幀地址的切換。
本文中所述H.265編碼器編碼圖像數據為YUV 4∶2∶0格式,而本設計的HDMI接口接收到的圖像為RGB 8∶8∶8格式,故需要把接收到的視頻圖像做格式轉換,并做下采樣處理。本設計先把RGB 8∶8∶8圖像格式轉為YUV 4∶4∶4,色彩轉換如式(2)所示;再把YUV 4∶4∶4下采樣為YUV 4∶2∶2,最終把YUV 4∶2∶2下采樣為YUV 4∶2∶0后存儲到DDR4中。在編碼器做率失真優化時,只需要用到Y亮度分量數據,故把Y分量與UV分量分開存儲,這樣更方便數據讀取。

H.265編碼器是以CTU為單位編碼的,但HDMI接收到的圖像是從左上頂點開始按行接收的。如果按行存儲輸入圖像數據,那么意味著讀出CTU數據的時候將需要做非常繁雜的地址映射,且需要頻繁地做內存頁、內存bank的跳轉,這會嚴重降低DDR4的訪問效率。另外,H.265編碼器的編碼單元(Coding Unit,CU)與預測單元(Prediction Unit,PU)原始數據分開讀取,意味著在DDR4中相同地址的數據可能會被重復讀取。這無疑增加了DDR4的帶寬壓力與數據讀取延時??紤]到H.265最大支持64×64的CTU塊劃分,本設計以最大支持的CTU單位劃分存儲數據,這樣可兼容編碼器在不同CTU劃分下的工作模式。按照CTU的劃分,在YUV 4∶2∶0圖像格式下亮度CTB以64×64為單位存儲,將兩個32×32色度CTB拼湊為32×64的數據塊存儲。為了隔離148.5 MHz的HDMI數據接收模塊與200 MHz寫DDR4內存模塊的時鐘域,以及控制AXI4總線讀寫突發長度,本文在這兩模塊之間插入了兩個FIFO緩存Y、UV分量數據。從FIFO讀出的數據經過寫地址映射模塊,把按行接收到的像素數據按照CTU劃分把數據寫入到DDR4對應的地址上。同時,寫地址模塊還會控制圖像幀的起始地址,以此實現幀圖像的乒乓緩存。在讀取待編碼圖像時,使用PL端的資源例化兩個64×64的乒乓RAM,用于存儲從DDR4讀取而來的同屬于同一個CTU的CU、PU數據,以此實現使用少量邏輯資源換取降低片外存儲器帶寬壓力與減少編碼器編碼延時的效果。待編碼圖像數據的存取如圖4所示。

圖4 待編碼圖像數據存取結構
把按行輸入的圖像數據轉換成按CTU方式存儲,同時還要控制圖像幀的乒乓存儲。此過程的地址控制若按照常規的方法采用狀態機實現,將會非常煩瑣,且消耗很多FPGA資源。本文設計了一個基于地址位操作的地址控制模塊用于實現讀寫數據地址控制。此模塊無需任何FIFO緩存,數據輸入后僅需兩級用于防止亞穩態傳播的同步寄存器接收后,即可把數據給到對應的DDR4地址上。對于8 bit×64×64的Y分量數據,一共需要4 kB的存儲空間;而由UV組成的數據包8 bit×2×32×32=2 kB。本文所使用的DDR4內存矩陣有效列地址位寬為10 bit,DQ位數為16,由式(1)可得一個內存頁恰為2 kB,故可使用一片內存頁存儲一個UV數據包,將64×64的Y分量分為64×32×2存放在兩片內存頁中。此后在讀取UV分量時無需做切換內存頁操作,讀取Y分量只需做一次頁跳轉,連續內存讀取,提升了存儲器的訪問效率。比如Y分量的存儲結構如圖5所示。

圖5 Y分量存儲結構示意圖
編碼器對原始像素編碼后,會輸出重構圖像供幀間編碼使用。重構像素寫入DDR4的過程與上述待編碼圖像的存儲方法一致,而重構圖像搜索框的讀取則相對復雜。對于圖像邊緣,需要做填充處理,重構圖像的填充如圖6所示。對于圖像邊緣的黃色正方形區域參考相應的頂點填充,綠色區域參考相鄰邊緣像素填充。

圖6 重構圖像邊緣填充
編碼器在做預測時,相鄰編碼單元使用的搜索框數據有大量重疊部分,搜索框數據移動如圖7所示。如果不做緩存處理,每個搜索框數據都讀一遍,將會使存儲帶寬的需求成倍增加。以CU大小為16×16、Y分量讀取為例,讀取示意如圖8所示。模塊以每次突發讀64×8像素點為單位將數據從DDR4中讀出,數據存儲在80行RAM中,然后對邊緣做填充,填充完成后等待編碼器讀走64行數據。第64行數據讀完后,立即開始從DDR4中繼續讀取。數據讀出后將第1—16行RAM數據覆蓋,與此同時,第65—80行數據繼續輸出給后續模塊。因為讀DDR并填充數據的速度大于編碼器請求數據的速度,因此在編碼器請求數據時,模塊總能提前準備好所需數據。UV分量重構像素的讀取與Y分量同理。

圖7 搜索框數據移動示意圖

圖8 Y分量滑動讀取示意圖
視頻圖像經編碼器編碼后生成8 bit位寬的碼流。為了減少對DDR4的訪問次數,本文先用FIFO緩存碼流數據,綜合考量FIFO資源,以1 kB大小把碼流數據寫入DDR4中。每次寫完成后產生一個中斷信號給CPU,CPU收到中斷信號后讀取碼流并對其RTP封包。
本設計從工作頻率、AXI4突發長度、功耗、資源使用等多方面綜合考慮,進一步分析、優化編碼器存儲系統的性能。AXI_HP口最大支持128 bit,系統以流水線方式工作。
表1為使用不同參數時,FPGA硬件在vivado 2020.2軟件上采用ZCU102評估板工藝節點綜合得到的數據。由表1可知,存儲系統工作在器件端口最高頻率333 MHz時,僅需增加小于0.1 W的功耗即可得到更高的存儲效率。以單通道128 bit總線、333 MHz為例子估算帶寬:相鄰兩次突發讀寫之間至少需要間隔兩個clk,突發長度設置為最大256,因此其最大理論帶寬約為4.92 GB·s-1,滿足8K(7 680×4 320)30 f·s-1視頻編碼帶寬需求;寫碼流模塊時鐘設為30 MHz、數據位寬32 bit時,允許的最大理論帶寬為 120 MB·s-1,約為 0.12 GB·s-1;原始圖像、重構圖像讀寫共4個通道,總帶寬約為14.76 GB·s-1。所使用的DDR4 2133理論最大帶寬為17 GB·s-1,故PL端存儲系統對DDR4內存使用的效率可達約87.52%。

表1 FPGA存儲系統實現結果
為了驗證本存儲系統是否可在硬件上成功運行,使用實驗室自研H.265內核搭建驗證平臺,其中各功能模塊的工作時鐘如表2所示。由于實驗室自研H.265內核目前最高支持200 MHz,為了方便與H.265內核進行數據交互,存儲系統工作時鐘設置為200 MHz。抓取存儲系統將數據讀給編碼器的時序波形,波形如圖9所示。64×64的數據塊僅需64個clk即可全部送給編碼器。

表2 驗證平臺各功能模塊的工作時鐘

圖9 編碼器讀取數據塊時序圖
使用高清攝像頭拍攝筆記本電腦播放的測試視頻,攝像頭輸出1 080P視頻給編碼器編碼,碼流由解碼板解碼播放,編解碼效果如圖10所示。

圖10 編解碼效果圖
本文根據H.265標準對CTU劃分、編碼時對原始像素、重構像素和預測搜索框需求的特點以及DDR4的訪問特性,設計了一種用于H.265硬編碼的實時、高效視頻數據存取方案。CPU與編碼數據共用一套DDR4以節省硬件成本,通過降低H.265硬編碼器在高清視頻編碼時對存儲器的訪問次數和帶寬的需求,更合理安排編碼數據在DDR中的存儲,減少內存頁跳轉訪問,提高存儲器訪問效率,減少數據存取延時,能夠自適應輸入視頻分辨率與重構圖像邊緣填充。在實際測試中,內存使用效率可達 87.52%,且可滿足 8K(7 680×4 320)30 f·s-1視頻編碼帶寬需求。與文獻[13]的FPGA視頻緩存所需總功耗16.242 W相比,本文方案節省了近10 W。所提框架在ZCU102平臺上完成驗證,攝像頭采集的1 080P視頻經編解碼后顯示正常。