sysstatemgmt/systemstatemgr/ssm/src/ssmserver.cpp
changeset 0 4e1aa6a622a0
child 10 1fc153c72b60
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/sysstatemgmt/systemstatemgr/ssm/src/ssmserver.cpp	Tue Feb 02 00:53:00 2010 +0200
@@ -0,0 +1,277 @@
+// Copyright (c) 2008-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 <ssm/ssmstates.hrh>
+#include <ssm/ssmstatetransition.h>
+#include <ssm/ssmstatepolicy.h>
+
+#include "ssmserverpanic.h"
+#include "ssmserver.h"
+#include "ssmsession.h"
+#include "ssmclisrv.h"
+#include "clesessionproxy.h"
+#include "ssmstatepolicyresolver.h"
+#include "ssmstatetransitionengine.h"
+#include "ssmstatepolicyresolverproxy.h"
+#include "ssmstatetransitionrequest.h"
+#include "ssmstatepolicyframe.h"
+#include "ssmswppolicyresolver.h"
+#include "ssmswprequesthandler.h"
+
+// ------------------- Policy Server Security Setup ----------------------
+
+const TUint  KRangeCount = 3;
+const TInt   KRanges[KRangeCount] =
+	{
+	0,						// op-code 0 not used
+	KSsmFirstUsedOpCode,	//range: KFirstUsedSsmOpCode...(EEndOfSsmOpCodes-1) inclusive
+	EEndOfSsmOpCodes
+	};
+
+/**
+ Specifies the appropriate action for each range in KRanges.
+ The nth element of KElementsIndex specifies the appropriate action for the nth range in KRanges.
+ */
+const TUint8 KElementsIndex[KRangeCount] =
+	{
+	CPolicyServer::ENotSupported,
+	CPolicyServer::EAlwaysPass,	//All request will be accepted and passed on to policy DLL for security checks
+	CPolicyServer::ENotSupported,
+	};
+
+/**
+ Setup a security policy that always allows connection requests for all requests.
+ */
+const CPolicyServer::TPolicy KSsmServerPolicy =
+	{
+	CPolicyServer::EAlwaysPass,	// Always allow connection requests
+	KRangeCount,
+	KRanges,
+	KElementsIndex,
+	NULL
+	};
+
+// ------------------- SsmServer Implementation ----------------------
+
+/**
+ EPriorityHigh to make sure the server is always scheduled before other AO such
+ as CSsmStateTransitionEngine.
+ */
+CSsmServer::CSsmServer() : CPolicyServer(EPriorityHigh, KSsmServerPolicy)
+	{
+	}
+
+/**
+ */
+CSsmServer::~CSsmServer()
+	{
+	const TInt ignore = User::SetCritical(User::ENotCritical);
+
+	delete iStateTransitionEngine;
+	delete iSwpRequestHandler;
+	delete iSwpResolver;
+	if(NULL != iSwpCleSession)
+		{
+		iSwpCleSession->ReleaseCle();
+		}
+
+	} //lint !e529 not subsequently referenced
+
+/**
+ */
+CSsmServer* CSsmServer::NewLC()
+	{
+	return CSsmServer::NewLC(ESsmStartup, EDoValidateCommandLists);
+	}
+
+/**
+ */
+CSsmServer* CSsmServer::NewLC(TUint16 aInitialState)
+	{
+	return CSsmServer::NewLC(aInitialState, EDoValidateCommandLists);
+	}
+
+/**
+ */
+CSsmServer* CSsmServer::NewLC(TUint16 aInitialState, TValidation aSetting)
+	{
+	CSsmServer* server = new(ELeave) CSsmServer();
+	CleanupStack::PushL(server);
+	server->ConstructL(aInitialState, aSetting);
+	server->StartL(KSsmServerName);
+	return server;
+	}
+
+#ifdef TEST_SSM_SERVER
+/**
+ Factory method used by automated tests to avoid clash with production server name.
+ */
+CSsmServer* CSsmServer::NewLC(const TDesC& aServerName, TUint16 aInitialState)
+	{
+	CSsmServer* server = new(ELeave) CSsmServer();
+	CleanupStack::PushL(server);
+	server->ConstructL(aInitialState, ENoCommandListValidation);
+	server->StartL(aServerName);
+	return server;
+	}
+#endif //TEST_SSM_SERVER
+/**
+ */
+void CSsmServer::ConstructL(TUint16 aInitialState, TValidation aSetting)
+	{
+	__ASSERT_ALWAYS( KErrNone == User::SetCritical(User::ESystemCritical), PanicNow(KPanicSysStateMgr,ESsmServerError1));
+	__ASSERT_ALWAYS( KErrNone == User::RenameThread(KSsmServerName), PanicNow(KPanicSysStateMgr,ESsmServerError2));
+
+	// --- Instantiate the "System State" handling classes ---
+	// Create a state policy resolver and load the initial policy
+	CSsmStatePolicyResolver* stateResolver = CSsmStatePolicyResolver::NewLC();
+	const TSsmState initalState = TSsmState(aInitialState, KSsmAnySubState);
+	stateResolver->GetStatePolicyL(initalState);
+	CCleSessionProxy* stateCleSession = CCleSessionProxy::NewL();
+	CleanupStack::PushL(stateCleSession);
+	// Create the state transition engine and let it take ownership of stateResolver and stateCleSession
+	iStateTransitionEngine = CSsmStateTransitionEngine::NewL(stateResolver, stateCleSession);
+	CleanupStack::Pop(2, stateResolver);
+	// Configure engine
+	iStateTransitionEngine->PerformCommandListValidation(EDoValidateCommandLists==aSetting);
+
+	// --- Instantiate the SWP handling classes ---
+	iSwpResolver = CSsmSwpPolicyResolver::NewL();
+	iSwpCleSession = CCleSessionProxy::NewL(); // Thought: Perhaps the CleSessionProxy should be a CLE session factory, thus allowing a separate session to be created for each engine
+	// Create the swp request handler and wire it up to the proxies
+	iSwpRequestHandler = CSsmSwpRequestHandler::NewL();
+	iSwpRequestHandler->SetSwpPolicyResolverProxy(iSwpResolver);
+	iSwpRequestHandler->SetCleSessionProxy(iSwpCleSession);
+	iSwpRequestHandler->PerformCommandListValidation(EDoValidateCommandLists==aSetting);
+
+	//Request initial actions
+	const TSsmStateTransition doStartup(initalState, 0);
+	iStateTransitionEngine->SubmitL(doStartup);
+	}
+
+/**
+ */
+CSession2* CSsmServer::NewSessionL(const TVersion& aVersion, const RMessage2& /*aMessage*/) const
+	{
+	// Check we're the right version
+	TVersion version(KSsmServMajorVersionNumber,KSsmServMinorVersionNumber,KSsmServBuildVersionNumber);
+	if (!User::QueryVersionSupported(version,aVersion))
+		{
+		User::Leave(KErrNotSupported);
+		}
+
+	// version supported, go ahead
+	return CSsmSession::NewL();
+	}
+
+/**
+ */
+void CSsmServer::RequestStateTransitionL(const TSsmState& aState, TInt aReason, const RMessage2& aMessage)
+	{
+	__ASSERT_DEBUG(iStateTransitionEngine, PanicNow(KPanicSysStateMgr,ESsmServerError3));
+
+	const TSsmStateTransition request(aState, aReason);
+	const MSsmStatePolicy::TResponse response = iStateTransitionEngine->TransitionAllowed(request, aMessage);
+	switch(response)
+		{
+		case MSsmStatePolicy::EDefinitelyAllowed:
+		case MSsmStatePolicy::ECurrentRemainReplaceQueued:
+			{
+			// A leave here will complete the client-request with KErrNoMemory
+			iStateTransitionEngine->SubmitL(request, aMessage);
+			break;
+			}
+
+		case MSsmStatePolicy::EReplaceCurrentClearQueue:
+			{
+			iStateTransitionEngine->Cancel(NULL);
+			iStateTransitionEngine->SubmitL(request, aMessage);
+			break;
+			}
+
+		case MSsmStatePolicy::ENotAllowed:
+		default:
+			{
+			aMessage.Complete(KErrNotSupported);
+			break;
+			}
+		}
+	}
+
+/**
+ Cancel any transition job that is accepted but not yet started.
+ */
+void CSsmServer::RequestStateTransitionCancel(CSession2* aSession)
+	{
+	iStateTransitionEngine->Cancel(aSession);
+	}
+
+/**
+ Initiate processing of the request for a system wide property change
+ */
+void CSsmServer::RequestSwpChangeL(const TSsmSwp& aSwp, const RMessage2& aMessage)
+	{
+	iSwpRequestHandler->SubmitRequestL(aSwp, aMessage);
+	}
+
+/**
+ Cancel processing of pending and running system wide property change requests
+ */
+void CSsmServer::RequestSwpChangeCancel(CSession2* aSession)
+	{
+	iSwpRequestHandler->Cancel(aSession);
+	}
+
+/**
+ Register the policy file name for this swp
+ This also marks the actual existence of the swp
+ */
+void CSsmServer::RequestRegisterSwpMappingL(TUint aSwpKey, const TDesC& aFilename)
+	{
+	iSwpResolver->RegisterSwpMappingL(aSwpKey, aFilename);
+	}  //lint !e1746 Suppress parameter 'aSwpKey' could be made const reference
+
+/**
+ * Used only for testing purposes
+ * DeRegister the policy file name for this swp
+ */
+#ifdef _DEBUG
+void CSsmServer::RequestDeRegisterSwpMappingL(TUint aSwpKey, const TDesC& aFilename)
+	{
+	iSwpResolver->DeRegisterSwpMappingL(aSwpKey, aFilename);
+	}
+#endif
+
+/**
+ * Used only for testing purposes
+ * Cleanup Transition Engine after the test is over
+ */
+#ifdef _DEBUG
+void CSsmServer::DoCleanupStateTransitionEngine()
+	{
+	iStateTransitionEngine->CleanupTransitionEngine();
+	}
+#endif
+
+/**
+ * Used only for testing purposes
+ * Cleanup Request Handler after the test is over
+ */
+#ifdef _DEBUG
+void CSsmServer::DoCleanupSwpRequestHandler()
+	{
+	iSwpRequestHandler->CleanupSwpTransitionScheduler();
+	}
+#endif