diff -r d38941471f1c -r cb32bcc88bad sysstatemgmt/systemstatemgr/cmn/src/ssmstateawaresession.cpp --- a/sysstatemgmt/systemstatemgr/cmn/src/ssmstateawaresession.cpp Wed Sep 29 15:13:21 2010 +0300 +++ b/sysstatemgmt/systemstatemgr/cmn/src/ssmstateawaresession.cpp Fri Oct 08 14:33:25 2010 +0300 @@ -1,4 +1,4 @@ -// Copyright (c) 2007-2009 Nokia Corporation and/or its subsidiary(-ies). +// Copyright (c) 2007-2010 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" @@ -25,15 +25,6 @@ @internalComponent @released */ -static void Panic(TInt aReason) - { - User::Panic(KPanicSsmCmn, aReason); - } - -/** - @internalComponent - @released - */ class RSsmStateAwareSession::RPrivateImpl : public RDmDomain { }; @@ -91,7 +82,7 @@ */ EXPORT_C TSsmState RSsmStateAwareSession::State() const { - __ASSERT_ALWAYS(iPimpl, Panic(ECmnErrState)); + __ASSERT_ALWAYS(iPimpl, User::Panic(KPanicSsmCmn, ECmnErrState)); TUint32 ds = 0; //returned TDmDomainState is currently only 8 bits @@ -108,7 +99,7 @@ */ EXPORT_C void RSsmStateAwareSession::RequestStateNotification(TRequestStatus& aStatus) { - __ASSERT_ALWAYS(iPimpl, Panic(ECmnErrRqstStateNotif)); + __ASSERT_ALWAYS(iPimpl, User::Panic(KPanicSsmCmn, ECmnErrRqstStateNotif)); iPimpl->RequestTransitionNotification(aStatus); //lint !e613 Possible use of NULL pointer - caught by ASSERT_ALWAYS } @@ -118,7 +109,7 @@ */ EXPORT_C void RSsmStateAwareSession::RequestStateNotificationCancel() { - __ASSERT_ALWAYS(iPimpl, Panic(ECmnErrRqstStateNotifCancel)); + __ASSERT_ALWAYS(iPimpl, User::Panic(KPanicSsmCmn, ECmnErrRqstStateNotifCancel)); iPimpl->CancelTransitionNotification(); //lint !e613 Possible use of NULL pointer - caught by ASSERT_ALWAYS } @@ -131,7 +122,7 @@ */ EXPORT_C void RSsmStateAwareSession::AcknowledgeStateNotification(TInt aError) { - __ASSERT_ALWAYS(iPimpl, Panic(ECmnErrAcknldgStateNotif)); + __ASSERT_ALWAYS(iPimpl, User::Panic(KPanicSsmCmn, ECmnErrAcknldgStateNotif)); iPimpl->AcknowledgeLastState(aError); //lint !e613 Possible use of NULL pointer - caught by ASSERT_ALWAYS } @@ -143,13 +134,83 @@ */ EXPORT_C void RSsmStateAwareSession::AcknowledgeAndRequestStateNotification(TInt aError, TRequestStatus& aStatus) { - __ASSERT_ALWAYS(iPimpl, Panic(ECmnErrAcknldgRqstStateNotif)); + __ASSERT_ALWAYS(iPimpl, User::Panic(KPanicSsmCmn, ECmnErrAcknldgRqstStateNotif)); //Typical pattern of using P&S is to subscribe first then get current state iPimpl->RequestTransitionNotification(aStatus); //lint !e613 Possible use of NULL pointer - caught by ASSERT_ALWAYS //Tell domain manager that we have processed the last state change. iPimpl->AcknowledgeLastState(aError); //lint !e613 Possible use of NULL pointer - caught by ASSERT_ALWAYS } +#ifdef SYMBIAN_INCLUDE_APP_CENTRIC +/** +Defers the acknowledgement requesting more time. +To be sure of deferring in time a client should call this immediately +after receiving notification. This asynchronous call will complete once the original deadline +is reached (ie. one period earlier than the final deadline), at which point the member must either +defer again or acknowledge the transition. In the meantime, the member should perform +its transition actions, whilst remaining responsive to new completion events. + +@note Deferrals are not always possible, +whether the member will actually be given more time depends on if + - The current transition allows deferrals at all. + - The member still has deferrals left - there may be a maximum number + allowed. + - The deferral request was received in time. + +@param aStatus Status of request + - KErrNone Request has completed i.e. The member must either defer again or acknowledge. + - KErrCompletion The deferral was obsoleted by a subsequent call to AcknowledgeLastState. + - KErrNotSupported The current transition may not be deferred, or maximum deferral count reached. + - KErrCancel The deferral was cancelled. + - KErrNotReady Deferral attempted before a transition notification was received + or after the deadline for the previous one. + - KErrPermissionDenied The member lacked the necessary capabilities. + - KErrAlreadyExists A deferral was already outstanding. + Both new and existing calls will complete with this error. + +This function is provided for members to inform the Domain Manager that they +are still active and are responding to a transition notification. +For example, a server may have to persist data using +the file server before shut down. Since this task should be allowed to complete +before shutdown continues, the member should defer the transition, and then persist +the data, using asynchronous calls. + +At least one of the below capabilities is required in order to defer a +domain transition. Without them, the client will get KErrPermissionDenied. + +@capability WriteDeviceData +@capability ProtServ + +@pre The member has been notified of a transition which it has not yet acknowledged. + */ +EXPORT_C void RSsmStateAwareSession::DeferAcknowledgement(TRequestStatus& aStatus) + { + __ASSERT_ALWAYS(iPimpl, User::Panic(KPanicSsmCmn, ECmnErrDeferAcknNotif)); + iPimpl->DeferAcknowledgement(aStatus); //lint !e613 Possible use of NULL pointer - caught by ASSERT_ALWAYS + + } + +/** +Cancels the deferred call. +Will cancel a call of DeferAcknowledgement, if one was pending. +If none was pending, it does nothing. +*/ +EXPORT_C void RSsmStateAwareSession::CancelDeferral() + { + __ASSERT_ALWAYS(iPimpl, User::Panic(KPanicSsmCmn, ECmnErrCancelDeferNotif)); + iPimpl->CancelDeferral(); //lint !e613 Possible use of NULL pointer - caught by ASSERT_ALWAYS + } +#else +EXPORT_C void RSsmStateAwareSession::DeferAcknowledgement(TRequestStatus& aStatus) + { + TRequestStatus* pStatus = &aStatus; + User::RequestComplete(pStatus, KErrNotSupported); + } + +EXPORT_C void RSsmStateAwareSession::CancelDeferral() + { + } +#endif // //---------------- class CSsmStateAwareSession ------------------ // @@ -218,7 +279,7 @@ */ EXPORT_C TSsmState CSsmStateAwareSession::State() const { - __ASSERT_ALWAYS(iMonitor, Panic(ECmnErrStateMon)); + __ASSERT_ALWAYS(iMonitor, User::Panic(KPanicSsmCmn, ECmnErrStateMon)); return iMonitor->State(); } @@ -270,3 +331,178 @@ #endif } } //lint !e1746 Suppress parameter 'aSsmState' could be made const reference + +// +//---------------- class CExtendedSsmStateAwareSession ------------------ +// +#ifdef SYMBIAN_INCLUDE_APP_CENTRIC +/** +Factory method that returns an instance of this object, connected to the domain +identified by the specified domain Id and setup to subscribe on System State changes. +@param aDomainId The Id of the domain to connect to. +@param aSubscriber reference to MStateChangeNotificationSubscriber2 +*/ +EXPORT_C CSsmStateAwareSession2* CSsmStateAwareSession2::NewL(TDmDomainId aDomainId, MStateChangeNotificationSubscriber2& aSubscriber) + { + CSsmStateAwareSession2* self = new (ELeave)CSsmStateAwareSession2(aSubscriber); + CleanupStack::PushL(self); + self->ConstructL(aDomainId); + CleanupStack::Pop(self); + return self; + } + +CSsmStateAwareSession2::CSsmStateAwareSession2(MStateChangeNotificationSubscriber2& aSubscriber): +CActive(CActive::EPriorityStandard), iDeferNotification(NULL), iSubscriber(&aSubscriber) + { + CActiveScheduler::Add(this); + } + +void CSsmStateAwareSession2::ConstructL(TDmDomainId aDomainId) + { + User::LeaveIfError(iSsmStateAwareSession.Connect(aDomainId)); + iDeferNotification = new (ELeave) CSsmDeferralMonitor(iSsmStateAwareSession, *this); + + } +/** +Destructor. +Cleanup the internal CSsmDeferralMonitor active object. +*/ +EXPORT_C CSsmStateAwareSession2::~CSsmStateAwareSession2() + { + Cancel(); + delete iDeferNotification; + iSsmStateAwareSession.Close(); + } + +/** + Gets the TSsmState state. + */ +EXPORT_C TSsmState CSsmStateAwareSession2::GetState() + { + return iSsmStateAwareSession.State(); + } + +/** + Use to get a notification when the System State changes. + */ +EXPORT_C void CSsmStateAwareSession2::RequestStateNotification() + { + __ASSERT_ALWAYS(!IsActive(), User::Panic(KPanicSsmCmn, ECmnErrRqstStateNotif)); + iSsmStateAwareSession.RequestStateNotification(iStatus); + SetActive(); + } + +/** + Cancels an outstanding RequestStateNotification operation. + */ +EXPORT_C void CSsmStateAwareSession2::RequestStateNotificationCancel() + { + iDeferNotification->Cancel(); + iSsmStateAwareSession.RequestStateNotificationCancel(); + } + +/** + Acknowledges the state change. + An application must acknowledge that it has performed all actions required by the last known state of the domain. + @param set aError while acknowledging. + */ +EXPORT_C void CSsmStateAwareSession2::AcknowledgeStateNotification(TInt aError) + { + iSsmStateAwareSession.AcknowledgeStateNotification(aError); + iDeferNotification->NotifyOfAcknowledgement(); + } + +/** + Acknowledges the state change. + An application must acknowledge that it has performed all actions required by the last known state of the domain. + This function appears like an atomic function and minimize the risk for missing a state notification. + @param aError for aknowledging with error. + */ +EXPORT_C void CSsmStateAwareSession2::AcknowledgeAndRequestStateNotification(TInt aError) + { + __ASSERT_ALWAYS(!IsActive(), User::Panic(KPanicSsmCmn, ECmnErrAcknldgRqstStateNotif)); + iSsmStateAwareSession.AcknowledgeAndRequestStateNotification(aError,iStatus); + iDeferNotification->NotifyOfAcknowledgement(); + SetActive(); + } + +/** + Handles the client deferral error. + @param aError Error code to handle + */ +TInt CSsmStateAwareSession2::HandleDeferralError(TInt aError) + { + return (iSubscriber->HandleDeferralError(aError)); + } + +/** + Handle completion of request notifications, begins deferrals. +@note Clients should not need to override this, they +will be notified of events via interface HandleTransition(). + */ +void CSsmStateAwareSession2::RunL() + { + iDeferNotification->DeferNotification(); + iSubscriber->HandleTransition(iStatus.Int()); + } + +/** +Cancels an outstanding notification request. +Any outstanding notification request completes with KErrCancel. +*/ +void CSsmStateAwareSession2::DoCancel() + { + iDeferNotification->Cancel(); + iSsmStateAwareSession.RequestStateNotificationCancel(); + } + +#else +EXPORT_C CSsmStateAwareSession2* CSsmStateAwareSession2::NewL(TDmDomainId /*aDomainId*/, MStateChangeNotificationSubscriber2& /*aSubscriber*/) + { + //This functionality is not supported , so returning NULL. + return NULL; + } + +//All the below functionality will not be provided. + +EXPORT_C CSsmStateAwareSession2::~CSsmStateAwareSession2() + { + } + +EXPORT_C TSsmState CSsmStateAwareSession2::GetState() + { + //returning dummyState to get rid of compiler warning. + TSsmState dummyState; + return dummyState; + } + +EXPORT_C void CSsmStateAwareSession2::RequestStateNotification() + { + } + +EXPORT_C void CSsmStateAwareSession2::RequestStateNotificationCancel() + { + } + +EXPORT_C void CSsmStateAwareSession2::AcknowledgeStateNotification(TInt /*aError*/) + { + } + +EXPORT_C void CSsmStateAwareSession2::AcknowledgeAndRequestStateNotification(TInt /*aError*/) + { + } + +void CSsmStateAwareSession2::RunL() + { + } + +void CSsmStateAwareSession2::DoCancel() + { + } + +TInt CSsmStateAwareSession2::HandleDeferralError(TInt aError) + { + return aError; + } + +#endif