轉碼應用涉及視頻服務器、通用多媒體訪問設備、監控系統、機頂盒、DVD等多媒體設備和系統。其基本原則是在環境和處理能力受限的情況下,在碼流轉換的質量和復雜性之間取得折衷。實現的關鍵是對壓縮視頻碼流中的壓縮數據進行復用,避免重新編碼中的復雜運算。研究中的轉碼技術主要包括:碼率轉換、分辨率轉換、幀率轉換、語法轉換等。
MediaCoder是目前比較的一款轉碼軟件,它將眾多來自開源社區的音視頻軟件整合于一個友好的圖形界面。它可以直接、批量地在眾多音頻視頻壓縮格式和容器格式之間轉換,支持的格式包括H.264,Xvid,MPEG-1/2/4等,但是沒有將AVS視頻編碼標準融合進來。本文介紹的軟件解碼器實現了H.264到AVS兩個視頻編碼標準的轉碼。針對這兩個標準的硬件轉碼器還在研發之中,上海龍晶微電子有限公司基于AVS標準提出了國內款具有完全自主知識產權的高清電視解碼芯片DS10000。雙核技術的廣泛應用可用并行處理辦法加快速度。視頻轉碼可分為同類視頻轉碼技術和不同類視頻轉碼技術。
2 像素域和變換域轉碼結構
圖1是空域轉碼器結構框圖,將H.264碼流進行熵解碼和反量化,然后逆DCT變換,得到像素域的像素值;根據解碼的運動矢量和頻域殘差數據進行運動估計(Motion Estimation,ME),根據得到的運動矢量進行運動補償(Motion Compensation,MC);再將得到的殘差數據進行變換和量化、熵編碼形成AVS碼流。
3 多線程轉碼器設計
應用程序加載到內存中,給出一個執行點稱為線程。線程是系統需要分配CPU時間的基本執行單元。單個進程在任何時刻可包含多個線程,它們可同時執行進程地址空間內的代碼。
1) 子線程的創建與終止
VC++應用程序的主線程在創建應用程序時生成,創建子線程可通過調用CreateThread函數創建,其格式:
HANDLE = CreateThread (LPSECURITY ATTRIBUTES Ipsa,DWORD cbstack,LPTHREAD START ROUTINE lpStartAd2dr,LPVOIDlpvThreadParm,DWORD fdwCreate,LPDWORD lpIDThread);
在本轉碼器中,子線程創建方法如下:
slot=0; hThrds[slot]=CreateThread(NULL,0,ThreadFunc,(LPVOID)slot,0,&threadID).
2) 轉碼器的多線程實現結構
由圖1和圖2可以看出,轉碼器的解碼和編碼部分是相對獨立的。雖然在編碼端要用到解碼得到的運動矢量、分塊模式還有頻域中的系數等信息,如果是單線程程序的話,在編碼到這一幀時,解碼程序就要停止,只有當編碼這一幀的程序執行完后,才能開始執行下一幀的解碼程序。所以,在解碼時編碼程序停止,在編碼時解碼程序停止,這將花費大量的時間來等待。
如果是在雙核或者多核計算機上,可采用并行處理的方法,可啟動兩個或多個線程,一個解碼線程和一個編碼線程,在編碼第n幀時,同時解碼第n+1幀,達到解碼和編碼同時執行的效果。考慮到對系統內存的要求,這里設置緩存區的大小為2,多線程轉碼器實現框架如圖3所示。
3) 多線程轉碼器的具體實現方法
緩存區大小設置為2,奇數幀共用一組變量,偶數幀共用一組變量。H.264中解碼的當前幀序號用img->number表示,AVS編碼端編碼的當前幀序號用img_avs->number表示。在解碼第n+2幀時,decode_slice()解碼一幀的函數前面加上判斷是否編碼完第n幀:
if (img->number=(img_aVs->number+2))WaitForSingleObject(hThrds[0],INFINITE);
解碼第n+2幀完成時,等待編碼線程結束,Wait-ForSingleObjeet(hThrds[0],INFINITE),然后開始一個新的進程:
slot=0;hThrds[0]=CreateThread(NULL,0,ThreadFunc,(LPVOID)slot,0,&threadID)
在整個程序執行完之前,等待線程執行完以后,再結束整個轉碼程序。
4 仿真結果
測試序列:foreman,格式為CIF(352×288),編碼成IPPPPIPPP…,264量化系數為28,AVS端編碼的量化系數為36,編碼幀數為100幀。
計算機配置:Intel奔騰1.6 GHz,內存1 Gbyte,Win-dows XP sp2操作系統。