mp23codec_libav=NULL;
mp23codec_context_libav=NULL;
+ decompress_buffer=NULL;
+ decompress_buffer_size=0;
+ decompress_buffer_filled=0;
+
}
AudioOMX::~AudioOMX()
unMute();
+ decompress_buffer_size=20000;
+ decompress_buffer=(UCHAR*)malloc(decompress_buffer_size);
+ decompress_buffer_filled=0;
+
av_register_all();
Log::getInstance()->log("Audio", Log::DEBUG, "audio shutdown called");
DeAllocateCodecsOMX();
+ free(decompress_buffer);
+ decompress_buffer=NULL;
+ decompress_buffer_size=0;
+ decompress_buffer_filled=0;
+
return 1;
}
av_init_packet(&incoming_paket_libav);
decode_frame_libav=avcodec_alloc_frame();
libav_mutex.Unlock();
+ decompress_buffer_filled=0;
}
#endif
+unsigned int AudioOMX::AdvanceMpAudioSync(UCHAR *data,unsigned int size)
+{
+ if (size<=2) return size; // silly;
+ unsigned int test=0;
+ while (test+1<size) {
+ if (data[test]==0xFF && (data[test+1] &0xe0)==0xe0) return test; // probably FrameSync
+ test++;
+ }
+ return size;
+}
+
+unsigned int AudioOMX::AdvanceAc3AudioSync(UCHAR *data,unsigned int size)
+{
+ if (size<=2) return size; // silly;
+ unsigned int test=0;
+ while (test+1<size) {
+ if (data[test]==0x0B && data[test+1]==0x77) return test; // probably FrameSync
+ test++;
+ }
+ return size;
+}
+
+
void AudioOMX::PrepareMediaSample(const MediaPacketList& mplist,UINT samplepos)
{
packet = mplist.front();
UINT headerstrip = 0;
if (packet.disconti) {
firstsynched = false;
+ decompress_buffer_filled=0;
if (cur_input_buf_omx) {
OMX_ERRORTYPE error = vw->ProtOMXEmptyThisBuffer(omx_aud_rend/*dec*/,
cur_input_buf_omx);
firstsynched = false;
achange=true;
lastAType = packet.type;
+ decompress_buffer_filled=0;
if (cur_input_buf_omx) {
OMX_ERRORTYPE error = vw->ProtOMXEmptyThisBuffer(omx_aud_rend/*dec*/,
}
cur_input_buf_omx = NULL;
}
+ vw->LockClock();
if (!ChangeAudioPortConfig()) {
Log::getInstance()->log("Audio", Log::DEBUG,
"Changing audio port config failed", error);
}
+ vw->UnlockClock();
}
cur_input_buf_omx = NULL;//write out old data
}
firstsynched = true;
+ //decompress_buffer_filled=0;
} else {
if (!firstsynched) {//
*samplepos = packet.length;//if we have not processed at least one
+ decompress_buffer_filled=0;
return packet.length;//synched packet ignore it!
}
}
}
lastreftimeOMX = packet.presentation_time;
// Log::getInstance()->log("Audio", Log::DEBUG,
- // "Time code %lld pts %lld dts %lld", lastreftimeOMX, packet.pts,packet.dts);
+ // "Time code %lld pts %lld dts %lld", lastreftimeOMX, packet.pts,packet.dts);
lastreftimePTS = packet.pts;
cur_input_buf_omx->nTimeStamp =0;// lastreftimeOMX; // the clock component is faulty;
} else {
}break;
};
- incoming_paket_libav.data =(uint8_t*) buffer+packet.pos_buffer+*samplepos;
- incoming_paket_libav.size = haveToCopy;
+ if (decompress_buffer_filled) { // have a remaining paket
+ incoming_paket_libav.data =(uint8_t*) decompress_buffer;
+ memcpy(decompress_buffer+decompress_buffer_filled,
+ buffer+packet.pos_buffer+*samplepos,
+ min(haveToCopy,decompress_buffer_size-decompress_buffer_filled));
+ incoming_paket_libav.size = decompress_buffer_filled
+ +min(haveToCopy,decompress_buffer_size-decompress_buffer_filled);
+ //Log::getInstance()->log("Audio", Log::DEBUG,"Use saved audio buffer %d",packet.type);
+ } else {
+ incoming_paket_libav.data =(uint8_t*) buffer+packet.pos_buffer+*samplepos;
+ incoming_paket_libav.size = haveToCopy;
+ }
- while (haveToCopy> 0 && errcount<2) {
+ while (haveToCopy> 0 && errcount<3) {
//Log::getInstance()->log("Audio", Log::DEBUG,"libav in %d %d",framesize,current_context->frame_size);
//Log::getInstance()->log("Audio", Log::DEBUG, "libav in %d %d",
// framesize, current_context->frame_size);
+
+ if (!decompress_buffer_filled) { // only do this if no old data is present
+ int adv = 0;
+ switch (packet.type) {
+ case MPTYPE_MPEG_AUDIO:
+ case MPTYPE_MPEG_AUDIO_LAYER3: {
+ adv = AdvanceMpAudioSync(incoming_paket_libav.data,
+ incoming_paket_libav.size);
+ }
+ break;
+ case MPTYPE_AC3:
+ case MPTYPE_AC3_PRE13: {
+ adv = AdvanceAc3AudioSync(incoming_paket_libav.data,
+ incoming_paket_libav.size);
+ }
+ break;
+ };
+ if (adv > 0) {
+ incoming_paket_libav.data += adv;
+ haveToCopy -= adv;
+ *samplepos += adv;
+ if (current_context->frame_size>0) framesize=min(current_context->frame_size,haveToCopy);
+ else framesize=haveToCopy;
+ //Log::getInstance()->log("Audio", Log::DEBUG,"Advance by %d %d from %d",adv,packet.type,*samplepos );
+ if (haveToCopy <= 0) {
+ // Log::getInstance()->log("Audio", Log::DEBUG,"No sync code in packet remove %d",packet.type);
+ *samplepos=packet.length;
+ return packet.length;
+ }
+ break;
+ } //
+ // else Log::getInstance()->log("Audio", Log::DEBUG,"Loop run" );
+ }
+
int oldcancelstate;
int oldcanceltype;
pthread_testcancel();
return *samplepos;
}
- if (len>0) {
- incoming_paket_libav.data += len;
- haveToCopy -= len;
- *samplepos += len;
+ if (decompress_buffer_filled) { // reset to normal decoding
+ if (len>0) {
+ Log::getInstance()->log("Audio", Log::DEBUG,"saved audio: %d",len);
+ haveToCopy -= min(len-decompress_buffer_filled,0);
+ *samplepos += min(len-decompress_buffer_filled,0);
+ if (current_context->frame_size>0) framesize=min(current_context->frame_size,haveToCopy);
+ else framesize=haveToCopy;
+ } else {
+ framesize=haveToCopy;
+ }
+ incoming_paket_libav.data =(uint8_t*) buffer+packet.pos_buffer+*samplepos;
errcount=0;
- if (current_context->frame_size>0) framesize=min(current_context->frame_size,haveToCopy);
- else framesize=haveToCopy;
+ decompress_buffer_filled=0;
} else {
- errcount++;
- framesize=haveToCopy;
+
+ if (len>0) {
+ incoming_paket_libav.data += len;
+ haveToCopy -= len;
+ *samplepos += len;
+ errcount=0;
+ if (current_context->frame_size>0) framesize=min(current_context->frame_size,haveToCopy);
+ else framesize=haveToCopy;
+ } else {
+ errcount++;
+ framesize=haveToCopy;
+ }
}
incoming_paket_libav.size =framesize;
//Log::getInstance()->log("Audio", Log::DEBUG,"memcpy out");
cur_input_buf_omx->nFilledLen += dsize;
} else {
- //Log::getInstance()->log("Audio", Log::DEBUG,"Incomplete mpeg frames in pes packet %d",incoming_paket_libav.size);
+ //Log::getInstance()->log("Audio", Log::DEBUG,"Incomplete mpeg frames in pes packet %d %d",incoming_paket_libav.size,packet.length);
+ /* uint8_t a1=incoming_paket_libav.data[0];
+ uint8_t a2=incoming_paket_libav.data[1];
+ uint8_t a3=incoming_paket_libav.data[2];
+ uint8_t a4=incoming_paket_libav.data[3];*/
+ // Log::getInstance()->log("Audio", Log::DEBUG,"Header %x %x %x %x",a1,a2,
+ // a3,a4);
}
}
+ }
+ decompress_buffer_filled=0;
+ if (haveToCopy ) {
+ Log::getInstance()->log("Audio", Log::DEBUG,"We can not decompress %d save for later %d %x %x",haveToCopy,packet.type,incoming_paket_libav.data,packet.pos_buffer);
+ memcpy(decompress_buffer,incoming_paket_libav.data,min(haveToCopy,decompress_buffer_size));
+
+ decompress_buffer_filled=min(haveToCopy,decompress_buffer_size);
+
}
if (cur_input_buf_omx->nFilledLen) {
+
*samplepos=packet.length;
return packet.length;
if (offset==0) offset=25;
offset=-2*10000000LL/offset;
target_time+=offset;
- if ((target_time-current_time)>1000000LL) target_time=current_time+1000000LL; // something is wrong do not wait too long
- //Log::getInstance()->log("Video", Log::DEBUG, "Wait for display pts: %lld target: %lld sys: %lld off: %lld diff %lld",pts,target_time,current_time,offset,
- // target_time-current_time);
+ //Log::getInstance()->log("Video", Log::DEBUG, "Wait for display pts: %lld tg: %lld sys: %lld off: %lld diff %lld po: %lld",pts,target_time,current_time,offset,
+ // target_time-current_time,playbacktimeoffset);
+ if ((target_time-current_time)>2000000LL) target_time=current_time+2000000LL; // something is wrong do not wait too long
+ //Log::getInstance()->log("Video", Log::DEBUG, "Wait for display pts: %lld tg: %lld sys: %lld off: %lld diff %lld po: %lld",pts,target_time,current_time,offset,
+ // target_time-current_time,playbacktimeoffset);
WaitUntil(target_time);
//Log::getInstance()->log("Video", Log::DEBUG, "Wait for display out %lld",GetCurrentSystemTime());
//Log::getInstance()->log("Video", Log::DEBUG, "threadMethod Frameskip");
} else {
+ // Log::getInstance()->log("Video", Log::DEBUG,
+ // "prot empty this buffer in");
OMX_ERRORTYPE error = ProtOMXEmptyThisBuffer(omx_vid_dec, pict);
if (error != OMX_ErrorNone) {
Log::getInstance()->log("Video", Log::DEBUG,
"OMX_EmptyThisBuffer failed %x", error);
}
+ // Log::getInstance()->log("Video", Log::DEBUG,
+ // "prot empty this buffer out");
if (deint_first_frame && dodeint) DeinterlaceFix();
if (islast) FrameWaitforDisplay(time);
}