os/mm/devsound/devsoundrefplugin/src/plugin/audio/Gsm610/GSM610.CPP
author sl
Tue, 10 Jun 2014 14:32:02 +0200
changeset 1 260cb5ec6c19
permissions -rw-r--r--
Update contrib.
     1 // Copyright (c) 2002-2009 Nokia Corporation and/or its subsidiary(-ies).
     2 // All rights reserved.
     3 // This component and the accompanying materials are made available
     4 // under the terms of "Eclipse Public License v1.0"
     5 // which accompanies this distribution, and is available
     6 // at the URL "http://www.eclipse.org/legal/epl-v10.html".
     7 //
     8 // Initial Contributors:
     9 // Nokia Corporation - initial contribution.
    10 //
    11 // Contributors:
    12 //
    13 // Description:
    14 // * INCLUDE FILES:
    15 // 
    16 //
    17 
    18 // Standard includes
    19 #include <e32std.h>
    20 #include <mmf/server/mmfswcodecwrapper.h>
    21 
    22 #include <ecom/implementationproxy.h>
    23 #include "GSM610.H"
    24 #include "gsm610fr.h"
    25 #include <ecom/ecom.h>
    26 #include <e32def.h>
    27 #include <mmf/plugin/mmfhwdeviceimplementationuids.hrh>
    28 
    29 /**
    30 *
    31 * NewL
    32 * @return CMmfGsm610ToPcm16HwDevice*
    33 *
    34 */
    35 CMmfGsm610ToPcm16HwDevice* CMmfGsm610ToPcm16HwDevice::NewL()
    36 	{
    37 	CMmfGsm610ToPcm16HwDevice* self=new(ELeave) CMmfGsm610ToPcm16HwDevice();
    38 	CleanupStack::PushL(self);
    39 	self->ConstructL();
    40 	CleanupStack::Pop(self);
    41 	return self;
    42 	}
    43 
    44 /**
    45 *
    46 * Codec
    47 *
    48 */
    49 CMMFSwCodec& CMmfGsm610ToPcm16HwDevice::Codec()
    50 	{						  
    51 	return *iCodec;
    52 	}
    53 
    54 /**
    55 *
    56 * CMmfGsm610ToPcm16HwDevice
    57 *
    58 */
    59 CMmfGsm610ToPcm16HwDevice::~CMmfGsm610ToPcm16HwDevice()
    60 	{
    61 	}
    62 
    63 
    64 /**
    65 *
    66 * ConstructL
    67 *
    68 */
    69 void CMmfGsm610ToPcm16HwDevice::ConstructL()
    70 	{
    71 	CMMFGsm610ToPcm16Codec* ptr= new(ELeave)CMMFGsm610ToPcm16Codec();
    72 	CleanupStack::PushL(ptr); 
    73 	ptr->ConstructL();
    74 	iCodec = ptr;
    75 	CleanupStack::Pop(ptr);
    76 	}
    77 
    78 /**
    79 *
    80 * CMmfPcm16ToGsm610HwDevice
    81 *
    82 */
    83 CMmfPcm16ToGsm610HwDevice* CMmfPcm16ToGsm610HwDevice::NewL()
    84 	{
    85 	CMmfPcm16ToGsm610HwDevice* self=new(ELeave) CMmfPcm16ToGsm610HwDevice();
    86 	CleanupStack::PushL(self);
    87 	self->ConstructL();
    88 	CleanupStack::Pop(self);
    89 	return self;
    90 	}
    91 
    92 /**
    93 *
    94 * Codec
    95 * @return CMMFSwCodec&
    96 *
    97 */
    98 CMMFSwCodec& CMmfPcm16ToGsm610HwDevice::Codec()
    99 	{
   100 	return *iCodec;
   101 	}
   102 
   103 /**
   104 *
   105 * ~CMmfPcm16ToGsm610HwDevice
   106 *
   107 */
   108 CMmfPcm16ToGsm610HwDevice::~CMmfPcm16ToGsm610HwDevice()
   109 	{
   110 	}
   111 
   112 /**
   113 *
   114 * ConstructL
   115 *
   116 */
   117 void CMmfPcm16ToGsm610HwDevice::ConstructL()
   118 	{
   119 	CMMFPcm16ToGsm610Codec* ptr =new(ELeave) CMMFPcm16ToGsm610Codec();
   120 	CleanupStack::PushL(ptr); 
   121 	ptr->ConstructL();
   122 	iCodec = ptr;
   123 	CleanupStack::Pop(ptr);
   124 	}
   125 
   126 /**
   127 *
   128 * CMMFGsm610ToPcm16Codec
   129 *
   130 */
   131 CMMFGsm610ToPcm16Codec::CMMFGsm610ToPcm16Codec()
   132 	{	
   133 	}
   134 
   135 /**
   136 *
   137 * ConstructL
   138 *
   139 */
   140 void CMMFGsm610ToPcm16Codec::ConstructL()
   141 	{
   142     iGsmDecoder = new (ELeave) CGSM610FR_Decoder;
   143 	iGsmDecoder->ConstructL();
   144 	iGsmDecoder->StartL();
   145 	}
   146 
   147 /**
   148 *
   149 * NewL
   150 *
   151 */
   152 CMMFGsm610ToPcm16Codec*  CMMFGsm610ToPcm16Codec::NewL()
   153 	{
   154 	CMMFGsm610ToPcm16Codec* self=new(ELeave) CMMFGsm610ToPcm16Codec();
   155 	CleanupStack::PushL(self);
   156 	self->ConstructL();
   157 	CleanupStack::Pop(self);
   158 	return self;
   159 	}
   160 
   161 /**
   162 *
   163 * ~CMMFGsm610ToPcm16Codec
   164 *
   165 */
   166 CMMFGsm610ToPcm16Codec::~CMMFGsm610ToPcm16Codec()
   167 	{
   168 	delete iGsmDecoder;
   169 	}
   170 
   171 /**
   172 *
   173 * ProcessL
   174 * @param aSource
   175 * @param aDest
   176 * @precondition input buffer length is mod 65
   177 * @precondition output buffer has sufficient space for coded input
   178 *
   179 */
   180 CMMFSwCodec::TCodecProcessResult CMMFGsm610ToPcm16Codec::ProcessL(const CMMFBuffer& aSrc, CMMFBuffer& aDest)
   181 	{
   182 	CMMFSwCodec::TCodecProcessResult result;
   183 	result.iCodecProcessStatus = TCodecProcessResult::EProcessComplete;
   184 
   185 	//convert from generic CMMFBuffer to CMMFDataBuffer
   186 	CMMFBuffer* pSrcBuffer =const_cast<CMMFBuffer*>(&aSrc);
   187 	if( !pSrcBuffer )
   188 		{
   189 		User::Leave( KErrArgument );
   190 		}
   191 
   192 	CMMFDataBuffer* src = static_cast<CMMFDataBuffer*>( pSrcBuffer );
   193     if( !src )
   194 		{
   195 		User::Leave( KErrArgument );
   196 		}
   197 
   198 	CMMFDataBuffer* dst = static_cast<CMMFDataBuffer*>(&aDest);
   199 	if( !dst )
   200 		{
   201 		User::Leave( KErrArgument );
   202 		}
   203 
   204 	if(!CheckInputBuffers( *src, *dst ))
   205 		{
   206 		User::Leave( KErrArgument );
   207 		}
   208 
   209 	TInt numBuffersToProcess = NumBuffersToProcess( *src );
   210 	TUint8* pSrc = CONST_CAST(TUint8*,src->Data().Ptr());
   211 	TUint8* pDst = CONST_CAST(TUint8*,dst->Data().Ptr());
   212 	
   213 	for( TInt count = 0; count < numBuffersToProcess; count++ )
   214 		{
   215 		// Encode two frames of gsm data
   216 		iGsmDecoder->ExecuteL( pSrc, pDst );
   217 		pSrc                      += KGsmFrameSize;;
   218 		pDst                      += KPcmDataForGsmFrame;
   219 		result.iSrcBytesProcessed += KGsmFrameSize;
   220 		result.iDstBytesAdded     += KPcmDataForGsmFrame;
   221 		}
   222 
   223     dst->Data().SetLength( result.iDstBytesAdded );
   224 	__ASSERT_DEBUG( ProcessPostCondition( result ), TMmfGsmCodecPanicsNameSpace::Panic( TMmfGsmCodecPanicsNameSpace::EPostConditionViolation ));
   225 	return result;
   226 	}
   227 
   228 /**
   229 *
   230 * CheckInputBuffers
   231 * @param aSrc
   232 * @param aDest
   233 * @return TBool
   234 * This function returns ETrue if the preconditions of processL are met
   235 *
   236 */
   237 TBool CMMFGsm610ToPcm16Codec::CheckInputBuffers( CMMFDataBuffer& aSrc, CMMFDataBuffer& aDest )
   238 	{
   239 	TBool result = ETrue;    
   240     TInt numInputSubFrames     = aSrc.Data().Length() / KGsmFrameSize;
   241 	TInt numOutputSubFrames    = aDest.Data().MaxLength() / KPcmDataForGsmFrame;
   242 	TBool validInputDataLength = (aSrc.Data().Length() % KGsmFrameSize == 0) ? ETrue : aSrc.LastBuffer();
   243     
   244 	if( (numInputSubFrames > numOutputSubFrames) ||  // sufficient space in the output for the input
   245         (aSrc.Position() > 0 )  ||                   // position must be zero since we can eat all the data
   246 		(aDest.Position() > 0 ) ||
   247 		(!validInputDataLength))                         //position must be zero
   248 		{
   249 		result = EFalse;
   250 		}
   251 
   252 	return result;
   253 	}
   254 
   255 /**
   256 *
   257 * NumBuffersToProcess
   258 * @param aSrc
   259 * @return TBool
   260 * This method returns the number of buffers to process
   261 *
   262 */
   263 TInt CMMFGsm610ToPcm16Codec::NumBuffersToProcess( const CMMFDataBuffer& aSrc )
   264 	{
   265     TInt numBuffers = (aSrc.Data().Length() / KGsmFrameSize );
   266 	return numBuffers;
   267 	}
   268 
   269 /**
   270 *
   271 * ProcessPostCondition
   272 * @param aResult
   273 * @result TBool Etrue if the post condition is satisfied
   274 *
   275 **/
   276 TBool CMMFGsm610ToPcm16Codec::ProcessPostCondition( const CMMFSwCodec::TCodecProcessResult& aResult )
   277 	{
   278      TBool status = ETrue;
   279 	 if( (aResult.iSrcBytesProcessed / KGsmFrameSize ) != (aResult.iDstBytesAdded / KPcmDataForGsmFrame ) )
   280 		 {
   281 		 status = EFalse;
   282 		 }
   283 	 return status;
   284 	}
   285 
   286 /************************>----------------------------------<*****************************/
   287 
   288 /**
   289 *
   290 * CMMFPcm16ToGsm610Codec
   291 *
   292 */
   293 CMMFPcm16ToGsm610Codec::CMMFPcm16ToGsm610Codec()
   294 	{	
   295 	}
   296 
   297 /**
   298 *
   299 * ConstructL
   300 *
   301 */
   302 void CMMFPcm16ToGsm610Codec::ConstructL()
   303 	{
   304 	iGsmEncoder = new (ELeave) CGSM610FR_Encoder;
   305 	iGsmEncoder->ConstructL();
   306 	iGsmEncoder->StartL();
   307 	}
   308 
   309 /**
   310 *
   311 * NewL
   312 *
   313 */
   314 CMMFPcm16ToGsm610Codec* CMMFPcm16ToGsm610Codec::NewL()
   315 	{
   316 	CMMFPcm16ToGsm610Codec* self=new(ELeave) CMMFPcm16ToGsm610Codec();
   317 	CleanupStack::PushL(self);
   318 	self->ConstructL();
   319 	CleanupStack::Pop(self);
   320 	return self;
   321 	}
   322 
   323 /**
   324 *
   325 * CMMFPcm16ToGsm610Codec
   326 *
   327 */
   328 CMMFPcm16ToGsm610Codec::~CMMFPcm16ToGsm610Codec()
   329 	{
   330 	delete iGsmEncoder;
   331 	}
   332 
   333 /**
   334 *
   335 * ProcessL
   336 * @param aSource
   337 * @param aDest TCodecProcessResult
   338 * @result
   339 * @precondition input buffer length is mod 320
   340 * @precondition output buffer has sufficient space for coded input
   341 */
   342 CMMFSwCodec::TCodecProcessResult CMMFPcm16ToGsm610Codec::ProcessL(const CMMFBuffer& aSrc, CMMFBuffer& aDest)
   343 	{
   344 	CMMFSwCodec::TCodecProcessResult result;
   345 	result.iCodecProcessStatus = TCodecProcessResult::EProcessComplete;
   346 
   347 	//convert from generic CMMFBuffer to CMMFDataBuffer
   348 	CMMFBuffer* pSrcBuffer =const_cast<CMMFBuffer*>(&aSrc);
   349 	if( !pSrcBuffer )
   350 		{
   351 		User::Leave( KErrArgument );
   352 		}
   353 
   354 	CMMFDataBuffer* src = static_cast<CMMFDataBuffer*>( pSrcBuffer );
   355     if( !src )
   356 		{
   357 		User::Leave( KErrArgument );
   358 		}
   359 
   360 	CMMFDataBuffer* dst = static_cast<CMMFDataBuffer*>(&aDest);
   361 	if( !dst )
   362 		{
   363 		User::Leave( KErrArgument );
   364 		}
   365 
   366 
   367 	if(!CheckInputBuffers( *src, *dst ))
   368 		{
   369 		User::Leave( KErrArgument );
   370 		}
   371 
   372 	TInt numBuffersToProcess = NumBuffersToProcess( *src );
   373 	TUint8* pSrc = CONST_CAST(TUint8*,src->Data().Ptr());
   374 	TUint8* pDst = CONST_CAST(TUint8*,dst->Data().Ptr());
   375 	
   376 	for( TInt count = 0; count < numBuffersToProcess; count++ )
   377 		{
   378 		// Encode two frames of gsm data
   379 		iGsmEncoder->ExecuteL (pSrc, pDst);
   380 		pSrc                      += KPcmDataForGsmFrame;
   381 		pDst                      += KGsmFrameSize;
   382 		result.iSrcBytesProcessed += KPcmDataForGsmFrame;
   383 		result.iDstBytesAdded     += KGsmFrameSize;
   384 		}
   385 
   386     dst->Data().SetLength( result.iDstBytesAdded ); 
   387 
   388 	__ASSERT_DEBUG( ProcessPostCondition(result), TMmfGsmCodecPanicsNameSpace::Panic( TMmfGsmCodecPanicsNameSpace::EPostConditionViolation ));
   389 
   390     return result ;
   391 	}
   392 
   393 /**
   394 *
   395 * CheckInputBuffers
   396 * @param aSrc
   397 * @param aDest
   398 * @return TBool
   399 * This function returns ETrue if there is sufficient space
   400 * in the output buffer for the coded input and
   401 * the position of both input buffers is zero
   402 *
   403 */
   404 TBool CMMFPcm16ToGsm610Codec::CheckInputBuffers( CMMFDataBuffer& aSrc, CMMFDataBuffer& aDest )
   405 	{
   406 	TBool result = ETrue;    
   407     TInt numInputSubFrames     = aSrc.Data().Length() / KPcmDataForGsmFrame;
   408 	TInt numOutputSubFrames    = aDest.Data().MaxLength() / KGsmFrameSize;
   409 #ifdef EABI
   410 	TBool validInputDataLength = (aSrc.Data().Length() % KPcmDataForGsmFrame == 0);
   411 #else
   412 	TBool validInputDataLength = (aSrc.LastBuffer()? ETrue: (aSrc.Data().Length() % KPcmDataForGsmFrame == 0));
   413 #endif
   414 	if( (numInputSubFrames > numOutputSubFrames) ||  // sufficient space in the output for the input
   415         (aSrc.Position() > 0 )  ||                   // position must be zero since we can eat all the data
   416 		(aDest.Position() > 0 ) ||
   417 		(!validInputDataLength))                         //position must be zero
   418 		{
   419 		result = EFalse;
   420 		}
   421 
   422 	return result;
   423 	}
   424 
   425 /**
   426 *
   427 * NumBuffersToProcess
   428 * @param aSrc
   429 * @return TBool
   430 * This method returns the number of buffers to process
   431 *
   432 */
   433 TInt CMMFPcm16ToGsm610Codec::NumBuffersToProcess( const CMMFDataBuffer& aSrc )
   434 	{
   435 	TInt numBuffers = ( aSrc.Data().Length() / KPcmDataForGsmFrame );
   436 	return numBuffers;
   437 	}
   438