installationservices/swi/inc/securitymanager.h
changeset 0 ba25891c3a9e
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/installationservices/swi/inc/securitymanager.h	Thu Dec 17 08:51:10 2009 +0200
@@ -0,0 +1,580 @@
+/*
+* Copyright (c) 1997-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: 
+*
+*/
+
+
+/**
+ @file
+ @released
+ @internalTechnology
+*/
+
+
+#ifndef __SECURITYMANAGER_H__
+#define __SECURITYMANAGER_H__
+
+#include <e32base.h>
+#include <securitydefs.h>
+#include <ct/rmpointerarray.h>
+#include <swi/msisuihandlers.h>
+#include "swi/siscontroller.h"
+#include "securitypolicy.h"
+#include <pkixcertchain.h>
+
+class CCTCertInfo;
+class CSWICertStore;
+class TCertMetaInfo;
+
+namespace Swi 
+{
+
+class CChainValidator;
+class CCertificateRetriever;
+class CRevocationHandler;
+class CHashContainer;
+
+namespace Sis
+	{
+	class CSignatureCertificateChain;
+	}
+
+class MSisDataProvider;
+
+enum TDevCertWarningState
+	{
+	ENoDevCerts	=0,
+	EFoundDevCerts	=1,
+	EDevCertsWarned =2	
+	};	
+	
+/** 
+ * The SecurityManager is the SWI component which takes care of the cryptographic
+ * protections in the installation process. Specifically it verifies the signatures
+ * in signed SISX files, validates their corresponding certificate chains,
+ * builds the list of granted capabilities and enforces mandatory certificates
+ * constraints. Moreover, driven from a compile time modifiable security policy,
+ * enforces additional constraints on the valid certificates, e.g. Code Signing 
+ * and other X509 extensions. It performs OCSP checks for the relevant certificate
+ * chains as well. 
+ * <P>
+ * To accomplish its task the Security Manager relies on a number of helper 
+ * classes:
+ * <ul>
+ *   <li> CCertificateRetriever to retrieve mandatory certificates
+ *   <li> CSignatureVerifier to verify signatures
+ *   <li> CChainValidator to validate PKIX certificate chains
+ *   <li> CRevocationHandler to perform OCSP checks
+ *   <li> CSecurityPolicy to access the compile time configurable security policy
+ * </ul>
+ * 
+ * @released
+ * @internalTechnology 
+ */
+class CSecurityManager : public CActive
+	{
+
+public: // life-cycle methods
+
+	/**
+	 * Constructs a new CSecurityManager object
+	 *
+	 * @return A new security manager
+	 */
+	IMPORT_C static CSecurityManager* NewL();
+	
+	/**
+	 * Constructs a new CSecurityManager object and leaves it on the cleanup stack
+	 *
+	 * @return A new security manager
+	 */
+	IMPORT_C static CSecurityManager* NewLC();
+	
+	virtual ~CSecurityManager();
+
+public: // from CActive 
+
+	void RunL();
+	void DoCancel();
+	TInt RunError(TInt aError);	
+		
+
+public: // business methods
+
+	/**
+	 * This method verifies a SISX controller. It checks:
+	 * <ul>
+	 *   <li> Whether the controller is signed
+	 *   <li> Whether at least a signature per certificate chain can be 
+	 *        verified
+	 *   <li> Whether at least a certificate chain can be validated 
+	 *        successfully
+	 *   <li> Whether we can meet all the mandatory certificate requirements
+	 *   <li> Hands over a collection of capabilities the controller has been 
+	 *        signed for
+	 * </ul>
+	 *
+	 * @param aControllerBinary The raw controller data.
+	 * @param aController       An instance of Sis::CController representing 
+	 *                          the raw data
+	 * @param aResultOut        A global result of the operation        
+	 * @param aPkixResultsOut   A list of PKIX validation results. To each of 
+	 *                          this corresponds an end entity certificate in 
+	 *                          aCertsOut
+	 * @param aCertsOut         A list of end entity certificates 
+	 * @param aCapabilitySetOut The set of capabilities the controller has been
+	 *                          signed for
+	 * @param aAllowUnsigned    Receives policy flag that controls installation
+	 *                          of unsigned SIS files
+	 * @param aIsEmbeddedController Controller is embedded.
+	 * @param aStatus           The client request status
+	 * @param aCheckDateAndTime Indicates whether the validity periods of the certificates 
+	 							in the chain are checked and verified.  A value of ETrue 
+	 							indicates they are.
+	 */
+	IMPORT_C void VerifyControllerL(
+					TDesC8& aControllerBinary, 
+					const Sis::CController& aController, 
+					TSignatureValidationResult* aResultOut,
+					RPointerArray<CPKIXValidationResultBase>& aPkixResultsOut,
+					RPointerArray<CX509Certificate>& aCertsOut,
+					TCapabilitySet* aCapabilitySetOut,
+					TBool& aAllowUnsigned,
+					TBool& aIsEmbeddedController,
+					TRequestStatus& aStatus,
+					TBool aCheckDateAndTime = ETrue);
+
+    /**
+	 * This method verifies a SISX controller given a list of chain indices. 
+	 * It checks:
+	 * <ul>
+	 *   <li> Whether the controller is signed
+	 *   <li> Whether at least a signature per certificate chain can be 
+	 *        verified
+	 *   <li> Whether at least a certificate chain can be validated 
+	 *        successfully
+	 *   <li> Whether we can meet all the mandatory certificate requirements
+	 *   <li> Hands over a collection of capabilities the controller has been 
+	 *        signed for
+	 * </ul>
+	 *
+	 * @param aControllerBinary The raw controller data.
+	 * @param aController       An instance of Sis::CController representing 
+	 *                          the raw data.
+	 * @param aChainListIndices List of indices to chains to be validated.
+	 * @param aResultOut        A global result of the operation.
+	 * @param aPkixResultsOut   A list of PKIX validation results. To each of 
+	 *                          this corresponds an end entity certificate in 
+	 *                          aCertsOut.
+	 * @param aCertsOut         A list of end entity certificates 
+	 * @param aCapabilitySetOut The set of capabilities the controller has been
+	 *                          signed for.
+	 * @param aAllowUnsigned    Receives policy flag that controls installation
+	 *                          of unsigned SIS files.
+	 * @param aStatus           The client request status.
+	 */		
+	IMPORT_C void ReverifyControllerL(
+					TDesC8& aControllerBinary, 
+					const Sis::CController& aController, 
+					const RArray<TInt>& aChainListIndices,
+					TSignatureValidationResult* aResultOut,
+					RPointerArray<CPKIXValidationResultBase>& aPkixResultsOut,
+					RPointerArray<CX509Certificate>& aCertsOut,
+					TCapabilitySet* aCapabilitySetOut,
+					TBool& aAllowUnsigned,
+					TRequestStatus& aStatus);
+
+	/**
+	 * Verifies the hash of a the data pointed to by a given data provider.
+	 *
+	 * @param aDataProvider A data provider which gives access to the file we want to check
+	 * @param aDigest The digest of the data pointed to by the given data provider
+	 *
+	 * @return ETrue if the has could be verified, EFalse otherwise.
+	 */								
+	IMPORT_C TBool VerifyFileHashL(MSisDataProvider& aDataProvider,
+								   const CHashContainer& aDigest);
+
+	/**
+	 * Perform an OCSP check on the certificate chain which have been 
+	 * previously validated by a call to VerifyControllerL(). This method can 
+	 * be called \b only after VerifyControllerL(). This makes the Security 
+	 * Manager a stateful object. But this is better than requiring the caller
+	 * to store all the intermediate data.
+	 *
+	 * @param aOcspUri              [in]  The default OCSP URI as specified by 
+	 *                                    the UI or read from the policy.
+	 * @param aIap					[in, out] The IAP to use for this connection 
+	 *									  (zero means show dialog)
+	 * @param aRevocationMessageOut [out] An output paramter containing the 
+	 *                                    result of the check
+	 * @param aOcspOutcomeOut       [out] A list of OCSP outcomes. To each of 
+	 *                                    this corresponds a certificate in the 
+	 *                                    \e aCertOut list.
+	 * @param aCertOut              [out] A list of end entity certificates.
+	 * @param aStatus               [in,out] The client status which will be 
+	 *                                    completed upon termination.
+	 */								
+	IMPORT_C void PerformOcspL(const TDesC8&  aOcspUri, 
+							   TUint32& aIap,
+							   TRevocationDialogMessage* aRevocationMessageOut, 
+							   RPointerArray<TOCSPOutcome>& aOcspOutcomeOut, 
+							   RPointerArray<CX509Certificate>& aCertOut,
+							   TRequestStatus& aStatus);
+							   
+	/**
+	 * Fills certificate info array from the X509 certificate array which was
+	 * filled by the security manager.
+	 *
+	 * @param aCertificates [in]  Array of X509 certificates constructed from 
+	 *                            controller.
+	 * @param aCertInfos    [out] Array of certificate info objects.
+	 */
+	IMPORT_C static void FillCertInfoArrayL(
+		const RPointerArray<CX509Certificate>& aCertificates,
+		RPointerArray<CCertificateInfo>& aCertInfos);
+	
+	/**
+	 * Retrieves end certificates from iController and stores them in 
+	 * iCertificates.
+	 *
+	 * @param aController [in]  SIS controller object.
+	 * @param aCerts      [out] Receives EE certificates from the controller.
+	 */
+	IMPORT_C void GetCertificatesFromControllerL(
+		const Sis::CController& aController,
+		RPointerArray<CX509Certificate>& aCerts);
+
+	/**
+	 * Returns the security policy associated with the security manager.
+	 *
+	 * @return The security policy object associated with the security manager.
+	 */
+	IMPORT_C CSecurityPolicy& SecurityPolicy() const;
+
+	/**
+	 * Returns the DeviceIDs retrieved from the Mobile.
+	 *
+	 * @return The array of the device IDs.
+	 */
+	IMPORT_C const RPointerArray<HBufC>& DeviceIDsInfo() const;
+	
+	/**
+	 * Resets Security Manager's list of valid certificate chains.
+	 * This is required to ensure that embedded SIS files do not include the certificate
+	 * chains of their parent SIS file.
+	 */
+	IMPORT_C void ResetValidCertChains();	
+
+	/** Calculates the hash of a file
+	@param aDataProvider Provides access to the data from the file
+	@param aAlgorithm The algorithm used to generate the hash
+	@return A buffer containing the hash result
+	*/
+	IMPORT_C HBufC8* CalculateHashLC(MSisDataProvider& aDataProvider, CMessageDigest::THashId aAlgorithm);
+	
+	/**
+	Set the devcert warning state.
+	@param aDevCertWarningState developer mode certificate warning state
+	@return none
+	*/
+	IMPORT_C void SetDevCertWarningState(TInt aDevCertWarningState);
+
+	/**
+	Get the devcert warning state.
+	@param aDevCertWarningState developer mode certificate warning state
+	@return none
+	*/
+	IMPORT_C TInt GetDevCertWarningState();
+	
+	/*
+	 * This function sets the user provided list of root certs. These certs will be used
+	 * for validation instead of fetching root certs from the certstore for validation.
+	 *
+	 * @param aX509CertArray caller provided list of root certs.
+	 * @return none
+	 */
+	IMPORT_C void SetRootCerts(RPointerArray<CX509Certificate>* aX509CertArray);
+	
+	
+protected: // Helper functions
+
+	/**
+	 * This helper function verifies a given certificate/signature block.
+	 * The signature block structure is defined in 
+	 * SGL.GT0188.251  Paragraph 4.3
+	 * Each block may contain multiple signatures using different
+	 * signature schemes.
+	 *
+	 * @param aChainIndex The index of the chain in iChains which is to be verified.
+	 */
+	void VerifyBlockL(TInt aChainIndex);
+
+	/**
+	 * This helper function calculates the size of the raw
+	 * SISX controller data.
+	 *
+	 * @param iChainsToAdd How many certificate/signature chains to add to the size
+	 *                     starting from the most internal one.
+	 *
+	 * @return The controller size (including iChainsToAdd certificate chains)
+	 */
+	TInt SignedSize(TInt iChainsToAdd) const;
+		
+	/**
+	 * It reduces the count based on the given certificate from the iMandatoryCertDNCount (count of mandatory 
+	 * certificates). If the certificate is not found nothing happens. Note 
+	 * that for a controller to be successfully validated the iMandatoryCertDNCount must 
+	 * be zero.
+	 *
+	 * @param aCertificate The certificate to be compared
+	 */
+	void UpdateListOfMissingRequiredCertsL(const CCertificate& aCertificate); 
+	
+	/**
+	 * It update the given certificate to be validated by System upgrade if the certificate is found in the  
+	 * trust anchors list. If the certificate is not found nothing happens. 
+	 *
+	 * @param aCertificate The certificate to be compared
+	 */
+	void UpdateSystemUpgradeCertStatusL(const CCertificate& aCertificate);
+	
+	/**
+	 * Translates the set of TOCSPOutcome values into a single 
+	 * TRevocationDialogMessage value and sets iRevocationMessage to this value.
+	 */
+	void ProcessOcspOutcomesL();
+	
+private:
+
+	CSecurityManager();
+
+	/**
+	 * Second phase constructor for CSecurityManager. It attempts to construct
+	 * a CSecurityPolicy object, consequently it accesses the security policy
+	 * file. If for any reason no such file is present this method will leave.
+	 * This renders impossible to create a security manager and, hence, to 
+	 * perform an installation.
+	 */
+	void ConstructL();
+	
+
+private: // fields
+
+	/**
+	 * The list of SisSignatureCertificateChain blocks in the actual
+	 * controller. Each of these must be validated.
+	 *
+	 */
+	RPointerArray<Sis::CSignatureCertificateChain> iChains; // We do not own this!
+	
+	/**
+	 * The list of the validation results. Each of this corresponds
+	 * to the SisSignatureCertificateChain in iChains of corresponding
+	 * index. This list is populated by VerifyBlockL(), the PKIX 
+	 * validator sets the result during the validation process.
+	 */
+	RPointerArray<CPKIXValidationResultBase>* iValidationResultsOut;
+
+	/**
+	 * List of the successfully constructed PKIX chains.
+	 * This list contains only the chains which have been
+	 * successfully validated.
+	 */
+	RPointerArray<CX509Certificate>* iEndCertificatesOut;
+
+	/**
+	 * The total capabilities so far. This is the union of the
+	 * capabilities of every root of every pkix chain which 
+	 * has validated successfully.
+	 */
+	TCapabilitySet* 				 iTotalCapabilitiesOut;
+
+	RPointerArray<TOCSPOutcome>*	 iOcspOutcomeOut;
+
+	TRevocationDialogMessage*		 iRevocationMessage;
+	
+	TSignatureValidationResult* 	 iResult;
+
+	/**
+	 * Count of the mandatory certificates in the certstore.
+	 * SISX files must be signed by chains which resolve
+	 * to <b>all</b> of them. See SGL.GT0209.201
+	 */
+	TInt iMandatoryCertDNCount;
+	
+	/**
+	 * A parsed version of the SisController which is signed.
+	 * This is passed to us by the client. We need it to calculate
+	 * the amount of data signed by each signature.
+	 */
+	const Sis::CController* iController;  // We do not own this!
+
+	/**
+	 * A raw version of the SisController which is signed.
+	 * This is passed to us by the client. We need it to verify
+	 * the signatures.
+	 */
+	TPtrC8 iRawController;
+		
+	/**
+	 * A book keeping index pointing to the current certificate chain
+	 * being examined. It starts from 0 (the innermost certificate chain
+	 * in the controller)
+	 */		
+	TInt iCurrentChain;
+
+	/** 
+	 * A book keeping flag indicating whether any certificate chain has
+	 * been validated successfully.
+	 */
+	TBool iHasValidated;
+	
+	/**
+	 * The capability set associated with the root (if any) of the
+	 * current certificate. This value is set by the chain validator.
+	 */
+	TCapabilitySet iCurrentCapabilities;
+
+	/**
+	 * The current PKIX chain which is being constructed.
+	 */
+	CPKIXCertChainBase* iCurrentPkixChain;
+
+	/**
+	 * A list of all the PKIX chains which have been successfully
+	 * validated. If an OCSP check is requested, these chains will
+	 * undergo the check.	
+	 */
+	RPointerArray<CPKIXCertChainBase> iValidPkixChains;
+
+	/** 
+	 * Access the SWIS security policy which drives some of our
+	 * decision making. E.g. whether end certificated must contain
+	 * a CodeSigning extension, etc.
+	 */
+	CSecurityPolicy* iSecPolicy;
+
+	/**
+	 * The underlying backend certificate store
+	 */
+	CSWICertStore* iCertStore;
+
+	/**
+	 * Helper class which retrieves all the <i>mandatory</i>
+	 * certificates in the certstore.
+	 */
+	CCertificateRetriever* iCertificateRetriever;
+
+	/**
+	 * Helper class to validate a certificate chain. 
+	 * It also collects the capabilities associated with
+	 * its root (if any) and whether the root (if any) is
+	 * marked as mandatory.
+	 */
+	CChainValidator* iChainValidator;
+
+	/**
+	 * Helper class which takes care of OCSP checks
+	 */
+	CRevocationHandler* iRevocationHandler;
+	
+ 	/**
+ 	 * 
+	 * A list of self-signed, untrusted root certificates
+ 	 * included in the chain currently being validated.
+	 *
+	 */ 
+ 	 RPointerArray<CX509Certificate> iUntrustedRoots;
+ 	 
+     // A book keeping flag indicating at least one 
+     // chain has validated that isn't self signed
+     
+     TBool iHasValidatedTrusted;
+     
+     // A list of all the roots in the SWI certstore
+     
+     RMPointerArray<CCTCertInfo> iTrustedRoots;
+     
+     TBool iIsEmbeddedController;
+     
+    /**
+ 	 * 
+	 * A list chain indices to be validated by ReverifyControllerL.
+	 *
+	 */
+     const RArray<TInt>* iChainListIndices;
+   
+	/** 
+	 * The internal state of the security manager.
+	 */
+    enum TSecManState
+	   {
+	   // Verification and validation
+	   EBuildCertificateList,
+  	   EValidatingChain,
+  	   
+  	   // Reverification and validation of chain set for revocation check
+  	   ERevalidatingChain,
+  	   
+  	   // OCSP Check
+   	   EOCSPCheck,
+   	   EChecksDone,
+   	   ERetrievedTrustedRoots
+       } iState;	
+	
+	/**
+	 * A pointer to the client request status.
+	 */
+	TRequestStatus* iClientStatus;
+		
+	/**
+	 * Handle to File server session
+	 */
+	 RFs iFs;
+ 	 
+	/**
+	 * Device ID retrieved from the device using RDeviceInfo API
+	 */
+	RPointerArray<HBufC> iDeviceIDs;
+
+	/**
+	Represent if the deveploper mode certificate is in the cert chains of an application,
+	or it is found but not warned to the user, or the user has been warned.  
+	*/	
+	TDevCertWarningState iDevCertWarningState;	
+	
+	/*
+	 * This member pointer is used to hold user provided list of root cert for 
+	 * certificate validation. The ownership of this variable remains with the
+	 * caller of SetRootCerts function.
+	 */
+
+	RPointerArray<CX509Certificate>* iRootCerts;
+
+	/**
+	 * Additional Information about the Certificate in the Certstore.
+	 */
+	RArray<TCertMetaInfo> iCertMetaInfo;
+	
+	/**
+	 * Indicates when verifying the certificate if we check the validity period.
+	 */
+	TBool iCheckDateAndTime;
+	};
+
+} //namespace Swi
+
+#endif // #ifndef __SECURITYMANAGER_H__