diff options
author | scop <scop> | 2005-04-18 19:26:16 +0000 |
---|---|---|
committer | scop <scop> | 2005-04-18 19:26:16 +0000 |
commit | f8a3d81fc0b548a0f76e205fee433e4c94a4ee57 (patch) | |
tree | 2f69513d7d57e15b920c8eb4bb4b4a877d5b0881 /dxr3multichannelaudio.c | |
parent | 37c4c7b0a4a388d6c933e95756ddd30dd0cca6fd (diff) | |
download | vdr-plugin-dxr3-f8a3d81fc0b548a0f76e205fee433e4c94a4ee57.tar.gz vdr-plugin-dxr3-f8a3d81fc0b548a0f76e205fee433e4c94a4ee57.tar.bz2 |
Oops, wrong tree... revert.
Diffstat (limited to 'dxr3multichannelaudio.c')
-rw-r--r-- | dxr3multichannelaudio.c | 298 |
1 files changed, 149 insertions, 149 deletions
diff --git a/dxr3multichannelaudio.c b/dxr3multichannelaudio.c index 673fee5..1f1471d 100644 --- a/dxr3multichannelaudio.c +++ b/dxr3multichannelaudio.c @@ -1,10 +1,10 @@ /* - * dxr3multichannelaudio.c: - * - * taken from the AC3overDVB Patch maintained by Stefan Huelswitt - * - * - */ +* dxr3multichannelaudio.c: +* +* taken from the AC3overDVB Patch maintained by Stefan Huelswitt +* +* +*/ #include <malloc.h> #include "dxr3multichannelaudio.h" @@ -38,7 +38,7 @@ // --- cAudioEncapsulator ------------------------------------------------------ class cAudioEncapsulator { - private: +private: int totalSize, frameCount; cFrame *frame; uchar *frameData; @@ -52,7 +52,7 @@ class cAudioEncapsulator { // void NewFrame(uchar PTSflags, const uchar *PTSdata); void SyncFound(const uchar *data); - protected: +protected: int streamType; cRingBufferFrame *ringBuffer; int fillup, firstBurst; @@ -66,14 +66,14 @@ class cAudioEncapsulator { virtual int SyncInfo(const uchar *data)=0; virtual void StartIECFrame(const uchar *buf, int length, uchar PTSflags, const uchar *PTSdata)=0; virtual void FinishIECFrame(void); - public: +public: cAudioEncapsulator(cRingBufferFrame *rb, int StreamType); virtual ~cAudioEncapsulator(); void Clear(void); void Decode(const uchar *data, int len, uchar PTSflags, int PTSdelay, const uchar *PTSdata); int StreamType() { return streamType; } void Mute(bool Mute) { mute=Mute; } -}; + }; cAudioEncapsulator::cAudioEncapsulator(cRingBufferFrame *rb, int StreamType) { @@ -100,7 +100,7 @@ void cAudioEncapsulator::StartFrame(int size, uchar PTSflags, const uchar *PTSda if(frame) { DEBUG("StartFrame() with unfinished frame!\n"); FinishFrame(); - } + } ED("StartFrame: size=%d ptsFlags=%d\n",size,PTSflags); totalSize=size; NewFrame(PTSflags,PTSdata); @@ -111,7 +111,7 @@ void cAudioEncapsulator::NewFrame(uchar PTSflags, const uchar *PTSdata) if(!totalSize) { DEBUG("NewFrame: new frame requested, but totalSize=0\n"); return; - } + } static const int ptslen[] = { 0,0,PTS_SIZE,PTS_SIZE*2 }; const int plen = ptslen[PTSflags]; int len = std::min(totalSize, MAX_FRAMECOUNT); @@ -149,9 +149,9 @@ void cAudioEncapsulator::NewFrame(uchar PTSflags, const uchar *PTSdata) buf[6] = 0x81; PutData(buf,7); return; - } + } else { free(frameData); frameData=0; } - } + } esyslog("Failed to build frame for audio encapsulation"); } @@ -160,14 +160,14 @@ void cAudioEncapsulator::FinishFrame(void) if (frameCount) { DEBUG("FinishFrame() with frameCount>0\n"); PutData(0,frameCount); - } + } if (frame && frameData) { ED("FinishFrame: totalSize=%d\n",totalSize); if (!ringBuffer->Put(frame)) { esyslog("Ringbuffer overflow. Encapsulated audio frame lost"); delete frame; + } } - } frame=0; frameData=0; frameCount=0; } @@ -180,7 +180,7 @@ void cAudioEncapsulator::PutData(const uchar *data, int len) if(data) { memcpy(frameData,data,l); data += l; - } + } else memset(frameData,0,l); frameData += l; len -= l; frameCount -= l; @@ -188,9 +188,9 @@ void cAudioEncapsulator::PutData(const uchar *data, int len) if (!frameCount) { FinishFrame(); if (totalSize > 0) NewFrame(0,0); + } } } - } } void cAudioEncapsulator::SendIECpause(int type, uchar PTSflags, const uchar *PTSdata) @@ -204,26 +204,26 @@ void cAudioEncapsulator::SendIECpause(int type, uchar PTSflags, const uchar *PTS burst[3] = 0x1F; switch (type) { - default: - case 0: - burst[4] = 7 << 5; // null frame, stream = 7 - burst[5] = 0x00; - burst[6] = 0x00; // No data therein - burst[7] = 0x00; - break; - case 1: - burst[4] = 0x00; // Audio ES Channel empty, wait - burst[5] = 0x03; // for DD Decoder or pause - burst[6] = 0x00; // Trailing frame size is 32 bits payload - burst[7] = 0x20; - break; - case -1: - burst[4] = 0x01; // User stop, skip or error - burst[5] = 0x03; - burst[6] = 0x08; // Trailing frame size is zero - burst[7] = 0x00; - break; - } + default: + case 0: + burst[4] = 7 << 5; // null frame, stream = 7 + burst[5] = 0x00; + burst[6] = 0x00; // No data therein + burst[7] = 0x00; + break; + case 1: + burst[4] = 0x00; // Audio ES Channel empty, wait + burst[5] = 0x03; // for DD Decoder or pause + burst[6] = 0x00; // Trailing frame size is 32 bits payload + burst[7] = 0x20; + break; + case -1: + burst[4] = 0x01; // User stop, skip or error + burst[5] = 0x03; + burst[6] = 0x08; // Trailing frame size is zero + burst[7] = 0x00; + break; + } PutData(burst,sizeof(burst)); PutData(0,AC3_SIZE-sizeof(burst)); FinishFrame(); @@ -236,7 +236,7 @@ void cAudioEncapsulator::FinishIECFrame(void) ED("FinishIECFrame: fillup=%d\n",fillup); if (fillup) PutData(0,fillup); FinishFrame(); - } + } muteData=false; fillup=0; } @@ -248,16 +248,16 @@ void cAudioEncapsulator::SyncFound(const uchar *data) ED("\ndata: "); for(int k=0 ; k<24 ; k++) ED("%02x ",data[k]); ED("\n"); skipped=0; - } + } uchar pf=0; ED("Decode: sync found ptsFlags=%d ptsDelay=%d\n",ptsFlags,ptsDelay); if(ptsFlags && ptsDelay<=1) { pf=ptsFlags; ptsFlags=0; - } + } if(firstBurst || mute) { SendIECpause(1,pf,ptsData); if(firstBurst && ++firstBurst>10) firstBurst=0; - } + } else StartIECFrame(data,length,pf,ptsData); PutData(data,SYNC_SIZE); have = SYNC_SIZE; @@ -276,31 +276,31 @@ void cAudioEncapsulator::Decode(const uchar *data, int len, uchar PTSflags, int PutData(0,miss); FinishIECFrame(); length=have=0; - } - /* + } +/* // we only send PTS info if we're nearly at frame start, except // if we're signaled to delay the PTS if(length && have>40) { - if(PTSdelay) ED("Decode: PTS delayed\n"); - else { - DEBUG("Decode: PTS info dropped length=%d have=%d\n",length,have); - PTSflags=0; - } - } - */ + if(PTSdelay) ED("Decode: PTS delayed\n"); + else { + DEBUG("Decode: PTS info dropped length=%d have=%d\n",length,have); + PTSflags=0; + } + } +*/ ptsFlags=PTSflags; ptsData=PTSdata; ptsDelay=PTSdelay; - // ED("Decode: saved PTS flags=%d delay=%d\n",ptsFlags,ptsDelay); - } +// ED("Decode: saved PTS flags=%d delay=%d\n",ptsFlags,ptsDelay); + } #if 0 { - printf("Decode: len=%d\n",len); - for(int i=0 ; i<len ; ) { - printf("%04x:",i); - for(int j=0 ; j<16 && i<len ; j++) { - printf(" %02x",data[i++]); + printf("Decode: len=%d\n",len); + for(int i=0 ; i<len ; ) { + printf("%04x:",i); + for(int j=0 ; j<16 && i<len ; j++) { + printf(" %02x",data[i++]); } - printf("\n"); + printf("\n"); } } #endif @@ -316,36 +316,36 @@ void cAudioEncapsulator::Decode(const uchar *data, int len, uchar PTSflags, int SyncFound(&data[used]); used += SYNC_SIZE; ptsDelay -= SYNC_SIZE; continue; - } + } else { used++; skipped++; } - } + } else { // not enough data to try a sync, buffer the rest ED("Decode: buffering started\n"); have = len-used; memcpy(syncBuff,&data[used],have); used += have; ptsDelay -= have; - } - } + } + } else { // unfortunaly buffer is not empty, so continue with buffering until sync found int need=std::min(SYNC_SIZE-have,len-used); if (need) { memcpy(&syncBuff[have],&data[used],need); have += need; used += need; ptsDelay -= need; - } + } if (have==SYNC_SIZE) { length=SyncInfo(syncBuff); if (length) { ED("Decode: (buffered) sync found at offset %d (len=%d)\n",used-7,length); SyncFound(syncBuff); continue; - } + } else { memmove(syncBuff,syncBuff+1,SYNC_SIZE-1); have--; skipped++; - } - } + } + } + } } - } else { // we have a header sync and are copying data int need = std::min(length-have,len-used); if(need) { @@ -356,53 +356,53 @@ void cAudioEncapsulator::Decode(const uchar *data, int len, uchar PTSflags, int FinishIECFrame(); length = have = 0; continue; - } + } + } } } - } ED("Decode: leave length=%d have=%d len=%d used=%d\n",length,have,len,used); } // --- cAudioEncapsulatorAC3 --------------------------------------------------- class cAudioEncapsulatorAC3 : public cAudioEncapsulator { - private: +private: virtual int SyncInfo(const uchar *buf); virtual void StartIECFrame(const uchar *buf, int length, uchar PTSflags, const uchar *PTSdata); - public: +public: cAudioEncapsulatorAC3(cRingBufferFrame *rb, int StreamType); -}; + }; cAudioEncapsulatorAC3::cAudioEncapsulatorAC3(cRingBufferFrame *rb, int StreamType) - :cAudioEncapsulator(rb, StreamType) +:cAudioEncapsulator(rb, StreamType) {} int cAudioEncapsulatorAC3::SyncInfo(const uchar *buf) { static const int rate[] = { 32, 40, 48, 56, 64, 80, 96, 112, - 128, 160, 192, 224, 256, 320, 384, 448, - 512, 576, 640}; + 128, 160, 192, 224, 256, 320, 384, 448, + 512, 576, 640}; if ((buf[0] != 0x0B) || (buf[1] != 0x77)) /* syncword */ - return 0; + return 0; if (buf[5] >= 0x60) /* bsid >= 12 */ - return 0; + return 0; int frmsizecod = buf[4] & 63; if (frmsizecod >= 38) - return 0; + return 0; int bitrate = rate[frmsizecod >> 1]; switch (buf[4] & 0xC0) { case 0: - return 4 * bitrate; + return 4 * bitrate; case 0x40: - return 2 * (320 * bitrate / 147 + (frmsizecod & 1)); + return 2 * (320 * bitrate / 147 + (frmsizecod & 1)); case 0x80: - return 6 * bitrate; + return 6 * bitrate; default: - return 0; - } + return 0; + } } void cAudioEncapsulatorAC3::StartIECFrame(const uchar *buf, int length, uchar PTSflags, const uchar *PTSdata) @@ -426,15 +426,15 @@ void cAudioEncapsulatorAC3::StartIECFrame(const uchar *buf, int length, uchar PT // --- cAudioEncapsulatorDTS --------------------------------------------------- class cAudioEncapsulatorDTS : public cAudioEncapsulator { - private: +private: virtual int SyncInfo(const uchar *buf); virtual void StartIECFrame(const uchar *buf, int length, uchar PTSflags, const uchar *PTSdata); - public: +public: cAudioEncapsulatorDTS(cRingBufferFrame *rb, int StreamType); -}; + }; cAudioEncapsulatorDTS::cAudioEncapsulatorDTS(cRingBufferFrame *rb, int StreamType) - : cAudioEncapsulator(rb, StreamType) +: cAudioEncapsulator(rb, StreamType) {} int cAudioEncapsulatorDTS::SyncInfo(const uchar *buf) @@ -445,8 +445,8 @@ int cAudioEncapsulatorDTS::SyncInfo(const uchar *buf) (buf[3] != 0x01)) return 0; int length = ((buf[5] & 0x03) << 12) | - ((buf[6] & 0xFF) << 4) | - ((buf[7] & 0xF0) >> 4); + ((buf[6] & 0xFF) << 4) | + ((buf[7] & 0xF0) >> 4); return length + 1; } @@ -457,24 +457,24 @@ void cAudioEncapsulatorDTS::StartIECFrame(const uchar *buf, int length, uchar PT uchar ac5_spdif_type; switch(ac5_type) { case 0x0F: - ac5_spdif_type = 0x0B; /* DTS */ - break; + ac5_spdif_type = 0x0B; /* DTS */ + break; case 0x1F: - ac5_spdif_type = 0x0C; /* DTS */ - break; + ac5_spdif_type = 0x0C; /* DTS */ + break; case 0x3F: - ac5_spdif_type = 0x0D; /* DTS */ - break; + ac5_spdif_type = 0x0D; /* DTS */ + break; default: - ac5_spdif_type = 0x00; /* DTS */ - esyslog("DTS: SPDIF type not detected: ac5 type = %X!\n", ac5_type); - break; - } + ac5_spdif_type = 0x00; /* DTS */ + esyslog("DTS: SPDIF type not detected: ac5 type = %X!\n", ac5_type); + break; + } if (length > DTS_SIZE-IEC_HDR_SIZE) { - DEBUG("DTS: length too long %d\n",length); - return; - } + DEBUG("DTS: length too long %d\n",length); + return; + } StartFrame(DTS_SIZE,PTSflags,PTSdata); fillup = DTS_SIZE-IEC_HDR_SIZE-length; @@ -522,12 +522,12 @@ void cMultichannelAudio::Reset() } /* - void cMultichannelAudio::Mute(bool Mute) - { +void cMultichannelAudio::Mute(bool Mute) +{ Lock(); if(encapsulator) encapsulator->Mute(Mute); Unlock(); - } +} */ int cMultichannelAudio::Check(uchar *b, int length, uchar *header) @@ -553,72 +553,72 @@ int cMultichannelAudio::Check(uchar *b, int length, uchar *header) if(ost>0) { ED("multichannel: crossing -> keep encapsulator\n"); subStreamType=ost; - } + } else { ED("multichannel: crossing -> skip\n"); res=1; goto out; // skip - } + } + } } - } else if(fixed && ost>0) { ED("multichannel: fixed unaligned -> keep encapsulator\n"); subStreamType=ost; + } } - } fixed=false; switch(subStreamType) { - case aDTS: - case aAC3: - offset=4; // skip the DVD stream infos - break; - default: - if(aligned || !ptsFlags) { + case aDTS: + case aAC3: + offset=4; // skip the DVD stream infos + break; + default: + if(aligned || !ptsFlags) { + if(encapsulator) { + Reset(); + DEBUG("multichannel: interrupted encapsulator stream (unknown)\n"); + } + DEBUG("multichannel: unknown substream type %x (skipped)\n",subStreamType); + res=1; goto out; // skip + } + subStreamType=aVDR; + ED("multichannel: assuming aVDR for unknown substream type\n"); + // fall through + case aVDR: + fixed=true; + break; + case aLPCM: if(encapsulator) { - Reset(); - DEBUG("multichannel: interrupted encapsulator stream (unknown)\n"); - } - DEBUG("multichannel: unknown substream type %x (skipped)\n",subStreamType); + Reset(); + DEBUG("multichannel: interrupted encapsulator stream (LPCM)\n"); + } + ED("multichannel: LPCM\n"); + res=2; goto out; // pass + case aSPU: + ED("multichannel: SPU stream (skipped)\n"); res=1; goto out; // skip } - subStreamType=aVDR; - ED("multichannel: assuming aVDR for unknown substream type\n"); - // fall through - case aVDR: - fixed=true; - break; - case aLPCM: - if(encapsulator) { - Reset(); - DEBUG("multichannel: interrupted encapsulator stream (LPCM)\n"); - } - ED("multichannel: LPCM\n"); - res=2; goto out; // pass - case aSPU: - ED("multichannel: SPU stream (skipped)\n"); - res=1; goto out; // skip - } // If the SubStreamType has changed then select the right encapsulator if(!encapsulator || encapsulator->StreamType()!=subStreamType) { DEBUG("multichannel: new encapsulator %x\n",subStreamType); Reset(); switch(subStreamType) { - case aAC3: - case aVDR: // AC3 - encapsulator=new cAudioEncapsulatorAC3(ringBuffer,subStreamType); - break; - case aDTS: // Dts - encapsulator=new cAudioEncapsulatorDTS(ringBuffer,subStreamType); - break; - } + case aAC3: + case aVDR: // AC3 + encapsulator=new cAudioEncapsulatorAC3(ringBuffer,subStreamType); + break; + case aDTS: // Dts + encapsulator=new cAudioEncapsulatorDTS(ringBuffer,subStreamType); + break; + } if(!encapsulator) { DEBUG("multichannel: no encapsulator\n"); res=1; goto out; // skip + } } - } - out: +out: ED("HEADER type=%x sub=%x ptsflags=%d length=%d\n",header[3],subStreamType,ptsFlags,length); ED("head: "); for(int k=0 ; k<24 ; k++) ED("%02x ",header[k]); ED("\ndata: "); for(int k=0 ; k<24 ; k++) ED("%02x ",b[k]); @@ -633,12 +633,12 @@ void cMultichannelAudio::Encapsulate(uchar *b, int length) if(offset && ptsFlags) { // get start of the packet to which the PTS belong (DVD only) if(offset>=2 && length>offset-2) ptsDelay|=b[offset-2]*256; if(offset>=1 && length>offset-1) ptsDelay|=b[offset-1]; - } + } if(length>=offset) { if(encapsulator) encapsulator->Decode(b+offset,length-offset,ptsFlags,ptsDelay,ptsData); ptsFlags=0; ptsDelay=0; offset=0; ptsData=0; - } + } else offset-=length; Unlock(); } |