예제 #1
0
void FormatContext::close()
{
    if (!m_raw)
        return;

    if (isOpened())
    {
        closeCodecContexts();

        AVIOContext *avio = m_raw->pb;
        if (isOutput())
        {
            OutputFormat fmt = outputFormat();
            if (!(fmt.flags() & AVFMT_NOFILE) && !(m_raw->flags & AVFMT_FLAG_CUSTOM_IO)) {
                avio_close(m_raw->pb);
            }
            avformat_free_context(m_raw);
        }
        else
        {
            avformat_close_input(&m_raw);
        }

        m_raw = avformat_alloc_context();
        m_monitor.reset(new char);
        m_isOpened = false;
        m_streamsInfoFound = false;
        m_headerWriten = false;

        // To prevent free not out custom IO, e.g. setted via raw pointer access
        if (m_customIO) {
            // Close custom IO
            av_freep(&avio->buffer);
            av_freep(&avio);
            m_customIO = false;
        }
    }
}
예제 #2
0
void FormatContext::openOutput(const string &uri, OutputFormat format, AVDictionary **options, OptionalErrorCode ec)
{
    clear_if(ec);
    if (!m_raw)
    {
        throws_if(ec, Errors::Unallocated);
        return;
    }

    if (isOpened())
    {
        throws_if(ec, Errors::FormatAlreadyOpened);
        return;
    }

    if (format.isNull())
        format = outputFormat();
    else
        setFormat(format);

    if (format.isNull())
    {
        // Guess format
        format = guessOutputFormat(string(), uri);

        if (format.isNull())
        {
            fflog(AV_LOG_ERROR, "Can't guess output format");
            throws_if(ec, Errors::FormatNullOutputFormat);
            return;
        }
        setFormat(format);
    }

    // Fix stream flags
#if !USE_CODECPAR
    FF_DISABLE_DEPRECATION_WARNINGS
    for (size_t i = 0; i < streamsCount(); ++i) {
        auto st = stream(i);
        if (st.raw()->codec) {
            if (outputFormat().isFlags(AVFMT_GLOBALHEADER)) {
                st.raw()->codec->flags |= AV_CODEC_FLAG_GLOBAL_HEADER;
            }
        }
    }
    FF_ENABLE_DEPRECATION_WARNINGS
#endif

    resetSocketAccess();
    if (!(format.flags() & AVFMT_NOFILE))
    {
        int sts = avio_open2(&m_raw->pb, uri.c_str(), AVIO_FLAG_WRITE, nullptr, options);
        if (sts < 0)
        {
            throws_if(ec, sts, ffmpeg_category());
            return;
        }
    }

    m_uri = uri;
    m_isOpened = true;
}