--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/genericservices/taskscheduler/SCHSVR/SchSSAMan.cpp Tue Feb 02 02:01:42 2010 +0200
@@ -0,0 +1,232 @@
+// Copyright (c) 2005-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:
+// Implementation of CSchStartupStateMgr class which connects to
+// the Domain manager to keep aware of the current start-up
+// state and distributes the state changes to registered observers.
+//
+//
+
+/**
+ @file
+ @internalComponent
+*/
+
+#include "SchSSAMan.h"
+#include "SchLogger.h"
+
+/**
+constructor of CSchStartupStateMgr
+@internalComponent
+*/
+CSchStartupStateMgr::CSchStartupStateMgr(TDmHierarchyId aHierarchyId, TDmDomainId aDomainId) :
+ CDmDomain(aHierarchyId,aDomainId),
+ iCurrentStartupState(EStartupStateUndefined)
+ {
+ }
+
+/**
+destructor of CSchStartupStateMgr
+@internalComponent
+*/
+CSchStartupStateMgr::~CSchStartupStateMgr()
+ {
+ Cancel();
+ iObserverList.Reset();
+ }
+
+/**
+Getter
+@internalComponent
+@return the current startup state
+*/
+TStartupStateIdentifier CSchStartupStateMgr::CurrentStartupState()
+ {
+ return iCurrentStartupState;
+ }
+
+/**
+updates the MSchStartupStateObserver objects.
+@internalComponent
+*/
+void CSchStartupStateMgr::UpdateStateAwareObjectsL(TStartupStateIdentifier aKnownState)
+ {
+ for (TInt i = 0; i < iObserverList.Count(); i++)
+ {
+ iObserverList[i]->ProcessSSAEventL(aKnownState);
+ }
+ }
+
+/**
+This method takes a a startup state which can be user defined
+state and maps it to a known startup state (KSS). KSS are
+Symbian defined states: undefined, critical static, critical dynamic,
+and non-critical.
+User defined states are refered to as USS - unknown startup state.
+
+@internalComponent
+*/
+TStartupStateIdentifier CSchStartupStateMgr::GetKnownStartupState(TDmDomainState aStartupState)
+ {
+ TStartupStateIdentifier knownStartupState = iCurrentStartupState;
+
+ if (aStartupState >= EStartupStateNonCritical)
+ {
+ knownStartupState = EStartupStateNonCritical;
+ }
+ else if(aStartupState >= EStartupStateCriticalDynamic)
+ {
+ knownStartupState = EStartupStateCriticalDynamic;
+ }
+ else if(aStartupState >= EStartupStateCriticalStatic)
+ {
+ knownStartupState = EStartupStateCriticalStatic;
+ }
+ else
+ {
+ knownStartupState = EStartupStateUndefined;
+ }
+
+ return knownStartupState;
+ }
+
+/**
+Register the MSchStartupStateObserver object with the CServerStartupMgr.
+@internalComponent
+@param aObs the pointer to the MStartupStateObserver object to be registered with CServerStartupMgr.
+*/
+void CSchStartupStateMgr::RegisterObserverL(const MSchStartupStateObserver* aObs)
+ {
+ User::LeaveIfError(iObserverList.Append(aObs));
+ }
+
+/**
+Handle the error if RunL leaves. Just tell the observers that
+we have reached the final state.
+
+@internalComponent
+@param aError error code generated by the RunL(), not used here.
+@return KErrNone to avoid CActiveScheduler to panic.
+*/
+TInt CSchStartupStateMgr::RunError(TInt /*aError*/)
+ {
+ LOGSTRING("CSchStartupStateMgr::RunL() leaves, set SS to final state.");
+ TRAP_IGNORE(UpdateStateAwareObjectsL(KSchFinalStartupState));
+ return KErrNone;
+ }
+
+/**
+Finsish constructing the CSchStartupStateMgr and start
+interacting with Domain Manager to receive startup state
+changes.
+All observers should have been registered before calling this method
+
+@internalComponent
+*/
+void CSchStartupStateMgr::InitialiseL()
+ {
+ TRAPD(err, CDmDomain::ConstructL());
+ if (err != KErrNone)
+ {
+ // the ConstructL leaves, go to final state
+ LOGSTRING2("CDmDomain::ConstructL leaves with %d. Goto final state", err);
+ UpdateStateAwareObjectsL(KSchFinalStartupState);
+ iCurrentStartupState = KSchFinalStartupState;
+ return;
+ }
+
+ // Typical pattern of using P&S is to subscribe first then get
+ // current state. Example implementation given
+ // in SSA Adaptation How-to also does it this way.
+ RequestTransitionNotification();
+
+ // get the start up state from the Domain Manager.
+ TDmDomainState rawstate = GetState();
+
+ // rawstate may be user defined. Map to known states.
+ TStartupStateIdentifier nextKnownState = GetKnownStartupState(rawstate);
+
+ // NB: nextKnownState can be KStartupStateUndefined for 2 reasons.
+ // One is rawstate == 0 which we must check first. Second:
+ // rawstate is user defined values lower than critical static. In
+ // the second case we must wait for next state change.
+ if (rawstate == EStartupStateUndefined ||
+ nextKnownState == KSchFinalStartupState)
+ {
+ // If either something wrong with DM or final state is reached,
+ // go to final state
+ iCurrentStartupState = KSchFinalStartupState;
+ UpdateStateAwareObjectsL(KSchFinalStartupState);
+ Cancel();
+ return;
+ }
+
+ iCurrentStartupState = nextKnownState;
+ }
+
+/**
+Executed when the startup state change is done, it does the
+same thing as the method InitialiseL() does
+@internalComponent
+*/
+void CSchStartupStateMgr::RunL()
+ {
+ if(iStatus != KErrNone) // something wrong with the RequestTransitionNotification().
+ {
+ AcknowledgeLastState(iStatus.Int()); //Acknowledge the domainmanager in case of leaving, this to avoid the acknowledgement in RunError()
+ User::LeaveIfError(iStatus.Int()); //RunError will handle this.
+ }
+
+ RequestTransitionNotification();
+
+ TDmDomainState rawstate = GetState();
+
+ // Must first check the case rawstate == undefined and deal with it here.
+ // GetKnowStartupState maps 1 to 15 to EStartupStateUndefined
+ // which means a SS before critical static. It does not mean go
+ // to final state.
+
+ //If the rawstate is EStartupStateUndefined there must be sth wrong.
+ if(rawstate == EStartupStateUndefined)
+ {
+ Cancel();
+ AcknowledgeLastState(KErrBadHandle);
+ User::Leave(KErrBadHandle); //RunError will handle this.
+ }
+
+ // get the known state
+ TStartupStateIdentifier nextKnownState = GetKnownStartupState(rawstate);
+
+ //Tell domain manager that we have processed the last state change before starting any time consuming work.
+ AcknowledgeLastState(KErrNone);
+
+ //Sleep 2 tickperiods this allows the acknowledgement reach the domain manager.
+ TTimeIntervalMicroSeconds32 tickPeriod;
+ UserHal::TickPeriod(tickPeriod);
+ User::After(2*tickPeriod.Int());
+
+ // Schsvr only want to know transition to non-critical.
+ // Ignore all states below that level.
+ if (iCurrentStartupState < KSchFinalStartupState && nextKnownState == KSchFinalStartupState)
+ {
+ UpdateStateAwareObjectsL(nextKnownState);
+ }
+
+ iCurrentStartupState = nextKnownState;
+
+ //do not request transition notification if we have reached the last state
+ if(iCurrentStartupState == KSchFinalStartupState)
+ {
+ Cancel();
+ }
+ }