harvester/server/src/harvesterao.cpp
branchRCL_3
changeset 19 b73252188534
parent 18 63c982fb92f2
child 20 f23c07ec56e2
--- a/harvester/server/src/harvesterao.cpp	Thu Jul 15 19:07:24 2010 +0300
+++ b/harvester/server/src/harvesterao.cpp	Thu Aug 19 10:20:41 2010 +0300
@@ -53,6 +53,7 @@
 
 const TInt KPlaceholderQueueSize = 99;
 const TInt KContainerPlaceholderQueueSize = 10;
+const TInt KReadyPlaceholderQueueSize = 10;
 const TInt KObjectDefStrSize = 20;
 
 _LIT( KTAGDaemonName, "ThumbAGDaemon" );
@@ -76,32 +77,34 @@
 
 void CHarvesterAoPropertyDefs::ConstructL(CMdEObjectDef& aObjectDef)
 	{
-	CMdENamespaceDef& nsDef = aObjectDef.NamespaceDef();
-
-	// Common property definitions
-	CMdEObjectDef& objectDef = nsDef.GetObjectDefL( MdeConstants::Object::KBaseObject );
-	iCreationDatePropertyDef = &objectDef.GetPropertyDefL( MdeConstants::Object::KCreationDateProperty );
-	iLastModifiedDatePropertyDef = &objectDef.GetPropertyDefL( MdeConstants::Object::KLastModifiedDateProperty );
-	iSizePropertyDef = &objectDef.GetPropertyDefL( MdeConstants::Object::KSizeProperty );
-	iOriginPropertyDef = &objectDef.GetPropertyDefL( MdeConstants::Object::KOriginProperty );
-	iItemTypePropertyDef = &objectDef.GetPropertyDefL( MdeConstants::Object::KItemTypeProperty );
-	iTitlePropertyDef = &objectDef.GetPropertyDefL( MdeConstants::Object::KTitleProperty );
-	iDefaultFolderPropertyDef = &objectDef.GetPropertyDefL( MdeConstants::Object::KInDefaultFolder );
-	
-	CMdEObjectDef& mediaDef = nsDef.GetObjectDefL( MdeConstants::MediaObject::KMediaObject );
-	iPreinstalledPropertyDef = &mediaDef.GetPropertyDefL( MdeConstants::MediaObject::KPreinstalledProperty );
+    SetByObjectDefL( aObjectDef );
 	}
 
-CHarvesterAoPropertyDefs* CHarvesterAoPropertyDefs::NewL(CMdEObjectDef& aObjectDef)
-	{
-	CHarvesterAoPropertyDefs* self = 
-		new (ELeave) CHarvesterAoPropertyDefs();
-	CleanupStack::PushL( self );
-	self->ConstructL( aObjectDef );
-	CleanupStack::Pop( self );
-	return self;
-	}
+CHarvesterAoPropertyDefs* CHarvesterAoPropertyDefs::NewL()
+    {
+    CHarvesterAoPropertyDefs* self = 
+        new (ELeave) CHarvesterAoPropertyDefs();
+    return self;
+    }
+
+void CHarvesterAoPropertyDefs::SetByObjectDefL(CMdEObjectDef& aObjectDef)
+    {
+    CMdENamespaceDef& nsDef = aObjectDef.NamespaceDef();
 
+    // Common property definitions
+    CMdEObjectDef& objectDef = nsDef.GetObjectDefL( MdeConstants::Object::KBaseObject );
+    iCreationDatePropertyDef = &objectDef.GetPropertyDefL( MdeConstants::Object::KCreationDateProperty );
+    iLastModifiedDatePropertyDef = &objectDef.GetPropertyDefL( MdeConstants::Object::KLastModifiedDateProperty );
+    iSizePropertyDef = &objectDef.GetPropertyDefL( MdeConstants::Object::KSizeProperty );
+    iOriginPropertyDef = &objectDef.GetPropertyDefL( MdeConstants::Object::KOriginProperty );
+    iItemTypePropertyDef = &objectDef.GetPropertyDefL( MdeConstants::Object::KItemTypeProperty );
+    iTitlePropertyDef = &objectDef.GetPropertyDefL( MdeConstants::Object::KTitleProperty );
+    iDefaultFolderPropertyDef = &objectDef.GetPropertyDefL( MdeConstants::Object::KInDefaultFolder );
+    
+    CMdEObjectDef& mediaDef = nsDef.GetObjectDefL( MdeConstants::MediaObject::KMediaObject );
+    iPreinstalledPropertyDef = &mediaDef.GetPropertyDefL( MdeConstants::MediaObject::KPreinstalledProperty );
+    }
+	
 // ---------------------------------------------------------------------------
 // NewLC
 // ---------------------------------------------------------------------------
@@ -186,14 +189,18 @@
     DeleteComposers();
 
     delete iDiskFullNotifier;
+    iDiskFullNotifier = NULL;
 	delete iBackupSubscriber;
+	iBackupSubscriber = NULL;
     
     if (iBlacklist)
 		{
 		iBlacklist->CloseDatabase();
 		delete iBlacklist;
+		iBlacklist = NULL;
 		}
 	delete iReHarvester;
