diff options
| -rwxr-xr-x[-rw-r--r--] | device.c | 23 | ||||
| -rwxr-xr-x[-rw-r--r--] | device.h | 1 | ||||
| -rwxr-xr-x[-rw-r--r--] | pvrinput.c | 2 | ||||
| -rwxr-xr-x[-rw-r--r--] | reader.c | 16 |
4 files changed, 37 insertions, 5 deletions
@@ -345,6 +345,29 @@ cPvrDevice *cPvrDevice::Get(int index) return NULL; } +int cPvrDevice::ReOpen(void) +{ + log(pvrDEBUG1, "cPvrDevice::ReOpen /dev/video%d = %s (%s)", number, CARDNAME[cardname], DRIVERNAME[driver]); + int retry_count = 5; + cString devName = cString::sprintf("/dev/video%d", number); + retry: + close(v4l2_fd); + v4l2_fd = open(devName, O_RDWR); + if (v4l2_fd < 0) { + log(pvrERROR, "cPvrDevice::ReOpen: error reopening %s (%s): %d:%s", + CARDNAME[cardname], *devName, errno, strerror(errno)); + retry_count--; + if (retry_count > 0) { + usleep(1000000); + goto retry; + } + } + else { + log(pvrDEBUG2, "cPvrDevice::ReOpen: %s (%s) successfully re-opened", *devName, CARDNAME[cardname]); + } + return v4l2_fd; +} + void cPvrDevice::ReInit(void) { log(pvrDEBUG1, "cPvrDevice::ReInit /dev/video%d = %s (%s)", number, CARDNAME[cardname], DRIVERNAME[driver]); @@ -133,6 +133,7 @@ public: virtual int NumProvidedSystems(void) const; bool ParseChannel(const cChannel *Channel, int *input, uint64_t *norm, int *LinesPerFrame, int *card, eInputType *inputType, int *apid, int *vpid, int *tpid) const; + int ReOpen(void); void ReInit(void); void StopReadThread(void); void GetStandard(void); diff --git a/pvrinput.c b/pvrinput.c index dc35949..00f75cc 100644..100755 --- a/pvrinput.c +++ b/pvrinput.c @@ -6,7 +6,7 @@ #endif #endif -static const char *VERSION = "2010-04-04"; +static const char *VERSION = "2010-06-09"; static const char *DESCRIPTION = tr("use Hauppauge PVR as input device"); static const char *MAINMENUENTRY = tr("PVR picture settings"); @@ -500,6 +500,7 @@ void cPvrReadThread::Action(void) uint8_t *buffer = new uint8_t[bufferSize]; int r; int retries = 3; + int reopen_retries = 5; struct timeval selTimeout; fd_set selSet; @@ -551,11 +552,11 @@ void cPvrReadThread::Action(void) FD_ZERO(&selSet); FD_SET(parent->v4l2_fd, &selSet); r = select(parent->v4l2_fd + 1, &selSet, 0, 0, &selTimeout); - if (r == 0) { - log(pvrDEBUG2, "cPvrReadThread::Action():timeout on select from /dev/video%d: %d:%s %s", + if ((r == 0) && (errno == 0)) { + log(pvrDEBUG1, "cPvrReadThread::Action():timeout on select from /dev/video%d: %d:%s %s", parent->number, errno, strerror(errno), (retries > 0) ? " - retrying" : ""); - } - else if (r < 0) { + } + else if ((r < 0) || (errno != 0)) { log(pvrERROR, "cPvrReadThread::Action():error on select from /dev/video%d: %d:%s %s", parent->number, errno, strerror(errno), (retries > 0) ? " - retrying" : ""); retries--; @@ -563,6 +564,13 @@ void cPvrReadThread::Action(void) usleep(100); goto retry; } + while (reopen_retries > 0) { + reopen_retries--; + if (parent->ReOpen() > 0) { + retries = 3; + goto retry; + } + } break; } else if (FD_ISSET(parent->v4l2_fd, &selSet)) { |
