请教个关于CUDA decoder的问题
小弟最近在做CUDA real time decoder,用的是CUDA5.0 里面的D3D9decoder的例子,api用的是cuvidXXXXXX,
现在已经做完了,但是突然发现一个问题,每次都是从第一帧开始进行decoder,如何选择从从视频中间开始进行decoder呢?
没有人回答嘛,太伤心了
LZ您好,这个问题我不会,目前无法回答您了,留待其他熟悉此项内容的斑竹/网友继续解答。
祝您好运。
非常感谢版主的帮助,但是我这边比较着急要解决问题,请问NVIDIA在CUDA方面只有一个论坛吗?英文的也可以,谢谢了
英文的cudazone也有,似乎是devtalk.nvidia.com(我这里打不开,需要翻墙)。
以及我建议您等NVIDIA官方支持/总版主来为您解答。他们也许知道, 这样你就不用翻墙了。
happyflyzl你好,据我所知没什么特别简单的办法。
编码好的帧有I/B/P三种,一般情况下可能是类似IBBPIBBP这种排列顺序,I帧可以不依赖任何帧独立解码,P帧依赖于I帧,B帧依赖于I帧和P帧,所以解码顺序实际上是IPBBIPBB。
从第k帧开始解码,如果第k帧是I帧那最好办,如果是B/P帧,就必须向前回溯,找到距离最近的I帧才行。如果你不想全部解码,只想解码特定部分,就需要读两遍videoSource,第一遍找到第一个可以解码的帧k,第二遍跳过k-1帧,开始解码。
如果你用的是SDK的API,可用以下方式先计算帧序号。
首先看你的输入视频是不是带timestamp的信息,就是HandleVideoData这个回调函数里CUVIDSOURCEDATAPACKET* pPacket的结构体,检查
if (pPacket->flags & CUVID_PKT_TIMESTAMP == CUVID_PKT_TIMESTAMP)
,满足这个条件就说明视频带timestamp信息。然后看pPacket->timestamp的值,用这个计算当前解码的帧序列号。
int k = pPacket->timestamp * oFormat.frame_rate.numerator /
(oFormat.frame_rate.denominator * oVideoParserParameters.ulClockRate);
其中,pPacket就是HandleVideoData的CUVIDSOURCEDATAPACKET* pPacket,oFormat可以用cuvidGetSourceVideoFormat从打开的CUvideosource得到,oVideoParserParameters是建立videoParser时传入的CUVIDPARSERPARAMS,默认的ulClockRate为0,就是10M,所以上式的oVideoParserParameters.ulClockRate可以直接写为10000000。
回调函数HandlePictureDecode(void* pUserData, CUVIDPICPARAMS* pPicParams)中pPicParams->intra_pic_flag为1表示当前帧是I帧。可以事先建立数组IPosition保存I帧序号,找到起始帧序号k后,就到数组搜索与k最接近的IPosition,且k>=IPosition。
第二遍调用HandleVideoData就直接从IPosition帧开始解码。
谢谢三位,问题已经解决了。
再问一个问题吧,我试了CUDA不能处理MKV格式的文件,应该是不能处理MKV这样的container,有什么办法能够让它可以处理MKV格式文件吗?
你可以换成ffmpeg的api进行demux,CUvideoSource可以更换,不是必须的。CUvideoParser和CUvideoDecoder是必须的。用demux出来的视频流填充CUVIDSOURCEDATAPACKET结构体然后调用cuvidParseVideoData就行了。
谢谢,大体思路我明白了,非常感谢agathah的帮助,请问你是NVIDIA的工程师吗?有空可以私下请教一下,呵呵
有个思路的问题,NVIDIA打算在下一代的terga SOC里面整合kepler构架的CUDA,请问,现在的terga里面的GPU和CUDA有什么区别?整合之后会带来什么样的优势呢?
Tegra方面的问题我不太清楚,有请横扫千军版主来吧。
有关tegra的我也不清楚,我没有5.5的测试版的toolkit之类可以用,也没有样品,也没有资料。
我建议楼主期待正式推出。以及,有请agathah官方支持来吧:)