+	iReHarvester = NULL;
 
     if ( iHarvestFileMessages.Count() > 0 )
         {
@@ -222,26 +229,43 @@
     iTempReadyPHArray.Close();
     
 	delete iHarvesterOomAO;
+	iHarvesterOomAO = NULL;
     delete iRestoreWatcher;
+    iRestoreWatcher = NULL;
 	delete iOnDemandAO;
+	iOnDemandAO = NULL;
 	delete iMdEHarvesterSession;
+	iMdEHarvesterSession = NULL;
 	delete iMdESession;
+	iMdESession = NULL;
 	delete iQueue;
+	iQueue = NULL;
 	delete iHarvesterPluginFactory;
+	iHarvesterPluginFactory = NULL;
 	delete iMdeObjectHandler;
+	iMdeObjectHandler = NULL;
 	delete iUnmountHandlerAO;
+	iUnmountHandlerAO = NULL;
 	
 	delete iPropDefs;
+	iPropDefs = NULL;
 	delete iCameraExtensionArray;
+	iCameraExtensionArray = NULL;
 	
     delete iPhoneImagesPath;
+    iPhoneImagesPath = NULL;
     delete iMmcImagesPath;
+    iMmcImagesPath = NULL;
     
     delete iPhoneVideosPath;
+    iPhoneVideosPath = NULL;
     delete iMmcVideosPath;
+    iMmcVideosPath = NULL;
     
     delete iPhoneSoundsPath;
+    iPhoneSoundsPath = NULL;
     delete iMmcSoundsPath;
+    iMmcSoundsPath = NULL;
 	
 	RMediaIdUtil::ReleaseInstance();
     
@@ -293,6 +317,8 @@
     // Reset harvesting status for clients in case blacklisted file was handled
     iHarvesterPluginFactory->SendHarvestingStatusEventL( EFalse );
     
+    iPropDefs = CHarvesterAoPropertyDefs::NewL();
+	
     iCameraExtensionArray = new ( ELeave ) CDesCArraySeg( 6 );
     iCameraExtensionArray->InsertIsqL( KExtensionMp4 );
     iCameraExtensionArray->InsertIsqL( KExtensionMpg4 );
@@ -354,8 +380,7 @@
     CleanupStack::PushL( cleanupItem );
     
     CMonitorPlugin::ListImplementationsL( infoArray );
-    TInt count( 0 );
-    count = infoArray.Count();
+    const TInt count( infoArray.Count() );
     CMonitorPlugin* plugin = NULL;
     
     for ( TInt i = 0; i < count; i++ )
@@ -410,7 +435,6 @@
     {
     WRITELOG( "CHarvesterAO::StartMonitoring()" );
     OstTrace0( TRACE_NORMAL, CHARVESTERAO_STARTMONITORING, "CHarvesterAO::StartMonitoring" );    
-    
     const TInt count( iMonitorPluginArray.Count() );  
     
     for ( TInt i = 0; i < count; i++ )
@@ -429,10 +453,8 @@
     WRITELOG( "CHarvesterAO::StopMonitoring()" );
     
     OstTrace0( TRACE_NORMAL, CHARVESTERAO_STOPMONITORING, "CHarvesterAO::StopMonitoring" );
-
-    const TInt count( iMonitorPluginArray.Count() );
     
-    for ( TInt i = 0; i < count; i++ )
+    for( TInt i = iMonitorPluginArray.Count() - 1; i >=0; i-- )
         {
         iMonitorPluginArray[i]->StopMonitoring();
         }
@@ -447,12 +469,11 @@
     WRITELOG( "CHarvesterAO::PauseMonitoring()" );
     OstTrace0( TRACE_NORMAL, CHARVESTERAO_PAUSEMONITORING, "CHarvesterAO::PauseMonitoring" );
     
-    const TInt count( iMonitorPluginArray.Count() );
-    
-    for ( TInt i = 0; i<count; i++ )
+    for( TInt i = iMonitorPluginArray.Count() - 1; i >=0; i-- )
         {
         iMonitorPluginArray[i]->PauseMonitoring();
         }
+    
     OstTrace0( TRACE_NORMAL, DUP1_CHARVESTERAO_PAUSEMONITORING, "CHarvesterAO::PauseMonitoring - end" );    
     WRITELOG( "CHarvesterAO::PauseMonitoring() - end" );
     }
@@ -518,6 +539,7 @@
                 WRITELOG1( "CHarvesterAO::HandleUnmount() remove iReadyPHArray %d", i);
                 OstTrace1( TRACE_NORMAL, DUP2_CHARVESTERAO_HANDLEUNMOUNT, "CHarvesterAO::HandleUnmount remove iReadyPHArray %d", i );
                 
+                HarvestCompleted( hd->ClientId(), hd->Uri(), KErrCancel );
                 delete hd;
                 hd = NULL;
                 iReadyPHArray.Remove( i );
@@ -555,6 +577,7 @@
                 WRITELOG1( "CHarvesterAO::HandleUnmount() remove iPHArray %d", i);
                 OstTrace1( TRACE_NORMAL, DUP5_CHARVESTERAO_HANDLEUNMOUNT, "CHarvesterAO::HandleUnmount remove iPHArray %d", i );
                 
+                HarvestCompleted( hd->ClientId(), hd->Uri(), KErrCancel );
                 delete hd;
 				hd = NULL;
                 iPHArray.Remove( i );
@@ -591,6 +614,7 @@
                 WRITELOG1( "CHarvesterAO::HandleUnmount() remove iContainerPHArray %d", i);
                 OstTrace1( TRACE_NORMAL, DUP8_CHARVESTERAO_HANDLEUNMOUNT, "CHarvesterAO::HandleUnmount remove iContainerPHArray %d", i );
                 
+                HarvestCompleted( hd->ClientId(), hd->Uri(), KErrCancel );
                 delete hd;
 				hd = NULL;
                 iContainerPHArray.Remove( i );
@@ -622,6 +646,7 @@
             if( err == KErrNone && mediaId == aMediaId )
                 {
                 WRITELOG1( "CHarvesterAO::HandleUnmount() remove iTempReadyPHArray %d", i);
+                HarvestCompleted( hd->ClientId(), hd->Uri(), KErrCancel );
                 delete hd;
                 hd = NULL;
                 iTempReadyPHArray.Remove( i );
@@ -681,6 +706,7 @@
 
 					TRAP_IGNORE( iMdESession->CancelObjectL( mdeobj ) );
 					
+					HarvestCompleted( hd->ClientId(), hd->Uri(), KErrCancel );
 					delete hd;
 					hd = NULL;
 					}
@@ -825,22 +851,31 @@
 				iPHArray.Count() < KPlaceholderQueueSize &&
 				hd->ObjectType() == EPlaceholder )
     		{
-        	iPHArray.Append( hd );
-        	if( hd->Origin() == MdeConstants::Object::ECamera || 
-        	    hd->ObjectType() == EFastHarvest  )
+        	if(iPHArray.Append( hd ) != KErrNone)
+        	    {
+        	    HarvestCompleted( hd->ClientId(), hd->Uri(), KErrNoMemory );
+        	    iHarvesterEventManager->DecreaseItemCountL( EHEObserverTypeMMC, 1 );
+                delete hd;
+                hd = NULL;
+        	    }
+        	else
         	    {
-        	    if( !iFastHarvestNeeded )
-        	        {
-                    iFastHarvestNeeded = ETrue;
-                    // Fast harvest event must be handled even if MMC handling would be ongoing
-                    SetPriority( KHarvesterPriorityMonitorPlugin );
-        	        }
-        	    break;
-        	    }
-        	else if( iFastHarvestNeeded )
-        	    {
-        	    iFastHarvestNeeded = EFalse;
-        	    SetPriority( KHarvesterCustomImportantPriority );
+                if( hd->Origin() == MdeConstants::Object::ECamera || 
+                    hd->ObjectType() == EFastHarvest  )
+                    {
+                    if( !iFastHarvestNeeded )
+                        {
+                        iFastHarvestNeeded = ETrue;
+                        // Fast harvest event must be handled even if MMC handling would be ongoing
+                        SetPriority( KHarvesterPriorityMonitorPlugin );
+                        }
+                    break;
+                    }
+                else if( iFastHarvestNeeded )
+                    {
+                    iFastHarvestNeeded = EFalse;
+                    SetPriority( KHarvesterCustomImportantPriority );
+        	    	}
         	    }
         	hd = iQueue->GetNextItem();
     		}
