mirror of https://github.com/mpv-player/mpv
demux_lavf: bluray: don't skip stream data when flushing
This code meant to flush demuxer internal buffers by doing a byte seek to the current position. In theory this shouldn't drop any stream data. However, if the stream positions mismatch, then avio_seek() (called by av_seek_frame()) stops being a no-op, and might for example read some data to skip to the seek target. (This can happen if the distance is less than SHORT_SEEK_THRESHOLD.) The positions get out of sync because we drop data at one point (which is what we _want_ to do). Strictly speaking, the AVIOContext flushing is done incorrectly, becuase pb->pos points to the start of the buffer, not the current position. So we have to increment pb->pos by the buffered amount. Since there are other weird reasons why the positions might go out of sync (such as stream_dvd.c dropping buffers itself), and they don't necessarily need to be in sync in the first place unless AVIOContext has nothing buffered internally, just use the sledgehammer approach and correct the position manually. Also run av_seek_frame() after this. Currently, it shouldn't read anything, but who knows how that might change with future libavformat development. This whole change didn't have any observable effect for me, but I'm hoping it fixes a reported problem.
This commit is contained in:
parent
39451732e9
commit
b0cb2977ed
|
@ -1010,12 +1010,13 @@ redo:
|
|||
* call the new API instead of relying on av_seek_frame() to do this
|
||||
* for us.
|
||||
*/
|
||||
av_seek_frame(priv->avfc, 0, stream_tell(demuxer->stream),
|
||||
AVSEEK_FLAG_BYTE);
|
||||
// avio_flush() is designed for write-only streams, and does the wrong
|
||||
// thing when reading. Flush it manually instead.
|
||||
priv->avfc->pb->buf_ptr = priv->avfc->pb->buf_end = priv->avfc->pb->buffer;
|
||||
stream_drop_buffers(demuxer->stream);
|
||||
priv->avfc->pb->buf_ptr = priv->avfc->pb->buf_end = priv->avfc->pb->buffer;
|
||||
priv->avfc->pb->pos = stream_tell(demuxer->stream);
|
||||
av_seek_frame(priv->avfc, 0, stream_tell(demuxer->stream),
|
||||
AVSEEK_FLAG_BYTE);
|
||||
return DEMUXER_CTRL_OK;
|
||||
default:
|
||||
return DEMUXER_CTRL_NOTIMPL;
|
||||
|
|
Loading…
Reference in New Issue