os/mm/mmlibs/mmfw/src/Client/Utility/mmfclientutility.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 // Audio, MIDI and Video client utility functions.
    15 // 
    16 //
    17 
    18 #include <e32std.h>
    19 #include <f32file.h>
    20 #include <bautils.h>
    21 #include <mmf/server/mmfdrmpluginserverproxy.h>
    22 #include <caf/content.h>
    23 #include <caf/data.h>
    24 using namespace ContentAccess;
    25 
    26 #include "mmfclientutility.h"
    27 #include <mmf/common/mmfpaniccodes.h>
    28 
    29 const TInt KMaxMimeLength = 256;
    30 const TInt KMaxHeaderSize = 256;
    31 const TInt KExpandSize = 100;
    32 
    33 #ifdef SYMBIAN_ENABLE_MMF_MULTISCREEN_SUPPORT
    34 	const TInt KDefaultScreenNo = 0;
    35 #endif
    36 
    37 void CUPanic(TInt aCUPanicCode)
    38 	{
    39 	_LIT(KMMFMediaClientUtilityPaanicCategory, "MMFClientUtility");
    40 	User::Panic(KMMFMediaClientUtilityPaanicCategory, aCUPanicCode);
    41 	}
    42 
    43 /**
    44  * @internalComponent
    45  */
    46 EXPORT_C TUid CMMFClientUtility::ConvertMdaFormatUidToECOMWrite(TUid aMdaFormatUid)
    47 	{
    48 	TUid ECOMUid = KNullUid;
    49 	if (aMdaFormatUid == KUidMdaClipFormatWav)	
    50 		ECOMUid = TUid::Uid(KMmfUidFormatWAVWrite);
    51 	else if (aMdaFormatUid == KUidMdaClipFormatAu)	
    52 		ECOMUid = TUid::Uid(KMmfUidFormatAUWrite);
    53 	else if (aMdaFormatUid == KUidMdaClipFormatRawAudio)	
    54 		ECOMUid = TUid::Uid(KMmfUidFormatRAWWrite);
    55 	else if (aMdaFormatUid == KUidMdaClipFormatRawAmr)	
    56 		ECOMUid = TUid::Uid(KAdvancedUidFormatAMRWrite);
    57 
    58 	return ECOMUid;
    59 	}
    60 
    61 /**
    62  * @internalComponent
    63  */
    64 EXPORT_C TUid CMMFClientUtility::ConvertMdaFormatUidToECOMRead(TUid aMdaFormatUid)
    65 	{
    66 	TUid ECOMUid = KNullUid;
    67 	if (aMdaFormatUid == KUidMdaClipFormatWav)	
    68 		ECOMUid = TUid::Uid(KMmfUidFormatWAVRead);
    69 	else if (aMdaFormatUid == KUidMdaClipFormatAu)	
    70 		ECOMUid = TUid::Uid(KMmfUidFormatAURead);
    71 	else if (aMdaFormatUid == KUidMdaClipFormatRawAudio)	
    72 		ECOMUid = TUid::Uid(KMmfUidFormatRAWRead);
    73 	else if (aMdaFormatUid == KUidMdaClipFormatRawAmr)	
    74 		ECOMUid = TUid::Uid(KAdvancedUidFormatAMRRead);
    75 
    76 	return ECOMUid;
    77 	}
    78 
    79 /**
    80  * @internalComponent
    81  */
    82 EXPORT_C TInt CMMFClientUtility::GetFileHeaderData(const TDesC& aFileName, TDes8& aHeaderData, TInt aMaxLength)
    83 	{
    84 	RFs fsSession;
    85 	RFile file;
    86 	TInt error = KErrNone;
    87 
    88 	if ((error = fsSession.Connect()) == KErrNone)
    89 		{
    90 		if ((error = file.Open(fsSession, aFileName, EFileShareReadersOrWriters)) == KErrNone)
    91 			{
    92 			TInt size = 0;
    93 
    94 			if ((error = file.Size(size)) == KErrNone)
    95 				{
    96 				if (size > 0)
    97 					{
    98 					if (size > aMaxLength) 
    99 						size = aMaxLength;
   100 
   101 					error = file.Read(aHeaderData, size);
   102 					}
   103 				}
   104 			file.Close();
   105 			}
   106 		fsSession.Close();
   107 		}
   108 
   109 	return error;
   110 	}
   111 
   112 /**
   113  * @internalComponent
   114  */
   115 EXPORT_C TFourCC CMMFClientUtility::ConvertMdaCodecToFourCC(TMdaPackage& aCodec)
   116 	{
   117 	TFourCC dataType = KMMFFourCCCodeNULL;	
   118 	switch (aCodec.Uid().iUid)
   119 		{
   120 		case KUidMdaWavPcmCodecDefine: 
   121 			{
   122 			TMdaPcmWavCodec* pcmWavCodec = (TMdaPcmWavCodec*)&aCodec;
   123 			if (pcmWavCodec->iBits == TMdaPcmWavCodec::E8BitPcm)
   124 				dataType = KMMFFourCCCodePCMU8; //8 bit PCM
   125 			else 
   126 				dataType = KMMFFourCCCodePCM16; //16 bit PCM
   127 			break;
   128 			}
   129 		case KUidMdaAu8PcmCodecDefine:
   130 			dataType = KMMFFourCCCodePCM8;
   131 			break;
   132 		case KUidMdaAuCodecDefine:
   133 		case KUidMdaAu16PcmCodecDefine:
   134 			dataType = KMMFFourCCCodePCM16B;
   135 			break;
   136 
   137 		case KUidMdaAuMulawCodecDefine:
   138 		case KUidMdaWavMulawCodecDefine:
   139 		case KUidMdaRawAudioMulawCodecDefine:  //uLAW
   140 			dataType = KMMFFourCCCodeMuLAW;
   141 			break;
   142 		case KUidMdaAuAlawCodecDefine:
   143 		case KUidMdaWavAlawCodecDefine:
   144 		case KUidMdaRawAudioAlawCodecDefine:	 //ALAW
   145 			dataType = KMMFFourCCCodeALAW;
   146 			break;
   147 		case KUidMdaRawAudioS8PcmCodecDefine:	 //  P8
   148 			dataType = KMMFFourCCCodePCM8;
   149 			break;
   150 		case KUidMdaRawAudioU8PcmCodecDefine:	  // PU8
   151 			dataType = KMMFFourCCCodePCMU8;
   152 			break;
   153 		case KUidMdaRawAudioSL16PcmCodecDefine: // P16
   154 			dataType = KMMFFourCCCodePCM16;
   155 			break;
   156 		case KUidMdaRawAudioSB16PcmCodecDefine: //P16B
   157 			dataType = KMMFFourCCCodePCM16B;
   158 			break;
   159 		case KUidMdaRawAudioUL16PcmCodecDefine: //PU16
   160 			dataType = KMMFFourCCCodePCMU16;
   161 			break;
   162 		case KUidMdaRawAudioUB16PcmCodecDefine: //PU6B
   163 			dataType = KMMFFourCCCodePCMU16B; 
   164 			break;
   165 		case KUidMdaGsmWavCodecDefine: //GSM6 
   166 			dataType = KMMFFourCCCodeGSM610;
   167 			break;
   168 		case KUidMdaWavImaAdpcmCodecDefine:
   169 			dataType = KMMFFourCCCodeIMAD;
   170 			break;
   171 		case KUidMdaRawAmrCodecDefine:
   172 			dataType = KMMFFourCCCodeAMR;
   173 			break;
   174 		default:	// Not a Uid we recognise
   175 			dataType = KMMFFourCCCodeNULL;
   176 			break;
   177 		}
   178 	return dataType;
   179 	}
   180 
   181 
   182 CMMFUtilityFileInfo* CMMFUtilityFileInfo::NewL(TMMSource& aSource, TBool aSecureDRMMode)
   183 	{
   184 	CMMFUtilityFileInfo* self = CMMFUtilityFileInfo::NewLC(aSource, aSecureDRMMode);
   185 	CleanupStack::Pop(self);
   186 	return self;
   187 	}
   188 
   189 
   190 CMMFUtilityFileInfo* CMMFUtilityFileInfo::NewLC(TMMSource& aSource, TBool aSecureDRMMode)
   191 	{
   192 	CMMFUtilityFileInfo* self = new (ELeave) CMMFUtilityFileInfo;
   193 	CleanupStack::PushL(self);
   194 	self->ConstructL(aSource, aSecureDRMMode);
   195 	return self;
   196 	}
   197 
   198 
   199 void CMMFUtilityFileInfo::ConstructL(const TMMSource& aSource, TBool aSecureDRMMode)
   200 	{
   201 	if (!aSecureDRMMode)
   202 		{
   203 		if (aSource.SourceType()==KUidMMFileSource)
   204 			{
   205 			const TMMFileSource& fileSource = static_cast<const TMMFileSource&>(aSource);
   206 			iData = CData::NewL(TVirtualPathPtr(fileSource.Name(), fileSource.UniqueId()),
   207 								EContentShareReadWrite);
   208 			}
   209 
   210 		if (aSource.SourceType()==KUidMMFileHandleSource)
   211 			{
   212 			const TMMFileHandleSource& fileHandleSource = static_cast<const TMMFileHandleSource&>(aSource);
   213 			iData = CData::NewL(fileHandleSource.Handle(), fileHandleSource.UniqueId());
   214 			}
   215 		
   216 		TInt err = iData->SetProperty(EAgentPropertyAgentUI, aSource.IsUIEnabled());		
   217 		if (err != KErrNone && err != KErrCANotSupported)
   218 			{
   219 			// KErrCANotSupported isn't a problem for us so eat the error code.
   220 			User::Leave(err);
   221 			}
   222 
   223 		err = iData->EvaluateIntent(aSource.Intent());
   224 		User::LeaveIfError(err);
   225 		}
   226 	else
   227 		{
   228 		// Use RMMFDRMPluginServerProxy as medium
   229 		iDrmPluginServer = new (ELeave) RMMFDRMPluginServerProxy;
   230 		User::LeaveIfError(iDrmPluginServer->Open());
   231 		
   232 		CBufFlat* dataBuffer = CBufFlat::NewL(KExpandSize);
   233 		CleanupStack::PushL(dataBuffer);
   234 		RBufWriteStream stream;
   235 		stream.Open(*dataBuffer);
   236 		CleanupClosePushL(stream);
   237 		
   238 		stream.WriteInt32L(aSource.UniqueId().Length());
   239 		stream.WriteL(aSource.UniqueId());
   240 		stream.WriteInt32L(aSource.IsUIEnabled());
   241 		TPckgBuf<ContentAccess::TIntent> intentPckg(aSource.Intent());
   242 		stream.WriteL(intentPckg);
   243 		stream.CommitL();
   244 	
   245 		CleanupStack::PopAndDestroy(&stream);
   246 		if (aSource.SourceType()==KUidMMFileSource)
   247 			{
   248 			const TMMFileSource& fileSource = static_cast<const TMMFileSource&>(aSource);
   249 			iDrmPluginServer->OpenDataContentL(fileSource.Name(), dataBuffer->Ptr(0));
   250 			}
   251 		if (aSource.SourceType()==KUidMMFileHandleSource)
   252 			{
   253 			const TMMFileHandleSource& fileHandleSource = static_cast<const TMMFileHandleSource&>(aSource);
   254 			iDrmPluginServer->OpenDataContentL(fileHandleSource.Handle(), dataBuffer->Ptr(0));
   255 			}
   256 		CleanupStack::PopAndDestroy(dataBuffer);
   257 		}
   258 	}
   259 
   260 TInt CMMFUtilityFileInfo::EvaluateIntent(TIntent aIntent)
   261 	{
   262 	if (iData)
   263 		{
   264 		return iData->EvaluateIntent(aIntent);
   265 		}
   266 	else
   267 		{
   268 		ASSERT(iDrmPluginServer);
   269 		return iDrmPluginServer->EvaluateDataContentIntent(aIntent);
   270 		}
   271 	}
   272 /**
   273  * @internalComponent
   274  */
   275 TBool CMMFUtilityFileInfo::GetFileMimeTypeL(TDes8& aMimeType)
   276 	{
   277 	if (iData)
   278 		{
   279 		return iData->GetMimeTypeL(aMimeType);
   280 		}
   281 	else
   282 		{
   283 		ASSERT(iDrmPluginServer);
   284 		return iDrmPluginServer->GetDataContentMimeTypeL(aMimeType);
   285 		}
   286 	}
   287 
   288 /**
   289  * @internalComponent
   290  */
   291 void CMMFUtilityFileInfo::GetFileHeaderDataL(TDes8& aHeaderData, TInt aMaxLength)
   292 	{
   293 	if (iData)
   294 		{
   295 		TInt size = 0;
   296 		iData->DataSizeL(size);
   297 		if (size > 0)
   298 			{
   299 			if (size > aMaxLength) 
   300 				size = aMaxLength;
   301 			TInt pos = 0;
   302 			User::LeaveIfError(iData->Seek(ESeekStart, pos));
   303 			User::LeaveIfError(iData->Read(aHeaderData, size));
   304 			}
   305 		}
   306 	else
   307 		{
   308 		ASSERT(iDrmPluginServer);
   309 		iDrmPluginServer->GetDataContentFileHeaderL(aHeaderData, aMaxLength);
   310 		}
   311 	}
   312 
   313 /**
   314  * @internalComponent
   315  */
   316 EXPORT_C HBufC8* CMMFClientUtility::GetFileExtensionL(const TDesC& aFileName)
   317 	{
   318 	TParse fileName;
   319 	fileName.Set(aFileName,NULL,NULL);
   320 	HBufC8* fileSuffix = NULL;
   321 	if(fileName.ExtPresent())
   322 		{
   323 		TPtrC fileSuffixPtr(fileName.Ext());
   324 		fileSuffix = HBufC8::NewL(fileSuffixPtr.Length());
   325 		fileSuffix->Des().Copy(fileSuffixPtr);
   326 		}
   327 	else
   328 		{
   329 		fileSuffix = KNullDesC8().AllocL();
   330 		}
   331 	return fileSuffix;
   332 	}
   333 
   334 
   335 /**
   336  * @internalComponent
   337  */
   338 CMMFUtilityFileInfo::~CMMFUtilityFileInfo()
   339 	{
   340 	if (iData)
   341 		{
   342 		delete iData;
   343 		}
   344 	if (iDrmPluginServer)
   345 		{
   346 		iDrmPluginServer->Close();
   347 		delete iDrmPluginServer;
   348 		}
   349 	}
   350 
   351 /*
   352  * @internalComponent
   353  *
   354  * Returns an integer rating indicating how well the supplied format matches
   355  * the header data and file extension supplied.
   356  * 3 brownie points awarded for data & suffix match.
   357  * 2 brownie points awarded for data match alone.
   358  * 1 brownie point awarded for suffix match alone.
   359  */
   360 TInt CMMFClientUtility::GetBestMatchL(const CMMFFormatImplementationInformation* format, const TDesC8& aHeaderData, const TDesC8& aFileExtension)
   361 	{
   362 	TInt browniePoints = 0;
   363 
   364 	if (aHeaderData.Length() > 0) // Non empty file
   365 		{
   366 		if (aFileExtension.Length() > 0) // With a file extension
   367 			{
   368 			if (format->SupportsHeaderDataL(aHeaderData) && 
   369 				format->SupportsFileExtension(aFileExtension))
   370 				{
   371 				browniePoints = 3;
   372 				}
   373 			else if (format->SupportsHeaderDataL(aHeaderData))
   374 				{
   375 				browniePoints = 2;
   376 				}
   377 			else
   378 				{
   379 				// See if this format has any 'empty' match data or no match data, indicating 
   380 				// that this format will match extension alone even if data present.
   381 				// (A format may have more than one match data string.)
   382 				const CDesC8Array& supportedHeaderData = format->SupportedHeaderData();
   383 
   384 				if (supportedHeaderData.Count() == 0)
   385 					{
   386 					// No header data indicated.
   387 					if (format->SupportsFileExtension(aFileExtension))
   388 						{
   389 							browniePoints = 1;
   390 						}
   391 					}
   392 				else
   393 					{
   394 					for (register TInt i = 0; i < supportedHeaderData.Count(); i++)
   395 						{
   396 						if ((supportedHeaderData[i].Length() == 0) && 
   397 							format->SupportsFileExtension(aFileExtension))
   398 							{
   399 							browniePoints = 1;
   400 							}
   401 						}
   402 					}
   403 				}
   404 			}
   405 		else
   406 			{
   407 			// No file suffix, so must match header data alone.
   408 			if (format->SupportsHeaderDataL(aHeaderData))
   409 				{
   410 				browniePoints = 2;
   411 				}
   412 			}
   413 		}
   414 	else // Empty File
   415 		{
   416 		// We have no choice but to match extension, if there is one.
   417 		if ((aFileExtension.Length() > 0) && format->SupportsFileExtension(aFileExtension))
   418 			{
   419 			browniePoints = 1;
   420 			}
   421 		}
   422 
   423 	return browniePoints;
   424 }
   425 
   426 /**
   427  * @internalComponent
   428  *
   429  * This function parses all the play & record formats in the given list of controllers,
   430  * looking for controllers & formats that best match the requirements. 
   431  * Play controllers will be returned before record controllers, and
   432  * in cases of equal priority between formats, ECom order will be maintained.
   433  *
   434  * @param	"aControllers"	
   435  *			A reference to a user supplied list of controllers retrieved from ECom.
   436  *			This list may be have been filtered for audio/video/play/record.
   437  * @param	"aHeaderDataPlayback"
   438  *			A descriptor reference containing the file's header data.
   439  *          for matching against a controller's play formats. May be KNullDesC8
   440  * @param	"aFileExtensionPlayback"
   441  *			A descriptor reference containing the filename's extension.
   442  *          for matching against a controller's play formats. May be KNullDesC8
   443  * @param	"aHeaderDataRecord"
   444  *			A descriptor reference containing the file's header data.
   445  *          for matching against a controller's record formats. May be KNullDesC8
   446  * @param	"aFileExtensionRecord"
   447  *			A descriptor reference containing the filename's extension.
   448  *          for matching against a controller's record formats. May be KNullDesC8
   449  * @param	"aPrioritisedControllers"
   450  *			A reference to a user supplied list through which the list of
   451  *			prioritised controllers will be returned.
   452  * @since	7.0s
   453  */
   454 void CMMFClientUtility::PrioritiseControllersL(
   455 	const RMMFControllerImplInfoArray& aControllers, 
   456 	const TDesC8& aHeaderDataPlayback, 
   457 	const TDesC8& aFileExtensionPlayback, 
   458 	const TDesC8& aHeaderDataRecord, 
   459 	const TDesC8& aFileExtensionRecord, 
   460 	RMMFControllerImplInfoArray& prioritisedControllers)
   461 	{
   462 	RMMFControllerImplInfoArray fullMatchControllers; // data AND suffix
   463 	CleanupClosePushL(fullMatchControllers);
   464 	RMMFControllerImplInfoArray partMatchControllers; // data OR suffix
   465 	CleanupClosePushL(partMatchControllers);
   466 
   467 	TBool checkingPlaybackFormats = EFalse;
   468 	TBool checkingRecordFormats = EFalse;
   469 
   470 	if (aHeaderDataPlayback != KNullDesC8 || aFileExtensionPlayback != KNullDesC8)
   471 		checkingPlaybackFormats = ETrue;
   472 	if (aHeaderDataRecord != KNullDesC8 || aFileExtensionRecord != KNullDesC8)
   473 		checkingRecordFormats = ETrue;
   474 
   475 	// Examine each format for each controller. We only want to know at this stage
   476 	// if the controller has suitable formats, so as soon as we know it has, we can
   477 	// add it to out list, ranked by how well it matched.
   478 	for (register TInt i = 0; i < aControllers.Count(); i++)
   479 		{
   480 		const CMMFControllerImplementationInformation* controller = aControllers[i];
   481 		TInt savedBrowniePointsPlayback = 0;
   482 		TInt savedBrowniePointsRecord = 0;
   483 
   484 		if (checkingPlaybackFormats)
   485 			{
   486 			for (register TInt p = 0; p < controller->PlayFormats().Count(); p++)
   487 				{
   488 				const CMMFFormatImplementationInformation* format = controller->PlayFormats()[p];
   489 
   490 				TInt browniePoints = GetBestMatchL(format, aHeaderDataPlayback, aFileExtensionPlayback);
   491 
   492 				if (browniePoints >= savedBrowniePointsPlayback)
   493 					savedBrowniePointsPlayback = browniePoints;
   494 				}
   495 			}
   496 
   497 		if (checkingRecordFormats)
   498 			{
   499 			for (register TInt r = 0; r < controller->RecordFormats().Count(); r++)
   500 				{
   501 				const CMMFFormatImplementationInformation* format = controller->RecordFormats()[r];
   502 
   503 				TInt browniePoints = GetBestMatchL(format, aHeaderDataRecord, aFileExtensionRecord);
   504 
   505 				if (browniePoints >= savedBrowniePointsRecord)
   506 					savedBrowniePointsRecord = browniePoints;
   507 				}
   508 			}
   509 
   510 		TInt savedBrowniePoints = 0;
   511 		// if we're checking both playback & record formats
   512 		// make sure we've found both
   513 		if (checkingPlaybackFormats && checkingRecordFormats)
   514 			{
   515 			savedBrowniePoints = Min(savedBrowniePointsPlayback, savedBrowniePointsRecord);
   516 			}
   517 		else if (checkingPlaybackFormats)
   518 			{
   519 			savedBrowniePoints = savedBrowniePointsPlayback;
   520 			}
   521 		else if (checkingRecordFormats)
   522 			{
   523 			savedBrowniePoints = savedBrowniePointsRecord;
   524 			}
   525 
   526 		// Checked all formats for this controller, now count our brownie points.
   527 		switch (savedBrowniePoints)
   528 			{
   529 			case 3:
   530 				User::LeaveIfError(fullMatchControllers.Append(controller));
   531 				break;
   532 			case 2:
   533 				User::LeaveIfError(partMatchControllers.Insert(controller, 0));
   534 				break;
   535 			case 1:
   536 				User::LeaveIfError(partMatchControllers.Append(controller));
   537 				break;
   538 			default:
   539 				break;
   540 			}
   541 		}
   542 
   543 	// The better the controller matches, the earlier it will be in the final list.
   544 	for (register TInt x = 0; x < fullMatchControllers.Count(); x++)
   545 		{
   546 		if (prioritisedControllers.Find(fullMatchControllers[x]) == KErrNotFound)
   547 			{
   548 			User::LeaveIfError(prioritisedControllers.Append(fullMatchControllers[x]));
   549 			}
   550 		}
   551 
   552 	for (register TInt y = 0; y < partMatchControllers.Count(); y++)
   553 		{
   554 		if (prioritisedControllers.Find(partMatchControllers[y]) == KErrNotFound)
   555 			{
   556 			User::LeaveIfError(prioritisedControllers.Append(partMatchControllers[y]));
   557 			}
   558 		}
   559 
   560 	CleanupStack::PopAndDestroy(2, &fullMatchControllers); // fullMatchControllers, partMatchControllers
   561 	}
   562 
   563 /**
   564  * @internalComponent
   565  */
   566 EXPORT_C CMMFMdaObjectStateChangeObserverCallback* CMMFMdaObjectStateChangeObserverCallback::NewL(MMdaObjectStateChangeObserver& aCallback)
   567 	{
   568 	return new(ELeave) CMMFMdaObjectStateChangeObserverCallback(aCallback);
   569 	}
   570 
   571 /**
   572  * @internalComponent
   573  */
   574 CMMFMdaObjectStateChangeObserverCallback::~CMMFMdaObjectStateChangeObserverCallback()
   575 	{
   576 	Cancel();
   577 	}
   578 
   579 /**
   580  * @internalComponent
   581  */
   582 EXPORT_C void CMMFMdaObjectStateChangeObserverCallback::CallBack(CBase* aObject, TInt aPreviousState, TInt aCurrentState, TInt aErrorCode)
   583 	{
   584 	iObject = aObject;
   585 	iPreviousState = aPreviousState;
   586 	iCurrentState = aCurrentState;
   587 	iErrorCode = aErrorCode;
   588 	if (!IsActive())
   589 		{
   590 		TRequestStatus* s = &iStatus;
   591 		SetActive();
   592 		User::RequestComplete(s, KErrNone);
   593 		}
   594 	}
   595 
   596 CMMFMdaObjectStateChangeObserverCallback::CMMFMdaObjectStateChangeObserverCallback(MMdaObjectStateChangeObserver& aCallback) :
   597 	CActive(CActive::EPriorityHigh),
   598 	iCallback(aCallback)
   599 	{
   600 	CActiveScheduler::Add(this);
   601 	}
   602 
   603 void CMMFMdaObjectStateChangeObserverCallback::RunL()
   604 	{
   605 	iCallback.MoscoStateChangeEvent(iObject, iPreviousState, iCurrentState, iErrorCode);
   606 	}
   607 
   608 void CMMFMdaObjectStateChangeObserverCallback::DoCancel()
   609 	{
   610 	//nothing to cancel
   611 	}
   612 
   613 
   614 //****************************************
   615 // CMMFFindAndOpenController
   616 //****************************************
   617 
   618 /**
   619  * Factory function to create a CMMFFindAndOpenController class
   620  *
   621  * @internalComponent
   622  */
   623 EXPORT_C CMMFFindAndOpenController* CMMFFindAndOpenController::NewL(MMMFFindAndOpenControllerObserver& aObserver)
   624 	{
   625 	CMMFFindAndOpenController* self = new(ELeave) CMMFFindAndOpenController(aObserver);
   626 	CleanupStack::PushL(self);
   627 	self->ConstructL();
   628 	CleanupStack::Pop(self);
   629 	return self;
   630 	}
   631 
   632 CMMFFindAndOpenController::~CMMFFindAndOpenController()
   633 	{
   634 	Cancel();
   635 
   636 	// delete temporary variables
   637 	Close();
   638 
   639 	// this should cancel the AO
   640 	delete iAddDataSourceSinkAsync;
   641 
   642 	delete iPrimaryConfig;
   643 	delete iSecondaryConfig;
   644 	}
   645 
   646 /**
   647  * Function to free up memory after a successful open has completed
   648  * Useful to allow a alloc testing to work.
   649  * Must not be called if ReOpen() is to be called
   650  *
   651  * @internalComponent
   652  */
   653 EXPORT_C void CMMFFindAndOpenController::Close()
   654 	{
   655 
   656 	Cancel();
   657 	
   658 	if(iAddDataSourceSinkAsync)
   659 		{
   660 		iAddDataSourceSinkAsync->Cancel();
   661 		}
   662 		
   663 	if (iPrimaryConfig)
   664 		iPrimaryConfig->Close();
   665 	if (iSecondaryConfig)
   666 		iSecondaryConfig->Close();
   667 
   668 	iPrioritisedControllers.Close();
   669 	iControllers.ResetAndDestroy();
   670 	iControllers.Close();
   671 	
   672 	iFileName.SetLength(0);
   673 	iFileNameSecondary.SetLength(0);
   674 
   675 	delete iUrl;
   676 	iUrl = NULL;
   677 	
   678 	delete iMimeType;
   679 	iMimeType = NULL;
   680 	
   681 	delete iUniqueId;
   682 	iUniqueId = NULL;
   683 
   684 	if (iOwnFileHandle)
   685 		{
   686 		iFileHandle.Close();
   687 		iOwnFileHandle = EFalse;	
   688 		}
   689 	}
   690 /**
   691  * Function to free up memory of which is not required in ReOpen()
   692  * after a successful open has completed
   693  * Useful to allow a alloc testing to work.
   694  *
   695  * @internalComponent
   696  */
   697 
   698 EXPORT_C void CMMFFindAndOpenController::CloseConfig()
   699 	{
   700 	Cancel();
   701 	if(iAddDataSourceSinkAsync)
   702 		{
   703 		iAddDataSourceSinkAsync->Cancel();
   704 		}
   705 	
   706 	if (iSecondaryConfig)
   707 		{
   708 		iSecondaryConfig->Close();
   709 		}
   710 	
   711 	iPrioritisedControllers.Close();
   712 	iControllers.ResetAndDestroy();
   713 	iControllers.Close();
   714 	
   715 	iFileName.SetLength(0);
   716 	iFileNameSecondary.SetLength(0);
   717 
   718 	delete iUrl;
   719 	iUrl = NULL;
   720 	
   721 	delete iMimeType;
   722 	iMimeType = NULL;
   723 	
   724 	delete iUniqueId;
   725 	iUniqueId = NULL;
   726 
   727 	if (iOwnFileHandle)
   728 		{
   729 		iFileHandle.Close();
   730 		iOwnFileHandle = EFalse;		
   731 		}
   732 	}
   733 
   734 CMMFFindAndOpenController::CMMFFindAndOpenController(MMMFFindAndOpenControllerObserver& aObserver) :
   735 	CActive(EPriorityStandard), 
   736 	iObserver(aObserver),
   737 	iDescriptor(NULL, 0)
   738 	{
   739 	CActiveScheduler::Add(this);
   740 	}
   741 
   742 void CMMFFindAndOpenController::ConstructL()
   743 	{
   744 	iAddDataSourceSinkAsync = CMMFAddDataSourceSinkAsync::NewL(*this);
   745 	iPrimaryConfig = new (ELeave)  CConfig();
   746 	iSecondaryConfig =  new (ELeave) CConfig;
   747 	iCurrentConfig =  iPrimaryConfig;
   748 	
   749 	RProcess thisProcess;
   750 	iHasDrmCapability = thisProcess.HasCapability(ECapabilityDRM, KSuppressPlatSecDiagnostic);
   751 	thisProcess.Close();
   752 	}
   753 
   754 void CMMFFindAndOpenController::RunL()
   755 	{
   756 	Process();
   757 	}
   758 
   759 void CMMFFindAndOpenController::DoCancel()
   760 	{
   761 	iAddDataSourceSinkAsync->Cancel();
   762 	}
   763 
   764 /**
   765  * Defines the media ID & priority to be used when opening a controller
   766  * Normally called once only after class has been constructed
   767  *
   768  * @param	aMediaId
   769  *			the media ID to use when searching for a controller
   770  *			e.g. KUidMediaTypeAudio 
   771  * @param	aPrioritySettings
   772  *			the priority settings to use when opening a controller
   773  * @param	aMediaIdMatchType
   774  *			Defines the type of media id match to be performed on the plugins 
   775  *			returned from the ECOM registry.
   776  * @leave	can leave with KErrNoMemory
   777 
   778  * @internalComponent
   779  */
   780 EXPORT_C void CMMFFindAndOpenController::Configure(
   781 	TUid aMediaId, 
   782 	TMMFPrioritySettings aPrioritySettings,
   783 	CMMFPluginSelectionParameters::TMediaIdMatchType aMediaIdMatchType)
   784 	{
   785 	iPrioritySettings = aPrioritySettings;
   786 
   787 	iMediaIdMatchType = aMediaIdMatchType;
   788 
   789 	iMediaId = aMediaId;
   790 	}
   791 
   792 void CMMFFindAndOpenController::ConfigureController(
   793 	CConfig& config,
   794 	RMMFController& aController, 
   795 	CMMFControllerEventMonitor& aEventMonitor,
   796 	TControllerMode aControllerMode)
   797 	{
   798 	config.iController = &aController;
   799 	config.iEventMonitor = &aEventMonitor;
   800 	config.iControllerMode = aControllerMode;
   801 	}
   802 
   803 /**
   804  * Configures the primary controller
   805  *
   806  * @param	aController
   807  *			a reference to the client controller object to use
   808  * @param	aEventMonitor
   809  *			a reference to an event monitor object for receiving 
   810  *			events from the controller
   811  * @param	aControllerMode
   812  *			indicates whether this controller is to be used for recording
   813  *          or playback
   814  *
   815  * @internalComponent
   816  */
   817 EXPORT_C void CMMFFindAndOpenController::ConfigureController(
   818 	RMMFController& aController, 
   819 	CMMFControllerEventMonitor& aEventMonitor,
   820 	TControllerMode aControllerMode)
   821 	{
   822 	ConfigureController(
   823 		*iPrimaryConfig,
   824 		aController, 
   825 		aEventMonitor,
   826 		aControllerMode);
   827 	}
   828 
   829 /**
   830  * Configures the secondary controller
   831  *
   832  * This is only needed for the audio recorder utility which opens
   833  * one controller for playback and another for recording
   834  *
   835  * @param	aController
   836  *			a reference to the client controller object to use
   837  * @param	aEventMonitor
   838  *			a reference to an event monitor object for receiving 
   839  *			events from the controller
   840  * @param	aControllerMode
   841  *			indicates whether this controller is to be used for recording
   842  *          or playback or converting
   843  *
   844  * @internalComponent
   845  */
   846 EXPORT_C void CMMFFindAndOpenController::ConfigureSecondaryController(
   847 	RMMFController& aController, 
   848 	CMMFControllerEventMonitor& aEventMonitor,
   849 	TControllerMode aControllerMode)
   850 	{
   851 	ConfigureController(
   852 		*iSecondaryConfig,
   853 		aController, 
   854 		aEventMonitor,
   855 		aControllerMode);
   856 	}
   857 
   858 /**
   859  * Makes any controllers that are opened subsequently share a single heap.
   860  * 
   861  * The default behaviour is that each controller is created with its own heap.
   862  * Each heap uses a chunk, so using this function avoids situations where the number
   863  * of chunks per process is limited.
   864  * The default behaviour is generally to be preferred, and should give lower overall
   865  * memory usage. However, if many controllers are to be created for a particular thread,
   866  * then this function should be used to prevent running out of heaps or chunks.
   867  *
   868  * @internalComponent
   869  */
   870 EXPORT_C void CMMFFindAndOpenController::UseSharedHeap()
   871 	{
   872 	iUseSharedHeap = ETrue;
   873 	}
   874 
   875 void CMMFFindAndOpenController::Init()
   876 	{
   877 	// This should be called prior to opening, so reset the error
   878 	iError = KErrNone;
   879 	iSourceSinkConfigured = EFalse;
   880 	iControllerCount = 0;
   881 	}
   882 
   883 void CMMFFindAndOpenController::ConfigureSourceSink(
   884 	CConfig& config,
   885 	TSourceSink aSource, 
   886 	TSourceSink aSink)
   887 	{
   888 	TInt err;
   889 	TRAP(err, config.iSource = CreateSourceSinkL(aSource));
   890 	if (err != KErrNone)
   891 		{
   892 		iError = err;
   893 		return;
   894 		}
   895 		
   896 	TRAP(err, config.iSink = CreateSourceSinkL(aSink));
   897 	if (err != KErrNone)
   898 		{
   899 		iError = err;
   900 		return;
   901 		}
   902 	}
   903 	
   904 
   905 void CMMFFindAndOpenController::ConfigureSourceSink(
   906 	CConfig& config,
   907 	const TMMSource& aSource, 
   908 	TSourceSink aSink)
   909 	{
   910 	TInt err;
   911 	TRAP(err, config.iSource = CreateSourceSinkL(aSource));
   912 	if (err != KErrNone)
   913 		{
   914 		iError = err;
   915 		return;
   916 		}
   917 		
   918 	TRAP(err, config.iSink = CreateSourceSinkL(aSink));
   919 	if (err != KErrNone)
   920 		{
   921 		iError = err;
   922 		return;
   923 		}
   924 	}
   925 
   926 
   927 	
   928 /**
   929  * Configure the primary controller's source and sink
   930  * The descriptors passed to this function are copied so they do not need to be persistent.
   931  * To simplify the API, any errors that occur are reported back asynchronously following
   932  * a subsequent call to OpenByXXX()
   933  *
   934  * @param	aSourceUid
   935  *			the UID of the data source
   936  * @param	aSourceData
   937  *			a reference to a descriptor used to configure the source
   938  * @param	aSinkUid
   939  *			the UID of the data sink
   940  * @param	aSinkData
   941  *			a reference to a descriptor used to configure the sink
   942  *
   943  * @internalComponent
   944  */
   945 EXPORT_C void CMMFFindAndOpenController::ConfigureSourceSink(
   946 	TSourceSink aSource,
   947 	TSourceSink aSink)
   948 	{
   949 
   950 	CConfig* config = NULL;
   951 	
   952 	Init();
   953 	config = iPrimaryConfig;
   954 
   955 
   956 	// must have already called ConfigureController()
   957 	__ASSERT_ALWAYS(config->iController != NULL, CUPanic(EMMFMediaClientUtilityBadState));
   958 
   959 	ConfigureSourceSink(
   960 		*config,
   961 		aSource, 
   962 		aSink);
   963 	iCurrentConfig = config;
   964 
   965 	iSourceSinkConfigured = ETrue;
   966 	}
   967 	
   968 	
   969 /**
   970  * Configure the primary controller's source and sink
   971  * The descriptors passed to this function are copied so they do not need to be persistent.
   972  * To simplify the API, any errors that occur are reported back asynchronously following
   973  * a subsequent call to OpenByXXX()
   974  *
   975  * @param	aSourceUid
   976  *			the UID of the data source
   977  * @param	aSourceData
   978  *			a reference to a descriptor used to configure the source
   979  * @param	aSinkUid
   980  *			the UID of the data sink
   981  * @param	aSinkData
   982  *			a reference to a descriptor used to configure the sink
   983  *
   984  * @internalComponent
   985  */
   986 EXPORT_C void CMMFFindAndOpenController::ConfigureSecondarySourceSink(
   987 	TSourceSink aSource,
   988 	TSourceSink aSink)
   989 	{
   990 	if (iError != KErrNone)
   991 		{
   992 		// if there was an error configuring the primary source/sink, do not try the secondary one
   993 		// Don't return the error, since the stored error will be returned by the OpenBy... method
   994 		return;
   995 		}
   996 
   997 	CConfig* config = NULL;
   998 	
   999 	config = iSecondaryConfig;
  1000 
  1001 	// must have already configured the primary controller
  1002 	__ASSERT_ALWAYS(iSourceSinkConfigured, CUPanic(EMMFMediaClientUtilityBadState));
  1003 	config = iSecondaryConfig;
  1004 			
  1005 	// must have already called ConfigureController()
  1006 	__ASSERT_ALWAYS(config->iController != NULL, CUPanic(EMMFMediaClientUtilityBadState));
  1007 
  1008 	ConfigureSourceSink(
  1009 		*config,
  1010 		aSource, 
  1011 		aSink);
  1012 	iCurrentConfig = config;
  1013 
  1014 	iSourceSinkConfigured = ETrue;
  1015 	}
  1016 	
  1017 
  1018 	
  1019 EXPORT_C void CMMFFindAndOpenController::ConfigureSourceSink(
  1020 	const TMMSource& aSource,
  1021 	TSourceSink aSink)
  1022 	{
  1023 	Init();
  1024 	CConfig* config = iPrimaryConfig;
  1025 			
  1026 	// must have already called ConfigureController()
  1027 	__ASSERT_ALWAYS(config->iController != NULL, CUPanic(EMMFMediaClientUtilityBadState));
  1028 
  1029 	ConfigureSourceSink(
  1030 		*config,
  1031 		aSource, 
  1032 		aSink);
  1033 	iCurrentConfig = config;
  1034 
  1035 	iSourceSinkConfigured = ETrue;
  1036 	}
  1037 
  1038 	
  1039 	
  1040 /**
  1041  * Opens a controller using the supplied controller UID
  1042  * and adds the source & sink
  1043  * Completion is indicated asynchonously by a call to MfaocComplete()
  1044  * 
  1045  * @param	aControllerUid
  1046  *			the UID of the primary controller
  1047  * @param	aControllerUid
  1048  *			the UID of the secondary controller
  1049  *
  1050  * @internalComponent
  1051  */
  1052 EXPORT_C void CMMFFindAndOpenController::OpenByControllerUid(
  1053 		TUid aControllerUid,
  1054 		TUid aSecondaryControllerUid)
  1055 	{
  1056 	// must have already called ConfigureSourceSink()
  1057 	__ASSERT_ALWAYS(iSourceSinkConfigured, CUPanic(EMMFMediaClientUtilityBadState));
  1058 
  1059 	// Have there been any errors so far ?
  1060 	if (iError != KErrNone)
  1061 		{
  1062 	    SchedSendError();
  1063 		return;
  1064 		}
  1065 
  1066 	if (iCurrentConfig == iPrimaryConfig)
  1067 		{
  1068 		// only do this for the playback controller
  1069 		TRAP(iError, iCurrentConfig->iSource->EvaluateIntentL())
  1070 		
  1071 		if (iError != KErrNone && 
  1072 			!(iCurrentConfig->iControllerMode == EPlayback && iError == KErrPermissionDenied && !iHasDrmCapability))
  1073 			{
  1074 			// KErrPermissionDenied error and no DRM capability are not problems in Playback mode
  1075 			// proper action will be performed when controller is loaded
  1076 	    	SchedSendError();
  1077 			return;
  1078 			}
  1079 		}
  1080 
  1081 	iPrimaryConfig->iControllerUid = aControllerUid;
  1082 	if (iCurrentConfig == iSecondaryConfig)
  1083 		{
  1084 		if (aSecondaryControllerUid == KNullUid)
  1085 			iSecondaryConfig->iControllerUid = aControllerUid;
  1086 		else
  1087 			iSecondaryConfig->iControllerUid = aSecondaryControllerUid;
  1088 		}
  1089 		
  1090 	iMode = EOpenByControllerUid;
  1091 	iControllerImplInfo = NULL;
  1092 	iState = EOpenController;
  1093 	KickState();
  1094 	}
  1095 
  1096 /**
  1097  * Opens a controller using the supplied file name
  1098  * and adds the source & sink
  1099  * A copy is made of the filename or file handle so that it need not be persistent
  1100  * Completion is indicated asynchonously by a call to MfaocComplete()
  1101  * 
  1102  * @param	aSource
  1103  *			a reference to a TFileSource object to be used when searching
  1104  *          for a controller
  1105  * @param	aFileNameSecondary
  1106  *			a reference to the seconday filename to be used when searching
  1107  *          for a controller. This need only be supplied when converting 
  1108  *			between two files.
  1109  *
  1110  * @internalComponent
  1111  */
  1112 EXPORT_C void CMMFFindAndOpenController::OpenByFileSource(const TMMSource& aSource, const TDesC& aFileNameSecondary)
  1113 	{
  1114 	// must have already called ConfigureSourceSink()
  1115 	__ASSERT_ALWAYS(iSourceSinkConfigured, CUPanic(EMMFMediaClientUtilityBadState));
  1116 
  1117 	TInt err;
  1118 	// Have there been any errors so far ?
  1119 	if (iError != KErrNone)
  1120 		{
  1121 		SchedSendError();
  1122 		return;
  1123 		}
  1124 		
  1125 	if (iOwnFileHandle)
  1126 		{
  1127 		// in case of error
  1128 		iFileHandle.Close();
  1129 		iOwnFileHandle = EFalse;
  1130 		}
  1131 		
  1132 	iEnableUi = aSource.IsUIEnabled();
  1133 	if (aSource.SourceType()==KUidMMFileSource)
  1134 		{
  1135 		const TMMFileSource& fileSource = static_cast<const TMMFileSource&>(aSource);
  1136 		iFileName = fileSource.Name();
  1137 		iUseFileHandle = EFalse;
  1138 		}
  1139 
  1140 	if (aSource.SourceType()==KUidMMFileHandleSource)
  1141 		{
  1142 		const TMMFileHandleSource& fileHandleSource = static_cast<const TMMFileHandleSource&>(aSource);
  1143 		ASSERT(iFileHandle.SubSessionHandle()==0); // closed just above
  1144 		err = iFileHandle.Duplicate(fileHandleSource.Handle());
  1145 		if (err != KErrNone)
  1146 			{
  1147 			SchedSendError(err);
  1148 			return;
  1149 			}
  1150 		iFileHandle.Name(iFileName); //ignore error return since we'll just do without the filename if not available
  1151 		iUseFileHandle = ETrue;
  1152 		iOwnFileHandle = ETrue; // because we dup'd it
  1153 		}
  1154 		
  1155 	TRAP(err, iUniqueId = aSource.UniqueId().AllocL());
  1156 	iIntent = aSource.Intent();
  1157 	if (err != KErrNone)
  1158 		{
  1159 		SchedSendError(err);
  1160 		return;
  1161 		}
  1162 
  1163 		
  1164 	// take a copy of the secondary file name
  1165 	iFileNameSecondary = aFileNameSecondary;
  1166 
  1167 	iMode = EOpenByFileName;
  1168 	iState = EBuildControllerList;
  1169 	KickState();
  1170 	}
  1171 	
  1172 /**
  1173  * Opens a controller using the supplied format UID
  1174  * and adds the source & sink
  1175  * Completion is indicated asynchonously by a call to MfaocComplete()
  1176  * 
  1177  * @param	aFormatUid
  1178  *			the UID of a format that must be supported by the controller
  1179  * @param	aFormatUidSecondary
  1180  *			the UID of a secondary format that must be supported by the controller
  1181  *			This need only be supplied when converting between two differnet formats.
  1182  *
  1183  * @internalComponent
  1184  */
  1185 EXPORT_C void CMMFFindAndOpenController::OpenByFormatUid(TUid aFormatUid, TUid aFormatUidSecondary)
  1186 	{
  1187 	// must have already called ConfigureSourceSink()
  1188 	__ASSERT_ALWAYS(iSourceSinkConfigured, CUPanic(EMMFMediaClientUtilityBadState));
  1189 
  1190 	// Have there been any errors so far ?
  1191 	if (iError != KErrNone)
  1192 		{
  1193 		SchedSendError();
  1194 		return;
  1195 		}
  1196 
  1197 	iFormatUid = aFormatUid;
  1198 	iFormatUidSecondary = aFormatUidSecondary;
  1199 
  1200 	iMode = EOpenByFormatUid;
  1201 	iState = EBuildControllerList;
  1202 	KickState();
  1203 	}
  1204 
  1205 /**
  1206  * Opens a controller using the supplied descriptor 
  1207  * and adds the source & sink
  1208  * Completion is indicated asynchonously by a call to MfaocComplete()
  1209  * 
  1210  * @param	aDescriptor
  1211  *			a reference to the descriptor to be used when searching
  1212  *          for a controller
  1213  *
  1214  * @internalComponent
  1215  */
  1216 EXPORT_C void  CMMFFindAndOpenController::OpenByDescriptor(const TDesC8& aDescriptor)
  1217 	{
  1218 	// must have already called ConfigureSourceSink()
  1219 	__ASSERT_ALWAYS(iSourceSinkConfigured, CUPanic(EMMFMediaClientUtilityBadState));
  1220 
  1221 	// Have there been any errors so far ?
  1222 	if (iError != KErrNone)
  1223 		{
  1224 		SchedSendError();
  1225 		return;
  1226 		}
  1227 
  1228 	// take a copy of the descriptor
  1229 	TUint8* desBufferPtr = const_cast<TUint8*> (aDescriptor.Ptr());
  1230 	iDescriptor.Set( desBufferPtr,aDescriptor.Length(),aDescriptor.Length());
  1231 	
  1232 	iMode = EOpenByDescriptor;
  1233 	iState = EBuildControllerList;
  1234 	KickState();
  1235 	}
  1236 
  1237 /**
  1238  * Opens a controller using the supplied URL
  1239  * and adds the source & sink
  1240  * Completion is indicated asynchonously by a call to MfaocComplete()
  1241  * 
  1242  * @param	aUrl
  1243  *			a reference to the URL to be used when searching for a controller
  1244  * @param	aIapId
  1245  *          the IAP ID to be used when searching for a controller
  1246  * @param	aMimeType
  1247  *          the MIME type of the data to be used when searching for a controller
  1248  *
  1249  * @internalComponent
  1250  */
  1251 EXPORT_C void CMMFFindAndOpenController::OpenByUrl(const TDesC& aUrl, TInt aIapId, const TDesC8& aMimeType)
  1252 	{
  1253 	// must have already called ConfigureSourceSink()
  1254 	__ASSERT_ALWAYS(iSourceSinkConfigured, CUPanic(EMMFMediaClientUtilityBadState));
  1255 
  1256 	// Have there been any errors so far ?
  1257 	if (iError != KErrNone)
  1258 		{
  1259 		SchedSendError();
  1260 		return;
  1261 		}
  1262 
  1263 	// take a copy of the Url
  1264 	delete iUrl;
  1265 	iUrl = NULL;
  1266 	iUrl = aUrl.Alloc();
  1267 	if (iUrl == NULL)
  1268 		{
  1269 		SchedSendError(KErrNoMemory);
  1270 		return;
  1271 		}
  1272 
  1273 	// take a copy of the IapId
  1274 	iIapId = aIapId;
  1275 	
  1276 	// take a copy of the mime type
  1277 	delete iMimeType;
  1278 	iMimeType = NULL;
  1279 	iMimeType = aMimeType.Alloc();
  1280 	if (iMimeType == NULL)
  1281 		{
  1282 		SchedSendError(KErrNoMemory);
  1283 		return;
  1284 		}
  1285 
  1286 	iMode = EOpenByUrl;
  1287 	iState = EBuildControllerList;
  1288 	KickState();
  1289 	}
  1290 
  1291 /**
  1292  * Static function to return a TMMFFileConfig object
  1293  * suitable for passing to ConfigureSourceSink()
  1294  * 
  1295  * @param	aFileName
  1296  *          the filename to use
  1297  *
  1298  * @internalComponent
  1299  */
  1300 EXPORT_C TMMFFileConfig CMMFFindAndOpenController::GetConfigFile(const TDesC& aFileName)
  1301 	{
  1302 	TMMFFileConfig sourceSinkData;
  1303 	sourceSinkData().iPath = aFileName;
  1304 	return sourceSinkData;
  1305 	}
  1306 
  1307 /**
  1308  * Static function to return a TMMFDescriptorConfig object
  1309  * suitable for passing to ConfigureSourceSink()
  1310  * 
  1311  * @param	aFileName
  1312  *          the filename to use
  1313  *
  1314  * @internalComponent
  1315  */
  1316 EXPORT_C TMMFDescriptorConfig CMMFFindAndOpenController::GetConfigDescriptor(const TDesC8& aDescriptor)
  1317 	{
  1318 	TMMFDescriptorConfig sourceSinkData;
  1319 	sourceSinkData().iDes = (TAny*)&aDescriptor;
  1320 	sourceSinkData().iDesThreadId = RThread().Id();
  1321 	return sourceSinkData;
  1322 	}
  1323 
  1324 /**
  1325  * Static function to create a CBufFlat object
  1326  * suitable for passing to ConfigureSourceSink()
  1327  * 
  1328  * @param	aUrlCfgBuffer
  1329  *          the reference to a caller-supplied pointer used to create
  1330  *			a CBufFlat object. The caller is responsible for deletion.
  1331  * @param	aUrl
  1332  *			a reference to the URL to be used
  1333  * @param	aIapId
  1334  *          the IAP ID to be used
  1335  * @return	can return KErrNone or KErrNoMemory
  1336  *
  1337  * @internalComponent
  1338  */
  1339 
  1340 EXPORT_C void CMMFFindAndOpenController::GetConfigUrlL(CBufFlat*& aUrlCfgBuffer, const TDesC& aUrl, TInt aIapId)
  1341 	{
  1342 	delete aUrlCfgBuffer;
  1343 	aUrlCfgBuffer = NULL;
  1344 	
  1345 	CMMFUrlParams* urlCfg = CMMFUrlParams::NewL(aUrl,aIapId);
  1346 	CleanupStack::PushL(urlCfg);
  1347 	aUrlCfgBuffer = urlCfg->ExternalizeToCBufFlatLC();
  1348 	CleanupStack::Pop(aUrlCfgBuffer);
  1349 	CleanupStack::PopAndDestroy(urlCfg);
  1350 	}
  1351 /**
  1352  * ReOpens the previously opened primary controller
  1353  *
  1354  * @internalComponent
  1355  */
  1356 EXPORT_C void CMMFFindAndOpenController::ReOpen()
  1357 	{
  1358 	// should already have a valid controller uid so just open it
  1359 	iControllerImplInfo = NULL;
  1360 	iState = EOpenController;
  1361 	KickState();
  1362 	}
  1363 
  1364 void CMMFFindAndOpenController::OpenPrimaryController(void)
  1365 	{
  1366 	iCurrentConfig = iPrimaryConfig;
  1367 	switch(iMode)
  1368 		{
  1369 		case EOpenByFileName:
  1370 		case EOpenByFormatUid:
  1371 		case EOpenByDescriptor:
  1372 		case EOpenByUrl:
  1373 			iState = EBuildControllerList;
  1374 			break;
  1375 		case EOpenByControllerUid:
  1376 			iControllerImplInfo = NULL;
  1377 			iState = EOpenController;
  1378 			break;
  1379 		}
  1380 	KickState();
  1381 	}
  1382 
  1383 void CMMFFindAndOpenController::KickState()
  1384 	{
  1385 	TRequestStatus* status = &iStatus;
  1386 	User::RequestComplete(status, KErrNone);
  1387 	SetActive();
  1388 	}
  1389 
  1390 void CMMFFindAndOpenController::CloseController()
  1391 	{
  1392 	if (iCurrentConfig->iEventMonitor)
  1393 		iCurrentConfig->iEventMonitor->Cancel();
  1394 	iCurrentConfig->iController->Close(); 
  1395 	}
  1396 
  1397 void CMMFFindAndOpenController::Process()
  1398 	{
  1399 	switch(iState)
  1400 		{
  1401 		case EBuildControllerList:
  1402 			switch(iMode)
  1403 				{
  1404 				case EOpenByFileName:
  1405 					TRAP(iError, BuildControllerListFileNameL());
  1406 					break;
  1407 				case EOpenByDescriptor:
  1408 					TRAP(iError, BuildControllerListDescriptorL());
  1409 					break;
  1410 				case EOpenByUrl:
  1411 					TRAP(iError, BuildControllerListUrlL());
  1412 					break;
  1413 				case EOpenByFormatUid:
  1414 					TRAP(iError, BuildControllerListFormatL());
  1415 					break;
  1416 				default:
  1417 					CUPanic(EMMFMediaClientUtilityBadState);
  1418 				}
  1419 			
  1420 			if (iError != KErrNone)
  1421 				{
  1422 				iState = EIdle;
  1423 				SendError();
  1424 				break;
  1425 				}
  1426 
  1427 			// try the first controller
  1428 			iControllerIndex = -1;
  1429 			TryNextController();
  1430 			break;
  1431 
  1432 		case EOpenController:
  1433 			{
  1434 			// Make sure any existing controller is closed.
  1435 			CloseController();
  1436 			
  1437 			TBool isSecureDrmProcess = EFalse;// need to keep it false as UseSecureDRMProcess may return error
  1438 			// Loading controller in new threading model is enabled only in playback mode
  1439 			TUid sourceUid = iCurrentConfig->iSource->SourceSinkUid();
  1440 			TBool localPlaybackMode = iCurrentConfig->iControllerMode == EPlayback && 
  1441 										(sourceUid == KUidMmfFileSource || sourceUid == KUidMmfDescriptorSource);
  1442             if(localPlaybackMode)
  1443                 {
  1444                 TRAPD(err,UseSecureDRMProcessL(isSecureDrmProcess));
  1445                 if(err == KErrPermissionDenied)
  1446                 	{
  1447                 	isSecureDrmProcess = ETrue;
  1448                 	}
  1449                 else if(err != KErrNone)
  1450                     {
  1451                     iError = err;
  1452                     SendError(err);
  1453                     return;
  1454                     }
  1455                 }
  1456 			// Open the controller 
  1457 			if (iControllerImplInfo)
  1458 				{
  1459 				if(isSecureDrmProcess && localPlaybackMode)
  1460 					{
  1461 					iError = iCurrentConfig->iController->OpenInSecureDRMProcess(*iControllerImplInfo, iPrioritySettings, iUseSharedHeap);
  1462 					iUsingSecureDrmProcess = ETrue;
  1463 					}
  1464 				else
  1465 					{
  1466 					iError = iCurrentConfig->iController->Open(*iControllerImplInfo, iPrioritySettings, iUseSharedHeap);
  1467 					iUsingSecureDrmProcess = EFalse;;
  1468 					}
  1469 				}
  1470 			else
  1471 				{
  1472 				if(isSecureDrmProcess && localPlaybackMode)
  1473 					{
  1474 					iError = iCurrentConfig->iController->OpenInSecureDRMProcess(iCurrentConfig->iControllerUid, iPrioritySettings, iUseSharedHeap);
  1475 					iUsingSecureDrmProcess = ETrue;
  1476 	
  1477 					}
  1478 				else
  1479 					{
  1480 					iError = iCurrentConfig->iController->Open(iCurrentConfig->iControllerUid, iPrioritySettings, iUseSharedHeap);
  1481 					iUsingSecureDrmProcess = EFalse;
  1482 					}
  1483 				}
  1484 			//in case of error, including KErrNomemory try next controller
  1485 			if (iError)
  1486 				{
  1487 				TryNextController();
  1488 				}
  1489 			else
  1490 				{	
  1491 			#ifdef SYMBIAN_ENABLE_MMF_MULTISCREEN_SUPPORT
  1492 			#ifndef SYMBIAN_BUILD_GCE
  1493 				if(iCurrentConfig->iControllerMode == EPlayback && iMediaId == KUidMediaTypeVideo)
  1494 					{
  1495 					iError = iVideoSetInitScreenCustomCommands->SetInitScreenNumber(iScreenNumber);
  1496 					if(iError)
  1497 						{
  1498 						if (iError == KErrNotSupported && iScreenNumber == KDefaultScreenNo)
  1499 							{
  1500 							iError = KErrNone;
  1501 							}
  1502 						else
  1503 							{
  1504 							iState = EIdle;
  1505 							SendError();
  1506 							break;
  1507 							}	
  1508 						}
  1509 					}
  1510 			#endif // SYMBIAN_BUILD_GCE
  1511 			#endif // SYMBIAN_ENABLE_MMF_MULTISCREEN_SUPPORT
  1512 				iCurrentConfig->iEventMonitor->Start();
  1513 
  1514 				if (iCurrentConfig == iSecondaryConfig)
  1515 					{
  1516 					iState = EAddSource;
  1517 					KickState();
  1518 					}
  1519 				else
  1520 					{
  1521 					iState = EAddSink;
  1522 					KickState();
  1523 					}
  1524 				}
  1525 			}
  1526 			break;
  1527 
  1528 		case EAddSource:
  1529 			{
  1530 			iState = EWaitingForSource;
  1531 			const CMMSourceSink* source = iCurrentConfig->iSource;
  1532 			// CMMSourceSink has the ability to transform the data it stored into a data stream
  1533 			// which can be passed to CMMFAddDataSourceSinkAsync for further processing.
  1534 			// CMMFileSourceSink, which is a specialized CMMSourceSink, stores info about a file
  1535 			// source/sink. The info about the file can be a file path or a file handle.
  1536 			// When it holds a file handle and turns info into data stream, the file handle is
  1537 			// stored as a pointer in the stream. However, at this point, it cannot guarantee that
  1538 			// the streamed info is always extracted within the same process. If the pointer is 
  1539 			// dereferenced in other process, a panic will raise in the system. Therefore, a file
  1540 			// handle, rather than pointer, is used when necessary.
  1541 			if (iUsingSecureDrmProcess && source->CarryingFileHandle())
  1542 				{
  1543 				iAddDataSourceSinkAsync->AddFileHandleDataSource(*iCurrentConfig->iController,
  1544 																 static_cast<const CMMFileSourceSink*>(source)->FileHandle(),
  1545 																 source->SourceSinkData());
  1546 				}
  1547 			else
  1548 				{
  1549 				iAddDataSourceSinkAsync->AddDataSource(*iCurrentConfig->iController, 
  1550 													   source->SourceSinkUid(), 
  1551 													   source->SourceSinkData());
  1552 				}
  1553 			}
  1554 			break;
  1555 
  1556 		case EAddSink:
  1557 			{
  1558 			iState = EWaitingForSink;
  1559 			const CMMSourceSink* sink = iCurrentConfig->iSink;
  1560 			// CMMSourceSink has the ability to transform the data it stored into a data stream
  1561 			// which can be passed to CMMFAddDataSourceSinkAsync for further processing.
  1562 			// CMMFileSourceSink, which is a specialized CMMSourceSink, stores info about a file
  1563 			// source/sink. The info about the file can be a file path or a file handle.
  1564 			// When it holds a file handle and turns info into data stream, the file handle is
  1565 			// stored as a pointer in the stream. However, at this point, it cannot guarantee that
  1566 			// the streamed info is always extracted within the same process. If the pointer is 
  1567 			// dereferenced in other process, a panic will raise in the system. Therefore, a file
  1568 			// handle, rather than pointer, is used when necessary.
  1569 			const TDesC8& sinkData = sink->SourceSinkData();
  1570 			if (iUsingSecureDrmProcess && sink->CarryingFileHandle())
  1571 				{
  1572 				iAddDataSourceSinkAsync->AddFileHandleDataSink(*iCurrentConfig->iController,
  1573 															   static_cast<const CMMFileSourceSink*>(sink)->FileHandle(),
  1574 															   sinkData);
  1575 				}
  1576 			else
  1577 				{
  1578 				iAddDataSourceSinkAsync->AddDataSink(*iCurrentConfig->iController, 
  1579 													 sink->SourceSinkUid(), 
  1580 													 sinkData);
  1581 				}
  1582 			}
  1583 			break;
  1584 		
  1585 		case EWaitingForSource:
  1586 			break;
  1587 
  1588 		case EWaitingForSink:
  1589 			break;
  1590 
  1591 		case ESendError:
  1592 			SendError();
  1593 			iState = EIdle;
  1594 			break;
  1595 
  1596 		case EIdle:
  1597 		default:
  1598 			break;
  1599 		}
  1600 	}
  1601 
  1602 void CMMFFindAndOpenController::TryNextController()
  1603 	{
  1604 	// If an error occurred close the controller.
  1605 	if (iError != KErrNone)
  1606 		{
  1607 		CloseController();
  1608 		}
  1609 	
  1610 	iStopTryLoadController = EFalse;
  1611 	
  1612 	if (iMode == EOpenByControllerUid || ++iControllerIndex >= iControllerCount)
  1613 		{
  1614 		//Raise a flag to stop trying to load the controllers
  1615 		iStopTryLoadController = ETrue;
  1616 		
  1617 		// KErrNotSupported is the default error, but will only be used if no other error 
  1618 		// has been discovered (the first error found is used by default)
  1619 		// However, KErrBadHandle seems to mean that we tried to use the DRM server without
  1620 		// RFs::ShareProtected() having been called, so force usage of KErrNotSupported so
  1621 		// client does not see changed 
  1622 		TBool forceErrorUse = EFalse;
  1623 		if (iError==KErrBadHandle)
  1624 			{
  1625 			forceErrorUse = ETrue;
  1626 			}
  1627 		SendError(KErrNotSupported, forceErrorUse);		
  1628 			
  1629 		return;
  1630 		}
  1631 
  1632 	if (iMode == EOpenByFileName || iMode == EOpenByFormatUid)
  1633 		{
  1634 		iControllerImplInfo = iPrioritisedControllers[iControllerIndex];
  1635 		}
  1636 	else	//if (iMode == EOpenByDescriptor || iMode == EOpenByUrl)
  1637 		{
  1638 		iControllerImplInfo = iControllers[iControllerIndex];
  1639 		}
  1640 
  1641 	iCurrentConfig->iControllerUid = iControllerImplInfo->Uid();
  1642 	iState = EOpenController;
  1643 	KickState();
  1644 	}
  1645 
  1646 void CMMFFindAndOpenController::MadssaoAddDataSourceSinkAsyncComplete(TInt aError, const TMMFMessageDestination& aHandle)
  1647 	{
  1648 	iError = aError;
  1649 
  1650 	// take the first available exit if we're out of memory
  1651 	// or we've been cancelled
  1652 	if (iError == KErrNoMemory || iError == KErrCancel)
  1653 		{
  1654 		SendError();
  1655 		return;
  1656 		}
  1657 
  1658 	// failed to add source or sink - try the next controller
  1659 	if (aError != KErrNone)
  1660 		{
  1661 		TryNextController();
  1662 		return;
  1663 		}
  1664 
  1665 	if (iState == EWaitingForSource)
  1666 		{
  1667 		#ifdef SYMBIAN_ENABLE_MMF_MULTISCREEN_SUPPORT
  1668 		#ifdef SYMBIAN_BUILD_GCE
  1669 		// If surfaces are required try to use them.  If this fails then fall back to using
  1670 		// direct screen access.
  1671 		if(iCurrentConfig->iControllerMode == EPlayback && iMediaId == KUidMediaTypeVideo)
  1672 			{
  1673 			// UseSurfaces call has to be done after adding data sink and adding data source.
  1674 			iSurfaceSupported = iVideoPlaySurfaceSupportCustomCommands->UseSurfaces();
  1675 			
  1676 			if (iSurfaceSupported == KErrNotSupported)
  1677 				{
  1678 				if (iUseVPU2)
  1679 					{
  1680 					if (ControllerIndex() < ControllerCount() - 1)
  1681 						{
  1682 						// Until end of the list of controllers,
  1683 						// try the next one for surface support
  1684 						TryNextController(); // this will also kick-state
  1685 						return;
  1686 						}
  1687 					else
  1688 						{
  1689 						iError = iSurfaceSupported;
  1690 						}
  1691 					}
  1692 				else 
  1693 					{
  1694 					// No surface enabled controller found 
  1695 					// not required to do only surface, 
  1696 					// use the last one that matched.
  1697 					iError = iVideoSetInitScreenCustomCommands->SetInitScreenNumber(iScreenNumber);
  1698 					if (iError == KErrNotSupported && iScreenNumber == KDefaultScreenNo)
  1699 						{
  1700 						iError = KErrNone;
  1701 						}
  1702 					}
  1703 				}
  1704 			else
  1705 				{
  1706 				iError = iSurfaceSupported;
  1707 				}
  1708 			}
  1709 		#endif // SYMBIAN_BUILD_GCE
  1710 		#endif // SYMBIAN_ENABLE_MMF_MULTISCREEN_SUPPORT
  1711 			
  1712 		iSourceHandle = aHandle;
  1713 		if (iCurrentConfig == iSecondaryConfig)
  1714 			{
  1715 			iState = EAddSink;
  1716 			}
  1717 		else	// completed ok !
  1718 			{
  1719 			iState = EIdle;
  1720 			SendError(KErrNone, ETrue);
  1721 			return;
  1722 			}
  1723 		}
  1724 	else if (iState == EWaitingForSink)
  1725 		{
  1726 		iSinkHandle = aHandle;
  1727 		if (iCurrentConfig == iSecondaryConfig)	// completed ok !
  1728 			{
  1729 			iState = EIdle;
  1730 			iError = KErrNone;
  1731 			SendError();
  1732 			return;
  1733 			}
  1734 		else
  1735 			{
  1736 			iState = EAddSource;
  1737 			}
  1738 		}
  1739 
  1740 	KickState();
  1741 	}
  1742 
  1743 void CMMFFindAndOpenController::SendError(TInt aError, TBool aOverrideError)
  1744 	{
  1745 	if (iError == KErrNone || aOverrideError)
  1746 		{
  1747 		iError = aError;		
  1748 		}
  1749 
  1750 	iObserver.MfaocComplete(iError, iCurrentConfig->iController, iCurrentConfig->iControllerUid, &iSourceHandle, &iSinkHandle);
  1751 
  1752 	// if we've just attempted to open the Secondary controller, 
  1753 	// try to open the Primary controller
  1754 	if (iCurrentConfig == iSecondaryConfig)
  1755 		{
  1756 		if (iError == KErrNone)
  1757 			OpenPrimaryController();
  1758 		}
  1759 
  1760 	// if we failed to open, may as well free up some memory
  1761 	// if open succeeded we need to preserve state in case of a re-open
  1762 	if (iError != KErrNone)
  1763 		{
  1764 		if(iControllerIndex >= iControllerCount-1)
  1765 			{
  1766 			Close();
  1767 			}
  1768 		else //if there are other controllers selected in the controller list, try them
  1769 			{
  1770 			Cancel();
  1771 			if(iAddDataSourceSinkAsync)
  1772 				{
  1773 				iAddDataSourceSinkAsync->Cancel();
  1774 				}
  1775 
  1776  			TryNextController();
  1777 			}
  1778 		}
  1779 	}
  1780 
  1781 void CMMFFindAndOpenController::SchedSendError(TInt aError)
  1782 	{
  1783 	if (aError != KErrNone)
  1784 		iError = aError;
  1785 	iState = ESendError;
  1786 	KickState();
  1787 	}
  1788 
  1789 void CMMFFindAndOpenController::BuildControllerListFileNameL()
  1790 	{
  1791 	// Retrieve a list of possible controllers from ECOM
  1792 	// If we don't have a match, leave with unsupported
  1793 
  1794 	iControllers.ResetAndDestroy();
  1795 	iPrioritisedControllers.Reset();
  1796 
  1797 	TControllerMode mode = iCurrentConfig->iControllerMode;
  1798 
  1799 	// if we're playing, try to get the MIME type from the Content Access
  1800 	// Framework (CAF) & use that to select a controller - if that fails, 
  1801 	// try to select a controller based on the header data/file extension
  1802 	
  1803 	CMMFUtilityFileInfo* fileInfo = NULL;
  1804 
  1805 	TInt error;
  1806 	
  1807 	//If the current CMMSourceSink is a CMMFileSourceSink
  1808 	// Using the previous version we'd get KErrCANoPermission when calling EvaluateIntent in the
  1809 	// CMMFUtilityFileInfo ConstructL as the intent == EUnknown, so now pass the intent as a parameter
  1810 	// to TMMFileHandleSource and....
  1811 	TBool isSecureDrmProcess = EFalse;
  1812 	//need to do this only in local playback mode
  1813 	//UseSecureDRMProcess() function in called only in case of local play / record
  1814 	// so we'll just chk for playback mode
  1815 	if(mode == EPlayback)
  1816 	    {
  1817 	    TRAP(error, UseSecureDRMProcessL(isSecureDrmProcess));
  1818 	    if(error == KErrPermissionDenied)
  1819 	    	{
  1820 	    	isSecureDrmProcess = ETrue;
  1821 	    	}
  1822 	    else
  1823 	    	{
  1824 	    	User::LeaveIfError(error);
  1825 	    	}
  1826 	    }
  1827     TRAP(error, fileInfo = CreateFileInfoL(isSecureDrmProcess));
  1828     
  1829 	if (fileInfo != NULL)
  1830 		{
  1831 		CleanupDeletePushL(fileInfo);
  1832 		}
  1833 	
  1834 	if (error != KErrNone)
  1835 		{
  1836 		// if playback mode, leave for any error
  1837 		// if record mode, allow KErrNotFound
  1838 		if (mode == EPlayback || (mode != EPlayback && error != KErrNotFound))
  1839 			{
  1840 			User::Leave(error);
  1841 			}
  1842 		}
  1843 
  1844 	CMMFControllerPluginSelectionParameters* cSelect = NULL;
  1845 	if (isSecureDrmProcess)
  1846 		{
  1847 		cSelect = CMMFControllerSecureDrmPluginSelectionParameters::NewLC();
  1848 		}
  1849 	else
  1850 		{
  1851 		cSelect = CMMFControllerPluginSelectionParameters::NewLC();
  1852 		}
  1853 	RArray<TUid> mediaIds;
  1854 	CleanupClosePushL(mediaIds);
  1855 	User::LeaveIfError(mediaIds.Append(iMediaId));
  1856 
  1857 	cSelect->SetMediaIdsL(mediaIds, iMediaIdMatchType);
  1858 
  1859 	if (mode == EPlayback)
  1860 		{
  1861 		ASSERT(fileInfo!=NULL);
  1862 		TBuf8<KMaxMimeLength> mimeType;
  1863 		TBool mimeTypeKnown = fileInfo->GetFileMimeTypeL(mimeType);
  1864 		if (mimeTypeKnown)
  1865 			{
  1866 			CMMFFormatSelectionParameters* fSelect = CMMFFormatSelectionParameters::NewLC();
  1867 			fSelect->SetMatchToMimeTypeL(mimeType);
  1868 			cSelect->SetRequiredPlayFormatSupportL(*fSelect);
  1869 			cSelect->ListImplementationsL(iControllers);
  1870 			CleanupStack::PopAndDestroy(fSelect);
  1871 			}
  1872 
  1873 
  1874 		// copy to the iPrioritisedControllers array - this is a NOOP if the 
  1875 		// MIME type is not known since iControllers will be empty
  1876 		ASSERT(mimeTypeKnown || iControllers.Count() == 0);
  1877 		for (TInt controllerIndex=0; controllerIndex < iControllers.Count(); controllerIndex++)
  1878 			User::LeaveIfError(iPrioritisedControllers.Append(iControllers[controllerIndex]));
  1879 
  1880 		iControllerCount = iPrioritisedControllers.Count();
  1881 		if (iControllerCount > 0)
  1882 			{
  1883 			// Clean up
  1884 			// cSelect, mediaIds, 
  1885 			CleanupStack::PopAndDestroy(2, cSelect);
  1886 			if (fileInfo != NULL)
  1887 				{
  1888 				CleanupStack::PopAndDestroy(fileInfo);
  1889 				}
  1890 			return;
  1891 			}
  1892 		}
  1893 
  1894 	// Retrieve header data first. If file doesn't exist, its ok.
  1895 	HBufC8* headerData = HBufC8::NewLC(KMaxHeaderSize);
  1896 	TPtr8 headerDataPtr = headerData->Des();
  1897 	if (fileInfo)
  1898 		{
  1899 		fileInfo->GetFileHeaderDataL(headerDataPtr, KMaxHeaderSize);
  1900 		}
  1901 
  1902 	// Get the filename's suffix
  1903 	HBufC8* fileSuffix = CMMFClientUtility::GetFileExtensionL(iFileName);
  1904 
  1905 	CleanupStack::PushL(fileSuffix);
  1906 	TPtr8 fileSuffixPtr = fileSuffix->Des();
  1907 
  1908 	// Get the secondary filename's header data (for convert)
  1909 	HBufC8* headerDataSecondary = HBufC8::NewLC(KMaxHeaderSize);
  1910 	TPtr8 headerDataPtrSecondary = headerDataSecondary->Des();
  1911 	if (iFileNameSecondary.Length() > 0 && fileInfo)
  1912 		{
  1913 		fileInfo->GetFileHeaderDataL(headerDataPtrSecondary, KMaxHeaderSize);
  1914 		}
  1915 
  1916 	// Get the secondary filename's suffix
  1917 	HBufC8* fileSuffixSecondary = CMMFClientUtility::GetFileExtensionL(iFileNameSecondary);
  1918 	CleanupStack::PushL(fileSuffixSecondary);
  1919 	TPtr8 fileSuffixPtrSecondary = fileSuffixSecondary->Des();
  1920 
  1921 
  1922 	CMMFFormatSelectionParameters* fSelect = CMMFFormatSelectionParameters::NewLC();
  1923 
  1924 	if (mode == EPlayback || mode == EConvert)
  1925 		cSelect->SetRequiredPlayFormatSupportL(*fSelect);
  1926 	if (mode == ERecord || mode == EConvert)
  1927 		cSelect->SetRequiredRecordFormatSupportL(*fSelect);
  1928 	
  1929 	cSelect->ListImplementationsL(iControllers);
  1930 	
  1931 	if (iControllers.Count()==0)
  1932 		User::Leave(KErrNotSupported);
  1933 
  1934 	if (mode == ERecord)
  1935 		{
  1936 		CMMFClientUtility::PrioritiseControllersL(
  1937 			iControllers, 
  1938 			headerDataPtrSecondary, 
  1939 			fileSuffixPtrSecondary, 
  1940 			headerDataPtr, 
  1941 			fileSuffixPtr, 
  1942 			iPrioritisedControllers);
  1943 		}
  1944 	else
  1945 		{
  1946 		CMMFClientUtility::PrioritiseControllersL(
  1947 			iControllers, 
  1948 			headerDataPtr, 
  1949 			fileSuffixPtr, 
  1950 			headerDataPtrSecondary, 
  1951 			fileSuffixPtrSecondary, 
  1952 			iPrioritisedControllers);
  1953 		}
  1954 	
  1955 	iControllerCount = iPrioritisedControllers.Count();
  1956 	if (iControllerCount == 0)
  1957 		User::Leave(KErrNotSupported);
  1958 	
  1959 	// Clean up
  1960 	// cSelect, mediaIds, 
  1961 	// headerData, fileSuffix, headerDataSecondary, fileSuffixSecondary, 
  1962 	// fSelect
  1963 	CleanupStack::PopAndDestroy(7, cSelect);
  1964 	if (fileInfo != NULL)
  1965 		{
  1966 		CleanupStack::PopAndDestroy(fileInfo);
  1967 		}
  1968 	}
  1969 
  1970 void CMMFFindAndOpenController::BuildControllerListDescriptorL()
  1971 	{
  1972 	// Retrieve a list of possible controllers from ECOM
  1973 	// If we don't have a match, leave with unsupported
  1974 
  1975 	iControllers.ResetAndDestroy();
  1976 
  1977 	CMMFControllerPluginSelectionParameters* cSelect = CMMFControllerPluginSelectionParameters::NewLC();
  1978 	CMMFFormatSelectionParameters* fSelect = CMMFFormatSelectionParameters::NewLC();
  1979 
  1980 	
  1981 	RArray<TUid> mediaIds;
  1982 	CleanupClosePushL(mediaIds);
  1983 	User::LeaveIfError(mediaIds.Append(iMediaId));
  1984 
  1985 	cSelect->SetMediaIdsL(mediaIds, iMediaIdMatchType);
  1986 	
  1987 	TPtrC8 header = iDescriptor.Left(KMaxHeaderSize);
  1988 	fSelect->SetMatchToHeaderDataL(header);
  1989 	
  1990 	
  1991 	TControllerMode mode = iCurrentConfig->iControllerMode;
  1992 	if (mode == EPlayback || mode == EConvert)
  1993 		cSelect->SetRequiredPlayFormatSupportL(*fSelect);
  1994 	if (mode == ERecord || mode == EConvert)
  1995 		cSelect->SetRequiredRecordFormatSupportL(*fSelect);
  1996 
  1997 	cSelect->ListImplementationsL(iControllers);
  1998 
  1999 	iControllerCount = iControllers.Count();
  2000 	if (iControllerCount == 0)
  2001 		User::Leave(KErrNotSupported);
  2002 
  2003 	// Clean up
  2004 	// cSelect, fSelect, mediaIds
  2005 	CleanupStack::PopAndDestroy(3, cSelect);
  2006 	}
  2007 
  2008 void CMMFFindAndOpenController::BuildControllerListUrlL()
  2009 	{
  2010 	// Retrieve a list of possible controllers from ECOM
  2011 	// If we don't have a match, leave with unsupported
  2012 
  2013 	iControllers.ResetAndDestroy();
  2014 
  2015 	CMMFControllerPluginSelectionParameters* cSelect = CMMFControllerPluginSelectionParameters::NewLC();
  2016 	CMMFFormatSelectionParameters* fSelect = CMMFFormatSelectionParameters::NewLC();
  2017 
  2018 	RArray<TUid> mediaIds;
  2019 	CleanupClosePushL(mediaIds);
  2020 	User::LeaveIfError(mediaIds.Append(iMediaId));
  2021 
  2022 	cSelect->SetMediaIdsL(mediaIds, iMediaIdMatchType);
  2023 	
  2024 
  2025  	if (*iMimeType != KNullDesC8)
  2026 		{
  2027 		fSelect->SetMatchToMimeTypeL(*iMimeType);//We match to mime type
  2028 		}
  2029 	else
  2030 		{
  2031 		fSelect->SetMatchToUriSupportL(*iUrl);
  2032 		}
  2033 	
  2034 	TControllerMode mode = iCurrentConfig->iControllerMode;
  2035 	if (mode == EPlayback || mode == EConvert)
  2036 		cSelect->SetRequiredPlayFormatSupportL(*fSelect);
  2037 	if (mode == ERecord || mode == EConvert)
  2038 		cSelect->SetRequiredRecordFormatSupportL(*fSelect);
  2039 
  2040 	cSelect->ListImplementationsL(iControllers);
  2041 
  2042 	iControllerCount = iControllers.Count();
  2043 	if (iControllerCount == 0)
  2044 		User::Leave(KErrNotSupported);
  2045 
  2046 	// Clean up
  2047 	// cSelect, fSelect, mediaIds
  2048 	CleanupStack::PopAndDestroy(3, cSelect);
  2049 	}
  2050 
  2051 void CMMFFindAndOpenController::BuildControllerListFormatL()
  2052 	{
  2053 	// Retrieve a list of possible controllers from ECOM
  2054 	// If we don't have a match, leave with unsupported
  2055 
  2056 	iControllers.ResetAndDestroy();
  2057 	iPrioritisedControllers.Reset();
  2058 
  2059 	CMMFControllerPluginSelectionParameters* cSelect = CMMFControllerPluginSelectionParameters::NewLC();
  2060 
  2061 	// Select the media IDs to allow
  2062 	RArray<TUid> mediaIds;
  2063 	CleanupClosePushL(mediaIds);
  2064 	User::LeaveIfError(mediaIds.Append(iMediaId));
  2065 
  2066 	cSelect->SetMediaIdsL(mediaIds, iMediaIdMatchType);
  2067 
  2068 	CMMFFormatSelectionParameters* fSelect = CMMFFormatSelectionParameters::NewLC();
  2069 
  2070 	TControllerMode mode = iCurrentConfig->iControllerMode;
  2071 	if (mode == EPlayback || mode == EConvert)
  2072 		cSelect->SetRequiredPlayFormatSupportL(*fSelect);
  2073 	if (mode == ERecord || mode == EConvert)
  2074 		cSelect->SetRequiredRecordFormatSupportL(*fSelect);
  2075 
  2076 	//Obtain a list of the controllers
  2077 	cSelect->ListImplementationsL(iControllers);
  2078 
  2079 	CleanupStack::PopAndDestroy(3, cSelect); // cSelect, mediaIds, fSelect
  2080 
  2081 	iControllerCount = iControllers.Count();
  2082 	if (iControllerCount == 0)
  2083 		User::Leave(KErrNotSupported);
  2084 
  2085 	TUid formatUidPrimary;
  2086 	TUid formatUidSecondary;
  2087 	if (mode == ERecord)
  2088 		{
  2089 		formatUidSecondary = iFormatUid;
  2090 		formatUidPrimary = iFormatUidSecondary;
  2091 		}
  2092 	else
  2093 		{
  2094 		formatUidPrimary = iFormatUid;
  2095 		formatUidSecondary = iFormatUidSecondary;
  2096 		}
  2097 	
  2098 	for (TInt controllerIndex=0; controllerIndex < iControllers.Count(); controllerIndex++)
  2099 		{
  2100 		const RMMFFormatImplInfoArray& recFormatInfo = iControllers[controllerIndex]->RecordFormats();
  2101 		const RMMFFormatImplInfoArray& playFormatInfo = iControllers[controllerIndex]->PlayFormats();
  2102 
  2103 		TBool playFormatMatched = EFalse;
  2104 		TBool recordFormatMatched = EFalse;
  2105 
  2106 		if (formatUidPrimary == KNullUid)
  2107 			{
  2108 			playFormatMatched = ETrue;
  2109 			}
  2110 		else
  2111 			{
  2112 			for(TInt playFormatIndex =0; playFormatIndex < playFormatInfo.Count(); playFormatIndex++)
  2113 				{
  2114 				if(playFormatInfo[playFormatIndex]->Uid() == formatUidPrimary)
  2115 					{
  2116 					playFormatMatched = ETrue;
  2117 					break;
  2118 					}
  2119 				}
  2120 			}
  2121 
  2122 		if (formatUidSecondary == KNullUid)
  2123 			{
  2124 			recordFormatMatched = ETrue;
  2125 			}
  2126 		else
  2127 			{
  2128 			for (TInt recFormatIndex =0; recFormatIndex < recFormatInfo.Count(); recFormatIndex++)
  2129 				{
  2130 				if (recFormatInfo[recFormatIndex]->Uid() == formatUidSecondary)
  2131 					{
  2132 					recordFormatMatched = ETrue;
  2133 					break;
  2134 					}
  2135 				}
  2136 			}
  2137 
  2138 		if (playFormatMatched && recordFormatMatched)
  2139 			User::LeaveIfError(iPrioritisedControllers.Append(iControllers[controllerIndex]));
  2140 		}
  2141 
  2142 	iControllerCount = iPrioritisedControllers.Count();
  2143 	if (iControllerCount == 0)
  2144 		User::Leave(KErrNotSupported);
  2145 	}
  2146 	
  2147 CMMSourceSink* CMMFFindAndOpenController::CreateSourceSinkL(const TSourceSink& aParams) 
  2148 	{
  2149 	if (aParams.iUseFileHandle)
  2150 		{
  2151 		return CMMFileSourceSink::NewL(aParams.iUid, aParams.iFileHandle);
  2152 		}
  2153 	return CMMSourceSink::NewL(aParams.iUid, aParams.iConfigData);
  2154 	}
  2155 
  2156 
  2157 CMMSourceSink* CMMFFindAndOpenController::CreateSourceSinkL(const TMMSource& aSource) 
  2158 	{	
  2159 	if (!(aSource.SourceType()==KUidMMFileSource || 
  2160 		aSource.SourceType()==KUidMMFileHandleSource))
  2161 		User::Leave(KErrNotSupported);
  2162 
  2163 	return CMMFileSourceSink::NewL(KUidMmfFileSource, aSource);
  2164 	}
  2165 
  2166 CMMFUtilityFileInfo* CMMFFindAndOpenController::CreateFileInfoL(TBool aSecureDRMMode)
  2167 	{
  2168 	CMMFUtilityFileInfo* fileInfo = NULL;
  2169 	if (iUseFileHandle) 
  2170 		{
  2171 		if (iUniqueId != NULL)
  2172 			{
  2173 			TMMFileHandleSource fileHandleSource(iFileHandle, (*iUniqueId), iIntent,iEnableUi);
  2174 			fileInfo = CMMFUtilityFileInfo::NewL(fileHandleSource, aSecureDRMMode);
  2175 			}
  2176 		else
  2177 			{
  2178 			TMMFileHandleSource fileHandleSource(iFileHandle);
  2179 			fileInfo = CMMFUtilityFileInfo::NewL(fileHandleSource, aSecureDRMMode);
  2180 			}
  2181 		}
  2182 	else
  2183 		{
  2184 		if (iUniqueId != NULL)
  2185 			{
  2186 			TMMFileSource fileSource(iFileName, (*iUniqueId), iIntent,iEnableUi);	
  2187 			fileInfo = CMMFUtilityFileInfo::NewL(fileSource, aSecureDRMMode);
  2188 			}
  2189 		else
  2190 			{
  2191 			TMMFileSource fileSource(iFileName);	
  2192 			fileInfo = CMMFUtilityFileInfo::NewL(fileSource, aSecureDRMMode);
  2193 			}
  2194 		}
  2195 	return fileInfo;
  2196 	}
  2197 	
  2198 EXPORT_C CMMFFindAndOpenController::TSourceSink::TSourceSink(TUid aUid, const TDesC8& aConfigData)	
  2199 	: iConfigData(aConfigData)
  2200 	{
  2201 	iUid = aUid;
  2202 
  2203 	iUseFileHandle = EFalse;
  2204 	}
  2205 	
  2206 EXPORT_C CMMFFindAndOpenController::TSourceSink::TSourceSink(TUid aUid, const RFile& aFile)	
  2207 	: iConfigData(KNullDesC8)
  2208 	{
  2209 	iUid = aUid;
  2210 
  2211 	iFileHandle = aFile;
  2212 	iUseFileHandle = ETrue;
  2213 	}
  2214 	
  2215 EXPORT_C void CMMFFindAndOpenController::SetInitScreenNumber(TInt aScreenNumber, RMMFVideoSetInitScreenCustomCommands* aVideoSetInitScreenCustomCommands)
  2216 	{	
  2217 	iScreenNumber = aScreenNumber;
  2218 	iVideoSetInitScreenCustomCommands = aVideoSetInitScreenCustomCommands;
  2219 	}
  2220 		
  2221 CMMFFindAndOpenController::CConfig::CConfig()
  2222 	{
  2223 	}
  2224 	
  2225 void CMMFFindAndOpenController::CConfig::Close()
  2226 	{
  2227 	delete iSource;
  2228 	iSource = NULL;
  2229 	delete iSink;
  2230 	iSink = NULL;
  2231 	}
  2232 CMMFFindAndOpenController::CConfig::~CConfig()
  2233 	{
  2234 	Close();
  2235 	}
  2236 
  2237 void CMMFFindAndOpenController::UseSecureDRMProcessL(TBool& aIsSecureDrmProcess)
  2238     {
  2239     if(iHasDrmCapability)//if client has DRM capability, we never use Secure DRM Process
  2240         {
  2241         aIsSecureDrmProcess = EFalse;
  2242         return;
  2243         }       
  2244     TBool isDataProtected = EFalse;
  2245     ContentAccess::CContent* content = NULL;
  2246     TControllerMode mode = iCurrentConfig->iControllerMode;
  2247 
  2248     //setting aUseSecureDrmProcess to false(default value)
  2249     aIsSecureDrmProcess = EFalse;
  2250 
  2251     //need to proceed only in case of local playback mode
  2252     TUid sourceUid = iCurrentConfig->iSource->SourceSinkUid();
  2253     TBool localPlaybackMode = ( mode == EPlayback && 
  2254                                 (sourceUid == KUidMmfFileSource || sourceUid == KUidMmfDescriptorSource) );
  2255     if(!localPlaybackMode)
  2256         {
  2257         return;
  2258         }
  2259 
  2260     if (iUseFileHandle && iOwnFileHandle) 
  2261         {
  2262         content = ContentAccess::CContent::NewLC(iFileHandle);
  2263         }
  2264     else if(iFileName.Length())  //need to check if file name exist
  2265         {
  2266         content = ContentAccess::CContent::NewLC(iFileName);
  2267         }
  2268     else
  2269         {//in case of descriptor source content object will not be created
  2270         return;
  2271         }
  2272     TInt value = 0;
  2273     TInt error = KErrNone;
  2274     if(iUniqueId != NULL)
  2275     	{
  2276     	error = content->GetAttribute(EIsProtected, value, *iUniqueId );
  2277     	}
  2278     else
  2279     	{
  2280     	error = content->GetAttribute(EIsProtected, value);
  2281     	}
  2282     if( (error == KErrNone && value) || error == KErrPermissionDenied )
  2283         {//2nd condition can be true if GetAttribute checks for DRM cap and return error if not found
  2284         isDataProtected = ETrue;
  2285         }
  2286     else if( error != KErrNone && error != KErrPermissionDenied)
  2287         {//leaving as GetAttribute of CAF caused an error.
  2288         User::Leave(error);
  2289         }
  2290 
  2291     CleanupStack::PopAndDestroy(content);
  2292     if(isDataProtected && !iHasDrmCapability && mode == EPlayback)
  2293         {//only when the Data is protected and client does not have the DRM capability, we need secure DRM process
  2294         aIsSecureDrmProcess = ETrue;
  2295         }
  2296     }
  2297 
  2298 EXPORT_C CMMSourceSink* CMMSourceSink::NewLC(TUid aUid, const TDesC8& aDescriptor)
  2299 	{
  2300 	CMMSourceSink* self = new (ELeave) CMMSourceSink(aUid);	
  2301 	CleanupStack::PushL(self);
  2302 	self->ConstructL(aDescriptor);
  2303 	return self;
  2304 	}
  2305 
  2306 EXPORT_C CMMSourceSink* CMMSourceSink::NewL(TUid aUid, const TDesC8& aDescriptor)
  2307 	{
  2308 	CMMSourceSink* sourcesink = CMMSourceSink::NewLC(aUid, aDescriptor);
  2309 	CleanupStack::Pop(sourcesink);
  2310 	return sourcesink;
  2311 	}
  2312 
  2313 CMMSourceSink::CMMSourceSink(TUid aUid)
  2314 	: iUid(aUid)
  2315 	{
  2316 	}
  2317 	
  2318 CMMSourceSink::~CMMSourceSink()
  2319 	{
  2320 	delete iBuf;
  2321 	}
  2322 	
  2323 void CMMSourceSink::ConstructL(const TDesC8& aDescriptor)
  2324 	{
  2325 	iBuf = aDescriptor.AllocL();
  2326 	}
  2327 	
  2328 TUid CMMSourceSink::SourceSinkUid() const
  2329 	{
  2330 	return iUid;
  2331 	}
  2332 	
  2333 const TDesC8& CMMSourceSink::SourceSinkData() const
  2334 	{
  2335 	return *iBuf;
  2336 	}
  2337 	
  2338 TBool CMMSourceSink::CarryingFileHandle() const
  2339 	{
  2340 	return EFalse;
  2341 	}
  2342 
  2343 EXPORT_C CMMFileSourceSink* CMMFileSourceSink::NewLC(TUid aUid, const RFile& aFile)
  2344 	{
  2345 	CMMFileSourceSink* self = new (ELeave) CMMFileSourceSink(aUid);	
  2346 	CleanupStack::PushL(self);
  2347 	self->ConstructL(aFile);
  2348 	return self;
  2349 	}
  2350 
  2351 EXPORT_C CMMFileSourceSink* CMMFileSourceSink::NewL(TUid aUid, const RFile& aFile)
  2352 	{
  2353 	CMMFileSourceSink* sourcesink = CMMFileSourceSink::NewLC(aUid, aFile);
  2354 	CleanupStack::Pop(sourcesink);
  2355 	return sourcesink;
  2356 	}
  2357 	
  2358 CMMFileSourceSink::CMMFileSourceSink(TUid aUid)
  2359 	: CMMSourceSink(aUid)
  2360 	{
  2361 	}
  2362 
  2363 void CMMFileSourceSink::ConstructL(const RFile& aFile)
  2364 	{
  2365 	User::LeaveIfError(iHandle.Duplicate(aFile));
  2366 	iUsingFileHandle = ETrue;
  2367 	iFileName = HBufC::NewMaxL(KMaxFileName);
  2368 	TPtr fileNamePtr = iFileName->Des();
  2369 	iHandle.Name(fileNamePtr);
  2370 	DoCreateFileHandleSourceConfigDataL();
  2371 	}
  2372 
  2373 void CMMFileSourceSink::DoCreateFileHandleSourceConfigDataL()
  2374 	{
  2375 	CBufFlat* buf = CBufFlat::NewL(KExpandSize);
  2376 	CleanupStack::PushL(buf);
  2377 	RBufWriteStream stream;
  2378 	stream.Open(*buf);
  2379 	CleanupClosePushL(stream);
  2380 	
  2381 	TPckgBuf<RFile*> fileptr(&iHandle);
  2382 	stream.WriteInt32L(KMMFileHandleSourceUid.iUid);
  2383 	stream.WriteL(fileptr);
  2384 	
  2385 	TInt length = 0;
  2386 	if (iUniqueId != NULL)
  2387 		length = iUniqueId->Length();
  2388 	stream.WriteInt32L(length);
  2389 	if (length>0)
  2390 		stream.WriteL(*iUniqueId);
  2391 	
  2392 	stream.WriteInt32L(iEnableUI);
  2393 	
  2394 	stream.CommitL();
  2395 	CleanupStack::PopAndDestroy(&stream);		
  2396 	iSourceSinkData = buf->Ptr(0).AllocL();
  2397 	
  2398 	CleanupStack::PopAndDestroy(buf); 
  2399 	}
  2400 	
  2401 const TDesC8& CMMFileSourceSink::SourceSinkData() const
  2402 	{
  2403 	ASSERT(iSourceSinkData);
  2404 	return *iSourceSinkData;
  2405 	}
  2406 
  2407 CMMFileSourceSink::~CMMFileSourceSink()
  2408 	{
  2409 	iHandle.Close(); // delete whatever
  2410 	delete iFileName;
  2411 	delete iSourceSinkData;
  2412 	delete iUniqueId;
  2413 	}
  2414 
  2415 EXPORT_C CMMFileSourceSink* CMMFileSourceSink::NewLC(TUid aUid, const TMMSource& aSource)
  2416 	{
  2417 	CMMFileSourceSink* self = new (ELeave) CMMFileSourceSink(aUid);	
  2418 	CleanupStack::PushL(self);
  2419 	self->ConstructL(aSource);
  2420 	return self;
  2421 	}
  2422 
  2423 EXPORT_C CMMFileSourceSink* CMMFileSourceSink::NewL(TUid aUid, const TMMSource& aSource)
  2424 	{
  2425 	CMMFileSourceSink* sourcesink = CMMFileSourceSink::NewLC(aUid, aSource);
  2426 	CleanupStack::Pop(sourcesink);
  2427 	return sourcesink;
  2428 	}
  2429 	
  2430 void CMMFileSourceSink::ConstructL(const TMMSource& aSource)
  2431 	{
  2432 	iUniqueId = aSource.UniqueId().AllocL();
  2433 	iIntent = aSource.Intent();
  2434 	iEnableUI = aSource.IsUIEnabled();
  2435 	
  2436 	if (aSource.SourceType() == KUidMMFileSource)
  2437 		{
  2438 		const TMMFileSource& fileSource = static_cast<const TMMFileSource&>(aSource);
  2439 		iFileName = fileSource.Name().AllocL();
  2440 		
  2441 		DoCreateFileSourceConfigDataL();
  2442 		}
  2443 	else if (aSource.SourceType() == KUidMMFileHandleSource)
  2444 		{
  2445 		const TMMFileHandleSource& fileHandleSource = static_cast<const TMMFileHandleSource&>(aSource);
  2446 		iHandle.Close(); // in case already open
  2447 		User::LeaveIfError(iHandle.Duplicate(fileHandleSource.Handle()));
  2448 		iUsingFileHandle = ETrue;
  2449 		iFileName = HBufC::NewMaxL(KMaxFileName);
  2450 		TPtr fileNamePtr = iFileName->Des();
  2451 		iHandle.Name(fileNamePtr);
  2452 		
  2453 		DoCreateFileHandleSourceConfigDataL();
  2454 		}
  2455 	else
  2456 		{
  2457 		User::Leave(KErrNotSupported);
  2458 		}
  2459 	}
  2460 	
  2461 void CMMSourceSink::EvaluateIntentL()
  2462 	{
  2463 	}
  2464 	
  2465 void CMMFileSourceSink::EvaluateIntentL()
  2466 	{
  2467 	if (iUsingFileHandle)
  2468 		{
  2469    		ContentAccess::CContent* Content = ContentAccess::CContent::NewLC(iHandle);
  2470    		Content->OpenContentLC(iIntent, *iUniqueId);
  2471    		CleanupStack::PopAndDestroy(2, Content);	
  2472 		}
  2473 	else	
  2474 		{
  2475 		ContentAccess::CContent* Content = ContentAccess::CContent::NewLC(*iFileName);
  2476    		Content->OpenContentLC(iIntent, *iUniqueId);
  2477    		CleanupStack::PopAndDestroy(2, Content);
  2478 		}
  2479 	}
  2480 
  2481 
  2482 	
  2483 EXPORT_C void CMMFileSourceSink::EvaluateIntentL(ContentAccess::TIntent aIntent)
  2484 	{
  2485 	if (iUsingFileHandle)
  2486 		{
  2487    		ContentAccess::CContent* Content = ContentAccess::CContent::NewLC(iHandle);
  2488    		Content->OpenContentLC(aIntent, *iUniqueId);
  2489    		CleanupStack::PopAndDestroy(2, Content);	
  2490 		}
  2491 	else	
  2492 		{
  2493 		ContentAccess::CContent* Content = ContentAccess::CContent::NewLC(*iFileName);
  2494    		Content->OpenContentLC(aIntent, *iUniqueId);
  2495    		CleanupStack::PopAndDestroy(2, Content);
  2496 		}
  2497 	}
  2498 
  2499 void CMMFileSourceSink::DoCreateFileSourceConfigDataL()
  2500 	{
  2501 	CBufFlat* buf = CBufFlat::NewL(KExpandSize);
  2502 	CleanupStack::PushL(buf);
  2503 	RBufWriteStream stream;
  2504 	stream.Open(*buf);
  2505 	CleanupClosePushL(stream);
  2506 	
  2507 	stream.WriteInt32L(KMMFileSourceUid.iUid);
  2508 	stream.WriteInt32L(iFileName->Length());
  2509 	stream.WriteL(*iFileName);
  2510 	TInt length = 0;
  2511 	if (iUniqueId != NULL)
  2512 		length = iUniqueId->Length();
  2513 	stream.WriteInt32L(length);
  2514 	if (length>0)
  2515 		stream.WriteL(*iUniqueId);
  2516 	
  2517 	stream.WriteInt32L(iEnableUI);
  2518 	
  2519 	stream.CommitL();
  2520 	CleanupStack::PopAndDestroy(&stream);
  2521 	iSourceSinkData = buf->Ptr(0).AllocL();
  2522 		
  2523 	CleanupStack::PopAndDestroy(buf); 
  2524 	}	
  2525 	
  2526 TBool CMMFileSourceSink::CarryingFileHandle() const
  2527 	{
  2528 	return iUsingFileHandle;
  2529 	}
  2530 
  2531