os/mm/mmlibs/mmfw/src/Plugin/Codec/audio/MMFCodecBaseDefinitions.cpp
author sl
Tue, 10 Jun 2014 14:32:02 +0200
changeset 1 260cb5ec6c19
permissions -rw-r--r--
Update contrib.
     1 // Copyright (c) 1997-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 //
    15 
    16 #include "MMFCodecBaseDefinitions.h"
    17 #include "MMFAudioCodecBase.h"
    18 #include <mmf/common/mmfpaniccodes.h>
    19 
    20 // Base of Audio codecs
    21 // These T Classes are "wrapped" by derived MMFCodecs, not exposed directly.
    22 
    23 
    24 void Panic(TInt aPanicCode)
    25 	{
    26 	_LIT(KMMFCodecBaseDefinitionsPanicCategory, "MMFCodecBaseDefinitions");
    27 	User::Panic(KMMFCodecBaseDefinitionsPanicCategory, aPanicCode);
    28 	}
    29 
    30 
    31 void TMMFImaAdpcmBaseCodecOld::ResetBuffer()
    32 	{
    33 	iBufferStep = ETrue;
    34 	iBuffer = 0;
    35 	}
    36 
    37 TBool TMMFImaAdpcmBaseCodecOld::OutputStep()
    38 	{
    39 	return !iBufferStep;
    40 	}
    41 
    42 void TMMFImaAdpcmTo16PcmCodecOld::Convert(TUint8* aSrc, TUint8* aDst, TInt aSamples)
    43 	{
    44     TInt delta;			// Current adpcm output value 
    45     TInt step;			// Stepsize
    46     TInt valpred;		// Predicted value 
    47     TInt vpdiff;		// Current change to valpred 
    48     TInt index;			// Current step change index 
    49 
    50 	TInt channelCount=16;//for stereo only
    51 
    52 	aSamples*=iChannels;
    53 
    54 	//Read first sample and index from block header
    55 	iState[0].iPredicted = *aSrc++;
    56 	iState[0].iPredicted |= STATIC_CAST(TInt16, ((*aSrc++) << 8));
    57 	iState[0].iIndex = *aSrc++;
    58 
    59 	aSrc++; //skip reserved header byte
    60 
    61 	valpred = iState[0].iPredicted;
    62 	index = iState[0].iIndex;
    63 	TUint8* dst=aDst;
    64 
    65 	//Write first sample to dest
    66 	*aDst++ = STATIC_CAST( TUint8, valpred);
    67 	*aDst++ = STATIC_CAST( TUint8, valpred >> 8);
    68 	dst += 2;
    69 	aSamples --;
    70 
    71 	if (iChannels==2)
    72 		{
    73 		iState[1].iPredicted = *aSrc++;
    74 		iState[1].iPredicted |= STATIC_CAST(TInt16, ((*aSrc++) << 8));
    75 		iState[1].iIndex = *aSrc++;
    76 		aSrc++;
    77 
    78 		*aDst++ = STATIC_CAST( TUint8, iState[1].iPredicted);
    79 		*aDst++ = STATIC_CAST( TUint8, iState[1].iPredicted >> 8);
    80 		dst += 2;
    81 		aSamples --;
    82 		}
    83 
    84     for ( ; aSamples > 0 ; aSamples-- ) 
    85 		{ 
    86 		// Step 1 - get the delta value
    87 		if (iBufferStep) 
    88 			{
    89 			iBuffer = *aSrc++;
    90 			delta = iBuffer & 0xf;
    91 			} 
    92 		else 
    93 			{
    94 			delta = (iBuffer >> 4) & 0xf;
    95 			}
    96 
    97 		iBufferStep = !iBufferStep;
    98 
    99 		ASSERT(index >= 0);
   100 		step = iStepSizeTable[index];
   101 
   102 		vpdiff = step>>3;
   103 		if ( delta & 4 ) 
   104 			vpdiff += step;
   105 		if ( delta & 2 ) 
   106 			vpdiff += step>>1;
   107 		if ( delta & 1 ) 
   108 			vpdiff += step>>2;
   109 
   110 		if ( delta & 8 )
   111 			valpred -= vpdiff;
   112 		else
   113 			valpred += vpdiff;
   114 
   115 		if ( valpred > (KClamp - 1) )
   116 			valpred = (KClamp - 1);
   117 		else if ( valpred < -KClamp )
   118 			valpred = -KClamp;
   119 
   120 		index += iIndexTable[delta];
   121 		if ( index < 0 ) 
   122 			index = 0;
   123 		if ( index > KMaxImaAdpcmTableEntries ) 
   124 			index = KMaxImaAdpcmTableEntries;
   125 
   126 		*dst++ = STATIC_CAST( TUint8, valpred&KAndMask8bit);
   127 		*dst++ = STATIC_CAST( TUint8, (valpred>>8)&KAndMask8bit);
   128 
   129 		if (iChannels==2)
   130 			{
   131 			dst+=2;
   132 			if (--channelCount == 8)
   133 				{
   134 				dst=aDst+2;	//right channel
   135 				iState[0].iPredicted=STATIC_CAST(TInt16, valpred);
   136 				iState[0].iIndex=STATIC_CAST(TUint8,index);
   137 				valpred = iState[1].iPredicted;
   138 				index = iState[1].iIndex;
   139 				}
   140 			else
   141 				{
   142 				if (!channelCount)
   143 					{
   144 					aDst+=32;
   145 					dst=aDst;
   146 					channelCount=16;
   147 					iState[1].iPredicted=STATIC_CAST(TInt16, valpred);
   148 					iState[1].iIndex=STATIC_CAST(TUint8, index);
   149 					valpred = iState[0].iPredicted;
   150 					index = iState[0].iIndex;
   151 					}
   152 				}
   153 			}
   154 		}
   155 	if (iChannels==1)
   156 		{
   157 		iState[0].iPredicted=STATIC_CAST(TInt16,valpred);
   158 		iState[0].iIndex=STATIC_CAST(TUint8,index);
   159 		}
   160 	}
   161 
   162 void TMMF16PcmToImaAdpcmCodecOld::Convert(TUint8* aSrc, TUint8* aDst, TInt aSamples)
   163 	{
   164 	TInt val;			// Current input sample value 
   165     TInt sign;			// Current adpcm sign bit 
   166     TInt delta;			// Current adpcm output value 
   167 	TInt diff;			// Difference between val and valprev 
   168 	TInt step;			// Stepsize
   169     TInt valpred;		// Predicted value 
   170     TInt vpdiff;		// Current change to valpred 
   171     TInt index;			// Current step change index 
   172 	
   173 	TInt16* srcPtr=REINTERPRET_CAST(TInt16*, aSrc);
   174 	TInt16* src=srcPtr;
   175 
   176 	TInt bufferCount=16;//for stereo only
   177 
   178 	if (iChannels==2)
   179 		{
   180 		aSamples*=2;
   181 		iBufferStep=ETrue;
   182 		}
   183 
   184 	iState[0].iPredicted = *aSrc++;
   185 	iState[0].iPredicted |= STATIC_CAST(TInt16, ((*aSrc++) << 8));
   186 
   187     valpred = iState[0].iPredicted;
   188     index = iState[0].iIndex;
   189     ASSERT(index >= 0);
   190     step = iStepSizeTable[index];
   191 
   192 	//Write block header
   193 	*aDst++ = STATIC_CAST( TUint8, valpred);
   194 	*aDst++ = STATIC_CAST( TUint8, valpred >> 8);
   195 	*aDst++ = STATIC_CAST( TUint8, index);
   196 	*aDst++ = 0; //reserved byte
   197 	src++;
   198 	aSamples --;	
   199 
   200 	if (iChannels==2)
   201 		{
   202 		iState[1].iPredicted = *aSrc++;
   203 		iState[1].iPredicted |= STATIC_CAST(TInt16, ((*aSrc++) << 8));
   204 
   205 		//Write header for second channel
   206 		*aDst++ = STATIC_CAST( TUint8, iState[1].iPredicted);
   207 		*aDst++ = STATIC_CAST( TUint8, iState[1].iPredicted >> 8);
   208 		*aDst++ = STATIC_CAST( TUint8, iState[1].iIndex);
   209 		*aDst++ = 0;
   210 		src ++;
   211 		aSamples --;
   212 		}
   213 
   214 	for (; aSamples > 0; aSamples--) 
   215 		{ 
   216 		val = *src;
   217 		src += iChannels;
   218 
   219 		ASSERT(index >= 0);
   220 	    step = iStepSizeTable[index];
   221 
   222 		// Step 1 - compute difference with previous value 
   223 		diff = val - valpred;
   224 		sign = (diff < 0) ? 8 : 0;
   225 		if ( sign ) diff = (-diff);
   226 
   227 		// Step 2 - Divide and clamp 
   228 		// Note:
   229 		// This code *approximately* computes:
   230 		//    delta = diff*4/step;
   231 		//    vpdiff = (delta+0.5)*step/4;
   232 		// but in shift step bits are dropped. The net result of this is
   233 		// that even if you have fast mul/div hardware you cannot put it to
   234 		// good use since the fixup would be too expensive.
   235 		//
   236 		delta = 0;
   237 		vpdiff = (step >> 3);
   238 		
   239 		if ( diff >= step ) 
   240 			{
   241 			delta = 4;
   242 			diff -= step;
   243 			vpdiff += step;
   244 			}
   245 		step >>= 1;
   246 		if ( diff >= step  ) 
   247 			{
   248 			delta |= 2;
   249 			diff -= step;
   250 			vpdiff += step;
   251 			}
   252 		step >>= 1;
   253 		if ( diff >= step ) 
   254 			{
   255 			delta |= 1;
   256 			vpdiff += step;
   257 			}
   258 
   259 		// Step 3 - Update previous value 
   260 		if ( sign )
   261 		  valpred -= vpdiff;
   262 		else
   263 		  valpred += vpdiff;
   264 
   265 		// Step 4 - Clamp previous value to 16 bits 
   266 		if ( valpred > KClamp - 1 )
   267 		  valpred = KClamp - 1;
   268 		else if ( valpred < - KClamp )
   269 		  valpred = - KClamp;
   270 
   271 		// Step 5 - Assemble value, update index and step values 
   272 		delta |= sign;
   273 		
   274 		index += iIndexTable[delta];
   275 		if ( index < 0 ) index = 0;
   276 		if ( index > 88 ) index = 88;
   277 
   278 		// Step 6 - Output value 
   279 		if (iBufferStep) 
   280 			iBuffer = delta & 0x0f;
   281 		else 
   282 			*aDst++ = STATIC_CAST( TInt8, ((delta << 4) & 0xf0) | iBuffer);
   283 
   284 		iBufferStep = !iBufferStep;
   285 		
   286 		if (iChannels==2)
   287 			{
   288 			if (--bufferCount==8)
   289 				{
   290 				src=srcPtr+1;	//right channel
   291 				iState[0].iPredicted = STATIC_CAST(TInt16, valpred);
   292 				iState[0].iIndex = STATIC_CAST(TUint8, index);
   293 				valpred = iState[1].iPredicted;
   294 				index = iState[1].iIndex;
   295 				}
   296 			else
   297 				{
   298 				if (!bufferCount)
   299 					{
   300 					iState[1].iPredicted = STATIC_CAST(TInt16, valpred);
   301 					iState[1].iIndex = STATIC_CAST(TUint8, index);
   302 					valpred = iState[0].iPredicted;
   303 					index = iState[0].iIndex;
   304 					bufferCount=16;
   305 					srcPtr+=16;//32bytes
   306 					src=srcPtr;
   307 					}
   308 				}
   309 			}
   310 		}
   311 
   312 	if (iChannels==1)
   313 		{
   314 		iState[0].iPredicted = STATIC_CAST(TInt16, valpred);
   315 		iState[0].iIndex = STATIC_CAST(TUint8, index);
   316 		}
   317 	}
   318 
   319 // IMA-ADPCM step variation table 
   320 const TInt TMMFImaAdpcmBaseCodecOld::iIndexTable[16] =
   321  	{
   322     -1, -1, -1, -1, 2, 4, 6, 8,
   323     -1, -1, -1, -1, 2, 4, 6, 8
   324 	};
   325 
   326 const TInt TMMFImaAdpcmBaseCodecOld::iStepSizeTable[89] = 
   327 	{
   328     7, 8, 9, 10, 11, 12, 13, 14, 16, 17,
   329     19, 21, 23, 25, 28, 31, 34, 37, 41, 45,
   330     50, 55, 60, 66, 73, 80, 88, 97, 107, 118,
   331     130, 143, 157, 173, 190, 209, 230, 253, 279, 307,
   332     337, 371, 408, 449, 494, 544, 598, 658, 724, 796,
   333     876, 963, 1060, 1166, 1282, 1411, 1552, 1707, 1878, 2066,
   334     2272, 2499, 2749, 3024, 3327, 3660, 4026, 4428, 4871, 5358,
   335     5894, 6484, 7132, 7845, 8630, 9493, 10442, 11487, 12635, 13899,
   336     15289, 16818, 18500, 20350, 22385, 24623, 27086, 29794, 32767
   337 	};
   338 
   339