Add buffering for SH4

Signed-off-by: max_10 <max_10@gmx.de>


Origin commit data
------------------
Branch: master
Commit: fdbe7eafd6
Author: samsamsam <samsamsam@o2.pl>
Date: 2018-04-14 (Sat, 14 Apr 2018)



------------------
This commit was generated by Migit
This commit is contained in:
samsamsam
2018-04-14 19:41:08 +02:00
committed by max_10
parent e27d067a7e
commit 8c04e56f9b
26 changed files with 261 additions and 70 deletions

View File

@@ -24,6 +24,7 @@ libeplayer3_arm_la_SOURCES = \
output/output.c \ output/output.c \
output/writer/common/pes.c \ output/writer/common/pes.c \
output/writer/common/misc.c \ output/writer/common/misc.c \
output/writer/common/writer.c \
output/writer/mipsel/writer.c \ output/writer/mipsel/writer.c \
output/writer/mipsel/aac.c \ output/writer/mipsel/aac.c \
output/writer/mipsel/ac3.c \ output/writer/mipsel/ac3.c \

View File

@@ -585,10 +585,16 @@ static void FFMPEGThread(Context_t *context)
ffmpeg_printf(10, "\n"); ffmpeg_printf(10, "\n");
while (context->playback->isCreationPhase) while (context->playback->isCreationPhase)
{ {
ffmpeg_err("Thread waiting for end of init phase...\n"); ffmpeg_printf(10, "Thread waiting for end of init phase...\n");
usleep(1000); usleep(1000);
} }
ffmpeg_printf(10, "Running!\n"); ffmpeg_printf(10, "Running!\n");
#ifdef __sh__
uint32_t bufferSize = 0;
context->output->Command(context, OUTPUT_GET_BUFFER_SIZE, &bufferSize);
ffmpeg_printf(10, "bufferSize [%u]\n", bufferSize);
#endif
int8_t isWaitingForFinish = 0; int8_t isWaitingForFinish = 0;
while (context && context->playback && context->playback->isPlaying) while (context && context->playback && context->playback->isPlaying)
@@ -602,7 +608,7 @@ static void FFMPEGThread(Context_t *context)
*/ */
#ifdef __sh__ #ifdef __sh__
//IF MOVIE IS PAUSED, WAIT //IF MOVIE IS PAUSED, WAIT
if (context->playback->isPaused) if (0 == bufferSize && context->playback->isPaused)
{ {
ffmpeg_printf(20, "paused\n"); ffmpeg_printf(20, "paused\n");
reset_finish_timeout(); reset_finish_timeout();

View File

@@ -29,6 +29,7 @@ typedef enum
OUTPUT_GET_FRAME_COUNT, OUTPUT_GET_FRAME_COUNT,
OUTPUT_GET_PROGRESSIVE, OUTPUT_GET_PROGRESSIVE,
OUTPUT_SET_BUFFER_SIZE, OUTPUT_SET_BUFFER_SIZE,
OUTPUT_GET_BUFFER_SIZE,
} OutputCmd_t; } OutputCmd_t;
typedef struct typedef struct

View File

@@ -23,7 +23,7 @@ typedef struct
unsigned int Height; unsigned int Height;
unsigned char Version; unsigned char Version;
unsigned int InfoFlags; unsigned int InfoFlags;
ssize_t (* WriteV) (int, const struct iovec *, size_t); ssize_t (* WriteV) (int, const struct iovec *, int);
} WriterAVCallData_t; } WriterAVCallData_t;
@@ -88,8 +88,9 @@ Writer_t *getWriter(char *encoding);
Writer_t *getDefaultVideoWriter(); Writer_t *getDefaultVideoWriter();
Writer_t *getDefaultAudioWriter(); Writer_t *getDefaultAudioWriter();
ssize_t write_with_retry(int fd, const void *buf, size_t size); ssize_t write_with_retry(int fd, const void *buf, int size);
ssize_t writev_with_retry(int fd, const struct iovec *iov, size_t ic); ssize_t writev_with_retry(int fd, const struct iovec *iov, int ic);
ssize_t WriteWithRetry(Context_t *context, int pipefd, int fd, const void *buf, size_t size); ssize_t WriteWithRetry(Context_t *context, int pipefd, int fd, const void *buf, int size);
void FlusPipe(int pipefd);
#endif #endif

View File

