|
|
|
@@ -1524,9 +1524,12 @@ static int64_t mpegts_get_pcr(AVFormatContext *s, int stream_index, |
|
|
|
return timestamp; |
|
|
|
} |
|
|
|
|
|
|
|
static int read_seek(AVFormatContext *s, int stream_index, int64_t target_ts, int flags); |
|
|
|
|
|
|
|
static int read_seek2(AVFormatContext *s, int stream_index, int64_t min_ts, int64_t target_ts, int64_t max_ts, int flags) |
|
|
|
static int read_seek2(AVFormatContext *s, |
|
|
|
int stream_index, |
|
|
|
int64_t min_ts, |
|
|
|
int64_t target_ts, |
|
|
|
int64_t max_ts, |
|
|
|
int flags) |
|
|
|
{ |
|
|
|
int64_t pos; |
|
|
|
|
|
|
|
@@ -1538,14 +1541,15 @@ static int read_seek2(AVFormatContext *s, int stream_index, int64_t min_ts, int6 |
|
|
|
backup = ff_store_parser_state(s); |
|
|
|
|
|
|
|
// detect direction of seeking for search purposes |
|
|
|
flags |= (target_ts - min_ts > (uint64_t)(max_ts - target_ts)) ? AVSEEK_FLAG_BACKWARD : 0; |
|
|
|
flags |= (target_ts - min_ts > (uint64_t)(max_ts - target_ts)) ? |
|
|
|
AVSEEK_FLAG_BACKWARD : 0; |
|
|
|
|
|
|
|
if (flags & AVSEEK_FLAG_BYTE) { |
|
|
|
/* use position directly, we will search starting from it */ |
|
|
|
// use position directly, we will search starting from it |
|
|
|
pos = target_ts; |
|
|
|
} else { |
|
|
|
/* search for some position with good timestamp match */ |
|
|
|
if(stream_index < 0){ |
|
|
|
// search for some position with good timestamp match |
|
|
|
if (stream_index < 0) { |
|
|
|
stream_index_gen_search = av_find_default_stream_index(s); |
|
|
|
if (stream_index_gen_search < 0) { |
|
|
|
ff_restore_parser_state(s, backup); |
|
|
|
@@ -1553,8 +1557,10 @@ static int read_seek2(AVFormatContext *s, int stream_index, int64_t min_ts, int6 |
|
|
|
} |
|
|
|
|
|
|
|
st = s->streams[stream_index_gen_search]; |
|
|
|
/* timestamp for default must be expressed in AV_TIME_BASE units */ |
|
|
|
ts_adj = av_rescale(target_ts, st->time_base.den, AV_TIME_BASE * (int64_t)st->time_base.num); |
|
|
|
// timestamp for default must be expressed in AV_TIME_BASE units |
|
|
|
ts_adj = av_rescale(target_ts, |
|
|
|
st->time_base.den, |
|
|
|
AV_TIME_BASE * (int64_t)st->time_base.num); |
|
|
|
} else { |
|
|
|
ts_adj = target_ts; |
|
|
|
stream_index_gen_search = stream_index; |
|
|
|
@@ -1570,8 +1576,10 @@ static int read_seek2(AVFormatContext *s, int stream_index, int64_t min_ts, int6 |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
/* search for actual matching keyframe/starting position for all streams */ |
|
|
|
if (ff_gen_syncpoint_search(s, stream_index, pos, min_ts, target_ts, max_ts, flags) < 0) { |
|
|
|
// search for actual matching keyframe/starting position for all streams |
|
|
|
if (ff_gen_syncpoint_search(s, stream_index, pos, |
|
|
|
min_ts, target_ts, max_ts, |
|
|
|
flags) < 0) { |
|
|
|
ff_restore_parser_state(s, backup); |
|
|
|
return -1; |
|
|
|
} |
|
|
|
@@ -1584,17 +1592,16 @@ static int read_seek(AVFormatContext *s, int stream_index, int64_t target_ts, in |
|
|
|
{ |
|
|
|
int ret; |
|
|
|
if (flags & AVSEEK_FLAG_BACKWARD) { |
|
|
|
ret = read_seek2(s, stream_index, INT64_MIN, target_ts, target_ts, flags & ~AVSEEK_FLAG_BACKWARD); |
|
|
|
if (ret < 0) { |
|
|
|
// for compatibility reasons, seek to best-fitting timestamp |
|
|
|
ret = read_seek2(s, stream_index, INT64_MIN, target_ts, INT64_MAX, flags & ~AVSEEK_FLAG_BACKWARD); |
|
|
|
} |
|
|
|
flags &= ~AVSEEK_FLAG_BACKWARD; |
|
|
|
ret = read_seek2(s, stream_index, INT64_MIN, target_ts, target_ts, flags); |
|
|
|
if (ret < 0) |
|
|
|
// for compatibility reasons, seek to the best-fitting timestamp |
|
|
|
ret = read_seek2(s, stream_index, INT64_MIN, target_ts, INT64_MAX, flags); |
|
|
|
} else { |
|
|
|
ret = read_seek2(s, stream_index, target_ts, target_ts, INT64_MAX, flags); |
|
|
|
if (ret < 0) { |
|
|
|
// for compatibility reasons, seek to best-fitting timestamp |
|
|
|
if (ret < 0) |
|
|
|
// for compatibility reasons, seek to the best-fitting timestamp |
|
|
|
ret = read_seek2(s, stream_index, INT64_MIN, target_ts, INT64_MAX, flags); |
|
|
|
} |
|
|
|
} |
|
|
|
return ret; |
|
|
|
} |
|
|
|
|