当前位置: 首页 > news >正文

网站建设深百度搜索资源平台token

网站建设深,百度搜索资源平台token,wordpress下載,360建筑网发布的信息怎么删除摘要:本文描述了FFmpeg中videotoobox解码器如何进行解码工作,如何将一个编码的码流解码为最终的裸流。   关键字:videotoobox,decoder,ffmpeg   VideoToolbox 是一个低级框架,提供对硬件编码器和解码器的直接访问。 它提供视频…

  摘要:本文描述了FFmpeg中videotoobox解码器如何进行解码工作,如何将一个编码的码流解码为最终的裸流。
  关键字:videotoobox,decoder,ffmpeg
  VideoToolbox 是一个低级框架,提供对硬件编码器和解码器的直接访问。 它提供视频压缩和解压缩服务,以及存储在 CoreVideo 像素缓冲区中的光栅图像格式之间的转换服务。 这些服务以会话对象(压缩、解压缩和像素传输)的形式提供,并作为 Core Foundation (CF) 类型输出。 VideoToolbox支持H.263, H.264, HEVC, MPEG-1, MPEG-2, MPEG-4 Part 2, ProRes解码,H.264, HEVC, ProRes编码,最新的版本似乎也支持了VP9解码。

1 主流程

1.1 涉及的Context

  FFmpeg中每个解码器都有自己的Context描述,该描述按照约定的格式描述对应的解码器参数和解码器的处理函数指针。FFmpeg中的VideoToolbox解码器主要实现代码在libavcodec/videotoobox.{h,c}中,其中针对每一种支持的解码格式定义了一个独立的Context,比如ff_h263_videotoolbox_hwaccel,ff_h263_videotoolbox_hwaccel,ff_h264_videotoolbox_hwaccel,...等,只是实现上有差异,我们主要关注其中一个即可,这里主要关注ff_h264_videotoolbox_hwaccel

const AVHWAccel ff_h264_videotoolbox_hwaccel = {.name           = "h264_videotoolbox",.type           = AVMEDIA_TYPE_VIDEO,.id             = AV_CODEC_ID_H264,.pix_fmt        = AV_PIX_FMT_VIDEOTOOLBOX,.alloc_frame    = ff_videotoolbox_alloc_frame,.start_frame    = ff_videotoolbox_h264_start_frame,.decode_slice   = ff_videotoolbox_h264_decode_slice,.decode_params  = videotoolbox_h264_decode_params,.end_frame      = videotoolbox_h264_end_frame,.frame_params   = ff_videotoolbox_frame_params,.init           = ff_videotoolbox_common_init,.uninit         = ff_videotoolbox_uninit,.priv_data_size = sizeof(VTContext),
};

  该结构中定义了:

  • 解码器的名称;
  • 解码数据的类型;
  • 解码器ID;
  • 硬件解码的格式;
  • 申请一个硬件相关的帧结构的函数指针;
  • 解码开始前针对帧进行内存拷贝之类的操作;
  • 解码数据;
  • 解析解码器需要的参数比如sps等;
  • 送帧结束后的后处理;
  • 初始化硬件解码器;
  • 销毁硬件解码器;
  • 当前硬件解码器的描述结构。

  ff_h264_videotoolbox_hwaccel是存储在hw_configs中的,运行时遍历该列表寻找期望的硬件解码器。所以解码工作是先经过FFmpeg内的ff_h264_decoder解码器再进入硬件解码器的。

