From db9ed727b09f0a895670fbd122b2451a800b7cbb Mon Sep 17 00:00:00 2001 From: samsamsam Date: Tue, 3 Apr 2018 09:37:33 +0200 Subject: [PATCH] Linux DVB output - workaround for BUG? in the DVB drivers Signed-off-by: max_10 Origin commit data ------------------ Branch: master Commit: https://github.com/neutrino-images/ni-libstb-hal/commit/ebf3abadda2ede823d1757a85e7b4529014db15b Author: samsamsam Date: 2018-04-03 (Tue, 03 Apr 2018) ------------------ This commit was generated by Migit --- libeplayer3-arm/main/exteplayer.c | 2 +- libeplayer3-arm/output/linuxdvb_buffering.c | 7 +++ libeplayer3-arm/output/linuxdvb_mipsel.c | 4 ++ libeplayer3-arm/output/writer/mipsel/aac.c | 2 - libeplayer3-arm/output/writer/mipsel/writer.c | 46 +++++++++++++++---- 5 files changed, 50 insertions(+), 11 deletions(-) diff --git a/libeplayer3-arm/main/exteplayer.c b/libeplayer3-arm/main/exteplayer.c index ed82df1..b333d9b 100644 --- a/libeplayer3-arm/main/exteplayer.c +++ b/libeplayer3-arm/main/exteplayer.c @@ -638,7 +638,7 @@ int main(int argc, char *argv[]) memset(argvBuff, '\0', sizeof(argvBuff)); int commandRetVal = -1; /* inform client that we can handle additional commands */ - fprintf(stderr, "{\"EPLAYER3_EXTENDED\":{\"version\":%d}}\n", 43); + fprintf(stderr, "{\"EPLAYER3_EXTENDED\":{\"version\":%d}}\n", 44); if (0 != ParseParams(argc, argv, file, audioFile, &audioTrackIdx, &subtitleTrackIdx, &linuxDvbBufferSizeMB)) { printf("Usage: exteplayer3 filePath [-u user-agent] [-c cookies] [-h headers] [-p prio] [-a] [-d] [-w] [-l] [-s] [-i] [-t audioTrackId] [-9 subtitleTrackId] [-x separateAudioUri] plabackUri\n"); diff --git a/libeplayer3-arm/output/linuxdvb_buffering.c b/libeplayer3-arm/output/linuxdvb_buffering.c index fb7adff..f4c5db3 100644 --- a/libeplayer3-arm/output/linuxdvb_buffering.c +++ b/libeplayer3-arm/output/linuxdvb_buffering.c @@ -349,6 +349,13 @@ int32_t LinuxDvbBuffFlush(Context_t *context __attribute__((unused))) return 0; } +int32_t LinuxDvbBuffResume(Context_t *context __attribute__((unused))) +{ + /* signal if we are waiting for write to DVB decoders */ + WriteWakeUp(); + return 0; +} + ssize_t BufferingWriteV(int fd, const struct iovec *iov, size_t ic) { OutputType_t dataType = OUTPUT_UNK; diff --git a/libeplayer3-arm/output/linuxdvb_mipsel.c b/libeplayer3-arm/output/linuxdvb_mipsel.c index 4ef70df..d9f084d 100644 --- a/libeplayer3-arm/output/linuxdvb_mipsel.c +++ b/libeplayer3-arm/output/linuxdvb_mipsel.c @@ -104,6 +104,8 @@ pthread_mutex_t LinuxDVBmutex; int32_t LinuxDvbBuffOpen(Context_t *context, char *type, int outfd); int32_t LinuxDvbBuffClose(Context_t *context); int32_t LinuxDvbBuffFlush(Context_t *context); +int32_t LinuxDvbBuffResume(Context_t *context); + ssize_t BufferingWriteV(int fd, const struct iovec *iov, size_t ic); int32_t WriteSetBufferingSize(const uint32_t bufferSize); int LinuxDvbStop(Context_t *context, char *type); @@ -383,6 +385,8 @@ int LinuxDvbContinue(Context_t *context __attribute__((unused)), char *type) ret = cERR_LINUXDVB_ERROR; } } + if (isBufferedOutput) + LinuxDvbBuffResume(context); linuxdvb_printf(10, "exiting\n"); return ret; } diff --git a/libeplayer3-arm/output/writer/mipsel/aac.c b/libeplayer3-arm/output/writer/mipsel/aac.c index c382f16..90b48c7 100644 --- a/libeplayer3-arm/output/writer/mipsel/aac.c +++ b/libeplayer3-arm/output/writer/mipsel/aac.c @@ -227,8 +227,6 @@ static int writeDataADTS(WriterAVCallData_t *call) if ((call->private_data && 0 == strncmp("ADTS", (const char *)call->private_data, call->private_size)) || HasADTSHeader(call->data, call->len)) { - //(aacbuf[2] & 0x1F) | 0x40 - //printf("%hhx %hhx %hhx %hhx %hhx %hhx %hhx %hhx\n", call->data[0], call->data[1], call->data[2], call->data[3], call->data[4], call->data[5], call->data[6], call->data[7]); return _writeData(call, 0); } diff --git a/libeplayer3-arm/output/writer/mipsel/writer.c b/libeplayer3-arm/output/writer/mipsel/writer.c index 594ee47..829e4db 100644 --- a/libeplayer3-arm/output/writer/mipsel/writer.c +++ b/libeplayer3-arm/output/writer/mipsel/writer.c @@ -101,6 +101,12 @@ static Writer_t *AvailableWriter[] = /* Functions */ /* ***************************** */ +static void FlusPipe(int pipefd) +{ + char tmp; + while(1 == read(pipefd, &tmp, 1)); +} + ssize_t WriteWithRetry(Context_t *context, int pipefd, int fd, const void *buf, size_t size) { fd_set rfds; @@ -109,6 +115,7 @@ ssize_t WriteWithRetry(Context_t *context, int pipefd, int fd, const void *buf, ssize_t ret; int retval = -1; int maxFd = pipefd > fd ? pipefd : fd; + struct timeval tv; while(size > 0 && 0 == PlaybackDieNow(0) && !context->playback->isSeeking) { @@ -118,18 +125,34 @@ ssize_t WriteWithRetry(Context_t *context, int pipefd, int fd, const void *buf, FD_SET(pipefd, &rfds); FD_SET(fd, &wfds); - retval = select(maxFd + 1, &rfds, &wfds, NULL, NULL); + /* When we PAUSE LINUX DVB outputs buffers then audio/video buffers + * will be filled to full unfortunately, in such case after resume + * select never return with fd set - bug in DVB drivers? + * So, there will be to workarounds: + * 1. write to pipe pipe at resume to exit select immediately + * 2. even if fd is not set exit from select after 0,1s + * (it seems that second workaround is not needed) + */ + //tv.tv_sec = 0; + //tv.tv_usec = 100000; // 100ms + + retval = select(maxFd + 1, &rfds, &wfds, NULL, NULL); //&tv); if (retval < 0) { break; } + //if (retval == 0) + //{ + // //printf("RETURN FROM SELECT DUE TO TIMEOUT TIMEOUT\n"); + // continue; + //} + if(FD_ISSET(pipefd, &rfds)) { - char tmp; - /* flush pipefd pipe */ - while(1 == read(pipefd, &tmp, 1)); - break; + FlusPipe(pipefd); + //printf("RETURN FROM SELECT DUE TO pipefd SET\n"); + continue; } if(FD_ISSET(fd, &wfds)) @@ -150,12 +173,19 @@ ssize_t WriteWithRetry(Context_t *context, int pipefd, int fd, const void *buf, { break; } - } - if (ret < 0) - { return ret; } + else if (ret == 0) + { + //printf("This should not happen. Select return fd ready to write, but write return 0, errno [%d]\n", errno); + tv.tv_sec = 0; + tv.tv_usec = 10000; // 10ms + retval = select(pipefd + 1, &rfds, NULL, NULL, &tv); + if (retval) + FlusPipe(pipefd); + continue; + } size -= ret; buf += ret;