mtpdataproviders/mtpfileandfolderdp/src/cmtpfiledp.cpp
changeset 0 d0791faffa3f
child 1 f8e15b44d440
equal deleted inserted replaced
-1:000000000000 0:d0791faffa3f
       
     1 // Copyright (c) 2006-2009 Nokia Corporation and/or its subsidiary(-ies).
       
     2 // All rights reserved.
       
     3 // This component and the accompanying materials are made available
       
     4 // under the terms of "Eclipse Public License v1.0"
       
     5 // which accompanies this distribution, and is available
       
     6 // at the URL "http://www.eclipse.org/legal/epl-v10.html".
       
     7 //
       
     8 // Initial Contributors:
       
     9 // Nokia Corporation - initial contribution.
       
    10 //
       
    11 // Contributors:
       
    12 //
       
    13 // Description:
       
    14 //
       
    15 
       
    16 #include <mtp/cmtpstoragemetadata.h>
       
    17 #include <mtp/mmtpconnection.h>
       
    18 #include <mtp/mmtpdataproviderframework.h>
       
    19 #include <mtp/mtpdataproviderapitypes.h>
       
    20 #include <mtp/mtpprotocolconstants.h>
       
    21 #include <ecom/ecom.h>
       
    22 
       
    23 #include "cmtpfiledp.h"
       
    24 #include "cmtpfiledpexclusionmgr.h"
       
    25 #include "cmtpfsenumerator.h"
       
    26 #include "cmtpfiledpconfigmgr.h"
       
    27 #include "cmtprequestprocessor.h"
       
    28 #include "mtpfiledpconst.h"
       
    29 #include "mtpfiledppanic.h"
       
    30 #include "mtpfiledpprocessor.h"
       
    31 
       
    32 // Class constants
       
    33 static const TInt KArrayGranularity = 3;
       
    34 static const TInt KActiveEnumeration = 0;
       
    35 __FLOG_STMT(_LIT8(KComponent,"CMTPFileDataProvider");)
       
    36 
       
    37 /**
       
    38 File data provider factory method.
       
    39 @return A pointer to a file data provider object. Ownership IS transfered.
       
    40 @leave One of the system wide error codes, if a processing failure occurs.
       
    41 */
       
    42 TAny* CMTPFileDataProvider::NewL(TAny* aParams)
       
    43     {
       
    44     CMTPFileDataProvider* self = new (ELeave) CMTPFileDataProvider(aParams);
       
    45     CleanupStack::PushL(self);
       
    46     self->ConstructL();
       
    47     CleanupStack::Pop(self);
       
    48     return self;
       
    49     }
       
    50 
       
    51 /**
       
    52 Destructor
       
    53 */    
       
    54 CMTPFileDataProvider::~CMTPFileDataProvider()
       
    55     {
       
    56     __FLOG(_L8("~CMTPFileDataProvider - Entry"));
       
    57     iPendingEnumerations.Close();
       
    58     TUint count(iActiveProcessors.Count());
       
    59     while (count--)
       
    60         {
       
    61         iActiveProcessors[count]->Release();
       
    62         }
       
    63     iActiveProcessors.Close();
       
    64     iDpSingletons.Close();
       
    65 	iFileDPSingletons.Close();
       
    66     delete iFileEnumerator;
       
    67     delete iExclusionMgr;
       
    68     __FLOG(_L8("~CMTPFileDataProvider - Exit"));
       
    69     __FLOG_CLOSE; 
       
    70     }
       
    71 
       
    72 void CMTPFileDataProvider::Cancel()
       
    73     {
       
    74     __FLOG(_L8("Cancel - Entry"));
       
    75     iFileEnumerator->Cancel();
       
    76     __FLOG(_L8("Cancel - Exit"));
       
    77     }
       
    78         
       
    79 void CMTPFileDataProvider::ProcessEventL(const TMTPTypeEvent& aEvent, MMTPConnection& aConnection)
       
    80     {
       
    81     __FLOG(_L8("ProcessEventL - Entry"));
       
    82     TInt idx(LocateRequestProcessorL(aEvent, aConnection));
       
    83     
       
    84     if (idx != KErrNotFound)
       
    85         {
       
    86         iActiveProcessors[idx]->HandleEventL(aEvent);
       
    87         }
       
    88     __FLOG(_L8("ProcessEventL - Exit"));
       
    89     }
       
    90      
       
    91 void CMTPFileDataProvider::ProcessNotificationL(TMTPNotification aNotification, const TAny* aParams)
       
    92     {
       
    93     __FLOG(_L8("ProcessNotificationL - Entry"));
       
    94     switch (aNotification)
       
    95         {
       
    96     case EMTPSessionClosed:
       
    97         SessionClosedL(*reinterpret_cast<const TMTPNotificationParamsSessionChange*>(aParams));
       
    98         break;
       
    99         
       
   100     case EMTPSessionOpened:
       
   101         SessionOpenedL(*reinterpret_cast<const TMTPNotificationParamsSessionChange*>(aParams));
       
   102         break;
       
   103         
       
   104     default:
       
   105         // Ignore all other notifications.
       
   106         break;
       
   107         }
       
   108     __FLOG(_L8("ProcessNotificationL - Exit"));
       
   109     }
       
   110         
       
   111 void CMTPFileDataProvider::ProcessRequestPhaseL(TMTPTransactionPhase aPhase, const TMTPTypeRequest& aRequest, MMTPConnection& aConnection)
       
   112     {    
       
   113     __FLOG(_L8("ProcessRequestPhaseL - Entry"));
       
   114     TInt idx(LocateRequestProcessorL(aRequest, aConnection));
       
   115     __ASSERT_DEBUG((idx != KErrNotFound), Panic(EMTPFileDpNoMatchingProcessor));
       
   116     MMTPRequestProcessor* processor(iActiveProcessors[idx]);
       
   117     iActiveProcessor = idx;
       
   118     iActiveProcessorRemoved = EFalse;
       
   119     TBool result(processor->HandleRequestL(aRequest, aPhase));
       
   120     if (iActiveProcessorRemoved)
       
   121 	    {
       
   122 	    processor->Release(); // destroy the processor
       
   123 	    }
       
   124     else if (result)
       
   125 	    {
       
   126 	    processor->Release();    	
       
   127 	    iActiveProcessors.Remove(idx);
       
   128 	    }
       
   129     iActiveProcessor = -1;
       
   130 
       
   131     __FLOG(_L8("ProcessRequestPhaseL - Exit"));
       
   132     }
       
   133     
       
   134 void CMTPFileDataProvider::StartObjectEnumerationL(TUint32 aStorageId, TBool /*aPersistentFullEnumeration*/)
       
   135     {
       
   136     __FLOG(_L8("StartObjectEnumerationL - Entry"));
       
   137 
       
   138     iExclusionMgr->AppendFormatExclusionListL();
       
   139     iDpSingletons.MTPUtility().FormatExtensionMapping();
       
   140     iPendingEnumerations.AppendL(aStorageId);
       
   141     if (iPendingEnumerations.Count() == 1)
       
   142         {
       
   143         iFileEnumerator->StartL(iPendingEnumerations[KActiveEnumeration]);
       
   144         }
       
   145     __FLOG(_L8("StartObjectEnumerationL - Exit"));
       
   146     }
       
   147     
       
   148 void CMTPFileDataProvider::StartStorageEnumerationL()
       
   149     {
       
   150     __FLOG(_L8("StartStorageEnumerationL - Entry"));
       
   151     Framework().StorageEnumerationCompleteL();
       
   152     __FLOG(_L8("StartStorageEnumerationL - Exit"));
       
   153     }
       
   154     
       
   155 void CMTPFileDataProvider::Supported(TMTPSupportCategory aCategory, RArray<TUint>& aArray) const
       
   156     {
       
   157     __FLOG(_L8("Supported - Entry"));
       
   158     switch (aCategory) 
       
   159         {        
       
   160     case EEvents:
       
   161         break;
       
   162         
       
   163     case EObjectCaptureFormats:
       
   164     case EObjectPlaybackFormats:
       
   165         aArray.Append(EMTPFormatCodeUndefined);
       
   166         
       
   167         /**
       
   168          * [SP-Format-0x3002]Special processing for PictBridge DP which own 6 dps file with format 0x3002, 
       
   169          * but it does not really own the format 0x3002.
       
   170          */
       
   171         if( PictbridgeDpExistL() )
       
   172         	{
       
   173         	aArray.Append(EMTPFormatCodeScript);
       
   174         	}
       
   175         break;
       
   176         
       
   177     case EObjectProperties:
       
   178         {
       
   179         TInt count(sizeof(KMTPFileDpSupportedProperties) / sizeof(KMTPFileDpSupportedProperties[0]));
       
   180         for (TInt i(0); (i < count); i++)
       
   181             {
       
   182             aArray.Append(KMTPFileDpSupportedProperties[i]);
       
   183             }   
       
   184         }
       
   185         break; 
       
   186         
       
   187     case EOperations:
       
   188         {
       
   189         TInt count(sizeof(KMTPFileDpSupportedOperations) / sizeof(KMTPFileDpSupportedOperations[0]));
       
   190         for (TInt i(0); (i < count); i++)
       
   191             {
       
   192             aArray.Append(KMTPFileDpSupportedOperations[i]);
       
   193             }   
       
   194         }
       
   195         break;  
       
   196         
       
   197     case EStorageSystemTypes:
       
   198         aArray.Append(CMTPStorageMetaData::ESystemTypeDefaultFileSystem);
       
   199         break; 
       
   200         
       
   201     default:
       
   202     
       
   203         // Unrecognised category, leave aArray unmodified.
       
   204         break;
       
   205         }
       
   206     __FLOG(_L8("Supported - Exit"));
       
   207     }    
       
   208        
       
   209 #ifdef __FLOG_ACTIVE  
       
   210 void CMTPFileDataProvider::NotifyEnumerationCompleteL(TUint32 aStorageId, TInt aError)
       
   211 #else
       
   212 void CMTPFileDataProvider::NotifyEnumerationCompleteL(TUint32 /*aStorageId*/, TInt /*aError*/)
       
   213 #endif // __FLOG_ACTIVE
       
   214     {
       
   215     __FLOG(_L8("HandleEnumerationCompletedL - Entry"));
       
   216     __FLOG_VA((_L8("Enumeration of storage 0x%08X completed with error status %d"), aStorageId, aError));
       
   217     __ASSERT_DEBUG((aStorageId == iPendingEnumerations[KActiveEnumeration]), User::Invariant());
       
   218     
       
   219     Framework().ObjectEnumerationCompleteL(iPendingEnumerations[KActiveEnumeration]);
       
   220     iPendingEnumerations.Remove(KActiveEnumeration);
       
   221     if (iPendingEnumerations.Count())
       
   222         {
       
   223         iFileEnumerator->StartL(iPendingEnumerations[KActiveEnumeration]);
       
   224         }
       
   225     __FLOG(_L8("HandleEnumerationCompletedL - Exit"));
       
   226     }
       
   227     
       
   228 /**
       
   229 Standard C++ constructor
       
   230 */
       
   231 CMTPFileDataProvider::CMTPFileDataProvider(TAny* aParams) :
       
   232     CMTPDataProviderPlugin(aParams),
       
   233     iActiveProcessors(KArrayGranularity),
       
   234     iPendingEnumerations(KArrayGranularity),
       
   235     iActiveProcessor(-1)
       
   236     {
       
   237 
       
   238     }
       
   239 
       
   240 /**
       
   241 Second-phase constructor.
       
   242 */    
       
   243 void CMTPFileDataProvider::ConstructL()
       
   244     {
       
   245     __FLOG_OPEN(KMTPSubsystem, KComponent);  
       
   246     __FLOG(_L8("ConstructL - Entry"));
       
   247   	iDpSingletons.OpenL(Framework());
       
   248   	iFileDPSingletons.OpenL(Framework());
       
   249   	
       
   250   	iExclusionMgr = CMTPFileDpExclusionMgr::NewL(Framework());
       
   251   	iDpSingletons.SetExclusionMgrL(*iExclusionMgr);
       
   252   	
       
   253   	TUint processLimit = iFileDPSingletons.FrameworkConfig().UintValueL(CMTPFileDpConfigMgr::EEnumerationIterationLength);
       
   254     iFileEnumerator = CMTPFSEnumerator::NewL(Framework(), iDpSingletons.ExclusionMgrL(), *this, processLimit);
       
   255     __FLOG(_L8("ConstructL - Exit"));
       
   256     }
       
   257 
       
   258 /**
       
   259 Find or create a request processor that can process the specified request.
       
   260 @param aRequest    The request to be processed
       
   261 @param aConnection The connection from which the request comes
       
   262 @return the idx of the found/created request processor
       
   263 */    
       
   264 TInt CMTPFileDataProvider::LocateRequestProcessorL(const TMTPTypeRequest& aRequest, MMTPConnection& aConnection)
       
   265     {
       
   266     __FLOG(_L8("LocateRequestProcessorL - Entry"));  
       
   267     TInt idx(KErrNotFound);
       
   268     TInt count(iActiveProcessors.Count());
       
   269     for (TInt i(0); (i < count); i++)
       
   270         {
       
   271         if (iActiveProcessors[i]->Match(aRequest, aConnection))
       
   272             {
       
   273             idx = i;
       
   274             break;
       
   275             }
       
   276         }
       
   277         
       
   278     if (idx == KErrNotFound)
       
   279         {
       
   280         MMTPRequestProcessor* processor = MTPFileDpProcessor::CreateL(Framework(), aRequest, aConnection);
       
   281         CleanupReleasePushL(*processor);
       
   282         iActiveProcessors.AppendL(processor);
       
   283         CleanupStack::Pop();
       
   284         idx = count;
       
   285         }
       
   286         
       
   287     __FLOG(_L8("LocateRequestProcessorL - Exit"));
       
   288     return idx;
       
   289     }
       
   290 
       
   291 /**
       
   292 Find or create a request processor that can process the specified event.
       
   293 @param aEvent    The event to be processed
       
   294 @param aConnection The connection from which the request comes
       
   295 @return the idx of the found request processor, KErrNotFound if not found
       
   296 */    
       
   297 TInt CMTPFileDataProvider::LocateRequestProcessorL(const TMTPTypeEvent& aEvent, MMTPConnection& aConnection)
       
   298     {
       
   299     __FLOG(_L8("LocateRequestProcessorL - Entry"));
       
   300     TInt idx(KErrNotFound);
       
   301     TInt count(iActiveProcessors.Count());
       
   302     for (TInt i(0); (i < count); i++)
       
   303         {
       
   304         if (iActiveProcessors[i]->Match(aEvent, aConnection))
       
   305             {
       
   306             idx = i;
       
   307             break;
       
   308             }
       
   309         }    
       
   310     __FLOG(_L8("LocateRequestProcessorL - Exit"));
       
   311     return idx;    
       
   312     }
       
   313 
       
   314 /**
       
   315 Cleans up outstanding request processors when a session is closed.
       
   316 @param aSession notification parameter block
       
   317 */
       
   318 void CMTPFileDataProvider::SessionClosedL(const TMTPNotificationParamsSessionChange& aSession)
       
   319     {
       
   320     __FLOG(_L8("SessionClosedL - Entry"));
       
   321     TInt count = iActiveProcessors.Count();
       
   322     while(count--)
       
   323         {
       
   324         MMTPRequestProcessor* processor = iActiveProcessors[count];
       
   325         TUint32 sessionId = processor->SessionId();
       
   326         if((sessionId == aSession.iMTPId) && (processor->Connection().ConnectionId() == aSession.iConnection.ConnectionId()))
       
   327             {
       
   328             iActiveProcessors.Remove(count);
       
   329             if (count == iActiveProcessor)
       
   330         		{
       
   331         		iActiveProcessorRemoved = ETrue;
       
   332         		}
       
   333         	else
       
   334 	       		{
       
   335         		processor->Release();
       
   336 	       		}
       
   337             }
       
   338         } 
       
   339     __FLOG(_L8("SessionClosedL - Exit"));   
       
   340     }
       
   341 
       
   342 /**
       
   343 Prepares for a newly-opened session.
       
   344 @param aSession notification parameter block
       
   345 */
       
   346 #ifdef __FLOG_ACTIVE
       
   347 void CMTPFileDataProvider::SessionOpenedL(const TMTPNotificationParamsSessionChange& aSession)
       
   348 #else
       
   349 void CMTPFileDataProvider::SessionOpenedL(const TMTPNotificationParamsSessionChange& /*aSession*/)
       
   350 #endif
       
   351     {
       
   352     __FLOG(_L8("SessionOpenedL - Entry"));
       
   353     __FLOG_VA((_L8("SessionID = %d"), aSession.iMTPId));
       
   354     __FLOG(_L8("SessionOpenedL - Exit"));
       
   355     }
       
   356 
       
   357 /**
       
   358  * [SP-Format-0x3002]Special processing for PictBridge DP which own 6 dps file with format 0x3002, 
       
   359  * but it does not really own the format 0x3002.
       
   360  * 
       
   361  * Check whether the Pictbridgedp exists or not.
       
   362  */
       
   363 TBool CMTPFileDataProvider::PictbridgeDpExistL() const
       
   364 	{
       
   365     __FLOG(_L8("PictbridgeDpExistL - Entry"));
       
   366     
       
   367 	RImplInfoPtrArray   implementations;
       
   368 	TCleanupItem        cleanup(ImplementationsCleanup, reinterpret_cast<TAny*>(&implementations));
       
   369 	CleanupStack::PushL(cleanup);
       
   370 	REComSession::ListImplementationsL(KMTPDataProviderPluginInterfaceUid, implementations);
       
   371 	
       
   372 	TBool ret = EFalse;
       
   373 	const TUint KUidPictBridge = 0x2001fe3c;
       
   374 	TInt count = implementations.Count();
       
   375 	while(--count)
       
   376 		{
       
   377 		if(implementations[count]->ImplementationUid().iUid == KUidPictBridge)
       
   378 			{
       
   379 			ret = ETrue;
       
   380 			break;
       
   381 			}
       
   382 		}
       
   383     CleanupStack::PopAndDestroy(&implementations);
       
   384     
       
   385     __FLOG_VA((_L8("return value ret = %d"), ret));
       
   386     __FLOG(_L8("PictbridgeDpExistL - Exit"));
       
   387     return ret;
       
   388 	}
       
   389 
       
   390 /**
       
   391  * [SP-Format-0x3002]Special processing for PictBridge DP which own 6 dps file with format 0x3002, 
       
   392  * but it does not really own the format 0x3002.
       
   393  * 
       
   394  * Cleanup function
       
   395  */
       
   396 void CMTPFileDataProvider::ImplementationsCleanup(TAny* aData)
       
   397     {
       
   398     reinterpret_cast<RImplInfoPtrArray*>(aData)->ResetAndDestroy();
       
   399     }