timestamps generation improvement when parsing avi
patch by Joakim \ elupus chez ecce dot se / original thread: date: 03/19/2007 01:47 AM subject: [Ffmpeg-devel] [RFC] Improvement for the odd timestamp generation when parser is in use. Originally committed as revision 8725 to svn://svn.ffmpeg.org/ffmpeg/trunk
This commit is contained in:
committed by
Benoit Fouet
parent
946d3b12a1
commit
a74008a4c3
@@ -37,8 +37,8 @@ extern "C" {
|
|||||||
#define AV_STRINGIFY(s) AV_TOSTRING(s)
|
#define AV_STRINGIFY(s) AV_TOSTRING(s)
|
||||||
#define AV_TOSTRING(s) #s
|
#define AV_TOSTRING(s) #s
|
||||||
|
|
||||||
#define LIBAVCODEC_VERSION_INT ((51<<16)+(40<<8)+2)
|
#define LIBAVCODEC_VERSION_INT ((51<<16)+(40<<8)+3)
|
||||||
#define LIBAVCODEC_VERSION 51.40.2
|
#define LIBAVCODEC_VERSION 51.40.3
|
||||||
#define LIBAVCODEC_BUILD LIBAVCODEC_VERSION_INT
|
#define LIBAVCODEC_BUILD LIBAVCODEC_VERSION_INT
|
||||||
|
|
||||||
#define LIBAVCODEC_IDENT "Lavc" AV_STRINGIFY(LIBAVCODEC_VERSION)
|
#define LIBAVCODEC_IDENT "Lavc" AV_STRINGIFY(LIBAVCODEC_VERSION)
|
||||||
@@ -2940,6 +2940,9 @@ typedef struct AVCodecParserContext {
|
|||||||
|
|
||||||
int flags;
|
int flags;
|
||||||
#define PARSER_FLAG_COMPLETE_FRAMES 0x0001
|
#define PARSER_FLAG_COMPLETE_FRAMES 0x0001
|
||||||
|
|
||||||
|
int64_t offset; ///< byte offset from starting packet start
|
||||||
|
int64_t last_offset;
|
||||||
} AVCodecParserContext;
|
} AVCodecParserContext;
|
||||||
|
|
||||||
typedef struct AVCodecParser {
|
typedef struct AVCodecParser {
|
||||||
|
|||||||
@@ -124,6 +124,7 @@ int av_parser_parse(AVCodecParserContext *s,
|
|||||||
s->fetch_timestamp=0;
|
s->fetch_timestamp=0;
|
||||||
s->last_pts = pts;
|
s->last_pts = pts;
|
||||||
s->last_dts = dts;
|
s->last_dts = dts;
|
||||||
|
s->last_offset = 0;
|
||||||
s->cur_frame_pts[k] =
|
s->cur_frame_pts[k] =
|
||||||
s->cur_frame_dts[k] = AV_NOPTS_VALUE;
|
s->cur_frame_dts[k] = AV_NOPTS_VALUE;
|
||||||
}
|
}
|
||||||
@@ -138,6 +139,7 @@ int av_parser_parse(AVCodecParserContext *s,
|
|||||||
s->frame_offset = s->last_frame_offset;
|
s->frame_offset = s->last_frame_offset;
|
||||||
s->pts = s->last_pts;
|
s->pts = s->last_pts;
|
||||||
s->dts = s->last_dts;
|
s->dts = s->last_dts;
|
||||||
|
s->offset = s->last_offset;
|
||||||
|
|
||||||
/* offset of the next frame */
|
/* offset of the next frame */
|
||||||
s->last_frame_offset = s->cur_offset + index;
|
s->last_frame_offset = s->cur_offset + index;
|
||||||
@@ -156,6 +158,7 @@ int av_parser_parse(AVCodecParserContext *s,
|
|||||||
|
|
||||||
s->last_pts = s->cur_frame_pts[k];
|
s->last_pts = s->cur_frame_pts[k];
|
||||||
s->last_dts = s->cur_frame_dts[k];
|
s->last_dts = s->cur_frame_dts[k];
|
||||||
|
s->last_offset = s->last_frame_offset - s->cur_frame_offset[k];
|
||||||
|
|
||||||
/* some parsers tell us the packet size even before seeing the first byte of the next packet,
|
/* some parsers tell us the packet size even before seeing the first byte of the next packet,
|
||||||
so the next pts/dts is in the next chunk */
|
so the next pts/dts is in the next chunk */
|
||||||
|
|||||||
@@ -25,8 +25,8 @@
|
|||||||
extern "C" {
|
extern "C" {
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define LIBAVFORMAT_VERSION_INT ((51<<16)+(12<<8)+0)
|
#define LIBAVFORMAT_VERSION_INT ((51<<16)+(12<<8)+1)
|
||||||
#define LIBAVFORMAT_VERSION 51.12.0
|
#define LIBAVFORMAT_VERSION 51.12.1
|
||||||
#define LIBAVFORMAT_BUILD LIBAVFORMAT_VERSION_INT
|
#define LIBAVFORMAT_BUILD LIBAVFORMAT_VERSION_INT
|
||||||
|
|
||||||
#define LIBAVFORMAT_IDENT "Lavf" AV_STRINGIFY(LIBAVFORMAT_VERSION)
|
#define LIBAVFORMAT_IDENT "Lavf" AV_STRINGIFY(LIBAVFORMAT_VERSION)
|
||||||
@@ -309,7 +309,8 @@ typedef struct AVStream {
|
|||||||
char language[4]; /** ISO 639 3-letter language code (empty string if undefined) */
|
char language[4]; /** ISO 639 3-letter language code (empty string if undefined) */
|
||||||
|
|
||||||
/* av_read_frame() support */
|
/* av_read_frame() support */
|
||||||
int need_parsing; ///< 1->full parsing needed, 2->only parse headers dont repack
|
#define AVSTREAM_PARSE_TIMESTAMPS 3 /**< full parsing and interpolation of timestamps for frames not starting on packet boundary */
|
||||||
|
int need_parsing; ///< 1->full parsing needed, 2->only parse headers dont repack, 3->full parsing and interpolate timestamps
|
||||||
struct AVCodecParserContext *parser;
|
struct AVCodecParserContext *parser;
|
||||||
|
|
||||||
int64_t cur_dts;
|
int64_t cur_dts;
|
||||||
|
|||||||
@@ -452,8 +452,8 @@ static int avi_read_header(AVFormatContext *s, AVFormatParameters *ap)
|
|||||||
if (size%2) /* 2-aligned (fix for Stargate SG-1 - 3x18 - Shades of Grey.avi) */
|
if (size%2) /* 2-aligned (fix for Stargate SG-1 - 3x18 - Shades of Grey.avi) */
|
||||||
url_fskip(pb, 1);
|
url_fskip(pb, 1);
|
||||||
/* Force parsing as several audio frames can be in
|
/* Force parsing as several audio frames can be in
|
||||||
* one packet. */
|
* one packet and timestamps refer to packet start*/
|
||||||
st->need_parsing = 1;
|
st->need_parsing = AVSTREAM_PARSE_TIMESTAMPS;
|
||||||
/* ADTS header is in extradata, AAC without header must be stored as exact frames, parser not needed and it will fail */
|
/* ADTS header is in extradata, AAC without header must be stored as exact frames, parser not needed and it will fail */
|
||||||
if (st->codec->codec_id == CODEC_ID_AAC && st->codec->extradata_size)
|
if (st->codec->codec_id == CODEC_ID_AAC && st->codec->extradata_size)
|
||||||
st->need_parsing = 0;
|
st->need_parsing = 0;
|
||||||
|
|||||||
@@ -584,6 +584,7 @@ static void compute_pkt_fields(AVFormatContext *s, AVStream *st,
|
|||||||
AVCodecParserContext *pc, AVPacket *pkt)
|
AVCodecParserContext *pc, AVPacket *pkt)
|
||||||
{
|
{
|
||||||
int num, den, presentation_delayed, delay, i;
|
int num, den, presentation_delayed, delay, i;
|
||||||
|
int64_t offset;
|
||||||
/* handle wrapping */
|
/* handle wrapping */
|
||||||
if(st->cur_dts != AV_NOPTS_VALUE){
|
if(st->cur_dts != AV_NOPTS_VALUE){
|
||||||
if(pkt->pts != AV_NOPTS_VALUE)
|
if(pkt->pts != AV_NOPTS_VALUE)
|
||||||
@@ -599,6 +600,16 @@ static void compute_pkt_fields(AVFormatContext *s, AVStream *st,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* correct timestamps with byte offset if demuxers only have timestamps on packet boundaries */
|
||||||
|
if(pc && st->need_parsing == AVSTREAM_PARSE_TIMESTAMPS && pkt->size){
|
||||||
|
/* this will estimate bitrate based on this frame's duration and size */
|
||||||
|
offset = av_rescale(pc->offset, pkt->duration, pkt->size);
|
||||||
|
if(pkt->pts != AV_NOPTS_VALUE)
|
||||||
|
pkt->pts += offset;
|
||||||
|
if(pkt->dts != AV_NOPTS_VALUE)
|
||||||
|
pkt->dts += offset;
|
||||||
|
}
|
||||||
|
|
||||||
if(is_intra_only(st->codec))
|
if(is_intra_only(st->codec))
|
||||||
pkt->flags |= PKT_FLAG_KEY;
|
pkt->flags |= PKT_FLAG_KEY;
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user