FFMPEG学习记录 :二,函数avformat_open_input分析

在上节中大体总结了播放前的步骤。

其中给流上下文赋能的接口:avformat_open_input(),今天简要记录下学习过程。如有错误欢迎指正。

/**
 * Open an input stream and read the header. The codecs are not opened.
 * The stream must be closed with avformat_close_input().
 *
 * @param ps Pointer to user-supplied AVFormatContext (allocated by avformat_alloc_context).
 *           May be a pointer to NULL, in which case an AVFormatContext is allocated by this
 *           function and written into ps.
 *           Note that a user-supplied AVFormatContext will be freed on failure.
 * @param url URL of the stream to open.
 * @param fmt If non-NULL, this parameter forces a specific input format.
 *            Otherwise the format is autodetected.
 * @param options  A dictionary filled with AVFormatContext and demuxer-private options.
 *                 On return this parameter will be destroyed and replaced with a dict containing
 *                 options that were not found. May be NULL.
 *
 * @return 0 on success, a negative AVERROR on failure.
 *
 * @note If you want to use custom IO, preallocate the format context and set its pb field.
 */
int avformat_open_input(AVFormatContext **ps, const char *url, ff_const59 AVInputFormat *fmt, AVDictionary **options);

大家注意到细节了没?

 @param fmt If non-NULL, this parameter forces a specific input format. Otherwise the format is autodetected.

这是细节。 

int avformat_open_input(AVFormatContext **ps, const char *filename,
                        ff_const59 AVInputFormat *fmt, AVDictionary **options)
{
    AVFormatContext *s = *ps;
...

    if (!s && !(s = avformat_alloc_context()))
        return AVERROR(ENOMEM);
...
    if (fmt)
        s->iformat = fmt;

...
    if ((ret = init_input(s, filename, &tmp)) < 0)
        goto fail;
    s->probe_score = ret;
...
}

如果url 和 fmt 都非空,最后该如何抉择?目的是什么?能不能瞎指定fmt? 反正我第一眼看到的时候就有这个疑问。

另外还有个小的知识点:第二个参数和第三个参数 带了const,不知道有没有人知道这个时候为啥加const ,能否去掉?这里就不推出自己的看法了,有兴趣大家留言。

init_input 是最主要的函数。以上流程图是最一般的走向。特殊情况就不画了。

而avformat_open_input函数最主要的作用就是为了确定format,初始化了结构体里的 AVStream **stream。format如何确定,就是靠着init_input函数。全局变量中有那么多format,花落谁家呢,就是靠着 谭浩强《C程序设计》 提到的打雷台,就是这么的神奇。

最后一个问题,fmt 能不能瞎指定? 可以也不可以,就是这么的玄妙。所有答案就在init_input里。

当url 不为空的时候,一般可以瞎指定,因为这种场景下,在后面的逻辑里会修改format。所以网上所见到的博客,基本上参数 fmt 都置NULL了,不是没有道理的,但是就是没有人解释为什么。

//modify begin @ 6/16

int av_probe_input_buffer2(AVIOContext *pb, ff_const59 AVInputFormat **fmt,
                          const char *filename, void *logctx,
                          unsigned int offset, unsigned int max_probe_size)
{     ...

 for (probe_size = PROBE_BUF_MIN; probe_size <= max_probe_size && !*fmt;
         probe_size = FFMIN(probe_size << 1,
                            FFMAX(max_probe_size, probe_size + 1))) { }

}

 

这里判断条件 !*fmt  ,inputfmt是不可以乱取得。 之前看的有误解。

modify end //

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值