@@ -849,11 +884,14 @@
     	    {
             TRAPD( err, HandlePlaceholdersL( ETrue ) );
 
-            // make sure that when HandlePlaceholdersL leaves, iPHArray is cleared
+            // make sure that when HandlePlaceholdersL leaves unexpectedly, iPHArray is cleared
             if ( err != KErrNone )
                 {
-                iPHArray.ResetAndDestroy();
-                iTempReadyPHArray.ResetAndDestroy();
+                if( err != KErrDiskFull )
+                    {
+                    iPHArray.ResetAndDestroy();
+                    iTempReadyPHArray.ResetAndDestroy();
+                    }
                 User::Leave( err );
                 }
             
@@ -877,16 +915,21 @@
     		{
 	    	if( hd->ObjectType() == EPlaceholder )
 	    		{
-	        	iPHArray.Append( hd );
+	        	if( iPHArray.Append( hd ) != KErrNone )
+	        	    {
+	        	    HarvestCompleted( hd->ClientId(), hd->Uri(), KErrNoMemory ); 
+	        	    iHarvesterEventManager->DecreaseItemCountL( EHEObserverTypeMMC, 1 );
+                    delete hd;
+                    hd = NULL;
+	        	    }
 	    		}
 	    	else
 	    		{
-	    		CheckFileExtensionAndHarvestL( hd );
-	    		if( iUnmountDetected )
-	    		    {
-	    		    iQueue->Append( hd );
-	    		    return;
-	    		    }
+                if( iReadyPHArray.Append( hd ) != KErrNone)
+                    {
+                    delete hd;
+                    hd = NULL;
+                    }
 	    		}
     		}
 			
@@ -894,11 +937,14 @@
     		{
 	    	TRAPD( err, HandlePlaceholdersL( ETrue ) );
 
-	    	// make sure that when HandlePlaceholdersL leaves, iPHArray is cleared
+	    	// make sure that when HandlePlaceholdersL leaves unexpectedly, iPHArray is cleared
 	    	if ( err != KErrNone )
 	    		{
-	    		iPHArray.ResetAndDestroy();
-	    		iTempReadyPHArray.ResetAndDestroy();
+	    	    if( err != KErrDiskFull )
+	    	        {
+	    	        iPHArray.ResetAndDestroy();
+	    	        iTempReadyPHArray.ResetAndDestroy();
+	    	        }
 	    		User::Leave( err );
 	    		}
     		}
@@ -911,7 +957,7 @@
             }
         iHarvestingPlaceholders = EFalse;
         CheckFileExtensionAndHarvestL( hd );
