forked from FFmpeg/FFmpeg
lavf: move demuxing-specific fields from FFFormatContext to FormatContextInternal
This commit is contained in:
parent
6d05e7e314
commit
cb80ec0b6c
5 changed files with 85 additions and 68 deletions
|
@ -137,12 +137,13 @@ void ff_remove_stream_group(AVFormatContext *s, AVStreamGroup *stg)
|
|||
/* XXX: suppress the packet queue */
|
||||
void ff_flush_packet_queue(AVFormatContext *s)
|
||||
{
|
||||
FFFormatContext *const si = ffformatcontext(s);
|
||||
avpriv_packet_list_free(&si->parse_queue);
|
||||
FormatContextInternal *const fci = ff_fc_internal(s);
|
||||
FFFormatContext *const si = &fci->fc;
|
||||
avpriv_packet_list_free(&fci->parse_queue);
|
||||
avpriv_packet_list_free(&si->packet_buffer);
|
||||
avpriv_packet_list_free(&si->raw_packet_buffer);
|
||||
avpriv_packet_list_free(&fci->raw_packet_buffer);
|
||||
|
||||
si->raw_packet_buffer_size = 0;
|
||||
fci->raw_packet_buffer_size = 0;
|
||||
}
|
||||
|
||||
void avformat_free_context(AVFormatContext *s)
|
||||
|
@ -191,7 +192,8 @@ void avformat_free_context(AVFormatContext *s)
|
|||
av_packet_free(&si->parse_pkt);
|
||||
av_freep(&s->streams);
|
||||
av_freep(&s->stream_groups);
|
||||
ff_flush_packet_queue(s);
|
||||
if (s->iformat)
|
||||
ff_flush_packet_queue(s);
|
||||
av_freep(&s->url);
|
||||
av_free(s);
|
||||
}
|
||||
|
|
|
@ -63,6 +63,37 @@ typedef struct FormatContextInternal {
|
|||
int missing_ts_warning;
|
||||
#endif
|
||||
};
|
||||
|
||||
// demuxing only
|
||||
struct {
|
||||
/**
|
||||
* Raw packets from the demuxer, prior to parsing and decoding.
|
||||
* This buffer is used for buffering packets until the codec can
|
||||
* be identified, as parsing cannot be done without knowing the
|
||||
* codec.
|
||||
*/
|
||||
PacketList raw_packet_buffer;
|
||||
|
||||
/**
|
||||
* Sum of the size of packets in raw_packet_buffer, in bytes.
|
||||
*/
|
||||
int raw_packet_buffer_size;
|
||||
|
||||
/**
|
||||
* Packets split by the parser get queued here.
|
||||
*/
|
||||
PacketList parse_queue;
|
||||
|
||||
/**
|
||||
* Contexts and child contexts do not contain a metadata option
|
||||
*/
|
||||
int metafree;
|
||||
|
||||
/**
|
||||
* Set if chapter ids are strictly monotonic.
|
||||
*/
|
||||
int chapter_ids_monotonic;
|
||||
};
|
||||
};
|
||||
|
||||
#if FF_API_LAVF_SHORTEST
|
||||
|
|
|
@ -216,6 +216,7 @@ static int update_stream_avctx(AVFormatContext *s)
|
|||
int avformat_open_input(AVFormatContext **ps, const char *filename,
|
||||
const AVInputFormat *fmt, AVDictionary **options)
|
||||
{
|
||||
FormatContextInternal *fci;
|
||||
AVFormatContext *s = *ps;
|
||||
FFFormatContext *si;
|
||||
AVDictionary *tmp = NULL;
|
||||
|
@ -224,7 +225,8 @@ int avformat_open_input(AVFormatContext **ps, const char *filename,
|
|||
|
||||
if (!s && !(s = avformat_alloc_context()))
|
||||
return AVERROR(ENOMEM);
|
||||
si = ffformatcontext(s);
|
||||
fci = ff_fc_internal(s);
|
||||
si = &fci->fc;
|
||||
if (!s->av_class) {
|
||||
av_log(NULL, AV_LOG_ERROR, "Input context has not been properly allocated by avformat_alloc_context() and is not NULL either\n");
|
||||
return AVERROR(EINVAL);
|
||||
|
@ -337,7 +339,7 @@ int avformat_open_input(AVFormatContext **ps, const char *filename,
|
|||
if (s->pb && !si->data_offset)
|
||||
si->data_offset = avio_tell(s->pb);
|
||||
|
||||
si->raw_packet_buffer_size = 0;
|
||||
fci->raw_packet_buffer_size = 0;
|
||||
|
||||
update_stream_avctx(s);
|
||||
|
||||
|
@ -411,7 +413,7 @@ static void force_codec_ids(AVFormatContext *s, AVStream *st)
|
|||
|
||||
static int probe_codec(AVFormatContext *s, AVStream *st, const AVPacket *pkt)
|
||||
{
|
||||
FFFormatContext *const si = ffformatcontext(s);
|
||||
FormatContextInternal *const fci = ff_fc_internal(s);
|
||||
FFStream *const sti = ffstream(st);
|
||||
|
||||
if (sti->request_probe > 0) {
|
||||
|
@ -441,8 +443,8 @@ no_packet:
|
|||
}
|
||||
}
|
||||
|
||||
end = si->raw_packet_buffer_size >= s->probesize
|
||||
|| sti->probe_packets <= 0;
|
||||
end = fci->raw_packet_buffer_size >= s->probesize ||
|
||||
sti->probe_packets <= 0;
|
||||
|
||||
if (end || av_log2(pd->buf_size) != av_log2(pd->buf_size - pkt->size)) {
|
||||
int score = set_codec_from_probe_data(s, st, pd);
|
||||
|
@ -564,7 +566,7 @@ static void update_timestamps(AVFormatContext *s, AVStream *st, AVPacket *pkt)
|
|||
*/
|
||||
static int handle_new_packet(AVFormatContext *s, AVPacket *pkt, int allow_passthrough)
|
||||
{
|
||||
FFFormatContext *const si = ffformatcontext(s);
|
||||
FormatContextInternal *const fci = ff_fc_internal(s);
|
||||
AVStream *st;
|
||||
FFStream *sti;
|
||||
int err;
|
||||
|
@ -588,17 +590,17 @@ static int handle_new_packet(AVFormatContext *s, AVPacket *pkt, int allow_passth
|
|||
|
||||
update_timestamps(s, st, pkt);
|
||||
|
||||
if (sti->request_probe <= 0 && allow_passthrough && !si->raw_packet_buffer.head)
|
||||
if (sti->request_probe <= 0 && allow_passthrough && !fci->raw_packet_buffer.head)
|
||||
return 0;
|
||||
|
||||
err = avpriv_packet_list_put(&si->raw_packet_buffer, pkt, NULL, 0);
|
||||
err = avpriv_packet_list_put(&fci->raw_packet_buffer, pkt, NULL, 0);
|
||||
if (err < 0) {
|
||||
av_packet_unref(pkt);
|
||||
return err;
|
||||
}
|
||||
|
||||
pkt = &si->raw_packet_buffer.tail->pkt;
|
||||
si->raw_packet_buffer_size += pkt->size;
|
||||
pkt = &fci->raw_packet_buffer.tail->pkt;
|
||||
fci->raw_packet_buffer_size += pkt->size;
|
||||
|
||||
err = probe_codec(s, st, pkt);
|
||||
if (err < 0)
|
||||
|
@ -616,7 +618,7 @@ int ff_buffer_packet(AVFormatContext *s, AVPacket *pkt)
|
|||
|
||||
int ff_read_packet(AVFormatContext *s, AVPacket *pkt)
|
||||
{
|
||||
FFFormatContext *const si = ffformatcontext(s);
|
||||
FormatContextInternal *const fci = ff_fc_internal(s);
|
||||
int err;
|
||||
|
||||
#if FF_API_INIT_PACKET
|
||||
|
@ -630,16 +632,16 @@ FF_ENABLE_DEPRECATION_WARNINGS
|
|||
#endif
|
||||
|
||||
for (;;) {
|
||||
PacketListEntry *pktl = si->raw_packet_buffer.head;
|
||||
PacketListEntry *pktl = fci->raw_packet_buffer.head;
|
||||
|
||||
if (pktl) {
|
||||
AVStream *const st = s->streams[pktl->pkt.stream_index];
|
||||
if (si->raw_packet_buffer_size >= s->probesize)
|
||||
if (fci->raw_packet_buffer_size >= s->probesize)
|
||||
if ((err = probe_codec(s, st, NULL)) < 0)
|
||||
return err;
|
||||
if (ffstream(st)->request_probe <= 0) {
|
||||
avpriv_packet_list_get(&si->raw_packet_buffer, pkt);
|
||||
si->raw_packet_buffer_size -= pkt->size;
|
||||
avpriv_packet_list_get(&fci->raw_packet_buffer, pkt);
|
||||
fci->raw_packet_buffer_size -= pkt->size;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
@ -766,11 +768,12 @@ static int has_decode_delay_been_guessed(AVStream *st)
|
|||
static PacketListEntry *get_next_pkt(AVFormatContext *s, AVStream *st,
|
||||
PacketListEntry *pktl)
|
||||
{
|
||||
FFFormatContext *const si = ffformatcontext(s);
|
||||
FormatContextInternal *const fci = ff_fc_internal(s);
|
||||
FFFormatContext *const si = &fci->fc;
|
||||
if (pktl->next)
|
||||
return pktl->next;
|
||||
if (pktl == si->packet_buffer.tail)
|
||||
return si->parse_queue.head;
|
||||
return fci->parse_queue.head;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
@ -850,10 +853,11 @@ static void update_dts_from_pts(AVFormatContext *s, int stream_index,
|
|||
static void update_initial_timestamps(AVFormatContext *s, int stream_index,
|
||||
int64_t dts, int64_t pts, AVPacket *pkt)
|
||||
{
|
||||
FFFormatContext *const si = ffformatcontext(s);
|
||||
FormatContextInternal *const fci = ff_fc_internal(s);
|
||||
FFFormatContext *const si = &fci->fc;
|
||||
AVStream *const st = s->streams[stream_index];
|
||||
FFStream *const sti = ffstream(st);
|
||||
PacketListEntry *pktl = si->packet_buffer.head ? si->packet_buffer.head : si->parse_queue.head;
|
||||
PacketListEntry *pktl = si->packet_buffer.head ? si->packet_buffer.head : fci->parse_queue.head;
|
||||
|
||||
uint64_t shift;
|
||||
|
||||
|
@ -903,9 +907,10 @@ static void update_initial_timestamps(AVFormatContext *s, int stream_index,
|
|||
static void update_initial_durations(AVFormatContext *s, AVStream *st,
|
||||
int stream_index, int64_t duration)
|
||||
{
|
||||
FFFormatContext *const si = ffformatcontext(s);
|
||||
FormatContextInternal *const fci = ff_fc_internal(s);
|
||||
FFFormatContext *const si = &fci->fc;
|
||||
FFStream *const sti = ffstream(st);
|
||||
PacketListEntry *pktl = si->packet_buffer.head ? si->packet_buffer.head : si->parse_queue.head;
|
||||
PacketListEntry *pktl = si->packet_buffer.head ? si->packet_buffer.head : fci->parse_queue.head;
|
||||
int64_t cur_dts = RELATIVE_TS_BASE;
|
||||
|
||||
if (sti->first_dts != AV_NOPTS_VALUE) {
|
||||
|
@ -931,7 +936,7 @@ static void update_initial_durations(AVFormatContext *s, AVStream *st,
|
|||
av_log(s, AV_LOG_DEBUG, "first_dts %s but no packet with dts in the queue\n", av_ts2str(sti->first_dts));
|
||||
return;
|
||||
}
|
||||
pktl = si->packet_buffer.head ? si->packet_buffer.head : si->parse_queue.head;
|
||||
pktl = si->packet_buffer.head ? si->packet_buffer.head : fci->parse_queue.head;
|
||||
sti->first_dts = cur_dts;
|
||||
} else if (sti->cur_dts != RELATIVE_TS_BASE)
|
||||
return;
|
||||
|
@ -963,7 +968,8 @@ static void compute_pkt_fields(AVFormatContext *s, AVStream *st,
|
|||
AVCodecParserContext *pc, AVPacket *pkt,
|
||||
int64_t next_dts, int64_t next_pts)
|
||||
{
|
||||
FFFormatContext *const si = ffformatcontext(s);
|
||||
FormatContextInternal *const fci = ff_fc_internal(s);
|
||||
FFFormatContext *const si = &fci->fc;
|
||||
FFStream *const sti = ffstream(st);
|
||||
int num, den, presentation_delayed, delay;
|
||||
int64_t offset;
|
||||
|
@ -1048,7 +1054,7 @@ static void compute_pkt_fields(AVFormatContext *s, AVStream *st,
|
|||
}
|
||||
}
|
||||
|
||||
if (pkt->duration > 0 && (si->packet_buffer.head || si->parse_queue.head))
|
||||
if (pkt->duration > 0 && (si->packet_buffer.head || fci->parse_queue.head))
|
||||
update_initial_durations(s, st, pkt->stream_index, pkt->duration);
|
||||
|
||||
/* Correct timestamps with byte offset if demuxers only have timestamps
|
||||
|
@ -1156,7 +1162,8 @@ static void compute_pkt_fields(AVFormatContext *s, AVStream *st,
|
|||
static int parse_packet(AVFormatContext *s, AVPacket *pkt,
|
||||
int stream_index, int flush)
|
||||
{
|
||||
FFFormatContext *const si = ffformatcontext(s);
|
||||
FormatContextInternal *const fci = ff_fc_internal(s);
|
||||
FFFormatContext *const si = &fci->fc;
|
||||
AVPacket *out_pkt = si->parse_pkt;
|
||||
AVStream *st = s->streams[stream_index];
|
||||
FFStream *const sti = ffstream(st);
|
||||
|
@ -1249,7 +1256,7 @@ static int parse_packet(AVFormatContext *s, AVPacket *pkt,
|
|||
|
||||
compute_pkt_fields(s, st, sti->parser, out_pkt, next_dts, next_pts);
|
||||
|
||||
ret = avpriv_packet_list_put(&si->parse_queue,
|
||||
ret = avpriv_packet_list_put(&fci->parse_queue,
|
||||
out_pkt, NULL, 0);
|
||||
if (ret < 0)
|
||||
goto fail;
|
||||
|
@ -1324,11 +1331,12 @@ static int extract_extradata(FFFormatContext *si, AVStream *st, const AVPacket *
|
|||
|
||||
static int read_frame_internal(AVFormatContext *s, AVPacket *pkt)
|
||||
{
|
||||
FFFormatContext *const si = ffformatcontext(s);
|
||||
FormatContextInternal *const fci = ff_fc_internal(s);
|
||||
FFFormatContext *const si = &fci->fc;
|
||||
int ret, got_packet = 0;
|
||||
AVDictionary *metadata = NULL;
|
||||
|
||||
while (!got_packet && !si->parse_queue.head) {
|
||||
while (!got_packet && !fci->parse_queue.head) {
|
||||
AVStream *st;
|
||||
FFStream *sti;
|
||||
|
||||
|
@ -1456,8 +1464,8 @@ static int read_frame_internal(AVFormatContext *s, AVPacket *pkt)
|
|||
}
|
||||
}
|
||||
|
||||
if (!got_packet && si->parse_queue.head)
|
||||
ret = avpriv_packet_list_get(&si->parse_queue, pkt);
|
||||
if (!got_packet && fci->parse_queue.head)
|
||||
ret = avpriv_packet_list_get(&fci->parse_queue, pkt);
|
||||
|
||||
if (ret >= 0) {
|
||||
AVStream *const st = s->streams[pkt->stream_index];
|
||||
|
@ -1508,7 +1516,7 @@ static int read_frame_internal(AVFormatContext *s, AVPacket *pkt)
|
|||
#endif
|
||||
}
|
||||
|
||||
if (!si->metafree) {
|
||||
if (!fci->metafree) {
|
||||
int metaret = av_opt_get_dict_val(s, "metadata", AV_OPT_SEARCH_CHILDREN, &metadata);
|
||||
if (metadata) {
|
||||
s->event_flags |= AVFMT_EVENT_FLAG_METADATA_UPDATED;
|
||||
|
@ -1516,7 +1524,7 @@ static int read_frame_internal(AVFormatContext *s, AVPacket *pkt)
|
|||
av_dict_free(&metadata);
|
||||
av_opt_set_dict_val(s, "metadata", NULL, AV_OPT_SEARCH_CHILDREN);
|
||||
}
|
||||
si->metafree = metaret == AVERROR_OPTION_NOT_FOUND;
|
||||
fci->metafree = metaret == AVERROR_OPTION_NOT_FOUND;
|
||||
}
|
||||
|
||||
if (s->debug & FF_FDEBUG_TS)
|
||||
|
|
|
@ -25,6 +25,7 @@
|
|||
#include "libavcodec/bytestream.h"
|
||||
#include "libavcodec/packet_internal.h"
|
||||
#include "avformat.h"
|
||||
#include "avformat_internal.h"
|
||||
#include "avio_internal.h"
|
||||
#include "demux.h"
|
||||
#include "internal.h"
|
||||
|
@ -42,7 +43,7 @@ void avpriv_stream_set_need_parsing(AVStream *st, enum AVStreamParseType type)
|
|||
AVChapter *avpriv_new_chapter(AVFormatContext *s, int64_t id, AVRational time_base,
|
||||
int64_t start, int64_t end, const char *title)
|
||||
{
|
||||
FFFormatContext *const si = ffformatcontext(s);
|
||||
FormatContextInternal *const fci = ff_fc_internal(s);
|
||||
AVChapter *chapter = NULL;
|
||||
int ret;
|
||||
|
||||
|
@ -52,13 +53,13 @@ AVChapter *avpriv_new_chapter(AVFormatContext *s, int64_t id, AVRational time_ba
|
|||
}
|
||||
|
||||
if (!s->nb_chapters) {
|
||||
si->chapter_ids_monotonic = 1;
|
||||
} else if (!si->chapter_ids_monotonic || s->chapters[s->nb_chapters-1]->id >= id) {
|
||||
fci->chapter_ids_monotonic = 1;
|
||||
} else if (!fci->chapter_ids_monotonic || s->chapters[s->nb_chapters-1]->id >= id) {
|
||||
for (unsigned i = 0; i < s->nb_chapters; i++)
|
||||
if (s->chapters[i]->id == id)
|
||||
chapter = s->chapters[i];
|
||||
if (!chapter)
|
||||
si->chapter_ids_monotonic = 0;
|
||||
fci->chapter_ids_monotonic = 0;
|
||||
}
|
||||
|
||||
if (!chapter) {
|
||||
|
@ -92,7 +93,7 @@ void av_format_inject_global_side_data(AVFormatContext *s)
|
|||
|
||||
int avformat_queue_attached_pictures(AVFormatContext *s)
|
||||
{
|
||||
FFFormatContext *const si = ffformatcontext(s);
|
||||
FormatContextInternal *const fci = ff_fc_internal(s);
|
||||
int ret;
|
||||
for (unsigned i = 0; i < s->nb_streams; i++)
|
||||
if (s->streams[i]->disposition & AV_DISPOSITION_ATTACHED_PIC &&
|
||||
|
@ -104,7 +105,7 @@ int avformat_queue_attached_pictures(AVFormatContext *s)
|
|||
continue;
|
||||
}
|
||||
|
||||
ret = avpriv_packet_list_put(&si->raw_packet_buffer,
|
||||
ret = avpriv_packet_list_put(&fci->raw_packet_buffer,
|
||||
&s->streams[i]->attached_pic,
|
||||
av_packet_ref, 0);
|
||||
if (ret < 0)
|
||||
|
|
|
@ -88,17 +88,6 @@ typedef struct FFFormatContext {
|
|||
/* av_seek_frame() support */
|
||||
int64_t data_offset; /**< offset of the first packet */
|
||||
|
||||
/**
|
||||
* Raw packets from the demuxer, prior to parsing and decoding.
|
||||
* This buffer is used for buffering packets until the codec can
|
||||
* be identified, as parsing cannot be done without knowing the
|
||||
* codec.
|
||||
*/
|
||||
PacketList raw_packet_buffer;
|
||||
/**
|
||||
* Packets split by the parser get queued here.
|
||||
*/
|
||||
PacketList parse_queue;
|
||||
/**
|
||||
* The generic code uses this as a temporary packet
|
||||
* to parse packets or for muxing, especially flushing.
|
||||
|
@ -120,10 +109,6 @@ typedef struct FFFormatContext {
|
|||
* permanent ones).
|
||||
*/
|
||||
AVPacket *pkt;
|
||||
/**
|
||||
* Sum of the size of packets in raw_packet_buffer, in bytes.
|
||||
*/
|
||||
int raw_packet_buffer_size;
|
||||
|
||||
#if FF_API_AVSTREAM_SIDE_DATA
|
||||
int inject_global_side_data;
|
||||
|
@ -140,16 +125,6 @@ typedef struct FFFormatContext {
|
|||
* Prefer the codec framerate for avg_frame_rate computation.
|
||||
*/
|
||||
int prefer_codec_framerate;
|
||||
|
||||
/**
|
||||
* Set if chapter ids are strictly monotonic.
|
||||
*/
|
||||
int chapter_ids_monotonic;
|
||||
|
||||
/**
|
||||
* Contexts and child contexts do not contain a metadata option
|
||||
*/
|
||||
int metafree;
|
||||
} FFFormatContext;
|
||||
|
||||
static av_always_inline FFFormatContext *ffformatcontext(AVFormatContext *s)
|
||||
|
|
Loading…
Add table
Reference in a new issue