From: Jaroslav Kysela Date: Sun, 3 Jan 2016 20:44:09 +0000 (+0100) Subject: timeshift: read from file fixes, added filemgr_dump traces X-Git-Tag: v4.2.1~1237 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=a1b7002f79ba05b1acd22a88b161122e4c950185;p=thirdparty%2Ftvheadend.git timeshift: read from file fixes, added filemgr_dump traces --- diff --git a/src/timeshift/private.h b/src/timeshift/private.h index f668060a1..e24ca74b2 100644 --- a/src/timeshift/private.h +++ b/src/timeshift/private.h @@ -180,4 +180,12 @@ void timeshift_filemgr_remove void timeshift_filemgr_flush ( timeshift_t *ts, timeshift_file_t *end ); void timeshift_filemgr_close ( timeshift_file_t *tsf ); +void timeshift_filemgr_dump0 ( timeshift_t *ts ); + +static inline void timeshift_filemgr_dump ( timeshift_t *ts ) +{ + if (tvhtrace_enabled()) + timeshift_filemgr_dump0(ts); +} + #endif /* __TVH_TIMESHIFT_PRIVATE_H__ */ diff --git a/src/timeshift/timeshift_filemgr.c b/src/timeshift/timeshift_filemgr.c index 7214c8646..0e0e4f0ae 100644 --- a/src/timeshift/timeshift_filemgr.c +++ b/src/timeshift/timeshift_filemgr.c @@ -119,6 +119,21 @@ static void timeshift_reaper_remove ( timeshift_file_t *tsf ) * File Handling * *************************************************************************/ +void +timeshift_filemgr_dump0 ( timeshift_t *ts ) +{ + timeshift_file_t *tsf; + + if (TAILQ_EMPTY(&ts->files)) { + tvhtrace("timeshift", "ts %d file dump - EMPTY", ts->id); + return; + } + TAILQ_FOREACH(tsf, &ts->files, link) { + tvhtrace("timeshift", "ts %d file dump tsf %p time %"PRId64" last %"PRId64, + ts->id, tsf, tsf->time, tsf->last); + } +} + /* * Get root directory * @@ -321,7 +336,7 @@ timeshift_file_t *timeshift_filemgr_get ( timeshift_t *ts, int64_t start_time ) /* Create File */ snprintf(path, sizeof(path), "%s/tvh-%"PRId64, ts->path, start_time); tvhtrace("timeshift", "ts %d create file %s", ts->id, path); - if ((fd = open(path, O_WRONLY | O_CREAT, 0600)) > 0) { + if ((fd = tvh_open(path, O_WRONLY | O_CREAT, 0600)) > 0) { tsf_tmp = timeshift_filemgr_file_init(ts, start_time); tsf_tmp->wfd = fd; tsf_tmp->path = strdup(path); @@ -339,6 +354,7 @@ timeshift_file_t *timeshift_filemgr_get ( timeshift_t *ts, int64_t start_time ) } } } + timeshift_filemgr_dump(ts); tsf_tl = tsf_tmp; } diff --git a/src/timeshift/timeshift_reader.c b/src/timeshift/timeshift_reader.c index 0668e5dd5..f4e2260b1 100644 --- a/src/timeshift/timeshift_reader.c +++ b/src/timeshift/timeshift_reader.c @@ -43,6 +43,8 @@ static ssize_t _read_buf ( timeshift_file_t *tsf, int fd, void *buf, size_t size ) { + size_t r, ret; + if (tsf && tsf->ram) { if (tsf->roff == tsf->woff) return 0; if (tsf->roff + size > tsf->woff) return -1; @@ -52,10 +54,26 @@ static ssize_t _read_buf ( timeshift_file_t *tsf, int fd, void *buf, size_t size pthread_mutex_unlock(&tsf->ram_lock); return size; } else { - size = read(tsf ? tsf->rfd : fd, buf, size); - if (size > 0 && tsf) - tsf->roff += size; - return size; + ret = 0; + while (size > 0) { + r = read(tsf ? tsf->rfd : fd, buf, size); + if (r < 0) { + if (ERRNO_AGAIN(errno)) + continue; + tvhtrace("timeshift", "read errno %d", errno); + return -1; + } + if (r > 0) { + size -= r; + ret += r; + buf += r; + } + if (r == 0) + return 0; + } + if (ret > 0 && tsf) + tsf->roff += r; + return ret; } } @@ -367,7 +385,7 @@ static int _timeshift_read { timeshift_file_t *tsf = *cur_file; ssize_t r; - off_t off; + off_t off = 0; *sm = NULL; @@ -375,7 +393,7 @@ static int _timeshift_read /* Open file */ if (tsf->rfd < 0 && !tsf->ram) { - tsf->rfd = open(tsf->path, O_RDONLY); + tsf->rfd = tvh_open(tsf->path, O_RDONLY, 0); tvhtrace("timeshift", "ts %d open file %s (fd %i)", ts->id, tsf->path, tsf->rfd); if (tsf->rfd < 0) return -1; @@ -395,19 +413,19 @@ static int _timeshift_read return -1; } tvhtrace("timeshift", "ts %d seek to %jd (fd %i) read msg %p/%"PRId64" (%"PRId64")", - ts->id, (intmax_t)tsf->roff, tsf->rfd, *sm, *sm ? (*sm)->sm_time : -1, (int64_t)r); + ts->id, (intmax_t)off, tsf->rfd, *sm, *sm ? (*sm)->sm_time : -1, (int64_t)r); /* Special case - EOF */ if (r <= sizeof(size_t) || tsf->roff > tsf->size || *sm == NULL) { if (tsf->rfd >= 0) close(tsf->rfd); tsf->rfd = -1; - *cur_file = tsf = timeshift_filemgr_next(tsf, NULL, 0); - if (tsf) - tsf->roff = 0; // reset + *cur_file = timeshift_filemgr_next(tsf, NULL, 0); + if (*cur_file) + (*cur_file)->roff = 0; // reset *wait = 0; - tvhtrace("timeshift", "ts %d eof, cur_file %p", ts->id, *cur_file); - + tvhtrace("timeshift", "ts %d eof, cur_file %p (prev %p)", ts->id, *cur_file, tsf); + timeshift_filemgr_dump(ts); } } return 0; @@ -821,11 +839,9 @@ void *timeshift_reader ( void *p ) /* Terminate */ if (!cur_file || end != 0) { - if (!end) - end = (cur_speed > 0) ? 1 : -1; /* Back to live (unless buffer is full) */ - if (end == 1 && !ts->full) { + if ((end == 1 && !ts->full) || !cur_file) { tvhlog(LOG_DEBUG, "timeshift", "ts %d eob revert to live mode", ts->id); cur_speed = 100; ctrl = streaming_msg_create_code(SMT_SPEED, cur_speed); @@ -834,8 +850,10 @@ void *timeshift_reader ( void *p ) tvhtrace("timeshift", "reader - set TS_LIVE"); /* Flush timeshift buffer to live */ - if (_timeshift_flush_to_live(ts, &cur_file, &wait) == -1) + if (_timeshift_flush_to_live(ts, &cur_file, &wait) == -1) { + pthread_mutex_unlock(&ts->state_mutex); break; + } ts->state = TS_LIVE; diff --git a/src/timeshift/timeshift_writer.c b/src/timeshift/timeshift_writer.c index 89e30d2b0..0d1682c7d 100644 --- a/src/timeshift/timeshift_writer.c +++ b/src/timeshift/timeshift_writer.c @@ -59,6 +59,7 @@ static ssize_t _write { uint8_t *ram; size_t alloc; + ssize_t ret; if (tsf->ram) { pthread_mutex_lock(&tsf->ram_lock); if (tsf->ram_size < tsf->woff + count) { @@ -80,7 +81,10 @@ static ssize_t _write pthread_mutex_unlock(&tsf->ram_lock); return count; } - return _write_fd(tsf->wfd, buf, count); + ret = _write_fd(tsf->wfd, buf, count); + if (ret > 0) + tsf->woff += ret; + return ret; } /*