-        if( iUnmountDetected )
+        if( iUnmountDetected && hd )
             {
             iQueue->Append( hd );
             }
@@ -932,6 +978,8 @@
 
 	TTimeIntervalSeconds timeOffsetSeconds = User::UTCOffset();
 	
+	CMdENamespaceDef& defNS = iMdESession->GetDefaultNamespaceDefL();
+	
 	TInt endindex( iPHArray.Count() );
 	for( TInt i = 0; i < endindex; i++ )
 		{
@@ -939,17 +987,25 @@
 		
 		if( aCheck && iHarvesterPluginFactory->IsContainerFileL( hd->Uri() ) )
 			{
-			iContainerPHArray.Append( hd );
+			if( iContainerPHArray.Append( hd ) != KErrNone )
+			    {
+			    HarvestCompleted( hd->ClientId(), hd->Uri(), KErrNoMemory );
+			    iHarvesterEventManager->DecreaseItemCountL( EHEObserverTypeMMC, 1 );
+                delete hd;
+                hd = NULL;
+			    }
+
 			iPHArray.Remove( i );
-            i--;
-            endindex--;
+			i--;
+			endindex--;
 			continue;
 			}
+		
 		TBuf<KObjectDefStrSize> objDefStr;
 		
 		if( !CheckForCameraItem( hd, objDefStr ) )
 		    {
-		    iHarvesterPluginFactory->GetObjectDefL( *hd, objDefStr );
+		    iHarvesterPluginFactory->GetObjectDefL( hd, objDefStr );
 		    }
 		
 		// GetObjectDef can cause context switch, and if unmount happens when this execution is 
@@ -960,8 +1016,15 @@
 		    WRITELOG( "CHarvesterAO::HandlePlaceholdersL() - Unmount detected during execution!" );
 		    for( TInt y( iTempReadyPHArray.Count() -1 ); y >=0; y-- )
 		        {
-		        CHarvesterData* hd = iTempReadyPHArray[y];
-		        iPHArray.Insert( hd, 0 );
+		        CHarvesterData* tempHd = iTempReadyPHArray[y];
+				
+		        if(iPHArray.Insert( tempHd, 0 ) != KErrNone)
+		            {
+		            HarvestCompleted( tempHd->ClientId(), tempHd->Uri(), KErrNoMemory );
+		            iHarvesterEventManager->DecreaseItemCountL( EHEObserverTypeMMC, 1 );
+                    delete tempHd;
+                    tempHd = NULL;
+		            }
 		        }
 		    iTempReadyPHArray.Reset();
 		    CleanupStack::PopAndDestroy( &mdeObjectArray );
@@ -976,21 +1039,41 @@
             const TInt currentPHArrayCount( iPHArray.Count() );
             for( TInt y( iTempReadyPHArray.Count() -1 ); y >=0; y-- )
                 {
-                CHarvesterData* hd = iTempReadyPHArray[y];
-                if( currentPHArrayCount )
+                CHarvesterData* tempHd = iTempReadyPHArray[y];
+                if(iPHArray.Insert( tempHd, 0 ) != KErrNone)
                     {
-                    // Leave the first item in the array as it is the priority item
-                    iPHArray.Insert( hd, 1 );
-                    }
-                else
-                    {
-                    iPHArray.Insert( hd, 0 );
+                    HarvestCompleted( tempHd->ClientId(), tempHd->Uri(), KErrNoMemory );
+                    iHarvesterEventManager->DecreaseItemCountL( EHEObserverTypeMMC, 1 );
+                    delete tempHd;
+                    tempHd = NULL;
                     }
                 }
             iTempReadyPHArray.Reset();
             CleanupStack::PopAndDestroy( &mdeObjectArray );
             return;		
 		    }
+	    // Check if disk is full
+	    // If disk is detected to be full, no items can be added to MDS db, thus abort the run, and start over 
+		// when disk space is available to make sure the arrays are valid.
+		else if( iDiskFull )
+		    {
+            WRITELOG( "CHarvesterAO::HandlePlaceholdersL() - No disk space available!" );
+            for( TInt y( iTempReadyPHArray.Count() -1 ); y >=0; y-- )
+                {
+                CHarvesterData* tempHd = iTempReadyPHArray[y];
+            
+                if(iPHArray.Insert( tempHd, 0 ) != KErrNone)
+                    {
+                    HarvestCompleted( tempHd->ClientId(), tempHd->Uri(), KErrNoMemory );
+                    iHarvesterEventManager->DecreaseItemCountL( EHEObserverTypeMMC, 1 );
+                    delete tempHd;
+                    tempHd = NULL;
+                    }
+                }
+            iTempReadyPHArray.Reset();
+            CleanupStack::PopAndDestroy( &mdeObjectArray );
+            User::Leave( KErrDiskFull );
+		    }
 		
 		if( objDefStr.Length() == 0 ||
 		    ( objDefStr == KInUse ) )
