实现FFMPEG 使用CUDA解码播放
生活随笔
收集整理的這篇文章主要介紹了
实现FFMPEG 使用CUDA解码播放
小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.
播放器使用ffmpeg讀取視頻文件,packet發(fā)給cuda解碼,解碼后OpenGL直接映射給pbo,pbo綁定texture,然后顯示出來(lái)
流程讀取文件,判斷packet,丟到CUDA那
if (av_read_frame(m_pFormatContext, &packet) >= 0)
{
if (packet.stream_index == m_VideoStreamIndex)
{
if (m_UseGPUDecode)
{
//MiniConsole::getInstance().Output("ThreadDecodeVideoGPU begin
");
ThreadDecodeVideoGPU(packet);
//MiniConsole::getInstance().Output("ThreadDecodeVideoGPU end
");
}
else
{
ThreadDecodeVideoCPU(packet);
}
}
else if (packet.stream_index == m_AudioStreamIndex)
{
ThreadDecodeAudio(packet);
}
else
{
av_free_packet(&packet);
}
}
數(shù)據(jù)丟給cuvidParseVideoData
CUVIDSOURCEDATAPACKET cudaPkt;
CUresult oResult;
if (pData == NULL)
{
cudaPkt.flags = CUVID_PKT_ENDOFSTREAM; //end of stream
}
else
{
cudaPkt.flags = CUVID_PKT_TIMESTAMP;
}
cudaPkt.payload_size = (unsigned long)nSize;
cudaPkt.payload = (const unsigned char*)pData;
cudaPkt.timestamp = packpts;
cuCtxPushCurrent(m_cudaResPtr->m_CuContext);
oResult = cuvidParseVideoData(m_CuVideoParser, &cudaPkt);
if ((cudaPkt.flags & CUVID_PKT_ENDOFSTREAM) || (oResult != CUDA_SUCCESS))
{
checkCudaErrors(cuCtxPopCurrent(NULL));
return false;
}
//printf("Succeed to read avpkt %d !
", iPkt);
checkCudaErrors(cuCtxPopCurrent(NULL));
然后數(shù)據(jù)到
HandlePictureDecode(CUVIDPICPARAMS *pPicParams) 發(fā)送解碼
HandlePictureDisplay(CUVIDPARSERDISPINFO *pDispInfo) GPU解碼結(jié)束發(fā)送到這里,存起來(lái)
然后映射pbo ,map texture就到紋理上了,就可以繪制了
這個(gè)4k x60fps的,如果CPU解碼cpu使用率100%都會(huì)卡頓
這個(gè)8k的視頻,CPU解碼無(wú)法播放
總結(jié)
以上是生活随笔為你收集整理的实现FFMPEG 使用CUDA解码播放的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: EA前CEO道歉:曾称不重视氪金的开发者
- 下一篇: 暴雨突袭上海堪比台风过境:树木被狂风吹倒