@@ -688,7 +688,7 @@ int main(int argc, char *argv[])
memset(argvBuff, '\0', sizeof(argvBuff)); memset(argvBuff, '\0', sizeof(argvBuff));
int commandRetVal = -1; int commandRetVal = -1;
/* inform client that we can handle additional commands */ /* inform client that we can handle additional commands */
fprintf(stderr, "{\"EPLAYER3_EXTENDED\":{\"version\":%d}}\n", 47); fprintf(stderr, "{\"EPLAYER3_EXTENDED\":{\"version\":%d}}\n", 49);
PlayFiles_t playbackFiles; PlayFiles_t playbackFiles;
memset(&playbackFiles, 0x00, sizeof(playbackFiles)); memset(&playbackFiles, 0x00, sizeof(playbackFiles));
@@ -784,7 +784,6 @@ int main(int argc, char *argv[])
if (linuxDvbBufferSizeMB) if (linuxDvbBufferSizeMB)
g_player->output->Command(g_player, OUTPUT_SET_BUFFER_SIZE, &linuxDvbBufferSizeMB); g_player->output->Command(g_player, OUTPUT_SET_BUFFER_SIZE, &linuxDvbBufferSizeMB);
g_player->manager->video->Command(g_player, MANAGER_REGISTER_UPDATED_TRACK_INFO, UpdateVideoTrack); g_player->manager->video->Command(g_player, MANAGER_REGISTER_UPDATED_TRACK_INFO, UpdateVideoTrack);
if (strncmp(playbackFiles.szFirstFile, "rtmp", 4) && strncmp(playbackFiles.szFirstFile, "ffrtmp", 4)) if (strncmp(playbackFiles.szFirstFile, "rtmp", 4) && strncmp(playbackFiles.szFirstFile, "ffrtmp", 4))
{ {

View File

@@ -224,18 +224,24 @@ static void LinuxDvbBuffThread(Context_t *context)
buff_printf(20, "EXIT\n"); buff_printf(20, "EXIT\n");
hasBufferingThreadStarted = false; hasBufferingThreadStarted = false;
close(g_pfd[0]); close(g_pfd[0]);
close(g_pfd[1]); close(g_pfd[1]);
g_pfd[0] = -1; g_pfd[0] = -1;
g_pfd[1] = -1; g_pfd[1] = -1;
} }
int32_t WriteSetBufferingSize(const uint32_t bufferSize) int32_t LinuxDvbBuffSetSize(const uint32_t bufferSize)
{ {
maxBufferingDataSize = bufferSize; maxBufferingDataSize = bufferSize;
return cERR_LINUX_DVB_BUFFERING_NO_ERROR; return cERR_LINUX_DVB_BUFFERING_NO_ERROR;
} }
uint32_t LinuxDvbBuffGetSize()
{
return maxBufferingDataSize;
}
int32_t LinuxDvbBuffOpen(Context_t *context, char *type, int outfd) int32_t LinuxDvbBuffOpen(Context_t *context, char *type, int outfd)
{ {
int32_t error = 0; int32_t error = 0;
@@ -380,7 +386,7 @@ int32_t LinuxDvbBuffResume(Context_t *context __attribute__((unused)))
return 0; return 0;
} }
ssize_t BufferingWriteV(int fd, const struct iovec *iov, size_t ic) ssize_t BufferingWriteV(int fd, const struct iovec *iov, int ic)
{ {
OutputType_t dataType = OUTPUT_UNK; OutputType_t dataType = OUTPUT_UNK;
BufferingNode_t *nodePtr = NULL; BufferingNode_t *nodePtr = NULL;

View File

@@ -104,8 +104,9 @@ int32_t LinuxDvbBuffClose(Context_t *context);
int32_t LinuxDvbBuffFlush(Context_t *context); int32_t LinuxDvbBuffFlush(Context_t *context);
int32_t LinuxDvbBuffResume(Context_t *context); int32_t LinuxDvbBuffResume(Context_t *context);
ssize_t BufferingWriteV(int fd, const struct iovec *iov, size_t ic); ssize_t BufferingWriteV(int fd, const struct iovec *iov, int ic);
int32_t WriteSetBufferingSize(const uint32_t bufferSize); int32_t LinuxDvbBuffSetSize(const uint32_t bufferSize);
uint32_t LinuxDvbBuffGetSize();
int LinuxDvbStop(Context_t *context, char *type); int LinuxDvbStop(Context_t *context, char *type);
@@ -1085,12 +1086,18 @@ static int Command(Context_t *context, OutputCmd_t command, void *argument)
ret = cERR_LINUXDVB_NO_ERROR; ret = cERR_LINUXDVB_NO_ERROR;
if (bufferSize > 0) if (bufferSize > 0)
{ {
WriteSetBufferingSize(bufferSize); LinuxDvbBuffSetSize(bufferSize);
isBufferedOutput = true; isBufferedOutput = true;
} }
} }
break; break;
} }
case OUTPUT_GET_BUFFER_SIZE:
{
ret = cERR_LINUXDVB_NO_ERROR;
*((uint32_t*)argument) = LinuxDvbBuffGetSize();
break;
}
default: default:
linuxdvb_err("ContainerCmd %d not supported!\n", command); linuxdvb_err("ContainerCmd %d not supported!\n", command);
ret = cERR_LINUXDVB_ERROR; ret = cERR_LINUXDVB_ERROR;