@@ -1008,10 +1091,12 @@
 			continue;
 			}
 
-		CMdENamespaceDef& defNS = iMdESession->GetDefaultNamespaceDefL();
 		CMdEObjectDef& mdeObjectDef = defNS.GetObjectDefL( objDefStr );
 
-		CMdEObject* mdeObject = iMdESession->NewObjectL( mdeObjectDef, hd->Uri() );
+		HBufC* hdUri = hd->Uri().AllocL();
+		CleanupStack::PushL( hdUri );
+		CMdEObject* mdeObject = iMdESession->NewObjectL( mdeObjectDef, *hdUri );
+		CleanupStack::PopAndDestroy( hdUri );
 		CleanupStack::PushL( mdeObject );
 		
 		CPlaceholderData* phData = NULL;
@@ -1080,10 +1165,10 @@
 	    // set placeholder
 	    mdeObject->SetPlaceholder( ETrue );
 	    
-	    if( !iPropDefs )
-	    	{
-	    	iPropDefs = CHarvesterAoPropertyDefs::NewL( defNS.GetObjectDefL( MdeConstants::Object::KBaseObject ) );
-	    	}
+	    if( !iPropDefs->iCreationDatePropertyDef )
+	        {
+            iPropDefs->SetByObjectDefL( defNS.GetObjectDefL( MdeConstants::Object::KBaseObject ) );
+	        }
 
 	    // set file size
     	mdeObject->AddUint32PropertyL( *iPropDefs->iSizePropertyDef, phData->FileSize() );
@@ -1172,33 +1257,68 @@
 	    
 	    CleanupStack::Pop( mdeObject );
 		
-	    iTempReadyPHArray.Append( hd );
+	    if(iTempReadyPHArray.Append( hd ) != KErrNone)
+	        {
+	        HarvestCompleted( hd->ClientId(), hd->Uri(), KErrNoMemory );
+            delete hd;
+            hd = NULL;
+	        }
 		iPHArray.Remove( i );
         i--;
         endindex--;
 		}
 	
