ui/uiengine/medialists/src/glxcachemanager.cpp
branchRCL_3
changeset 59 8e5f6eea9c9f
equal deleted inserted replaced
57:ea65f74e6de4 59:8e5f6eea9c9f
       
     1 /*
       
     2 * Copyright (c) 2008-2009 Nokia Corporation and/or its subsidiary(-ies). 
       
     3 * All rights reserved.
       
     4 * This component and the accompanying materials are made available
       
     5 * under the terms of "Eclipse Public License v1.0"
       
     6 * which accompanies this distribution, and is available
       
     7 * at the URL "http://www.eclipse.org/legal/epl-v10.html".
       
     8 *
       
     9 * Initial Contributors:
       
    10 * Nokia Corporation - initial contribution.
       
    11 *
       
    12 * Contributors:
       
    13 *
       
    14 * Description:    Manager of media item cache
       
    15 *
       
    16 */
       
    17 
       
    18 
       
    19 
       
    20 
       
    21 #include "glxcachemanager.h"
       
    22 
       
    23 #include <mpxcollectionutility.h>
       
    24 #include <glxtracer.h>
       
    25 #include <glxthumbnailattributeinfo.h>
       
    26 #include <glxthumbnail.h>
       
    27 #include <glxsingletonstore.h>
       
    28 #include <glximageviewermanager.h>
       
    29 
       
    30 #include "glxcache.h"
       
    31 #include "glxerrormanager.h"
       
    32 #include "glxgarbagecollector.h"
       
    33 #include "glxmedialist.h"
       
    34 #include <hal.h>
       
    35 #include <glxcollectionpluginimageviewer.hrh>
       
    36 #include <mpxmediacollectiondetaildefs.h>
       
    37 #include <mpxmediadrmdefs.h>
       
    38 #include <f32file.h>
       
    39 #include <lbsposition.h>
       
    40 #include <apgcli.h>
       
    41 #include <caf/content.h>
       
    42 #include <caf/attributeset.h>
       
    43 #include <DRMHelper.h>
       
    44 
       
    45 #ifdef USE_S60_TNM
       
    46 #include <thumbnaildata.h>
       
    47 const TInt KMaxGridThumbnailWidth = 200;
       
    48 _LIT(KFileIdentifier, ":\\");
       
    49 #endif
       
    50 
       
    51 _LIT(KDefaultType, "image/jpg");
       
    52 /// How long to wait before rechecking for cleared temporary errors
       
    53 /// @todo Find optimal value for this
       
    54 const TInt KGlxTemporaryErrorRecheckPeriodInSeconds = 5;
       
    55 
       
    56 const TInt KGlxLowerMemoryLimitForCleanUp = 15000000;
       
    57 
       
    58 const TInt KGlxUpperMemoryLimitForCleanUp = 25000000;
       
    59 
       
    60 //Defining number of pages to be flushed in critical low memory conditions.
       
    61 const TInt KGlxNoOfPagesToFlushInCriticalLowMemory = 4;
       
    62 // -----------------------------------------------------------------------------
       
    63 // InstanceL
       
    64 // -----------------------------------------------------------------------------
       
    65 //
       
    66 CGlxCacheManager* CGlxCacheManager::InstanceL()
       
    67 	{
       
    68 	TRACER("CGlxCacheManager::InstanceL");
       
    69 	
       
    70 	return CGlxSingletonStore::InstanceL(&NewL);
       
    71 	}
       
    72 
       
    73 // -----------------------------------------------------------------------------
       
    74 // NewL
       
    75 // -----------------------------------------------------------------------------
       
    76 //
       
    77 CGlxCacheManager* CGlxCacheManager::NewL()
       
    78     {
       
    79     TRACER("CGlxCacheManager::NewL");
       
    80     
       
    81     CGlxCacheManager* self = new( ELeave ) CGlxCacheManager();
       
    82     CleanupStack::PushL( self );
       
    83     self->ConstructL();
       
    84     CleanupStack::Pop(self);
       
    85     return self;
       
    86     }
       
    87 
       
    88 // -----------------------------------------------------------------------------
       
    89 // Close
       
    90 // -----------------------------------------------------------------------------
       
    91 //
       
    92 void CGlxCacheManager::Close()
       
    93 	{
       
    94 	TRACER("CGlxCacheManager::Close");
       
    95 	
       
    96 	CGlxSingletonStore::Close(this);
       
    97 	}
       
    98 
       
    99 // -----------------------------------------------------------------------------
       
   100 // Constructor
       
   101 // -----------------------------------------------------------------------------
       
   102 //
       
   103 CGlxCacheManager::CGlxCacheManager()
       
   104     {
       
   105     TRACER("CGlxCacheManager::Default Constructor");
       
   106     
       
   107     }
       
   108     
       
   109 // -----------------------------------------------------------------------------
       
   110 // ConstructL
       
   111 // -----------------------------------------------------------------------------
       
   112 //
       
   113 void CGlxCacheManager::ConstructL()
       
   114     {
       
   115     TRACER("CGlxCacheManager::ConstructL");
       
   116     
       
   117     iGarbageCollector = CGlxGarbageCollector::NewL( iCaches );
       
   118     iTempErrorTimer = CPeriodic::NewL(CActive::EPriorityStandard);
       
   119     iMaintainCacheCallback = new ( ELeave )
       
   120 	    CAsyncCallBack( TCallBack( MaintainCacheL, this ), CActive::EPriorityStandard );
       
   121 	    
       
   122 #ifdef USE_S60_TNM
       
   123     iTnEngine = CThumbnailManager::NewL( *this);
       
   124     iTnEngine->SetDisplayModeL( EColor64K );
       
   125 #endif
       
   126     }
       
   127         
       
   128 // -----------------------------------------------------------------------------
       
   129 // Destructor
       
   130 // -----------------------------------------------------------------------------
       
   131 //
       
   132 CGlxCacheManager::~CGlxCacheManager()
       
   133 	{
       
   134 	TRACER("CGlxCacheManager::Destructor");
       
   135 	
       
   136  	iObserverList.ResetAndDestroy();
       
   137  	iCaches.ResetAndDestroy();
       
   138  	delete iTempThumbnail;
       
   139  	iRequestedItemIds.Reset();
       
   140  	iRequestedAttrs.Reset();
       
   141  	iRequestedItemIndexes.Reset();
       
   142     if(iReader)
       
   143         {
       
   144         delete iReader;
       
   145         }
       
   146 
       
   147  	delete iGarbageCollector;
       
   148 
       
   149     if (iTempErrorTimer)
       
   150         {
       
   151 		iTempErrorTimer->Cancel();	
       
   152 		delete iTempErrorTimer;
       
   153         }
       
   154 
       
   155 #ifdef USE_S60_TNM
       
   156     GLX_DEBUG2("CGlxCacheManager::~CGlxCacheManager() TN Ids count()=%d",
       
   157 										 iThumbnailRequestIds.Count());
       
   158     for (TInt i = 0; i < iThumbnailRequestIds.Count(); i++)
       
   159         {
       
   160         iTnEngine->CancelRequest(iThumbnailRequestIds[i].iId);
       
   161         }
       
   162 	iThumbnailRequestIds.Reset();
       
   163     delete iTnEngine;
       
   164     delete iMPXMedia;
       
   165 #endif
       
   166     
       
   167     delete iMaintainCacheCallback;
       
   168 	}
       
   169 
       
   170 // -----------------------------------------------------------------------------
       
   171 // HandleWindowChangedL
       
   172 // From MVieMediaItemListManager
       
   173 // The list calls this function to hint the list manager, that the items 
       
   174 // the list contains might not all be loaded, and it would be nice if the list
       
   175 // manager could load the missing items to the cache.
       
   176 // -----------------------------------------------------------------------------
       
   177 //
       
   178 void CGlxCacheManager::HandleWindowChangedL(CGlxMediaList* /*aList*/) 
       
   179 	{
       
   180 	TRACER("CGlxCacheManager::HandleWindowChangedL");
       
   181 	
       
   182 	GLX_LOG_INFO("---- MGallery - CGlxCacheManager::HandleWindowChangedL()---- ");
       
   183     
       
   184     iMaintainCacheCallback->CallBack();
       
   185     // Its Better if we are not Cleaning Cache here; Instaed Can Do inside MainTainCache
       
   186     //MaintainCacheL();
       
   187     //iGarbageCollector->Cleanup();
       
   188     }
       
   189 
       
   190 // -----------------------------------------------------------------------------
       
   191 // CancelPreviousRequest
       
   192 // This API cancels the pending attributes and thumbnail request  
       
   193 // when the media item in focus is NULL
       
   194 // -----------------------------------------------------------------------------
       
   195 //
       
   196 void CGlxCacheManager::CancelPreviousRequest()
       
   197 	{
       
   198 	TRACER("CGlxCacheManager::CancelPreviousRequest");		
       
   199 	
       
   200 	// iRequestOwner is NULL, if there are no pending attribute/thumbnail request
       
   201 	// If no pending request, do nothing, else cancel the the pending requests
       
   202 	if(iRequestOwner)
       
   203 		{		
       
   204 		MMPXCollection& collection = iRequestOwner->Collection();
       
   205 		// Cancel the pending attribute request
       
   206 		collection.CancelRequest();	
       
   207 		
       
   208 #ifdef USE_S60_TNM
       
   209 		GLX_DEBUG2("CGlxCacheManager::CancelPreviousRequest() iThumbnailRequestIds.Count() %d", iThumbnailRequestIds.Count());
       
   210 		
       
   211 		// Check if any thumbnail requests are pending and cancel the requests.		
       
   212 		for (TInt i = 0; i < iThumbnailRequestIds.Count(); i++)
       
   213 			{ 			
       
   214 			iTnEngine->CancelRequest(iThumbnailRequestIds[i].iId);									
       
   215 			}
       
   216 		iThumbnailRequestIds.Reset();		
       
   217 #endif
       
   218 		iRequestOwner = NULL;
       
   219 		}
       
   220 	}
       
   221 
       
   222 // -----------------------------------------------------------------------------
       
   223 // HandleGarbageCollection
       
   224 // Garbage Collection Quick or with Timer
       
   225 // -----------------------------------------------------------------------------
       
   226 //
       
   227 void CGlxCacheManager::HandleGarbageCollectionL(TBool aStart)
       
   228     {
       
   229     TRACER("CGlxCacheManager::HandleGarbageCollection");
       
   230     TInt freeMemory = 0;
       
   231     
       
   232     HAL::Get( HALData::EMemoryRAMFree, freeMemory );
       
   233         
       
   234     if(aStart)
       
   235         {
       
   236            if(freeMemory < KGlxLowerMemoryLimitForCleanUp)
       
   237                {
       
   238                // 2 page - 30 Items for Flush
       
   239                TInt count = 2;  
       
   240                if(freeMemory < (KGlxLowerMemoryLimitForCleanUp/2))
       
   241                    {
       
   242                    // If Memory is below this limit it's ok i can wait for 60 items to clean-up
       
   243                    count = KGlxNoOfPagesToFlushInCriticalLowMemory;
       
   244                    }
       
   245                // Cancel Clean-up before Flush Page; Clean-up will be starting just after Flush page
       
   246                iGarbageCollector->CancelCleanup(); 
       
   247                iGarbageCollector->FlushPagesL(count);
       
   248                iGarbageCollector->CleanupL();
       
   249                iCleanUpOnGoing = ETrue;         // Clean up is Started now i can call CancelClean-up to Stop Clean Up
       
   250                }
       
   251            else if((freeMemory < KGlxUpperMemoryLimitForCleanUp) && !iCleanUpOnGoing)
       
   252                {
       
   253                iGarbageCollector->CleanupL();
       
   254                iCleanUpOnGoing = ETrue;         // Clean up is Started now i can call CancelClean-up to Stop Clean Up
       
   255                }
       
   256            // This is Added to Keep Assure Clean-up is not going to Disturb normal Flow if there is Enough Memory
       
   257            // We Remove this Code After Evaluation of Use of this Code
       
   258            else if(iCleanUpOnGoing)
       
   259                {
       
   260                iGarbageCollector->CancelCleanup();
       
   261                iCleanUpOnGoing = EFalse;
       
   262                }
       
   263                
       
   264            }
       
   265        else if(freeMemory < KGlxLowerMemoryLimitForCleanUp)
       
   266            {
       
   267            // 2 page - 30 Items for Flush
       
   268            TInt count = 2;
       
   269            if(freeMemory < (KGlxLowerMemoryLimitForCleanUp/2))
       
   270                {
       
   271                // If Memory is below this limit it's ok i can wait for 60 items to clean-up
       
   272                count = KGlxNoOfPagesToFlushInCriticalLowMemory;
       
   273                }
       
   274            // Cancel Clean-up before Flush Page; Clean-up will be starting just after Flush page
       
   275            iGarbageCollector->CancelCleanup();
       
   276            iGarbageCollector->FlushPagesL(count);
       
   277         iGarbageCollector->CleanupL();
       
   278         iCleanUpOnGoing = ETrue;         // Clean up is Started now i can call CancelClean-up to Stop Clean Up
       
   279         }
       
   280     else if(iCleanUpOnGoing)
       
   281         {
       
   282         iGarbageCollector->CancelCleanup();
       
   283         iCleanUpOnGoing = EFalse;
       
   284         }
       
   285     }
       
   286 		
       
   287 // -----------------------------------------------------------------------------
       
   288 // Match
       
   289 // return ETrue if path levels match
       
   290 // -----------------------------------------------------------------------------
       
   291 //
       
   292 TBool CGlxCacheManager::Match(const CMPXCollectionPath& aPath1, 
       
   293 		const CMPXCollectionPath& aPath2)
       
   294 	{
       
   295 	TRACER("CGlxCacheManager::Match");
       
   296 	
       
   297 	TInt levels1 = aPath1.Levels();
       
   298 	TInt levels2 = aPath2.Levels();
       
   299 	
       
   300 	// Paths must be as deep to match
       
   301 	if (levels1 != levels2) 
       
   302 		{
       
   303 		return EFalse; 
       
   304 		}
       
   305 		
       
   306 	// Check if all levels match
       
   307 	for (TInt i = 0; i < levels1; i++) 
       
   308 		{
       
   309 		if (aPath1.Index(i) != aPath2.Index(i))
       
   310 			{
       
   311 			return EFalse;
       
   312 			}
       
   313 		}
       
   314 		
       
   315 	return ETrue;
       
   316 	}
       
   317 	
       
   318 // -----------------------------------------------------------------------------
       
   319 // HandleCollectionMediaL
       
   320 // -----------------------------------------------------------------------------
       
   321 //
       
   322 void CGlxCacheManager::HandleCollectionMediaL(const TGlxIdSpaceId& aIdSpaceId, const CMPXMedia& aMedia, TInt aError)
       
   323     {
       
   324     TRACER("CGlxCacheManager::HandleCollectionMediaL");
       
   325     
       
   326     iRequestOwner = NULL;
       
   327 
       
   328     if ( KErrNone == aError )
       
   329         {
       
   330         // Update the cache
       
   331         CGlxCache* cache = FindCacheForceCreateL(aIdSpaceId);
       
   332         cache->MediaUpdatedL(aMedia);
       
   333         }
       
   334     else
       
   335         {
       
   336         RPointerArray< MGlxMediaUser > users;
       
   337         CleanupClosePushL( users );
       
   338         
       
   339         // Record the error on all requested attributes
       
   340         TInt idCount = iRequestedItemIds.Count();
       
   341         
       
   342         for( TInt idIndex = 0; idIndex < idCount; idIndex++ )
       
   343             {
       
   344             CGlxMedia* item = MediaForceCreateL(aIdSpaceId, iRequestedItemIds[idIndex]);
       
   345             GlxErrorManager::SetAttributeErrorL(item, iRequestedAttrs, aError);
       
   346             
       
   347             // Keep track of media lists to notify later
       
   348             TInt userCount = item->UserCount();
       
   349             for ( TInt userIndex = 0; userIndex < userCount; userIndex++ )
       
   350                 {
       
   351 				users.InsertInAddressOrderL( &item->User( userIndex ) );
       
   352                 }
       
   353             }
       
   354 
       
   355         // Notify all affected users of error
       
   356         TInt userCount = users.Count();
       
   357         for ( TInt i = 0; i < userCount; i++ )
       
   358             {
       
   359             users[ i ]->HandleError( aError );
       
   360             }
       
   361 
       
   362         CleanupStack::PopAndDestroy( &users );
       
   363         }
       
   364     
       
   365     MaintainCacheL();
       
   366     }
       
   367 
       
   368 // -----------------------------------------------------------------------------
       
   369 // FindCacheForceCreateL
       
   370 // -----------------------------------------------------------------------------
       
   371 //
       
   372 CGlxCache* CGlxCacheManager::FindCacheForceCreateL(const TGlxIdSpaceId& aIdSpaceId)
       
   373     {
       
   374     TRACER("CGlxCacheManager::FindCacheForceCreateL");
       
   375     
       
   376     CGlxCache* cache = NULL;
       
   377 
       
   378     // Look for existing cache
       
   379     TInt index = iCaches.FindInOrder(aIdSpaceId, (&CacheOrderByKey));
       
   380     if ( KErrNotFound == index )
       
   381         {
       
   382         // Not found: create one
       
   383     	TLinearOrder<CGlxCache> orderer (&CacheOrderById);
       
   384         cache = new (ELeave) CGlxCache(aIdSpaceId, this);
       
   385 
       
   386         CleanupStack::PushL(cache);
       
   387         iCaches.InsertInOrderL(cache, orderer);
       
   388         CleanupStack::Pop(cache);
       
   389         }
       
   390     else
       
   391         {
       
   392         cache = iCaches[index];
       
   393         }
       
   394 
       
   395     return cache;
       
   396     }
       
   397     
       
   398 // -----------------------------------------------------------------------------
       
   399 // Media
       
   400 // -----------------------------------------------------------------------------
       
   401 //
       
   402 CGlxMedia* CGlxCacheManager::Media( const TGlxIdSpaceId& aIdSpaceId, 
       
   403         const TGlxMediaId& aMediaId ) const
       
   404     {
       
   405     TRACER("CGlxCacheManager::Media");
       
   406     
       
   407     // Look for the correct subcache
       
   408     TInt index = iCaches.FindInOrder( aIdSpaceId, &CacheOrderByKey );
       
   409     
       
   410     if ( KErrNotFound == index )
       
   411         {
       
   412         // No caches exist with this space id
       
   413         return NULL;
       
   414         }
       
   415     else
       
   416         {
       
   417         return iCaches[index]->Media( aMediaId );
       
   418         }
       
   419     }
       
   420     
       
   421 // -----------------------------------------------------------------------------
       
   422 // MediaForceCreateL
       
   423 // -----------------------------------------------------------------------------
       
   424 //
       
   425 CGlxMedia* CGlxCacheManager::MediaForceCreateL(const TGlxIdSpaceId& aIdSpaceId, const TGlxMediaId& aMediaId)
       
   426     {
       
   427     TRACER("CGlxCacheManager::MediaForceCreateL");
       
   428     
       
   429     CGlxCache* cache = FindCacheForceCreateL(aIdSpaceId);
       
   430     return cache->FindItemForceCreateL(aMediaId);
       
   431     }
       
   432     
       
   433 // -----------------------------------------------------------------------------
       
   434 // AddObserverL
       
   435 // -----------------------------------------------------------------------------
       
   436 //
       
   437 void CGlxCacheManager::AddObserverL(MGlxCacheObserver* aObserver)
       
   438     {
       
   439     TRACER("CGlxCacheManager::AddObserverL");
       
   440     
       
   441     if ( aObserver )
       
   442         {
       
   443         if ( KErrNotFound == iObserverList.Find( aObserver ))
       
   444             {
       
   445             iObserverList.AppendL(aObserver);
       
   446             }
       
   447         }
       
   448     }
       
   449     
       
   450 // -----------------------------------------------------------------------------
       
   451 // RemoveObserver
       
   452 // -----------------------------------------------------------------------------
       
   453 //
       
   454 void CGlxCacheManager::RemoveObserver(MGlxCacheObserver* aObserver)
       
   455     {
       
   456     TRACER("CGlxCacheManager::RemoveObserver");
       
   457     
       
   458     if ( aObserver )
       
   459         {
       
   460         TInt index = iObserverList.Find( aObserver );
       
   461         if ( KErrNotFound != index )
       
   462             {
       
   463             iObserverList.Remove(index);
       
   464             }
       
   465         }
       
   466     }
       
   467 
       
   468 // ---------------------------------------------------------------------------
       
   469 // Refresh
       
   470 // ---------------------------------------------------------------------------
       
   471 //
       
   472 void CGlxCacheManager::RefreshL()
       
   473     {
       
   474     TRACER("CGlxCacheManager::Refresh");
       
   475     
       
   476     if ( !iRequestOwner )
       
   477         {
       
   478         // Currently idle, so trigger timer immediately to begin refresh
       
   479         iTempErrorTimer->Cancel();
       
   480         iTempErrorTimer->Start( 0, 0,
       
   481                             TCallBack( TempErrorTimerCallbackL, this ) );
       
   482         
       
   483         HandleGarbageCollectionL(ETrue);  // Clean-up is needed here; Considering Current Memory Condition
       
   484         }
       
   485     }
       
   486 
       
   487 // -----------------------------------------------------------------------------
       
   488 // MaintainCache
       
   489 // -----------------------------------------------------------------------------
       
   490 //
       
   491 TInt CGlxCacheManager::MaintainCacheL(TAny* aPtr)
       
   492     {
       
   493     TRACER("CGlxCacheManager::MaintainCache");
       
   494     
       
   495     CGlxCacheManager* self
       
   496                     = reinterpret_cast<CGlxCacheManager*>( aPtr );
       
   497     self->MaintainCacheL();
       
   498     
       
   499     // Clean-up is needed here; Considering Current Memory Condition
       
   500     // For Every HandleWindowChangedL; We Should not do Clean-up 
       
   501     self->HandleGarbageCollectionL(ETrue);  
       
   502     return 0;
       
   503     }
       
   504     
       
   505 // -----------------------------------------------------------------------------
       
   506 // MaintainCacheL
       
   507 // -----------------------------------------------------------------------------
       
   508 //
       
   509 void CGlxCacheManager::MaintainCacheL() 
       
   510     {
       
   511     TRACER("CGlxCacheManager::MaintainCacheL");
       
   512     
       
   513 	// Handle lists in priority order: all data for the highest priority list 
       
   514 	// is retrieved before the data for a lower priority list. NOTE: This
       
   515 	// may need to be changed, since it might not always lead to the best
       
   516 	// user experienced. (It may be sensible to retrieve item properties
       
   517 	// for a lower priority list before all thumbnails for a higher priority 
       
   518 	// list, but this probably depends on the speed of the data sources.
       
   519 	// It might be wise to decouple the contexts from the media lists
       
   520 
       
   521     if (!iRequestOwner)
       
   522         {
       
   523         iTempError = EFalse;
       
   524         iTempErrorTimer->Cancel();
       
   525 
       
   526     	RPointerArray<CGlxMediaList>& mediaLists = CGlxMediaList::MediaListsL();
       
   527      	iRequestedItemIds.Reset();
       
   528      	iRequestedAttrs.Reset();
       
   529     	iRequestedItemIndexes.Reset();
       
   530     	
       
   531     	TInt listCount = mediaLists.Count();
       
   532 
       
   533     	// Request attributes in the fetch contexts
       
   534         for (TInt listIndex = 0; listIndex < listCount && !iRequestOwner; listIndex++)      
       
   535             {
       
   536             CGlxMediaList* list = mediaLists[listIndex];
       
   537 
       
   538     		CMPXAttributeSpecs* attrSpecs = NULL;
       
   539 
       
   540     		list->AttributeRequestL(iRequestedItemIndexes, iRequestedItemIds, iRequestedAttrs, attrSpecs );
       
   541     		CleanupStack::PushL(attrSpecs);
       
   542 
       
   543             TInt itemIdsCount = iRequestedItemIds.Count();
       
   544             if (itemIdsCount > 0)
       
   545                 {
       
   546                 if (attrSpecs)
       
   547                     {
       
   548                     GLX_DEBUG2("CGlxCacheManager::MaintainCacheL() attrSpecs->Count() %d", attrSpecs->Count());
       
   549                     }
       
   550                 
       
   551                 TGlxMediaId itemId = iRequestedItemIds[0];
       
   552 
       
   553                 CMPXCollectionPath* path = RequestAsPathLC( *list );
       
   554 
       
   555                 // Add request for id, if does not exist already. Id is used to 
       
   556                 // identify which media object the attribute belongs to when
       
   557                 // it is returned
       
   558                 TIdentityRelation<TMPXAttribute> match (&TMPXAttribute::Match);
       
   559                 if (iRequestedAttrs.Find(KMPXMediaGeneralId, match) == KErrNotFound) 
       
   560                     {
       
   561                     iRequestedAttrs.AppendL(KMPXMediaGeneralId);
       
   562                     }
       
   563 
       
   564                 // Create the empty bitmap, if the request is for a bitmap
       
   565                 TIdentityRelation<TMPXAttribute> matchContent(&TMPXAttribute::MatchContentId);
       
   566                 TMPXAttribute tnAttr(KGlxMediaIdThumbnail, 0);
       
   567                 if (iRequestedAttrs.Find(tnAttr, matchContent) != KErrNotFound) 
       
   568                     {
       
   569 #ifdef USE_S60_TNM
       
   570 					if (iRequestedItemIndexes.Count())
       
   571 						{
       
   572                         // Cancel Clean-up is needed here;
       
   573                         HandleGarbageCollectionL(EFalse);                           
       
   574 						
       
   575 			            TSize tnSize;
       
   576 						const TMPXAttributeData sizeAttrib = { KGlxMediaIdThumbnail , KGlxAttribSpecThumbnailSize };
       
   577       					if (attrSpecs && attrSpecs->IsSupported(sizeAttrib))
       
   578                         	{
       
   579 				    		tnSize = attrSpecs->ValueTObjectL<TSize>(sizeAttrib);
       
   580                         	}
       
   581 
       
   582 						const TGlxMedia& item = list->Item( iRequestedItemIndexes[0] );
       
   583       					TBool priority = ETrue;
       
   584       					const TMPXAttributeData priorityAttrib = { KGlxMediaIdThumbnail , KGlxAttribSpecThumbnailQualityOverSpeed };
       
   585       					if (attrSpecs && attrSpecs->IsSupported(priorityAttrib))
       
   586       					    {
       
   587       					    priority = attrSpecs->ValueTObjectL<TBool>(priorityAttrib);
       
   588       					    }
       
   589       					
       
   590 						TGlxIdSpaceId spaceId = list->IdSpaceId(iRequestedItemIndexes[0]);	
       
   591 #ifdef MEDIA_ID_BASED_TN_FETCH_ENABLED
       
   592 	               	 	GLX_DEBUG2("CGlxCacheManager::MaintainCacheL() requesting TN attribute (Medialist) itemId %d", itemId.Value());
       
   593 						if (item.Uri().Find(KFileIdentifier) != KErrNotFound ||
       
   594 						    item.Uri().Length() == 0 && itemId.Value())
       
   595 #else
       
   596 	               	 	GLX_DEBUG1("CGlxCacheManager::MaintainCacheL() requesting TN attribute (Medialist) Uri");
       
   597 						if (item.Uri().Find(KFileIdentifier) != KErrNotFound)
       
   598 #endif
       
   599 							{
       
   600 #ifdef _DEBUG
       
   601 							iStartTime.HomeTime(); // Get home time
       
   602 #endif							
       
   603 						    if (tnSize.iWidth < KMaxGridThumbnailWidth)
       
   604 						    	{
       
   605 						    	iTnEngine->SetFlagsL(CThumbnailManager::ECropToAspectRatio);
       
   606 							    iTnEngine->SetThumbnailSizeL(EGridThumbnailSize);
       
   607 							    GLX_DEBUG1("MaintainCacheL() - Fetch TN attrib - EGridThumbnailSize");
       
   608 						    	}
       
   609 						    else
       
   610 							    {
       
   611 							    iTnEngine->SetFlagsL(CThumbnailManager::EDefaultFlags);
       
   612 							    iTnEngine->SetThumbnailSizeL(EFullScreenThumbnailSize);
       
   613                                 GLX_DEBUG1("MaintainCacheL() - Fetch TN attrib - EFullScreenThumbnailSize");							    
       
   614 							    }
       
   615 						    
       
   616 						    if (priority)
       
   617 						        {
       
   618 						        iTnEngine->SetQualityPreferenceL(CThumbnailManager::EOptimizeForQuality);
       
   619                                 GLX_DEBUG1("MaintainCacheL() - Fetch TN attrib - EOptimizeForQuality");                                
       
   620 						        }
       
   621 						    else
       
   622 						        {
       
   623 						        //iTnEngine->SetQualityPreferenceL(CThumbnailManager::EOptimizeForQualityWithPreview);
       
   624 						        iTnEngine->SetQualityPreferenceL(CThumbnailManager::EOptimizeForPerformance);
       
   625                                 GLX_DEBUG1("MaintainCacheL() - Fetch TN attrib - EOptimizeForQualityWithPreview");                                
       
   626                                 }
       
   627                             
       
   628                             if (list->Collection().UidL().iUid == KGlxCollectionPluginImageViewerImplementationUid)
       
   629                                 {
       
   630                                 GLX_DEBUG1("void CGlxCacheManager::MaintainCacheL:Imageviewer TN");
       
   631                                 _LIT( KPrivateFolder, "\\Private\\" );    // Platsec private folder  
       
   632                                 TParsePtrC parse( item.Uri() );
       
   633                                 if( parse.PathPresent() &&
       
   634                                     parse.Path().Length() > KPrivateFolder().Length() &&
       
   635                                     parse.Path().Left( KPrivateFolder().Length() ).CompareF( KPrivateFolder ) == 0 )
       
   636                                     {
       
   637                                     CGlxImageViewerManager *imageVwrMgr = CGlxImageViewerManager::InstanceL();
       
   638 									CleanupClosePushL(*imageVwrMgr);
       
   639                                     GLX_DEBUG1("KGlxCollectionPluginImageViewerImplementationUid - Fetch (Private) TN!");
       
   640                                     if ( &(imageVwrMgr->ImageFileHandle()) != NULL )
       
   641                                         {
       
   642                                         //CThumbnailObjectSource* source = CThumbnailObjectSource::NewLC(imageVwrMgr->ImageFileHandle());
       
   643                                         CThumbnailObjectSource* source = CThumbnailObjectSource::NewLC(imageVwrMgr->ImageUri()->Des(), 0);
       
   644                                         iThumbnailRequestIds.AppendL(TLoadingTN(iTnEngine->GetThumbnailL(*source), spaceId, tnSize, itemId));
       
   645                                         CleanupStack::PopAndDestroy(source);
       
   646                                         }
       
   647                                     CleanupStack::PopAndDestroy(imageVwrMgr);	
       
   648                                     }
       
   649                                 else
       
   650                                     {
       
   651                                     GLX_DEBUG1("void CGlxCacheManager::MaintainCacheL:Imageviewer In else");
       
   652                                     GLX_DEBUG2("CGlxCacheManager::MaintainCacheL: uri %S", &item.Uri());	
       
   653                                     CThumbnailObjectSource* source = CThumbnailObjectSource::NewLC(item.Uri(), 0);
       
   654                                     iThumbnailRequestIds.AppendL(TLoadingTN(iTnEngine->GetThumbnailL(*source), spaceId, tnSize, itemId));
       
   655                                     CleanupStack::PopAndDestroy(source);
       
   656                                     }
       
   657                                 }
       
   658                             else
       
   659                                 {
       
   660 #ifdef MEDIA_ID_BASED_TN_FETCH_ENABLED
       
   661 						    iThumbnailRequestIds.AppendL(TLoadingTN(iTnEngine->GetThumbnailL(itemId.Value()), spaceId, tnSize, itemId));
       
   662 #else
       
   663 						    CThumbnailObjectSource* source = CThumbnailObjectSource::NewLC(item.Uri(), 0);
       
   664                                 iThumbnailRequestIds.AppendL(TLoadingTN(
       
   665                                         iTnEngine->GetThumbnailL(*source), 
       
   666                                         spaceId, tnSize, itemId));
       
   667 						    CleanupStack::PopAndDestroy(source);
       
   668 #endif
       
   669                                 }
       
   670 		                    iThumbnailId = itemId;
       
   671 							}
       
   672 						else
       
   673 							{
       
   674 		                    delete iTempThumbnail;
       
   675 		                    iTempThumbnail = NULL;
       
   676 		                    iTempThumbnail = new (ELeave) CFbsBitmap;
       
   677 		                    User::LeaveIfError(iTempThumbnail->Create(TSize(), KGlxThumbnailDisplayMode));
       
   678 		                    iThumbnailId = itemId;
       
   679 	               		 	GLX_DEBUG2("CGlxCacheManager::MaintainCacheL() requesting TN (DataSourceMde) attribute itemId %d", itemId.Value());
       
   680 
       
   681 		                    // Set bitmap handle in attribute spec
       
   682 		                    if (attrSpecs)
       
   683 		                        {
       
   684 		                        TMPXAttribute thHandleAttrSpec(KGlxMediaIdThumbnail, KGlxAttribSpecThumbnailBitmapHandle);
       
   685 		                        attrSpecs->SetTObjectValueL<TInt>(thHandleAttrSpec, iTempThumbnail->Handle());
       
   686 		                        }
       
   687 
       
   688 		                    // Cancel Clean-up is needed here;
       
   689 		                    // This is Going to Highly Used Call
       
   690 		                    // Can Think about an Ulternative.
       
   691 		                    HandleGarbageCollectionL(EFalse);
       
   692 
       
   693 			                GLX_DEBUG3("MGallery - CGlxCacheManager::MaintainCacheL() requesting attribute for list %x and item %d", list, itemId.Value());
       
   694 
       
   695 			                // Use list's isolated collection
       
   696 			                MMPXCollection& collection = list->Collection();
       
   697 
       
   698 			    			// Issue the request
       
   699 			    			collection.MediaL(*path, iRequestedAttrs.Array(), attrSpecs);
       
   700 							}
       
   701 						}
       
   702                     }
       
   703                 else
       
   704                 	{
       
   705 	                GLX_DEBUG3("MGallery - CGlxCacheManager::MaintainCacheL() requesting attribute for list %x and item %d", list, itemId.Value());
       
   706 
       
   707 	                // Use list's isolated collection
       
   708 	                MMPXCollection& collection = list->Collection();
       
   709                     if (collection.UidL().iUid == KGlxCollectionPluginImageViewerImplementationUid)
       
   710                         {
       
   711                         CGlxImageViewerManager *imageVwrMgr = CGlxImageViewerManager::InstanceL();
       
   712 						CleanupClosePushL(*imageVwrMgr);
       
   713 #ifdef _DEBUG
       
   714                         TInt mediaCnt = list->Count();
       
   715 #endif                        
       
   716                         TInt errInImage = KErrNone;
       
   717  
       
   718                         
       
   719                         GLX_DEBUG3("Image Viewer Collection - Attrib population! mediaCnt=%d, Media Id=%d",
       
   720                                 mediaCnt, itemId.Value());
       
   721                         
       
   722                         delete iMPXMedia;
       
   723                         iMPXMedia = NULL;
       
   724 
       
   725                         TFileName fileName(KNullDesC);
       
   726                         //retrieve the filename as per the caller app.
       
   727                         if(imageVwrMgr->IsPrivate())
       
   728                             {
       
   729                             const TGlxMedia& item = list->Item( iRequestedItemIndexes[0] );
       
   730                             // If there is an URI available, then the request is due to EPathChanged message 
       
   731                             // due to a file save from Image Viewer, and attribs needs to be re-populated. 
       
   732                             // So, use the same URI; Oherwise getting fullname from handle might result in a crash.
       
   733                             if (item.Uri().Length())
       
   734                                 {
       
   735                                 fileName.Append(item.Uri());
       
   736                                 }
       
   737                             else
       
   738                                 {
       
   739                                 // private path
       
   740                                 RFile64& imageHandle = imageVwrMgr->ImageFileHandle();
       
   741                                 if ( &imageHandle != NULL )
       
   742                                     {
       
   743                                     imageHandle.FullName(fileName);
       
   744                                     }
       
   745                                 else
       
   746                                     {
       
   747                                     errInImage = KErrArgument;
       
   748                                     }   
       
   749                                 }
       
   750                             }
       
   751                         else
       
   752                             {
       
   753                             // user data path
       
   754                             if(  imageVwrMgr->ImageUri() != NULL  )
       
   755                                 {
       
   756                                 fileName.Append(imageVwrMgr->ImageUri()->Des());
       
   757                                 RFs fs;
       
   758                                 CleanupClosePushL(fs);
       
   759                                 TInt err = fs.Connect();   
       
   760                                 errInImage = KErrArgument;
       
   761                                 if(err == KErrNone)
       
   762                                     {
       
   763                                     if (fs.IsValidName(fileName))
       
   764                                         {
       
   765                                         errInImage = KErrNone;
       
   766                                         }
       
   767                                     }
       
   768                                 CleanupStack::PopAndDestroy(&fs);
       
   769                                 }
       
   770                             else
       
   771                                 {
       
   772                                 errInImage = KErrArgument;
       
   773                                 }
       
   774                             }
       
   775 
       
   776                         iMPXMedia = CMPXMedia::NewL();
       
   777 
       
   778                         if (errInImage != KErrNone)
       
   779                             {
       
   780                             HandleGarbageCollectionL(EFalse);
       
   781                             CleanupStack::PopAndDestroy(path);
       
   782                             iRequestOwner = list;
       
   783                             CleanupStack::PopAndDestroy(attrSpecs); 
       
   784                             TGlxIdSpaceId spaceId = list->IdSpaceId(iRequestedItemIndexes[0]);
       
   785                             HandleCollectionMediaL(spaceId, *iMPXMedia, errInImage);
       
   786                             CleanupStack::PopAndDestroy(imageVwrMgr);
       
   787                             return;
       
   788                             }
       
   789 
       
   790                         if(!iReader)
       
   791                             {
       
   792                             TRAP(errInImage, iReader = CGlxImageReader::NewL());
       
   793                             }
       
   794 
       
   795                         for ( TInt i = 0; i < iRequestedAttrs.Count(); i++ )
       
   796                             {
       
   797                             if ( iRequestedAttrs[i] == KMPXMediaGeneralId )
       
   798                                 {
       
   799                                 iMPXMedia->SetTObjectValueL<TMPXItemId>(KMPXMediaGeneralId, 
       
   800                                         (TMPXItemId)itemId.Value());
       
   801                                 }
       
   802                             else if ( iRequestedAttrs[i] == KMPXMediaGeneralType )
       
   803                                 {
       
   804                                 iMPXMedia->SetTObjectValueL(KMPXMediaGeneralType, EMPXItem);
       
   805                                 }
       
   806                             else if ( iRequestedAttrs[i] == KMPXMediaGeneralCategory )
       
   807                                 {
       
   808                                 iMPXMedia->SetTObjectValueL(KMPXMediaGeneralCategory, EMPXImage);
       
   809                                 }                           
       
   810                             else if ( iRequestedAttrs[i] == KMPXMediaGeneralUri )
       
   811                                 {
       
   812                                 iMPXMedia->SetTextValueL(KMPXMediaGeneralUri, fileName);
       
   813                                 }
       
   814                             else if ( iRequestedAttrs[i] == KMPXMediaGeneralTitle )
       
   815                                 {
       
   816                                 TParsePtrC parser(fileName);
       
   817                                 iMPXMedia->SetTextValueL(KMPXMediaGeneralTitle, parser.Name());
       
   818                                 }
       
   819                             else if ( iRequestedAttrs[i] == KMPXMediaGeneralDate )
       
   820                                 {
       
   821                                 TTime time;
       
   822                                 time.HomeTime();
       
   823                                 iMPXMedia->SetTObjectValueL(KMPXMediaGeneralDate, time.Int64());
       
   824                                 }
       
   825                             else if ( iRequestedAttrs[i] == KGlxMediaGeneralLastModifiedDate )
       
   826                                 {
       
   827                                 if(errInImage == KErrNone)
       
   828                                     {
       
   829                                     RFs fs;
       
   830                                     CleanupClosePushL(fs);
       
   831                                     TInt err = fs.Connect();   
       
   832                                     if(err == KErrNone)
       
   833                                         {                                    
       
   834                                         TEntry entry;   
       
   835                                         fs.Entry(fileName,entry);    
       
   836                                         TTime time = entry.iModified;   
       
   837                                         iMPXMedia->SetTObjectValueL(
       
   838                                                 KGlxMediaGeneralLastModifiedDate, 
       
   839                                                 time.Int64());
       
   840                                         }
       
   841                                     else
       
   842                                         {
       
   843                                         TTime time;
       
   844                                         time.HomeTime();
       
   845                                         iMPXMedia->SetTObjectValueL(
       
   846                                                 KGlxMediaGeneralLastModifiedDate, 
       
   847                                                 time.Int64());
       
   848                                         }
       
   849                                     CleanupStack::PopAndDestroy(&fs);                                    
       
   850                                     }
       
   851                                 else
       
   852                                     {
       
   853                                     TTime time;
       
   854                                     time.HomeTime();
       
   855                                     iMPXMedia->SetTObjectValueL(KGlxMediaGeneralLastModifiedDate, time.Int64());
       
   856                                     }
       
   857                                 }
       
   858                             else if ( iRequestedAttrs[i] == KMPXMediaGeneralSize )
       
   859                                 {
       
   860                                 if(errInImage == KErrNone)
       
   861                                     {
       
   862                                     if(imageVwrMgr->IsPrivate())
       
   863                                         {
       
   864                                         TInt64 sz = 0;
       
   865                                         TInt err = KErrNotFound;                                      
       
   866                                         RFile64& imageHandle = imageVwrMgr->ImageFileHandle();
       
   867                                         if ( imageHandle.SubSessionHandle() != KNullHandle )
       
   868                                             {
       
   869                                             err = imageHandle.Size(sz);
       
   870                                             }
       
   871                                         if(err == KErrNone)
       
   872                                             {
       
   873                                             iMPXMedia->SetTObjectValueL(KMPXMediaGeneralSize, sz);
       
   874                                             }
       
   875                                         else
       
   876                                             {
       
   877                                             iMPXMedia->SetTObjectValueL(KMPXMediaGeneralSize, 0);                                            
       
   878                                             }
       
   879                                         }
       
   880                                     else
       
   881                                         {
       
   882                                         RFs fs;
       
   883                                         CleanupClosePushL(fs);
       
   884                                         TInt err = fs.Connect();   
       
   885                                         if(err == KErrNone)
       
   886                                             {
       
   887                                             TEntry entry;   
       
   888                                             fs.Entry(fileName,entry);    
       
   889                                             TInt sz = (TUint)entry.iSize;                                      
       
   890                                             iMPXMedia->SetTObjectValueL(KMPXMediaGeneralSize, sz);
       
   891                                             }
       
   892                                         else
       
   893                                             {
       
   894                                             iMPXMedia->SetTObjectValueL(KMPXMediaGeneralSize, 0);
       
   895                                             }
       
   896                                         CleanupStack::PopAndDestroy(&fs);
       
   897                                         }
       
   898                                     }
       
   899                                 // If any error while image is being decoded by image decorder, Need to set
       
   900                                 // default vaule for that image. Typical case is corrupted image.
       
   901                                 else
       
   902                                     {
       
   903                                     iMPXMedia->SetTObjectValueL(KMPXMediaGeneralSize, 0);
       
   904                                     }
       
   905                                 }
       
   906                             else if ( iRequestedAttrs[i] == KMPXMediaGeneralDrive )
       
   907                                 {
       
   908                                 TParsePtrC parser(fileName);
       
   909                                 iMPXMedia->SetTextValueL(KMPXMediaGeneralDrive, parser.Drive());
       
   910                                 }
       
   911                             else if ( iRequestedAttrs[i] == KMPXMediaGeneralMimeType )
       
   912                                 {
       
   913                                 if(errInImage == KErrNone)
       
   914                                     {
       
   915                                     TDataType dataType;
       
   916                                     GetMimeTypeL(fileName, dataType);
       
   917                                     iMPXMedia->SetTextValueL(KMPXMediaGeneralMimeType, dataType.Des());
       
   918                                     }
       
   919                                 else
       
   920                                     {
       
   921                                     iMPXMedia->SetTextValueL(KMPXMediaGeneralMimeType, KDefaultType);
       
   922                                     }                                
       
   923                                 }
       
   924                             else if ( iRequestedAttrs[i] == KMPXMediaGeneralDuration )
       
   925                                 {
       
   926                                 iMPXMedia->SetTObjectValueL(KMPXMediaGeneralDuration, 0);
       
   927                                 }
       
   928                             else if ( iRequestedAttrs[i] == KGlxMediaGeneralSystemItem)
       
   929                                 {
       
   930                                 iMPXMedia->SetTObjectValueL(KGlxMediaGeneralSystemItem, EFalse);
       
   931                                 }
       
   932                             else if ( iRequestedAttrs[i] == KGlxMediaGeneralDimensions )
       
   933                                 {
       
   934                                 TSize dimensions = TSize();
       
   935                                 if(errInImage == KErrNone)
       
   936                                     {
       
   937                                     //need to fetch the original file dimensions
       
   938                                         dimensions = iReader->GetDimensions();
       
   939                                     iMPXMedia->SetTObjectValueL(KGlxMediaGeneralDimensions, dimensions);
       
   940                                     }
       
   941                                 else
       
   942                                     {
       
   943                                     iMPXMedia->SetTObjectValueL(KGlxMediaGeneralDimensions, dimensions);
       
   944                                     }
       
   945                                 }
       
   946                             else if ( iRequestedAttrs[i] == KGlxMediaGeneralFramecount )
       
   947                                 {
       
   948                                 TInt fcount = 1;
       
   949                                 if(errInImage == KErrNone)
       
   950                                     {
       
   951                                     fcount = iReader->GetFrameCount();
       
   952                                     }
       
   953                                 GLX_DEBUG2("Imageviewer Collection framecount(%d)", fcount);
       
   954                                 iMPXMedia->SetTObjectValueL(KGlxMediaGeneralFramecount, fcount);
       
   955                                 }
       
   956                             else if ( iRequestedAttrs[i] == KMPXMediaGeneralComment )
       
   957                                 {
       
   958                                 iMPXMedia->SetTextValueL(KMPXMediaGeneralComment, KNullDesC); 
       
   959                                 }
       
   960                             else if (iRequestedAttrs[i] == KMPXMediaDrmProtected )
       
   961                                 {
       
   962                                 TBool protection = EFalse;
       
   963                                 if(errInImage == KErrNone)
       
   964                                     {
       
   965                                     protection = iReader->GetDRMRightsL
       
   966                                     (ContentAccess::EIsProtected);
       
   967                                     }
       
   968                                 iMPXMedia->SetTObjectValueL(KMPXMediaDrmProtected, protection);
       
   969                                 }
       
   970                             else if ( iRequestedAttrs[i] == KGlxMediaGeneralDRMRightsValid )
       
   971                                 {
       
   972                                 TInt rightsValid = EGlxDrmRightsValidityUnknown;
       
   973                                 if(errInImage == KErrNone)
       
   974                                     {
       
   975                                     TBool canView = iReader->GetDRMRightsL(ContentAccess::ECanView);
       
   976                                     rightsValid = canView ? 
       
   977                                         EGlxDrmRightsValid : EGlxDrmRightsInvalid;
       
   978                                     }
       
   979                                 iMPXMedia->SetTObjectValueL(KGlxMediaGeneralDRMRightsValid,
       
   980                                                              rightsValid); 
       
   981                                 }
       
   982                             else if ( iRequestedAttrs[i] == KMPXMediaGeneralCount )
       
   983                                 {
       
   984                                 iMPXMedia->SetTObjectValueL(KMPXMediaGeneralCount, 1);
       
   985                                 }
       
   986                             else if ( iRequestedAttrs[i] == KMPXMediaColDetailSpaceId )
       
   987                                 {
       
   988                                 TGlxIdSpaceId spaceId = list->IdSpaceId(iRequestedItemIndexes[0]);
       
   989                                 iMPXMedia->SetTObjectValueL(KMPXMediaColDetailSpaceId,
       
   990                                 		 spaceId.Value());
       
   991                                 }
       
   992                             else if ( iRequestedAttrs[i] == KGlxMediaGeneralSlideshowableContent )
       
   993                                 {
       
   994                                 iMPXMedia->SetTObjectValueL(KGlxMediaGeneralSlideshowableContent, -1);
       
   995                                 }
       
   996                             else if ( iRequestedAttrs[i] == KGlxMediaGeneralLocation)
       
   997                                 {
       
   998                                 // Set the attribute to a TCoordinate initialised to NaN. 
       
   999                                 iMPXMedia->SetTObjectValueL(KGlxMediaGeneralLocation, TCoordinate());
       
  1000                                 }
       
  1001                             else
       
  1002                                 {
       
  1003                                 User::Leave(KErrNotSupported);
       
  1004                                 }
       
  1005                             }
       
  1006                         
       
  1007                         HandleGarbageCollectionL(EFalse);
       
  1008                         CleanupStack::PopAndDestroy(imageVwrMgr);
       
  1009                         CleanupStack::PopAndDestroy(path);
       
  1010                         iRequestOwner = list;
       
  1011                         CleanupStack::PopAndDestroy(attrSpecs); 
       
  1012                         TGlxIdSpaceId spaceId = list->IdSpaceId(iRequestedItemIndexes[0]);
       
  1013                         HandleCollectionMediaL(spaceId, *iMPXMedia, KErrNone);
       
  1014                         return;
       
  1015                         }
       
  1016                     else
       
  1017                         {
       
  1018                     // Issue the request
       
  1019                     collection.MediaL(*path, iRequestedAttrs.Array(), attrSpecs);
       
  1020                         }
       
  1021                     }
       
  1022 #else // USE_S60_TNM
       
  1023                     delete iTempThumbnail;
       
  1024                     iTempThumbnail = NULL;
       
  1025                     iTempThumbnail = new (ELeave) CFbsBitmap;
       
  1026                     User::LeaveIfError(iTempThumbnail->Create(TSize(), KGlxThumbnailDisplayMode));
       
  1027                     iThumbnailId = itemId;
       
  1028 
       
  1029                     // Set bitmap handle in attribute spec
       
  1030                     if (attrSpecs)
       
  1031                         {
       
  1032                         TMPXAttribute thHandleAttrSpec(KGlxMediaIdThumbnail, KGlxAttribSpecThumbnailBitmapHandle);
       
  1033                         attrSpecs->SetTObjectValueL<TInt>(thHandleAttrSpec, iTempThumbnail->Handle());
       
  1034                         }
       
  1035                     // Cancel Clean-up is needed here;
       
  1036                     // This is Going to Highly Used Call
       
  1037                     // Can Think about an Ulternative.
       
  1038                     HandleGarbageCollectionL(EFalse);
       
  1039                     }
       
  1040 
       
  1041                 GLX_DEBUG3("MGallery - CGlxCacheManager::MaintainCacheL() requesting attribute for list %x and item %d", list, itemId.Value());
       
  1042 
       
  1043                 // Use list's isolated collection
       
  1044                 MMPXCollection& collection = list->Collection();
       
  1045 
       
  1046     			// Issue the request
       
  1047     			collection.MediaL(*path, iRequestedAttrs.Array(), attrSpecs);
       
  1048 #endif
       
  1049     			CleanupStack::PopAndDestroy(path);
       
  1050     			
       
  1051     			iRequestOwner = list;
       
  1052     			}		
       
  1053     			
       
  1054     		CleanupStack::PopAndDestroy(attrSpecs);	
       
  1055     		}
       
  1056     		
       
  1057         if ( !iRequestOwner )
       
  1058             {
       
  1059             if ( iTempError )
       
  1060                 {
       
  1061                 // Reawaken in a while to check again
       
  1062                 StartTempErrorTimer();
       
  1063                 }
       
  1064             }
       
  1065     	}
       
  1066     }
       
  1067 
       
  1068 // -----------------------------------------------------------------------------
       
  1069 // BroadcastAttributesAvailableL
       
  1070 // -----------------------------------------------------------------------------
       
  1071 //
       
  1072 void CGlxCacheManager::BroadcastAttributesAvailableL(const TGlxIdSpaceId& aIdSpaceId, 
       
  1073                     const TGlxMediaId& aMediaId, 
       
  1074                     const RArray<TMPXAttribute>& aAttributes, 
       
  1075                     const CGlxMedia* aMedia)
       
  1076    {
       
  1077    TRACER("CGlxCacheManager::BroadcastAttributesAvailableL");
       
  1078    
       
  1079     TInt count = iObserverList.Count();
       
  1080     TInt i;
       
  1081     for ( i = 0; i < count; i++ )
       
  1082         {
       
  1083         iObserverList[i]->HandleAttributesAvailableL(aIdSpaceId, aMediaId, aAttributes, aMedia);
       
  1084         }
       
  1085    }
       
  1086 
       
  1087 /**
       
  1088  * Cleanup the media of the given media id: broadcast this to all observers
       
  1089  * @param aMediaId The media id of the item
       
  1090  */ 
       
  1091 void CGlxCacheManager::CleanupMedia(const TGlxMediaId& aMediaId)
       
  1092 	{
       
  1093 	TRACER("CGlxCacheManager::CleanupMedia");
       
  1094     TInt count = iObserverList.Count();
       
  1095     GLX_DEBUG2("CGlxCacheManager::CleanupMedia -  aMediaId = %d", aMediaId.Value());
       
  1096     TInt i;
       
  1097     for ( i = 0; i < count; i++ )
       
  1098         {
       
  1099         iObserverList[i]->CleanupMedia(aMediaId);
       
  1100         }
       
  1101    }
       
  1102 
       
  1103 // -----------------------------------------------------------------------------
       
  1104 // Handles modification of item in a cache
       
  1105 // -----------------------------------------------------------------------------
       
  1106 void CGlxCacheManager::HandleItemModified(const TGlxIdSpaceId& aIdSpaceId, const TGlxMediaId& aMediaId, const RArray<TMPXAttribute>& aAttributes)
       
  1107 	{
       
  1108 	TRACER("CGlxCacheManager::HandleItemModified");
       
  1109 	
       
  1110 	// Look for the correct subcache
       
  1111 	TInt index = iCaches.FindInOrder(aIdSpaceId, (&CacheOrderByKey));
       
  1112 	if (index != KErrNotFound)
       
  1113 		{
       
  1114 		iCaches[index]->HandleItemModified(aMediaId, aAttributes);
       
  1115 		}
       
  1116 	}
       
  1117 
       
  1118 // -----------------------------------------------------------------------------
       
  1119 // CacheOrderById
       
  1120 // -----------------------------------------------------------------------------
       
  1121 //
       
  1122 TInt CGlxCacheManager::CacheOrderById(const CGlxCache& aItem1, const CGlxCache& aItem2) 
       
  1123 	{
       
  1124 	TRACER("CGlxCacheManager::CacheOrderById");
       
  1125 	
       
  1126 	// Cannot do aItem1.IdSpaceId() - aItem2.IdSpaceId(), since IdSpaceId().Value() returns an unsigned value
       
  1127 	TGlxIdSpaceId id1 = aItem1.IdSpaceId();
       
  1128 	TGlxIdSpaceId id2 = aItem2.IdSpaceId();
       
  1129 	if (id1 < id2) 
       
  1130 		{
       
  1131 		return -1;
       
  1132 		}
       
  1133 		
       
  1134 	if (id1 > id2) 
       
  1135 		{
       
  1136 		return 1;
       
  1137 		}
       
  1138 
       
  1139 	return 0;
       
  1140 	}
       
  1141 
       
  1142 // -----------------------------------------------------------------------------
       
  1143 // CacheOrderByKey
       
  1144 // -----------------------------------------------------------------------------
       
  1145 //
       
  1146 TInt CGlxCacheManager::CacheOrderByKey(const TGlxIdSpaceId* aIdSpaceId, const CGlxCache& aItem2) 
       
  1147 	{
       
  1148 	TRACER("CGlxCacheManager::CacheOrderByKey");
       
  1149 	
       
  1150 	TGlxIdSpaceId id2 = aItem2.IdSpaceId();
       
  1151 	if (*aIdSpaceId < id2) 
       
  1152 		{
       
  1153 		return -1;
       
  1154 		}
       
  1155 		
       
  1156 	if (*aIdSpaceId > id2) 
       
  1157 		{
       
  1158 		return 1;
       
  1159 		}
       
  1160 
       
  1161 	return 0;
       
  1162 	}
       
  1163 
       
  1164 // -----------------------------------------------------------------------------
       
  1165 // TempThumbnail
       
  1166 // -----------------------------------------------------------------------------
       
  1167 //
       
  1168 CFbsBitmap* CGlxCacheManager::TempThumbnail()
       
  1169     {
       
  1170     TRACER("CGlxCacheManager::TempThumbnail");
       
  1171     
       
  1172     return iTempThumbnail;
       
  1173     }
       
  1174     
       
  1175 // -----------------------------------------------------------------------------
       
  1176 // TempThumbnailId
       
  1177 // -----------------------------------------------------------------------------
       
  1178 //
       
  1179 TGlxMediaId CGlxCacheManager::TempThumbnailId()
       
  1180     {
       
  1181     TRACER("CGlxCacheManager::TempThumbnailId");
       
  1182     
       
  1183     return iThumbnailId;
       
  1184     }
       
  1185 
       
  1186 // -----------------------------------------------------------------------------
       
  1187 // SetTempThumbnail
       
  1188 // -----------------------------------------------------------------------------
       
  1189 //
       
  1190 void CGlxCacheManager::SetTempThumbnailToNull()
       
  1191     {
       
  1192     TRACER("CGlxCacheManager::SetTempThumbnailToNull");
       
  1193     
       
  1194     iTempThumbnail = NULL;
       
  1195     }
       
  1196 
       
  1197 // -----------------------------------------------------------------------------
       
  1198 // ErrorsOnRequestedItemsL
       
  1199 // -----------------------------------------------------------------------------
       
  1200 //
       
  1201 TBool CGlxCacheManager::ErrorsOnRequestedItemsL()
       
  1202     {
       
  1203     TRACER("CGlxCacheManager::ErrorsOnRequestedItemsL");
       
  1204     
       
  1205     TBool errorFound = EFalse;
       
  1206     
       
  1207     TInt itemCount = iRequestedItemIds.Count();
       
  1208     TInt attrCount = iRequestedAttrs.Count();
       
  1209     
       
  1210     for ( TInt itemIndex = 0; itemIndex < itemCount && !errorFound; itemIndex++ )
       
  1211         {
       
  1212         CGlxMedia* media = Media(iRequestedItemsIdSpace, iRequestedItemIds[itemIndex]);
       
  1213         
       
  1214         if ( media )
       
  1215             {
       
  1216             for ( TInt attrIndex = 0; attrIndex < attrCount && !errorFound; attrIndex++ )
       
  1217                 {
       
  1218                 errorFound = (KErrNone != GlxErrorManager::HasAttributeErrorL(media, iRequestedAttrs[attrIndex]));
       
  1219                 }
       
  1220             }
       
  1221         }
       
  1222     
       
  1223     return errorFound;
       
  1224     }
       
  1225     
       
  1226 // -----------------------------------------------------------------------------
       
  1227 // Caches
       
  1228 // -----------------------------------------------------------------------------
       
  1229 //
       
  1230 const RPointerArray<CGlxCache>& CGlxCacheManager::Caches()
       
  1231     {
       
  1232     TRACER("CGlxCacheManager::Caches");
       
  1233     
       
  1234     return iCaches;
       
  1235     }
       
  1236 
       
  1237 // -----------------------------------------------------------------------------
       
  1238 // SetTemporaryErrorFlag
       
  1239 // -----------------------------------------------------------------------------
       
  1240 //
       
  1241 void CGlxCacheManager::SetTemporaryErrorFlag()
       
  1242     {
       
  1243     TRACER("CGlxCacheManager::SetTemporaryErrorFlag");
       
  1244     
       
  1245     iTempError = ETrue;
       
  1246     }
       
  1247     
       
  1248 // -----------------------------------------------------------------------------
       
  1249 // StartTempErrorTimer
       
  1250 // -----------------------------------------------------------------------------
       
  1251 //
       
  1252 void CGlxCacheManager::StartTempErrorTimer()
       
  1253     {
       
  1254     TRACER("CGlxCacheManager::StartTempErrorTimer");
       
  1255     
       
  1256     iTempErrorTimer->Cancel();
       
  1257 	iTempErrorTimer->Start(
       
  1258 		TTimeIntervalMicroSeconds32(KGlxTemporaryErrorRecheckPeriodInSeconds * 1000000),
       
  1259 		TTimeIntervalMicroSeconds32(KGlxTemporaryErrorRecheckPeriodInSeconds * 1000000),
       
  1260 		TCallBack(&CGlxCacheManager::TempErrorTimerCallbackL,(TAny *)this));
       
  1261 	}
       
  1262 
       
  1263 // -----------------------------------------------------------------------------
       
  1264 // TempErrorTimerCallbackL
       
  1265 // -----------------------------------------------------------------------------
       
  1266 //
       
  1267 TInt CGlxCacheManager::TempErrorTimerCallbackL(TAny* aPtr)
       
  1268     {
       
  1269     TRACER("CGlxCacheManager::TempErrorTimerCallback");
       
  1270     
       
  1271 	CGlxCacheManager* self = (CGlxCacheManager*) aPtr;
       
  1272 	
       
  1273 	if ( self )
       
  1274 	    {
       
  1275     	self->TempErrorTimerCompleteL();
       
  1276     	}
       
  1277 
       
  1278     return 0;
       
  1279     }
       
  1280 
       
  1281 // -----------------------------------------------------------------------------
       
  1282 // TempErrorTimerComplete
       
  1283 // -----------------------------------------------------------------------------
       
  1284 //
       
  1285 void CGlxCacheManager::TempErrorTimerCompleteL()
       
  1286     {
       
  1287     TRACER("CGlxCacheManager::TempErrorTimerComplete");
       
  1288     
       
  1289     iTempErrorTimer->Cancel();
       
  1290     TRAPD(err, MaintainCacheL());
       
  1291     
       
  1292     // If MaintainCacheL leaves, force gabage collection to start and restart timer
       
  1293     if ( KErrNone != err )
       
  1294         {
       
  1295         if ( KErrNoMemory == err )
       
  1296             {
       
  1297             //iGarbageCollector->Cleanup();
       
  1298             HandleGarbageCollectionL(ETrue);
       
  1299             }
       
  1300             
       
  1301         if ( !iRequestOwner )
       
  1302             {
       
  1303             StartTempErrorTimer();
       
  1304             }
       
  1305         }
       
  1306     }
       
  1307     
       
  1308 // -----------------------------------------------------------------------------
       
  1309 // Create a path with the request items
       
  1310 // -----------------------------------------------------------------------------
       
  1311 //
       
  1312 inline CMPXCollectionPath* CGlxCacheManager::RequestAsPathLC(const CGlxMediaList& aList)
       
  1313     {
       
  1314     TRACER("CGlxCacheManager::RequestAsPathLC");
       
  1315     
       
  1316     CMPXCollectionPath* path = aList.PathLC( NGlxListDefs::EPathParent );
       
  1317 
       
  1318     RArray<TMPXItemId> mpxIds;
       
  1319     CleanupClosePushL( mpxIds );
       
  1320 
       
  1321     TInt itemIdsCount = iRequestedItemIds.Count();
       
  1322 
       
  1323     // Reserve space for all items
       
  1324     mpxIds.ReserveL( itemIdsCount );
       
  1325 
       
  1326     for (TInt i = 0; i < itemIdsCount; ++i)
       
  1327         {
       
  1328         mpxIds.AppendL( iRequestedItemIds[ i ].Value() );
       
  1329         }
       
  1330 
       
  1331     path->AppendL( mpxIds.Array() );
       
  1332     path->SelectAllL();
       
  1333 
       
  1334     CleanupStack::PopAndDestroy( &mpxIds );
       
  1335 
       
  1336     return path;
       
  1337     }
       
  1338 
       
  1339 // -----------------------------------------------------------------------------
       
  1340 // HandleListDeleted
       
  1341 // -----------------------------------------------------------------------------
       
  1342 void CGlxCacheManager::HandleListDeleted(CGlxMediaList* aList)
       
  1343     {
       
  1344     TRACER("CGlxCacheManager::HandleListDeleted");
       
  1345     
       
  1346     if (iRequestOwner == aList)
       
  1347         {
       
  1348         iRequestOwner = NULL;
       
  1349 
       
  1350         TRAP_IGNORE( MaintainCacheL() );
       
  1351         }
       
  1352     }
       
  1353 
       
  1354 // -----------------------------------------------------------------------------
       
  1355 // Inform cache manager to reserve users for an item, for a particular cache
       
  1356 // -----------------------------------------------------------------------------
       
  1357 //
       
  1358 void CGlxCacheManager::ReserveUsersL(const TGlxIdSpaceId& aIdSpaceId, TInt aCount)
       
  1359     {
       
  1360     TRACER("CGlxCacheManager::ReserveUsersL");
       
  1361     
       
  1362     // Look for existing cache
       
  1363     TInt index = iCaches.FindInOrder( aIdSpaceId, ( &CacheOrderByKey ) );
       
  1364     if (index != KErrNotFound)
       
  1365         {
       
  1366         iCaches[index]->ReserveUsersL( aCount );
       
  1367         }
       
  1368     }
       
  1369 //OOM 
       
  1370 // -----------------------------------------------------------------------------
       
  1371 // Start cache cleanup on Low memory event from OOM
       
  1372 // -----------------------------------------------------------------------------
       
  1373 //   
       
  1374 void CGlxCacheManager::ReleaseRAML(TBool aFlushOnRequest)
       
  1375 {
       
  1376     TRACER("CGlxCacheManager::ReleaseRAM");
       
  1377     if(aFlushOnRequest)
       
  1378         {
       
  1379         HandleGarbageCollectionL(aFlushOnRequest);        
       
  1380         }
       
  1381 	else
       
  1382 	{
       
  1383 		iGarbageCollector->CleanupL(); 	 				
       
  1384 	} 	
       
  1385 }
       
  1386 // -----------------------------------------------------------------------------
       
  1387 // Force a cleanup on particular media id : remove all attributes
       
  1388 // -----------------------------------------------------------------------------
       
  1389 // 
       
  1390 void CGlxCacheManager::ForceCleanupMedia(TGlxIdSpaceId aSpaceId, 
       
  1391                                           TGlxMediaId aMediaId)
       
  1392     {
       
  1393     TRACER("CGlxCacheManager::ForceCleanupMedia");  
       
  1394     TInt spaceIdIndex = iCaches.FindInOrder( aSpaceId, &CacheOrderByKey );
       
  1395     if ( KErrNotFound != spaceIdIndex )
       
  1396         {
       
  1397         if ( iCaches[spaceIdIndex]->Media( aMediaId ) )
       
  1398             {            
       
  1399             TInt mediaIdIndex = iCaches[spaceIdIndex]->FindMediaIndexInCache(aMediaId);
       
  1400             if ( KErrNotFound != mediaIdIndex )
       
  1401             	{
       
  1402             	iCaches[spaceIdIndex]->Delete(mediaIdIndex);
       
  1403             	}
       
  1404             }
       
  1405         }
       
  1406     }
       
  1407 
       
  1408 // -----------------------------------------------------------------------------
       
  1409 // Stop cache cleanup on good memory event from OOM
       
  1410 // -----------------------------------------------------------------------------
       
  1411 //
       
  1412 void CGlxCacheManager::StopRAMReleaseL()
       
  1413 {
       
  1414     TRACER("CGlxCacheManager::StopRAMRelease");
       
  1415     iGarbageCollector->CancelCleanup(); 		
       
  1416 
       
  1417 }
       
  1418 //OOM
       
  1419 
       
  1420 #ifdef USE_S60_TNM
       
  1421 // -----------------------------------------------------------------------------
       
  1422 // CGlxCacheManager::FindLoadingById()
       
  1423 // -----------------------------------------------------------------------------
       
  1424 //
       
  1425 TInt CGlxCacheManager::FindLoadingById(TThumbnailRequestId aId, TBool aRemove)
       
  1426     {
       
  1427     TRACER("CGlxCacheManager::FindLoadingById");
       
  1428     TInt index = KErrNotFound;
       
  1429     for(TInt i = 0; i < iThumbnailRequestIds.Count(); ++i)
       
  1430         {
       
  1431         if(iThumbnailRequestIds[i].iId == aId)
       
  1432             {
       
  1433             index = i;
       
  1434             if(aRemove)
       
  1435                 {
       
  1436                 iThumbnailRequestIds.Remove(i);
       
  1437                 }
       
  1438             break;
       
  1439             }
       
  1440         }
       
  1441     return index;
       
  1442     }
       
  1443 
       
  1444 // -----------------------------------------------------------------------------
       
  1445 // CGlxCacheManager::ThumbnailPreviewReady()
       
  1446 // -----------------------------------------------------------------------------
       
  1447 //
       
  1448 void CGlxCacheManager::ThumbnailPreviewReady(MThumbnailData& aThumbnail,
       
  1449         TThumbnailRequestId aId)
       
  1450     {
       
  1451     TRACER("CGlxCacheManager::ThumbnailPreviewReady");
       
  1452     TInt error = KErrNotSupported;
       
  1453     if (aThumbnail.Bitmap() != NULL)
       
  1454          {
       
  1455 		 GLX_DEBUG1("CGlxCacheManager::ThumbnailPreviewReady preview aval");
       
  1456          error = KErrNone;
       
  1457          }
       
  1458     ThumbnailReadyL(error, aThumbnail, aId, EFalse);
       
  1459     }
       
  1460 
       
  1461 // -----------------------------------------------------------------------------
       
  1462 // CGlxCacheManager::ThumbnailReady()
       
  1463 // -----------------------------------------------------------------------------
       
  1464 //
       
  1465 void CGlxCacheManager::ThumbnailReady(TInt aError,
       
  1466         MThumbnailData& aThumbnail, TThumbnailRequestId aId)
       
  1467     {
       
  1468     TRACER("CGlxCacheManager::ThumbnailReady");
       
  1469     GLX_DEBUG2("CGlxCacheManager::ThumbnailReady aError=%d", aError);
       
  1470     ThumbnailReadyL(aError, aThumbnail, aId, ETrue);
       
  1471     }
       
  1472 
       
  1473 // -----------------------------------------------------------------------------
       
  1474 // CGlxCacheManager::ThumbnailReadyL()
       
  1475 // -----------------------------------------------------------------------------
       
  1476 //
       
  1477 void CGlxCacheManager::ThumbnailReadyL(TInt aError, MThumbnailData& aThumbnail, 
       
  1478                                        TThumbnailRequestId aId, TBool aQuality)
       
  1479     {
       
  1480     TRACER("CGlxCacheManager::ThumbnailReadyL");
       
  1481     GLX_DEBUG3("CGlxCacheManager::ThumbnailReadyL aError=%d, aQuality=%d",
       
  1482                                 aError, aQuality);
       
  1483 
       
  1484 #ifdef _DEBUG
       
  1485     iStopTime.HomeTime(); // Get home time
       
  1486     GLX_DEBUG2("=>CGlxCacheManager::ThumbnailReadyL - TN Fetch took <%d> us", 
       
  1487                     (TInt)iStopTime.MicroSecondsFrom(iStartTime).Int64());
       
  1488 #endif
       
  1489     
       
  1490 	TInt reqIndex = FindLoadingById(aId, EFalse);
       
  1491 		
       
  1492     if (reqIndex == KErrNotFound)
       
  1493         {
       
  1494 		return;
       
  1495         }
       
  1496 
       
  1497     delete iMPXMedia;
       
  1498     iMPXMedia = NULL;
       
  1499         
       
  1500     iMPXMedia = CMPXMedia::NewL();
       
  1501     if (aError == KErrNone)
       
  1502         {
       
  1503         delete iTempThumbnail;
       
  1504         iTempThumbnail = NULL;
       
  1505         iTempThumbnail = aThumbnail.DetachBitmap();
       
  1506 
       
  1507         CGlxThumbnailAttribute* tnAttribute = new (ELeave) CGlxThumbnailAttribute;
       
  1508         CleanupStack::PushL(tnAttribute);
       
  1509         tnAttribute->iDimensions = iThumbnailRequestIds[reqIndex].iSize;
       
  1510 	    tnAttribute->iThumbnailQuality = aQuality;
       
  1511                 
       
  1512         iMPXMedia->SetTObjectValueL<TMPXItemId>(KMPXMediaGeneralId, 
       
  1513 						iThumbnailRequestIds[reqIndex].iThumbnailId.Value());
       
  1514         TUint attributeId = GlxFullThumbnailAttributeId(aQuality, 
       
  1515 								iThumbnailRequestIds[reqIndex].iSize.iWidth, 
       
  1516 								iThumbnailRequestIds[reqIndex].iSize.iHeight);
       
  1517         iMPXMedia->SetNoNewLCObjectL(
       
  1518                TMPXAttribute(KGlxMediaIdThumbnail, attributeId), tnAttribute);
       
  1519         CleanupStack::PopAndDestroy(tnAttribute);
       
  1520 
       
  1521         HandleCollectionMediaL(iThumbnailRequestIds[reqIndex].iSpaceId,
       
  1522                                                     *iMPXMedia, aError);
       
  1523         }
       
  1524     else
       
  1525         {
       
  1526         HandleCollectionMediaL(iThumbnailRequestIds[reqIndex].iSpaceId, 
       
  1527 													*iMPXMedia, aError);
       
  1528         }
       
  1529     
       
  1530     if (aQuality)
       
  1531         {
       
  1532         FindLoadingById(aId, ETrue);
       
  1533         }   
       
  1534     }
       
  1535 #endif
       
  1536 
       
  1537 // -----------------------------------------------------------------------------
       
  1538 // GetMimeTypeL()
       
  1539 // -----------------------------------------------------------------------------
       
  1540 //
       
  1541 void CGlxCacheManager::GetMimeTypeL(TFileName& aFileName, TDataType& aMimeType)
       
  1542     {
       
  1543     TRACER("CGlxCacheManager::GetMimeTypeL");
       
  1544     RApaLsSession session;
       
  1545     User::LeaveIfError( session.Connect() );
       
  1546     CleanupClosePushL( session );
       
  1547 
       
  1548     TUid uid;
       
  1549     User::LeaveIfError( session.AppForDocument( aFileName, uid, aMimeType ) );
       
  1550     CleanupStack::PopAndDestroy(&session);
       
  1551     }
       
  1552 
       
  1553 
       
  1554 //End of file