diff options
author | Michael Niedermayer <michaelni@gmx.at> | 2013-08-18 16:35:38 +0200 |
---|---|---|
committer | Michael Niedermayer <michaelni@gmx.at> | 2013-08-18 16:40:18 +0200 |
commit | c666c59ac1a9d78cc706fa9708c400d8bf454cda (patch) | |
tree | ed2fc126f5046d6cdcc057db699de61bd9b79f5e /libavformat | |
parent | 7d776062f97d14d5d9db96764f4785c91fb3e1f2 (diff) | |
download | ffmpeg-c666c59ac1a9d78cc706fa9708c400d8bf454cda.tar.gz |
mpegts: reanalyze packet size on mismatches
Fixes Ticket1812
Fixes Ticket2838
Signed-off-by: Michael Niedermayer <michaelni@gmx.at>
Diffstat (limited to 'libavformat')
-rw-r--r-- | libavformat/mpegts.c | 38 |
1 files changed, 38 insertions, 0 deletions
diff --git a/libavformat/mpegts.c b/libavformat/mpegts.c index 996348af92..e1f9865e47 100644 --- a/libavformat/mpegts.c +++ b/libavformat/mpegts.c @@ -99,6 +99,10 @@ struct MpegTSContext { /** raw packet size, including FEC if present */ int raw_packet_size; + int size_stat[3]; + int size_stat_count; +#define SIZE_STAT_THRESHOLD 10 + int64_t pos47_full; /** if true, all pids are analyzed to find streams */ @@ -1901,6 +1905,39 @@ static int handle_packet(MpegTSContext *ts, const uint8_t *packet) return 0; } +static void reanalyze(MpegTSContext *ts) { + AVIOContext *pb = ts->stream->pb; + int64_t pos = avio_tell(pb); + if(pos < 0) + return; + pos += ts->raw_packet_size - ts->pos47_full; + if (pos == TS_PACKET_SIZE) { + ts->size_stat[0] ++; + } else if (pos == TS_DVHS_PACKET_SIZE) { + ts->size_stat[1] ++; + } else if (pos == TS_FEC_PACKET_SIZE) { + ts->size_stat[2] ++; + } + + ts->size_stat_count ++; + if(ts->size_stat_count > SIZE_STAT_THRESHOLD) { + int newsize = 0; + if (ts->size_stat[0] > SIZE_STAT_THRESHOLD) { + newsize = TS_PACKET_SIZE; + } else if (ts->size_stat[1] > SIZE_STAT_THRESHOLD) { + newsize = TS_DVHS_PACKET_SIZE; + } else if (ts->size_stat[2] > SIZE_STAT_THRESHOLD) { + newsize = TS_FEC_PACKET_SIZE; + } + if (newsize) { + av_log(ts->stream, AV_LOG_WARNING, "changing packet size to %d\n", newsize); + ts->raw_packet_size = newsize; + } + ts->size_stat_count = 0; + memset(ts->size_stat, 0, sizeof(ts->size_stat)); + } +} + /* XXX: try to find a better synchro over several packets (use get_packet_size() ?) */ static int mpegts_resync(AVFormatContext *s) @@ -1914,6 +1951,7 @@ static int mpegts_resync(AVFormatContext *s) return -1; if (c == 0x47) { avio_seek(pb, -1, SEEK_CUR); + reanalyze(s->priv_data); return 0; } } |