examples/sfexamples/oggvorbiscodec/src/omx/decoder/OmxVorbisDecoder.cpp

Go to the documentation of this file.
00001 // OmxVorbisDecoder.cpp
00002 //
00003 // Copyright (c) 2007-2008 Symbian Software Ltd. All rights reserved.
00004 //
00005 
00011 #include <e32debug.h>
00012 #include <stdio.h>
00013 #include <string.h>
00014 #include <stdlib.h>
00015 #include <OMX_Core.h>
00016 #include <OMX_Audio.h>
00017 
00018 #include "OmxImpl.h"
00019 #include "OmxVorbisDecoder.h"
00020 #include "VorbisDecoder.h"
00021 
00022 const TInt KIndexInputPort = 0;
00023 const TInt KIndexOutputPort = 1;
00024 
00025 // Vorbis decoder requires 8k input and 16k output buffer
00026 const TInt KVorbisDecoderInputBufferSize        = 0x2000;
00027 const TInt KVorbisDecoderOutputBufferSize       = 0x4000;
00028 
00029 const TInt KThreadStackSize = 16384; 
00030 
00031 const TInt KDefaultOutputBitsPerSample = 16;
00032 const OMX_NUMERICALDATATYPE KDefaultOutputDataType = OMX_NumericalDataSigned;
00033 
00034 _LIT(KVorbisDecoder, "VorbisDecoder");
00035                                                         
00036 TInt ProcessingThread(TAny* aComponent)
00037         {
00038         // get our class
00039         CCodecProcessor* codecprocessor = static_cast<CCodecProcessor*>(aComponent);
00040         // run the thread
00041         TRAPD(err, codecprocessor->RunThreadL());
00042         // thread has exited or failed to start so return error to the client. 
00043         return err;
00044         }
00045 
00046 
00047 TInt COmxVorbisDecoder::CreateComponent(OMX_HANDLETYPE hComponent)
00048         {
00049         COmxVorbisDecoder* self = new COmxVorbisDecoder(hComponent);
00050         if (self==NULL)
00051                 return KErrNoMemory;
00052         TRAPD(err, self->ConstructL());
00053         // self is stored in the handle, so we won't return it
00054         return err;
00055         }
00056         
00057 OMX_ERRORTYPE COmxVorbisDecoder::GetComponentVersion(
00058        OMX_STRING /*pComponentName*/,
00059        OMX_VERSIONTYPE* /*pComponentVersion*/,
00060        OMX_VERSIONTYPE* /*pSpecVersion*/,
00061        OMX_UUIDTYPE* /*pComponentUUID*/)
00062         {
00063 // to be implemented
00064         return OMX_ErrorNone;
00065         }
00066 
00067 void COmxVorbisDecoder::ConstructL()
00068         {
00069         iCodecProcessor = CCodecProcessor::NewL(*this); 
00070         iState = OMX_StateLoaded;
00071         }
00072 
00073 COmxVorbisDecoder::COmxVorbisDecoder(OMX_HANDLETYPE hComponent)
00074         :COmxComponentImpl(hComponent)
00075         {
00076         }
00077         
00078 COmxVorbisDecoder::~COmxVorbisDecoder()
00079         {
00080         if (iState == OMX_StateExecuting)
00081                 {
00082                 iCodecProcessor->Stop();
00083                 iState = OMX_StateIdle;
00084                 }
00085 
00086         if (iCreatedThread)
00087                 {
00088                 iCodecProcessor->Exit();
00089                 TRequestStatus status;
00090                 iProcessingThread.Logon(status);
00091                 User::WaitForRequest(status);
00092                 iProcessingThread.Close();
00093                 }
00094         delete iCodecProcessor;
00095         }
00096 
00097 OMX_ERRORTYPE COmxVorbisDecoder::SendCommand(
00098        OMX_COMMANDTYPE Cmd,
00099        TUint32 nParam1,
00100        TAny* /*pCmdData*/)
00101         {
00102         OMX_ERRORTYPE error = OMX_ErrorNone;
00103         switch (Cmd)
00104                 {
00105         case OMX_CommandStateSet:
00106                 OMX_STATETYPE state = (OMX_STATETYPE)nParam1;
00107                 if (state == iState)
00108                         {
00109                         error = OMX_ErrorSameState;
00110                         }
00111                 else
00112                         {
00113                         // notify client of the state change
00114                         switch (state)
00115                                 {
00116                         case OMX_StateIdle:
00117                                 {
00118                                 if (iState == OMX_StateExecuting)
00119                                         {
00120                                         iCodecProcessor->Stop();
00121                                         }
00122                                 break;
00123                                 }
00124                         case OMX_StateExecuting:
00125                                 StartExecution();
00126                                 break;
00127                                 };
00128         
00129                         iState = state;
00130                         
00131                         EventHandlerCallback(
00132                                 OMX_EventCmdComplete,
00133                                 OMX_CommandStateSet,
00134                                 iState,
00135                                 NULL);  
00136                         break;
00137                         }
00138                 };      
00139         return error;
00140         }
00141         
00142 OMX_ERRORTYPE COmxVorbisDecoder::GetParameter(
00143        OMX_INDEXTYPE nParamIndex,  
00144        TAny* ComponentParameterStructure)
00145         {
00146         switch (nParamIndex)
00147                 {
00148         case OMX_IndexParamAudioInit :
00149                 {
00150                 OMX_PORT_PARAM_TYPE* param = static_cast<OMX_PORT_PARAM_TYPE*>(ComponentParameterStructure);
00151                 param->nPorts = 2;
00152                 }
00153                 break;
00154         case OMX_IndexParamPortDefinition:
00155                 {
00156                 OMX_PARAM_PORTDEFINITIONTYPE* portDef = static_cast<OMX_PARAM_PORTDEFINITIONTYPE*>(ComponentParameterStructure);
00157                 if (portDef->nPortIndex==0)     
00158                         {
00159                         portDef->eDir = OMX_DirInput;   
00160                         portDef->nBufferSize = KVorbisDecoderInputBufferSize;
00161                         }
00162                 else
00163                         {
00164                         portDef->eDir = OMX_DirOutput;
00165                         portDef->nBufferSize = KVorbisDecoderOutputBufferSize;
00166                         }
00167                 }
00168                 break;
00169         default:
00170                 return OMX_ErrorUnsupportedIndex;
00171                 }
00172         return OMX_ErrorNone;
00173         }
00174         
00175 OMX_ERRORTYPE COmxVorbisDecoder::SetParameter(
00176        OMX_INDEXTYPE nIndex,
00177        TAny* ComponentParameterStructure)
00178         {
00179         ASSERT(iState == OMX_StateLoaded);
00180         switch (nIndex)
00181                 {
00182                 case OMX_IndexParamAudioVorbis:
00183                         {
00184                         OMX_AUDIO_PARAM_VORBISTYPE* param = static_cast<OMX_AUDIO_PARAM_VORBISTYPE*>(ComponentParameterStructure);
00185                         switch(param->nPortIndex)
00186                                 {
00187                                 case 0: // Input port = Vorbis
00188                                         {
00189                                         // nothing to set
00190                                         return OMX_ErrorNone;
00191                                         }                       
00192                                 case 1: // Output port
00193                                 default:
00194                                         {
00195                                         return OMX_ErrorUnsupportedIndex;       
00196                                         }
00197                                 };
00198                         }
00199                 case OMX_IndexParamAudioPcm:
00200                         {
00201                         OMX_AUDIO_PARAM_PCMMODETYPE* param = static_cast<OMX_AUDIO_PARAM_PCMMODETYPE*>(ComponentParameterStructure);
00202                         switch(param->nPortIndex)
00203                                 {
00204                                 case 1: // Output port = PCM
00205                                         {
00206                                         iCodecProcessor->SetOutputBitsPerSample(param->nBitPerSample);
00207                                         iCodecProcessor->SetOutputDataType(param->eNumData);
00208                                         return OMX_ErrorNone;
00209                                         }
00210                                 case 0: // Input port
00211                                 default:
00212                                         {
00213                                         return OMX_ErrorUnsupportedIndex;       
00214                                         }
00215                                 };
00216                         }
00217                 default:
00218                         {
00219                         return OMX_ErrorUnsupportedIndex;
00220                         }
00221                 };              
00222         }
00223         
00224 OMX_ERRORTYPE COmxVorbisDecoder::GetConfig(
00225        OMX_INDEXTYPE /*nIndex*/, 
00226        TAny* /*value*/)
00227         {
00228         return OMX_ErrorUnsupportedIndex;
00229         }
00230         
00231 OMX_ERRORTYPE COmxVorbisDecoder::SetConfig(
00232        OMX_INDEXTYPE /*nIndex*/, 
00233        TAny* /*value*/)
00234         {
00235         return OMX_ErrorUnsupportedIndex;
00236         }
00237         
00238 OMX_ERRORTYPE COmxVorbisDecoder::GetExtensionIndex(
00239        OMX_STRING /*ParameterName*/,
00240        OMX_INDEXTYPE* /*pIndexType*/)
00241         {
00242         return OMX_ErrorNotImplemented;
00243         }
00244         
00245 OMX_ERRORTYPE COmxVorbisDecoder::GetState(
00246        OMX_STATETYPE* pState)
00247         {
00248         *pState = iState;
00249         return OMX_ErrorNone;
00250         }
00251         
00252 // To be implemented for DM4
00253 OMX_ERRORTYPE COmxVorbisDecoder::ComponentTunnelRequest(
00254                 OMX_HANDLETYPE /*hInput*/,
00255                 TUint32 /*nInputPort*/,
00256                 OMX_HANDLETYPE /*hOutput*/,
00257                 TUint32 /*nOutputPort*/,
00258                 OMX_TUNNELSETUPTYPE* /*pTunnelSetup*/)
00259         {
00260         return OMX_ErrorNotImplemented;
00261         }
00262         
00263 OMX_ERRORTYPE COmxVorbisDecoder::UseBuffer(
00264        OMX_BUFFERHEADERTYPE** ppBufferHeader,
00265        TUint32 nPortIndex,
00266        TAny* pAppPrivate,
00267        TUint32 nSizeBytes,
00268        TUint8* pBuffer)
00269         {
00270         ASSERT(iState == OMX_StateLoaded);
00271         *ppBufferHeader = new OMX_BUFFERHEADERTYPE;
00272         if (*ppBufferHeader != NULL)
00273                 {
00274                 (*ppBufferHeader)->pBuffer = pBuffer;
00275                 (*ppBufferHeader)->pAppPrivate = pAppPrivate;
00276                 (*ppBufferHeader)->nAllocLen = nSizeBytes;
00277                 (*ppBufferHeader)->nFilledLen = 0;
00278                 (*ppBufferHeader)->nFlags = 0;
00279                 (*ppBufferHeader)->pInputPortPrivate = NULL;
00280                 (*ppBufferHeader)->pOutputPortPrivate = NULL;
00281                 }
00282 
00283 
00284                 
00285         if (*ppBufferHeader)
00286                 {
00287                 TPtr8 ptr(pBuffer,nSizeBytes,nSizeBytes);
00288                 CMMFBuffer* buffer = NULL;
00289                 TRAPD(err, buffer = CMMFPtrBuffer::NewL(ptr));
00290                 if (err != KErrNone)
00291                         {
00292                         return OMX_ErrorInsufficientResources;
00293                         }
00294                 switch (nPortIndex)
00295                         {
00296                 case KIndexInputPort:
00297                                 {
00298                                 (*ppBufferHeader)->pInputPortPrivate = buffer;
00299                                 (*ppBufferHeader)->nInputPortIndex = nPortIndex;
00300                                 }
00301                                 break;
00302                         case KIndexOutputPort:
00303                                 {
00304                                 (*ppBufferHeader)->pOutputPortPrivate = buffer; 
00305                                 (*ppBufferHeader)->nOutputPortIndex = nPortIndex;
00306                                 }
00307                                 break;
00308                         
00309                         }
00310                 return OMX_ErrorNone;
00311                 }
00312         else
00313                 {
00314                 return OMX_ErrorInsufficientResources;
00315                 }
00316         }
00317         
00318 OMX_ERRORTYPE COmxVorbisDecoder::AllocateBuffer(
00319                 OMX_BUFFERHEADERTYPE** pBuffer,
00320                 TUint32 nPortIndex,
00321                 TAny* pAppData,
00322                 TUint32 nSizeBytes)
00323         {
00324         ASSERT(iState == OMX_StateLoaded);
00325         
00326         *pBuffer = new OMX_BUFFERHEADERTYPE;
00327         if (*pBuffer != NULL)
00328                 {
00329                 CMMFDescriptorBuffer* buffer = NULL;
00330                 TRAPD(err, buffer = CMMFDescriptorBuffer::NewL(nSizeBytes));
00331                 if (err != KErrNone)
00332                         {
00333                         return OMX_ErrorInsufficientResources;
00334                         }
00335                 (*pBuffer)->pBuffer = const_cast<TUint8*>(buffer->Data().Ptr());
00336                 // store our allocated memory in component's private store
00337                 switch (nPortIndex)
00338                         {
00339                 case KIndexInputPort:
00340                         (*pBuffer)->pInputPortPrivate = buffer;
00341                         (*pBuffer)->pOutputPortPrivate = NULL;
00342                         break;
00343                 case KIndexOutputPort:
00344                         (*pBuffer)->pOutputPortPrivate = buffer;
00345                         (*pBuffer)->pInputPortPrivate = NULL;
00346                         break;
00347                         };
00348                 
00349                 
00350                 (*pBuffer)->nAllocLen = nSizeBytes;
00351                 (*pBuffer)->nFilledLen = 0;
00352                 (*pBuffer)->pAppPrivate = pAppData;
00353                 }
00354                 
00355         if (*pBuffer && (*pBuffer)->pBuffer)
00356                 {
00357                 return OMX_ErrorNone;
00358                 }
00359         else
00360                 {
00361                 return OMX_ErrorInsufficientResources;
00362                 }
00363         }
00364 
00365 OMX_ERRORTYPE COmxVorbisDecoder::FreeBuffer(
00366                 TUint32 nPortIndex,
00367        OMX_BUFFERHEADERTYPE* pBuffer)
00368         {
00369         switch (nPortIndex) 
00370                 {               
00371                 case KIndexInputPort:
00372                         {
00373                         delete (static_cast<CMMFBuffer*>(pBuffer->pInputPortPrivate));
00374                         pBuffer->pInputPortPrivate = NULL;
00375                         break;
00376                         }
00377                 case KIndexOutputPort:
00378                         delete (static_cast<CMMFBuffer*>(pBuffer->pOutputPortPrivate));
00379                         pBuffer->pOutputPortPrivate = NULL;
00380                         break;  
00381                         
00382                 }
00383         delete pBuffer;
00384         return OMX_ErrorNone;
00385         }
00386 OMX_ERRORTYPE COmxVorbisDecoder::EmptyThisBuffer(
00387        OMX_BUFFERHEADERTYPE* pBuffer)
00388         {
00389         ASSERT(iState == OMX_StateExecuting ||
00390                         iState == OMX_StateIdle ||
00391                         iState == OMX_StatePause);
00392         return iCodecProcessor->EmptyThisBuffer(pBuffer);
00393         }
00394 OMX_ERRORTYPE COmxVorbisDecoder::FillThisBuffer(
00395            OMX_BUFFERHEADERTYPE* pBuffer)
00396         {
00397         ASSERT(iState == OMX_StateExecuting ||
00398                         iState == OMX_StateIdle ||
00399                         iState == OMX_StatePause);
00400         return iCodecProcessor->FillThisBuffer(pBuffer);        
00401         }
00402         
00403 OMX_ERRORTYPE COmxVorbisDecoder::SetCallbacks(
00404            OMX_CALLBACKTYPE* pCallbacks, 
00405            TAny* pAppData)
00406         {
00407         iCallback = pCallbacks;
00408         iAppData = pAppData;
00409         return OMX_ErrorNone;
00410         }
00411         
00412 CCodecProcessor::CCodecProcessor(COmxVorbisDecoder& aParent) 
00413         : iParent(&aParent)
00414         {
00415         }
00416 
00417 void CCodecProcessor::RunThreadL()
00418         {
00419         iQueueStatus = KRequestPending;
00420         iMessageQueue.NotifyDataAvailable(iQueueStatus);
00421         
00422         for (;;)
00423                 {
00424                 User::WaitForRequest(iQueueStatus);
00425                 TCodecMessage msg;
00426                 
00427                 TBool exit = EFalse;
00428                 
00429                 while (iMessageQueue.Receive(msg)==KErrNone)
00430                         {
00431                         switch (msg.iType)
00432                                 {
00433                                 case EStopProcessing:
00434                                         iStarted = EFalse;
00435                                         iLastInputBuffer = EFalse;
00436                                         iBuffersToEmpty.Reset();
00437                                         iBuffersToFill.Reset();
00438                                         break;
00439                                 case EExit:
00440                                         exit = ETrue;
00441                                         break;
00442                                 case EInputBuffer:
00443                                         iBuffersToEmpty.Append(msg.iBuffer); 
00444                                         break;
00445                                 case EOutputBuffer:
00446                                         iBuffersToFill.Append(msg.iBuffer);
00447                                         break;
00448                                 }
00449                         }
00450                         
00451                 if (exit)
00452                         {
00453                         break;
00454                         }
00455                 else
00456                         {
00457                         // process all available buffers
00458                         ProcessAvailableBuffers();      
00459                         
00460                         // request notification of further queue events
00461                         iQueueStatus = KRequestPending;
00462                         iMessageQueue.NotifyDataAvailable(iQueueStatus);
00463                         }
00464                 }
00465         }
00466 
00467 CCodecProcessor* CCodecProcessor::NewL(COmxVorbisDecoder& aParent) 
00468         {
00469         CCodecProcessor* self = new (ELeave) CCodecProcessor(aParent);
00470         CleanupStack::PushL(self);
00471         self->ConstructL();
00472         CleanupStack::Pop(self);
00473         return self;
00474         }       
00475         
00476         
00477 void CCodecProcessor::ConstructL()
00478         {
00479         User::LeaveIfError(iMessageQueue.CreateLocal(10));
00480 
00481         // set the default case
00482         // input = Vorbis, output = PCM16
00483         iOutputBitsPerSample = KDefaultOutputBitsPerSample;
00484         iOutputDataType = KDefaultOutputDataType;
00485 
00486         // create the Vorbis codec
00487         iCodec = CVorbisDecoderProcessor::NewL();       
00488         
00489         // create a dummy buffer used if there are no more encoded data to process
00490         iDummyBuffer = (CMMFDataBuffer*)CMMFDescriptorBuffer::NewL();
00491         iDummyBuffer->SetStatus(EUnAvailable);
00492         }
00493         
00494 OMX_ERRORTYPE CCodecProcessor::EmptyThisBuffer( 
00495                 OMX_BUFFERHEADERTYPE* pBuffer) 
00496         {
00497         TCodecMessage message;
00498         message.iType = EInputBuffer;
00499         message.iBuffer = pBuffer;
00500         if (iMessageQueue.Send(message) == KErrNone)
00501                 {
00502                 return OMX_ErrorNone;   
00503                 }
00504         else
00505                 {
00506                 return OMX_ErrorUndefined;
00507                 }
00508         }
00509         
00510 void CCodecProcessor::Stop()
00511         {
00512         TCodecMessage message;
00513         message.iType = EStopProcessing;
00514         message.iBuffer = NULL;
00515         iMessageQueue.Send(message);
00516         }
00517         
00518 void CCodecProcessor::Exit()
00519         {
00520         TCodecMessage message;
00521         message.iType = EExit;
00522         message.iBuffer = NULL;
00523         iMessageQueue.Send(message);
00524         }
00525         
00526 OMX_ERRORTYPE CCodecProcessor::FillThisBuffer(
00527                                                                         OMX_BUFFERHEADERTYPE* pBuffer) 
00528         {
00529         TCodecMessage message;
00530         message.iType = EOutputBuffer;
00531         message.iBuffer = pBuffer;
00532         if (iMessageQueue.Send(message)== KErrNone)
00533                 {
00534                 return OMX_ErrorNone;
00535                 }
00536         else
00537                 {
00538                 return OMX_ErrorUndefined;
00539                 }
00540         }
00541         
00542 void CCodecProcessor::SetOutputBitsPerSample(TInt aOutputBitsPerSample)
00543         {
00544         iOutputBitsPerSample = aOutputBitsPerSample;
00545         }
00546         
00547 void CCodecProcessor::SetOutputDataType(OMX_NUMERICALDATATYPE aType)
00548         {
00549         iOutputDataType = aType;
00550         }
00551         
00552 void CCodecProcessor::ProcessAvailableBuffers()
00553         {
00554         // Setup wait for data in queue
00555         while (iBuffersToFill.Count()>0 && (iBuffersToEmpty.Count()>0 || iLastInputBuffer))
00556                 {
00557                 if (!iStarted)
00558                         {
00559                         iStarted = ETrue;
00560                         }
00561                 
00562                 OMX_BUFFERHEADERTYPE* srcBuffer = NULL;
00563                 CMMFDataBuffer* mmfSrcBuffer = NULL;
00564                 
00565                 TBool useSrcBuffer = iBuffersToEmpty.Count()>0;
00566                 if (useSrcBuffer)
00567                         {                       
00568                         srcBuffer = iBuffersToEmpty[0]; 
00569                         if (srcBuffer->nFlags & OMX_BUFFERFLAG_EOS)
00570                                 {
00571                                 iLastInputBuffer = ETrue;
00572                                 }
00573                                 
00574                         // the buffer contains an ogg packet.
00575                         // no need to pre-calculate samples as in PCM->PCM
00576                         // set up CMMFDataBuffers from the source and dest
00577                         mmfSrcBuffer = (CMMFDataBuffer*)(srcBuffer->pInputPortPrivate);
00578                         mmfSrcBuffer->Data().SetLength(srcBuffer->nFilledLen);
00579                         }
00580                 else
00581                         {
00582                         if (!iLastInputBuffer)
00583                                 { // need more input data
00584                                 return;
00585                                 }
00586                         // otherwise we can go on with a dummy input buffer to extract output   
00587                         mmfSrcBuffer = iDummyBuffer;
00588                         }
00589                         
00590                 OMX_BUFFERHEADERTYPE* destBuffer = iBuffersToFill[0];
00591                 CMMFDataBuffer* mmfDestBuffer = (CMMFDataBuffer*)(destBuffer->pOutputPortPrivate);
00592                 mmfDestBuffer->Data().SetLength(destBuffer->nFilledLen);
00593                 const TDesC8& srcData = mmfSrcBuffer->Data();
00594                 const TUint8* srcDataPtr = srcData.Ptr();
00595 
00596                 CVorbisDecoderProcessor::TProcessResult processResult;
00597                 TUint bytesRead = 0;
00598                 TUint bytesWritten = 0;         
00599                 TRAPD(err, iCodec->ProcessL(*mmfSrcBuffer,
00600                                                                         *mmfDestBuffer, 
00601                                                                         processResult,
00602                                                                         bytesRead,
00603                                                                         bytesWritten) );
00604                 if(err)  
00605                         {
00606                         // we couldn't process the buffer       
00607                         // TO DO : set error condition?
00608                         }
00609                 if (useSrcBuffer)
00610                         {
00611                         srcBuffer->nFilledLen = 0;
00612                         iBuffersToEmpty.Remove(0);                      
00613                         iParent->EmptyBufferDoneCallback(srcBuffer);
00614                         }
00615                         
00616                 destBuffer->nFilledLen = bytesWritten;
00617                 iBuffersToFill.Remove(0);
00618                 
00619                 if (iLastInputBuffer && (bytesWritten == 0))
00620                         {
00621                         // clear all remaining read requests
00622                         iBuffersToFill.Reset();
00623                         destBuffer->nFlags |= OMX_BUFFERFLAG_EOS;
00624                         // propagate the EOS flag
00625                         iParent->EventHandlerCallback(
00626                                                 OMX_EventBufferFlag,
00627                                                 0,
00628                                                 destBuffer->nFlags,
00629                                                 NULL);  
00630                         }
00631                 iParent->FillBufferDoneCallback(destBuffer);
00632                 }
00633         }
00634         
00635 CCodecProcessor::~CCodecProcessor()
00636         {
00637         iBuffersToEmpty.Close();
00638         iBuffersToFill.Close();
00639         iMessageQueue.Close();
00640         
00641         // delete the codec
00642         delete iCodec;
00643         iCodec = NULL;
00644         
00645         delete iDummyBuffer;
00646         iDummyBuffer = NULL;
00647         }
00648         
00649 TInt COmxVorbisDecoder::StartExecution()
00650         {
00651         // create thread with current thread's heap
00652         // we can thus allocate and free memory across threads
00653         if (!iCreatedThread)
00654                 {
00655                 // create thread with unique name, as two decoders may
00656                 // exist at once
00657                 TTime threadTime;
00658                 threadTime.HomeTime();
00659         TName threadName;
00660         threadName.Copy(KVorbisDecoder);
00661         threadName.AppendNum(threadTime.Int64(), EHex);
00662 
00663                 TInt err = iProcessingThread.Create(threadName, 
00664                                                         &ProcessingThread, 
00665                                                         KThreadStackSize, 
00666                                                         &User::Heap(),
00667                                                         iCodecProcessor);
00668                                                         
00669                 if (err!=KErrNone)
00670                         {
00671                         return err;
00672                         }
00673                 iCreatedThread = ETrue;
00674                 iThreadDeath = KRequestPending;
00675                 iProcessingThread.Resume();
00676                 }
00677 
00678         return KErrNone;                                                
00679         }
00680 
00681 // Callbacks for the Vorbis Decoder
00682 void COmxVorbisDecoder::EventHandlerCallback( 
00683                                 OMX_OUT OMX_EVENTTYPE eEvent, 
00684                                 OMX_OUT TUint32 nData1,
00685                                 OMX_OUT TUint32 nData2,
00686                                 OMX_OUT OMX_STRING cExtraInfo)
00687         {
00688         iCallback->EventHandler(
00689                         this,
00690                         iAppData,
00691                         eEvent,
00692                         nData1,
00693                         nData2,
00694                         cExtraInfo);    
00695         }
00696         
00697 void COmxVorbisDecoder::FillBufferDoneCallback(OMX_BUFFERHEADERTYPE* aBuffer)
00698         {
00699         iCallback->FillBufferDone(
00700                 *this,
00701                 iAppData,
00702                 aBuffer);
00703         }
00704         
00705 void COmxVorbisDecoder::EmptyBufferDoneCallback(OMX_BUFFERHEADERTYPE* aBuffer)
00706         {
00707         iCallback->EmptyBufferDone(
00708                 *this,
00709                 iAppData,
00710                 aBuffer);               
00711         }
00712         
00713 // Component Entry Point
00714 OMX_ERRORTYPE OMX_ComponentInit(OMX_HANDLETYPE hComponent)
00715         {
00716         TInt err = COmxVorbisDecoder::CreateComponent(hComponent);
00717         if (err == KErrNone)
00718                 return OMX_ErrorNone;
00719         else 
00720                 {
00721                 // return some problem
00722                 return OMX_ErrorInsufficientResources;
00723                 
00724                 }
00725         }

Generated by  doxygen 1.6.2