2 Copyright 2004-2005 Chris Tallon, 2009 Marten Richter
4 This file is part of VOMP.
6 VOMP is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2 of the License, or
9 (at your option) any later version.
11 VOMP is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with VOMP; if not, write to the Free Software
18 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
25 #include "woptionpane.h"
27 #include "osdopenvg.h"
35 lastAType = MPTYPE_MPEG_AUDIO;
41 canpass_pcm_mch=false;
43 prefered_ac3=0; //0 stereo PCM, 1 passthrough 2 Multichannel PCM
51 omx_aud_rend/*dec*/=0;
52 cur_input_buf_omx=NULL;
55 ac3codec_context_libav=NULL;
58 mp23codec_context_libav=NULL;
60 decompress_buffer=NULL;
61 decompress_buffer_size=0;
62 decompress_buffer_filled=0;
70 int AudioOMX::init(UCHAR tstreamType) {
75 streamType = tstreamType;
77 if (!initAllParams()) {
84 decompress_buffer_size=20000;
85 decompress_buffer=(UCHAR*)malloc(decompress_buffer_size);
86 decompress_buffer_filled=0;
91 av_log_set_flags(AV_LOG_SKIP_REPEATED);
93 ac3codec_libav = avcodec_find_decoder(CODEC_ID_AC3);
94 if (ac3codec_libav == NULL) {
95 Log::getInstance()->log("Audio", Log::DEBUG,
96 "Find libav ac3 decoder failed");
100 mp23codec_libav = avcodec_find_decoder(CODEC_ID_MP3);
101 if (mp23codec_libav == NULL) {
102 Log::getInstance()->log("Audio", Log::DEBUG,
103 "Find libav mpeg audio decoder failed");
107 aaclatmcodec_libav = avcodec_find_decoder(CODEC_ID_AAC_LATM);
108 if (aaclatmcodec_libav == NULL) {
109 Log::getInstance()->log("Audio", Log::DEBUG,
110 "Find libav aac latm decoder failed");
116 ret=vc_tv_hdmi_audio_supported( EDID_AudioFormat_eMPEG1,2,EDID_AudioSampleRate_e48KHz,0);
120 Log::getInstance()->log("Audio", Log::NOTICE,
121 "TV hdmi supports mpeg1 layer 1 and 2");
123 ret=vc_tv_hdmi_audio_supported( EDID_AudioFormat_eMP3,2,EDID_AudioSampleRate_e48KHz,0);
127 Log::getInstance()->log("Audio", Log::NOTICE,
128 "TV hdmi supports mpeg1 layer 3");
131 ret=vc_tv_hdmi_audio_supported( EDID_AudioFormat_eAC3,6,EDID_AudioSampleRate_e48KHz,0);
134 Log::getInstance()->log("Audio", Log::NOTICE,
135 "TV hdmi supports AC3");
137 ret=vc_tv_hdmi_audio_supported( EDID_AudioFormat_eAAC,6,EDID_AudioSampleRate_e48KHz,0);
141 Log::getInstance()->log("Audio", Log::NOTICE,
142 "TV hdmi supports AAC");
145 canpass_pcm_mch=false;
150 int AudioOMX::initAllParams()
152 return (setStreamType(streamType) && setChannel() && setSource());
155 int AudioOMX::shutdown()
157 if (!initted) return 0;
160 Log::getInstance()->log("Audio", Log::DEBUG, "audio shutdown called");
161 DeAllocateCodecsOMX();
163 free(decompress_buffer);
164 decompress_buffer=NULL;
165 decompress_buffer_size=0;
166 decompress_buffer_filled=0;
171 bool AudioOMX::loadOptionsfromServer(VDR* vdr)
173 Log::getInstance()->log("Audio", Log::DEBUG, "AudioOMX config load");
174 char *name=vdr->configLoad("AudioOMX","AC3DecodingMode");
177 if (STRCASECMP(name, "PCM") == 0) {
179 } else if (STRCASECMP(name, "Passthrough") == 0) {
181 } else if (STRCASECMP(name, "PCMMultichannel") == 0) {
186 name = vdr->configLoad("AudioOMX", "Mp2DecodingMode");
189 if (STRCASECMP(name, "PCM") == 0) {
191 } else if (STRCASECMP(name, "Passthrough") == 0) {
193 } else if (STRCASECMP(name, "PCMMultichannel") == 0) {
198 name = vdr->configLoad("AudioOMX", "AACDecodingMode");
201 if (STRCASECMP(name, "PCM") == 0) {
203 } else if (STRCASECMP(name, "Passthrough") == 0) {
205 } else if (STRCASECMP(name, "PCMMultichannel") == 0) {
210 name = vdr->configLoad("AudioOMX", "Mp3DecodingMode");
213 if (STRCASECMP(name, "PCM") == 0) {
215 } else if (STRCASECMP(name, "Passthrough") == 0) {
217 } else if (STRCASECMP(name, "PCMMultichannel") == 0) {
222 name = vdr->configLoad("AudioOMX", "AudioOutput");
225 if (STRCASECMP(name, "analog") == 0) {
227 } else if (STRCASECMP(name, "HDMI") == 0) {
237 bool AudioOMX::handleOptionChanges(Option* option)
239 if (Audio::handleOptionChanges(option))
241 switch (option->id) {
243 if (STRCASECMP(option->options[option->userSetChoice], "analog") == 0) {
245 } else if (STRCASECMP(option->options[option->userSetChoice], "HDMI")
253 if (STRCASECMP(option->options[option->userSetChoice], "PCM") == 0) {
255 } else if (STRCASECMP(option->options[option->userSetChoice],
256 "Passthrough") == 0) {
258 } else if (STRCASECMP(option->options[option->userSetChoice],
259 "PCMMultichannel") == 0) {
265 if (STRCASECMP(option->options[option->userSetChoice], "PCM") == 0) {
267 } else if (STRCASECMP(option->options[option->userSetChoice],
268 "Passthrough") == 0) {
270 } else if (STRCASECMP(option->options[option->userSetChoice],
271 "PCMMultichannel") == 0) {
277 if (STRCASECMP(option->options[option->userSetChoice], "PCM") == 0) {
279 } else if (STRCASECMP(option->options[option->userSetChoice],
280 "Passthrough") == 0) {
282 } else if (STRCASECMP(option->options[option->userSetChoice],
283 "PCMMultichannel") == 0) {
289 if (STRCASECMP(option->options[option->userSetChoice], "PCM") == 0) {
291 } else if (STRCASECMP(option->options[option->userSetChoice],
292 "Passthrough") == 0) {
294 } else if (STRCASECMP(option->options[option->userSetChoice],
295 "PCMMultichannel") == 0) {
305 bool AudioOMX::saveOptionstoServer()
308 switch (prefered_ac3) {
310 VDR::getInstance()->configSave("AudioOMX", "AC3DecodingMode", "PCM");
313 VDR::getInstance()->configSave("AudioOMX", "AC3DecodingMode",
317 VDR::getInstance()->configSave("AudioOMX", "AC3DecodingMode",
322 switch (prefered_aac) {
324 VDR::getInstance()->configSave("AudioOMX", "AACDecodingMode", "PCM");
327 VDR::getInstance()->configSave("AudioOMX", "AACDecodingMode",
331 VDR::getInstance()->configSave("AudioOMX", "AACDecodingMode",
336 switch (prefered_mp2) {
338 VDR::getInstance()->configSave("AudioOMX", "Mp2DecodingMode", "PCM");
341 VDR::getInstance()->configSave("AudioOMX", "Mp2DecodingMode",
345 VDR::getInstance()->configSave("AudioOMX", "Mp2DecodingMode",
350 switch (prefered_mp3) {
352 VDR::getInstance()->configSave("AudioOMX", "Mp3DecodingMode", "PCM");
355 VDR::getInstance()->configSave("AudioOMX", "Mp3DecodingMode",
359 VDR::getInstance()->configSave("AudioOMX", "Mp3DecodingMode",
365 VDR::getInstance()->configSave("AudioOMX", "AudioOutput", "analog");
367 VDR::getInstance()->configSave("AudioOMX", "AudioOutput", "HDMI");
373 /*Option(UINT id, const char* displayText, const char* configSection, const char* configKey, UINT optionType,
374 UINT numChoices, UINT defaultChoice, UINT startInt,
375 const char * const * options, const char * const * optionkeys = NULL, AbstractOption* handler=NULL);*/
377 bool AudioOMX::addOptionsToPanes(int panenumber,Options *options,WOptionPane* pane)
379 if (!Audio::addOptionsToPanes(panenumber,options,pane)) return false;
386 static const char* audioopts[]={"analog","HDMI"};
387 option = new Option(4,tr("Audio Output"), "AudioOMX","AudioOutput",Option::TYPE_TEXT,2,0,0,audioopts,NULL,false,this);
388 options->push_back(option);
389 pane->addOptionLine(option);
392 char **ac3opts=new char *[3];
394 ac3opts[i]=new char[strlen("PCM")+1];
395 strcpy(ac3opts[i],"PCM");
398 ac3opts[i]=new char[strlen("Passthrough")+1];
399 strcpy(ac3opts[i],"PassThrough");
402 if (canpass_pcm_mch) {
403 ac3opts[i]=new char[strlen("PCMMultichannel")+1];
404 strcpy(ac3opts[i],"PCMMultichannel");
407 option = new Option(1 ,tr("AC3 HDMI Mode"), "AudioOMX", "AC3DecodingMode", Option::TYPE_TEXT, i, 0, 0, ac3opts,NULL,true, this);
408 options->push_back(option);
409 pane->addOptionLine(option);
411 /* char **aacopts = new char *[3];
413 aacopts[i] = new char[strlen("PCM") + 1];
414 strcpy(mp2opts[i], "PCM");
417 aacopts[i] = new char[strlen("Passthrough") + 1];
418 strcpy(aacopts[i], "PassThrough");
421 if (canpass_pcm_mch) {
422 aacopts[i] = new char[strlen("PCMMultichannel") + 1];
423 strcpy(aacopts[i], "PCMMultichannel");
426 option = new Option(5, tr("Mp2 HDMI Mode"), "AudioOMX",
427 "AACDecodingMode", Option::TYPE_TEXT, i, 0, 0,
428 aacopts, NULL, true, this);
429 options->push_back(option);
430 pane->addOptionLine(option);
433 char **mp2opts = new char *[3];
435 mp2opts[i] = new char[strlen("PCM") + 1];
436 strcpy(mp2opts[i], "PCM");
439 mp2opts[i] = new char[strlen("Passthrough") + 1];
440 strcpy(mp2opts[i], "PassThrough");
443 if (canpass_pcm_mch) {
444 mp2opts[i] = new char[strlen("PCMMultichannel") + 1];
445 strcpy(mp2opts[i], "PCMMultichannel");
448 option = new Option(2, tr("Mp2 HDMI Mode"), "AudioOMX",
449 "Mp2DecodingMode", Option::TYPE_TEXT, i, 0, 0,
450 mp2opts, NULL, true, this);
451 options->push_back(option);
452 pane->addOptionLine(option);
454 char **mp3opts = new char *[3];
456 mp3opts[i] = new char[strlen("PCM") + 1];
457 strcpy(mp3opts[i], "PCM");
460 mp3opts[i] = new char[strlen("Passthrough") + 1];
461 strcpy(mp3opts[i], "PassThrough");
464 if (canpass_pcm_mch) {
465 mp3opts[i] = new char[strlen("PCMMultichannel") + 1];
466 strcpy(mp3opts[i], "PCMMultichannel");
469 option = new Option(3, tr("Mp3 HDMI Mode"), "AudioOMX",
470 "Mp2DecodingMode", Option::TYPE_TEXT, i, 0, 0, mp3opts,
472 options->push_back(option);
473 pane->addOptionLine(option);*/
474 // Comment unsupported modes out
487 OMX_ERRORTYPE AudioOMX::EmptyBufferDone_OMX(OMX_IN OMX_HANDLETYPE hcomp,OMX_IN OMX_PTR appdata,OMX_IN OMX_BUFFERHEADERTYPE* buffer){
489 //Log::getInstance()->log("Audio", Log::NOTICE, "EmptyBufferDone");
490 AudioOMX *audio=(AudioOMX *)getInstance();
491 audio->ReturnEmptyOMXBuffer(buffer);
492 return OMX_ErrorNone;
496 void AudioOMX::ReturnEmptyOMXBuffer(OMX_BUFFERHEADERTYPE* buffer){
497 input_bufs_omx_mutex.Lock();
498 //Log::getInstance()->log("Audio", Log::NOTICE, "ReturnEmptyOMXBuffer %d",input_bufs_omx_free.size());
499 input_bufs_omx_free.push_back(buffer);
500 //Log::getInstance()->log("Audio", Log::NOTICE, "ReturnEmptyOMXBuffer %d",input_bufs_omx_free.size());
501 input_bufs_omx_mutex.Unlock();
504 OMX_ERRORTYPE AudioOMX::FillBufferDone_OMX(OMX_IN OMX_HANDLETYPE hcomp, OMX_IN OMX_PTR appdata,OMX_IN OMX_BUFFERHEADERTYPE* buffer) {
505 Log::getInstance()->log("Audio", Log::NOTICE, "FillBufferDone");
506 return OMX_ErrorNone;
511 int AudioOMX::setStreamType(UCHAR type)
513 if (!initted) return 0;
515 // if (ioctl(fdAudio, AV_SET_AUD_STREAMTYPE, type) != 0) return 0;
519 int AudioOMX::setChannel()
521 if (!initted) return 0;
523 // if (ioctl(fdAudio, AV_SET_AUD_CHANNEL, 0) != 0) return 0;
527 int AudioOMX::setSource()
529 if (!initted) return 0;
531 // if (ioctl(fdAudio, AV_SET_AUD_SRC, 1) != 0) return 0;
537 if (!initted) return 0;
539 // if (ioctl(fdAudio, AV_SET_AUD_SYNC, 2) != 0) return 0;
543 int AudioOMX::play() {
546 lastAType=MPTYPE_MPEG_AUDIO;
547 Log::getInstance()->log("Audio", Log::DEBUG, "enter play");
549 if (!AllocateCodecsOMX()) {
556 int AudioOMX::ChangeAudioDestination() //clock aka omx mutex needs to be locked
559 const char * destinations[]={"local","hdmi"};
564 OMX_CONFIG_BRCMAUDIODESTINATIONTYPE auddest;
565 memset(&auddest,0,sizeof(auddest));
566 auddest.nSize=sizeof(auddest);
567 auddest.nVersion.nVersion=OMX_VERSION;
568 strcpy((char *)auddest.sName, destinations[dest]);
570 Log::getInstance()->log("Audio", Log::DEBUG, "setting destination to: %s",auddest.sName);
571 error=OMX_SetConfig(omx_aud_rend,OMX_IndexConfigBrcmAudioDestination,&auddest);
572 if (error!=OMX_ErrorNone){
573 Log::getInstance()->log("Audio", Log::DEBUG, "Init OMX_IndexConfigBrcmAudioDestination failed %x %x %s", error,omx_aud_rend,auddest.sName);
574 DeAllocateCodecsOMX();
582 int AudioOMX::ChangeAudioPortConfig(bool disport) //clock aka omx mutex needs to be locked
585 //Ok first fidle a working configuration
586 Log::getInstance()->log("Audio", Log::DEBUG,
587 "ChangeAudioPortConfig");
589 OMX_AUDIO_CODINGTYPE encoding;
592 case MPTYPE_MPEG_AUDIO: {
593 if (prefered_mp2 == 2 && false) { //not supported yet
596 if (prefered_mp2 == 1 && canpass_mp2) {
598 encoding=OMX_AUDIO_CodingMP3;
601 encoding=OMX_AUDIO_CodingPCM;
606 case MPTYPE_AAC_LATM: {
607 if (prefered_aac == 2 && false) { //not supported yet
610 Log::getInstance()->log("Audio", Log::DEBUG,
611 "ChangeAudioPortConfig debug %d %d",prefered_aac,canpass_aac);
612 if (prefered_aac == 1 && canpass_aac) {
614 encoding=OMX_AUDIO_CodingAAC;
617 encoding=OMX_AUDIO_CodingPCM;
622 case MPTYPE_AC3_PRE13:
624 if (prefered_ac3 == 2 && false) { //not supported yet
627 Log::getInstance()->log("Audio", Log::DEBUG,
628 "ChangeAudioPortConfig debug %d %d",prefered_ac3,canpass_ac3);
629 if (prefered_ac3 == 1 && canpass_ac3) {
631 encoding=OMX_AUDIO_CodingDDP;
634 encoding=OMX_AUDIO_CodingPCM;
639 case MPTYPE_MPEG_AUDIO_LAYER3: {
640 if (prefered_mp3 == 2 && false) { //not supported yet
643 if (prefered_mp3 == 1 && canpass_mp2) {
645 encoding=OMX_AUDIO_CodingMP3;
648 encoding=OMX_AUDIO_CodingPCM;
656 encoding=OMX_AUDIO_CodingPCM;
657 //mch=false; // multichannel also false
662 /*OMX_CONFIG_BOOLEANTYPE booly;
663 memset(&booly, 0, sizeof(booly));
664 booly.nSize = sizeof(booly);
665 booly.nVersion.nVersion = OMX_VERSION;
667 booly.bEnabled = OMX_TRUE;
669 booly.bEnabled = OMX_FALSE;
671 error = OMX_SetParameter(omx_aud_dec, OMX_IndexParamBrcmDecoderPassThrough,
673 if (error != OMX_ErrorNone) {
674 Log::getInstance()->log("Audio", Log::DEBUG,
675 "Init OMX_IndexParamBrcmDecoderPassThrough failed %x", error);
676 DeAllocateCodecsOMX();
679 VideoOMX* video=(VideoOMX*)Video::getInstance();
681 video->DisablePort(omx_aud_rend,omx_rend_input_port,false);
682 //DestroyInputBufsOMXwhilePlaying();
683 //video->CommandFinished(omx_aud_rend,OMX_CommandPortDisable,omx_rend_input_port);
688 OMX_AUDIO_PARAM_PORTFORMATTYPE format;
689 memset(&format, 0, sizeof(format));
690 format.nSize = sizeof(format);
691 format.nVersion.nVersion = OMX_VERSION;
692 format.nPortIndex = omx_rend_input_port;
693 error = OMX_GetParameter(omx_aud_rend, OMX_IndexParamAudioPortFormat,
695 if (error != OMX_ErrorNone) {
696 Log::getInstance()->log("Audio", Log::DEBUG,
697 "Get OMX_IndexParamAudioPortFormat failed %x %d", error,
698 omx_rend_input_port);
703 Log::getInstance()->log("Audio", Log::DEBUG,
704 "Get OMX_IndexParamAudioPortFormat returned %d",format.eEncoding );
705 format.eEncoding = encoding;
707 error = OMX_SetParameter(omx_aud_rend, OMX_IndexParamAudioPortFormat,
709 if (error != OMX_ErrorNone) {
710 Log::getInstance()->log("Audio", Log::DEBUG,
711 "Set OMX_IndexParamAudioPortFormat failed %x %d %d", error,
712 omx_rend_input_port,format.eEncoding );
717 case OMX_AUDIO_CodingPCM: {
718 OMX_AUDIO_PARAM_PCMMODETYPE audio_pcm;
719 memset(&audio_pcm, 0, sizeof(audio_pcm));
720 audio_pcm.nSize = sizeof(audio_pcm);
721 audio_pcm.nVersion.nVersion = OMX_VERSION;
722 audio_pcm.nChannels = 2;
723 audio_pcm.eChannelMapping[0] = OMX_AUDIO_ChannelLF;
724 audio_pcm.eChannelMapping[1] = OMX_AUDIO_ChannelRF;
725 //audio_pcm.eChannelMapping[2]=OMX_AUDIO_ChannelMax;
726 audio_pcm.eNumData = OMX_NumericalDataSigned;
727 audio_pcm.eEndian = OMX_EndianLittle;
728 audio_pcm.bInterleaved = OMX_TRUE;
729 audio_pcm.nBitPerSample = 16;
730 audio_pcm.ePCMMode = OMX_AUDIO_PCMModeLinear;
731 audio_pcm.nChannels = 2;
732 audio_pcm.nSamplingRate = 48000;
733 audio_pcm.nPortIndex = omx_rend_input_port;
734 error = OMX_SetParameter(omx_aud_rend, OMX_IndexParamAudioPcm,
736 if (error != OMX_ErrorNone) {
737 Log::getInstance()->log("Audio", Log::DEBUG,
738 "Init OMX_IndexParamAudioPcm failed %x %d", error,
739 omx_rend_input_port);
743 case OMX_AUDIO_CodingDDP: {
744 OMX_AUDIO_PARAM_DDPTYPE audio_ddp;
745 memset(&audio_ddp, 0, sizeof(audio_ddp));
746 audio_ddp.nSize = sizeof(audio_ddp);
747 audio_ddp.nVersion.nVersion = OMX_VERSION;
748 audio_ddp.nPortIndex = omx_rend_input_port;
749 audio_ddp.nChannels = 8; //unknown
750 audio_ddp.nBitRate=0;
751 audio_ddp.nSampleRate=48000;
752 audio_ddp.eChannelMapping[0] =OMX_AUDIO_ChannelLF;
753 audio_ddp.eChannelMapping[1] =OMX_AUDIO_ChannelRF;
754 audio_ddp.eChannelMapping[2] =OMX_AUDIO_ChannelCF;
755 audio_ddp.eChannelMapping[3] =OMX_AUDIO_ChannelLFE;
756 audio_ddp.eChannelMapping[4] =OMX_AUDIO_ChannelLR;
757 audio_ddp.eChannelMapping[5] =OMX_AUDIO_ChannelRR;
758 audio_ddp.eChannelMapping[6] =OMX_AUDIO_ChannelLS;
759 audio_ddp.eChannelMapping[7] =OMX_AUDIO_ChannelRS;
760 audio_ddp.eChannelMapping[8] =OMX_AUDIO_ChannelCS;
761 error = OMX_SetParameter(omx_aud_rend, OMX_IndexParamAudioDdp,
763 if (error != OMX_ErrorNone) {
764 Log::getInstance()->log("Audio", Log::DEBUG,
765 "Init OMX_IndexParamAudioDdp failed %x %d", error,
766 omx_rend_input_port);
771 default: break; //Make compiler happy
778 //PrepareInputBufsOMX(false);
779 video->EnablePort(omx_aud_rend,omx_rend_input_port,false);
789 int AudioOMX::InitDecoderLibAV()
792 ac3codec_context_libav = avcodec_alloc_context3(ac3codec_libav);
793 if (!ac3codec_context_libav) {
794 Log::getInstance()->log("Audio", Log::DEBUG, "Alloc avcodec for ac3 decoding context failed!");
798 ac3codec_context_libav->flags |= CODEC_FLAG_TRUNCATED;
799 ac3codec_context_libav->request_channels=2;
801 int avc_ret = avcodec_open2(ac3codec_context_libav, ac3codec_libav, NULL);
803 Log::getInstance()->log("Audio", Log::DEBUG, "Opening libav codec failed \n");
804 libav_mutex.Unlock();
808 aaclatmcodec_context_libav = avcodec_alloc_context3(aaclatmcodec_libav);
809 if (!aaclatmcodec_context_libav) {
810 Log::getInstance()->log("Audio", Log::DEBUG, "Alloc avcodec for aac decoding context failed!");
814 aaclatmcodec_context_libav->flags |= CODEC_FLAG_TRUNCATED;
815 aaclatmcodec_context_libav->request_channels=2;
817 avc_ret = avcodec_open2(aaclatmcodec_context_libav, aaclatmcodec_libav, NULL);
819 Log::getInstance()->log("Audio", Log::DEBUG, "Opening libav codec failed \n");
820 libav_mutex.Unlock();
825 mp23codec_context_libav = avcodec_alloc_context3(mp23codec_libav);
826 if (!ac3codec_context_libav) {
827 Log::getInstance()->log("Audio", Log::DEBUG, "Alloc avcodec for mp23 decoding context failed!");
828 libav_mutex.Unlock();
832 mp23codec_context_libav->flags |= CODEC_FLAG_TRUNCATED;
833 mp23codec_context_libav->request_channels=2;
835 avc_ret = avcodec_open2(mp23codec_context_libav, mp23codec_libav, NULL);
837 Log::getInstance()->log("Audio", Log::DEBUG, "Opening libav codec failed \n");
838 libav_mutex.Unlock();
842 av_init_packet(&incoming_paket_libav);
843 decode_frame_libav=avcodec_alloc_frame();
844 libav_mutex.Unlock();
845 decompress_buffer_filled=0;
852 void AudioOMX::DeinitDecoderLibAV() {
856 if (ac3codec_context_libav) {
857 avcodec_close(ac3codec_context_libav);
858 av_free(ac3codec_context_libav);
859 ac3codec_context_libav = NULL;
861 avcodec_close(aaclatmcodec_context_libav);
862 av_free(aaclatmcodec_context_libav);
863 aaclatmcodec_context_libav = NULL;
865 av_free(decode_frame_libav);
867 avcodec_close(mp23codec_context_libav);
868 av_free(mp23codec_context_libav);
869 mp23codec_context_libav = NULL;
872 libav_mutex.Unlock();
877 int AudioOMX::AllocateCodecsOMX()
880 static OMX_CALLBACKTYPE callbacks= {&VideoOMX::EventHandler_OMX,&EmptyBufferDone_OMX,&FillBufferDone_OMX};
882 Log::getInstance()->log("Audio", Log::NOTICE, "Allocate Codecs OMX");
883 //Clock, move later to audio
884 VideoOMX *video=(VideoOMX*)Video::getInstance();
886 if (!InitDecoderLibAV()) return 0;;
889 OMX_PORT_PARAM_TYPE p_param;
890 memset(&p_param,0,sizeof(p_param));
891 p_param.nSize=sizeof(p_param);
892 p_param.nVersion.nVersion=OMX_VERSION;
895 if (!video->getClockAudioandInit(&omx_clock,&omx_clock_output_port)){
896 return 0;// get the clock and init it if necessary
900 if (!video->idleClock()) {
905 error = OMX_GetHandle(&omx_aud_rend, VPE_OMX_AUDIO_REND, NULL, &callbacks);
906 if (error != OMX_ErrorNone) {
907 Log::getInstance()->log("Audio", Log::DEBUG,
908 "Init OMX audio rend failed %x", error);
909 video->UnlockClock();
910 DeAllocateCodecsOMX();
914 if (!ChangeAudioDestination()) {
915 video->UnlockClock();
916 DeAllocateCodecsOMX();
920 error = OMX_GetParameter(omx_aud_rend, OMX_IndexParamAudioInit, &p_param);
921 if (error != OMX_ErrorNone) {
922 Log::getInstance()->log("Audio", Log::DEBUG,
923 "Init OMX audio rend OMX_GetParameter failed %x", error);
924 video->UnlockClock();
925 DeAllocateCodecsOMX();
928 omx_rend_input_port = p_param.nStartPortNumber;
930 error = OMX_GetParameter(omx_aud_rend, OMX_IndexParamOtherInit, &p_param);
931 if (error != OMX_ErrorNone) {
932 Log::getInstance()->log("Audio", Log::DEBUG,
933 "Init OMX aud rend OMX_GetParameter failed %x", error);
934 video->UnlockClock();
935 DeAllocateCodecsOMX();
938 // buggy return value
939 omx_rend_clock_port = p_param.nStartPortNumber;
942 /* error=OMX_GetHandle(&omx_aud_dec,VPE_OMX_AUDIO_DECODER,NULL,&callbacks);
944 if (error!=OMX_ErrorNone){
945 Log::getInstance()->log("Audio", Log::DEBUG, "Init OMX audio decoder failed %x", error);
946 video->UnlockClock();
947 DeAllocateCodecsOMX();
951 error=OMX_GetParameter(omx_aud_dec,OMX_IndexParamAudioInit,&p_param);
952 if (error!=OMX_ErrorNone){
953 Log::getInstance()->log("Audio", Log::DEBUG, "Init OMX audio decoder OMX_GetParameter failed %x", error);
954 video->UnlockClock();
955 DeAllocateCodecsOMX();
958 omx_codec_input_port=p_param.nStartPortNumber;
959 omx_codec_output_port=p_param.nStartPortNumber+1;
961 if (!video->DisablePort(omx_aud_dec,omx_codec_input_port) || !video->DisablePort(omx_aud_dec,omx_codec_output_port)) {
962 Log::getInstance()->log("Audio", Log::DEBUG, "Disable Ports OMX audio decoder failed");
963 video->UnlockClock();
964 DeAllocateCodecsOMX();
971 if (!video->DisablePort(omx_aud_rend,omx_rend_input_port,true) ) {
972 Log::getInstance()->log("Audio", Log::DEBUG, "Disable Ports OMX audio rend failed %d",omx_rend_input_port);
973 video->UnlockClock();
974 DeAllocateCodecsOMX();
978 if ( !video->DisablePort(omx_aud_rend, omx_rend_clock_port, true)) {
979 Log::getInstance()->log("Audio", Log::DEBUG,
980 "Disable Ports OMX rend clock port failed %d",omx_rend_clock_port);
981 video->UnlockClock();
982 DeAllocateCodecsOMX();
992 error=OMX_SetupTunnel(omx_clock,omx_clock_output_port,omx_aud_rend,omx_rend_clock_port);
993 if (error!=OMX_ErrorNone){
994 Log::getInstance()->log("Audio", Log::DEBUG, "OMX_Setup tunnel clock to rend failed %x %d %d", error,omx_clock_output_port,omx_rend_clock_port);
995 video->UnlockClock();
996 DeAllocateCodecsOMX();
1000 if (!video->EnablePort(omx_clock,omx_clock_output_port,false) || !video->EnablePort(omx_aud_rend,omx_rend_clock_port,false)
1002 Log::getInstance()->log("Audio", Log::DEBUG, "Enable Ports OMX clock rend failed");
1003 video->UnlockClock();
1004 DeAllocateCodecsOMX();
1008 if (!video->ChangeComponentState(omx_aud_rend,OMX_StateIdle)) {
1009 Log::getInstance()->log("Audio", Log::DEBUG, "aud_rend idle ChangeComponentState");
1010 video->UnlockClock();
1011 DeAllocateCodecsOMX();
1018 if ( !video->CommandFinished(omx_aud_rend,OMX_CommandPortEnable,omx_rend_clock_port)) {
1019 video->UnlockClock();
1020 DeAllocateCodecsOMX();
1024 if ( !video->CommandFinished(omx_clock,OMX_CommandPortEnable,omx_clock_output_port)) {
1025 video->UnlockClock();
1026 DeAllocateCodecsOMX();
1032 if (!ChangeAudioPortConfig(false)){
1033 Log::getInstance()->log("Audio", Log::NOTICE, "Change AudioPortConfig failed");
1034 video->UnlockClock();
1035 DeAllocateCodecsOMX();
1039 /* if (!video->ChangeComponentState(omx_aud_dec,OMX_StateIdle)) {
1040 Log::getInstance()->log("Audio", Log::DEBUG, "aud_dec ChangeComponentState");
1041 DeAllocateCodecsOMX();
1047 if (!PrepareInputBufsOMX(true)) {
1048 video->UnlockClock();
1049 DeAllocateCodecsOMX();
1055 /* error=OMX_SetupTunnel(omx_aud_dec,omx_codec_output_port,omx_aud_rend,omx_rend_input_port);
1056 if (error!=OMX_ErrorNone){
1057 Log::getInstance()->log("Audio", Log::DEBUG, "OMX_Setup tunnel dec to render failed %x", error);
1058 video->UnlockClock();
1059 DeAllocateCodecsOMX();
1065 /* if (!video->EnablePort(omx_aud_dec,omx_codec_output_port,false) || !video->EnablePort(omx_aud_rend,omx_rend_input_port,false)
1067 Log::getInstance()->log("Audio", Log::DEBUG, "Enable Ports OMX codec rend failed");
1068 video->UnlockClock();
1069 DeAllocateCodecsOMX();
1073 /* if ( !video->CommandFinished(omx_aud_dec,OMX_CommandPortEnable,omx_codec_output_port)
1074 || !video->CommandFinished(omx_aud_rend,OMX_CommandPortEnable,omx_rend_input_port)) {
1075 video->UnlockClock();
1076 DeAllocateCodecsOMX();
1080 if (!video->ChangeComponentState(omx_aud_rend,OMX_StateExecuting)) {
1081 Log::getInstance()->log("Audio", Log::DEBUG, "omx_aud_rend ChangeComponentState Execute");
1082 video->UnlockClock();
1083 DeAllocateCodecsOMX();
1088 video->UnlockClock();
1094 if (!video->setClockExecutingandRunning()) return 0;
1096 Log::getInstance()->log("Audio", Log::NOTICE, "Allocate Codecs OMX finished");
1104 int AudioOMX::PrepareInputBufsOMX(bool setportdef) //needs to be called with locvke omx clock mutex
1106 VideoOMX *video=(VideoOMX*)Video::getInstance();
1107 OMX_ERRORTYPE error;
1108 OMX_PARAM_PORTDEFINITIONTYPE port_def_type;
1109 memset(&port_def_type,0,sizeof(port_def_type));
1110 port_def_type.nSize=sizeof(port_def_type);
1111 port_def_type.nVersion.nVersion=OMX_VERSION;
1112 port_def_type.nPortIndex=omx_rend_input_port;//omx_codec_input_port;
1114 error=OMX_GetParameter(omx_aud_rend/*dec*/,OMX_IndexParamPortDefinition, &port_def_type);
1116 if (error!=OMX_ErrorNone){
1117 Log::getInstance()->log("Audio", Log::DEBUG, "Get OMX OMX_IndexParamPortDefinition failed %x", error);
1122 port_def_type.nBufferCountActual=2;
1123 port_def_type.nBufferSize=max(port_def_type.nBufferSize,50000); // for transcoder important
1125 error=OMX_SetParameter(omx_aud_rend/*dec*/,OMX_IndexParamPortDefinition, &port_def_type);
1127 if (error!=OMX_ErrorNone){
1128 Log::getInstance()->log("Audio", Log::DEBUG, "Set OMX OMX_IndexParamPortDefinition failed %x", error);
1133 error=OMX_SendCommand(omx_aud_rend/*dec*/,OMX_CommandPortEnable,omx_rend_input_port/*codec*/,0);
1134 if (error!=OMX_ErrorNone){
1135 Log::getInstance()->log("Audio", Log::DEBUG, "Prepare Input bufs Send Command to enable port %x", error);
1139 input_bufs_omx_mutex.Lock();
1140 for (unsigned int i=0; i< port_def_type.nBufferCountActual;i++) {
1141 OMX_BUFFERHEADERTYPE *buf_head=NULL;
1142 error=OMX_AllocateBuffer(omx_aud_rend/*dec*/,&buf_head,omx_rend_input_port/*codec*/,NULL,port_def_type.nBufferSize);
1143 if (error!=OMX_ErrorNone){
1144 Log::getInstance()->log("Audio", Log::DEBUG, "Use OMX_AllocateBuffer failed %x", error);
1145 input_bufs_omx_mutex.Unlock();
1148 input_bufs_omx_all.push_back(buf_head);
1149 input_bufs_omx_free.push_back(buf_head);
1151 omx_first_frame=true;
1154 cur_input_buf_omx=NULL;
1155 input_bufs_omx_mutex.Unlock();
1157 if (!video->CommandFinished(omx_aud_rend/*dec*/,OMX_CommandPortEnable,omx_rend_input_port /*codec*/)) {
1164 int AudioOMX::DestroyInputBufsOMX() //call with clock mutex locked
1166 OMX_ERRORTYPE error;
1168 cur_input_buf_omx=NULL;
1169 input_bufs_omx_mutex.Lock();
1170 for (int i=0; i< input_bufs_omx_all.size();i++) {
1171 error=OMX_FreeBuffer(omx_aud_rend/*dec*/,omx_rend_input_port/*codec*/,input_bufs_omx_all[i]);
1172 if (error!=OMX_ErrorNone){
1173 Log::getInstance()->log("Audio", Log::DEBUG, "Use OMX_FreeBuffer failed %x", error);
1174 input_bufs_omx_mutex.Unlock();
1179 input_bufs_omx_all.clear();
1180 input_bufs_omx_free.clear();
1181 input_bufs_omx_mutex.Unlock();
1185 int AudioOMX::DestroyInputBufsOMXwhilePlaying() //call with clock mutex locked
1187 OMX_ERRORTYPE error;
1189 cur_input_buf_omx=NULL;
1190 input_bufs_omx_mutex.Lock();
1191 while (input_bufs_omx_all.size()>0) {
1192 if (input_bufs_omx_free.size()>0) {
1193 // Destroy one buffer
1194 vector<OMX_BUFFERHEADERTYPE*>::iterator itty=input_bufs_omx_all.begin();
1195 OMX_BUFFERHEADERTYPE* cur_buf=input_bufs_omx_free.front();
1196 for (; itty!= input_bufs_omx_all.end();itty++) {
1197 if ((*itty)==cur_buf) {
1198 input_bufs_omx_all.erase(itty);
1199 input_bufs_omx_free.pop_front();
1204 input_bufs_omx_mutex.Unlock();
1206 input_bufs_omx_mutex.Lock();
1210 Log::getInstance()->log("Audio", Log::DEBUG, "DestroyInputBufsOMXwhilePlaying %d %d", input_bufs_omx_all.size(),input_bufs_omx_free.size());
1211 input_bufs_omx_mutex.Unlock();
1216 int AudioOMX::DeAllocateCodecsOMX()
1218 OMX_ERRORTYPE error;
1220 VideoOMX *video=(VideoOMX*)Video::getInstance();
1221 Log::getInstance()->log("Audio", Log::DEBUG, "enter deallocatecodecsomx");
1225 Log::getInstance()->log("Audio", Log::DEBUG, "deallocatecodecsomx mark 1");
1226 if (cur_input_buf_omx) {
1227 cur_input_buf_omx->nFlags|=OMX_BUFFERFLAG_EOS;
1228 OMX_ERRORTYPE error=video->ProtOMXEmptyThisBuffer(omx_aud_rend/*dec*/,cur_input_buf_omx);
1229 if (error!=OMX_ErrorNone) {
1230 Log::getInstance()->log("Audio", Log::DEBUG, "OMX_EmptyThisBuffer 6 failed %x", error);
1233 cur_input_buf_omx=NULL;//write out old data
1235 Log::getInstance()->log("Audio", Log::DEBUG, "deallocatecodecsomx mark 2");
1238 if (omx_aud_rend/*dec*/) {
1239 // first stop the omx elements
1240 /* if (!video->ChangeComponentState(omx_aud_dec,OMX_StateIdle)) {
1241 Log::getInstance()->log("Audio", Log::DEBUG, "aud_dec ChangeComponentState");
1243 Log::getInstance()->log("Audio", Log::DEBUG, "deallocatecodecsomx mark 3");
1245 video->UnlockClock();
1246 Log::getInstance()->log("Audio", Log::DEBUG, "deallocatecodecsomx mark 4");
1248 Log::getInstance()->log("Audio", Log::DEBUG, "deallocatecodecsomx mark 5");
1251 if (!video->ChangeComponentState(omx_aud_rend,OMX_StateIdle)) {
1252 Log::getInstance()->log("Audio", Log::DEBUG, "aud_rend ChangeComponentState");
1255 // TODO proper deinit sequence
1256 // first flush all buffers
1258 error=OMX_SendCommand(omx_aud_rend,OMX_CommandFlush, omx_rend_input_port, NULL);
1259 if (error!=OMX_ErrorNone) {
1260 Log::getInstance()->log("Audio", Log::DEBUG, "OMX_Flush rend in failed %x", error);
1264 /* error=OMX_SendCommand(omx_aud_dec,OMX_CommandFlush, omx_codec_input_port, NULL);
1265 if (error!=OMX_ErrorNone){
1266 Log::getInstance()->log("Audio", Log::DEBUG, "OMX_Flush codec out failed %x", error);
1271 /* if (!video->CommandFinished(omx_aud_dec,OMX_CommandFlush,omx_codec_input_port)) {
1272 Log::getInstance()->log("Audio", Log::DEBUG, "flush cmd codec input failed");
1277 error=OMX_SendCommand(omx_clock,OMX_CommandFlush, omx_clock_output_port, NULL);
1278 if (error!=OMX_ErrorNone){
1279 Log::getInstance()->log("Audio", Log::DEBUG, "OMX_Flush clock out failed %x", error);
1283 error=OMX_SendCommand(omx_aud_rend,OMX_CommandFlush, omx_rend_clock_port, NULL);
1284 if (error!=OMX_ErrorNone){
1285 Log::getInstance()->log("Audio", Log::DEBUG, "OMX_Flush rend clock failed %x", error);
1288 Log::getInstance()->log("Audio", Log::DEBUG, "deallocatecodecsomx mark 6");
1290 if (!video->CommandFinished(omx_clock,OMX_CommandFlush,omx_clock_output_port) ||
1291 !video->CommandFinished(omx_aud_rend,OMX_CommandFlush,omx_rend_clock_port)) {
1292 Log::getInstance()->log("Audio", Log::DEBUG, "flush cmd clock shed failed");
1295 DestroyInputBufsOMX(); //We have to make sure that no buffers are in use
1296 Log::getInstance()->log("Audio", Log::DEBUG, "deallocatecodecsomx mark 6a");
1297 DeinitDecoderLibAV();
1298 Log::getInstance()->log("Audio", Log::DEBUG, "deallocatecodecsomx mark 7");
1301 if (!video->DisablePort(omx_aud_rend,omx_rend_input_port,true)) {
1302 Log::getInstance()->log("Audio", Log::DEBUG, "Disable Tunnel Port failed 1");
1305 /* if (!video->DisablePort(omx_aud_dec,omx_codec_output_port,true)) {
1306 Log::getInstance()->log("Audio", Log::DEBUG, "Disable Tunnel Port failed 6");
1309 if (!video->DisablePort(omx_aud_dec,omx_codec_input_port,true)) {
1310 Log::getInstance()->log("Audio", Log::DEBUG, "Disable Tunnel Port failed 7");
1314 if (!video->DisablePort(omx_aud_rend,omx_rend_clock_port,true)) {
1315 Log::getInstance()->log("Audio", Log::DEBUG, "Disable Tunnel Port failed 4");
1318 if (!video->DisablePort(omx_clock,omx_clock_output_port,true)) {
1319 Log::getInstance()->log("Audio", Log::DEBUG, "Disable Tunnel Port failed 5");
1324 /* error=OMX_SetupTunnel(omx_aud_dec,omx_codec_output_port,NULL,NULL);
1325 if (error!=OMX_ErrorNone) {
1326 Log::getInstance()->log("Audio", Log::DEBUG, "OMX_Setup tunnel teardown failed %x", error);
1332 error=OMX_SetupTunnel(omx_aud_rend,omx_rend_input_port,NULL,NULL);
1333 if (error!=OMX_ErrorNone) {
1334 Log::getInstance()->log("Audio", Log::DEBUG, "OMX_Setup tunnel teardown failed %x", error);
1338 error=OMX_SetupTunnel(omx_clock,omx_clock_output_port,NULL,NULL);
1339 if (error!=OMX_ErrorNone) {
1340 Log::getInstance()->log("Audio", Log::DEBUG, "OMX_Setup tunnel teardown failed %x", error);
1344 error=OMX_SetupTunnel(omx_aud_rend,omx_rend_clock_port,NULL,NULL);
1345 if (error!=OMX_ErrorNone) {
1346 Log::getInstance()->log("Audio", Log::DEBUG, "OMX_Setup tunnel teardown failed %x", error);
1349 Log::getInstance()->log("Audio", Log::DEBUG, "deallocatecodecsomx mark 8");
1352 //error=OMX_FreeHandle(omx_aud_dec);
1353 error=OMX_FreeHandle(omx_aud_rend);
1354 video->UnlockClock();
1355 video->destroyClock();
1356 omx_aud_rend/*dec*/=NULL;
1357 if (error!=OMX_ErrorNone) {
1358 Log::getInstance()->log("Audio", Log::DEBUG, "FreeHandle failed %d", error);
1362 video->UnlockClock();
1363 DeinitDecoderLibAV();
1365 Log::getInstance()->log("Audio", Log::DEBUG, "leave deallocate codecs OMX");
1372 int AudioOMX::stop()
1374 if (!initted) return 0;
1376 Log::getInstance()->log("Audio", Log::DEBUG, "Audio stop called");
1377 DeAllocateCodecsOMX();
1378 //if (ioctl(fdAudio, AV_SET_AUD_RESET, 0x11) != 0) return 0;
1382 int AudioOMX::mute() {
1385 Log::getInstance()->log("Audio", Log::DEBUG, "MUTE MUTE MUTE");
1387 VideoOMX *vw = (VideoOMX*) Video::getInstance();
1389 OMX_AUDIO_CONFIG_MUTETYPE amute;
1390 memset(&amute, 0, sizeof(amute));
1391 amute.nSize = sizeof(amute);
1392 amute.nVersion.nVersion = OMX_VERSION;
1393 amute.nPortIndex = omx_rend_input_port;
1394 amute.bMute = OMX_TRUE;
1395 OMX_ERRORTYPE error= OMX_SetParameter(omx_aud_rend, OMX_IndexConfigAudioMute,
1397 if (error != OMX_ErrorNone) {
1398 Log::getInstance()->log("Audio", Log::DEBUG,
1399 "Set OMX_IndexConfigAudioMute failed %x %d", error,
1400 omx_rend_input_port);
1410 int AudioOMX::unMute()
1412 if (!initted) return 0;
1414 Log::getInstance()->log("Audio", Log::DEBUG, "MUTE OFF OFF OFF");
1416 VideoOMX *vw = (VideoOMX*) Video::getInstance();
1418 OMX_AUDIO_CONFIG_MUTETYPE amute;
1419 memset(&amute, 0, sizeof(amute));
1420 amute.nSize = sizeof(amute);
1421 amute.nVersion.nVersion = OMX_VERSION;
1422 amute.nPortIndex = omx_rend_input_port;
1423 amute.bMute = OMX_FALSE;
1424 OMX_ERRORTYPE error = OMX_SetParameter(omx_aud_rend, OMX_IndexConfigAudioMute,
1426 if (error != OMX_ErrorNone) {
1427 Log::getInstance()->log("Audio", Log::DEBUG,
1428 "Set OMX_IndexConfigAudioMute failed %x %d", error,
1429 omx_rend_input_port);
1439 int AudioOMX::pause() {
1444 VideoOMX *vw = (VideoOMX*) Video::getInstance();
1447 OMX_ERRORTYPE error;
1448 error = OMX_SendCommand(omx_aud_rend, OMX_CommandFlush,
1449 omx_rend_input_port, NULL);
1450 if (error != OMX_ErrorNone) {
1451 Log::getInstance()->log("Audio", Log::DEBUG,
1452 "OMX_Flush rend in failed %x", error);
1455 if (!vw->ChangeComponentState(omx_aud_rend,OMX_StateIdle)) {
1456 Log::getInstance()->log("Audio", Log::DEBUG, " pause aud_rend idle ChangeComponentState");
1465 int AudioOMX::unPause()
1467 if (!initted) return 0;
1469 paused=false; // may be also change omx clock
1470 VideoOMX *vw = (VideoOMX*) Video::getInstance();
1472 if (!vw->ChangeComponentState(omx_aud_rend,OMX_StateExecuting)) {
1473 Log::getInstance()->log("Audio", Log::DEBUG, " unpause aud_rend idle ChangeComponentState");
1481 int AudioOMX::reset()
1483 if (!initted) return 0;
1485 Log::getInstance()->log("Audio", Log::DEBUG, "reset called");
1486 DeAllocateCodecsOMX();
1488 // if (ioctl(fdAudio, AV_SET_AUD_RESET, 0x11) != 0) return 0;
1489 // Log::getInstance()->log("Audio", Log::DEBUG, "reset back");
1490 // if (ioctl(fdAudio, AV_SET_AUD_PLAY, 0) != 0) return 0;
1496 int AudioOMX::setVolume(int tvolume)
1498 // parameter: 0 for silence, 20 for full
1499 if ((tvolume < 0) || (tvolume > 20)) return 0;
1501 // volume = 2 * (20 - volume);
1502 // Right, that one was rubbish... 0-10 were almost
1503 // inaudible, 11-20 did what should have been done
1504 // over the whole 0-20 range
1510 VideoOMX *vw = (VideoOMX*) Video::getInstance();
1512 OMX_AUDIO_CONFIG_VOLUMETYPE avol;
1513 memset(&avol, 0, sizeof(avol));
1514 avol.nSize = sizeof(avol);
1515 avol.nVersion.nVersion = OMX_VERSION;
1516 avol.nPortIndex = omx_rend_input_port;
1517 avol.bLinear=OMX_FALSE;
1518 avol.sVolume.nValue =(volume-20)*200;
1519 OMX_ERRORTYPE error = OMX_SetParameter(omx_aud_rend, OMX_IndexConfigAudioVolume,
1521 if (error != OMX_ErrorNone) {
1522 Log::getInstance()->log("Audio", Log::DEBUG,
1523 "Set OMX_IndexConfigAudioVolume failed %x %d", error,
1524 omx_rend_input_port);
1534 int AudioOMX::test()
1537 // return ioctl(fdAudio, AV_SET_AUD_STC, &stc);
1539 /* aud_sync_parms_t a;
1543 // int b = ioctl(fdAudio, AV_SET_AUD_DISABLE_SYNC, &a);
1546 /*OK*/ //printf("Audio sync disable = %i\n", b);
1554 unsigned int AudioOMX::AdvanceMpAudioSync(const UCHAR *data,unsigned int size,unsigned int *framesize)
1556 if (size<=2) return size; // silly;
1557 unsigned int test=0;
1559 while (test+1<size) {
1560 if (data[test]==0xFF && (data[test+1] &0xe0)==0xe0) return test; // probably FrameSync
1566 unsigned int AudioOMX::AdvanceAc3AudioSync(const UCHAR *data,unsigned int size,unsigned int *framesize)
1568 if (size<=4) return size; // silly;
1569 const int frm_size_tab[] = { 64, 64, 80, 80, 96, 96, 112, 112, 128, 128,
1570 160, 160, 192, 192, 224, 224, 256, 256, 320, 320, 384, 384, 448,
1571 448, 512, 512, 640, 640, 768, 768, 896, 896, 1024, 1024, 1152,
1572 1152, 1280, 1280, };
1573 unsigned int test=0;
1574 *framesize=20000; //if we do not find a start code do not decompress
1575 while (test+4<size) {
1576 if (data[test]==0x0B && data[test+1]==0x77) {
1577 // now figure out the length of the frame
1578 unsigned char code=data[test+4];
1579 unsigned char fscod=(code& 0xC0)>>6;
1580 unsigned char frmsize=(code &0x3f);
1581 if (fscod!=0) Log::getInstance()->log("Audio", Log::DEBUG, "warning we only support 48 KHz sampling rate");
1582 *framesize=frm_size_tab[frmsize]*2;
1583 return test; // probably FrameSync
1590 unsigned int AudioOMX::AdvanceAacLatmAudioSync(const UCHAR *data,unsigned int size,unsigned int *framesize)
1592 if (size<=4) return size; // silly;
1593 unsigned int test=0;
1594 *framesize=20000; //if we do not find a start code do not decompress
1595 while (test+4<size) {
1596 if (data[test] ==0x56 && (data[test+1]& 0xe0)==0xe0) {
1597 // now figure out the length of the frame
1598 unsigned int length= ((0x1f & data[test+1])<<8) | data[test+2];
1600 return test; // probably FrameSync
1608 void AudioOMX::PrepareMediaSample(const MediaPacketList& mplist,UINT samplepos)
1610 packet = mplist.front();
1613 UINT AudioOMX::DeliverMediaSample(UCHAR* buffer, UINT* samplepos) {
1614 DeliverMediaPacket(packet, buffer, samplepos);
1615 if (*samplepos == packet.length) {
1623 long long AudioOMX::correctAudioLatency(long long pts,int addsamples,int srate) {
1625 VideoOMX *video = (VideoOMX*) Video::getInstance();
1627 OMX_PARAM_U32TYPE audio_lat;
1628 OMX_ERRORTYPE error;
1629 memset(&audio_lat, 0, sizeof(audio_lat));
1630 audio_lat.nSize = sizeof(audio_lat);
1631 audio_lat.nVersion.nVersion = OMX_VERSION;
1632 audio_lat.nPortIndex = omx_rend_input_port;
1634 error = OMX_GetConfig(omx_aud_rend, OMX_IndexConfigAudioRenderingLatency,
1636 video->UnlockClock();
1637 if (error != OMX_ErrorNone) {
1638 Log::getInstance()->log("Audio", Log::DEBUG,
1639 "Init OMX_IndexConfigAudioRenderingLatencyfailed %x %d", error,
1640 omx_rend_input_port);
1641 return pts; // no correction in case of error
1643 /*Log::getInstance()->log("Audio", Log::DEBUG, "Current audio latency %d",
1646 long long workpts=0;
1647 workpts+=addsamples;
1648 workpts-=audio_lat.nU32;
1649 workpts*=10LL*1000LL*1000LL;
1650 workpts=workpts/((long long)srate); //one second /samplerate
1658 UINT AudioOMX::DeliverMediaPacket(MediaPacket packet, const UCHAR* buffer,
1660 /*First Check, if we have an audio sample*/
1661 VideoOMX *vw = (VideoOMX*) Video::getInstance();
1663 OMX_ERRORTYPE error;
1664 Log *logger=Log::getInstance();
1665 if (vw->InIframemode()) {
1668 return 0; //Not in iframe mode!
1671 if (!omx_running) return 0; // if we are not runnig do not do this
1672 if (paused) return 0; //Block if we pause
1673 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 1");
1675 //Log::getInstance()->log("Audio", Log::DEBUG, "DeliverMediaPacketOMX time %lld",packet.presentation_time);
1677 /* if (packet.synched && packet.presentation_time <= 0) {
1678 *samplepos = packet.length;
1679 firstsynched = false;
1681 Log::getInstance()->log("Audio", Log::DEBUG,
1682 "DeliverMediaPacketOMX Frameskip");
1683 return packet.length;
1686 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 2");
1688 UINT headerstrip = 0;
1689 if (packet.disconti) {
1690 firstsynched = false;
1691 decompress_buffer_filled=0;
1692 if (cur_input_buf_omx) {
1693 OMX_ERRORTYPE error = vw->ProtOMXEmptyThisBuffer(omx_aud_rend/*dec*/,
1695 if (error != OMX_ErrorNone) {
1696 Log::getInstance()->log("Audio", Log::DEBUG,
1697 "OMX_EmptyThisBuffer 1 failed %x", error);
1699 cur_input_buf_omx = NULL;
1703 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 3");
1704 if (packet.type != lastAType) {//Format Change //Push data out !
1705 firstsynched = false;
1707 lastAType = packet.type;
1708 decompress_buffer_filled=0;
1710 if (cur_input_buf_omx) {
1711 OMX_ERRORTYPE error = vw->ProtOMXEmptyThisBuffer(omx_aud_rend/*dec*/,
1713 if (error != OMX_ErrorNone) {
1714 Log::getInstance()->log("Audio", Log::DEBUG,
1715 "OMX_EmptyThisBuffer 2 failed %x", error);
1717 cur_input_buf_omx = NULL;
1721 pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, &oldcancelstate);
1722 pthread_setcanceltype(PTHREAD_CANCEL_DEFERRED, &oldcanceltype);
1724 if (!ChangeAudioPortConfig(true)) {
1725 Log::getInstance()->log("Audio", Log::DEBUG,
1726 "Changing audio port config failed", error);
1729 pthread_setcancelstate(oldcancelstate, NULL);
1730 pthread_setcanceltype(oldcanceltype, NULL);
1734 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 4");
1736 /*Inspect PES-Header */
1737 if (*samplepos == 0 && packet.type != MPTYPE_MPEG_AUDIO_LAYER3) {//stripheader
1738 headerstrip = buffer[packet.pos_buffer + 8] + 9;
1739 if (packet.type == MPTYPE_AC3)
1740 headerstrip += 4; //skip ac3 bytes
1741 *samplepos += headerstrip;
1742 if (packet.synched) {
1743 if (cur_input_buf_omx) {
1744 //cur_input_buf_omx->nFlags |= OMX_BUFFERFLAG_ENDOFFRAME;
1745 OMX_ERRORTYPE error = vw->ProtOMXEmptyThisBuffer(omx_aud_rend/*dec*/,
1747 if (error != OMX_ErrorNone) {
1748 Log::getInstance()->log("Audio", Log::DEBUG,
1749 "OMX_EmptyThisBuffer 3 failed %x", error);
1751 //vw->AdjustAudioPTS(correctAudioLatency(lastreftimeOMX,cur_input_buf_omx->nFilledLen/(2*2),48000));
1753 cur_input_buf_omx = NULL;//write out old data
1755 firstsynched = true;
1756 //decompress_buffer_filled=0;
1758 if (!firstsynched) {//
1759 *samplepos = packet.length;//if we have not processed at least one
1760 decompress_buffer_filled=0;
1761 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 5");
1762 return packet.length;//synched packet ignore it!
1766 if (!cur_input_buf_omx) {
1767 input_bufs_omx_mutex.Lock();
1768 if (input_bufs_omx_free.size()==0) {
1769 input_bufs_omx_mutex.Unlock();
1770 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 6");
1771 //Log::getInstance()->log("Audio", Log::DEBUG, "Deliver MediaPacket no free sample");
1772 return 0; // we do not have a free media sample
1775 cur_input_buf_omx=input_bufs_omx_free.front();
1776 cur_input_buf_omx->nFilledLen=0;
1777 cur_input_buf_omx->nOffset=0;
1778 cur_input_buf_omx->nTimeStamp=VideoOMX::intToOMXTicks(0);
1779 input_bufs_omx_free.pop_front();
1780 input_bufs_omx_mutex.Unlock();
1782 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 7");
1784 if (cur_input_buf_omx->nFilledLen == 0) {//will only be changed on first packet
1785 if (packet.synched) {
1786 //Log::getInstance()->log("Audio", Log::DEBUG,
1787 // "packet synched marker");
1789 //lastreftimePTS=packet.pts;
1790 if (omx_first_frame) { // TODO time
1791 cur_input_buf_omx->nFlags = OMX_BUFFERFLAG_STARTTIME;
1792 Log::getInstance()->log("Audio", Log::DEBUG, "Starttime");
1793 omx_first_frame = false;
1795 cur_input_buf_omx->nFlags = 0;
1796 //cur_input_buf_omx->nFlags|=OMX_BUFFERFLAG_TIME_UNKNOWN;
1798 lastreftimeOMX = packet.presentation_time;
1799 // Log::getInstance()->log("Audio", Log::DEBUG,
1800 // "Time code %lld pts %lld dts %lld", lastreftimeOMX, packet.pts,packet.dts);
1801 lastreftimePTS = packet.pts;
1802 cur_input_buf_omx->nTimeStamp = VideoOMX::intToOMXTicks(lastreftimeOMX/10LL); // the clock component is faulty;
1804 // Log::getInstance()->log("Audio", Log::DEBUG,
1805 // "packet NOT synched marker");
1806 cur_input_buf_omx->nFlags = OMX_BUFFERFLAG_TIME_UNKNOWN;
1807 cur_input_buf_omx->nTimeStamp = VideoOMX::intToOMXTicks(0);
1810 if (packet.disconti || achange) {
1811 cur_input_buf_omx->nFlags |= OMX_BUFFERFLAG_DISCONTINUITY;
1812 //mp23codec_context_libav->frame_size=-1;
1813 //ac3codec_context_libav->frame_size=-1;
1817 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 8");
1819 if (*samplepos>packet.length) *samplepos=0; //propably the thread got interrupted and sample is not valid any more!
1820 unsigned int haveToCopy=packet.length-*samplepos;
1823 while (haveToCopy>0) {
1824 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 9");
1826 unsigned int gotframesize=0;
1828 switch (packet.type) {
1829 case MPTYPE_MPEG_AUDIO:
1830 case MPTYPE_MPEG_AUDIO_LAYER3: {
1831 adv = AdvanceMpAudioSync(buffer+packet.pos_buffer+*samplepos,
1832 haveToCopy,&gotframesize);
1836 case MPTYPE_AC3_PRE13: {
1837 adv = AdvanceAc3AudioSync(buffer+packet.pos_buffer+*samplepos,
1838 haveToCopy,&gotframesize);
1842 case MPTYPE_AAC_LATM: {
1843 adv = AdvanceAacLatmAudioSync(buffer+packet.pos_buffer+*samplepos,
1844 haveToCopy,&gotframesize);
1848 if (adv!=haveToCopy) {
1853 *samplepos=packet.length; //no ac3 sync byte
1854 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 10");
1855 return packet.length;
1858 // so everything is fine now do a memcpy
1859 int cancopy=min(haveToCopy,cur_input_buf_omx->nAllocLen-cur_input_buf_omx->nFilledLen);
1860 memcpy(cur_input_buf_omx->pBuffer+cur_input_buf_omx->nFilledLen,buffer+packet.pos_buffer+*samplepos,cancopy);
1861 haveToCopy-=cancopy;
1862 cur_input_buf_omx->nFilledLen+=cancopy;
1863 *samplepos+=cancopy;
1864 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 11");
1866 error = vw->ProtOMXEmptyThisBuffer(omx_aud_rend/*dec*/, cur_input_buf_omx);
1867 if (error != OMX_ErrorNone) {
1868 Log::getInstance()->log("Audio", Log::DEBUG,
1869 "OMX_EmptyThisBuffer 5 failed %x", error);
1871 cur_input_buf_omx=NULL;
1874 input_bufs_omx_mutex.Lock();
1875 if (input_bufs_omx_free.size()==0) {
1876 input_bufs_omx_mutex.Unlock();
1877 // Log::getInstance()->log("Audio", Log::DEBUG, "Deliver MediaPacket no free sample2");
1878 return *samplepos; // we do not have a free media sample
1880 cur_input_buf_omx=input_bufs_omx_free.front();
1881 cur_input_buf_omx->nFilledLen=0;
1882 cur_input_buf_omx->nOffset=0;
1883 cur_input_buf_omx->nFlags=OMX_BUFFERFLAG_TIME_UNKNOWN;
1884 cur_input_buf_omx->nTimeStamp=VideoOMX::intToOMXTicks(0);
1885 input_bufs_omx_free.pop_front();
1886 input_bufs_omx_mutex.Unlock();
1888 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 12");
1891 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 13");
1899 AVCodecContext *current_context;
1900 switch (packet.type) {
1901 case MPTYPE_MPEG_AUDIO:
1902 case MPTYPE_MPEG_AUDIO_LAYER3: {
1903 current_context = mp23codec_context_libav;
1904 if (current_context->frame_size<0) framesize=1152; //Maximum framesize
1905 else framesize=current_context->frame_size;
1907 case MPTYPE_AAC_LATM: {
1908 current_context = aaclatmcodec_context_libav;
1911 case MPTYPE_AC3_PRE13: {
1912 current_context = ac3codec_context_libav;
1916 if (decompress_buffer_filled) { // have a remaining paket
1917 incoming_paket_libav.data =(uint8_t*) decompress_buffer;
1918 memcpy(decompress_buffer+decompress_buffer_filled,
1919 buffer+packet.pos_buffer+*samplepos,
1920 min(haveToCopy,decompress_buffer_size-decompress_buffer_filled));
1921 incoming_paket_libav.size = decompress_buffer_filled
1922 +min(haveToCopy,decompress_buffer_size-decompress_buffer_filled);
1923 //Log::getInstance()->log("Audio", Log::DEBUG,"Use saved audio buffer %d",packet.type);
1925 incoming_paket_libav.data =(uint8_t*) buffer+packet.pos_buffer+*samplepos;
1926 incoming_paket_libav.size = haveToCopy;
1928 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 18");
1930 while (haveToCopy> 0 && errcount<3) {
1932 //Log::getInstance()->log("Audio", Log::DEBUG,"libav in %d %d",framesize,current_context->frame_size);
1933 //Log::getInstance()->log("Audio", Log::DEBUG, "libav in %d %d",
1934 // framesize, current_context->frame_size);
1936 bool donotdecompress=false;
1937 unsigned int gotframesize=0;
1938 if (!decompress_buffer_filled) { // only do this if no old data is present
1940 switch (packet.type) {
1941 case MPTYPE_MPEG_AUDIO:
1942 case MPTYPE_MPEG_AUDIO_LAYER3: {
1943 adv = AdvanceMpAudioSync(incoming_paket_libav.data,
1944 incoming_paket_libav.size,&gotframesize);
1948 case MPTYPE_AC3_PRE13: {
1949 adv = AdvanceAc3AudioSync(incoming_paket_libav.data,
1950 incoming_paket_libav.size,&gotframesize);
1953 case MPTYPE_AAC_LATM: {
1954 adv = AdvanceAacLatmAudioSync(incoming_paket_libav.data,
1955 incoming_paket_libav.size,&gotframesize);
1960 incoming_paket_libav.data += adv;
1961 incoming_paket_libav.size-=adv;
1964 /*if (current_context->frame_size>0) framesize=min(current_context->frame_size,haveToCopy);
1965 else*/ framesize=haveToCopy;
1966 //Log::getInstance()->log("Audio", Log::DEBUG,"Advance by %d %d from %d",adv,packet.type,*samplepos );
1967 if (haveToCopy <= 0) {
1968 // Log::getInstance()->log("Audio", Log::DEBUG,"No sync code in packet remove %d",packet.type);
1969 *samplepos=packet.length;
1970 return packet.length;
1976 if (gotframesize>0 && gotframesize>haveToCopy) {
1977 donotdecompress=true;
1978 errcount=100; // exit loop
1980 // else Log::getInstance()->log("Audio", Log::DEBUG,"Loop run" );
1982 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 19");
1983 if (!donotdecompress) {
1986 pthread_testcancel();
1987 pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, &oldcancelstate);
1988 pthread_setcanceltype(PTHREAD_CANCEL_DEFERRED, &oldcanceltype);
1990 if (!omx_running || !mp23codec_context_libav
1991 || !ac3codec_context_libav) {
1992 libav_mutex.Unlock();
1995 libav_mutex.Unlock();
1996 // Log::getInstance()->log("Audio", Log::DEBUG,"libav out");
1997 len = avcodec_decode_audio4(current_context, decode_frame_libav,
1998 &gotta, &incoming_paket_libav);
1999 //Log::getInstance()->log("Audio", Log::DEBUG, "libav out1");
2000 pthread_setcancelstate(oldcancelstate, NULL);
2001 pthread_setcanceltype(oldcanceltype, NULL);
2002 pthread_testcancel();
2008 //Log::getInstance()->log("Audio", Log::DEBUG, "libav out2");
2009 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 20");
2011 libav_mutex.Unlock();
2015 if (decompress_buffer_filled) { // reset to normal decoding
2017 Log::getInstance()->log("Audio", Log::DEBUG,"saved audio: %d",len);
2018 haveToCopy -= min(len-decompress_buffer_filled,0);
2019 *samplepos += min(len-decompress_buffer_filled,0);
2020 //if (current_context->frame_size>0) framesize=min(current_context->frame_size,haveToCopy);
2021 /*else*/ framesize=haveToCopy;
2023 framesize=haveToCopy;
2025 incoming_paket_libav.data =(uint8_t*) buffer+packet.pos_buffer+*samplepos;
2027 decompress_buffer_filled=0;
2031 incoming_paket_libav.data += len;
2035 /*if (current_context->frame_size>0) framesize=min(current_context->frame_size,haveToCopy);
2036 else*/framesize=haveToCopy;
2039 framesize=haveToCopy;
2042 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 21");
2044 incoming_paket_libav.size =framesize;
2046 //Log::getInstance()->log("Audio", Log::DEBUG,
2048 int dsize = av_samples_get_buffer_size(NULL,
2049 current_context->channels, decode_frame_libav->nb_samples,
2050 current_context->sample_fmt, 1);
2051 if ((cur_input_buf_omx->nFilledLen + dsize)
2052 > cur_input_buf_omx->nAllocLen ) {
2053 // I doubt that this will ever happen
2054 // Log::getInstance()->log("Audio", Log::DEBUG,
2055 // "P 2 Time code %lld pts %lld", lastreftimeOMX, packet.pts);
2056 OMX_ERRORTYPE error = vw->ProtOMXEmptyThisBuffer(omx_aud_rend/*dec*/,
2058 if (error != OMX_ErrorNone) {
2059 Log::getInstance()->log("Audio", Log::DEBUG,
2060 "OMX_EmptyThisBuffer 4 failed %x", error);
2062 cur_input_buf_omx = NULL;
2064 if (!cur_input_buf_omx) {
2066 while (count < 10 && omx_running) {
2068 input_bufs_omx_mutex.Lock();
2069 if (input_bufs_omx_free.size() == 0) {
2070 input_bufs_omx_mutex.Unlock();
2071 // Log::getInstance()->log("Audio", Log::DEBUG,
2072 // "Deliver MediaPacket no free sample");
2074 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark22");
2075 if (!omx_running) return *samplepos;
2076 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 23");
2079 cur_input_buf_omx = input_bufs_omx_free.front();
2080 cur_input_buf_omx->nFilledLen = 0;
2081 cur_input_buf_omx->nOffset = 0;
2082 cur_input_buf_omx->nTimeStamp = VideoOMX::intToOMXTicks(0);
2083 cur_input_buf_omx->nFlags=OMX_BUFFERFLAG_TIME_UNKNOWN;
2084 input_bufs_omx_free.pop_front();
2085 input_bufs_omx_mutex.Unlock();
2088 if (!cur_input_buf_omx) return *samplepos;
2093 //Log::getInstance()->log("Audio", Log::DEBUG,"memcpy in %d %d %d" ,dsize,current_context->sample_rate,cur_input_buf_omx->nFilledLen);
2094 memcpy(cur_input_buf_omx->pBuffer + cur_input_buf_omx->nFilledLen,
2095 decode_frame_libav->data[0], dsize);
2096 //Log::getInstance()->log("Audio", Log::DEBUG,"memcpy out");
2097 cur_input_buf_omx->nFilledLen += dsize;
2099 //Log::getInstance()->log("Audio", Log::DEBUG,"Incomplete mpeg frames in pes packet %d %d",incoming_paket_libav.size,packet.length);
2100 /* uint8_t a1=incoming_paket_libav.data[0];
2101 uint8_t a2=incoming_paket_libav.data[1];
2102 uint8_t a3=incoming_paket_libav.data[2];
2103 uint8_t a4=incoming_paket_libav.data[3];*/
2104 // Log::getInstance()->log("Audio", Log::DEBUG,"Header %x %x %x %x",a1,a2,
2109 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 24");
2110 decompress_buffer_filled=0;
2112 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);
2113 memcpy(decompress_buffer,incoming_paket_libav.data,min(haveToCopy,decompress_buffer_size));
2115 decompress_buffer_filled=min(haveToCopy,decompress_buffer_size);
2119 if (cur_input_buf_omx->nFilledLen) {
2120 //Log::getInstance()->log("Audio", Log::DEBUG,
2121 // "P 3 Time code %lld pts %lld", lastreftimeOMX, packet.pts);
2122 error = vw->ProtOMXEmptyThisBuffer(omx_aud_rend/*dec*/, cur_input_buf_omx);
2123 if (error != OMX_ErrorNone) {
2124 Log::getInstance()->log("Audio", Log::DEBUG,
2125 "OMX_EmptyThisBuffer 5 failed %x", error);
2127 //if (packet.synched) vw->AdjustAudioPTS(correctAudioLatency(lastreftimeOMX,cur_input_buf_omx->nFilledLen/(2*2),48000));
2128 cur_input_buf_omx = NULL;
2133 //Log::getInstance()->log("Audio", Log::DEBUG, "DMP mark 25");
2135 *samplepos=packet.length;
2136 return packet.length;
2142 long long AudioOMX::SetStartOffset(long long curreftime, bool *rsync){
2143 VideoOMX *vw=(VideoOMX*)Video::getInstance();
2144 return vw->SetStartAudioOffset(curreftime,rsync);
2147 void AudioOMX::ResetTimeOffsets() {
2148 VideoOMX *vw=(VideoOMX*)Video::getInstance();
2149 vw->ResetTimeOffsets();