View File

@@ -37,6 +37,7 @@
#include <pthread.h> #include <pthread.h>
#include <errno.h> #include <errno.h>
#include <poll.h> #include <poll.h>
#include <sys/uio.h>
#include "bcm_ioctls.h" #include "bcm_ioctls.h"
@@ -90,12 +91,21 @@ struct DVBApiVideoInfo_s
static struct DVBApiVideoInfo_s videoInfo = {-1, -1, -1, -1, -1}; static struct DVBApiVideoInfo_s videoInfo = {-1, -1, -1, -1, -1};
unsigned long long int sCURRENT_PTS = 0; unsigned long long int sCURRENT_PTS = 0;
bool isBufferedOutput = false;
pthread_mutex_t LinuxDVBmutex; pthread_mutex_t LinuxDVBmutex;
/* ***************************** */ /* ***************************** */
/* Prototypes */ /* Prototypes */
/* ***************************** */ /* ***************************** */
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, int ic);
int32_t LinuxDvbBuffSetSize(const uint32_t bufferSize);
uint32_t LinuxDvbBuffGetSize();
int LinuxDvbStop(Context_t *context, char *type); int LinuxDvbStop(Context_t *context, char *type);
@@ -163,11 +173,12 @@ int LinuxDvbOpen(Context_t *context __attribute__((unused)), char *type)
linuxdvb_err("VIDEO_SET_SPEED: %s\n", strerror(errno)); linuxdvb_err("VIDEO_SET_SPEED: %s\n", strerror(errno));
} }
if (isBufferedOutput)
LinuxDvbBuffOpen(context, type, videofd);
} }
if (audio && audiofd < 0) if (audio && audiofd < 0)
{ {
audiofd = open(AUDIODEV, O_RDWR); audiofd = open(AUDIODEV, O_RDWR);
if (audiofd < 0) if (audiofd < 0)
{ {
linuxdvb_err("failed to open %s - errno %d\n", AUDIODEV, errno); linuxdvb_err("failed to open %s - errno %d\n", AUDIODEV, errno);
@@ -195,15 +206,18 @@ int LinuxDvbOpen(Context_t *context __attribute__((unused)), char *type)
linuxdvb_err("ioctl failed with errno %d\n", errno); linuxdvb_err("ioctl failed with errno %d\n", errno);
linuxdvb_err("AUDIO_SET_STREAMTYPE: %s\n", strerror(errno)); linuxdvb_err("AUDIO_SET_STREAMTYPE: %s\n", strerror(errno));
} }
if (isBufferedOutput)
LinuxDvbBuffOpen(context, type, audiofd);
} }
return cERR_LINUXDVB_NO_ERROR; return cERR_LINUXDVB_NO_ERROR;
} }
int LinuxDvbClose(Context_t *context, char *type) int LinuxDvbClose(Context_t *context, char *type)
{ {
unsigned char video = !strcmp("video", type); uint8_t video = !strcmp("video", type);
unsigned char audio = !strcmp("audio", type); uint8_t audio = !strcmp("audio", type);
linuxdvb_printf(10, "v%d a%d\n", video, audio); linuxdvb_printf(10, "v%d a%d\n", video, audio);
@@ -215,6 +229,9 @@ int LinuxDvbClose(Context_t *context, char *type)
getLinuxDVBMutex(FILENAME, __FUNCTION__, __LINE__); getLinuxDVBMutex(FILENAME, __FUNCTION__, __LINE__);
if (isBufferedOutput)
LinuxDvbBuffClose(context);
if (video && videofd != -1) if (video && videofd != -1)
{ {
close(videofd); close(videofd);
@@ -438,6 +455,9 @@ int LinuxDvbContinue(Context_t *context __attribute__((unused)), char *type)
ret = cERR_LINUXDVB_ERROR; ret = cERR_LINUXDVB_ERROR;
} }
} }
if (isBufferedOutput)
LinuxDvbBuffResume(context);
linuxdvb_printf(10, "exiting\n"); linuxdvb_printf(10, "exiting\n");
@@ -1060,6 +1080,7 @@ static int Write(void *_context, void *_out)
call.Height = out->height; call.Height = out->height;
call.InfoFlags = out->infoFlags; call.InfoFlags = out->infoFlags;
call.Version = 0; // is unsingned char call.Version = 0; // is unsingned char
call.WriteV = isBufferedOutput ? BufferingWriteV : writev;
if (writer->writeData) if (writer->writeData)
{ {
@@ -1109,6 +1130,7 @@ static int Write(void *_context, void *_out)
call.FrameScale = out->timeScale; call.FrameScale = out->timeScale;
call.InfoFlags = out->infoFlags; call.InfoFlags = out->infoFlags;
call.Version = 0; /* -1; unsigned char cannot be negative */ call.Version = 0; /* -1; unsigned char cannot be negative */
call.WriteV = isBufferedOutput ? BufferingWriteV : writev;
if (writer->writeData) if (writer->writeData)
{ {
@@ -1166,6 +1188,9 @@ static int reset(Context_t *context)
} }
free(Encoding); free(Encoding);
if (isBufferedOutput)
LinuxDvbBuffFlush(context);
return ret; return ret;
} }
@@ -1283,6 +1308,27 @@ static int Command(void *_context, OutputCmd_t command, void *argument)
*((int *)argument) = videoInfo.progressive; *((int *)argument) = videoInfo.progressive;
break; break;
} }
case OUTPUT_SET_BUFFER_SIZE:
{
ret = cERR_LINUXDVB_ERROR;
if (!isBufferedOutput)
{
uint32_t bufferSize = *((uint32_t*)argument);
ret = cERR_LINUXDVB_NO_ERROR;
if (bufferSize > 0)
{
LinuxDvbBuffSetSize(bufferSize);
isBufferedOutput = true;
}
}
break;
}
case OUTPUT_GET_BUFFER_SIZE:
{
ret = cERR_LINUXDVB_NO_ERROR;
*((uint32_t*)argument) = LinuxDvbBuffGetSize();
break;
}
default: default:
linuxdvb_err("ContainerCmd %d not supported!\n", command); linuxdvb_err("ContainerCmd %d not supported!\n", command);
ret = cERR_LINUXDVB_ERROR; ret = cERR_LINUXDVB_ERROR;

