--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/src/clientdll/featurenotifier.cpp Fri Jan 22 11:06:30 2010 +0200
@@ -0,0 +1,311 @@
+// Copyright (c) 2007-2009 Nokia Corporation and/or its subsidiary(-ies).
+// All rights reserved.
+// This component and the accompanying materials are made available
+// under the terms of "Eclipse Public License v1.0"
+// which accompanies this distribution, and is available
+// at the URL "http://www.eclipse.org/legal/epl-v10.html".
+//
+// Initial Contributors:
+// Nokia Corporation - initial contribution.
+//
+// Contributors:
+//
+// Description:
+//
+
+
+
+// INCLUDE FILES
+#include <featmgr/featurenotifier.h>
+#include "featmgrdebug.h"
+#include <featmgr/featurecmn.h>
+#include "featmgrclient.h"
+
+// ============================= LOCAL FUNCTIONS ===============================
+
+// -----------------------------------------------------------------------------
+// FindByUid
+// Returns Zero if UIDs do match.
+// -----------------------------------------------------------------------------
+//
+static TInt FindByUid( const TUid* aFeature, const TUid& aItem )
+ {
+ if ( aFeature->iUid == aItem.iUid )
+ {
+ return 1;
+ }
+
+ return 0;
+ }
+
+
+// ============================ MEMBER FUNCTIONS ===============================
+
+// -----------------------------------------------------------------------------
+// CFeatureNotifier::CFeatureNotifier()
+// -----------------------------------------------------------------------------
+//
+CFeatureNotifier::CFeatureNotifier( MFeatureObserver& aObserver ) :
+ CActive( EPriorityStandard ),
+ iObserver( aObserver )
+ {
+ }
+
+// -----------------------------------------------------------------------------
+// CFeatureNotifier::NewL()
+// Two-phased constructor.
+// -----------------------------------------------------------------------------
+//
+EXPORT_C CFeatureNotifier* CFeatureNotifier::NewL( MFeatureObserver& aObserver )
+ {
+ CFeatureNotifier* self = new( ELeave ) CFeatureNotifier( aObserver );
+ CleanupStack::PushL( self );
+ self->ConstructL();
+ CleanupStack::Pop( self );
+ return self;
+ }
+
+// -----------------------------------------------------------------------------
+// CFeatureNotifier::ConstructL
+// -----------------------------------------------------------------------------
+//
+void CFeatureNotifier::ConstructL()
+ {
+ FUNC_LOG
+
+ iFeatMgrClient = new (ELeave) RFeatMgrClient;
+ // Connect to Feature Manager server
+ TInt err( iFeatMgrClient->Connect() );
+ User::LeaveIfError(err);
+
+ CActiveScheduler::Add( this );
+ }
+
+// -----------------------------------------------------------------------------
+// CFeatureNotifier::~CFeatureNotifier()
+// -----------------------------------------------------------------------------
+//
+EXPORT_C CFeatureNotifier::~CFeatureNotifier()
+ {
+ FUNC_LOG
+
+ if( iFeatMgrClient )
+ {
+ iFeatMgrClient->RequestNotifyCancelAll();
+ iFeatMgrClient->Close();
+ delete iFeatMgrClient;
+ }
+ Cancel();
+
+ iFeatures.Close();
+ }
+
+// -----------------------------------------------------------------------------
+// CFeatureNotifier::NotifyRequest(TUid)
+// -----------------------------------------------------------------------------
+//
+EXPORT_C TInt CFeatureNotifier::NotifyRequest( TUid aFeature )
+ {
+ if(IsActive())
+ {
+ return KErrAlreadyExists;
+ }
+
+ iFeatures.Reset();
+ iFeatures.Append( aFeature );
+ TInt err = iFeatMgrClient->RequestNotification( iFeatures, iFeatureChanged, iStatus );
+ if ( err == KErrNone )
+ {
+ SetActive();
+ }
+
+ return err;
+ }
+
+// -----------------------------------------------------------------------------
+// CFeatureNotifier::NotifyRequest(RFeatureUidArray&)
+// -----------------------------------------------------------------------------
+//
+EXPORT_C TInt CFeatureNotifier::NotifyRequest( RFeatureUidArray& aFeatures )
+ {
+ if(IsActive())
+ {
+ return KErrAlreadyExists;
+ }
+
+ iFeatures.Reset();
+ TInt count = aFeatures.Count();
+
+ for(TInt i = 0; i < count; i++ )
+ {
+ // Do not append duplicate entries
+ const TUid& uid( aFeatures[i] );
+ TInt index = iFeatures.Find( uid, FindByUid );
+ if( index == KErrNotFound )
+ {
+ iFeatures.Append( uid );
+ }
+ }
+
+ TInt err = iFeatMgrClient->RequestNotification( iFeatures, iFeatureChanged, iStatus );
+ if ( err == KErrNone )
+ {
+ SetActive();
+ }
+
+ return err;
+ }
+
+// -----------------------------------------------------------------------------
+// CFeatureNotifier::NotifyCancel(TUid aFeature)
+// -----------------------------------------------------------------------------
+//
+EXPORT_C TInt CFeatureNotifier::NotifyCancel( TUid aFeature )
+ {
+ TInt err( KErrNotFound );
+ TInt count = iFeatures.Count();
+
+ for(TInt i = 0; i < count; i++ )
+ {
+ if( iFeatures[i].iUid == aFeature.iUid )
+ {
+ err = iFeatMgrClient->RequestNotifyCancel( aFeature );
+
+ if( err == KErrNone )
+ {
+ iFeatures.Remove( i );
+ // If this is the last feature in the list, then also cancel the Active Object
+ if( 0 == iFeatures.Count() )
+ {
+ Cancel();
+ }
+ break;
+ }
+ }
+ }
+
+ return err;
+ }
+
+// -----------------------------------------------------------------------------
+// CFeatureNotifier::NotifyCancelAll()
+// -----------------------------------------------------------------------------
+//
+EXPORT_C TInt CFeatureNotifier::NotifyCancelAll()
+ {
+ iFeatures.Reset();
+ TInt err = iFeatMgrClient->RequestNotifyCancelAll( );
+ Cancel();
+
+ return err;
+ }
+
+/**
+ Gets the number of features in the server's array.
+ This API is only for internal use and testing purposes.
+
+ @return The number of features on the server for debug builds, otherwise it returns KErrNotSupported in release builds.
+ @internalComponent
+*/
+EXPORT_C TInt CFeatureNotifier::NumberOfNotifyFeatures()
+ {
+#ifdef EXTENDED_FEATURE_MANAGER_TEST
+ TInt count = iFeatMgrClient->NumberOfNotifyFeatures();
+ return count;
+#else
+ return KErrNotSupported;
+#endif
+ }
+
+/**
+ Gets the number of heap cells in the thread.
+ This API is only for internal use and testing purposes.
+
+ @return The number of heap cells for debug build, otherwise it returns KErrNotSupported in release builds.
+ @internalComponent
+*/
+EXPORT_C TInt CFeatureNotifier::CountAllocCells()
+ {
+#ifdef EXTENDED_FEATURE_MANAGER_TEST
+ TInt count = iFeatMgrClient->CountAllocCells();
+ return count;
+#else
+ return KErrNotSupported;
+#endif
+ }
+
+// -----------------------------------------------------------------------------
+// CFeatureNotifier::RunL()
+// -----------------------------------------------------------------------------
+//
+void CFeatureNotifier::RunL( )
+ {
+ FUNC_LOG
+
+ TInt status = iStatus.Int();
+ if( status < 0 )
+ {
+ // Got an error
+ if( status != KErrCancel )
+ {
+ iObserver.HandleNotifyError( status );
+ }
+ return;
+ }
+
+ // iStatus >= 0 means it contains the change type
+ TFeatureChangeType changeType = static_cast<TFeatureChangeType>(status);
+
+ // If the feature was deleted, remove it from the array of features with notifications requested
+ if( changeType == EFeatureFeatureDeleted )
+ {
+ TInt index = iFeatures.Find( iFeatureChanged, FindByUid );
+ if( index != KErrNotFound )
+ {
+ iFeatures.Remove( index );
+ }
+ }
+ // Should we validate whether iFeatureChanged matches
+ // to any UID in the array of requested features?
+
+ TFeatureEntry feature( iFeatureChanged );
+ if( iFeatures.Count() > 0 )
+ {
+ // Asynchronously resubscribe notify request
+ iFeatMgrClient->ReRequestNotification( iFeatureChanged, iStatus );
+ // Next inform client about changed feature
+ // Should we validate whether iFeatureChanged matches
+ // to any UID in the array of requested features
+ iObserver.HandleNotifyChange( changeType, feature );
+ // Set us active
+ SetActive();
+ }
+ else
+ {
+ // All features with notifications requested were deleted,
+ // so don't need to resubscribe notify request -
+ // just notify client about the deleted feature
+ iObserver.HandleNotifyChange( changeType, feature );
+ }
+ }
+
+// -----------------------------------------------------------------------------
+// CFeatureNotifier::DoCancel()
+// -----------------------------------------------------------------------------
+//
+void CFeatureNotifier::DoCancel( )
+ {
+ }
+
+// -----------------------------------------------------------------------------
+// CFeatureNotifier::RunError()
+// -----------------------------------------------------------------------------
+//
+TInt CFeatureNotifier::RunError( TInt aError )
+ {
+ iObserver.HandleNotifyError( aError );
+
+ return KErrNone;
+ }
+
+// End of File