-	const TInt tempArrayCount( iTempReadyPHArray.Count() );
-	for( TInt i( 0 ); i < tempArrayCount; i++ )
-	    {
-	    CHarvesterData* hd = iTempReadyPHArray[i];
-	    iReadyPHArray.Append( hd );
-	    }
-	iTempReadyPHArray.Reset();
-	
 	const TInt objectCount = mdeObjectArray.Count();  
 	
     if( objectCount > 0 )
 		{
 		// add object to mde
 		iMdEHarvesterSession->AutoLockL( mdeObjectArray );
-		const TInt addError( iMdESession->AddObjectsL( mdeObjectArray ) );
+		TInt addError( KErrNone );
+		TRAPD( addFailure, addError = iMdESession->AddObjectsL( mdeObjectArray ) );
+		if( addFailure == KErrDiskFull )
+		    {
+            WRITELOG( "CHarvesterAO::HandlePlaceholdersL() - No disk space available!" );
+            for( TInt y( iTempReadyPHArray.Count() -1 ); y >=0; y-- )
+                {
+                CHarvesterData* tempHd = iTempReadyPHArray[y];
+        
+                if(iPHArray.Insert( tempHd, 0 ) != KErrNone)
+                    {
+                    HarvestCompleted( tempHd->ClientId(), tempHd->Uri(), KErrNoMemory );
+                    iHarvesterEventManager->DecreaseItemCountL( EHEObserverTypeMMC, 1 );
+                    delete tempHd;
+                    tempHd = NULL;
+                    }
+                }
+            iTempReadyPHArray.Reset();
+            CleanupStack::PopAndDestroy( &mdeObjectArray );
+            User::Leave( KErrDiskFull );		
+		    }
+		else if( addFailure != KErrNone )
+		    {
+		    User::Leave( addFailure );      
+		    }
+		
 		if( addError != KErrNone )
 		    {
 		    // If some error occures, retry
 		    iMdESession->AddObjectsL( mdeObjectArray );
 		    }
 
+	    const TInt tempArrayCount( iTempReadyPHArray.Count() );
+	    for( TInt i( 0 ); i < tempArrayCount; i++ )
+	        {
+	        CHarvesterData* tempHd = iTempReadyPHArray[i];
+            if(iReadyPHArray.Append( tempHd ) != KErrNone)
+                 {
+                 HarvestCompleted( tempHd->ClientId(), tempHd->Uri(), KErrNoMemory );
+                 delete tempHd;
+                 tempHd = NULL;
+                 }
+	        }
+	    iTempReadyPHArray.Reset();
+		
 	    iHarvesterEventManager->IncreaseItemCount( EHEObserverTypePlaceholder, 
 		        objectCount );
 		iHarvesterEventManager->SendEventL( EHEObserverTypePlaceholder, EHEStateStarted, 
@@ -1234,17 +1354,17 @@
     const TDesC& uri = aHD->Uri();
     TBool objectExisted = ETrue;
     
-    if( ! mdeObject )
+    if( !mdeObject )
     	{
     	objectExisted = EFalse;
     	WRITELOG1( "CHarvesterAO::CheckFileExtensionAndHarvestL() - no mdeobject. URI: %S", &uri );
 	    TBuf<KObjectDefStrSize> objDefStr;
-		iHarvesterPluginFactory->GetObjectDefL( *aHD, objDefStr );
+		iHarvesterPluginFactory->GetObjectDefL( aHD, objDefStr );
 
         // GetObjectDef can cause context switch, and if unmount happens when this execution is 
         // interrupted, the ph data can be invalid. Thus, abort whole run, and start over to make sure 
         // the data is valid.
-        if( iUnmountDetected )
+        if( !aHD )
             {
             return;
             }
@@ -1349,9 +1469,16 @@
     	{
     	iMdESession->RemoveObjectL( aHD->Uri() );
     	}
+    
+    // If context swich occures just right due to RemoveObjectL, check aHD for validity
+    if( !aHD )
+        {
+        return;
+        }
 	
 	TInt pluginErr = KErrNone;
     TRAPD( err, pluginErr = iHarvesterPluginFactory->HarvestL( aHD ));
+    
     if ( err != KErrNone )
     	{
     	WRITELOG1( "CHarvesterAO::CheckFileExtensionAndHarvestL() - plugin error: %d", err );
@@ -1381,8 +1508,6 @@
     
     WRITELOG1("CHarvesterAO::CheckFileExtensionAndHarvestL() - ends with error %d", pluginErr );
     OstTrace1( TRACE_NORMAL, DUP8_CHARVESTERAO_CHECKFILEEXTENSIONANDHARVESTL, "CHarvesterAO::CheckFileExtensionAndHarvestL) - ends with error %d", pluginErr );
-    
-    SetNextRequest( ERequestHarvest );
     }
 
 // ---------------------------------------------------------------------------
@@ -1512,8 +1637,6 @@
         OstTrace0( TRACE_NORMAL, DUP12_CHARVESTERAO_HARVESTINGCOMPLETED, "==============================ERROR done =========================" );
         
         }
-           
-    SetNextRequest( ERequestHarvest );
     }
 
 // ---------------------------------------------------------------------------
@@ -1660,25 +1783,41 @@
         TRAP_IGNORE( BootPartialRestoreScanL() );
 #endif
         
-        if( !iMassMemoryIdChecked )
+        // Store the internal mass memory media ID to DB, and update data if necessary
+        TInt drive( -1 );
+        TInt internalMassStorageError( DriveInfo::GetDefaultDrive( DriveInfo::EDefaultMassStorage, drive ) );
+        if( internalMassStorageError == KErrNone )
             {
-            TInt drive( -1 );
-            TInt massStorageError( DriveInfo::GetDefaultDrive( DriveInfo::EDefaultMassStorage, drive ) );
-            if( massStorageError == KErrNone )
+            TVolumeInfo internalMassStorageVolumeInfo;
+            internalMassStorageError = iFs.Volume( internalMassStorageVolumeInfo, drive );
+            if( internalMassStorageError == KErrNone )
                 {
-                TVolumeInfo massStorageVolumeInfo;
-                iFs.Volume( massStorageVolumeInfo, drive );
-                const TUint32 massStorageMediaId( massStorageVolumeInfo.iUniqueID );
-                massStorageError = DriveInfo::GetDefaultDrive( DriveInfo::EDefaultRemovableMassStorage, drive );
-                if( massStorageError == KErrNone )
+                const TUint32 massStorageMediaId( internalMassStorageVolumeInfo.iUniqueID );
+                TUint32 mmcMediaId( 0 );
+                TInt mmcError( DriveInfo::GetDefaultDrive( DriveInfo::EDefaultRemovableMassStorage, drive ) );
+                if( mmcError == KErrNone )
                     {
-                    iFs.Volume( massStorageVolumeInfo, drive );
-                    // Update mass storage media id if the mass storage is not memory card
-                    if( massStorageVolumeInfo.iUniqueID != massStorageMediaId && massStorageMediaId != 0 )
+                    TVolumeInfo mmcVolumeInfo;
+                    mmcError = iFs.Volume( mmcVolumeInfo, drive );
+                    if( mmcError == KErrNone )
+                        {
+                        mmcMediaId = mmcVolumeInfo.iUniqueID;
+                        }
+                    }
+                
+                // If removable storage is not found, assume internal mass storage was mounted
+                if( mmcError )
+                    {
+                    if( massStorageMediaId != 0 )
                         {
                         iMdEHarvesterSession->CheckMassStorageMediaId( massStorageMediaId );
-                        }
+                        }                    
                     }
+                else if( massStorageMediaId != mmcMediaId && 
+                            massStorageMediaId != 0 )
+                    {
+                    iMdEHarvesterSession->CheckMassStorageMediaId( massStorageMediaId );
+                    }          
                 }
             }
         }
