summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--stream/stream.c35
1 files changed, 21 insertions, 14 deletions
diff --git a/stream/stream.c b/stream/stream.c
index a18739eb8c..26bbb7a55a 100644
--- a/stream/stream.c
+++ b/stream/stream.c
@@ -305,22 +305,29 @@ int stream_read_internal(stream_t *s, void *buf, int len)
len= s->fill_buffer ? s->fill_buffer(s, buf, len) : 0;
}
if(len<=0){
+ off_t pos = s->pos;
+ // do not retry if this looks like proper eof
+ if (s->eof || (s->end_pos && pos == s->end_pos))
+ goto eof_out;
// dvdnav has some horrible hacks to "suspend" reads,
// we need to skip this code or seeks will hang.
- if (!s->eof && s->type != STREAMTYPE_DVDNAV) {
- // just in case this is an error e.g. due to network
- // timeout reset and retry
- // Seeking is used as a hack to make network streams
- // reopen the connection, ideally they would implement
- // e.g. a STREAM_CTRL_RECONNECT to do this
- off_t pos = s->pos;
- s->eof=1;
- stream_reset(s);
- stream_seek_internal(s, pos);
- // make sure EOF is set to ensure no endless loops
- s->eof=1;
- return stream_read_internal(s, buf, orig_len);
- }
+ if (s->type == STREAMTYPE_DVDNAV)
+ goto eof_out;
+
+ // just in case this is an error e.g. due to network
+ // timeout reset and retry
+ // Seeking is used as a hack to make network streams
+ // reopen the connection, ideally they would implement
+ // e.g. a STREAM_CTRL_RECONNECT to do this
+ s->eof=1;
+ stream_reset(s);
+ if (stream_seek_internal(s, pos) >= 0 || s->pos != pos) // seek failed
+ goto eof_out;
+ // make sure EOF is set to ensure no endless loops
+ s->eof=1;
+ return stream_read_internal(s, buf, orig_len);
+
+eof_out:
s->eof=1;
return 0;
}