View File

@@ -564,6 +564,25 @@ static int Command(Context_t *context, OutputCmd_t command, void *argument)
} }
break; break;
} }
case OUTPUT_GET_BUFFER_SIZE:
{
if (context && context->playback)
{
if (context->output->video)
{
return context->output->video->Command(context, OUTPUT_GET_BUFFER_SIZE, argument);
}
else if (context->output->audio)
{
return context->output->audio->Command(context, OUTPUT_GET_BUFFER_SIZE, argument);
}
}
else
{
ret = cERR_OUTPUT_INTERNAL_ERROR;
}
break;
}
default: default:
output_err("%s::%s OutputCmd %d not supported!\n", __FILE__, __FUNCTION__, command); output_err("%s::%s OutputCmd %d not supported!\n", __FILE__, __FUNCTION__, command);
ret = cERR_OUTPUT_INTERNAL_ERROR; ret = cERR_OUTPUT_INTERNAL_ERROR;

View File

@@ -0,0 +1,74 @@
/*
* linuxdvb output/writer handling.
*
* konfetti 2010
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*
*/
/* ***************************** */
/* Includes */
/* ***************************** */
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include "misc.h"
#include "writer.h"
#include "common.h"
/* ***************************** */
/* Makros/Constants */
/* ***************************** */
#define WRITER_DEBUG
#ifdef WRITER_DEBUG
static short debug_level = 0;
#define writer_printf(level, x...) do { \
if (debug_level >= level) printf(x); } while (0)
#else
#define writer_printf(level, x...)
#endif
#ifndef WRITER_SILENT
#define writer_err(x...) do { printf(x); } while (0)
#else
#define writer_err(x...)
#endif
/* ***************************** */
/* Types */
/* ***************************** */
/* ***************************** */
/* Varaibles */
/* ***************************** */
/* ***************************** */
/* Prototypes */
/* ***************************** */
/* ***************************** */
/* Functions */
/* ***************************** */
void FlusPipe(int pipefd)
{
char tmp;
while(1 == read(pipefd, &tmp, 1));
}

View File

@@ -323,8 +323,8 @@ static int writeDataLATM(WriterAVCallData_t *call)
int ret = latmenc_decode_extradata(pLATMCtx, call->private_data, call->private_size); int ret = latmenc_decode_extradata(pLATMCtx, call->private_data, call->private_size);
if (ret) if (ret)
{ {
printf("%02x %02x %02x %02x %02x %02x %02x %02x\n", (int)call->data[0], (int)call->data[1], (int)call->data[2], (int)call->data[3], \ //printf("%02x %02x %02x %02x %02x %02x %02x %02x\n", (int)call->data[0], (int)call->data[1], (int)call->data[2], (int)call->data[3], \
(int)call->data[4], (int)call->data[5], (int)call->data[6], (int)call->data[7]); // (int)call->data[4], (int)call->data[5], (int)call->data[6], (int)call->data[7]);
aac_err("latm_decode_extradata failed. ignoring...\n"); aac_err("latm_decode_extradata failed. ignoring...\n");
return 0; return 0;
} }

