????????ffavdemo 代碼庫實現了一個基于FFmpeg和VAAPI的硬件加速視頻解碼與渲染框架,主要用于演示視頻解碼與渲染的完整硬件加速流程。支持多種渲染后端(X11、DRM、EGL),適應不同顯示環境。包含視頻處理過濾器,可進行格式轉換和調整。提供RTSP客戶端功能,支持從網絡流接收并解碼視頻。使用多線程處理渲染和用戶輸入,確保流暢的播放體驗。
?????????其核心功能包括:
- ?視頻解碼:通過 VA-API 調用 GPU 的硬件解碼能力(如 H.264/HEVC 等格式)。
- ?幀處理:支持對解碼后的幀進行格式轉換、縮放等后處理操作。
- ?渲染輸出:將處理后的視頻幀渲染到屏幕或導出為圖像文件
1、程序文件分析
- ffmpeg_utils.c:包含FFmpeg與VAAPI之間的轉換工具函數。
ffmpeg_to_vaapi_profile():將FFmpeg的編解碼器ID和Profile轉換為VAProfile。
ffmpeg_to_vaapi_pix_fmt()和vaapi_to_ffmpeg_pix_fmt():像素格式轉換。
vaapi_to_ffmpeg_error():將VA狀態碼轉換為FFmpeg錯誤碼。
結構體ffva_pix_fmt_map用于映射像素格式。
- ffvademo.c:主程序,展示如何使用FFmpeg和VAAPI進行視頻解碼和渲染。
main()函數初始化顯示、解碼器、渲染器,并處理視頻幀。
支持不同的渲染后端(DRM、X11、EGL)和內存類型。
多線程處理用戶輸入(如退出命令)。
- ?ffvadisplay.c:管理VA顯示連接,支持DRM和X11后端。
ffva_display_new()創建顯示對象,ffva_display_free()釋放資源。
包含不同顯示類型的初始化(如DRM打開設備節點,X11連接X服務器)。
- ffvafilter.c:視頻處理過濾器,使用VA的視頻處理管道(VPP)進行后處理。
ffva_filter_new()初始化過濾器,ffva_filter_process()應用處理。
支持格式轉換、裁剪、縮放等操作。
- ?ffvarenderer.c:渲染器抽象基類,定義通用接口。
ffva_renderer_put_surface()提交表面進行渲染。
子類(如DRM、X11、EGL)實現具體的渲染邏輯。
- ffvarenderer_drm.c:DRM渲染器實現,但目前似乎未完整實現渲染邏輯。主要處理與KMS(Kernel Mode Setting)的交互。
- ?ffvarenderer_egl.c:使用EGL和OpenGL ES進行渲染,支持DMA-BUF導入。創建EGL上下文,管理紋理和著色器,處理YUV到RGB的轉換。
- ?ffvarenderer_x11.c:X11渲染器實現,創建X窗口并處理事件。
window_create()創建X窗口,處理窗口事件(如關閉)。
renderer_put_surface()使用X11的API進行圖像渲染。
- ?ffvasurface.c:管理VA表面的結構,初始化和釋放表面資源。
ffva_surface_init()初始化表面信息。
- ?vaapi_utils.c:VAAPI工具函數,處理VA配置、上下文、表面和緩沖區的生命周期。
va_create_buffer()創建并映射VA緩沖區。
- ?ffvadecoder.c:FFmpeg與VAAPI集成的解碼器實現。
vaapi_init_decoder()初始化VA解碼器,創建配置和表面。
vaapi_acquire_surface()和vaapi_release_surface()管理解碼后的幀表面。
- ?ffvartsp.hh和相關代碼:RTSP客戶端實現,處理媒體流的接收和解包。
2、流程分析
- ?解碼流程:通過ffvadecoder中的VAAPI解碼器將視頻數據解碼為VA表面。
- ?渲染流程:渲染器(如X11、EGL)將VA表面轉換為適合顯示的格式并呈現。
- ?格式轉換:ffmpeg_utils中的函數處理編解碼器Profile和像素格式的轉換。
- ?錯誤處理:將VAAPI錯誤轉換為FFmpeg錯誤碼,便于統一處理。
- ?網絡流支持:RTSP客戶端接收流媒體,解碼后送入渲染管道。
3、ffavdemo.c分析
先來看看這個程序支持那些參數。
- -x, --window-width=WIDTH:設置窗口的寬度,參數類型為整數,默認值為 0。
-y, --window-height=HEIGHT
:設置窗口的高度,參數類型為整數,默認值為?0
。- -r, --renderer=TYPE:選擇特定的渲染器,參數類型為字符串,默認值根據編譯選項而定(可能是 x11)。支持的渲染器類型有 drm、x11、egl。
- -m, --mem-type=TYPE:設置VA緩沖區導出的內存類型,參數類型為字符串,默認值根據編譯選項而定(可能是 auto)。支持的內存類型有 dma_buf、gem_buf、mesa_image、mesa_texture。
- -f, --format=FORMAT:設置輸出像素格式,參數類型為 AVPixelFormat,默認值為 none。
程序基本流程圖如下:
4、程序測試
? * 播放一個采用MP4格式的H.264視頻
? ? $ ffvademo /path/to/video.mp4
? * 播放一個VC-1視頻,并將輸出轉換為I420格式
? ? $ ffvademo -f yuv420p /path/to/video.wmv
? * 播放一個采用MP4格式的H.264視頻,并使用EGL/GLESv2進行渲染
? ? $ ffvademo -r egl -f argb /path/to/video.mp4