00001
00031 #include <omxcore.h>
00032 #include <omx_base_audio_port.h>
00033 #include <omx_maddec_component.h>
00034 #include <id3tag.h>
00035
00036 #define MIN(X,Y) ((X) < (Y) ? (X) : (Y))
00037
00039 #define MAX_COMPONENT_MADDEC 4
00040
00042 static OMX_U32 noMadDecInstance=0;
00043
00044
00047 #define TEMP_BUF_COPY_SPACE 1024
00048
00050 #define TEMP_BUFFER_SIZE DEFAULT_IN_BUFFER_SIZE * 2
00051
00053 OMX_ERRORTYPE omx_maddec_component_madLibInit(omx_maddec_component_PrivateType* omx_maddec_component_Private) {
00054
00055 mad_stream_init (omx_maddec_component_Private->stream);
00056 mad_frame_init (omx_maddec_component_Private->frame);
00057 mad_synth_init (omx_maddec_component_Private->synth);
00058 tsem_up (omx_maddec_component_Private->madDecSyncSem);
00059 return OMX_ErrorNone;
00060 }
00061
00062
00064 void omx_maddec_component_madLibDeInit(omx_maddec_component_PrivateType* omx_maddec_component_Private) {
00065
00066 mad_synth_finish (omx_maddec_component_Private->synth);
00067 mad_frame_finish (omx_maddec_component_Private->frame);
00068 mad_stream_finish (omx_maddec_component_Private->stream);
00069 }
00070
00076 OMX_ERRORTYPE omx_maddec_component_Constructor(OMX_COMPONENTTYPE *openmaxStandComp, OMX_STRING cComponentName) {
00077
00078 OMX_ERRORTYPE err = OMX_ErrorNone;
00079 omx_maddec_component_PrivateType* omx_maddec_component_Private;
00080 omx_base_audio_PortType *inPort,*outPort;
00081 OMX_U32 i;
00082
00083 if (!openmaxStandComp->pComponentPrivate) {
00084 openmaxStandComp->pComponentPrivate = calloc(1, sizeof(omx_maddec_component_PrivateType));
00085 if(openmaxStandComp->pComponentPrivate==NULL) {
00086 return OMX_ErrorInsufficientResources;
00087 }
00088 } else {
00089 DEBUG(DEB_LEV_FUNCTION_NAME, "In %s, Error Component %x Already Allocated\n",
00090 __func__, (int)openmaxStandComp->pComponentPrivate);
00091 }
00092
00093 omx_maddec_component_Private = openmaxStandComp->pComponentPrivate;
00094 omx_maddec_component_Private->ports = NULL;
00095
00099 err = omx_base_filter_Constructor(openmaxStandComp, cComponentName);
00100
00101 DEBUG(DEB_LEV_SIMPLE_SEQ, "constructor of mad decoder component is called\n");
00102
00107 omx_maddec_component_Private->sPortTypesParam[OMX_PortDomainAudio].nStartPortNumber = 0;
00108 omx_maddec_component_Private->sPortTypesParam[OMX_PortDomainAudio].nPorts = 2;
00109
00111 if (omx_maddec_component_Private->sPortTypesParam[OMX_PortDomainAudio].nPorts && !omx_maddec_component_Private->ports) {
00112 omx_maddec_component_Private->ports = calloc(omx_maddec_component_Private->sPortTypesParam[OMX_PortDomainAudio].nPorts, sizeof(omx_base_PortType *));
00113 if (!omx_maddec_component_Private->ports) {
00114 return OMX_ErrorInsufficientResources;
00115 }
00116 for (i=0; i < omx_maddec_component_Private->sPortTypesParam[OMX_PortDomainAudio].nPorts; i++) {
00117 omx_maddec_component_Private->ports[i] = calloc(1, sizeof(omx_base_audio_PortType));
00118 if (!omx_maddec_component_Private->ports[i]) {
00119 return OMX_ErrorInsufficientResources;
00120 }
00121 }
00122 }
00123
00124 base_audio_port_Constructor(openmaxStandComp, &omx_maddec_component_Private->ports[0], 0, OMX_TRUE);
00125 base_audio_port_Constructor(openmaxStandComp, &omx_maddec_component_Private->ports[1], 1, OMX_FALSE);
00126
00127
00129 inPort = (omx_base_audio_PortType *) omx_maddec_component_Private->ports[OMX_BASE_FILTER_INPUTPORT_INDEX];
00130
00131 inPort->sPortParam.nBufferSize = DEFAULT_IN_BUFFER_SIZE;
00132 strcpy(inPort->sPortParam.format.audio.cMIMEType, "audio/mpeg");
00133 inPort->sPortParam.format.audio.eEncoding = OMX_AUDIO_CodingMP3;
00134
00135 inPort->sAudioParam.eEncoding = OMX_AUDIO_CodingMP3;
00136
00137 setHeader(&omx_maddec_component_Private->pAudioMp3, sizeof(OMX_AUDIO_PARAM_MP3TYPE));
00138 omx_maddec_component_Private->pAudioMp3.nPortIndex = 0;
00139 omx_maddec_component_Private->pAudioMp3.nChannels = 2;
00140 omx_maddec_component_Private->pAudioMp3.nBitRate = 28000;
00141 omx_maddec_component_Private->pAudioMp3.nSampleRate = 44100;
00142 omx_maddec_component_Private->pAudioMp3.nAudioBandWidth = 0;
00143 omx_maddec_component_Private->pAudioMp3.eChannelMode = OMX_AUDIO_ChannelModeStereo;
00144 omx_maddec_component_Private->pAudioMp3.eFormat=OMX_AUDIO_MP3StreamFormatMP1Layer3;
00145
00147 outPort = (omx_base_audio_PortType *) omx_maddec_component_Private->ports[OMX_BASE_FILTER_OUTPUTPORT_INDEX];
00148 outPort->sPortParam.format.audio.eEncoding = OMX_AUDIO_CodingPCM;
00149 outPort->sPortParam.nBufferSize = DEFAULT_OUT_BUFFER_SIZE;
00150
00151 outPort->sAudioParam.eEncoding = OMX_AUDIO_CodingPCM;
00152
00154 setHeader(&omx_maddec_component_Private->pAudioPcmMode, sizeof(OMX_AUDIO_PARAM_PCMMODETYPE));
00155 omx_maddec_component_Private->pAudioPcmMode.nPortIndex = 1;
00156 omx_maddec_component_Private->pAudioPcmMode.nChannels = 2;
00157 omx_maddec_component_Private->pAudioPcmMode.eNumData = OMX_NumericalDataSigned;
00158 omx_maddec_component_Private->pAudioPcmMode.eEndian = OMX_EndianLittle;
00159 omx_maddec_component_Private->pAudioPcmMode.bInterleaved = OMX_TRUE;
00160 omx_maddec_component_Private->pAudioPcmMode.nBitPerSample = 16;
00161 omx_maddec_component_Private->pAudioPcmMode.nSamplingRate = 44100;
00162 omx_maddec_component_Private->pAudioPcmMode.ePCMMode = OMX_AUDIO_PCMModeLinear;
00163 omx_maddec_component_Private->pAudioPcmMode.eChannelMapping[0] = OMX_AUDIO_ChannelLF;
00164 omx_maddec_component_Private->pAudioPcmMode.eChannelMapping[1] = OMX_AUDIO_ChannelRF;
00165
00167 if(!strcmp(cComponentName, AUDIO_DEC_MP3_NAME)) {
00168 omx_maddec_component_Private->audio_coding_type = OMX_AUDIO_CodingMP3;
00169 } else if (!strcmp(cComponentName, AUDIO_DEC_BASE_NAME)) {
00170 omx_maddec_component_Private->audio_coding_type = OMX_AUDIO_CodingUnused;
00171 } else {
00172
00173 return OMX_ErrorInvalidComponentName;
00174 }
00176 if(!omx_maddec_component_Private->madDecSyncSem) {
00177 omx_maddec_component_Private->madDecSyncSem = malloc(sizeof(tsem_t));
00178 if(omx_maddec_component_Private->madDecSyncSem == NULL) {
00179 return OMX_ErrorInsufficientResources;
00180 }
00181 tsem_init(omx_maddec_component_Private->madDecSyncSem, 0);
00182 }
00183
00187 omx_maddec_component_Private->maddecReady = OMX_FALSE;
00188 omx_maddec_component_Private->BufferMgmtCallback = omx_maddec_component_BufferMgmtCallback;
00189 omx_maddec_component_Private->messageHandler = omx_mad_decoder_MessageHandler;
00190 omx_maddec_component_Private->destructor = omx_maddec_component_Destructor;
00191 openmaxStandComp->SetParameter = omx_maddec_component_SetParameter;
00192 openmaxStandComp->GetParameter = omx_maddec_component_GetParameter;
00193
00194 noMadDecInstance++;
00195
00196 if(noMadDecInstance>MAX_COMPONENT_MADDEC)
00197 return OMX_ErrorInsufficientResources;
00198
00200 omx_maddec_component_Private->stream = malloc (sizeof(struct mad_stream));
00201 omx_maddec_component_Private->synth = malloc (sizeof(struct mad_synth));
00202 omx_maddec_component_Private->frame = malloc (sizeof(struct mad_frame));
00203
00204 return err;
00205 }
00206
00208 void omx_maddec_component_SetInternalParameters(OMX_COMPONENTTYPE *openmaxStandComp) {
00209
00210 omx_maddec_component_PrivateType* omx_maddec_component_Private;
00211 omx_base_audio_PortType *pPort;;
00212
00213 omx_maddec_component_Private = openmaxStandComp->pComponentPrivate;
00214
00216 strcpy(omx_maddec_component_Private->ports[OMX_BASE_FILTER_INPUTPORT_INDEX]->sPortParam.format.audio.cMIMEType, "audio/mpeg");
00217 omx_maddec_component_Private->ports[OMX_BASE_FILTER_INPUTPORT_INDEX]->sPortParam.format.audio.eEncoding = OMX_AUDIO_CodingMP3;
00218
00219 setHeader(&omx_maddec_component_Private->pAudioMp3, sizeof(OMX_AUDIO_PARAM_MP3TYPE));
00220 omx_maddec_component_Private->pAudioMp3.nPortIndex = 0;
00221 omx_maddec_component_Private->pAudioMp3.nChannels = 2;
00222 omx_maddec_component_Private->pAudioMp3.nBitRate = 28000;
00223 omx_maddec_component_Private->pAudioMp3.nSampleRate = 44100;
00224 omx_maddec_component_Private->pAudioMp3.nAudioBandWidth = 0;
00225 omx_maddec_component_Private->pAudioMp3.eChannelMode = OMX_AUDIO_ChannelModeStereo;
00226 omx_maddec_component_Private->pAudioMp3.eFormat=OMX_AUDIO_MP3StreamFormatMP1Layer3;
00227
00228 pPort = (omx_base_audio_PortType *) omx_maddec_component_Private->ports[OMX_BASE_FILTER_INPUTPORT_INDEX];
00229 setHeader(&pPort->sAudioParam, sizeof(OMX_AUDIO_PARAM_PORTFORMATTYPE));
00230 pPort->sAudioParam.nPortIndex = 0;
00231 pPort->sAudioParam.nIndex = 0;
00232 pPort->sAudioParam.eEncoding = OMX_AUDIO_CodingMP3;
00233
00234 }
00235
00236
00238 OMX_ERRORTYPE omx_maddec_component_Destructor(OMX_COMPONENTTYPE *openmaxStandComp) {
00239
00240 omx_maddec_component_PrivateType* omx_maddec_component_Private = openmaxStandComp->pComponentPrivate;
00241 OMX_U32 i;
00242
00243 if(omx_maddec_component_Private->madDecSyncSem) {
00244 tsem_deinit(omx_maddec_component_Private->madDecSyncSem);
00245 free(omx_maddec_component_Private->madDecSyncSem);
00246 omx_maddec_component_Private->madDecSyncSem = NULL;
00247 }
00248
00250 if(omx_maddec_component_Private->stream != NULL) {
00251 free(omx_maddec_component_Private->stream);
00252 omx_maddec_component_Private->stream = NULL;
00253 }
00254 if(omx_maddec_component_Private->synth != NULL) {
00255 free(omx_maddec_component_Private->synth);
00256 omx_maddec_component_Private->synth = NULL;
00257 }
00258 if(omx_maddec_component_Private->frame != NULL) {
00259 free(omx_maddec_component_Private->frame);
00260 omx_maddec_component_Private->frame = NULL;
00261 }
00262
00263
00264 if (omx_maddec_component_Private->ports) {
00265 for (i=0; i < omx_maddec_component_Private->sPortTypesParam[OMX_PortDomainAudio].nPorts; i++) {
00266 if(omx_maddec_component_Private->ports[i])
00267 omx_maddec_component_Private->ports[i]->PortDestructor(omx_maddec_component_Private->ports[i]);
00268 }
00269 free(omx_maddec_component_Private->ports);
00270 omx_maddec_component_Private->ports=NULL;
00271 }
00272
00273 DEBUG(DEB_LEV_FUNCTION_NAME, "Destructor of mad decoder component is called\n");
00274
00275 omx_base_filter_Destructor(openmaxStandComp);
00276
00277 noMadDecInstance--;
00278
00279 return OMX_ErrorNone;
00280
00281 }
00282
00284 OMX_ERRORTYPE omx_maddec_component_Init(OMX_COMPONENTTYPE *openmaxStandComp) {
00285
00286 omx_maddec_component_PrivateType* omx_maddec_component_Private = openmaxStandComp->pComponentPrivate;
00287 OMX_ERRORTYPE err = OMX_ErrorNone;
00288
00290 omx_maddec_component_Private->temporary_buffer = malloc(sizeof(OMX_BUFFERHEADERTYPE));
00291 omx_maddec_component_Private->temporary_buffer->pBuffer = malloc(DEFAULT_IN_BUFFER_SIZE*2);
00292 memset(omx_maddec_component_Private->temporary_buffer->pBuffer, 0, DEFAULT_IN_BUFFER_SIZE*2);
00293
00294 omx_maddec_component_Private->temp_input_buffer = omx_maddec_component_Private->temporary_buffer->pBuffer;
00295 omx_maddec_component_Private->temporary_buffer->nFilledLen=0;
00296 omx_maddec_component_Private->temporary_buffer->nOffset=0;
00297
00298 omx_maddec_component_Private->isFirstBuffer = 1;
00299 omx_maddec_component_Private->isNewBuffer = 1;
00300
00301 return err;
00302 }
00303
00305 OMX_ERRORTYPE omx_maddec_component_Deinit(OMX_COMPONENTTYPE *openmaxStandComp) {
00306
00307 omx_maddec_component_PrivateType* omx_maddec_component_Private = openmaxStandComp->pComponentPrivate;
00308 OMX_ERRORTYPE err = OMX_ErrorNone;
00309
00310 if (omx_maddec_component_Private->maddecReady) {
00311 omx_maddec_component_madLibDeInit(omx_maddec_component_Private);
00312 omx_maddec_component_Private->maddecReady = OMX_FALSE;
00313 }
00314
00315
00316 omx_maddec_component_Private->temporary_buffer->pBuffer = omx_maddec_component_Private->temp_input_buffer;
00317 DEBUG(DEB_LEV_SIMPLE_SEQ, "Freeing Temporary Buffer\n");
00318
00319 if(omx_maddec_component_Private->temporary_buffer->pBuffer) {
00320 free(omx_maddec_component_Private->temporary_buffer->pBuffer);
00321 omx_maddec_component_Private->temporary_buffer->pBuffer = NULL;
00322 }
00323 if(omx_maddec_component_Private->temporary_buffer) {
00324 free(omx_maddec_component_Private->temporary_buffer);
00325 omx_maddec_component_Private->temporary_buffer = NULL;
00326 }
00327
00328 return err;
00329 }
00330
00336 static inline int scale_int (mad_fixed_t sample) {
00337
00338 #if MAD_F_FRACBITS < 28
00339
00340 sample += (1L << (28 - MAD_F_FRACBITS - 1));
00341 #endif
00342
00343
00344 if (sample >= MAD_F_ONE)
00345 sample = MAD_F_ONE - 1;
00346 else if (sample < -MAD_F_ONE)
00347 sample = -MAD_F_ONE;
00348
00349 #if MAD_F_FRACBITS < 28
00350
00351 sample >>= (28 - MAD_F_FRACBITS);
00352 #endif
00353
00354
00355 return (int) (sample << 3);
00356 }
00357
00365 void omx_maddec_component_BufferMgmtCallback(OMX_COMPONENTTYPE *openmaxStandComp, OMX_BUFFERHEADERTYPE* inputbuffer, OMX_BUFFERHEADERTYPE* outputbuffer) {
00366 omx_maddec_component_PrivateType* omx_maddec_component_Private = openmaxStandComp->pComponentPrivate;
00367 OMX_U32 nchannels;
00368 int count;
00369 int consumed = 0;
00370 int nsamples;
00371 unsigned char const *before_sync, *after_sync;
00372 mad_fixed_t const *left_ch, *right_ch;
00373 unsigned short *outdata;
00374 int tocopy;
00375
00376 outputbuffer->nFilledLen = 0;
00377 outputbuffer->nOffset=0;
00378
00379 if(omx_maddec_component_Private->isNewBuffer==1 || omx_maddec_component_Private->need_mad_stream == 1) {
00380 DEBUG(DEB_LEV_SIMPLE_SEQ,"In %s New Buffer len=%d\n", __func__,(int)inputbuffer->nFilledLen);
00381
00383 tocopy = MIN (MAD_BUFFER_MDLEN, MIN (inputbuffer->nFilledLen,
00384 MAD_BUFFER_MDLEN * 3 - omx_maddec_component_Private->temporary_buffer->nFilledLen));
00385
00386 if (tocopy == 0) {
00387 DEBUG(DEB_LEV_ERR,"mad claims to need more data than %u bytes, we don't have that much", MAD_BUFFER_MDLEN * 3);
00388 inputbuffer->nFilledLen=0;
00389 omx_maddec_component_Private->isNewBuffer = 1;
00390 return;
00391 }
00392
00393 if(omx_maddec_component_Private->need_mad_stream == 1) {
00394 DEBUG(DEB_LEV_SIMPLE_SEQ,"In %s memmove temp buf len=%d\n", __func__,(int)omx_maddec_component_Private->temporary_buffer->nFilledLen);
00395 memmove (omx_maddec_component_Private->temp_input_buffer, omx_maddec_component_Private->temporary_buffer->pBuffer, omx_maddec_component_Private->temporary_buffer->nFilledLen);
00396 omx_maddec_component_Private->temporary_buffer->pBuffer = omx_maddec_component_Private->temp_input_buffer;
00397 omx_maddec_component_Private->need_mad_stream = 0;
00398 memcpy(omx_maddec_component_Private->temporary_buffer->pBuffer+omx_maddec_component_Private->temporary_buffer->nFilledLen, inputbuffer->pBuffer + inputbuffer->nOffset, tocopy);
00399 omx_maddec_component_Private->temporary_buffer->nFilledLen += tocopy;
00400 inputbuffer->nFilledLen -= tocopy;
00401 inputbuffer->nOffset += tocopy;
00402
00403 DEBUG(DEB_LEV_SIMPLE_SEQ, "Input buffer filled len : %d temp buf len = %d tocopy=%d\n", (int)inputbuffer->nFilledLen, (int)omx_maddec_component_Private->temporary_buffer->nFilledLen,tocopy);
00404 omx_maddec_component_Private->isNewBuffer = 0;
00405
00406 mad_stream_buffer(omx_maddec_component_Private->stream, omx_maddec_component_Private->temporary_buffer->pBuffer, omx_maddec_component_Private->temporary_buffer->nFilledLen);
00407 }
00408 if(inputbuffer->nFilledLen == 0) {
00409 omx_maddec_component_Private->isNewBuffer = 1;
00410 inputbuffer->nOffset=0;
00411 }
00412 }
00413
00414
00415
00416 DEBUG(DEB_LEV_SIMPLE_SEQ,"decoding the header now\n");
00417
00418 if (mad_header_decode (&(omx_maddec_component_Private->frame->header), omx_maddec_component_Private->stream) == -1) {
00419 DEBUG(DEB_LEV_SIMPLE_SEQ,"mad_header_decode had an error: %s\n",
00420 mad_stream_errorstr (omx_maddec_component_Private->stream));
00421 }
00422
00423 DEBUG(DEB_LEV_SIMPLE_SEQ,"decoding one frame now\n");
00424
00426 omx_maddec_component_Private->frame->header.flags &= ~MAD_FLAG_PROTECTION;
00427
00428 if (mad_frame_decode (omx_maddec_component_Private->frame, omx_maddec_component_Private->stream) == -1) {
00429 DEBUG(DEB_LEV_SIMPLE_SEQ,"got error %d\n", omx_maddec_component_Private->stream->error);
00430
00431
00432 if (omx_maddec_component_Private->stream->error == MAD_ERROR_BUFLEN) {
00433 if (omx_maddec_component_Private->stream->next_frame == omx_maddec_component_Private->temporary_buffer->pBuffer) {
00434 DEBUG(DEB_LEV_SIMPLE_SEQ,"not enough data in tempbuffer breaking to get more\n");
00435 omx_maddec_component_Private->need_mad_stream=1;
00436 return;
00437 } else {
00438 DEBUG(DEB_LEV_SIMPLE_SEQ,"sync error, flushing unneeded data\n");
00439
00443 if (consumed == 0) {
00444 consumed = omx_maddec_component_Private->stream->next_frame - omx_maddec_component_Private->temporary_buffer->pBuffer;
00445 }
00446 DEBUG(DEB_LEV_SIMPLE_SEQ,"consumed %d bytes\n", consumed);
00447
00448 omx_maddec_component_Private->temporary_buffer->pBuffer += consumed;
00449 omx_maddec_component_Private->temporary_buffer->nFilledLen -= consumed;
00450 return;
00451 }
00452 }
00453 DEBUG(DEB_LEV_SIMPLE_SEQ,"mad_frame_decode had an error: %s\n",
00454 mad_stream_errorstr (omx_maddec_component_Private->stream));
00455 if (!MAD_RECOVERABLE (omx_maddec_component_Private->stream->error)) {
00456 DEBUG(DEB_LEV_ERR,"non recoverable error");
00457 } else if (omx_maddec_component_Private->stream->error == MAD_ERROR_LOSTSYNC) {
00458
00459 signed long tagsize;
00460 tagsize = id3_tag_query(omx_maddec_component_Private->stream->this_frame, omx_maddec_component_Private->stream->bufend - omx_maddec_component_Private->stream->this_frame);
00461 mad_stream_skip(omx_maddec_component_Private->stream, tagsize);
00462 DEBUG(DEB_LEV_SIMPLE_SEQ,"recoverable lost sync error\n");
00463 }
00464
00465 mad_frame_mute (omx_maddec_component_Private->frame);
00466 mad_synth_mute (omx_maddec_component_Private->synth);
00467 before_sync = omx_maddec_component_Private->stream->ptr.byte;
00468 if (mad_stream_sync (omx_maddec_component_Private->stream) != 0)
00469 DEBUG(DEB_LEV_ERR,"mad_stream_sync failed\n");
00470 after_sync = omx_maddec_component_Private->stream->ptr.byte;
00471
00472
00473 consumed = after_sync - before_sync;
00474 DEBUG(DEB_LEV_SIMPLE_SEQ,"resynchronization consumes %d bytes\n", consumed);
00475 DEBUG(DEB_LEV_SIMPLE_SEQ,"synced to data: 0x%0x 0x%0x\n", *omx_maddec_component_Private->stream->ptr.byte,
00476 *(omx_maddec_component_Private->stream->ptr.byte + 1));
00477
00478 mad_stream_sync (omx_maddec_component_Private->stream);
00479
00480
00484 if (consumed == 0) {
00485 consumed = omx_maddec_component_Private->stream->next_frame - omx_maddec_component_Private->temporary_buffer->pBuffer;
00486 }
00487 DEBUG(DEB_LEV_SIMPLE_SEQ,"consumed %d bytes\n", consumed);
00488
00489 omx_maddec_component_Private->temporary_buffer->pBuffer += consumed;
00490 omx_maddec_component_Private->temporary_buffer->nFilledLen -= consumed;
00491 return;
00492 }
00493
00494
00495 nsamples = MAD_NSBSAMPLES (&omx_maddec_component_Private->frame->header) *
00496 (omx_maddec_component_Private->stream->options & MAD_OPTION_HALFSAMPLERATE ? 16 : 32);
00497 nchannels = MAD_NCHANNELS (&omx_maddec_component_Private->frame->header);
00498
00499 if((omx_maddec_component_Private->pAudioPcmMode.nSamplingRate != omx_maddec_component_Private->frame->header.samplerate) ||
00500 ( omx_maddec_component_Private->pAudioPcmMode.nChannels!=nchannels)) {
00501 DEBUG(DEB_LEV_FULL_SEQ, "---->Sending Port Settings Change Event\n");
00502
00503 switch(omx_maddec_component_Private->audio_coding_type) {
00504 case OMX_AUDIO_CodingMP3 :
00505
00506
00507 omx_maddec_component_Private->pAudioMp3.nChannels = nchannels;
00508 omx_maddec_component_Private->pAudioMp3.nBitRate = omx_maddec_component_Private->frame->header.bitrate;
00509 omx_maddec_component_Private->pAudioMp3.nSampleRate = omx_maddec_component_Private->frame->header.samplerate;
00510
00511 omx_maddec_component_Private->pAudioPcmMode.nChannels = nchannels;
00512 omx_maddec_component_Private->pAudioPcmMode.nSamplingRate = 32;
00513 omx_maddec_component_Private->pAudioPcmMode.nSamplingRate = omx_maddec_component_Private->frame->header.samplerate;
00514 break;
00515 default :
00516 DEBUG(DEB_LEV_ERR, "Audio formats other than MP3 not supported\nCodec not found\n");
00517 break;
00518 }
00519
00520
00521 (*(omx_maddec_component_Private->callbacks->EventHandler))
00522 (openmaxStandComp,
00523 omx_maddec_component_Private->callbackData,
00524 OMX_EventPortSettingsChanged,
00525 0,
00526 1,
00527 NULL);
00528 }
00529
00530
00531 mad_synth_frame (omx_maddec_component_Private->synth, omx_maddec_component_Private->frame);
00532 left_ch = omx_maddec_component_Private->synth->pcm.samples[0];
00533 right_ch = omx_maddec_component_Private->synth->pcm.samples[1];
00534
00535 outdata = (unsigned short *)outputbuffer->pBuffer;
00536 outputbuffer->nFilledLen=nsamples * nchannels * 2;
00537
00538
00539 if (nchannels == 1) {
00540 count = nsamples;
00541
00542 while (count--) {
00543 *outdata++ = (scale_int (*left_ch++) >>16) & 0xffff;
00544 }
00545 } else {
00546 count = nsamples;
00547 while (count--) {
00548 *outdata++ = (scale_int (*left_ch++) >>16) & 0xffff;
00549 *outdata++ = (scale_int (*right_ch++)>>16) & 0xffff;
00550 }
00551 }
00552
00553 DEBUG(DEB_LEV_SIMPLE_SEQ,"Returning output buffer size=%d \n", (int)outputbuffer->nFilledLen);
00554
00555
00559 if (consumed == 0)
00560 consumed = omx_maddec_component_Private->stream->next_frame - omx_maddec_component_Private->temporary_buffer->pBuffer;
00561
00562 DEBUG(DEB_LEV_SIMPLE_SEQ,"consumed %d bytes\n", consumed);
00563
00564 omx_maddec_component_Private->temporary_buffer->pBuffer += consumed;
00565 omx_maddec_component_Private->temporary_buffer->nFilledLen -= consumed;
00566 }
00567
00569 OMX_ERRORTYPE omx_maddec_component_SetParameter(
00570 OMX_IN OMX_HANDLETYPE hComponent,
00571 OMX_IN OMX_INDEXTYPE nParamIndex,
00572 OMX_IN OMX_PTR ComponentParameterStructure) {
00573
00574 OMX_ERRORTYPE err = OMX_ErrorNone;
00575 OMX_AUDIO_PARAM_PORTFORMATTYPE *pAudioPortFormat;
00576 OMX_AUDIO_PARAM_PCMMODETYPE* pAudioPcmMode;
00577 OMX_AUDIO_PARAM_MP3TYPE * pAudioMp3;
00578 OMX_PARAM_COMPONENTROLETYPE * pComponentRole;
00579 OMX_U32 portIndex;
00580
00581
00582 OMX_COMPONENTTYPE *openmaxStandComp = (OMX_COMPONENTTYPE *)hComponent;
00583 omx_maddec_component_PrivateType* omx_maddec_component_Private = openmaxStandComp->pComponentPrivate;
00584 omx_base_audio_PortType *port;
00585 if (ComponentParameterStructure == NULL) {
00586 return OMX_ErrorBadParameter;
00587 }
00588
00589 DEBUG(DEB_LEV_SIMPLE_SEQ, " Setting parameter %i\n", nParamIndex);
00590 switch(nParamIndex) {
00591 case OMX_IndexParamAudioPortFormat:
00592 pAudioPortFormat = (OMX_AUDIO_PARAM_PORTFORMATTYPE*)ComponentParameterStructure;
00593 portIndex = pAudioPortFormat->nPortIndex;
00594
00595 err = omx_base_component_ParameterSanityCheck(hComponent, portIndex, pAudioPortFormat, sizeof(OMX_AUDIO_PARAM_PORTFORMATTYPE));
00596 if(err!=OMX_ErrorNone) {
00597 DEBUG(DEB_LEV_ERR, "In %s Parameter Check Error=%x\n",__func__,err);
00598 break;
00599 }
00600 if (portIndex <= 1) {
00601 port = (omx_base_audio_PortType *) omx_maddec_component_Private->ports[portIndex];
00602 memcpy(&port->sAudioParam, pAudioPortFormat, sizeof(OMX_AUDIO_PARAM_PORTFORMATTYPE));
00603 } else {
00604 return OMX_ErrorBadPortIndex;
00605 }
00606 break;
00607
00608 case OMX_IndexParamAudioPcm:
00609 pAudioPcmMode = (OMX_AUDIO_PARAM_PCMMODETYPE*)ComponentParameterStructure;
00610 portIndex = pAudioPcmMode->nPortIndex;
00611
00612 err = omx_base_component_ParameterSanityCheck(hComponent, portIndex, pAudioPcmMode, sizeof(OMX_AUDIO_PARAM_PCMMODETYPE));
00613 if(err!=OMX_ErrorNone) {
00614 DEBUG(DEB_LEV_ERR, "In %s Parameter Check Error=%x\n",__func__,err);
00615 break;
00616 }
00617 memcpy(&omx_maddec_component_Private->pAudioPcmMode, pAudioPcmMode, sizeof(OMX_AUDIO_PARAM_PCMMODETYPE));
00618 break;
00619
00620 case OMX_IndexParamStandardComponentRole:
00621 pComponentRole = (OMX_PARAM_COMPONENTROLETYPE*)ComponentParameterStructure;
00622 if (!strcmp( (char*) pComponentRole->cRole, AUDIO_DEC_MP3_ROLE)) {
00623 omx_maddec_component_Private->audio_coding_type = OMX_AUDIO_CodingMP3;
00624 } else {
00625 return OMX_ErrorBadParameter;
00626 }
00627 omx_maddec_component_SetInternalParameters(openmaxStandComp);
00628 break;
00629
00630 case OMX_IndexParamAudioMp3:
00631 pAudioMp3 = (OMX_AUDIO_PARAM_MP3TYPE*) ComponentParameterStructure;
00632 portIndex = pAudioMp3->nPortIndex;
00633 err = omx_base_component_ParameterSanityCheck(hComponent,portIndex,pAudioMp3,sizeof(OMX_AUDIO_PARAM_MP3TYPE));
00634 if(err!=OMX_ErrorNone) {
00635 DEBUG(DEB_LEV_ERR, "In %s Parameter Check Error=%x\n",__func__,err);
00636 break;
00637 }
00638 if (pAudioMp3->nPortIndex == 0) {
00639 memcpy(&omx_maddec_component_Private->pAudioMp3, pAudioMp3, sizeof(OMX_AUDIO_PARAM_MP3TYPE));
00640 } else {
00641 return OMX_ErrorBadPortIndex;
00642 }
00643 break;
00644
00645 default:
00646 return omx_base_component_SetParameter(hComponent, nParamIndex, ComponentParameterStructure);
00647 }
00648 return err;
00649
00650 }
00651
00653 OMX_ERRORTYPE omx_maddec_component_GetParameter(
00654 OMX_IN OMX_HANDLETYPE hComponent,
00655 OMX_IN OMX_INDEXTYPE nParamIndex,
00656 OMX_INOUT OMX_PTR ComponentParameterStructure) {
00657
00658 OMX_AUDIO_PARAM_PORTFORMATTYPE *pAudioPortFormat;
00659 OMX_AUDIO_PARAM_PCMMODETYPE *pAudioPcmMode;
00660 OMX_PARAM_COMPONENTROLETYPE * pComponentRole;
00661 OMX_AUDIO_PARAM_MP3TYPE *pAudioMp3;
00662 omx_base_audio_PortType *port;
00663 OMX_ERRORTYPE err = OMX_ErrorNone;
00664
00665 OMX_COMPONENTTYPE *openmaxStandComp = (OMX_COMPONENTTYPE *)hComponent;
00666 omx_maddec_component_PrivateType* omx_maddec_component_Private = openmaxStandComp->pComponentPrivate;
00667 if (ComponentParameterStructure == NULL) {
00668 return OMX_ErrorBadParameter;
00669 }
00670 DEBUG(DEB_LEV_SIMPLE_SEQ, " Getting parameter %i\n", nParamIndex);
00671
00672 switch(nParamIndex) {
00673 case OMX_IndexParamAudioInit:
00674 if ((err = checkHeader(ComponentParameterStructure, sizeof(OMX_PORT_PARAM_TYPE))) != OMX_ErrorNone) {
00675 break;
00676 }
00677 memcpy(ComponentParameterStructure, &omx_maddec_component_Private->sPortTypesParam[OMX_PortDomainAudio], sizeof(OMX_PORT_PARAM_TYPE));
00678 break;
00679
00680 case OMX_IndexParamAudioPortFormat:
00681 pAudioPortFormat = (OMX_AUDIO_PARAM_PORTFORMATTYPE*)ComponentParameterStructure;
00682 if ((err = checkHeader(ComponentParameterStructure, sizeof(OMX_AUDIO_PARAM_PORTFORMATTYPE))) != OMX_ErrorNone) {
00683 break;
00684 }
00685 if (pAudioPortFormat->nPortIndex <= 1) {
00686 port = (omx_base_audio_PortType *)omx_maddec_component_Private->ports[pAudioPortFormat->nPortIndex];
00687 memcpy(pAudioPortFormat, &port->sAudioParam, sizeof(OMX_AUDIO_PARAM_PORTFORMATTYPE));
00688 } else {
00689 return OMX_ErrorBadPortIndex;
00690 }
00691 break;
00692
00693 case OMX_IndexParamAudioPcm:
00694 pAudioPcmMode = (OMX_AUDIO_PARAM_PCMMODETYPE*)ComponentParameterStructure;
00695 if ((err = checkHeader(ComponentParameterStructure, sizeof(OMX_AUDIO_PARAM_PCMMODETYPE))) != OMX_ErrorNone) {
00696 break;
00697 }
00698 if (pAudioPcmMode->nPortIndex > 1) {
00699 return OMX_ErrorBadPortIndex;
00700 }
00701 memcpy(pAudioPcmMode, &omx_maddec_component_Private->pAudioPcmMode, sizeof(OMX_AUDIO_PARAM_PCMMODETYPE));
00702 break;
00703
00704 case OMX_IndexParamAudioMp3:
00705 pAudioMp3 = (OMX_AUDIO_PARAM_MP3TYPE*)ComponentParameterStructure;
00706 if (pAudioMp3->nPortIndex != 0) {
00707 return OMX_ErrorBadPortIndex;
00708 }
00709 if ((err = checkHeader(ComponentParameterStructure, sizeof(OMX_AUDIO_PARAM_MP3TYPE))) != OMX_ErrorNone) {
00710 break;
00711 }
00712 memcpy(pAudioMp3, &omx_maddec_component_Private->pAudioMp3, sizeof(OMX_AUDIO_PARAM_MP3TYPE));
00713 break;
00714
00715 case OMX_IndexParamStandardComponentRole:
00716 pComponentRole = (OMX_PARAM_COMPONENTROLETYPE*)ComponentParameterStructure;
00717 if ((err = checkHeader(ComponentParameterStructure, sizeof(OMX_PARAM_COMPONENTROLETYPE))) != OMX_ErrorNone) {
00718 break;
00719 }
00720 if (omx_maddec_component_Private->audio_coding_type == OMX_AUDIO_CodingMP3) {
00721 strcpy( (char*) pComponentRole->cRole, AUDIO_DEC_MP3_ROLE);
00722 } else {
00723 strcpy( (char*) pComponentRole->cRole,"\0");;
00724 }
00725 break;
00726 default:
00727 return omx_base_component_GetParameter(hComponent, nParamIndex, ComponentParameterStructure);
00728 }
00729 return OMX_ErrorNone;
00730
00731 }
00732
00734 OMX_ERRORTYPE omx_mad_decoder_MessageHandler(OMX_COMPONENTTYPE* openmaxStandComp, internalRequestMessageType *message) {
00735
00736 omx_maddec_component_PrivateType* omx_maddec_component_Private = (omx_maddec_component_PrivateType*)openmaxStandComp->pComponentPrivate;
00737 OMX_ERRORTYPE err;
00738 OMX_STATETYPE eCurrentState = omx_maddec_component_Private->state;
00739 DEBUG(DEB_LEV_SIMPLE_SEQ, "In %s\n", __func__);
00740
00741 if (message->messageType == OMX_CommandStateSet){
00742 if ((message->messageParam == OMX_StateIdle) && (omx_maddec_component_Private->state == OMX_StateLoaded)) {
00743 err = omx_maddec_component_Init(openmaxStandComp);
00744 if(err!=OMX_ErrorNone) {
00745 DEBUG(DEB_LEV_ERR, "In %s MAD Decoder Init Failed Error=%x\n",__func__,err);
00746 return err;
00747 }
00748 } else if ((message->messageParam == OMX_StateExecuting) && (omx_maddec_component_Private->state == OMX_StateIdle)) {
00749 DEBUG(DEB_LEV_FULL_SEQ, "State Changing from Idle to Exec\n");
00750 omx_maddec_component_Private->temporary_buffer->nFilledLen=0;
00751 omx_maddec_component_Private->temporary_buffer->nOffset=0;
00752 omx_maddec_component_Private->need_mad_stream = 1;
00753 if (!omx_maddec_component_Private->maddecReady) {
00754 err = omx_maddec_component_madLibInit(omx_maddec_component_Private);
00755 if (err != OMX_ErrorNone) {
00756 return OMX_ErrorNotReady;
00757 }
00758 omx_maddec_component_Private->maddecReady = OMX_TRUE;
00759 }
00760 }
00761 }
00763 err = omx_base_component_MessageHandler(openmaxStandComp, message);
00764
00765 if (message->messageType == OMX_CommandStateSet){
00766 if ((message->messageParam == OMX_StateLoaded) && (eCurrentState == OMX_StateIdle)) {
00767 err = omx_maddec_component_Deinit(openmaxStandComp);
00768 if(err!=OMX_ErrorNone) {
00769 DEBUG(DEB_LEV_ERR, "In %s MAD Decoder Deinit Failed Error=%x\n",__func__,err);
00770 return err;
00771 }
00772 }else if ((message->messageParam == OMX_StateIdle) && (eCurrentState == OMX_StateExecuting)) {
00773 omx_maddec_component_madLibDeInit(omx_maddec_component_Private);
00774 omx_maddec_component_Private->maddecReady = OMX_FALSE;
00775 }
00776 }
00777
00778 return err;
00779 }
00780