View File

@@ -101,13 +101,7 @@ static Writer_t *AvailableWriter[] =
/* Functions */ /* Functions */
/* ***************************** */ /* ***************************** */
static void FlusPipe(int pipefd) ssize_t WriteWithRetry(Context_t *context, int pipefd, int fd, const void *buf, int size)
{
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; fd_set rfds;
fd_set wfds; fd_set wfds;
@@ -194,14 +188,13 @@ ssize_t WriteWithRetry(Context_t *context, int pipefd, int fd, const void *buf,
return 0; return 0;
} }
ssize_t write_with_retry(int fd, const void *buf, size_t size) ssize_t write_with_retry(int fd, const void *buf, int size)
{ {
ssize_t ret; ssize_t ret;
int retval = 0; int retval = 0;
while (size > 0 && 0 == PlaybackDieNow(0)) while (size > 0 && 0 == PlaybackDieNow(0))
{ {
ret = write(fd, buf, size); ret = write(fd, buf, size);
//printf("[%d] write [%lld]\n", fd, ret);
if (ret < 0) if (ret < 0)
{ {
switch (errno) switch (errno)
@@ -239,7 +232,7 @@ ssize_t write_with_retry(int fd, const void *buf, size_t size)
return 0; return 0;
} }
ssize_t writev_with_retry(int fd, const struct iovec *iov, size_t ic) ssize_t writev_with_retry(int fd, const struct iovec *iov, int ic)
{ {
ssize_t len = 0; ssize_t len = 0;
uint32_t i = 0; uint32_t i = 0;

View File

@@ -211,7 +211,7 @@ static int _writeData(void *_call, int type)
iov[0].iov_len = HeaderLength; iov[0].iov_len = HeaderLength;
iov[1].iov_base = call->data; iov[1].iov_base = call->data;
iov[1].iov_len = call->len; iov[1].iov_len = call->len;
return writev(call->fd, iov, 2); return call->WriteV(call->fd, iov, 2);
} }
static int writeDataADTS(void *_call) static int writeDataADTS(void *_call)
@@ -279,7 +279,7 @@ static int writeDataADTS(void *_call)
iov[1].iov_base = call->data; iov[1].iov_base = call->data;
iov[1].iov_len = call->len; iov[1].iov_len = call->len;
return writev(call->fd, iov, 2); return call->WriteV(call->fd, iov, 2);
} }
static int writeDataLATM(void *_call) static int writeDataLATM(void *_call)
@@ -325,8 +325,8 @@ static int writeDataLATM(void *_call)
int ret = latmenc_decode_extradata(pLATMCtx, call->private_data, call->private_size); int ret = latmenc_decode_extradata(pLATMCtx, call->private_data, call->private_size);
if (ret) if (ret)
{ {
printf("%02x %02x %02x %02x %02x %02x %02x %02x\n", (int)call->data[0], (int)call->data[1], (int)call->data[2], (int)call->data[3], \ //printf("%02x %02x %02x %02x %02x %02x %02x %02x\n", (int)call->data[0], (int)call->data[1], (int)call->data[2], (int)call->data[3], \
(int)call->data[4], (int)call->data[5], (int)call->data[6], (int)call->data[7]); // (int)call->data[4], (int)call->data[5], (int)call->data[6], (int)call->data[7]);
aac_err("latm_decode_extradata failed. ignoring...\n"); aac_err("latm_decode_extradata failed. ignoring...\n");
return 0; return 0;
} }
@@ -349,7 +349,7 @@ static int writeDataLATM(void *_call)
iov[2].iov_base = pLATMCtx->buffer; iov[2].iov_base = pLATMCtx->buffer;
iov[2].iov_len = pLATMCtx->len; iov[2].iov_len = pLATMCtx->len;
return writev(call->fd, iov, 3); return call->WriteV(call->fd, iov, 3);
} }
/* ***************************** */ /* ***************************** */

View File

@@ -130,7 +130,7 @@ static int writeData(void *_call)
iov[1].iov_base = call->data; iov[1].iov_base = call->data;
iov[1].iov_len = call->len; iov[1].iov_len = call->len;
return writev(call->fd, iov, 2); return call->WriteV(call->fd, iov, 2);
} }
/* ***************************** */ /* ***************************** */

View File

@@ -179,7 +179,7 @@ static int writeData(void *_call)
iov[ic].iov_base = call->data; iov[ic].iov_base = call->data;
iov[ic++].iov_len = call->len; iov[ic++].iov_len = call->len;
int len = writev(call->fd, iov, ic); int len = call->WriteV(call->fd, iov, ic);
divx_printf(10, "xvid_Write < len=%d\n", len); divx_printf(10, "xvid_Write < len=%d\n", len);