const AVCodec ff_h264_decoder = {.name                  = "h264",.long_name             = NULL_IF_CONFIG_SMALL("H.264 / AVC / MPEG-4 AVC / MPEG-4 part 10"),.type                  = AVMEDIA_TYPE_VIDEO,.id                    = AV_CODEC_ID_H264,.priv_data_size        = sizeof(H264Context),.init                  = h264_decode_init,.close                 = h264_decode_end,.decode                = h264_decode_frame,.capabilities          = /*AV_CODEC_CAP_DRAW_HORIZ_BAND |*/ AV_CODEC_CAP_DR1 |AV_CODEC_CAP_DELAY | AV_CODEC_CAP_SLICE_THREADS |AV_CODEC_CAP_FRAME_THREADS,.hw_configs            = (const AVCodecHWConfigInternal *const []) {
#if CONFIG_H264_DXVA2_HWACCELHWACCEL_DXVA2(h264),
#endif
#if CONFIG_H264_D3D11VA_HWACCELHWACCEL_D3D11VA(h264),
#endif
#if CONFIG_H264_D3D11VA2_HWACCELHWACCEL_D3D11VA2(h264),
#endif
#if CONFIG_H264_NVDEC_HWACCELHWACCEL_NVDEC(h264),
#endif
#if CONFIG_H264_VAAPI_HWACCELHWACCEL_VAAPI(h264),
#endif
#if CONFIG_H264_VDPAU_HWACCELHWACCEL_VDPAU(h264),
#endif
#if CONFIG_H264_VIDEOTOOLBOX_HWACCELHWACCEL_VIDEOTOOLBOX(h264),
#endifNULL},.caps_internal         = FF_CODEC_CAP_INIT_THREADSAFE | FF_CODEC_CAP_EXPORTS_CROPPING |FF_CODEC_CAP_ALLOCATE_PROGRESS | FF_CODEC_CAP_INIT_CLEANUP,.flush                 = h264_decode_flush,.update_thread_context = ONLY_IF_THREADS_ENABLED(ff_h264_update_thread_context),.update_thread_context_for_user = ONLY_IF_THREADS_ENABLED(ff_h264_update_thread_context_for_user),.profiles              = NULL_IF_CONFIG_SMALL(ff_h264_profiles),.priv_class            = &h264_class,
};

  VTContextVT解码过程中描述VT的Context。

typedef struct VTContext {// The current bitstream buffer.uint8_t                     *bitstream;// The current size of the bitstream.int                         bitstream_size;// The reference size used for fast reallocation.int                         allocated_size;// The core video bufferCVImageBufferRef            frame;// Current dummy frames context (depends on exact CVImageBufferRef params).struct AVBufferRef         *cached_hw_frames_ctx;// Non-NULL if the new hwaccel API is used. This is only a separate struct// to ease compatibility with the old API.struct AVVideotoolboxContext *vt_ctx;// Current H264 parameters (used to trigger decoder restart on SPS changes).uint8_t                     sps[3];bool                        reconfig_needed;void *logctx;
} VTContext;

1.2 主要流程

在这里插入图片描述

2 每个步骤的具体实现

2.1ff_videotoolbox_common_init

  ff_videotoolbox_common_init在初始化解码器时调用,一般是在avcodec_open2时初始化硬件解码器。一般FFmpeg为了更加准确的探测当前视频的媒体信息,在avformat_find_stream_info时就会初始化解码器解码少部分的帧来进行流媒体信息探测。
  初始化时首先就时申请VT的Context内存,并设置一些参数,实际上只设置了VT的callback函数和PixFormat。之后及时根据需要初始化AVHWFramesContext,主要就是申请内存并设置帧格式比如宽高,格式等等。
  最后就是调用videotoolbox_start创建VT的Session,创建的过程比较简单就是直接调用Apple的API创建Session,需要重点关注的是如何设置的。具体的实现函数为videotoolbox_decoder_config_create,其中设置硬件加速的配置时写死的,无法进行配置。另外就是从当前的CodecCteonxt中取出sps等信息送给解码器,如果没有这些信息,解码器是无法准确识别出时间戳信息的。sps和pps的解析是由FFmpeg完成的。

    switch (codec_type) {case kCMVideoCodecType_MPEG4Video :if (avctx->extradata_size)data = videotoolbox_esds_extradata_create(avctx);if (data)CFDictionarySetValue(avc_info, CFSTR("esds"), data);break;case kCMVideoCodecType_H264 :data = ff_videotoolbox_avcc_extradata_create(avctx);if (data)CFDictionarySetValue(avc_info, CFSTR("avcC"), data);break;case kCMVideoCodecType_HEVC :data = ff_videotoolbox_hvcc_extradata_create(avctx);if (data)CFDictionarySetValue(avc_info, CFSTR("hvcC"), data);break;
#if CONFIG_VP9_VIDEOTOOLBOX_HWACCELcase kCMVideoCodecType_VP9 :data = ff_videotoolbox_vpcc_extradata_create(avctx);if (data)CFDictionarySetValue(avc_info, CFSTR("vpcC"), data);break;
#endifdefault:break;}

  解码callback的实现比较简单就是Retain一下CVPixelBuffer。

static void videotoolbox_decoder_callback(void *opaque,void *sourceFrameRefCon,OSStatus status,VTDecodeInfoFlags flags,CVImageBufferRef image_buffer,CMTime pts,CMTime duration)
{VTContext *vtctx = opaque;if (vtctx->frame) {CVPixelBufferRelease(vtctx->frame);vtctx->frame = NULL;}if (!image_buffer) {av_log(vtctx->logctx,  AV_LOG_DEBUG,"vt decoder cb: output image buffer is null: %i\n", status);return;}vtctx->frame = CVPixelBufferRetain(image_buffer);
}

2.2 videotoolbox_h264_decode_paramsff_videotoolbox_frame_params

 &esmp;videotoolbox_h264_decode_params主要的工作就是将上层解码出来额sps和pps信息拷贝到VTContext中。

case H264_NAL_SPS: {GetBitContext tmp_gb = nal->gb;if (avctx->hwaccel && avctx->hwaccel->decode_params) {ret = avctx->hwaccel->decode_params(avctx,nal->type,nal->raw_data,nal->raw_size);if (ret < 0)goto end;}if (ff_h264_decode_seq_parameter_set(&tmp_gb, avctx, &h->ps, 0) >= 0)break;av_log(h->avctx, AV_LOG_DEBUG,"SPS decoding failure, trying again with the complete NAL\n");init_get_bits8(&tmp_gb, nal->raw_data + 1, nal->raw_size - 1);if (ff_h264_decode_seq_parameter_set(&tmp_gb, avctx, &h->ps, 0) >= 0)break;ff_h264_decode_seq_parameter_set(&nal->gb, avctx, &h->ps, 1);break;

  ff_videotoolbox_frame_params比较简单就是将CodecContext中的参数传递给HWFramesContext。

ff_videotoolbox_alloc_frame,ff_videotoolbox_h264_start_frame,ff_videotoolbox_h264_decode_slice,videotoolbox_h264_end_frame

  这几个函数每一帧都会调用,顺序是alloc_frame->start_frame->decode_frame->end_frame
  ff_videotoolbox_alloc_frame用来申请一块内存,此时的内存只是一块儿裸内存只是将release函数指针设置成了VT的release指针,还未与CVPixelBuffer绑定,绑定是在解码器的Callback中进行的。
  ff_videotoolbox_h264_start_frame主要就是将上层传下来的stream数据流拷贝到VTContext中。
  videotoolbox_common_decode_slice也是拷贝数据流。
  videotoolbox_h264_end_frame才是具体将数据送给解码器的地方,核心的地方就是videotoolbox_session_decode_frame,这里送给解码器的数据流就上上面拷贝的数据流,需要注意的是在初始化时的callback中只是做了拷贝内存其他什么也没有做。这是因为在这里调用了VTDecompressionSessionWaitForAsynchronousFrames等待异步解码完成,能够保证上一帧解码完成后才送下一帧数据。

2.3 ff_videotoolbox_uninit

  ff_videotoolbox_uninit比较简单就是释放解码器的Context和缓存中的内存。

  • Apple Documentation——VideoToolbox

文章转载自:
http://cinque.c7617.cn
http://gossyplure.c7617.cn
http://unscripted.c7617.cn
http://hamadan.c7617.cn
http://godhead.c7617.cn
http://diplomatise.c7617.cn
http://blackleggery.c7617.cn
http://drawback.c7617.cn
http://curbing.c7617.cn
http://audibility.c7617.cn
http://hydraemic.c7617.cn
http://duplex.c7617.cn
http://smallclothes.c7617.cn
http://pileup.c7617.cn
http://drudgery.c7617.cn
http://diamagnetism.c7617.cn
http://causey.c7617.cn
http://nonparticipating.c7617.cn
http://antinucleon.c7617.cn
http://insipience.c7617.cn
http://chayote.c7617.cn
http://baddeleyite.c7617.cn
http://malapportioned.c7617.cn
http://contrariwise.c7617.cn
http://kin.c7617.cn
http://hydrazide.c7617.cn
http://paratonic.c7617.cn
http://tuff.c7617.cn
http://cicatrix.c7617.cn
http://microgroove.c7617.cn
http://helipod.c7617.cn
http://archespore.c7617.cn
http://verdict.c7617.cn
http://individualize.c7617.cn
http://lathe.c7617.cn
http://guttle.c7617.cn
http://apocrine.c7617.cn
http://yogurt.c7617.cn
http://camptothecin.c7617.cn
http://diamondoid.c7617.cn
http://incisory.c7617.cn
http://bear.c7617.cn
http://amesace.c7617.cn
http://aleatorism.c7617.cn
http://enantiotropic.c7617.cn
http://hardgoods.c7617.cn
http://intemperate.c7617.cn
http://ethics.c7617.cn
http://sunbreaker.c7617.cn
http://broadax.c7617.cn
http://biennialy.c7617.cn
http://fluidise.c7617.cn
http://enarchist.c7617.cn
http://malty.c7617.cn
http://cyclonoscope.c7617.cn
http://spectacle.c7617.cn
http://generator.c7617.cn
http://tamanoir.c7617.cn
http://reflex.c7617.cn
http://thereout.c7617.cn
http://microtec.c7617.cn
http://occultism.c7617.cn
http://faveolus.c7617.cn
http://reprofile.c7617.cn
http://auding.c7617.cn
http://perceptivity.c7617.cn
http://baudelairean.c7617.cn
http://considering.c7617.cn
http://laicism.c7617.cn
http://extraordinarily.c7617.cn
http://californite.c7617.cn
http://quirites.c7617.cn
http://skin.c7617.cn
http://basilic.c7617.cn
http://drugster.c7617.cn
http://nevada.c7617.cn
http://dross.c7617.cn
http://headcloth.c7617.cn
http://polis.c7617.cn
http://insulant.c7617.cn
http://jumpy.c7617.cn
http://currant.c7617.cn
http://rhodesoid.c7617.cn
http://telferage.c7617.cn
http://besought.c7617.cn
http://baal.c7617.cn
http://cellulose.c7617.cn
http://colligate.c7617.cn
http://semolina.c7617.cn
http://antimutagenic.c7617.cn
http://supersound.c7617.cn
http://parent.c7617.cn
http://avian.c7617.cn
http://pterygoid.c7617.cn
http://throttlehold.c7617.cn
http://istle.c7617.cn
http://suburbicarian.c7617.cn
http://flakeboard.c7617.cn
http://manucode.c7617.cn
http://calchas.c7617.cn
http://www.zhongyajixie.com/news/99438.html

相关文章:

  • 三丰云做网站步骤凤凰军事新闻最新消息
  • 网站建设和咨询服务合同东莞网站推广的公司
  • 阿里巴巴网站威海哪里做十大广告联盟
  • 网站空间一定要买吗网站建设推广服务
  • 用自己的电脑做网站需要备案吗网站推广的方法有哪些?
  • 网站开发管理系统有哪些一键免费生成网页的网站
  • 郑州交友网站建设企业网站有哪些功能
  • 移动网站开发公司seo发帖论坛
  • 海南省澄迈住房和城乡建设厅网站百度推广登录首页
  • 中国个人优秀网站长沙seo网络优化
  • 与建设部网站2023必考十大时政热点
  • 外贸网站开发哪家好目前病毒的最新情况
  • wordpress快速建站教程视频深圳网络营销推广外包
  • 小语种网站建设宁波优化推广找哪家
  • 做网站公司促销海报电子商务网站建设的步骤
  • 龙川网站建设黑帽seo工具
  • 济南汇展做网站b站引流推广
  • 武汉网站建设询搜点网络临沂色度广告有限公司
  • 深圳做专业网站免费发广告的平台
  • 国示范校建设网站免费外链代发
  • 网站开发与设计实训报告心得windows优化大师如何卸载
  • 合肥seo建站网络推广专员是干什么的
  • 台州做网站设计的公司windows优化大师官方免费
  • 策划网站做营销推广万能导航网
  • godaddy网站建设怎么样网络销售公司经营范围
  • tcga做多因素分析的网站qq群推广平台
  • 随州做网站公司水果营销软文
  • linux网站备份免费域名空间申请网址
  • 厦门网页建站申请比较好网站seo优化总结
  • 做国外的营销的网站百度竞价ocpc投放策略