bool WriterAC3::Write(AVPacket *packet, int64_t pts) { if (!packet || !packet->data) return false; uint8_t PesHeader[PES_MAX_HEADER_SIZE]; for (int pos = 0; pos < packet->size; ) { int PacketLength = std::min(packet->size - pos, MAX_PES_PACKET_SIZE); struct iovec iov[2]; iov[0].iov_base = PesHeader; iov[0].iov_len = InsertPesHeader(PesHeader, PacketLength, PRIVATE_STREAM_1_PES_START_CODE, pts, 0); iov[1].iov_base = packet->data + pos; iov[1].iov_len = PacketLength; ssize_t l = writev(fd, iov, 2); if (l < 0) { return false; } pos += PacketLength; pts = INVALID_PTS_VALUE; } return true; }
static int writeData(void* _call) { WriterAVCallData_t* call = (WriterAVCallData_t*) _call; unsigned char PesHeader[PES_MAX_HEADER_SIZE]; int len = 0; unsigned int Position = 0; mpeg2_printf(10, "\n"); if (call == NULL) { mpeg2_err("call data is NULL...\n"); return 0; } mpeg2_printf(10, "VideoPts %lld\n", call->Pts); if ((call->data == NULL) || (call->len <= 0)) { mpeg2_err("parsing NULL Data. ignoring...\n"); return 0; } if (call->fd < 0) { mpeg2_err("file pointer < 0. ignoring ...\n"); return 0; } while(Position < call->len) { int PacketLength = (call->len - Position) <= MAX_PES_PACKET_SIZE ? (call->len - Position) : MAX_PES_PACKET_SIZE; int Remaining = call->len - Position - PacketLength; mpeg2_printf(20, "PacketLength=%d, Remaining=%d, Position=%d\n", PacketLength, Remaining, Position); struct iovec iov[2]; iov[0].iov_base = PesHeader; iov[0].iov_len = InsertPesHeader (PesHeader, PacketLength, 0xe0, call->Pts, 0); iov[1].iov_base = call->data + Position; iov[1].iov_len = PacketLength; ssize_t l = writev_with_retry(call->fd, iov, 2); if (l < 0) { len = l; break; } len += l; Position += PacketLength; call->Pts = INVALID_PTS_VALUE; } mpeg2_printf(10, "< len %d\n", len); return len; }
static int writeData(void* _call) { WriterAVCallData_t* call = (WriterAVCallData_t*) _call; int i = 0; unsigned char PesHeader[PES_AUDIO_HEADER_SIZE]; unsigned char * Data = 0; dts_printf(10, "\n"); if (call == NULL) { dts_err("call data is NULL...\n"); return 0; } dts_printf(10, "AudioPts %lld\n", call->Pts); if ((call->data == NULL) || (call->len <= 0)) { dts_err("parsing NULL Data. ignoring...\n"); return 0; } if (call->fd < 0) { dts_err("file pointer < 0. ignoring ...\n"); return 0; } memset (PesHeader, '0', PES_AUDIO_HEADER_SIZE); Data = (unsigned char *) malloc(call->len); memcpy(Data, call->data, call->len); /* 16-bit byte swap all data before injecting it */ for (i=0; i< call->len; i+=2) { unsigned char Tmp = Data[i]; Data[i] = Data[i+1]; Data[i+1] = Tmp; } int HeaderLength = InsertPesHeader (PesHeader, call->len, MPEG_AUDIO_PES_START_CODE/*PRIVATE_STREAM_1_PES_START_CODE*/, call->Pts, 0); unsigned char* PacketStart = malloc(call->len + HeaderLength); memcpy (PacketStart, PesHeader, HeaderLength); memcpy (PacketStart + HeaderLength, call->data, call->len); int len = write(call->fd,PacketStart,call->len + HeaderLength); free(PacketStart); free(Data); dts_printf(10, "< len %d\n", len); return len; }
static int writeData(void* _call) { WriterAVCallData_t* call = (WriterAVCallData_t*) _call; unsigned char PesHeader[PES_MAX_HEADER_SIZE]; mpeg4_printf(10, "\n"); if (call == NULL) { mpeg4_err("call data is NULL...\n"); return 0; } if ((call->data == NULL) || (call->len <= 0)) { mpeg4_err("parsing NULL Data. ignoring...\n"); return 0; } if (call->fd < 0) { mpeg4_err("file pointer < 0. ignoring ...\n"); return 0; } mpeg4_printf(10, "VideoPts %lld\n", call->Pts); unsigned int PacketLength = call->len; if (initialHeader && call->private_size && call->private_data != NULL) { PacketLength += call->private_size; } struct iovec iov[3]; int ic = 0; iov[ic].iov_base = PesHeader; iov[ic++].iov_len = InsertPesHeader (PesHeader, PacketLength, MPEG_VIDEO_PES_START_CODE, call->Pts, 0); if (initialHeader && call->private_size && call->private_data != NULL) { initialHeader = 0; iov[ic].iov_base = call->private_data; iov[ic++].iov_len = call->private_size; } iov[ic].iov_base = call->data; iov[ic++].iov_len = call->len; int len = call->WriteV(call->fd, iov, ic); mpeg4_printf(10, "xvid_Write < len=%d\n", len); return len; }
static int writeData(void* _call, int is_vp6) { WriterAVCallData_t* call = (WriterAVCallData_t*) _call; vp_printf(10, "\n"); if (call == NULL) { vp_err("call data is NULL...\n"); return 0; } if ((call->data == NULL) || (call->len <= 0)) { vp_err("parsing NULL Data. ignoring...\n"); return 0; } if (call->fd < 0) { vp_err("file pointer < 0. ignoring ...\n"); return 0; } vp_printf(10, "VideoPts %lld\n", call->Pts); vp_printf(10, "Got Private Size %d\n", call->private_size); unsigned char PesHeader[PES_MAX_HEADER_SIZE]; struct iovec iov[2]; iov[0].iov_base = PesHeader; uint32_t pes_header_len = InsertPesHeader(PesHeader, call->len, MPEG_VIDEO_PES_START_CODE, call->Pts, 0); uint32_t len = call->len + 4 + 6; memcpy(PesHeader + pes_header_len, "BCMV", 4); pes_header_len += 4; if (is_vp6) ++len; PesHeader[pes_header_len++] = (len & 0xFF000000) >> 24; PesHeader[pes_header_len++] = (len & 0x00FF0000) >> 16; PesHeader[pes_header_len++] = (len & 0x0000FF00) >> 8; PesHeader[pes_header_len++] = (len & 0x000000FF) >> 0; PesHeader[pes_header_len++] = 0; PesHeader[pes_header_len++] = 0; if (is_vp6) PesHeader[pes_header_len++] = 0; iov[0].iov_len = pes_header_len; iov[1].iov_base = call->data; iov[1].iov_len = call->len; return writev_with_retry(call->fd, iov, 2); }
static int writeData(void* _call) { WriterAVCallData_t* call = (WriterAVCallData_t*) _call; unsigned char PesHeader[PES_MAX_HEADER_SIZE + 22]; mp3_printf(10, "\n"); if (call == NULL) { mp3_err("call data is NULL...\n"); return 0; } mp3_printf(10, "AudioPts %lld\n", call->Pts); if ((call->data == NULL) || (call->len <= 0)) { mp3_err("parsing NULL Data. ignoring...\n"); return 0; } if (call->fd < 0) { mp3_err("file pointer < 0. ignoring ...\n"); return 0; } call->private_size = 0; uint32_t headerSize = InsertPesHeader (PesHeader, call->len + call->private_size, MPEG_AUDIO_PES_START_CODE, call->Pts, 0); if(call->private_size > 0) { memcpy(&PesHeader[headerSize], call->private_data, call->private_size); headerSize += call->private_size; } struct iovec iov[2]; iov[0].iov_base = PesHeader; iov[0].iov_len = headerSize; iov[1].iov_base = call->data; iov[1].iov_len = call->len; int len = call->WriteV(call->fd, iov, 2); mp3_printf(10, "mp3_Write-< len=%d\n", len); return len; }
static int writeData(void* _call) { WriterAVCallData_t* call = (WriterAVCallData_t*) _call; ac3_printf(10, "\n"); unsigned char PesHeader[PES_MAX_HEADER_SIZE]; if (call == NULL) { ac3_err("call data is NULL...\n"); return 0; } ac3_printf(10, "AudioPts %lld\n", call->Pts); if ((call->data == NULL) || (call->len <= 0)) { ac3_err("parsing NULL Data. ignoring...\n"); return 0; } if (call->fd < 0) { ac3_err("file pointer < 0. ignoring ...\n"); return 0; } struct iovec iov[3]; iov[0].iov_base = PesHeader; iov[0].iov_len = InsertPesHeader (PesHeader, call->len, MPEG_AUDIO_PES_START_CODE, call->Pts, 0); //+ sizeof(AC3_SYNC_HEADER) //PesHeader[6] = 0x81; //PesHeader[7] = 0x80; //PesHeader[8] = 0x09; //iov[1].iov_base = AC3_SYNC_HEADER; //iov[1].iov_len = sizeof(AC3_SYNC_HEADER); iov[1].iov_base = call->data; iov[1].iov_len = call->len; ac3_printf(40, "PES HEADER LEN %d\n", iov[0].iov_len); return writev_with_retry(call->fd, iov, 2); }
static int writeData(void* _call) { WriterAVCallData_t* call = (WriterAVCallData_t*) _call; unsigned char PesHeader[PES_MAX_HEADER_SIZE]; flac_printf(10, "\n"); if (call == NULL) { flac_err("call data is NULL...\n"); return 0; } flac_printf(10, "AudioPts %lld\n", call->Pts); if ((call->data == NULL) || (call->len <= 0)) { flac_err("parsing NULL Data. ignoring...\n"); return 0; } if (call->fd < 0) { flac_err("file pointer < 0. ignoring ...\n"); return 0; } int HeaderLength = InsertPesHeader (PesHeader, call->len , MPEG_AUDIO_PES_START_CODE, call->Pts, 0); unsigned char* PacketStart = malloc(call->len + HeaderLength); memcpy (PacketStart, PesHeader, HeaderLength); memcpy (PacketStart + HeaderLength, call->data, call->len); int len = write(call->fd, PacketStart, call->len + HeaderLength); free(PacketStart); flac_printf(10, "flac_Write-< len=%d\n", len); return len; }
static int writeData(void *_call) { WriterAVCallData_t *call = (WriterAVCallData_t *) _call; unsigned char PesHeader[PES_MAX_HEADER_SIZE]; flac_printf(10, "\n"); if (call == NULL) { flac_err("call data is NULL...\n"); return 0; } flac_printf(10, "AudioPts %lld\n", call->Pts); if ((call->data == NULL) || (call->len <= 0)) { flac_err("parsing NULL Data. ignoring...\n"); return 0; } if (call->fd < 0) { flac_err("file pointer < 0. ignoring ...\n"); return 0; } struct iovec iov[2]; iov[0].iov_base = PesHeader; iov[0].iov_len = InsertPesHeader(PesHeader, call->len , MPEG_AUDIO_PES_START_CODE, call->Pts, 0); iov[1].iov_base = call->data; iov[1].iov_len = call->len; int len = writev(call->fd, iov, 2); flac_printf(10, "flac_Write-< len=%d\n", len); return len; }
static int writeData(void* _call) { WriterAVCallData_t* call = (WriterAVCallData_t*) _call; int len = 0; vc1_printf(10, "\n"); if (call == NULL) { vc1_err("call data is NULL...\n"); return 0; } if ((call->data == NULL) || (call->len <= 0)) { vc1_err("parsing NULL Data. ignoring...\n"); return 0; } if (call->fd < 0) { vc1_err("file pointer < 0. ignoring ...\n"); return 0; } vc1_printf(10, "VideoPts %lld\n", call->Pts); vc1_printf(10, "Got Private Size %d\n", call->private_size); if (initialHeader) { unsigned char PesHeader[PES_MAX_HEADER_SIZE]; unsigned char PesPayload[128]; unsigned char *PesPtr; unsigned int crazyFramerate = 0; struct iovec iov[2]; vc1_printf(10, "Framerate: %u\n", call->FrameRate); vc1_printf(10, "biWidth: %d\n", call->Width); vc1_printf(10, "biHeight: %d\n", call->Height); crazyFramerate = ((10000000.0 / call->FrameRate) * 1000.0); vc1_printf(10, "crazyFramerate: %u\n", crazyFramerate); memset(PesPayload, 0, sizeof(PesPayload)); PesPtr = PesPayload; memcpy(PesPtr, SequenceLayerStartCode, sizeof(SequenceLayerStartCode)); PesPtr += sizeof(SequenceLayerStartCode); memcpy(PesPtr, Metadata, sizeof(Metadata)); PesPtr += METADATA_STRUCT_C_START; PesPtr += WMV3_PRIVATE_DATA_LENGTH; /* Metadata Header Struct A */ *PesPtr++ = (call->Height >> 0) & 0xff; *PesPtr++ = (call->Height >> 8) & 0xff; *PesPtr++ = (call->Height >> 16) & 0xff; *PesPtr++ = call->Height >> 24; *PesPtr++ = (call->Width >> 0) & 0xff; *PesPtr++ = (call->Width >> 8) & 0xff; *PesPtr++ = (call->Width >> 16) & 0xff; *PesPtr++ = call->Width >> 24; PesPtr += 12; /* Skip flag word and Struct B first 8 bytes */ *PesPtr++ = (crazyFramerate >> 0) & 0xff; *PesPtr++ = (crazyFramerate >> 8) & 0xff; *PesPtr++ = (crazyFramerate >> 16) & 0xff; *PesPtr++ = crazyFramerate >> 24; iov[0].iov_base = PesHeader; iov[1].iov_base = 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); 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 */ iov[0].iov_base = PesHeader; iov[1].iov_base = call->private_data; 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); len = call->WriteV(call->fd, iov, 2); initialHeader = 0; } if(call->len > 0 && call->data) { uint32_t Position = 0; uint8_t insertSampleHeader = 1; while(Position < call->len) { int32_t PacketLength = (call->len - Position) <= MAX_PES_PACKET_SIZE ? (call->len - Position) : MAX_PES_PACKET_SIZE; int32_t Remaining = call->len - Position - PacketLength; vc1_printf(20, "PacketLength=%d, Remaining=%d, Position=%d\n", PacketLength, Remaining, Position); uint8_t PesHeader[PES_MAX_HEADER_SIZE]; int32_t HeaderLength = InsertPesHeader (PesHeader, PacketLength, VC1_VIDEO_PES_START_CODE, call->Pts, 0); if(insertSampleHeader) { const uint8_t Vc1FrameStartCode[] = {0, 0, 1, VC1_FRAME_START_CODE}; if (!FrameHeaderSeen && (call->len > 3) && (memcmp (call->data, Vc1FrameStartCode, 4) == 0)) { FrameHeaderSeen = 1; } if (!FrameHeaderSeen) { memcpy (&PesHeader[HeaderLength], Vc1FrameStartCode, sizeof(Vc1FrameStartCode)); HeaderLength += sizeof(Vc1FrameStartCode); } insertSampleHeader = 0; } struct iovec iov[2]; iov[0].iov_base = PesHeader; iov[0].iov_len = HeaderLength; iov[1].iov_base = call->data + Position; iov[1].iov_len = PacketLength; ssize_t l = call->WriteV(call->fd, iov, 2); if (l < 0) { len = l; break; } len += l; Position += PacketLength; call->Pts = INVALID_PTS_VALUE; } } vc1_printf(10, "< %d\n", len); return len; }
static int writeData(void* _call) { WriterAVCallData_t* call = (WriterAVCallData_t*) _call; unsigned char PesHeader[PES_MAX_HEADER_SIZE]; unsigned long long int VideoPts; unsigned int TimeDelta; unsigned int TimeScale; int len = 0; int ic = 0; struct iovec iov[IOVEC_SIZE]; h265_printf(20, "\n"); if (call == NULL) { h264_err("call data is NULL...\n"); return 0; } TimeDelta = call->FrameRate; TimeScale = call->FrameScale; VideoPts = call->Pts; h265_printf(20, "VideoPts %lld - %d %d\n", call->Pts, TimeDelta, TimeScale); if ((call->data == NULL) || (call->len <= 0)) { h264_err("NULL Data. ignoring...\n"); return 0; } if (call->fd < 0) { h264_err("file pointer < 0. ignoring ...\n"); return 0; } if( call->InfoFlags & 0x1 ) // TS container { h265_printf(10, "H265 simple inject method!\n"); uint32_t PacketLength = 0; uint32_t FakeStartCode = (call->Version << 8) | PES_VERSION_FAKE_START_CODE; iov[ic++].iov_base = PesHeader; initialHeader = 0; if (initialHeader) { initialHeader = 0; iov[ic].iov_base = call->private_data; iov[ic++].iov_len = call->private_size; PacketLength += call->private_size; } iov[ic].iov_base = ""; iov[ic++].iov_len = 1; iov[ic].iov_base = call->data; iov[ic++].iov_len = call->len; PacketLength += call->len; iov[0].iov_len = InsertPesHeader(PesHeader, -1, MPEG_VIDEO_PES_START_CODE, VideoPts, FakeStartCode); return call->WriteV(call->fd, iov, ic); } uint32_t PacketLength = 0; ic = 0; iov[ic++].iov_base = PesHeader; if (initialHeader) { if (CodecData) { free(CodecData); CodecData = NULL; } uint8_t *private_data = call->private_data; uint32_t private_size = call->private_size; PreparCodecData(private_data, private_size, &NalLengthBytes); if (CodecData != NULL) { iov[ic].iov_base = CodecData; iov[ic++].iov_len = CodecDataLen; PacketLength += CodecDataLen; initialHeader = 0; } } if (CodecData != NULL) { uint32_t pos = 0; do { if (ic >= IOVEC_SIZE) { h264_err(">> Drop data due to ic overflow\n"); break; } uint32_t pack_len = 0; uint32_t i = 0; for (i = 0; i < NalLengthBytes; i++, pos++) { pack_len <<= 8; pack_len += call->data[pos]; } if ( (pos + pack_len) > call->len ) { pack_len = call->len - pos; } iov[ic].iov_base = Head; iov[ic++].iov_len = sizeof(Head); PacketLength += sizeof(Head); iov[ic].iov_base = call->data + pos; iov[ic++].iov_len = pack_len; PacketLength += pack_len; pos += pack_len; } while ((pos + NalLengthBytes) < call->len); h265_printf (10, "<<<< PacketLength [%d]\n", PacketLength); iov[0].iov_len = InsertPesHeader(PesHeader, -1, MPEG_VIDEO_PES_START_CODE, VideoPts, 0); len = call->WriteV(call->fd, iov, ic); PacketLength += iov[0].iov_len; if (PacketLength != len) { h264_err("<<<< not all data have been written [%d/%d]\n", len, PacketLength); } } h265_printf (10, "< len %d\n", len); return len; }
static int writeData(void* _call) { WriterAVCallData_t* call = (WriterAVCallData_t*) _call; int len = 0; wma_printf(10, "\n"); if (call == NULL) { wma_err("call data is NULL...\n"); return 0; } wma_printf(10, "AudioPts %lld\n", call->Pts); if ((call->data == NULL) || (call->len <= 0)) { wma_err("parsing NULL Data. ignoring...\n"); return 0; } if (call->fd < 0) { wma_err("file pointer < 0. ignoring ...\n"); return 0; } if (initialHeader) { unsigned char PesHeader[PES_MAX_HEADER_SIZE]; int HeaderLength; if ((call->private_size <= 0) || (call->private_data == NULL)) { wma_err("private NULL.\n"); return -1; } HeaderLength = InsertPesHeader (PesHeader, call->private_size, MPEG_AUDIO_PES_START_CODE, 0, 0); unsigned char* PacketStart = malloc(call->private_size + HeaderLength); memcpy (PacketStart, PesHeader, HeaderLength); memcpy (PacketStart + HeaderLength, call->private_data, call->private_size); len = write(call->fd, PacketStart, call->private_size + HeaderLength); free(PacketStart); initialHeader = 0; } if (call->len > 0 && call->data) { unsigned char PesHeader[PES_MAX_HEADER_SIZE]; int HeaderLength = InsertPesHeader (PesHeader, call->len, MPEG_AUDIO_PES_START_CODE, call->Pts, 0); unsigned char* PacketStart = malloc(call->len + HeaderLength); memcpy (PacketStart, PesHeader, HeaderLength); memcpy (PacketStart + HeaderLength, call->data, call->len); len = write(call->fd, PacketStart, call->len + HeaderLength); free(PacketStart); } wma_printf(10, "wma < %d\n", len); return len; }
static int writeData(void* _call) { WriterAVCallData_t* call = (WriterAVCallData_t*) _call; unsigned char PesHeader[PES_MAX_HEADER_SIZE]; pcm_printf(10, "\n"); if (!call) { pcm_err("call data is NULL...\n"); return 0; } pcm_printf(10, "AudioPts %lld\n", call->Pts); if (!call->data || (call->len <= 0)) { pcm_err("parsing NULL Data. ignoring...\n"); return 0; } if (call->fd < 0) { pcm_err("file pointer < 0. ignoring ...\n"); return 0; } pcmPrivateData_t* pcmPrivateData = (pcmPrivateData_t*)call->private_data; if (initialHeader) { initialHeader = 0; prepareClipPlay(pcmPrivateData->uNoOfChannels, pcmPrivateData->uSampleRate, pcmPrivateData->uBitsPerSample, pcmPrivateData->bLittleEndian); } unsigned char * buffer = call->data; unsigned int size = call->len; unsigned int n; unsigned char * injectBuffer = (unsigned char *)malloc(SubFrameLen); unsigned int pos; for(pos = 0; pos < size; ) { //printf("PCM %s - Position=%d\n", __FUNCTION__, pos); if((size - pos) < SubFrameLen) { breakBufferFillSize = size - pos; memcpy(breakBuffer, &buffer[pos], sizeof(unsigned char) * breakBufferFillSize); //printf("PCM %s - Unplayed=%d\n", __FUNCTION__, breakBufferFillSize); break; } //get first PES's worth if(breakBufferFillSize > 0) { memcpy(injectBuffer, breakBuffer, sizeof(unsigned char)*breakBufferFillSize); memcpy(&injectBuffer[breakBufferFillSize], &buffer[pos], sizeof(unsigned char)*(SubFrameLen - breakBufferFillSize)); pos += (SubFrameLen - breakBufferFillSize); breakBufferFillSize = 0; } else { memcpy(injectBuffer, &buffer[pos], sizeof(unsigned char)*SubFrameLen); pos += SubFrameLen; } struct iovec iov[3]; iov[0].iov_base = PesHeader; iov[1].iov_base = lpcm_prv; iov[1].iov_len = sizeof(lpcm_prv); iov[2].iov_base = injectBuffer; iov[2].iov_len = SubFrameLen; //write the PCM data if(pcmPrivateData->uBitsPerSample == 16) { for(n=0; n<SubFrameLen; n+=2) { unsigned char tmp; tmp=injectBuffer[n]; injectBuffer[n]=injectBuffer[n+1]; injectBuffer[n+1]=tmp; } } else { // 0 1 2 3 4 5 6 7 8 9 10 11 // A1c A1b A1a-B1c B1b B1a-A2c A2b A2a-B2c B2b B2a // to A1a A1b B1a B1b.A2a A2b B2a B2b-A1c B1c A2c B2c for(n=0; n<SubFrameLen; n+=12) { unsigned char t, *p = &injectBuffer[n]; t = p[0]; p[ 0] = p[ 2]; p[ 2] = p[ 5]; p[ 5] = p[ 7]; p[ 7] = p[11]; p[11] = p[ 9]; p[ 9] = p[ 3]; p[ 3] = p[ 4]; p[ 4] = p[ 8]; p[ 8] = t; } } //increment err... subframe count? 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); int len = writev(call->fd, iov, 3); if (len < 0) break; } free(injectBuffer); return size; }
static int writeData(void* _call) { WriterAVCallData_t* call = (WriterAVCallData_t*) _call; int len = 0; vc1_printf(10, "\n"); if (call == NULL) { vc1_err("call data is NULL...\n"); return 0; } if ((call->data == NULL) || (call->len <= 0)) { vc1_err("parsing NULL Data. ignoring...\n"); return 0; } if (call->fd < 0) { vc1_err("file pointer < 0. ignoring ...\n"); return 0; } vc1_printf(10, "VideoPts %lld\n", call->Pts); vc1_printf(10, "Got Private Size %d\n", call->private_size); unsigned char PesHeader[PES_MAX_HEADER_SIZE + sizeof(Vc1FrameStartCode)]; int32_t ic = 0; struct iovec iov[5]; unsigned int PacketLength = 0; iov[ic++].iov_base = PesHeader; if (initialHeader) { initialHeader = 0; if(videocodecdata.data) { free(videocodecdata.data); videocodecdata.data = NULL; } videocodecdata.length = call->private_size + 8; videocodecdata.data = malloc(videocodecdata.length); memset(videocodecdata.data, 0, videocodecdata.length); memcpy(videocodecdata.data + 8, call->private_data, call->private_size); if(IsDreambox() || 0 != ioctl(call->fd, VIDEO_SET_CODEC_DATA, &videocodecdata)) { iov[ic].iov_base = videocodecdata.data; iov[ic++].iov_len = videocodecdata.length; PacketLength += videocodecdata.length; } } uint8_t needFrameStartCode = 0; if( sizeof(Vc1FrameStartCode) >= call->len || memcmp(call->data, Vc1FrameStartCode, sizeof(Vc1FrameStartCode)) != 0 ) { needFrameStartCode = 1; PacketLength += sizeof(Vc1FrameStartCode); } iov[ic].iov_base = call->data; iov[ic++].iov_len = call->len; PacketLength += call->len; iov[0].iov_len = InsertPesHeader(PesHeader, PacketLength, MPEG_VIDEO_PES_START_CODE, call->Pts, 0); /* some mipsel receiver(s) like et4x00 needs to have Copy(0)/Original(1) flag set to Original */ PesHeader[6] |= 1; if(needFrameStartCode) { memcpy(PesHeader + iov[0].iov_len, Vc1FrameStartCode, sizeof(Vc1FrameStartCode) ); iov[0].iov_len += sizeof(Vc1FrameStartCode); } if(videocodecdata.data) { free(videocodecdata.data); videocodecdata.data = NULL; } return call->WriteV(call->fd, iov, ic); }
static int32_t writeData(void *_call) { WriterAVCallData_t* call = (WriterAVCallData_t*) _call; unsigned char PesHeader[PES_MAX_HEADER_SIZE]; pcm_printf(10, "\n"); if (!call) { pcm_err("call data is NULL...\n"); return 0; } pcm_printf(10, "AudioPts %lld\n", call->Pts); if (!call->data || (call->len <= 0)) { pcm_err("parsing NULL Data. ignoring...\n"); return 0; } if (call->fd < 0) { pcm_err("file pointer < 0. ignoring ...\n"); return 0; } pcmPrivateData_t *pcmPrivateData = (pcmPrivateData_t*)call->private_data; if (initialHeader) { uint32_t codecID = (uint32_t)pcmPrivateData->ffmpeg_codec_id; uint8_t LE = 0; switch (codecID) { case AV_CODEC_ID_PCM_S8: case AV_CODEC_ID_PCM_U8: break; case AV_CODEC_ID_PCM_S16LE: case AV_CODEC_ID_PCM_U16LE: LE = 1; case AV_CODEC_ID_PCM_S16BE: case AV_CODEC_ID_PCM_U16BE: break; case AV_CODEC_ID_PCM_S24LE: case AV_CODEC_ID_PCM_U24LE: LE = 1; case AV_CODEC_ID_PCM_S24BE: case AV_CODEC_ID_PCM_U24BE: break; case AV_CODEC_ID_PCM_S32LE: case AV_CODEC_ID_PCM_U32LE: LE = 1; case AV_CODEC_ID_PCM_S32BE: case AV_CODEC_ID_PCM_U32BE: break; default: break; } initialHeader = 0; prepareClipPlay(pcmPrivateData->channels, pcmPrivateData->sample_rate, pcmPrivateData->bits_per_coded_sample, LE); } uint8_t *buffer = call->data; uint32_t size = call->len; uint32_t n; uint8_t *injectBuffer = malloc(SubFrameLen); uint32_t pos; for(pos = 0; pos < size; ) { //printf("PCM %s - Position=%d\n", __FUNCTION__, pos); if((size - pos) < SubFrameLen) { breakBufferFillSize = size - pos; memcpy(breakBuffer, &buffer[pos], sizeof(uint8_t) * breakBufferFillSize); //printf("PCM %s - Unplayed=%d\n", __FUNCTION__, breakBufferFillSize); break; } //get first PES's worth if(breakBufferFillSize > 0) { memcpy(injectBuffer, breakBuffer, sizeof(uint8_t)*breakBufferFillSize); memcpy(&injectBuffer[breakBufferFillSize], &buffer[pos], sizeof(unsigned char)*(SubFrameLen - breakBufferFillSize)); pos += (SubFrameLen - breakBufferFillSize); breakBufferFillSize = 0; } else { memcpy(injectBuffer, &buffer[pos], sizeof(uint8_t)*SubFrameLen); pos += SubFrameLen; } struct iovec iov[3]; iov[0].iov_base = PesHeader; iov[1].iov_base = lpcm_prv; iov[1].iov_len = sizeof(lpcm_prv); iov[2].iov_base = injectBuffer; iov[2].iov_len = SubFrameLen; //write the PCM data if(16 == pcmPrivateData->bits_per_coded_sample) { for(n=0; n<SubFrameLen; n+=2) { uint8_t tmp; tmp=injectBuffer[n]; injectBuffer[n]=injectBuffer[n+1]; injectBuffer[n+1]=tmp; } } else { // 0 1 2 3 4 5 6 7 8 9 10 11 // A1c A1b A1a-B1c B1b B1a-A2c A2b A2a-B2c B2b B2a // to A1a A1b B1a B1b.A2a A2b B2a B2b-A1c B1c A2c B2c for(n=0; n<SubFrameLen; n+=12) { unsigned char t, *p = &injectBuffer[n]; t = p[0]; p[ 0] = p[ 2]; p[ 2] = p[ 5]; p[ 5] = p[ 7]; p[ 7] = p[11]; p[11] = p[ 9]; p[ 9] = p[ 3]; p[ 3] = p[ 4]; p[ 4] = p[ 8]; p[ 8] = t; } } //increment err... subframe count? 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); int32_t len = call->WriteV(call->fd, iov, 3); if (len < 0) { break; } } free(injectBuffer); return size; }
static int writeData(void* _call) { WriterAVCallData_t* call = (WriterAVCallData_t*) _call; unsigned char PesHeader[PES_MAX_HEADER_SIZE]; unsigned char FakeHeaders[64]; // 64bytes should be enough to make the fake headers unsigned int FakeHeaderLength; unsigned int ExtraLength = 0; unsigned char Version = 5; unsigned int FakeStartCode = (Version << 8) | PES_VERSION_FAKE_START_CODE; unsigned int HeaderLength = 0; unsigned int usecPerFrame = 41708; /* Hellmaster1024: default value */ BitPacker_t ld = {FakeHeaders, 0, 32}; divx_printf(10, "\n"); if (call == NULL) { divx_err("call data is NULL...\n"); return 0; } divx_printf(10, "AudioPts %lld\n", call->Pts); if ((call->data == NULL) || (call->len <= 0)) { divx_err("parsing NULL Data. ignoring...\n"); return 0; } if (call->fd < 0) { divx_err("file pointer < 0. ignoring ...\n"); return 0; } usecPerFrame = 1000000000 / call->FrameRate; divx_printf(10, "Microsecends per frame = %d\n", usecPerFrame); memset(FakeHeaders, 0, sizeof(FakeHeaders)); /* Create info record for frame parser */ /* divx4 & 5 VOS PutBits(&ld, 0x0, 8); PutBits(&ld, 0x0, 8); */ PutBits(&ld, 0x1b0, 32); // startcode PutBits(&ld, 0, 8); // profile = reserved PutBits(&ld, 0x1b2, 32); // startcode (user data) PutBits(&ld, 0x53545443, 32); // STTC - an embedded ST timecode from an avi file PutBits(&ld, usecPerFrame , 32); // microseconds per frame FlushBits(&ld); FakeHeaderLength = (ld.Ptr - (FakeHeaders)); if (initialHeader) ExtraLength = call->private_size; HeaderLength = InsertPesHeader (PesHeader, call->len, MPEG_VIDEO_PES_START_CODE, call->Pts, FakeStartCode); int iovcnt = 0; struct iovec iov[4]; iov[iovcnt].iov_base = PesHeader; iov[iovcnt].iov_len = HeaderLength; iovcnt++; iov[iovcnt].iov_base = FakeHeaders; iov[iovcnt].iov_len = FakeHeaderLength; iovcnt++; if (initialHeader) { initialHeader = 0; iov[iovcnt].iov_base = call->private_data; iov[iovcnt].iov_len = call->private_size; iovcnt++; } iov[iovcnt].iov_base = call->data; iov[iovcnt].iov_len = call->len; iovcnt++; int len = writev(call->fd, iov, iovcnt); divx_printf(10, "xvid_Write < len=%d\n", len); return len; }
bool WriterVC1::Write(AVPacket *packet, int64_t pts) { if (!packet || !packet->data) return false; if (initialHeader) { initialHeader = false; FrameHeaderSeen = false; const uint8_t SequenceLayerStartCode[] = { 0x00, 0x00, 0x01, VC1_SEQUENCE_LAYER_METADATA_START_CODE }; const uint8_t Metadata[] = { 0x00, 0x00, 0x00, 0xc5, 0x04, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, /* Struct C set for for advanced profile */ 0x00, 0x00, 0x00, 0x00, /* Struct A */ 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, /* Struct B */ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }; uint8_t PesHeader[PES_MAX_HEADER_SIZE]; uint8_t PesPayload[128]; uint8_t *PesPtr; unsigned int usecPerFrame = av_rescale(AV_TIME_BASE, stream->r_frame_rate.den, stream->r_frame_rate.num); struct iovec iov[2]; memset(PesPayload, 0, sizeof(PesPayload)); PesPtr = PesPayload; memcpy(PesPtr, SequenceLayerStartCode, sizeof(SequenceLayerStartCode)); PesPtr += sizeof(SequenceLayerStartCode); memcpy(PesPtr, Metadata, sizeof(Metadata)); PesPtr += METADATA_STRUCT_C_START; PesPtr += WMV3_PRIVATE_DATA_LENGTH; /* Metadata Header Struct A */ *PesPtr++ = (stream->codec->height >> 0) & 0xff; *PesPtr++ = (stream->codec->height >> 8) & 0xff; *PesPtr++ = (stream->codec->height >> 16) & 0xff; *PesPtr++ = stream->codec->height >> 24; *PesPtr++ = (stream->codec->width >> 0) & 0xff; *PesPtr++ = (stream->codec->width >> 8) & 0xff; *PesPtr++ = (stream->codec->width >> 16) & 0xff; *PesPtr++ = stream->codec->width >> 24; PesPtr += 12; /* Skip flag word and Struct B first 8 bytes */ *PesPtr++ = (usecPerFrame >> 0) & 0xff; *PesPtr++ = (usecPerFrame >> 8) & 0xff; *PesPtr++ = (usecPerFrame >> 16) & 0xff; *PesPtr++ = usecPerFrame >> 24; iov[0].iov_base = PesHeader; iov[1].iov_base = 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); if (writev(fd, iov, 2) < 0) return false; /* 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[1].iov_base = stream->codec->extradata; iov[1].iov_len = stream->codec->extradata_size; iov[0].iov_len = InsertPesHeader(PesHeader, iov[1].iov_len, VC1_VIDEO_PES_START_CODE, INVALID_PTS_VALUE, 0); if (writev(fd, iov, 2) < 0) return false; initialHeader = false; } if (packet->size > 0) { int Position = 0; bool insertSampleHeader = true; while (Position < packet->size) { int PacketLength = std::min(packet->size - Position, MAX_PES_PACKET_SIZE); uint8_t PesHeader[PES_MAX_HEADER_SIZE]; int HeaderLength = InsertPesHeader(PesHeader, PacketLength, VC1_VIDEO_PES_START_CODE, pts, 0); if (insertSampleHeader) { const uint8_t Vc1FrameStartCode[] = { 0, 0, 1, VC1_FRAME_START_CODE }; if (!FrameHeaderSeen && (packet->size > 3) && (memcmp(packet->data, Vc1FrameStartCode, 4) == 0)) FrameHeaderSeen = true; if (!FrameHeaderSeen) { memcpy(&PesHeader[HeaderLength], Vc1FrameStartCode, sizeof(Vc1FrameStartCode)); HeaderLength += sizeof(Vc1FrameStartCode); } insertSampleHeader = false; } struct iovec iov[2]; iov[0].iov_base = PesHeader; iov[0].iov_len = HeaderLength; iov[1].iov_base = packet->data + Position; iov[1].iov_len = PacketLength; ssize_t l = writev(fd, iov, 2); if (l < 0) return false; Position += PacketLength; pts = INVALID_PTS_VALUE; } } return true; }
static int writeData(void *_call) { WriterAVCallData_t *call = (WriterAVCallData_t *) _call; int len = 0; wma_printf(10, "\n"); if (call == NULL) { wma_err("call data is NULL...\n"); return 0; } wma_printf(10, "AudioPts %lld\n", call->Pts); if ((call->data == NULL) || (call->len <= 0)) { wma_err("parsing NULL Data. ignoring...\n"); return 0; } if (call->fd < 0) { wma_err("file pointer < 0. ignoring ...\n"); return 0; } if (initialHeader) { unsigned char PesHeader[PES_MAX_HEADER_SIZE]; if ((call->private_size <= 0) || (call->private_data == NULL)) { wma_err("private NULL.\n"); return -1; } struct iovec iov[2]; iov[0].iov_base = PesHeader; 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_len = call->private_size; len = writev(call->fd, iov, 2); initialHeader = 0; } if (len > -1 && call->len > 0 && call->data) { unsigned char PesHeader[PES_MAX_HEADER_SIZE]; struct iovec iov[2]; iov[0].iov_base = PesHeader; iov[0].iov_len = InsertPesHeader(PesHeader, call->len, MPEG_AUDIO_PES_START_CODE, call->Pts, 0); iov[1].iov_base = call->data; iov[1].iov_len = call->len; ssize_t l = writev(call->fd, iov, 2); if (l > -1) len += l; else len = l; } wma_printf(10, "wma < %d\n", len); return len; }
static int writeData(void* _call) { WriterAVCallData_t* call = (WriterAVCallData_t*) _call; static uint8_t PesHeader[PES_MAX_HEADER_SIZE]; int32_t len = 0; uint32_t Position = 0; mpeg2_printf(10, "\n"); if (call == NULL) { mpeg2_err("call data is NULL...\n"); return 0; } mpeg2_printf(10, "VideoPts %lld\n", call->Pts); if ((call->data == NULL) || (call->len <= 0)) { mpeg2_err("parsing NULL Data. ignoring...\n"); return 0; } if (call->fd < 0) { mpeg2_err("file pointer < 0. ignoring ...\n"); return 0; } uint8_t *data = call->data; uint32_t data_len = call->len; if (!private_data && !call->private_data && data_len > 3 && !memcmp(data, "\x00\x00\x01\xb3", 4)) { bool ok = true; uint32_t pos = 4; uint32_t sheader_data_len = 0; while (pos < data_len && ok) { if (pos >= data_len) break; pos += 7; if (pos >=data_len) break; sheader_data_len = 12; if (data[pos] & 2) { // intra matrix pos += 64; if (pos >=data_len) break; sheader_data_len += 64; } if (data[pos] & 1) { // non intra matrix pos += 64; if (pos >=data_len) break; sheader_data_len += 64; } pos += 1; if (pos + 3 >=data_len) break; if (!memcmp(&data[pos], "\x00\x00\x01\xb5", 4)) { // extended start code pos += 3; sheader_data_len += 3; do { pos += 1; ++sheader_data_len; if (pos + 2 > data_len) { ok = false; break; } } while (memcmp(&data[pos], "\x00\x00\x01", 3)); if (!ok) break; } if (pos + 3 >= data_len) break; if (!memcmp(&data[pos], "\x00\x00\x01\xb2", 4)) { // private data pos += 3; sheader_data_len += 3; do { pos += 1; ++sheader_data_len; if (pos + 2 > data_len) { ok = false; break; } } while (memcmp(&data[pos], "\x00\x00\x01", 3)); if (!ok) break; } free(private_data); private_data = malloc(sheader_data_len); if (private_data) { private_size = sheader_data_len; memcpy(private_data, data + pos - sheader_data_len, sheader_data_len); } must_send_header = false; break; } } else if ((private_data || call->private_data) && must_send_header) { uint8_t *codec_data = NULL; uint32_t codec_data_size = 0; int pos = 0; if (private_data) { codec_data = private_data; codec_data_size = private_size; } else { codec_data = call->private_data; codec_data_size = call->private_size; } while (pos <= data_len - 4) { if (memcmp(&data[pos], "\x00\x00\x01\xb8", 4)) /* find group start code */ { pos++; continue; } struct iovec iov[4]; iov[0].iov_base = PesHeader; iov[0].iov_len = InsertPesHeader(PesHeader, call->len + codec_data_size, MPEG_VIDEO_PES_START_CODE, call->Pts, 0); iov[1].iov_base = data; iov[1].iov_len = pos; iov[2].iov_base = codec_data; iov[2].iov_len = codec_data_size; iov[3].iov_base = data + pos; iov[3].iov_len = data_len - pos; must_send_header = false; return call->WriteV(call->fd, iov, 4); } } struct iovec iov[2]; iov[0].iov_base = PesHeader; iov[0].iov_len = InsertPesHeader(PesHeader, call->len, MPEG_VIDEO_PES_START_CODE, call->Pts, 0); iov[1].iov_base = data; iov[1].iov_len = data_len; PesHeader[6] = 0x81; UpdatePesHeaderPayloadSize(PesHeader, data_len + iov[0].iov_len - 6); if (iov[0].iov_len != WriteExt(call->WriteV, call->fd, iov[0].iov_base, iov[0].iov_len)) return -1; if (iov[1].iov_len != WriteExt(call->WriteV, call->fd, iov[1].iov_base, iov[1].iov_len)) return -1; return 1; }