View File

@@ -209,7 +209,7 @@ static int writeData(void *_call)
iov[ic].iov_base = call->data; iov[ic].iov_base = call->data;
iov[ic++].iov_len = call->len; iov[ic++].iov_len = call->len;
int len = writev(call->fd, iov, ic); int len = call->WriteV(call->fd, iov, ic);
divx_printf(10, "xvid_Write < len=%d\n", len); divx_printf(10, "xvid_Write < len=%d\n", len);

View File

@@ -161,7 +161,7 @@ static int32_t writeData(void *_call)
iov[1].iov_base = Data; iov[1].iov_base = Data;
iov[1].iov_len = Size; iov[1].iov_len = Size;
int32_t len = writev(call->fd, iov, 2); int32_t len = call->WriteV(call->fd, iov, 2);
dts_printf(10, "< len %d\n", len); dts_printf(10, "< len %d\n", len);
return len; return len;
} }

View File

@@ -141,7 +141,7 @@ static int writeData(void *_call)
iov[0].iov_len = HeaderLength; iov[0].iov_len = HeaderLength;
iov[1].iov_base = call->data; iov[1].iov_base = call->data;
iov[1].iov_len = call->len; iov[1].iov_len = call->len;
len = writev(call->fd, iov, 2); len = call->WriteV(call->fd, iov, 2);
h263_printf(10, "< len %d\n", len); h263_printf(10, "< len %d\n", len);
return len; return len;

View File

