installationservices/swi/source/sisregistry/server_legacy/sisregistryserversession.cpp
changeset 0 ba25891c3a9e
child 4 3eebb1e54d3a
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/installationservices/swi/source/sisregistry/server_legacy/sisregistryserversession.cpp	Thu Dec 17 08:51:10 2009 +0200
@@ -0,0 +1,2174 @@
+/*
+* Copyright (c) 2004-2009 Nokia Corporation and/or its subsidiary(-ies).
+* All rights reserved.
+* This component and the accompanying materials are made available
+* under the terms of the License "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: 
+* CSisRegistrySession class implementation
+*
+*/
+
+
+/**
+ @file 
+ @released
+ @internalComponent
+*/
+#include <s32mem.h>
+#include <f32file.h>
+#include <s32file.h>
+
+#include "log.h"
+
+#include <swi/sistruststatus.h>
+#include <scs/ipcstream.h>
+#include "swi/siscontroller.h"
+#include "sisregistryserversession.h"
+#include "sisregistryserver.h"
+#include "sisregistrypackage.h"
+#include "sisregistryserverconst.h"
+#include "sisregistryobject.h"
+#include "sisregistrycache.h"
+#include "sisregistryfiledescription.h"
+#include "sisregistrydependency.h"
+#include "controllerinfo.h"
+
+#include "arrayutils.h"
+
+#include "integrityservices.h"
+#include "hashcontainer.h"
+#include "filesisdataprovider.h"
+#include "dessisdataprovider.h"
+#include "sisrevocationmanager.h"
+#include "siscontroller.h"
+#include "siscertificatechain.h"
+
+#include "cleanuputils.h"
+#include "sisregistryutil.h"
+#include "sisinfo.h"
+#include "sisuid.h"
+#include "securitymanager.h"
+#include "siscontrollerverifier.h"
+#ifdef SYMBIAN_ENABLE_SPLIT_HEADERS
+#include "swi/sisregistrylogversion.h"
+#endif //SYMBIAN_ENABLE_SPLIT_HEADERS
+#include <swi/sisregistrylog.h>
+#include "sisinstallblock.h"
+#include "sisregistryfiledescription.h"
+#include "sisregistrywritablesession.h"
+  
+
+using namespace Swi;
+
+template<class T> 
+void SendDataL(const RMessage2& aMessage, const T& aProvider, TInt aIpcIndx);
+template<class T> 
+void SendDataArrayL(const RMessage2& aMessage, const RArray<T> aProvider, TInt aIpcIndx);
+template<class T> 
+void SendDataPointerArrayL(const RMessage2& aMessage, const RPointerArray<T> aProvider, TInt aIpcIndx);
+	
+/**
+ * Function to panic an offending client
+ * @internalTechnology
+ * @released
+ */
+ void CSisRegistrySession::PanicClient(const RMessagePtr2& aMessage, Swi::TSisRegistryPanic aPanic)
+	{
+	aMessage.Panic(KSisRegistryShortName, aPanic);
+	}
+
+void CSisRegistrySession::CreateL()
+//
+// 2nd phase construct for sessions - called by the CServer framework
+//
+	{
+	Server().AddSession();
+	
+	iRevocationManager =
+      CSisRevocationManager::NewL(*this);
+    
+	// Just obtain a handle reference to use 
+	iFs = Server().Cache().RFsHandle();
+	}
+
+CSisRegistrySession::~CSisRegistrySession()
+	{
+	Server().DropSession();
+    
+	delete iRevocationManager;
+	delete iSisControllerVerifier;
+	iControllerArray.ResetAndDestroy();
+	}
+
+void CSisRegistrySession::ServiceL(const RMessage2& aMessage)
+//
+// Handle a client request.
+// Leaving is handled by CSisRegistry::ServiceError() which reports
+// the error code to the client
+//
+	{
+	DEBUG_PRINTF2(_L8("SIS Registry Server - ServiceL (function %d)"), aMessage.Function());
+	switch (aMessage.Function())
+		{	
+	// general registry	
+	case EInstalledUids:
+		RequestInstalledUidsL(aMessage);
+		break;
+	case EInstalledPackages:
+		RequestInstalledPackagesL(aMessage);
+		break;
+	case EUidInstalled:
+	    UidInstalledL(aMessage);
+	    break;
+	case EControllerInstalled:
+	    ControllerInstalledL(aMessage);
+	    break;
+	case ESidToPackage:
+		RequestSidToPackageL(aMessage);
+	    break;
+	case ESidToFileName:
+		RequestSidToFileNameL(aMessage);
+		break;
+	case EModifiable:
+		RequestModifiableL(aMessage);
+		break;
+	case EHash:
+		RequestHashL(aMessage);
+		break;		
+	// general entry 	
+	case EOpenRegistryUid:
+		OpenRegistryUidEntryL(aMessage);
+		break;
+	case EOpenRegistryPackage:
+		OpenRegistryPackageEntryL(aMessage);
+		break;
+	case EOpenRegistryNames:
+		OpenRegistryNamesEntryL(aMessage);
+		break;
+	case ECloseRegistryEntry:
+		CloseRegistryEntryL(aMessage);
+		break;
+	case EVersion:
+	    RequestVersionRegistryEntryL(aMessage);
+		break;
+	case EPackageName:
+		RequestPackageNameRegistryEntryL(aMessage);
+		break;
+	case EUniqueVendorName:
+		RequestUniqueVendorNameRegistryEntryL(aMessage);
+		break;	
+	case ELocalizedVendorName:
+		RequestLocalizedVendorNameRegistryEntryL(aMessage);
+		break;
+	case EUid:
+		RequestUidRegistryEntryL(aMessage);
+		break;
+	case ESids:
+		RequestSidsRegistryEntryL(aMessage);
+		break;
+	case ELanguage:
+		RequestLanguageRegistryEntryL(aMessage);
+		break;
+	case EUidPresent:
+		UidPresentRegistryEntryL(aMessage);
+		break;
+	case ESigned:
+	    SignedRegistryEntryL(aMessage);
+		break;
+	case EGetTrust:
+		RegistryEntryTrustL(aMessage);
+		break;	
+	case ETrustTimeStamp:
+		TrustTimeStampL(aMessage);
+		break;	
+	case ETrustStatus:
+		TrustStatusEntryL(aMessage);
+		break; 
+	case EIsSidPresent:
+		IsSidPresentL(aMessage);
+		break;
+	case EShutdownAllApps:
+		ShutdownAllAppsL(aMessage);
+		break;
+	case ERevocationStatus:
+		RevocationCheckEntryL(aMessage);
+		break;	
+	case ECancelRevocationStatus:
+		CancelRevocationCheckEntryL(aMessage);
+		break;			
+	case EInRom:
+		InRomRegistryEntryL(aMessage);
+		break;
+	case EAugmentation:
+		AugmentationRegistryEntryL(aMessage);
+		break;
+	case EControllers:
+		RequestControllersL(aMessage);
+		break;
+	case EProperty:
+		RequestPropertyRegistryEntryL(aMessage);
+		break;
+	case EFiles:
+		RequestFileNamesRegistryEntryL(aMessage);
+		break;
+	case EHashEntry:
+		RequestHashRegistryEntryL(aMessage);
+		break;	
+	case EFileDescriptions:
+		RequestFileDescriptionsRegistryEntryL(aMessage);
+		break;	
+	case ESelectedDrive:
+		RequestSelectedDriveRegistryEntryL(aMessage);
+		break;
+	case EInstalledDrives:
+		RequestInstalledDrivesRegistryEntryL(aMessage);
+		break;			
+	case EPreInstalled:
+		PreInstalledRegistryEntryL(aMessage);
+		break;
+	case EInstallType:
+		RequestInstallTypeRegistryEntryL(aMessage);
+		break;
+	case ECertificateChains:
+		RequestCertificateChainsRegistryEntryL(aMessage);
+		break;
+	case EEmbeddedPackages:
+	    RequestEmbeddedPackageRegistryEntryL(aMessage);
+	    break; 
+	case EEmbeddingPackages:
+		RequestEmbeddingPackagesRegistryEntryL(aMessage);
+	    break; 
+	case EPackageAugmentations:
+	    RequestPackageAugmentationsRegistryEntryL(aMessage);
+	    break;
+	case EPackageAugmentationsNumber:
+		RequestPackageAugmentationsNumberL(aMessage);
+		break;
+	case ESize:
+		RequestSizeRegistryEntryL(aMessage);
+	    break;
+	case EPackage:
+		RequestPackageRegistryEntryL(aMessage);
+	    break;
+	case EAddEntry:
+		RegisterEntryL(aMessage, ETrue);
+		break;
+	case EUpdateEntry:
+		RegisterEntryL(aMessage, EFalse);
+		break;
+	case EDeleteEntry:
+		DeleteEntryL(aMessage);
+		break;
+	case EDependencies:
+		RequestDependenciesRegistryEntryL(aMessage);
+		break; 
+	case EDependentPackages:
+		RequestDependentPackagesRegistryEntryL(aMessage);
+		break;
+	case EGetEntry:
+		RequestRegistryEntryL(aMessage);
+		break;
+	case EAddDrive:
+		AddDriveL(aMessage);
+		break;
+	case ERemoveDrive:
+		RemoveDriveL(aMessage);
+		break;
+ 	case ERegenerateCache:
+ 		RegenerateCacheL(aMessage);	
+ 		break;
+	case EDeletablePreInstalled:
+		DeletablePreInstalledRegistryEntryL(aMessage);
+		break;
+	case EVerifyController:
+		{
+		VerifyControllerL(aMessage);
+		break;
+		}
+	case ERemoveWithLastDependent:
+		{
+		RemoveWithLastDependentL(aMessage);
+		break;
+		} 
+	case ESetRemoveWithLastDependent:
+		{
+		SetRemoveWithLastDependentL(aMessage);
+		break;
+		} 
+	case EloggingFile:
+ 		LoggingFileInfoL(aMessage);
+ 		break;
+	case ENonRemovable:
+		IsRemovableL(aMessage);
+		break;
+	case ERemovablePackages:
+		RequestRemovablePackagesL(aMessage);
+		break;
+	case EPackageExistsInRom:
+		PackageExistsInRomL(aMessage);
+		break;	
+	case EInitRecovery:
+		RecoverL(aMessage);
+		break;
+	case EStubFileEntries:
+		RequestStubFileEntriesL(aMessage);
+		break;
+	case ESignedBySuCert:
+ 		SignedBySuCertRegistryEntryL(aMessage);
+ 		break;
+	case EGetMatchingSupportedLanguages:
+		RequestMatchingSupportedLanguagesL(aMessage);
+	    break;	
+	default:
+		PanicClient(aMessage,EPanicIllegalFunction);
+		break;
+		}
+	}
+
+void CSisRegistrySession::VerifyControllerL(const RMessage2& aMessage)
+	{
+	DEBUG_PRINTF(_L("CSisRegistry::VerifyControllerSignature"));
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	RPointerArray<HBufC8> controllers;
+
+	iControllerArray.ResetAndDestroy();
+	Server().Cache().GenerateControllersArrayL(object, iControllerArray);
+	
+	delete iSisControllerVerifier;
+	iSisControllerVerifier = CSisControllerVerifier::NewL(aMessage);
+
+	iSisControllerVerifier->VerifyControllerL(iControllerArray); 
+	}
+
+void CSisRegistrySession::RequestInstalledUidsL(const RMessage2& aMessage)
+	{
+	RArray<TUid> uids;
+	CleanupClosePushL(uids);
+	Server().Cache().UidListL(uids);
+	SendDataArrayL(aMessage, uids, EIpcArgument0);
+	CleanupStack::PopAndDestroy(&uids);
+	}
+	
+void CSisRegistrySession::RequestInstalledPackagesL(const RMessage2& aMessage)
+	{
+    RPointerArray<CSisRegistryPackage> packages; 
+    CleanupResetAndDestroy<RPointerArray<CSisRegistryPackage> >::PushL(packages);
+    Server().Cache().PackageListL(packages); 
+    SendDataPointerArrayL(aMessage, packages, EIpcArgument0);
+    CleanupStack::PopAndDestroy(&packages);
+	}
+	
+void CSisRegistrySession::UidInstalledL(const RMessage2& aMessage)
+	{
+	TBool isRegistered;
+	TUid uid; 
+	TPckg<TUid> packageUid(uid);
+	
+	aMessage.ReadL(EIpcArgument0, packageUid);
+	
+	// check whether is registered
+	isRegistered = Server().Cache().IsRegistered(uid); 
+	
+	DEBUG_CODE_SECTION(
+		if (isRegistered)
+			{
+			DEBUG_PRINTF2(_L8("SIS Registry Server - UID 0x%08x is registered."), uid);
+			}
+		else
+			{
+			DEBUG_PRINTF2(_L8("SIS Registry Server - UID 0x%08x is not registered."), uid);
+			}
+	);
+	
+	// return the data back
+    TPckgC<TBool> packageBool(isRegistered);
+	aMessage.WriteL(EIpcArgument1, packageBool);
+	
+	aMessage.Complete(KErrNone);
+	}
+
+void CSisRegistrySession::ControllerInstalledL(const RMessage2& aMessage)
+	{
+	TBool installed;
+	
+	TInt srcLen = aMessage.GetDesLengthL(EIpcArgument0);
+	HBufC8* buffer = HBufC8::NewLC(srcLen);
+	TPtr8 dest = buffer->Des();
+	
+	// read data in the buffer
+	aMessage.ReadL(EIpcArgument0, dest, 0);
+		
+	// lets store all in a stream
+	RDesReadStream stream(dest);
+    CleanupClosePushL(stream);
+
+	// now create the hash object to look for
+	CHashContainer* hash = CHashContainer::NewLC(stream);
+  	
+  	// is the entry present already?
+	installed = Server().Cache().IsRegistered(*hash);
+	
+	DEBUG_CODE_SECTION(
+		if (installed)
+			{
+			DEBUG_PRINTF(_L8("SIS Registry Server - Controller is installed."));
+			}
+		else
+			{
+			DEBUG_PRINTF(_L8("SIS Registry Server - Controller is not installed."));
+			}
+	);
+	
+	// return the data back
+	TPckgC<TBool> isInstalled(installed);
+	aMessage.WriteL(EIpcArgument1, isInstalled);
+	
+	aMessage.Complete(KErrNone);
+	// reclaim memory back
+	CleanupStack::PopAndDestroy(3, buffer); // buffer, stream, hash  
+	}
+
+void CSisRegistrySession::RegisterEntryL(const RMessage2& aMessage, TBool aNewEntry)
+	// register/update new/existing registry entry 
+	{
+	// get the registry object from client space
+	// get the size of the descriptor in client space
+	// and allocate sufficient buffer 
+	TInt srcLen = aMessage.GetDesLengthL(EIpcArgument0);
+	HBufC8* buffer = HBufC8::NewLC(srcLen);
+	TPtr8 dest = buffer->Des();
+	// read data in the buffer
+	aMessage.ReadL(EIpcArgument0, dest, 0);
+		
+	// lets store all in a stream
+	RDesReadStream stream(dest);
+    CleanupClosePushL(stream);   
+
+	// now create a registry entry from the stream
+	CSisRegistryObject* object = CSisRegistryObject::NewL(stream);	
+	CleanupStack::PopAndDestroy(2, buffer); // buffer, stream 
+	CleanupStack::PushL(object);
+	buffer = NULL;
+	
+	DEBUG_CODE_SECTION(
+		if (aNewEntry)
+			{
+			DEBUG_PRINTF4(_L("Sis Registry Server - registering entry for object with UID: 0x%08x, Name: %S, Vendor: %S."),
+				object->Uid().iUid, &(object->Name()), &(object->Vendor()));
+			}
+		else
+			{
+			DEBUG_PRINTF4(_L("Sis Registry Server - updating entry for object with UID: 0x%08x, Name: %S, Vendor: %S."),
+				object->Uid().iUid, &(object->Name()), &(object->Vendor()));
+			}
+	);
+	
+	TBool isRegistered;
+	if(aNewEntry)
+		{
+		isRegistered = Server().Cache().IsRegistered(*object);
+		}
+	else
+		{
+		// We're upgrading an existing entry, if it's not an augmentation upgrade,
+		// check for the existance of the base package. Otherwise, check by package
+		if (object->InstallType() != Sis::EInstAugmentation)
+			{
+			isRegistered = Server().Cache().IsRegistered(object->Uid());
+			}
+		else
+			{
+			isRegistered = Server().Cache().IsRegistered(*object);
+			}
+		}
+
+  	// the entry should not be existing - new or
+  	// the entry should be existing - upgrade
+	if (isRegistered == (!aNewEntry))	
+		{			 
+		// get this transaction ID from client space, using packaging
+		TInt64 transactionID;
+		TPckg<TInt64> pkgTransactionID(transactionID);
+		aMessage.ReadL(EIpcArgument1, pkgTransactionID);
+		
+		CIntegrityServices* integrityService = CIntegrityServices::NewLC(transactionID, KIntegrityServicesPath);
+		if (!aNewEntry)
+			{
+			CSisRegistryObject* existingObject = NULL;
+			existingObject = Server().Cache().ObjectL(object->Uid(), object->Index());
+			CleanupStack::PushL(existingObject);
+			
+			// DEF085506 fix. remove control files (Previous SA and any of PUs) also while SA upgrading.
+			if (object->InstallType() == Sis::EInstInstallation)
+				{
+				Server().Cache().RemoveRegistryEntryL(*existingObject, *integrityService);	
+				}
+			else // PartialUpgarde case remove only registry file.
+				{
+				// Essentially, this is an uninstall except we leave the controller file intact.
+				Server().Cache().RemoveRegistryFilesL(*existingObject, *integrityService);	
+				}	
+								
+			CleanupStack::PopAndDestroy(existingObject);
+			}
+		// get the current controller from client space
+		// check the size of the descriptor in client space
+		// and allocate accordingly
+		TInt srcLenCtrl = aMessage.GetDesLengthL(EIpcArgument2);
+		HBufC8* bufferCtrl = HBufC8::NewLC(srcLenCtrl);
+		TPtr8 destCtrl = bufferCtrl->Des();
+
+		// read controller content as a binary data
+		aMessage.ReadL(EIpcArgument2, destCtrl, 0);
+			
+		Server().Cache().AddRegistryEntryL(*object, *integrityService, *bufferCtrl);
+		
+		HBufC* logName = SisRegistryUtil::BuildLogFileNameLC();
+ 	
+ 		TDriveUnit sysDrive(RFs::GetSystemDrive());
+		TBuf<128> logDir = sysDrive.Name();
+		logDir.Append(KLogDir);
+ 	
+ 		if( SisRegistryUtil::FileExistsL(iFs,*logName))
+ 			{
+ 			TInt sizeOfFile = 0;
+ 			RFile file;
+ 			User::LeaveIfError(file.Open(iFs,logDir,EFileRead));
+ 			CleanupClosePushL(file);
+ 			User::LeaveIfError(file.Size(sizeOfFile));
+ 			RBuf8 text;
+ 			text.CreateL(sizeOfFile);
+ 			text.CleanupClosePushL();
+ 			file.Read(text,sizeOfFile);
+ 			file.Close();
+ 			integrityService->RemoveL(*logName);
+ 			User::LeaveIfError(file.Create(iFs,logDir,EFileWrite| EFileShareExclusive |EFileStream));
+ 			User::LeaveIfError(file.Write(text,sizeOfFile));
+ 			CleanupStack::PopAndDestroy(2,&file);
+ 			}
+ 		integrityService->AddL(*logName);
+ 		
+ 		if (!aNewEntry)
+ 			{
+ 			Server().Cache().AddLogEntryL(*object,ESwiLogUpgrade);
+ 			}
+ 		else
+ 			{
+ 			Server().Cache().AddLogEntryL(*object,ESwiLogInstall);
+ 			}
+ 
+ 		CleanupStack::PopAndDestroy(3, integrityService); // integrityService, bufferCtrl, logName		
+	
+		aMessage.Complete(KErrNone);				
+		}  
+	else
+		{
+		DEBUG_CODE_SECTION(
+			if (aNewEntry)
+				{
+				DEBUG_PRINTF(_L8("Sis Registry Server - Error, package already exists!"));
+				}
+			else
+				{
+				DEBUG_PRINTF(_L8("Sis Registry Server - Error, package was not found!"));
+				}
+		);
+			
+		TInt reason = (aNewEntry)? KErrAlreadyExists:KErrNotFound; 
+		aMessage.Complete(reason);				
+		}
+	
+	// need to free up the used memory
+	CleanupStack::PopAndDestroy(object); 
+	}
+
+void CSisRegistrySession::DeleteEntryL(const RMessage2& aMessage)
+// Delete a registry entry keyed by package and vendor names
+// uses integrity services and the associated transactionId
+	{
+	TInt srcLen;
+	
+	TUid uid;
+	TPckg<TUid> packageUid(uid);
+	aMessage.ReadL(EIpcArgument0, packageUid, 0);
+	
+	// Package Name - ipc(1)
+	srcLen = aMessage.GetDesLengthL(EIpcArgument1);
+	HBufC* packageName = HBufC::NewLC(srcLen);
+	TPtr namePtr1 = packageName->Des();
+	aMessage.ReadL(EIpcArgument1, namePtr1, 0);	
+	
+	// Vendor's Name - ipc(2)	
+	srcLen = aMessage.GetDesLengthL(EIpcArgument2);
+	HBufC* vendorName = HBufC::NewLC(srcLen);
+	TPtr namePtr2 = vendorName->Des();
+	aMessage.ReadL(EIpcArgument2, namePtr2, 0);
+	
+	CSisRegistryObject* object = Server().Cache().ObjectL(uid, *packageName, *vendorName);
+	CleanupStack::PopAndDestroy(2, packageName); // packageName,vendorName 
+	CleanupStack::PushL(object);
+	
+	DEBUG_PRINTF4(_L("Sis Registry Server - Removing package registry entry for UID: %08x, Name: %S, Vendor %S."),
+		object->Uid().iUid, &(object->Name()), &(object->Vendor()));
+	
+	// transaction ID - ipc(3)
+	TInt64 transactionID;
+	TPckg<TInt64> pkgTransactionID(transactionID);
+	aMessage.ReadL(EIpcArgument3, pkgTransactionID);
+	
+	// create a integrity service object
+    CIntegrityServices* integrityService = CIntegrityServices::NewLC(transactionID, KIntegrityServicesPath);
+	Server().Cache().RemoveRegistryEntryL(*object, *integrityService);
+
+	//If removal is for ROM upgrade type, 
+	//After removing the existing registry entry set,
+	//re generate the Registry Entry Cache. 
+	//If any of the ROM based stub doesn't have it's registry set 
+	//in appropriate path, it will create them (.reg & . ctl) 
+	//from the ROM based stub sis file.	
+	if ((object->InstallType() == Sis::EInstInstallation || 
+		 object->InstallType() == Sis::EInstPartialUpgrade) &&	
+		SisRegistryUtil::RomBasedPackageL(object->Uid()))
+		{	
+		Server().Cache().RegenerateCacheL();					
+		}		
+		
+	HBufC* logName = SisRegistryUtil::BuildLogFileNameLC();
+	
+	TDriveUnit sysDrive(RFs::GetSystemDrive());
+	TBuf<128> logDir = sysDrive.Name();
+	logDir.Append(KLogDir);
+	
+ 	if( SisRegistryUtil::FileExistsL(iFs,*logName))
+			{
+ 			TInt sizeOfFile = 0;
+ 			RFile file;
+ 			User::LeaveIfError(file.Open(iFs,logDir,EFileRead));
+ 			CleanupClosePushL(file);
+ 			User::LeaveIfError(file.Size(sizeOfFile));
+ 			RBuf8 text;
+ 			text.CreateL(sizeOfFile);
+ 			text.CleanupClosePushL();
+ 			file.Read(text,sizeOfFile);
+ 			file.Close();
+ 			integrityService->RemoveL(*logName);
+ 			User::LeaveIfError(file.Create(iFs,logDir,EFileWrite| EFileShareExclusive |EFileStream));
+ 			User::LeaveIfError(file.Write(text,sizeOfFile));
+ 			CleanupStack::PopAndDestroy(2,&file);
+ 			}			
+ 	integrityService->AddL(*logName);
+ 	Server().Cache().AddLogEntryL(*object,ESwiLogUnInstall);	
+ 	
+ 	CleanupStack::PopAndDestroy(3, object);// object, integrityService , logName
+	
+	aMessage.Complete(KErrNone);
+	}
+
+void CSisRegistrySession::OpenRegistryUidEntryL(const RMessage2& aMessage)
+	{
+	// expects a UID as an arg 0
+	TUid uid;
+	TPckg<TUid> packageUid(uid);
+	aMessage.ReadL(EIpcArgument0, packageUid, 0);
+	
+	DEBUG_PRINTF2(_L8("Sis Registry Server - Opening entry subsession for UID: %08x"),
+		uid.iUid);
+		
+	// check uid is present in the list
+	if (Server().Cache().IsRegistered(uid))	
+		{
+		// get the id of the object stored in the cache
+	    TUint id;
+	    TRAPD(err, Server().Cache().OpenReadHandleL(Server().Cache().PackageL(uid), id));
+	    if((err != KErrPathNotFound) && (err != KErrNotFound) && (err != KErrNone) )
+	    	{
+	    	User::Leave(err);
+	    	}
+	    // return this handle to identify the subsession
+		if((err == KErrPathNotFound) || (err == KErrNotFound))
+			{
+			err = KErrNotFound;
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Could not find UID: %08x."), uid.iUid);
+			Server().Cache().RegenerateCacheL();
+			}
+		else
+			{
+			TPckgC<TInt> refId(id);
+	    	DEBUG_PRINTF2(_L8("Sis Registry Server - Sucessfully opened, subsession ID %d."), id);
+			aMessage.WriteL(EIpcArgument3, refId);
+			}
+		aMessage.Complete(err);
+		}
+	else
+		{
+		DEBUG_PRINTF(_L8("Sis Registry Server - Failed to open package by UID, does not exist."));
+		
+		aMessage.Complete(KErrNotFound);		
+		}
+	}
+
+void CSisRegistrySession::OpenRegistryPackageEntryL(const RMessage2& aMessage)
+	{
+	// Package Name - ipc(0)
+	TInt srcLen = aMessage.GetDesLengthL(EIpcArgument0);
+	HBufC8* buffer = HBufC8::NewLC(srcLen);
+	TPtr8 dest = buffer->Des();
+	// read data in the buffer
+	aMessage.ReadL(EIpcArgument0, dest, 0);
+		
+	// lets store all in a stream
+	RDesReadStream stream(dest);
+    CleanupClosePushL(stream);
+
+	// now create a registry entry
+	CSisRegistryPackage* package = CSisRegistryPackage::NewLC(stream);
+
+	DEBUG_PRINTF4(_L("Sis Registry Server - Opening entry subsession for UID: %08x, Name: %S, Vendor: %S"),
+		package->Uid().iUid, &(package->Name()), &(package->Vendor()));
+
+	// get the package handle
+	TUint id;
+	Server().Cache().OpenReadHandleL(*package, id);
+	TPckgC<TInt> refId(id);
+	
+	DEBUG_PRINTF2(_L8("Sis Registry Server - Sucessfully opened, subsession ID %d."),
+		id);
+	
+	// return this handle to identify the subsession
+	aMessage.WriteL(EIpcArgument3, refId);
+	aMessage.Complete(KErrNone);
+	
+	CleanupStack::PopAndDestroy(3, buffer); // buffer, stream, package
+	}
+	
+void CSisRegistrySession::OpenRegistryNamesEntryL(const RMessage2& aMessage)
+	{
+	// expects a package name and a vendor name as an arg 0 and 1
+	TInt srcLen;
+	
+	// Package Name - ipc(0)
+	srcLen = aMessage.GetDesLengthL(EIpcArgument0);
+	HBufC* packageName = HBufC::NewLC(srcLen);
+	TPtr namePtr1 = packageName->Des();
+	aMessage.ReadL(EIpcArgument0, namePtr1, 0);
+	
+	// Vendor's Name - ipc(1)	
+	srcLen = aMessage.GetDesLengthL(EIpcArgument1);
+	HBufC* vendorName = HBufC::NewLC(srcLen);
+	TPtr namePtr2 = vendorName->Des();
+	// read 
+	aMessage.ReadL(EIpcArgument1, namePtr2, 0);
+	
+	DEBUG_PRINTF3(_L("Sis Registry Server - Opening entry subsession by name/vendor. Name: %S, Vendor: %S."),
+		packageName, vendorName);
+	
+	// we cannot use default constructor to create a package
+	// so we are going to return pointer/reference to the value 
+	// pointer implementation, so it should not be deallocated
+	const CSisRegistryPackage& package = Server().Cache().PackageL(*packageName, *vendorName);
+	// get the package handle
+	TUint id;
+	Server().Cache().OpenReadHandleL(package, id);
+	TPckgC<TInt> refId(id);
+	
+	DEBUG_PRINTF2(_L8("Sis Registry Server - Sucessfully opened, subsession ID %d"),
+		id);
+	
+	// return this handle to identify the subsession
+	aMessage.WriteL(EIpcArgument3, refId);
+	aMessage.Complete(KErrNone);
+	
+	CleanupStack::PopAndDestroy(2, packageName);// packageName, vendorName	
+	}
+
+void CSisRegistrySession::CloseRegistryEntryL(const RMessage2& aMessage)
+	{
+	DEBUG_PRINTF2(_L8("Sis Registry Server - Closing open subsession, ID %d."),
+		aMessage.Int3());
+	
+	// the identity of the current entry/subsession is passed in IPC 3!
+	// all we have to do is destroy the relevant object 
+	Server().Cache().CloseReadHandleL(aMessage.Int3());
+	aMessage.Complete(KErrNone);	
+	}
+
+void CSisRegistrySession::RequestVersionRegistryEntryL(const RMessage2& aMessage)
+	{
+	// the identity of the current entry/subsession is passed in IPC 3!
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	
+	TVersion version;
+	version = object.Version();
+	TPckg<TVersion> packageVersion(version);
+	
+	DEBUG_PRINTF5(_L8("Sis Registry Server - Version for subsession ID %d is %d.%d.%d"),
+		aMessage.Int3(), version.iMajor, version.iMinor, version.iBuild);
+	
+	aMessage.WriteL(EIpcArgument0, packageVersion);
+	aMessage.Complete(KErrNone);	
+	}
+	
+void CSisRegistrySession::RequestPackageNameRegistryEntryL(const RMessage2& aMessage)
+	{
+	// the identity of the current entry/subsession is passed in IPC 3!
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	
+	DEBUG_PRINTF3(_L("Sis Registry Server - Name for subsession ID %d is '%S'"),
+		aMessage.Int3(), &(object.Name()));
+			
+	aMessage.WriteL(EIpcArgument0, object.Name());	
+	aMessage.Complete(KErrNone);	
+	}
+	
+void CSisRegistrySession::RequestLocalizedVendorNameRegistryEntryL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+
+	DEBUG_PRINTF3(_L("Sis Registry Server - Vendor for subsession ID %d is '%S'"),
+		aMessage.Int3(), &(object.VendorLocalizedName()));
+
+	aMessage.WriteL(EIpcArgument0, object.VendorLocalizedName());
+	aMessage.Complete(KErrNone);	
+	}
+	
+void CSisRegistrySession::RequestUniqueVendorNameRegistryEntryL(const RMessage2& aMessage)
+	{
+	// the identity of the current entry/subsession is passed in IPC 3!
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+
+	DEBUG_PRINTF3(_L("Sis Registry Server - Unique Vendor for subsession ID %d is '%S'"),
+		aMessage.Int3(), &(object.Vendor()));
+
+	aMessage.WriteL(EIpcArgument0, object.Vendor());	
+	aMessage.Complete(KErrNone);	
+	}
+	
+void CSisRegistrySession::RequestEmbeddedPackageRegistryEntryL(const RMessage2& aMessage)
+	{
+	// the identity of the current entry/subsession is passed in IPC 3!
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+
+	RPointerArray<CSisRegistryPackage> embeddedPackages;
+	CleanupResetAndDestroy<RPointerArray<CSisRegistryPackage> >::PushL(embeddedPackages);
+	object.EmbeddedPackagesL(embeddedPackages);
+	
+	DEBUG_PRINTF3(_L8("Sis Registry Server - Package for subsession %d has %d embedded packages."),
+		aMessage.Int3(), embeddedPackages.Count());
+	
+	SendDataPointerArrayL(aMessage, embeddedPackages, EIpcArgument0);
+
+	CleanupStack::PopAndDestroy(&embeddedPackages);
+	}
+
+void CSisRegistrySession::RequestHashRegistryEntryL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	
+	// get file name
+	TUint srcLen = aMessage.GetDesLengthL(EIpcArgument0);
+	HBufC* fileName = HBufC::NewLC(srcLen);
+	TPtr namePtr1 = fileName->Des();
+	aMessage.ReadL(EIpcArgument0, namePtr1, 0);
+
+	DEBUG_PRINTF3(_L("Sis Registry Server - Subsession ID %d requested hash for file '%S'."),
+		aMessage.Int3(), fileName);
+	
+	SendDataL(aMessage, object.FileDescriptionL(*fileName).Hash(), EIpcArgument1);
+	CleanupStack::PopAndDestroy(fileName);	
+	}	
+	
+void CSisRegistrySession::RequestUidRegistryEntryL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	
+	DEBUG_PRINTF3(_L8("Sis Registry Server - Subsession ID %d has Package UID 0x%08x."),
+		aMessage.Int3(), object.Uid().iUid);
+	
+	TUid uid = object.Uid();
+	TPckg<TUid> packageUid(uid);
+	aMessage.WriteL(EIpcArgument0, packageUid);
+	aMessage.Complete(KErrNone);	
+	}
+	
+void CSisRegistrySession::RequestLanguageRegistryEntryL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	
+	DEBUG_PRINTF3(_L8("Sis Registry Server - Subsession ID %d is localised in language %d."),
+		aMessage.Int3(), object.Language());
+	
+	TLanguage language = object.Language();
+	TPckgC<TLanguage> packageLanguage(language);
+	aMessage.WriteL(EIpcArgument0, packageLanguage);
+	aMessage.Complete(KErrNone);	
+	}
+	
+void CSisRegistrySession::UidPresentRegistryEntryL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	
+	// The file object is not updated, but the cache token is
+	TBool isPresent = Server().Cache().TokenL(object.Uid(), object.Name(), object.Vendor()).PresentState(); 
+	TPckgC<TBool> package(isPresent);
+	
+	DEBUG_CODE_SECTION(
+		if (isPresent)
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package for subsession ID %d is completely present."),
+				aMessage.Int3());
+			}
+		else
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package for subsession ID %d is not completely present."),
+				aMessage.Int3());
+			}
+	);
+	
+	aMessage.WriteL(EIpcArgument0, package);	
+	aMessage.Complete(KErrNone);		
+	}
+	
+void CSisRegistrySession::SignedRegistryEntryL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	
+	TBool isSigned = object.IsSigned(); 	
+	TPckgC<TBool> package(isSigned);
+	
+	DEBUG_CODE_SECTION(
+		if (isSigned)
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package for subsession ID %d is signed."),
+				aMessage.Int3());
+			}
+		else
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package for subsession ID %d is not signed."),
+				aMessage.Int3());
+			}
+	);
+	
+	aMessage.WriteL(EIpcArgument0, package);	
+	aMessage.Complete(KErrNone);			
+	}
+
+void CSisRegistrySession::SignedBySuCertRegistryEntryL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	
+	TBool isSignedBySuCert = object.IsSignedBySuCert(); 	
+	TPckgC<TBool> package(isSignedBySuCert);
+	
+	DEBUG_CODE_SECTION(
+		if (isSignedBySuCert)
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package for subsession ID %d is signed with RU Cert."),
+				aMessage.Int3());
+			}
+		else
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package for subsession ID %d is not signed with RU Cert."),
+				aMessage.Int3());
+			}
+	);
+	
+	aMessage.WriteL(EIpcArgument0, package);	
+	aMessage.Complete(KErrNone);			
+	}
+
+void CSisRegistrySession::RegistryEntryTrustL(const RMessage2& aMessage)
+	{
+	TUint id = aMessage.Int3();
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(id);
+	
+	TSisPackageTrust trust = object.Trust(); 	
+	TPckgC<TSisPackageTrust> package(trust);
+	
+	DEBUG_PRINTF3(_L8("Sis Registry Server - Package trust status for subsession ID %d is %d."),
+		aMessage.Int3(), trust);
+	
+	aMessage.WriteL(0, package);	
+	aMessage.Complete(KErrNone);			
+	}
+
+void CSisRegistrySession::TrustTimeStampL(const RMessage2& aMessage)
+	{
+	TUint id = aMessage.Int3();
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(id);
+	
+	TTime time = object.TrustTimeStamp(); 	
+	TPckgC<TTime> package(time);
+	
+	DEBUG_PRINTF3(_L8("Sis Registry Server - Last package trust update time for subsession %d was %Ld"),
+		aMessage.Int3(), time.Int64());
+	
+	aMessage.WriteL(EIpcArgument0, package);	
+	aMessage.Complete(KErrNone);			
+	}
+
+void CSisRegistrySession::TrustStatusEntryL(const RMessage2& aMessage)
+    {
+	CSisRegistryObject& object = 
+	    Server().Cache().EntryObjectL(aMessage.Int3());
+	
+	TSisTrustStatus status = object.TrustStatus();
+	
+	DEBUG_PRINTF4(_L8("Sis Registry Server - Package for subsession ID %d has Validation Status: %d, Revocation Status: %d."),
+		aMessage.Int3(), status.ValidationStatus(), status.RevocationStatus());
+	
+	SendDataL(aMessage,status,EIpcArgument0);
+    }
+    
+void CSisRegistrySession::RevocationCheckEntryL(const RMessage2& aMessage)
+    {
+    TInt    uid       = aMessage.Int3();
+    TUint   uriLen    = aMessage.GetDesLengthL(EIpcArgument0);
+    HBufC8*  ocspUri   = HBufC8::NewLC(uriLen);
+    
+    TPtr8    ocspPtr   = ocspUri->Des();	    
+    
+    aMessage.ReadL(EIpcArgument0, ocspPtr);
+    
+    CSisRegistryObject& object = 
+	    Server().Cache().EntryObjectL(uid);
+    
+    DEBUG_PRINTF3(_L8("Sis Registry Server - Client has requested a revocation check for package 0x%08x with URI '%S'."),
+    	uid, ocspUri);
+    
+    /*
+     * An array which contains the list of controllers. 
+     * Note that just the first controller is used here.
+     */
+    RPointerArray<HBufC8> array;
+	CleanupResetAndDestroyPushL(array);
+	Server().Cache().GenerateControllersArrayL(object, array);
+	
+	CDesDataProvider* dataProvider = CDesDataProvider::NewLC(*array[0]);
+    
+    Sis::CController* controllers = Sis::CController::NewLC(*dataProvider,
+                                                            Sis::EAssumeType);	
+    
+    iRevocationManager->
+        RevocationStatusRequestL(
+        	array[0], controllers,
+                           const_cast<TSisTrustStatus&>(object.TrustStatus()),
+                           object.InstallChainIndicies(),
+                           ocspPtr,
+                           aMessage);
+
+    array.Remove(0); // remove the buffer passed to the revocation manager
+    CleanupStack::Pop(controllers); // belongs to revocation manager now
+    CleanupStack::PopAndDestroy(3, ocspUri);
+	}
+	
+void CSisRegistrySession::CancelRevocationCheckEntryL(const RMessage2& aMessage)
+    {
+    DEBUG_PRINTF(_L8("Sis Registry Server - Cancelling revocation check."));
+    
+	if (iRevocationManager)   	
+		{
+		iRevocationManager->Cancel();
+		}
+	aMessage.Complete(KErrNone);	
+	}
+		
+void CSisRegistrySession::InRomRegistryEntryL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());	
+	
+	TBool inRom = object.InRom();
+	TPckgC<TBool> package(inRom);
+	
+	DEBUG_CODE_SECTION(
+		if (inRom)
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package for subsession ID %d is in ROM."),
+				aMessage.Int3());
+			}
+		else
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package for subsession ID %d is not in ROM."),
+				aMessage.Int3());
+			}
+	);
+	
+	aMessage.WriteL(EIpcArgument0, package);	
+	aMessage.Complete(KErrNone);	
+	}
+	
+void CSisRegistrySession::PreInstalledRegistryEntryL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());	
+		
+	TBool preInstalled = object.PreInstalled();	
+	TPckgC<TBool> package(preInstalled);
+	
+	DEBUG_CODE_SECTION(
+		if (preInstalled)
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package for subsession ID %d is preinstalled."),
+				aMessage.Int3());
+			}
+		else
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package for subsession ID %d is not preinstalled."),
+				aMessage.Int3());
+			}
+	);
+	
+	aMessage.WriteL(EIpcArgument0, package);	
+	aMessage.Complete(KErrNone);	
+	}
+
+void CSisRegistrySession::DeletablePreInstalledRegistryEntryL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());	
+		
+	TBool deletablePreInstalled = object.DeletablePreInstalled();	
+	TPckgC<TBool> package(deletablePreInstalled);
+	
+	DEBUG_CODE_SECTION(
+		if (deletablePreInstalled)
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package for subsession ID %d is a 'deleteable' presinstalled package."),
+				aMessage.Int3());
+			}
+		else
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package for subsession ID %d is not a 'deleteable' presinstalled package."),
+				aMessage.Int3());
+			}
+	);
+	
+	aMessage.WriteL(EIpcArgument0, package);	
+	aMessage.Complete(KErrNone);	
+	}
+
+void CSisRegistrySession::AugmentationRegistryEntryL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());	
+		
+	TBool aug = (object.InstallType() == Sis::EInstAugmentation);	
+	TPckgC<TBool> package(aug);
+	
+	DEBUG_CODE_SECTION(
+		if (aug)
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package for subsession ID %d is an augmentation."),
+				aMessage.Int3());
+			}
+		else
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package for subsession ID %d is not an augmentation."),
+				aMessage.Int3());
+			}
+	);
+	
+	aMessage.WriteL(EIpcArgument0, package);	
+	aMessage.Complete(KErrNone);	
+	}
+	
+void CSisRegistrySession::RequestSelectedDriveRegistryEntryL(const RMessage2& aMessage)	
+//
+// Request the user selected drive
+//
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	
+	TInt drive = object.SelectedDrive();
+	TPckg<TInt> packageDrive(drive);
+	
+	DEBUG_PRINTF3(_L8("Sis Registry Server - Package for subsession ID %d has selected drive %d"),	
+		aMessage.Int3(), drive);
+	
+	aMessage.WriteL(EIpcArgument0, packageDrive);
+	aMessage.Complete(KErrNone);	
+	}
+
+/**
+* Request the drive bitmask where the files are installed
+*/
+void CSisRegistrySession::RequestInstalledDrivesRegistryEntryL(const RMessage2& aMessage)	
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	
+	TUint drive = object.Drives();
+	TPckg<TUint> installedfilesDrive(drive);
+	
+	DEBUG_PRINTF3(_L8("Sis Registry Server - Package for subsession ID %d has Installed drives bitmask %d"),	
+		aMessage.Int3(), drive);
+	
+	aMessage.WriteL(EIpcArgument0, installedfilesDrive);
+	aMessage.Complete(KErrNone);	
+	}
+
+void CSisRegistrySession::RequestInstallTypeRegistryEntryL(const RMessage2& aMessage)	
+//
+// Request the install type
+//
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	
+	Sis::TInstallType installType = object.InstallType();
+	TPckgC<Sis::TInstallType> packageInstallType(installType);
+	
+	DEBUG_PRINTF3(_L8("Sis Registry Server - Package for subsession ID %d is of type %d."),
+		aMessage.Int3(), installType);
+	
+	aMessage.WriteL(EIpcArgument0, packageInstallType);
+	aMessage.Complete(KErrNone);	
+	}	
+	
+void CSisRegistrySession::RequestPropertyRegistryEntryL(const RMessage2& aMessage)
+//
+// Request the value of property, based on specific property key.
+// if not found returns to client KErrNotFound.
+//
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	
+	TInt value = object.Property(aMessage.Int0());
+
+	DEBUG_PRINTF4(_L8("Sis Registry Server - Value of property %d for subsession ID %d is %d"),
+		aMessage.Int0(), aMessage.Int3(), value);
+
+	TPckgC<TInt> packageValue(value);
+	aMessage.WriteL(EIpcArgument1, packageValue);
+	aMessage.Complete(KErrNone);
+	}
+	
+void CSisRegistrySession::RequestSizeRegistryEntryL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	TInt64 size = object.SizeL();
+	TPckg<TInt64> packageSize(size);
+	
+	DEBUG_PRINTF3(_L8("Sis Registry Server - Package for subsession ID %d takes up %Ld bytes."),	
+		aMessage.Int3(), size);
+	
+	aMessage.WriteL(EIpcArgument0, packageSize);
+	aMessage.Complete(KErrNone);
+	}
+
+void CSisRegistrySession::RequestPackageRegistryEntryL(const RMessage2& aMessage)
+	{
+	CSisRegistryPackage& package = Server().Cache().EntryObjectL(aMessage.Int3());
+	
+	DEBUG_PRINTF5(_L("Sis Registry Server - Package for subsession ID %d is UID: 0x%08x, Name: %S, Vendor: %S."),
+		aMessage.Int3(), package.Uid().iUid, &(package.Name()), &(package.Vendor()));
+	
+	SendDataL(aMessage, package, EIpcArgument0);
+	}
+
+void CSisRegistrySession::RequestFileNamesRegistryEntryL(const RMessage2& aMessage)
+	{
+	TStubExtractionMode tMode;
+	TPckg<TStubExtractionMode> packageMode(tMode);
+	aMessage.ReadL(EIpcArgument0, packageMode, 0);
+	
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	RPointerArray<CSisRegistryFileDescription>& filesDescription = object.FileDescriptions();
+	
+	if (tMode == EGetFiles)
+		{
+		TInt sentFilenamesMemoSize = 0;
+		TInt startingFileNo;	
+		TPckg<TInt> start(startingFileNo);
+		aMessage.ReadL(EIpcArgument1, start, 0);	
+		
+		RPointerArray<TPtrC> fileNames;
+		CleanupResetAndDestroy<RPointerArray<TPtrC> >::PushL(fileNames);
+
+		TInt totalFileDescCount = filesDescription.Count();
+		// Populate the files in to a temporary array.
+		for(TInt fileCount = startingFileNo; fileCount < totalFileDescCount; ++fileCount )
+			{
+			sentFilenamesMemoSize += filesDescription[fileCount]->Target().Size();
+			// If amount of data red exceeds the client buffer size, break reading.
+			if (sentFilenamesMemoSize > KDefaultBufferSize)
+				{
+				break;
+				}
+			
+			// Only create a TPtrC when we know we have space available
+			TPtrC* fileName = new(ELeave) TPtrC(filesDescription[fileCount]->Target());
+			CleanupStack::PushL(fileName);
+			fileNames.AppendL(fileName);
+			CleanupStack::Pop(fileName); 
+			}
+		// Stream via multiple IPC writes instead of
+		// copying to a buffer and streaming from there.
+		RIpcWriteStream ipcstream;
+		ipcstream.Open(aMessage, EIpcArgument2);
+		CleanupClosePushL(ipcstream);
+		ExternalizePointerArrayL(fileNames,ipcstream);
+		ipcstream.CommitL();
+		aMessage.Complete(KErrNone);
+		CleanupStack::PopAndDestroy(&ipcstream);
+		CleanupStack::PopAndDestroy(&fileNames);
+		}
+		// If only the count needed, send the stub file's total entries count.
+	else if (tMode == EGetCount)
+		{
+		TPckgBuf<TInt> fileCount(filesDescription.Count());
+		
+		DEBUG_PRINTF3(_L8("Sis Registry Server - Package for subsession ID %d contains %d file names."),
+				aMessage.Int3(), filesDescription.Count());		
+		
+		aMessage.WriteL(EIpcArgument1, fileCount);
+		aMessage.Complete(KErrNone);					
+		} 
+	else
+		{
+		// No operation mode specified
+		PanicClient(aMessage, EPanicBadOperationMode);
+		}
+	}
+
+// Gets the total numbr of files in a stub file and all the entries as well.
+// The output will be based on the request parameters (operational mode) sent as input.
+void CSisRegistrySession::RequestStubFileEntriesL(const RMessage2& aMessage)
+	{
+	TBool stubNotFound(ETrue);
+	
+	TUid tUid;	
+	TPckg<TUid> packageUid(tUid);
+	aMessage.ReadL(EIpcArgument0, packageUid, 0);
+	
+	TStubExtractionMode tMode;
+	TPckg<TStubExtractionMode> packageMode(tMode);
+	aMessage.ReadL(EIpcArgument1, packageMode, 0);
+	
+	// Prepare the stub file path.
+	TDriveUnit romDrive(EDriveZ);
+	RBuf romRegistryPath;
+	romRegistryPath.CreateL(romDrive.Name(), KMaxPath);
+	CleanupClosePushL(romRegistryPath);
+	romRegistryPath.Append(KPreInstalledPath);	
+
+	RFs tFs;
+	CDir* dir;
+	
+	// Get stub files under the ROM stub directory (Z:\system\install\).
+	User::LeaveIfError(tFs.Connect());
+	CleanupClosePushL(tFs);
+		
+	TInt err = tFs.GetDir(romRegistryPath, KEntryAttMatchExclude | KEntryAttDir, ESortNone, dir);
+
+	if (err == KErrNone)
+		{
+		CleanupStack::PushL(dir);	
+		TInt count(dir->Count());
+		RBuf controllerFileName;
+		controllerFileName.CreateL(KMaxFileName);
+		CleanupClosePushL(controllerFileName);
+		for (TInt index = 0; index < count; ++index)
+			{
+			controllerFileName = romRegistryPath;
+			controllerFileName.Append((*dir)[index].iName);
+
+  			// Read the ROM stub controller
+  			CFileSisDataProvider* fileProvider = CFileSisDataProvider::NewLC(tFs, controllerFileName);
+  			Swi::Sis::CController* stubController = NULL;
+  			TRAPD(errCode, stubController = Swi::Sis::CController::NewL(*fileProvider));
+  			if (errCode != KErrNone)
+	  			{
+	  			// Ignore the broken stub file under the ROM stub directory.
+	  			DEBUG_PRINTF2(_L8("Sis Registry Server - Failed to read the stub controller. Error code %d."), errCode);
+	  			CleanupStack::PopAndDestroy(fileProvider);
+	  			continue;
+	  			}
+  			CleanupStack::PushL(stubController);
+
+  			// If the UID in a stub file matches the current package's UID,
+  			// populate the list of eclipsable files from the same stub file.
+  			if ( stubController->Info().Uid().Uid() == tUid )
+  				{
+  				stubNotFound = EFalse;
+  				const RPointerArray<Sis::CFileDescription>& depArray = stubController->InstallBlock().FileDescriptions();
+  				// Get as many number of files as possible that can be accomodate in client allocated buffer.
+  				if (tMode == EGetFiles)
+  					{
+  					TInt sizeRed = 0;
+  					TInt startingFileNo;	
+					TPckg<TInt> start(startingFileNo);
+					aMessage.ReadL(EIpcArgument2, start, 0);
+  						
+  					RPointerArray<TPtrC> fileNames;
+  					CleanupResetAndDestroy<RPointerArray<TPtrC> >::PushL(fileNames);
+
+  					TInt totalDepArrayCount = depArray.Count();
+  					// Populate the files in to a temporary array.
+  					for(TInt fileCount = startingFileNo; fileCount < totalDepArrayCount; ++fileCount )
+  						{
+  						sizeRed += depArray[fileCount]->Target().Data().Size();
+  						// If amount of data red exceeds the client buffer size, break reading.
+  						if (sizeRed > KDefaultBufferSize)
+  							{
+  							break;
+  							}
+  							
+  						// Only create a TPtrC when we know we have space available
+  						TPtrC* fileName = new(ELeave) TPtrC(depArray[fileCount]->Target().Data());
+  						CleanupStack::PushL(fileName);
+  						fileNames.AppendL(fileName);
+  						CleanupStack::Pop(fileName);   						
+	  					}	  	
+  					// Stream via multiple IPC writes instead of
+  					// copying to a buffer and streaming from there.
+  					RIpcWriteStream ipcstream;
+  					ipcstream.Open(aMessage, EIpcArgument3);
+  					CleanupClosePushL(ipcstream);
+  					ExternalizePointerArrayL(fileNames,ipcstream);
+  					ipcstream.CommitL();
+  					aMessage.Complete(KErrNone);
+  					CleanupStack::PopAndDestroy(&ipcstream);
+  					CleanupStack::PopAndDestroy(&fileNames);					
+  					}
+  				// If only the count needed, send the stub file's total entrie's count.
+  				else if (tMode == EGetCount)
+  					{
+  					TPckgBuf<TInt> fileCount(depArray.Count());
+					aMessage.WriteL(EIpcArgument2, fileCount);
+					aMessage.Complete(KErrNone);					
+  					}  				
+	  			CleanupStack::PopAndDestroy(2, fileProvider);
+	  			break;	
+  				}
+  			CleanupStack::PopAndDestroy(2, fileProvider);  		
+			}
+		CleanupStack::PopAndDestroy(2, dir); // controllerFileName
+		// If the stub file itself not found, leave with the same error info'
+		if (stubNotFound)
+  			{
+  			aMessage.Complete(KErrNotFound);
+  			}		
+		}
+	else if(err != KErrPathNotFound)
+		{
+		aMessage.Complete(err);		
+		}
+	CleanupStack::PopAndDestroy(2, &romRegistryPath); // tFs
+	}
+
+void CSisRegistrySession::RequestFileDescriptionsRegistryEntryL(const RMessage2& aMessage)
+	{
+	// check that it has the right settings 
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+ 
+	RPointerArray<CSisRegistryFileDescription>& filesDescription = object.FileDescriptions();
+	
+	DEBUG_PRINTF3(_L8("Sis Registry Server - Package for subsession ID %d contains %d file descriptions."),
+		aMessage.Int3(), filesDescription.Count());
+	
+	// as a reference to the member is returned no deallocation
+	SendDataPointerArrayL(aMessage, filesDescription, EIpcArgument0);
+	}
+
+void CSisRegistrySession::RequestSidsRegistryEntryL(const RMessage2& aMessage)
+	{
+	// check that it has the right settings 
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	
+	DEBUG_PRINTF3(_L8("Sis Registry Server - Package for subsession ID %d contains %d SIDs."),
+		aMessage.Int3(), object.Sids().Count()); 
+	
+    SendDataArrayL(aMessage, object.Sids(), EIpcArgument0);
+	}
+	
+void CSisRegistrySession::RequestCertificateChainsRegistryEntryL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	RPointerArray<HBufC8> chainList;
+	CleanupResetAndDestroy<RPointerArray<HBufC8> >::PushL(chainList);
+	
+	// only signed entries have certificate chains
+	if (object.IsSigned())
+		{
+		Server().Cache().GenerateChainListL(object, chainList);	 
+		}
+		
+	DEBUG_PRINTF3(_L8("Sis Registry Server - Package for subsession ID %d is signed with %d certificate chains"),
+		aMessage.Int3(), chainList.Count());
+		
+	SendDataPointerArrayL(aMessage, chainList, EIpcArgument0);
+	CleanupStack::PopAndDestroy(&chainList);
+	}
+	
+void CSisRegistrySession::RequestDependenciesRegistryEntryL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	RPointerArray<CSisRegistryDependency> dependencies;
+	CleanupResetAndDestroy<RPointerArray<CSisRegistryDependency> >::PushL(dependencies);
+	
+	object.DependsOnL(dependencies);
+	
+	DEBUG_PRINTF3(_L8("Sis Registry Server - Package for subsession ID %d has %d dependencies."),
+		aMessage.Int3(), dependencies.Count());
+	
+	SendDataPointerArrayL(aMessage, dependencies, EIpcArgument0);
+	CleanupStack::PopAndDestroy(&dependencies);
+	}
+	
+void CSisRegistrySession::RequestDependentPackagesRegistryEntryL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	RPointerArray<CSisRegistryPackage> dependents;
+	CleanupResetAndDestroy<RPointerArray<CSisRegistryPackage> >::PushL(dependents); 
+	// allocates memory
+	Server().Cache().DependentsPackagesL(object, dependents);
+	
+	DEBUG_PRINTF3(_L8("Sis Registry Server - Package for subsession ID %d has %d dependencies."),
+		aMessage.Int3(), dependents.Count());
+	
+	// add
+    SendDataPointerArrayL(aMessage, dependents, EIpcArgument0);
+    // free
+    CleanupStack::PopAndDestroy(&dependents);
+	}
+	
+
+	
+void CSisRegistrySession::RequestEmbeddingPackagesRegistryEntryL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	RPointerArray<CSisRegistryPackage> embeddingPackages;
+	CleanupResetAndDestroy<RPointerArray<CSisRegistryPackage> >::PushL(embeddingPackages);
+	
+	Server().Cache().EmbeddingPackagesL(object, embeddingPackages);
+	
+	DEBUG_PRINTF3(_L8("Sis Registry Server - Package for subsession ID %d (and its partial upgrades) was embedded in %d other packages."),
+		aMessage.Int3(), embeddingPackages.Count());
+    
+    SendDataPointerArrayL(aMessage, embeddingPackages, EIpcArgument0);
+    
+    CleanupStack::PopAndDestroy(&embeddingPackages);
+	}
+
+void CSisRegistrySession::RequestControllersL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	RPointerArray<HBufC8> controllers;
+
+	CleanupResetAndDestroy<RPointerArray<HBufC8> >::PushL(controllers);
+	Server().Cache().GenerateControllersArrayL(object, controllers);
+   
+   	DEBUG_PRINTF3(_L8("Sis Registry Server - Package entry for subsession ID %d has %d controllers."),
+		aMessage.Int3(), controllers.Count());
+
+	TInt len(0);
+   	TPckg<TInt> lenPckg(len);
+   	
+   	// calculate the total length for the buffer.
+   	TInt controllersCount(controllers.Count());
+   	TInt total = controllersCount * lenPckg.Length(); // metadata length
+   	for (TInt i = 0; i < controllersCount; ++i)
+   		{
+   		total += controllers[i]->Length();
+   		}
+   		
+   	if (aMessage.GetDesMaxLengthL(EIpcArgument0) < total)
+		{
+		len = total;
+		aMessage.WriteL(EIpcArgument0, lenPckg);
+		aMessage.Complete(KErrOverflow);
+		}
+	else
+		{
+		TInt pos(0);
+		for (TInt i = 0; i < controllersCount; ++i)
+			{
+			len = controllers[i]->Length();
+			aMessage.WriteL(EIpcArgument0, lenPckg, pos);
+			pos += lenPckg.Length();
+			
+			aMessage.WriteL(EIpcArgument0, *controllers[i], pos);
+			pos += len;
+			}
+		aMessage.Complete(KErrNone);
+		} 
+   
+	//SendDataPointerArrayL(aMessage, controllers, EIpcArgument0);
+	CleanupStack::PopAndDestroy(&controllers);
+	}
+
+void CSisRegistrySession::ShutdownAllAppsL(const RMessage2& aMessage)
+	{
+	TBool shutdownAllApps = EFalse;
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+		
+	// check for the shutdown flag in all controllers
+	TInt count = object.ControllerInfo().Count();
+	TInt i = 0;
+	while (!shutdownAllApps && i < count)
+		{
+		// construct the name using the package and offset
+		HBufC* fileName = SisRegistryUtil::BuildControllerFileNameLC(object.Uid(), object.Index(), 
+			object.ControllerInfo()[i]->Offset());
+		
+		// load the controller directly from the file
+		// DO NOT TRY TO LOAD THE CONTROLLER FROM A BUFFER BECAUSE 
+		// THIS CAN CAUSE SISREGISTRY SERVER TO RUN OUT OF MEMORY.
+		CFileSisDataProvider* dataProvider = CFileSisDataProvider::NewLC(iFs, *fileName);
+		
+		Sis::CController* controller = Sis::CController::NewLC(*dataProvider, Sis::EAssumeType);
+		
+		shutdownAllApps |= (controller->Info().InstallFlags() & Sis::EInstFlagShutdownApps);
+			
+		CleanupStack::PopAndDestroy(3, fileName); // controller, dataprovider, fileName
+		i++;
+		}
+	TPckg<TBool> packageShutdownAllApps(shutdownAllApps);
+	aMessage.WriteL(EIpcArgument0, packageShutdownAllApps);
+	aMessage.Complete(KErrNone);
+	}
+
+void CSisRegistrySession::RequestPackageAugmentationsRegistryEntryL(const RMessage2& aMessage)
+	{
+	// the identity of the current entry/subsession is passed in IPC 3!
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	RPointerArray<CSisRegistryPackage> augmentationPackages;
+	CleanupResetAndDestroy<RPointerArray<CSisRegistryPackage> >::PushL(augmentationPackages);
+	if (object.InstallType() != Sis::EInstAugmentation)
+		{
+		//augmentationPackages = Server().Cache().PackageAugmentationsL(object.Uid());
+		Server().Cache().PackageAugmentationsL(object.Uid(), augmentationPackages);
+		}
+		
+	DEBUG_PRINTF3(_L8("Sis Registry Server - Package for subsession ID %d has %d augmentations."),
+		aMessage.Int3(), augmentationPackages.Count());
+	
+	SendDataPointerArrayL(aMessage, augmentationPackages, EIpcArgument0);
+	CleanupStack::PopAndDestroy(&augmentationPackages);
+	}
+	
+void CSisRegistrySession::RequestPackageAugmentationsNumberL(const RMessage2& aMessage)
+	{
+	// the identity of the current entry/subsession is passed in IPC 3!
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	TInt numAugmentations = 0;
+	
+	if (object.InstallType() != Sis::EInstAugmentation)
+		{
+		numAugmentations = Server().Cache().PackageAugmentationsNumber(object.Uid());
+		}
+	
+	TPckgC<TInt> package(numAugmentations);
+	aMessage.WriteL(EIpcArgument0, package);	
+	aMessage.Complete(KErrNone);
+	}
+	
+void CSisRegistrySession::RequestRegistryEntryL(const RMessage2& aMessage)
+	{
+    TUid uid; 
+	TPckg<TUid> packageUid(uid);
+	
+	aMessage.ReadL(EIpcArgument0, packageUid);
+    
+    // create the entry filename using index 0 (non-augmentation)
+    HBufC* name = SisRegistryUtil::BuildEntryFileNameLC(uid, 0); 
+    
+	RFileReadStream fileStream;
+	User::LeaveIfError(fileStream.Open(iFs, *name, EFileRead | EFileShareReadersOnly));
+	CleanupStack::PopAndDestroy(name);
+	CleanupClosePushL(fileStream);
+	
+	CSisRegistryObject*	object = CSisRegistryObject::NewLC(fileStream);
+	
+  	SendDataL(aMessage, *object, EIpcArgument1);
+  	
+	CleanupStack::PopAndDestroy(2, &fileStream); // fileStream, object
+	}
+
+void CSisRegistrySession::AddDriveL(const RMessage2& aMessage)
+	{
+	TInt drive;
+	TPckg<TInt> pkgDrive(drive);
+	aMessage.ReadL(EIpcArgument0, pkgDrive);
+
+	DEBUG_PRINTF2(_L8("Sis Registry Server - Removable drive %d added."), drive);
+
+	// update the drives state
+	Server().Cache().AddDriveAndRefreshL(drive);
+	aMessage.Complete(KErrNone);
+	}
+
+void CSisRegistrySession::RemoveDriveL(const RMessage2& aMessage)
+	{
+	TInt drive;
+	TPckg<TInt> pkgDrive(drive);
+	aMessage.ReadL(EIpcArgument0, pkgDrive);
+
+	DEBUG_PRINTF2(_L8("Sis Registry Server - Removable drive %d removed."), drive);
+
+	// update the drives state
+	Server().Cache().RemoveDriveAndRefresh(drive);
+	aMessage.Complete(KErrNone);
+	}
+
+void CSisRegistrySession::RequestSidToPackageL(const RMessage2& aMessage)
+	{
+	TUid sid; 
+	TPckg<TUid> executableSid(sid);
+	
+	aMessage.ReadL(EIpcArgument0, executableSid);
+	CSisRegistryPackage& package = Server().Cache().SidToPackageL(sid);
+	
+	DEBUG_PRINTF5(_L("Sis Registry Server - SID 0x%08x is owned by package UID: 0x%08x, Name: %S, Vendor: %S."),
+		sid.iUid, package.Uid().iUid, &(package.Name()), &(package.Vendor()));
+	
+	SendDataL(aMessage, package, EIpcArgument1);
+	}
+
+void CSisRegistrySession::RequestSidToFileNameL(const RMessage2& aMessage)
+	{
+	TBool checkDrive = EFalse;
+	TInt thirdParameter; 
+	TDriveUnit expectedDrive;
+	TUid sid;
+	TPckg<TUid> fileSid(sid);
+	TInt matchingIndex = 0 ;
+
+	// Obtain the sid from argument slot 0 from the client
+	aMessage.ReadL(EIpcArgument0, fileSid);
+
+	// Obtain drive from argument slot 2 from the client.
+	// This parameter will be set to -1 if user did not specified a drive with this request.
+	thirdParameter = aMessage.Int2(); 
+	if(thirdParameter >=0 )
+		{
+		checkDrive = ETrue;
+		expectedDrive = thirdParameter;
+		}
+
+	RArray<CSisRegistryPackage> matchingPkgs;
+	CleanupClosePushL(matchingPkgs);
+	// Get the registry objects matching the sid.
+	Server().Cache().SidToPackageL(sid,matchingPkgs);
+
+	CSisRegistryObject* sidObject = NULL;
+	if(checkDrive) 
+		{
+		// Finds sid that matches expected drive.  
+		for (TInt index =0; index < matchingPkgs.Count(); index++ )
+			{
+			CSisRegistryPackage&  singlePkg = matchingPkgs[index];
+			sidObject = Server().Cache().ObjectL(singlePkg.Uid(),singlePkg.Name(),singlePkg.Vendor());
+			CleanupStack::PushL(sidObject);
+			const CSisRegistryFileDescription& fileNameDesc = sidObject->FileDescriptionL(sid);
+
+			TInt drive; 
+			User::LeaveIfError(RFs::CharToDrive(fileNameDesc.Target()[0], drive));
+			if(drive == expectedDrive )
+				{
+				break;
+				}
+			else
+				{
+				// Destroys object so we continue to next iteration.
+				CleanupStack::PopAndDestroy(sidObject);
+				}
+			}  // End for loop.
+
+		if (!sidObject)
+			{
+			// No match, something has gone wrong, should not arrive to this point.
+			User::Leave(KErrNotFound);
+			}
+		}
+
+	if (!sidObject ) // Only when no drive was especified, matchingIndex will be zero.
+		{
+		CSisRegistryPackage& sidPackage =  matchingPkgs[matchingIndex];
+		sidObject = Server().Cache().ObjectL(sidPackage.Uid(),sidPackage.Name(),sidPackage.Vendor());
+		CleanupStack::PushL(sidObject);
+		}
+
+	const CSisRegistryFileDescription& desc = sidObject->FileDescriptionL(sid);
+
+	// Send the filedescription object back to the client in argument slot 1
+	DEBUG_PRINTF3(_L("Sis Registry Server - SID 0x%08x maps to file '%S'."),sid.iUid, &(desc.Target()));
+	SendDataL(aMessage, desc, EIpcArgument1);		
+
+	CleanupStack::PopAndDestroy(sidObject);
+	CleanupStack::PopAndDestroy(&matchingPkgs);
+	}
+
+void CSisRegistrySession::RequestModifiableL(const RMessage2& aMessage)
+	{
+	// get file name
+	TUint srcLen = aMessage.GetDesLengthL(EIpcArgument0);
+	HBufC* fileName = HBufC::NewLC(srcLen);
+	TPtr namePtr1 = fileName->Des();
+	aMessage.ReadL(EIpcArgument0, namePtr1, 0);
+	
+	TBool modifiableFile = Server().Cache().ModifiableL(*fileName);
+
+	DEBUG_CODE_SECTION(
+		if (modifiableFile)
+			{
+			DEBUG_PRINTF2(_L("Sis Registry Server - File '%S' is modifiable."),
+				fileName);
+			}
+		else
+			{
+			DEBUG_PRINTF2(_L("Sis Registry Server - File '%S' is not modifiable."),
+				fileName);
+			}
+	);
+
+	TPckgC<TBool> isModifiable(modifiableFile);
+	aMessage.WriteL(EIpcArgument1, isModifiable);
+	aMessage.Complete(KErrNone);
+
+	CleanupStack::PopAndDestroy(fileName);	
+	}
+
+void CSisRegistrySession::RequestHashL(const RMessage2& aMessage)
+	{
+	// get file name
+	TUint srcLen = aMessage.GetDesLengthL(EIpcArgument0);
+	HBufC* fileName = HBufC::NewLC(srcLen);
+	TPtr namePtr1 = fileName->Des();
+	aMessage.ReadL(EIpcArgument0, namePtr1, 0);
+
+	DEBUG_PRINTF2(_L("Sis Registry Server - Client requested the hash of file '%S'."),
+		fileName);
+
+	CHashContainer* hashContainer = Server().Cache().HashL(*fileName);
+	CleanupStack::PushL(hashContainer);
+
+	SendDataL(aMessage, *hashContainer, EIpcArgument1);
+
+	CleanupStack::PopAndDestroy(hashContainer);
+	CleanupStack::PopAndDestroy(fileName);
+	}
+	
+void CSisRegistrySession::ServiceError(const RMessage2& aMessage, TInt aError)
+//
+// Handle an error from CSisRegistrySession::ServiceL()
+// A bad descriptor error implies a badly programmed client, so panic it;
+// otherwise use the default handling (report the error to the client)
+//
+	{
+	DEBUG_PRINTF2(_L8("Sis Registry Server - ServiceL left with code %d."), aError);
+	
+	if (aError == KErrBadDescriptor)
+		{
+		PanicClient(aMessage, EPanicBadDescriptor);
+		}
+	CSession2::ServiceError(aMessage, aError);
+	}
+
+template<class T> 
+void SendDataPointerArrayL(const RMessage2& aMessage, const RPointerArray<T> aProvider, TInt aIpcIndx)
+	// templated version for a RPointerArray of T objects 
+	// aMessage - the message
+	// aProvider - the data to be serialised 
+	// aIpcIndx - the index of the IPC argument where the data will be serialised
+	{
+	// dynamic buffer since we don't know in advance the size required
+    CBufFlat* tempBuffer = CBufFlat::NewL(KDefaultBufferSize);
+	CleanupStack::PushL(tempBuffer);
+	
+	RBufWriteStream stream(*tempBuffer);
+	CleanupClosePushL(stream);
+	
+	// externalise the pointer array		
+	ExternalizePointerArrayL(aProvider, stream);
+	stream.CommitL();
+	
+	// Create an HBufC8 from the stream buf's length, and copy 
+	// the stream buffer into this descriptor
+	HBufC8* buffer = HBufC8::NewLC(tempBuffer->Size());
+	TPtr8 ptr(buffer->Des());
+	tempBuffer->Read(0, ptr, tempBuffer->Size());
+	
+    TPtr8 pbuffer(buffer->Des());
+    	
+	if (aMessage.GetDesMaxLengthL(aIpcIndx) < buffer->Size())
+		{
+		TInt bufferSize = buffer->Size();
+		TPckgC<TInt> bufferSizePackage(bufferSize);
+		aMessage.WriteL(aIpcIndx, bufferSizePackage);
+		aMessage.Complete(KErrOverflow);
+		}
+	else
+		{
+		aMessage.WriteL(aIpcIndx, *buffer);
+		aMessage.Complete(KErrNone);
+		}
+		
+	CleanupStack::PopAndDestroy(3, tempBuffer); // tempBuffer, stream, buffer	
+	}
+	
+template<class T> 
+void SendDataArrayL(const RMessage2& aMessage, const RArray<T> aProvider, TInt aIpcIndx)
+	// templated version for a an array of objects
+	// aMessage - the message
+	// aProvider - the data to be serialised 
+	// aIpcIndx - the index of the IPC argument where the data will be serialised
+	{
+	// dynamic buffer since we don't know in advance the size required
+    CBufFlat* tempBuffer = CBufFlat::NewL(KDefaultBufferSize);
+	CleanupStack::PushL(tempBuffer);
+	
+	RBufWriteStream stream(*tempBuffer);
+	CleanupClosePushL(stream);
+		
+	// externalise the array of objects		
+	ExternalizeArrayL(aProvider, stream);
+	stream.CommitL();
+
+	// Now, create an HBufC8 from the stream buf's length, and copy 
+	// the stream buffer into this descriptor
+	HBufC8* buffer = HBufC8::NewLC(tempBuffer->Size());
+	TPtr8 ptr(buffer->Des());
+	tempBuffer->Read(0, ptr, tempBuffer->Size());
+	
+    TPtr8 pbuffer(buffer->Des());
+    	
+	if (aMessage.GetDesMaxLengthL(aIpcIndx) < buffer->Size())
+		{
+		TInt bufferSize = buffer->Size();
+		TPckgC<TInt> bufferSizePackage(bufferSize);
+		aMessage.WriteL(aIpcIndx, bufferSizePackage);
+		aMessage.Complete(KErrOverflow);
+		}
+	else
+		{
+		aMessage.WriteL(aIpcIndx, *buffer);
+		aMessage.Complete(KErrNone);
+		}
+		
+	CleanupStack::PopAndDestroy(3, tempBuffer); // tempBuffer, stream, buffer		
+	}	
+
+template<class T> 
+void SendDataL(const RMessage2& aMessage, const T& aProvider, TInt aIpcIndx)
+	// templated version for a single object 
+	// aMessage - the message
+	// aProvider - the data to be serialised - object 
+	// aIpcIndx - the index of the IPC argument where the data will be serialised
+	{
+	// dynamic buffer since we don't know in advance the size required
+    CBufFlat* tempBuffer = CBufFlat::NewL(KDefaultBufferSize);
+	CleanupStack::PushL(tempBuffer);
+	
+	RBufWriteStream stream(*tempBuffer);
+	CleanupClosePushL(stream);	
+	
+	// externalise the object		
+	aProvider.ExternalizeL(stream);
+	stream.CommitL();
+
+	// Create an HBufC8 from the stream buf's length, and copy 
+	// the stream buffer into this descriptor
+	HBufC8* buffer = HBufC8::NewLC(tempBuffer->Size());
+	TPtr8 ptr(buffer->Des());
+	tempBuffer->Read(0, ptr, tempBuffer->Size());
+	
+    TPtr8 pbuffer(buffer->Des());
+    	
+	if (aMessage.GetDesMaxLengthL(aIpcIndx) < buffer->Size())
+		{
+		TInt bufferSize = buffer->Size();
+		TPckgC<TInt> bufferSizePackage(bufferSize);
+		aMessage.WriteL(aIpcIndx, bufferSizePackage);
+		aMessage.Complete(KErrOverflow);
+		}
+	else
+		{
+		aMessage.WriteL(aIpcIndx, *buffer);
+		aMessage.Complete(KErrNone);
+		}
+	CleanupStack::PopAndDestroy(3, tempBuffer); // tempBuffer, stream, buffer	
+	}
+
+void CSisRegistrySession::RegenerateCacheL(const RMessage2& aMessage)
+	{
+	Server().Cache().RegenerateCacheL();
+	aMessage.Complete(KErrNone);
+	}
+
+void CSisRegistrySession::UpdateTrustStatusL(const TUid& uid, const TSisTrustStatus& status )
+	{
+	Server().Cache().UpdateTrustStatusL(uid, status);
+	}
+
+void CSisRegistrySession::IsSidPresentL(const RMessage2& aMessage)
+/**
+	Handle the EIsSidPresent message by extracting a SID from the
+	message and checking whether is in any registered package.
+	
+	@param	aMessage		Message refers to client-side descriptors
+							which contains SID and boolean.
+ */
+	{
+	TPckgBuf<TUid> uid;
+	aMessage.ReadL(EIpcArgument0, uid);
+	TBool isPresent = Server().Cache().IsSidPresent(uid());
+	
+	DEBUG_CODE_SECTION(
+		if (isPresent)
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - SID 0x%08x is present in registry."),
+				uid().iUid);
+			}
+		else
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - SID 0x%08x is not present in registry."),
+				uid().iUid);
+			}
+	);
+	
+	TPckgBuf<TBool> present(isPresent);
+	aMessage.WriteL(EIpcArgument1, present);
+	aMessage.Complete(KErrNone);
+	}
+	
+void CSisRegistrySession::PackageExistsInRomL(const RMessage2& aMessage)
+/**
+	Handle the EPackageExistsInRom message by extracting a pkg uid in the message 
+		
+	@param	aMessage		Message refers to client-side descriptors
+							which contains a pkg uid to be searched on ROM stub files 
+							and a boolean which holds the return value (string found or not).
+ */
+	{
+	
+    TPckgBuf<TUid> tuid;
+	aMessage.ReadL(EIpcArgument0, tuid);
+	TBool isInRom = SisRegistryUtil::RomBasedPackageL(tuid());
+	
+	TPckgBuf<TBool> present(isInRom);
+	aMessage.WriteL(EIpcArgument1, present);
+	aMessage.Complete(KErrNone);
+	}
+
+
+void CSisRegistrySession::RemoveWithLastDependentL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	
+	TInt isRemoveWithLastDependent = object.RemoveWithLastDependent(); 	
+	TPckgC<TInt> package(isRemoveWithLastDependent);
+	
+	DEBUG_CODE_SECTION(
+		if (isRemoveWithLastDependent)
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package for subsession ID %d will be removed by uninstalling the last dependant."),
+				aMessage.Int3());
+			}
+		else
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package for subsession ID %d will not be removed by uninstalling the last dependant."),
+				aMessage.Int3());
+			}
+	);
+	
+	aMessage.WriteL(EIpcArgument0, package);	
+	aMessage.Complete(KErrNone);			
+	}
+	
+void CSisRegistrySession::SetRemoveWithLastDependentL(const RMessage2& aMessage)
+	{
+	TPckgBuf<TUid> uid;
+	aMessage.ReadL(EIpcArgument0, uid);
+	
+	Server().Cache().SetRemoveWithLastDependentL(uid());
+	
+	aMessage.Complete(KErrNone);			
+	}
+
+void CSisRegistrySession::RequestRemovablePackagesL(const RMessage2& aMessage)
+	{
+    RPointerArray<CSisRegistryPackage> packages; 
+    CleanupResetAndDestroy<RPointerArray<CSisRegistryPackage> >::PushL(packages);
+    Server().Cache().RemovablePackageListL(packages);
+    SendDataPointerArrayL(aMessage, packages, EIpcArgument0);
+    CleanupStack::PopAndDestroy(&packages);
+	}
+		
+void CSisRegistrySession::IsRemovableL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());	
+	
+	TBool isRemovable = object.IsRemovable();
+	TPckgC<TBool> package(isRemovable);
+	
+	DEBUG_CODE_SECTION(
+		if (isRemovable)
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package UID 0x%08x is removable."),
+				object.Uid().iUid);
+			}
+		else
+			{
+			DEBUG_PRINTF2(_L8("Sis Registry Server - Package UID 0x%08x is non-removable."),
+				object.Uid().iUid);
+			}
+	);
+	
+	aMessage.WriteL(EIpcArgument0, package);	
+	aMessage.Complete(KErrNone);
+	}
+	
+void CSisRegistrySession::RecoverL(const RMessage2& aMessage)
+	{
+	Server().Cache().RecoverL();
+	aMessage.Complete(KErrNone);	
+	}
+
+void CSisRegistrySession::LoggingFileInfoL(const RMessage2& aMessage)
+ 	{
+ 	RFile file;
+ 	
+ 	TDriveUnit sysDrive(RFs::GetSystemDrive());
+	TBuf<128> logDir = sysDrive.Name();
+	logDir.Append(KLogDir);
+		
+ 	TInt err = file.Open(iFs,logDir,EFileRead|EFileShareExclusive);
+ 	if(err == KErrNone)
+		{
+		CleanupClosePushL(file);
+	 	TInt fileSize;
+	 	file.Size(fileSize);
+	 	
+	 	HBufC8* buffer = HBufC8::NewLC(2);
+	 	TPtr8 ptr = buffer->Des();
+	 	file.Read(ptr,2); 	
+	 	RDesReadStream stream(ptr);
+	 	CleanupClosePushL(stream);
+	 	CLogFileVersion* logVer = CLogFileVersion::NewL(stream);
+	 	CleanupStack::PushL(logVer);
+	 	
+	 	HBufC8* buf = HBufC8::NewLC(fileSize-2);
+	 	TPtr8 filePtr = buf->Des();
+	 	file.Read(filePtr,fileSize - 2); 
+	 	
+	 	aMessage.WriteL(EIpcArgument0,filePtr);
+	 	CleanupStack::PopAndDestroy(5,&file);	//file,buffer,stream,logVer,buf
+	 	aMessage.Complete(KErrNone);
+		}
+	else 
+		{
+		aMessage.Complete(KErrNone);
+		}		
+ 	}
+
+void CSisRegistrySession::RequestMatchingSupportedLanguagesL(const RMessage2& aMessage)
+	{
+	CSisRegistryObject& object = Server().Cache().EntryObjectL(aMessage.Int3());
+	
+	RArray<TInt>& supportedLanguageIds = object.GetSupportedLanguageIdsArray(); 	
+	SendDataArrayL(aMessage, supportedLanguageIds, EIpcArgument0);	
+	}