@@ -1818,7 +1957,7 @@
             WRITELOG( "CHarvesterAO::RunL - ERequestHarvest" );
             OstTrace0( TRACE_NORMAL, DUP2_CHARVESTERAO_RUNL, "CHarvesterAO::RunL - ERequestHarvest" );
             
-            // harvest new items first...
+            // harvest new items first
             if ( iQueue->ItemsInQueue() > 0 )
                 {
                 WRITELOG( "CHarvesterAO::RunL - Items in queue - calling ReadItemFromQueueL()" );
@@ -1831,9 +1970,29 @@
             else
                 {
                 WRITELOG( "CHarvesterAO::RunL - No items in main queue" );
+                // If interrupts occured, check the normal placeholder array for possible items to
+                // be handled before moving on to container or ready placeholders
+                if( iPHArray.Count() > 0 )
+                    {
+                    WRITELOG( "CHarvesterAO::RunL - Items found in placeholder array" );
+                    TRAPD( err, HandlePlaceholdersL( ETrue ) );
+
+                    // make sure that when HandlePlaceholdersL leaves unexpectedly, iPHArray is cleared
+                    if ( err != KErrNone )
+                        {
+                        if( err != KErrDiskFull )
+                            {
+                            iPHArray.ResetAndDestroy();
+                            iTempReadyPHArray.ResetAndDestroy();
+                            }
+                        User::Leave( err );
+                        }
+                    SetNextRequest( ERequestHarvest );
+                    break;
+                    }
                 // All registered fast harvested items or placeholders handled at this point     
                 // if container files to harvest, handle those next
-                if( iContainerPHArray.Count() > 0 )
+                else if( iContainerPHArray.Count() > 0 )
                 	{
                     WRITELOG( "CHarvesterAO::RunL - Items in iContainterPHArray - requesting ERequestContainerPlaceholder handling" );
                     iFastHarvestNeeded = EFalse;
@@ -1864,8 +2023,8 @@
             		WRITELOG1("CHarvesterAO::RunL - items in ready pharray: %d", arrayCount );
             		OstTrace1( TRACE_NORMAL, DUP3_CHARVESTERAO_RUNL, "CHarvesterAO::RunL - items in ready pharray: %d", arrayCount );
 #endif   		
-            		TInt endIndex( KPlaceholderQueueSize );
-            		if( arrayCount < KPlaceholderQueueSize )
+            		TInt endIndex( KReadyPlaceholderQueueSize );
+            		if( arrayCount < KReadyPlaceholderQueueSize )
             		    {
             		    endIndex = arrayCount;
             		    }
@@ -1913,14 +2072,17 @@
         		}
         	TRAPD( err, HandlePlaceholdersL( EFalse ) );
 
-	    	// make sure that when HandlePlaceholdersL leaves, iPHArray is cleared
-	    	if ( err != KErrNone )
-	    		{
-	    	    iContainerPHArray.ResetAndDestroy();
-	    		iPHArray.ResetAndDestroy();
-	    		iTempReadyPHArray.ResetAndDestroy();
-	    		User::Leave( err );
-	    		}
+            // make sure that when HandlePlaceholdersL leaves unexpectedly, iPHArray is cleared
+            if ( err != KErrNone )
+                {
+                if( err != KErrDiskFull )
+                    {
+                    iContainerPHArray.ResetAndDestroy();
+                    iPHArray.ResetAndDestroy();
+                    iTempReadyPHArray.ResetAndDestroy();
+                    }
+                User::Leave( err );
+                }
 	    	SetNextRequest( ERequestHarvest );
         	}
         break;
@@ -1980,7 +2142,7 @@
 //
 TInt CHarvesterAO::RunError( TInt aError )
     {
-    WRITELOG( "CHarvesterAO::RunError" );
+    WRITELOG1( "CHarvesterAO::RunError, error: %d", aError );
     OstTrace0( TRACE_NORMAL, CHARVESTERAO_RUNERROR, "CHarvesterAO::RunError" );
     
     switch( iNextRequest )
@@ -1989,6 +2151,21 @@
             {
             WRITELOG( "CHarvesterAO::RunError - state ERequestHarvest" );
             OstTrace0( TRACE_NORMAL, DUP1_CHARVESTERAO_RUNERROR, "CHarvesterAO::RunError - state ERequestHarvest" );
+            if( aError == KErrDiskFull || aError == KErrNoMemory )
+                {
+                SetNextRequest( ERequestIdle );
+                }
+            }
+        break;
+        
+        case ERequestContainerPlaceholder:
+            {
+            WRITELOG( "CHarvesterAO::RunError - state ERequestContainerPlaceholder" );
+            OstTrace0( TRACE_NORMAL, DUP5_CHARVESTERAO_RUNERROR, "CHarvesterAO::RunError - state ERequestContainerPlaceholder" );
+            if( aError == KErrDiskFull || aError == KErrNoMemory )
+                {
+                SetNextRequest( ERequestIdle );
+                }
             }
         break;
         
@@ -2105,14 +2282,14 @@
     
     if( MMdSHarvesterDiskSpaceObserver::EMore == aDiskSpaceDirection )
         {
-        WRITELOG("CHarvesterAO::HandleDiskSpaceNotificationL() - disk full");
-        OstTrace0( TRACE_NORMAL, DUP1_CHARVESTERAO_HANDLEDISKSPACENOTIFICATIONL, "CHarvesterAO::HandleDiskSpaceNotificationL - disk full" );        
+        WRITELOG("CHarvesterAO::HandleDiskSpaceNotificationL() - disk space available");
+        OstTrace0( TRACE_NORMAL, DUP2_CHARVESTERAO_HANDLEDISKSPACENOTIFICATIONL, "CHarvesterAO::HandleDiskSpaceNotificationL - disk space available" );
         iDiskFull = EFalse;
         }
     else
         {
-        WRITELOG("CHarvesterAO::HandleDiskSpaceNotificationL() - disk space available");
-        OstTrace0( TRACE_NORMAL, DUP2_CHARVESTERAO_HANDLEDISKSPACENOTIFICATIONL, "CHarvesterAO::HandleDiskSpaceNotificationL - disk space available" );
+        WRITELOG("CHarvesterAO::HandleDiskSpaceNotificationL() - disk full");
+        OstTrace0( TRACE_NORMAL, DUP1_CHARVESTERAO_HANDLEDISKSPACENOTIFICATIONL, "CHarvesterAO::HandleDiskSpaceNotificationL - disk full" );        
         iDiskFull = ETrue;
         if( iServerPaused )
             {
@@ -2320,6 +2497,7 @@
     else
         {
         delete hd;
+        hd = NULL;
         err = KErrUnknown;
         }
     
@@ -2327,6 +2505,10 @@
         {
         aMessage.Complete( err );
         }
+    else if( err != KErrNone )
+        {
+        HarvestCompleted( aMessage.Identity(), uri->Des(), err );
+        }
     
     albumIds.Close();
     }
@@ -2517,6 +2699,7 @@
     else
         {
         delete hd;
+        hd = NULL;
         err = KErrUnknown;
         }
 
@@ -2524,6 +2707,10 @@
         {
         aMessage.Complete( err );
         }
+    else if( err != KErrNone )
+        {
+        HarvestCompleted( aMessage.Identity(), uri->Des(), err );
+        }
     
     albumIds.Close();
     }
@@ -2941,25 +3128,6 @@
 	{
 	WRITELOG("CHarvesterAO::BootScanL() - begin");
     OstTrace0( TRACE_NORMAL, CHARVESTERAO_BOOTSCANL, "CHarvesterAO::BootScanL - begin" );
-    	
-    TInt drive( -1 );
-    TInt massStorageError( DriveInfo::GetDefaultDrive( DriveInfo::EDefaultMassStorage, drive ) );
-    if( massStorageError == KErrNone )
-        {
-        TVolumeInfo massStorageVolumeInfo;
-        iFs.Volume( massStorageVolumeInfo, drive );
-        const TUint32 massStorageMediaId( massStorageVolumeInfo.iUniqueID );
-        massStorageError = DriveInfo::GetDefaultDrive( DriveInfo::EDefaultRemovableMassStorage, drive );
-        if( massStorageError == KErrNone )
-            {
-            iFs.Volume( massStorageVolumeInfo, drive );
-            // Update mass storage media id if the mass storage is not memory card
-            if( massStorageVolumeInfo.iUniqueID != massStorageMediaId && massStorageMediaId != 0 )
-                {
-                iMdEHarvesterSession->CheckMassStorageMediaId( massStorageMediaId );
-                }
-            }
-        }
 	
 	TVolumeInfo volumeInfo;
 	iFs.Volume( volumeInfo, EDriveC );
@@ -3041,9 +3209,11 @@
 						WRITELOG("CHarvesterAO::BootScanL() - scanFolders.AppendL");
 						OstTrace0( TRACE_NORMAL, DUP2_CHARVESTERAO_BOOTSCANL, "CHarvesterAO::BootScanL - scanFolders.AppendL" );
 						TScanItem* item = new (ELeave) TScanItem();
+						CleanupStack::PushL( item );
 						item->iPath = name->AllocL();
 						item->iPreinstalled = MdeConstants::MediaObject::ENotPreinstalled;
-						aScanItems.AppendL( item );
+						CleanupStack::Pop( item );
+						aScanItems.AppendL( item ); // ownership is transferred
 						}
 					}
 				else
@@ -3103,7 +3273,12 @@
 	                        hd->SetClientData( phData );
 
 	                        CleanupStack::Pop( phData );
-	                        hdArray.Append( hd );
+							
+	                        if(hdArray.Append( hd ) != KErrNone )
+	                            {
+                                delete hd;
+                                hd = NULL;
+	                            }
 						    }
 						CleanupStack::PopAndDestroy( &results );
 						CleanupStack::PopAndDestroy( &fileInfos );
@@ -3128,8 +3303,6 @@
 
 	iMdEHarvesterSession->RemoveFilesNotPresent( volumeInfo.iUniqueID, ETrue );
 	
-	iMassMemoryIdChecked = ETrue;
-	
 	WRITELOG("CHarvesterAO::BootScanL() - end");
 	OstTrace0( TRACE_NORMAL, DUP5_CHARVESTERAO_BOOTSCANL, "CHarvesterAO::BootScanL - end" );
 	}