@@ -100,7 +100,6 @@ const uint8_t Head[] = {0, 0, 0, 1};
static int32_t initialHeader = 1; static int32_t initialHeader = 1;
static uint32_t NalLengthBytes = 1; static uint32_t NalLengthBytes = 1;
static int avc3 = 0; static int avc3 = 0;
static int sps_pps_in_stream = 0;
/* ***************************** */ /* ***************************** */
/* Prototypes */ /* Prototypes */
/* ***************************** */ /* ***************************** */
@@ -263,23 +262,12 @@ static int32_t writeData(void *_call)
(call->len > 3) && ((call->data[0] == 0x00 && call->data[1] == 0x00 && call->data[2] == 0x00 && call->data[3] == 0x01) || (call->len > 3) && ((call->data[0] == 0x00 && call->data[1] == 0x00 && call->data[2] == 0x00 && call->data[3] == 0x01) ||
(call->data[0] == 0xff && call->data[1] == 0xff && call->data[2] == 0xff && call->data[3] == 0xff)))) (call->data[0] == 0xff && call->data[1] == 0xff && call->data[2] == 0xff && call->data[3] == 0xff))))
{ {
uint32_t i = 0;
uint8_t InsertPrivData = !sps_pps_in_stream;
uint32_t PacketLength = 0; uint32_t PacketLength = 0;
uint32_t FakeStartCode = PES_VERSION_FAKE_START_CODE; uint32_t FakeStartCode = /*(call->Version << 8) | */PES_VERSION_FAKE_START_CODE;
iov[ic++].iov_base = PesHeader; iov[ic++].iov_base = PesHeader;
initialHeader = 0;
while (InsertPrivData && i < 36 && (call->len - i) > 5) if (initialHeader)
{
if ((call->data[i] == 0x00 && call->data[i + 1] == 0x00 && call->data[i + 2] == 0x00 && call->data[i + 3] == 0x01 && (call->data[i + 4] == 0x67 || call->data[i + 4] == 0x68)))
{
InsertPrivData = 0;
sps_pps_in_stream = 1;
}
i += 1;
}
if (InsertPrivData && call->private_size > 0 /*&& initialHeader*/) // some rtsp streams can update codec data at runtime
{ {
initialHeader = 0; initialHeader = 0;
iov[ic].iov_base = call->private_data; iov[ic].iov_base = call->private_data;
@@ -301,7 +289,7 @@ static int32_t writeData(void *_call)
iov[ic++].iov_len = 1; iov[ic++].iov_len = 1;
iov[0].iov_len = InsertPesHeader(PesHeader, -1, MPEG_VIDEO_PES_START_CODE, VideoPts, FakeStartCode); iov[0].iov_len = InsertPesHeader(PesHeader, -1, MPEG_VIDEO_PES_START_CODE, VideoPts, FakeStartCode);
int ret = writev(call->fd, iov, ic); int ret = call->WriteV(call->fd, iov, ic);
return ret; return ret;
} }
else if (!call->private_data || call->private_size < 7 || 1 != call->private_data[0]) else if (!call->private_data || call->private_size < 7 || 1 != call->private_data[0])
@@ -310,7 +298,7 @@ static int32_t writeData(void *_call)
return 0; return 0;
} }
if (!avc3) if (initialHeader)
{ {
uint8_t *private_data = call->private_data; uint8_t *private_data = call->private_data;
uint32_t private_size = call->private_size; uint32_t private_size = call->private_size;
@@ -368,7 +356,7 @@ static int32_t writeData(void *_call)
iov[ic++].iov_len = InsertPesHeader(PesHeader, ParametersLength, MPEG_VIDEO_PES_START_CODE, INVALID_PTS_VALUE, 0); iov[ic++].iov_len = InsertPesHeader(PesHeader, ParametersLength, MPEG_VIDEO_PES_START_CODE, INVALID_PTS_VALUE, 0);
iov[ic].iov_base = HeaderData; iov[ic].iov_base = HeaderData;
iov[ic++].iov_len = ParametersLength; iov[ic++].iov_len = ParametersLength;
len = writev(call->fd, iov, ic); len = call->WriteV(call->fd, iov, ic);
if (len < 0) if (len < 0)
{ {
return len; return len;
@@ -424,7 +412,7 @@ static int32_t writeData(void *_call)
} }
iov[0].iov_len = InsertPesHeader(PesHeader, InitialHeaderLength, MPEG_VIDEO_PES_START_CODE, INVALID_PTS_VALUE, 0); iov[0].iov_len = InsertPesHeader(PesHeader, InitialHeaderLength, MPEG_VIDEO_PES_START_CODE, INVALID_PTS_VALUE, 0);
ssize_t l = writev(call->fd, iov, ic); ssize_t l = call->WriteV(call->fd, iov, ic);
if (private_data != call->private_data) if (private_data != call->private_data)
{ {
@@ -498,7 +486,7 @@ static int32_t writeData(void *_call)
h264_printf(20, " pts=%llu\n", VideoPts); h264_printf(20, " pts=%llu\n", VideoPts);
iov[0].iov_len = InsertPesHeader(PesHeader, NalLength, MPEG_VIDEO_PES_START_CODE, VideoPts, 0); iov[0].iov_len = InsertPesHeader(PesHeader, NalLength, MPEG_VIDEO_PES_START_CODE, VideoPts, 0);
ssize_t l = writev(call->fd, iov, ic); ssize_t l = call->WriteV(call->fd, iov, ic);
if (l < 0) if (l < 0)
return l; return l;
len += l; len += l;
@@ -537,4 +525,4 @@ struct Writer_s WriterVideoH264 =
&reset, &reset,
&writeData, &writeData,
&caps &caps
}; };

View File

@@ -128,7 +128,7 @@ static int writeData(void *_call)
iov[1].iov_base = call->data; iov[1].iov_base = call->data;
iov[1].iov_len = call->len; iov[1].iov_len = call->len;
int len = writev(call->fd, iov, 2); int len = call->WriteV(call->fd, iov, 2);
mp3_printf(10, "mp3_Write-< len=%d\n", len); mp3_printf(10, "mp3_Write-< len=%d\n", len);
return len; return len;

View File

@@ -140,7 +140,7 @@ static int writeData(void *_call)
iov[1].iov_base = call->data + Position; iov[1].iov_base = call->data + Position;
iov[1].iov_len = PacketLength; iov[1].iov_len = PacketLength;
ssize_t l = writev(call->fd, iov, 2); ssize_t l = call->WriteV(call->fd, iov, 2);
if (l < 0) if (l < 0)
{ {
len = l; len = l;

View File

@@ -333,7 +333,7 @@ static int32_t writeData(void *_call)
lpcm_prv[1] = ((lpcm_prv[1] + SubFramesPerPES) & 0x1F); lpcm_prv[1] = ((lpcm_prv[1] + SubFramesPerPES) & 0x1F);
iov[0].iov_len = InsertPesHeader(PesHeader, iov[1].iov_len + iov[2].iov_len, PCM_PES_START_CODE, call->Pts, 0); iov[0].iov_len = InsertPesHeader(PesHeader, iov[1].iov_len + iov[2].iov_len, PCM_PES_START_CODE, call->Pts, 0);
int32_t len = writev(call->fd, iov, 3); int32_t len = call->WriteV(call->fd, iov, 3);
if (len < 0) if (len < 0)
{ {
break; break;

View File

@@ -199,14 +199,14 @@ static int writeData(void *_call)
iov[1].iov_base = PesPayload; iov[1].iov_base = PesPayload;
iov[1].iov_len = PesPtr - PesPayload; iov[1].iov_len = PesPtr - PesPayload;
iov[0].iov_len = InsertPesHeader(PesHeader, iov[1].iov_len, VC1_VIDEO_PES_START_CODE, INVALID_PTS_VALUE, 0); iov[0].iov_len = InsertPesHeader(PesHeader, iov[1].iov_len, VC1_VIDEO_PES_START_CODE, INVALID_PTS_VALUE, 0);
len = writev(call->fd, iov, 2); len = call->WriteV(call->fd, iov, 2);
/* For VC1 the codec private data is a standard vc1 sequence header so we just copy it to the output */ /* For VC1 the codec private data is a standard vc1 sequence header so we just copy it to the output */
iov[0].iov_base = PesHeader; iov[0].iov_base = PesHeader;
iov[1].iov_base = call->private_data; iov[1].iov_base = call->private_data;
iov[1].iov_len = call->private_size; iov[1].iov_len = call->private_size;
iov[0].iov_len = InsertPesHeader(PesHeader, iov[1].iov_len, VC1_VIDEO_PES_START_CODE, INVALID_PTS_VALUE, 0); iov[0].iov_len = InsertPesHeader(PesHeader, iov[1].iov_len, VC1_VIDEO_PES_START_CODE, INVALID_PTS_VALUE, 0);
len = writev(call->fd, iov, 2); len = call->WriteV(call->fd, iov, 2);
initialHeader = 0; initialHeader = 0;
} }
@@ -251,7 +251,7 @@ static int writeData(void *_call)
iov[1].iov_base = call->data + Position; iov[1].iov_base = call->data + Position;
iov[1].iov_len = PacketLength; iov[1].iov_len = PacketLength;
ssize_t l = writev(call->fd, iov, 2); ssize_t l = call->WriteV(call->fd, iov, 2);
if (l < 0) if (l < 0)
{ {
len = l; len = l;

View File

@@ -140,7 +140,7 @@ static int writeData(void *_call)
iov[0].iov_len = InsertPesHeader(PesHeader, call->private_size, MPEG_AUDIO_PES_START_CODE, 0, 0); iov[0].iov_len = InsertPesHeader(PesHeader, call->private_size, MPEG_AUDIO_PES_START_CODE, 0, 0);
iov[1].iov_base = call->private_data; iov[1].iov_base = call->private_data;
iov[1].iov_len = call->private_size; iov[1].iov_len = call->private_size;
len = writev(call->fd, iov, 2); len = call->WriteV(call->fd, iov, 2);
initialHeader = 0; initialHeader = 0;
} }
@@ -153,7 +153,7 @@ static int writeData(void *_call)
iov[1].iov_base = call->data; iov[1].iov_base = call->data;
iov[1].iov_len = call->len; iov[1].iov_len = call->len;
ssize_t l = writev(call->fd, iov, 2); ssize_t l = call->WriteV(call->fd, iov, 2);
len = (l > -1) ? len + l : l; len = (l > -1) ? len + l : l;
} }

View File

@@ -26,6 +26,7 @@
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#include "misc.h"
#include "writer.h" #include "writer.h"
/* ***************************** */ /* ***************************** */
@@ -96,6 +97,54 @@ static Writer_t *AvailableWriter[] =
/* ***************************** */ /* ***************************** */
/* Functions */ /* Functions */
/* ***************************** */ /* ***************************** */
ssize_t WriteWithRetry(Context_t *context, int pipefd, int fd, const void *buf, int size)
{
fd_set rfds;
ssize_t ret;
int retval = -1;
struct timeval tv;
while(size > 0 && 0 == PlaybackDieNow(0) && !context->playback->isSeeking)
{
if (context->playback->isPaused)
{
FD_ZERO(&rfds);
FD_SET(pipefd, &rfds);
tv.tv_sec = 0;
tv.tv_usec = 500000; // 500ms
retval = select(pipefd + 1, &rfds, 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))
{
FlusPipe(pipefd);
//printf("RETURN FROM SELECT DUE TO pipefd SET\n");
continue;
}
}
//printf(">> Before Write fd [%d]\n", fd);
ret = write(fd, buf, size);
//printf(">> After Write ret[%d] size[%d]\n", (int)ret, size);
if (ret == size)
ret = 0; // no error
break;
}
return ret;
}
Writer_t *getWriter(char *encoding) Writer_t *getWriter(char *encoding)
{ {

View File

@@ -361,9 +361,10 @@ static int PlaybackPause(Context_t *context)
if (context->playback->SlowMotion) if (context->playback->SlowMotion)
context->output->Command(context, OUTPUT_CLEAR, NULL); context->output->Command(context, OUTPUT_CLEAR, NULL);
context->playback->isPaused = 1;
context->output->Command(context, OUTPUT_PAUSE, NULL); context->output->Command(context, OUTPUT_PAUSE, NULL);
context->playback->isPaused = 1;
//context->playback->isPlaying = 1; //context->playback->isPlaying = 1;
context->playback->isForwarding = 0; context->playback->isForwarding = 0;
context->playback->BackWard = 0; context->playback->BackWard = 0;