contentmgmt/cafstreamingsupport/test/tscaf/source/tscafstep.cpp
branchRCL_3
changeset 43 2f10d260163b
child 61 641f389e9157
equal deleted inserted replaced
42:eb9b28acd381 43:2f10d260163b
       
     1 // Copyright (c) 2007-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 the License "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 // Implements the basic test step for the Streaming CAF test harness
       
    15 // 
       
    16 //
       
    17 
       
    18 #include "tscafstep.h"
       
    19 #ifdef INTERNALLY_ENABLE_UPWARD_DEPENDENCY
       
    20 #include <sdpconnectionfield.h>
       
    21 #include <sdporiginfield.h>
       
    22 #endif
       
    23 
       
    24 TSdpAttribute::TSdpAttribute()
       
    25 	{
       
    26 	}
       
    27 
       
    28 CTestDecoderConfiguration* CTestDecoderConfiguration::NewLC()
       
    29 	{
       
    30 	CTestDecoderConfiguration* self = new (ELeave) CTestDecoderConfiguration();
       
    31 	CleanupStack::PushL(self);
       
    32 	return self;	
       
    33 	}
       
    34 	
       
    35 CTestDecoderConfiguration::~CTestDecoderConfiguration()
       
    36 	{
       
    37 	iAttributeArray.Close();	
       
    38 	}
       
    39 
       
    40 CTestDecoderConfiguration::CTestDecoderConfiguration()
       
    41 	{	
       
    42 	} 
       
    43 
       
    44 TExpectedKeyStreamDecoderAttributes::TExpectedKeyStreamDecoderAttributes()
       
    45 	{
       
    46 	}
       
    47 
       
    48 CScafStep::CScafStep(CScafServer& aParent)
       
    49 /**
       
    50  	Constructor.
       
    51  */
       
    52 	: iParent(aParent), iThreadId(0), iOOMTest(EFalse)
       
    53 	{
       
    54 	//empty
       
    55 	}
       
    56 
       
    57 CScafStep::~CScafStep()
       
    58 /**
       
    59  	Destructor.
       
    60  */
       
    61 	{
       
    62 	//empty
       
    63 	}
       
    64 	
       
    65 	
       
    66 TVerdict CScafStep::doTestStepPreambleL()
       
    67 /**
       
    68  	From CTestStep. Creates an active scheduler for the test step.
       
    69  */
       
    70 	{
       
    71 	__UHEAP_MARK;
       
    72 	INFO_PRINTF2(_L("HEAP CELLS: %d"), User::CountAllocCells());
       
    73 	
       
    74 	iActiveScheduler = new (ELeave) CActiveScheduler;
       
    75 	CActiveScheduler::Install(iActiveScheduler);
       
    76 	
       
    77 	ReadTestConfigurationL();
       
    78 	
       
    79 	SetTestStepResult(EPass);
       
    80 	return TestStepResult();
       
    81 	}
       
    82 
       
    83 TVerdict CScafStep::doTestStepL()
       
    84 /**
       
    85  * From CTestStep. Default behaviour of doTestStepL() allows for the test case to be run both
       
    86  * under 'Normal' and 'Out of Memory' Conditions. 
       
    87  * 
       
    88  * Implementation of the test case itself is called from the doTestL() of the derived test step.
       
    89  * 
       
    90  * The state of the iOOMTest member variable determines the type of test conditons:
       
    91  * EFalse - Normal Test 
       
    92  * ETrue - Out of Memory Test
       
    93  */
       
    94 	{
       
    95 	if (!iOOMTest)
       
    96 		{
       
    97 		doTestL();
       
    98 		}
       
    99 	else
       
   100 		{
       
   101 		doOOMTestL();
       
   102 		}	
       
   103 	
       
   104 	return TestStepResult();
       
   105 	}
       
   106 
       
   107 TVerdict CScafStep::doTestStepPostambleL()
       
   108 /**
       
   109  	From CTestStep. Destroys the active scheduler of the test step.
       
   110  */
       
   111 	{
       
   112 	CActiveScheduler::Install(NULL);
       
   113 	delete iActiveScheduler;
       
   114 	
       
   115 	iDecoderConfigurationArray.ResetAndDestroy();
       
   116 	iExpectedKeyStreamDecoderData.Close();
       
   117 	
       
   118 	INFO_PRINTF2(_L("HEAP CELLS: %d"),User::CountAllocCells());
       
   119 	__UHEAP_MARKEND;
       
   120 	
       
   121 	return TestStepResult();
       
   122 	}
       
   123 
       
   124 #ifdef INTERNALLY_ENABLE_UPWARD_DEPENDENCY
       
   125 // We need this dummy function because TCleanupItem c'tor (see below) does not accept functions without parameters
       
   126 void CloseSdpCodecPool(TAny *)
       
   127 	{
       
   128 	SdpCodecStringPool::Close();
       
   129 	}
       
   130 
       
   131 CSdpDocument* CScafStep::CreateSdpDocumentLC()
       
   132 /**
       
   133  	Creates an SDP document object which is a collection of all media fields and session attributes.
       
   134  	@return A pointer to the SDP document object. 
       
   135  			The ownership is transferred. Please note that
       
   136  			the returned object must be deleted by DeleteSdpAndCloseCodecPool method.
       
   137  */
       
   138 	{
       
   139 	// Open the string pool to access all predefined SDP constants
       
   140 	SdpCodecStringPool::OpenL();
       
   141 	CleanupStack::PushL(TCleanupItem(CloseSdpCodecPool,this)); //Pass the class pointer to make armv5 compiler (for urel) happy
       
   142 	
       
   143 	// Create the CSdpDocument object
       
   144 	CSdpDocument* sdpDocument = CSdpDocument::NewLC();
       
   145 	
       
   146 	// Define the session name
       
   147 	sdpDocument->SetSessionNameL(_L8("ScafTest"));
       
   148 	
       
   149 	// Set the origin field. The values are not important. 
       
   150 	// Because they are not used in our tests.
       
   151 	TInt64 sessionId(TUint(2055478987));
       
   152 	TInt64 sessionVersion(TUint(2027813655));
       
   153 	TInetAddr address;
       
   154 	const TUint32 KInetAddr = INET_ADDR(192,168,0,3);
       
   155 	address.SetAddress( KInetAddr );
       
   156 	CSdpOriginField* originField = CSdpOriginField::NewLC(_L8("scafuser"), sessionId, sessionVersion, address);
       
   157 	sdpDocument->SetOriginField(originField);
       
   158 	CleanupStack::Pop(originField);
       
   159 	
       
   160 	CleanupStack::Pop(); // Pop the temporary guard on SDP Codec string pool close
       
   161 	CleanupStack::Pop(); // Pop sdpDocument object
       
   162 	CleanupStack::PushL(TCleanupItem(CScafStep::DeleteSdpDocAndCloseCodecPool, reinterpret_cast<TAny *>(sdpDocument)));
       
   163 	
       
   164 	return sdpDocument;
       
   165 	}
       
   166 
       
   167 void CScafStep::AddMediaFieldL(CSdpDocument& aSdpDoc, const CSdpMediaField* aSdpKeyStream)
       
   168 /**
       
   169  	Adds an SDP media field object to a given SDP document object.
       
   170  	@param aSdpDoc The SDP document object
       
   171  	@param aSdpKeyStream Sdp media field which will be appended to the SDP document object.
       
   172  						 This object should be popped from the cleanupstack after this function runs successfully.
       
   173  */
       
   174 	{
       
   175 	// Set the key stream field given
       
   176 	User::LeaveIfError(aSdpDoc.MediaFields().Append(aSdpKeyStream));
       
   177 	}
       
   178 
       
   179 CSdpMediaField* CScafStep::CreateSdpLC(TInt aSdpNum)
       
   180 /**
       
   181  	Creates a simple SDP media field object.
       
   182  	@param aSdpNum An integer representing the accessor to the SDP parameter
       
   183  	 		array and the required data 
       
   184  	@return A pointer to the SDP media field object. 
       
   185  			The ownership is transferred. Please note that
       
   186  			the returned object must be deleted by DeleteSdpAndCloseCodecPool method.
       
   187  	@see CScafStep::DeleteSdp
       
   188  */
       
   189 	{
       
   190 	TPtrC pMedia;
       
   191 	pMedia.Set(iDecoderConfigurationArray[aSdpNum]->iMedia);
       
   192 	
       
   193 	TInt mIndex = 0;
       
   194 	if(!pMedia.CompareF(KSdpMediaAudio))
       
   195 		{
       
   196 		mIndex = SdpCodecStringConstants::EMediaAudio;
       
   197 		}
       
   198 	else if(!pMedia.CompareF(KSdpMediaVideo))
       
   199 		{
       
   200 		mIndex = SdpCodecStringConstants::EMediaVideo;
       
   201 		}
       
   202 	else if(!pMedia.CompareF(KSdpMediaData))
       
   203 		{
       
   204 		mIndex = SdpCodecStringConstants::EMediaData;
       
   205 		}
       
   206 	else
       
   207 		{
       
   208 		ERR_PRINTF2(_L("Unsupported media type: '%S'"),&pMedia);
       
   209 		SetTestStepResult(EFail);
       
   210 		User::Leave(KErrNotFound);
       
   211 		}
       
   212 	
       
   213 	TPtrC pProtocol;
       
   214 	pProtocol.Set(iDecoderConfigurationArray[aSdpNum]->iProtocol);
       
   215 	
       
   216 	TInt mProtocol = 0;
       
   217 	if(!pProtocol.CompareF(KSdpProtocolUdp))
       
   218 		{
       
   219 		mProtocol = SdpCodecStringConstants::EProtocolUdp;
       
   220 		}
       
   221 	else if(!pProtocol.CompareF(KSdpProtocolTcp))
       
   222 		{
       
   223 		mProtocol = SdpCodecStringConstants::EProtocolTcp;
       
   224 		}
       
   225 	else if(!pProtocol.CompareF(KSdpProtocolRtp))
       
   226 		{
       
   227 		mProtocol = SdpCodecStringConstants::EProtocolRtpAvp;
       
   228 		}
       
   229 	else
       
   230 		{
       
   231 		ERR_PRINTF2(_L("Unsupported protocol type: '%S'"),mProtocol);
       
   232 		SetTestStepResult(EFail);
       
   233 		User::Leave(KErrNotFound);
       
   234 		}
       
   235 	
       
   236 	TInt port = iDecoderConfigurationArray[aSdpNum]->iPort;
       
   237 	
       
   238 	TPtrC pFormat;
       
   239 	pFormat.Set(iDecoderConfigurationArray[aSdpNum]->iFormat);
       
   240 	
       
   241 	//Convert 16-bit to 8-bit
       
   242 	TPtr8 ptrFormat(Convert16To8LC(pFormat));
       
   243 		
       
   244 	RStringPool pool = SdpCodecStringPool::StringPoolL();	
       
   245 	RStringF mediaData = pool.StringF(mIndex, SdpCodecStringPool::StringTableL());
       
   246 	CleanupClosePushL(mediaData);
       
   247 	RStringF protocol = pool.StringF(mProtocol, SdpCodecStringPool::StringTableL());
       
   248 	CleanupClosePushL(protocol);
       
   249 
       
   250 	CSdpMediaField* sdp = CSdpMediaField::NewL(mediaData, port, protocol, ptrFormat);
       
   251 	CleanupStack::PopAndDestroy(3);
       
   252 	CleanupStack::PushL(sdp);
       
   253 	
       
   254 	//If a connection address is defined, create an SDP connection field and add it to the SDP media field
       
   255 	if(iDecoderConfigurationArray[aSdpNum]->iConnAddr.Length()>0)
       
   256 		{
       
   257 		//The only supported network type is ENetType
       
   258 		RStringF netType = pool.StringF(SdpCodecStringConstants::ENetType, SdpCodecStringPool::StringTableL());
       
   259 		CleanupClosePushL(netType);
       
   260 		//The only supported address type is IP v4
       
   261 		RStringF addressType = pool.StringF(SdpCodecStringConstants::EAddressTypeIP4, SdpCodecStringPool::StringTableL());
       
   262 		CleanupClosePushL(addressType);
       
   263 		//Create the connection field
       
   264 		CSdpConnectionField* connField = CSdpConnectionField::NewL(netType, addressType, Convert16To8LC(iDecoderConfigurationArray[aSdpNum]->iConnAddr));
       
   265 		CleanupStack::PushL(connField);
       
   266 		//Set the connection field into the SDP media field
       
   267 		sdp->ConnectionFields().AppendL(connField);
       
   268 		CleanupStack::Pop(connField);
       
   269 		CleanupStack::PopAndDestroy(3, &netType); //netType, addressType, Convert16To8LC
       
   270 		}
       
   271 	
       
   272 	//Add atrributes
       
   273 	AddAttributes2SdpL(*sdp, aSdpNum);
       
   274 	
       
   275 	return sdp;
       
   276 	}
       
   277 #endif
       
   278 
       
   279 CKeyStreamSink* CScafStep::CreateKeyStreamSinkLC(const TDesC& aFileName, const TDesC& aPrivPath)
       
   280 /**
       
   281  	Creates a test key stream sink object.
       
   282  	@param aFilePath The output file name of the test key stream sink.
       
   283  	@param aPrivPath Stream Agents Private Folder Path
       
   284  	@return A pointer to the test key stream sink object. 
       
   285  			The ownership is transferred.
       
   286  */
       
   287 	{
       
   288 	HBufC* privFolder = GetFullPathLC(aPrivPath, aFileName);
       
   289 	CTestKeyStreamSink* sink = CTestKeyStreamSink::NewL(*privFolder);
       
   290 	CleanupStack::PopAndDestroy(privFolder);
       
   291 	CleanupStack::PushL(sink);
       
   292 	return sink;
       
   293 	}
       
   294 
       
   295 void CScafStep::CleanAgentsPrivateFolderL(const TDesC& aPrivatePath)
       
   296 /**
       
   297  	Delete all files and folders under the private directory of the test agent.
       
   298  */
       
   299 	{
       
   300 	HBufC* agentPrivFol = GetFullPathLC(aPrivatePath, _L("*.*"));
       
   301 	CFileMan *fm = CFileMan::NewL(iParent.Fs());
       
   302 	CleanupStack::PushL(fm);
       
   303 	
       
   304 	TInt ret = fm->Delete(*agentPrivFol,0);
       
   305 	if((ret != KErrNone)&&(ret != KErrNotFound)&&(ret != KErrPathNotFound))
       
   306 		{
       
   307 		User::Leave(ret);
       
   308 		}
       
   309 	CleanupStack::PopAndDestroy(2, agentPrivFol);
       
   310 	}
       
   311 
       
   312  
       
   313 void CScafStep::DeleteSdpDocAndCloseCodecPool(TAny* aSdpDoc)
       
   314 /**
       
   315  	Delete the SDP document object and close the codec pool
       
   316  	@param aSdp The SDP object which will be deleted.
       
   317  */
       
   318 	{
       
   319 #ifdef INTERNALLY_ENABLE_UPWARD_DEPENDENCY
       
   320 	delete reinterpret_cast<CSdpDocument *>(aSdpDoc);
       
   321 	SdpCodecStringPool::Close();
       
   322 #else
       
   323 	(void) aSdpDoc;
       
   324 #endif
       
   325 	}
       
   326 
       
   327 void CScafStep::CopyFile2AgentsPrivateFolderL(RFs& aFs, const TDesC& aFileName, const TDesC& aPrivPath)
       
   328 /**
       
   329  	Copy a test file from Z drive to the private folder of the test agent server.
       
   330  	@param aFs File Server session.
       
   331  	@param aPrivPath Stream Agents Private Folder Path
       
   332  	@param aFileName The name of the file which lives in the folder of Z drive.
       
   333  */
       
   334 	{
       
   335 	//Gets the target file path
       
   336 	HBufC* fTarget = GetFullPathLC(aPrivPath, aFileName);
       
   337 	//Make sure that the path exists
       
   338 	TInt err = aFs.MkDirAll(*fTarget);
       
   339 	if(err != KErrNone && err != KErrAlreadyExists)
       
   340 		{
       
   341 		User::Leave(err);
       
   342 		}
       
   343 	
       
   344 	//Get the file source path
       
   345 	TFileName fSource(KDataFilesPath);
       
   346 	fSource.Append(aFileName);
       
   347 	
       
   348 	//Create a file manager
       
   349 	CFileMan *fm = CFileMan::NewL(aFs);
       
   350 	CleanupStack::PushL(fm);
       
   351 	
       
   352 	//Copy the source file to the target
       
   353 	User::LeaveIfError(fm->Copy(fSource, *fTarget));
       
   354 	// Make the file writeable 
       
   355     User::LeaveIfError(fm->Attribs(*fTarget, 0, KEntryAttReadOnly, TTime(0), 0));
       
   356 	CleanupStack::PopAndDestroy(2, fTarget);
       
   357 	}
       
   358 
       
   359 #ifdef INTERNALLY_ENABLE_UPWARD_DEPENDENCY
       
   360 void CScafStep::AddAttributes2SdpL(CSdpMediaField& aSdp, TInt aSdpNum)
       
   361 /**
       
   362  * Add attributes from the instance within the CSdpConfiguration array, where 
       
   363  * the attribute information is stored, into the SDP object being constructed.
       
   364  * @param aSdp The SDP object where the attribute is added.
       
   365  */
       
   366 	{	
       
   367 	TInt attrCount = iDecoderConfigurationArray[aSdpNum]->iAttributeArray.Count();
       
   368 
       
   369 	RStringPool pool = SdpCodecStringPool::StringPoolL();
       
   370 	
       
   371 	for(TInt i=0; i < attrCount; ++i)
       
   372 		{
       
   373 		TPtrC pAttrType;
       
   374 		pAttrType.Set(iDecoderConfigurationArray[aSdpNum]->iAttributeArray[i].iAttributeType);
       
   375 		
       
   376 		TPtrC pAttrName;
       
   377 		pAttrName.Set(iDecoderConfigurationArray[aSdpNum]->iAttributeArray[i].iAttributeName);
       
   378 		
       
   379 		//Convert 16-bit to 8-bit
       
   380 		TPtr8 ptrAttrName(Convert16To8LC(pAttrName));
       
   381 		
       
   382 		TPtrC pAttrValue;
       
   383 		pAttrValue.Set(iDecoderConfigurationArray[aSdpNum]->iAttributeArray[i].iAttributeValue);
       
   384 		
       
   385 		//Convert 16-bit to 8-bit
       
   386 		TPtr8 ptrAttrValue(Convert16To8LC(pAttrValue));
       
   387 		
       
   388 		if(pAttrType.Compare(_L("Format")))
       
   389 			{
       
   390 			RStringF attrName = pool.OpenFStringL(ptrAttrName);
       
   391 			CleanupClosePushL(attrName);
       
   392 			CSdpAttributeField *attribute = CSdpAttributeField::NewLC(attrName, ptrAttrValue);
       
   393 			User::LeaveIfError((aSdp.AttributeFields()).Append(attribute));
       
   394 			CleanupStack::Pop(attribute);
       
   395 			}
       
   396 		else
       
   397 			{
       
   398 			RStringF fmtpStr = pool.StringF(SdpCodecStringConstants::EAttributeFmtp, SdpCodecStringPool::StringTableL());
       
   399 			CleanupClosePushL(fmtpStr);
       
   400 			CSdpFmtAttributeField* fmtpAttribute = CSdpFmtAttributeField::NewLC(fmtpStr, ptrAttrName, ptrAttrValue);
       
   401 			User::LeaveIfError(aSdp.FormatAttributeFields().Append(fmtpAttribute));
       
   402 			CleanupStack::Pop(fmtpAttribute);
       
   403 			}
       
   404 		CleanupStack::PopAndDestroy(3);
       
   405 		}//for
       
   406 	}//End of function
       
   407 #endif
       
   408 
       
   409 void CScafStep::PrintErrorAndLeaveL(TDesC& aKey)
       
   410 /**
       
   411  	Prints an error message and then leaves with not found error.
       
   412  	@param aKey The name of the key which is not found.
       
   413  */
       
   414 	{
       
   415 	ERR_PRINTF2(_L("Failed to read '%S' key of configuration"), &aKey);
       
   416 	SetTestStepResult(EFail);
       
   417 	User::Leave(KErrNotFound);
       
   418 	}
       
   419 
       
   420 TPtr8 CScafStep::Convert16To8LC(TDesC& aDes)
       
   421 /**
       
   422  	Convert a 16-bit descriptor into 8-bit.
       
   423  	@param aVal The 16-bit descriptor.
       
   424  	@return The descriptor converted to 8-bit.
       
   425  */
       
   426 	{
       
   427 	HBufC8* buf = HBufC8::NewLC(aDes.Size());
       
   428 	TPtr8 ptr(buf->Des());
       
   429 	ptr.Copy(aDes);
       
   430 	return ptr;
       
   431 	}
       
   432 
       
   433 HBufC* CScafStep::GetFullPathLC(const TDesC& aPath, const TDesC& aFileName)
       
   434 /**
       
   435  	Create a fully qualified file path.
       
   436  	@param aPath The folder path of the file.
       
   437  	@param aFileName The name of the file.
       
   438  	@return A pointer to the fully qualified file path.
       
   439  */
       
   440 	{
       
   441 	HBufC* fullPath = HBufC::NewLC(aPath.Length()+aFileName.Length()+1);
       
   442 	TPtr ptr(fullPath->Des());
       
   443 	ptr.Copy(aPath);
       
   444 	ptr[0] = iParent.Fs().GetSystemDriveChar();
       
   445 	if(aFileName.Length()>0)
       
   446 		{
       
   447 		ptr.Append(aFileName);
       
   448 		}
       
   449 	return fullPath;
       
   450 	}
       
   451 
       
   452 CSraRightsObject* CScafStep::GetRightsObjectLC(const TDesC& aName, const TDesC& aPrivPath)
       
   453 /**
       
   454  	Reads the given RO file and creates a RO object.
       
   455  	@param aName The name of the RO file.
       
   456  	@param aPrivPath Stream Agents Private Folder Path
       
   457  	@return The RO object.
       
   458  */
       
   459 	{
       
   460 	RFile f;
       
   461 	HBufC* path = GetFullPathLC(aPrivPath, aName);
       
   462 	User::LeaveIfError(f.Open(iParent.Fs(), *path, EFileRead));
       
   463 	CleanupStack::PopAndDestroy(path);
       
   464 	CleanupClosePushL(f);
       
   465 	RFileReadStream stream(f);
       
   466 	CleanupClosePushL(stream);
       
   467 	CSraRightsObject* ro = CSraRightsObject::NewL(stream);
       
   468 	CleanupStack::PopAndDestroy(2, &f);
       
   469 	CleanupStack::PushL(ro);
       
   470 	return ro;
       
   471 	}
       
   472 
       
   473 TVerdict CScafStep::doOOMTestL()
       
   474 /**
       
   475  * 	Runs the test step under OOM Conditions checking that each heap allocation is fail safe
       
   476  */
       
   477 	{	
       
   478 	// Pre and Post test heap cell allocation counts
       
   479  	TInt cellCountAfter = 0;
       
   480 	TInt cellCountBefore = 0;
       
   481 	
       
   482 	/**
       
   483 	 * The loop tests each heap allocation under out of memory conditions to determine whether
       
   484 	 * the framework cleans up correctly without leaking memory.
       
   485 	 * 
       
   486 	 * The 'for' loop does not have any completion criteria, so the loop breaks out as soon 
       
   487 	 * as any of the following events occur:
       
   488 	 * a) The pre and post heap cell counts mismatch signalling a memory leakage
       
   489 	 * b) An unexpected leave (any leave with an error code other than 'KErrNoMemory')
       
   490 	 * c) All heap allocations have been tested and the test returns 'KErrNone'
       
   491 	 */
       
   492 	for (TInt testCount = 0; ; ++testCount)
       
   493  		{
       
   494  		__UHEAP_MARK;
       
   495  		__UHEAP_SETFAIL(RHeap::EDeterministic, testCount+1);
       
   496  		cellCountBefore = User::CountAllocCells();
       
   497  		TRAPD(err, doTestL());
       
   498  		cellCountAfter = User::CountAllocCells();
       
   499  		__UHEAP_MARKEND;
       
   500  		
       
   501  		INFO_PRINTF3(_L("OOM Test %d: Status = %d"),testCount,err);
       
   502  		
       
   503  		if (err == KErrNone)
       
   504  			{
       
   505 			INFO_PRINTF1(_L("OOM Test Finished"));
       
   506  			break;
       
   507  			}
       
   508  		else if(err == KErrNoMemory)
       
   509  			{
       
   510  			if (cellCountBefore != cellCountAfter)
       
   511  				{
       
   512  				ERR_PRINTF2(_L("OOM Test Result: Failed - Memory leakage on iteration %d"), testCount);
       
   513  				ERR_PRINTF2(_L("Pre-Test Heap Cell Count: %d"), cellCountBefore);
       
   514  				ERR_PRINTF2(_L("Post-Test Heap Cell Count: %d"), cellCountAfter);
       
   515  				SetTestStepResult(EFail);
       
   516  				break;
       
   517  				}
       
   518  			}
       
   519  		else
       
   520  			{
       
   521  			User::Leave(err);
       
   522  			break;
       
   523  			}
       
   524 		}
       
   525 	
       
   526 	return TestStepResult();
       
   527 	}
       
   528 
       
   529 TVerdict CScafStep::doTestL()
       
   530 	{
       
   531 	return TestStepResult();
       
   532 	}
       
   533 
       
   534 void CScafStep::ReadTestConfigurationL()
       
   535 	{
       
   536 	TInt baseIndex=0;
       
   537 	
       
   538 	// Read SDP Configuration Data
       
   539 	TName fMedia;
       
   540 	TName fProtocol;
       
   541 	TName fPort;
       
   542 	TName fFormat;
       
   543 	TName fConnAddr;
       
   544 	
       
   545 	fMedia.Format(KSdpMedia, baseIndex);
       
   546 	fProtocol.Format(KSdpProtocol, baseIndex);
       
   547 	fPort.Format(KSdpPort, baseIndex);
       
   548 	fFormat.Format(KSdpFormat, baseIndex);
       
   549 	fConnAddr.Format(KSdpConnAddr, baseIndex);
       
   550 	
       
   551 	TPtrC mediaData;
       
   552 	TPtrC protocolData;
       
   553 	TInt portData;
       
   554 	TPtrC formatData;
       
   555 	TPtrC connAddrData;
       
   556 	
       
   557 	while (GetStringFromConfig(ConfigSection(), fMedia, mediaData) &&
       
   558 			GetStringFromConfig(ConfigSection(), fProtocol, protocolData) &&
       
   559 			GetIntFromConfig(ConfigSection(), fPort, portData) &&
       
   560 			GetStringFromConfig(ConfigSection(), fFormat, formatData))
       
   561 		{
       
   562 		
       
   563 		CTestDecoderConfiguration* newSdpConfig = CTestDecoderConfiguration::NewLC();
       
   564 		
       
   565 		newSdpConfig->iMedia.Set(mediaData);
       
   566 		newSdpConfig->iProtocol.Set(protocolData);
       
   567 		newSdpConfig->iPort = portData;
       
   568 		newSdpConfig->iFormat.Set(formatData);
       
   569 		
       
   570 		if(GetStringFromConfig(ConfigSection(), fConnAddr, connAddrData))
       
   571 			{
       
   572 			newSdpConfig->iConnAddr.Set(connAddrData);
       
   573 			}
       
   574 		
       
   575 		// Read Stream Associated Agents Private Folder Path
       
   576 		TName fPrivateFolderPath;
       
   577 		TName fSingleProcessAgent;
       
   578 		
       
   579 		fPrivateFolderPath.Format(KScafConfigPrivateFolderPath, baseIndex);
       
   580 		fSingleProcessAgent.Format(KScafConfigSingleProcessAgent, baseIndex);
       
   581 		
       
   582 		TPtrC privateFolderPath;
       
   583 		TBool singleProcessAgent;
       
   584 		
       
   585 		if(GetStringFromConfig(ConfigSection(), fPrivateFolderPath, privateFolderPath) &&
       
   586 			GetBoolFromConfig(ConfigSection(), fSingleProcessAgent, singleProcessAgent))
       
   587 			{
       
   588 			newSdpConfig->iPrivateFolderPath.Set(privateFolderPath);
       
   589 			newSdpConfig->iSingleProcessAgent = singleProcessAgent;
       
   590 			}
       
   591 		
       
   592 		// Read SDP Attribute Data
       
   593 		TInt attributeIndex = 0;
       
   594 		
       
   595 		TName fAttributeType;
       
   596 		TName fAttributeName;
       
   597 		TName fAttributeValue;
       
   598 		
       
   599 		fAttributeType.Format(KSdpAttributeType,baseIndex,attributeIndex);
       
   600 		fAttributeName.Format(KSdpAttributeName,baseIndex,attributeIndex);
       
   601 		fAttributeValue.Format(KSdpAttributeValue,baseIndex,attributeIndex);
       
   602 		
       
   603 		TPtrC attributeType;
       
   604 		TPtrC attributeName;
       
   605 		TPtrC attributeValue;
       
   606 		
       
   607 		while (GetStringFromConfig(ConfigSection(), fAttributeType, attributeType) &&
       
   608 				GetStringFromConfig(ConfigSection(), fAttributeName, attributeName) &&
       
   609 				GetStringFromConfig(ConfigSection(), fAttributeValue, attributeValue))
       
   610 				{
       
   611 				TSdpAttribute newAttribute;
       
   612 				
       
   613 				newAttribute.iAttributeType.Set(attributeType);
       
   614 				newAttribute.iAttributeName.Set(attributeName);
       
   615 				newAttribute.iAttributeValue.Set(attributeValue);
       
   616 				
       
   617 				newSdpConfig->iAttributeArray.Append(newAttribute);
       
   618 				
       
   619 				attributeIndex++;
       
   620 				fAttributeType.Format(KSdpAttributeType,baseIndex,attributeIndex);
       
   621 				fAttributeName.Format(KSdpAttributeName,baseIndex,attributeIndex);
       
   622 				fAttributeValue.Format(KSdpAttributeValue,baseIndex,attributeIndex);
       
   623 				}
       
   624 		
       
   625 		iDecoderConfigurationArray.Append(newSdpConfig);
       
   626 		
       
   627 		CleanupStack::Pop(newSdpConfig);
       
   628 		
       
   629 		baseIndex++;
       
   630 		fMedia.Format(KSdpMedia, baseIndex);
       
   631 		fProtocol.Format(KSdpProtocol, baseIndex);
       
   632 		fPort.Format(KSdpPort, baseIndex);
       
   633 		fFormat.Format(KSdpFormat, baseIndex);
       
   634 		fConnAddr.Format(KSdpConnAddr, baseIndex);
       
   635 		}
       
   636 	
       
   637 	// Read Expected Key Stream Decoder Attribute Values
       
   638 	TName fIsProgramProtected;
       
   639 	TName fIsServiceProtected;
       
   640 	TName fCanExport;
       
   641 	TName fMustProtectIfRecording;
       
   642 	TName fCanPlay;
       
   643 	TName fContentId;
       
   644 	TName fRightsIssuerUri;
       
   645 	
       
   646 	baseIndex = 0;
       
   647 	
       
   648 	fIsProgramProtected.Format(KScafConfigIsProgramProtected,baseIndex);
       
   649 	fIsServiceProtected.Format(KScafConfigIsServiceProtected,baseIndex);
       
   650 	fCanExport.Format(KScafConfigCanExport,baseIndex);
       
   651 	fMustProtectIfRecording.Format(KScafConfigMustProtectIfRecording,baseIndex);
       
   652 	fCanPlay.Format(KScafConfigCanPlay,baseIndex);
       
   653 	fContentId.Format(KScafConfigContentId,baseIndex);
       
   654 	fRightsIssuerUri.Format(KScafConfigRightsIssuerUri,baseIndex);
       
   655 	
       
   656 	TBool isProgramProtected;
       
   657 	TBool isServiceProtected;
       
   658 	TBool canExport;
       
   659 	TBool mustProtectIfRecording;
       
   660 	TBool canPlay;
       
   661 	TPtrC contentId;
       
   662 	TPtrC rightsIssuerUri;
       
   663 	
       
   664 	while(GetBoolFromConfig(ConfigSection(),fIsProgramProtected,isProgramProtected) &&
       
   665 		GetBoolFromConfig(ConfigSection(),fIsServiceProtected,isServiceProtected) &&
       
   666 		GetBoolFromConfig(ConfigSection(),fCanExport,canExport) &&
       
   667 		GetBoolFromConfig(ConfigSection(),fMustProtectIfRecording,mustProtectIfRecording) &&
       
   668 		GetBoolFromConfig(ConfigSection(),fCanPlay,canPlay) &&
       
   669 		GetStringFromConfig(ConfigSection(),fContentId,contentId) &&
       
   670 		GetStringFromConfig(ConfigSection(),fRightsIssuerUri,rightsIssuerUri))
       
   671 		{
       
   672 		TExpectedKeyStreamDecoderAttributes newExpectedValues;
       
   673 		
       
   674 		newExpectedValues.IsProgramProtected = isProgramProtected;
       
   675 		newExpectedValues.IsServiceProtected = isServiceProtected;
       
   676 		newExpectedValues.CanExport = canExport;
       
   677 		newExpectedValues.MustProtectIfRecording = mustProtectIfRecording;
       
   678 		newExpectedValues.CanPlay = canPlay;
       
   679 		newExpectedValues.ContentId.Set(contentId);
       
   680 		newExpectedValues.RightsIssuerUri.Set(rightsIssuerUri);
       
   681 		
       
   682 		iExpectedKeyStreamDecoderData.Append(newExpectedValues);
       
   683 		
       
   684 		baseIndex++;
       
   685 		fIsProgramProtected.Format(KScafConfigIsProgramProtected,baseIndex);
       
   686 		fIsServiceProtected.Format(KScafConfigIsServiceProtected,baseIndex);
       
   687 		fCanExport.Format(KScafConfigCanExport,baseIndex);
       
   688 		fMustProtectIfRecording.Format(KScafConfigMustProtectIfRecording,baseIndex);
       
   689 		fCanPlay.Format(KScafConfigCanPlay,baseIndex);
       
   690 		fContentId.Format(KScafConfigContentId,baseIndex);
       
   691 		fRightsIssuerUri.Format(KScafConfigRightsIssuerUri,baseIndex);
       
   692 		}
       
   693 	
       
   694 	// Read OOM Test Flag
       
   695 	GetBoolFromConfig(ConfigSection(), KScafConfigOOMTest, iOOMTest);
       
   696 	}
       
   697 
       
   698 TBool CScafStep::CheckKeyStreamDecoderAttributesL(const CKeyStreamDecoder& aDecoder,
       
   699 													const TExpectedKeyStreamDecoderAttributes& aExpectedData)
       
   700 	{
       
   701 	// Overall result of the attribute value checks (ETrue = Pass / EFalse = Fail)
       
   702 	TBool result = ETrue;
       
   703 	
       
   704 	_LIT(KIsProgramProtectedDescription,"IsProgramProtected");
       
   705 	_LIT(KIsServiceProtectedDescription,"IsServiceProtected");
       
   706 	_LIT(KCanExportDescription,"CanExport");
       
   707 	_LIT(KMustProtectIfRecordingDescription,"MustProtectIfRecording");
       
   708 	_LIT(KCanPlayDescription,"CanPlay");
       
   709 	_LIT(KContentIDDescription,"ContentID");
       
   710 	_LIT(KRightIssuerURIDescription,"RightIssuerURI");
       
   711 	
       
   712 	// Query the stream agent to determine whether the program is protected
       
   713 	if(!CompareBooleanAttributeL(aDecoder,
       
   714 								EIsProgramProtected,
       
   715 								KIsProgramProtectedDescription,
       
   716 								aExpectedData.IsProgramProtected))
       
   717 		{
       
   718 		result = EFalse;
       
   719 		}	
       
   720 	
       
   721 	// Query the stream agent to determine whether the whole service is protected
       
   722 	if(!CompareBooleanAttributeL(aDecoder,
       
   723 								EIsServiceProtected,
       
   724 								KIsServiceProtectedDescription,
       
   725 								aExpectedData.IsServiceProtected))
       
   726 		{
       
   727 		result = EFalse;
       
   728 		}
       
   729 	
       
   730 	// Query the stream agent to determine whether the content can be exported
       
   731 	if(!CompareBooleanAttributeL(aDecoder,
       
   732 								ECanExport,
       
   733 								KCanExportDescription,
       
   734 								aExpectedData.CanExport))
       
   735 		{
       
   736 		result = EFalse;
       
   737 		}
       
   738 	
       
   739 	// Query the stream agent to determine whether the content must be protected whilst recording
       
   740 	if(!CompareBooleanAttributeL(aDecoder,
       
   741 								EMustProtectIfRecording,
       
   742 								KMustProtectIfRecordingDescription,
       
   743 								aExpectedData.MustProtectIfRecording))
       
   744 		{
       
   745 		result = EFalse;
       
   746 		}	
       
   747 	
       
   748 	// Query the stream agent to determine whether the content can be played
       
   749 	if(!CompareBooleanAttributeL(aDecoder,
       
   750 								ECanPlay,
       
   751 								KCanPlayDescription,
       
   752 								aExpectedData.CanPlay))
       
   753 		{
       
   754 		result = EFalse;
       
   755 		}	
       
   756 	
       
   757 	// Query the stream agent to retrieve the Content ID
       
   758 	if(!CompareStringAttributeL(aDecoder,
       
   759 								EContentID,
       
   760 								KContentIDDescription,
       
   761 								aExpectedData.ContentId))
       
   762 		{
       
   763 		result = EFalse;
       
   764 		}
       
   765 	
       
   766 	// Query the stream agent to retrieve the Rights Issuer URI
       
   767 	if(!CompareStringAttributeL(aDecoder,
       
   768 								ERightsIssuerURI,
       
   769 								KRightIssuerURIDescription,
       
   770 								aExpectedData.RightsIssuerUri))
       
   771 		{
       
   772 		result = EFalse;
       
   773 		}
       
   774 	
       
   775 	return result;
       
   776 	}
       
   777 
       
   778 TBool CScafStep::CompareBooleanAttributeL(const CKeyStreamDecoder& aDecoder,
       
   779 											const TAttribute& aAttributeEnum,
       
   780 											const TDesC& aAttributeDescription,
       
   781 											const TBool aExpectedValue)
       
   782 	{
       
   783 	TBool retrievedValue;
       
   784 	
       
   785 	// Query the stream agent to determine the actual value of the attribute
       
   786 	TRAPD(err,aDecoder.GetAttributeL(aAttributeEnum,retrievedValue));
       
   787 	
       
   788 	if(err != KErrNone)
       
   789 		{
       
   790 		ERR_PRINTF4(_L("*** Thread %d: Failed to Retrieve '%S' Value - %d ***"),iThreadId,&aAttributeDescription,err);
       
   791 		User::Leave(err);
       
   792 		}
       
   793 	
       
   794 	if(retrievedValue != aExpectedValue)
       
   795 		{
       
   796 		INFO_PRINTF4(_L("Thread %d: Expected '%S' Value = %d"),iThreadId,&aAttributeDescription,aExpectedValue);
       
   797 		INFO_PRINTF4(_L("Thread %d: Retrieved '%S' Value = %d"),iThreadId,&aAttributeDescription,retrievedValue);
       
   798 		ERR_PRINTF3(_L("*** Thread %d: Unexpected '%S' Value ***"),iThreadId,&aAttributeDescription);
       
   799 		return EFalse;
       
   800 		}
       
   801 	
       
   802 	return ETrue;
       
   803 	}
       
   804 
       
   805 TBool CScafStep::CompareStringAttributeL(const CKeyStreamDecoder& aDecoder,
       
   806 											const TStringAttribute& aAttributeEnum,
       
   807 											const TDesC& aAttributeDescription,
       
   808 											const TDesC& aExpectedValue)
       
   809 	{
       
   810 	TBool result = ETrue;
       
   811 	
       
   812 	// Query the stream agent to determine the actual value of the attribute
       
   813 	HBufC* retrievedValue = aDecoder.GetStringAttributeLC(aAttributeEnum);
       
   814 	
       
   815 	if(retrievedValue->Des() != aExpectedValue)
       
   816 		{
       
   817 		INFO_PRINTF4(_L("Thread %d: Expected '%S' Value = %S"),iThreadId,&aAttributeDescription,&aExpectedValue);
       
   818 		INFO_PRINTF4(_L("Thread %d: Retrieved '%S' Value = %S"),iThreadId,&aAttributeDescription,retrievedValue);
       
   819 		ERR_PRINTF3(_L("*** Thread %d: Unexpected '%S' Value ***"),iThreadId,&aAttributeDescription);
       
   820 		result = EFalse;
       
   821 		}
       
   822 	
       
   823 	// Destroy the heap based descriptor
       
   824 	CleanupStack::PopAndDestroy(retrievedValue);
       
   825 	
       
   826 	return result;
       
   827 	}