cryptomgmtlibs/cryptotokenfw/source/ctframework/SecurityDialog.cpp
changeset 0 2c201484c85f
child 8 35751d3474b7
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/cryptomgmtlibs/cryptotokenfw/source/ctframework/SecurityDialog.cpp	Wed Jul 08 11:25:26 2009 +0100
@@ -0,0 +1,617 @@
+/*
+* Copyright (c) 2001-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: 
+*
+*/
+
+
+#include "CRefSecurityDialog.h"
+
+// ----------------------------------------------------------------------------
+// SecurityDialogFactory
+//
+
+EXPORT_C MSecurityDialog* SecurityDialogFactory::CreateL()
+	{
+	return CRefSecurityDialog::NewL();
+	}
+
+
+
+// ----------------------------------------------------------------------------
+// CRefSecurityDialog
+//
+
+
+
+CRefSecurityDialog::~CRefSecurityDialog()
+	{
+	delete iRequester;
+	}
+
+void CRefSecurityDialog::Release()
+	{
+	delete this;
+	}
+
+
+CRefSecurityDialog* CRefSecurityDialog::NewL()
+	{
+	CRefSecurityDialog* self = new (ELeave) CRefSecurityDialog();
+	CleanupStack::PushL( self );
+	self->ConstructL();
+	CleanupStack::Pop( self );
+	return self;
+	}
+
+
+
+void CRefSecurityDialog::ConstructL()
+	{
+	iRequester = CDialogRequester::NewL( *this );
+	}
+
+
+
+void CRefSecurityDialog::EnterPIN( const TPINParams& aPINParams, TBool aRetry,
+										   TPINValue& aPINValue, TRequestStatus& aStatus )
+	{
+	iClientPINValuePtr = &aPINValue;
+	DoBasicPINOperation( EEnterPIN, aPINParams, aRetry, iPINValueBuf, aStatus );
+	}
+
+
+
+void CRefSecurityDialog::EnablePIN( const TPINParams& aPINParams, TBool aRetry,
+											TPINValue& aPINValue, TRequestStatus& aStatus )
+	{
+	iClientPINValuePtr = &aPINValue;
+	DoBasicPINOperation( EEnablePIN, aPINParams, aRetry, iPINValueBuf, aStatus );
+	}
+
+
+
+void CRefSecurityDialog::DisablePIN( const TPINParams& aPINParams, TBool aRetry,
+											 TPINValue& aPINValue, TRequestStatus& aStatus )
+	{
+	iClientPINValuePtr = &aPINValue;
+	DoBasicPINOperation( EDisablePIN, aPINParams, aRetry, iPINValueBuf, aStatus );
+	}
+
+
+
+void CRefSecurityDialog::ChangePIN( const TPINParams& aPINParams, TBool aRetry,
+											TPINValue& aOldPINValue, TPINValue& aNewPINValue,
+											TRequestStatus& aStatus )
+	{
+	iClientPINValuePtr = &aOldPINValue;
+	iClientSecondPINValuePtr = &aNewPINValue;
+	DoBasicPINOperation( EChangePIN, aPINParams, aRetry, iTwoPINOutputBuf, aStatus );
+	}
+
+
+
+void CRefSecurityDialog::UnblockPIN( const TPINParams& aBlockedPINParams,
+						 const TPINParams& aUnblockingPINParams, TBool aRetry,
+						 TPINValue& aUnblockingPINValue, TPINValue& aNewPINValue,
+						 TRequestStatus& aStatus )
+	{
+	iCurrentOperation = EUnblockPIN;
+	InitClientStatus( aStatus );
+
+	TUnblockPINInput unblockPINInput;
+	unblockPINInput.iOperation = EUnblockPIN;
+	if ( aRetry )
+		{
+		unblockPINInput.iOperation |= EPINValueIncorrect;
+		}
+	unblockPINInput.iPIN = aBlockedPINParams;
+	unblockPINInput.iUnblockPIN = aUnblockingPINParams;
+	TUnblockPINInputBuf unblockPINInputBuf( unblockPINInput );
+	iUnblockPINInputBuf.Copy( unblockPINInputBuf );
+	iClientPINValuePtr = &aUnblockingPINValue;
+	iClientSecondPINValuePtr = &aNewPINValue;
+
+	iRequester->RequestDialog( iUnblockPINInputBuf, iTwoPINOutputBuf );
+	}
+
+void CRefSecurityDialog::UnblockPINInClear( const TPINParams& aBlockedPINParams,
+									const TPINParams& aUnblockingPINParams, TBool aRetry,
+									TUnblockPINValue& aUnblockingPINValue, TPINValue& aNewPINValue,
+									TRequestStatus& aStatus )
+	{
+	iCurrentOperation = EUnblockPINInClear;
+	InitClientStatus( aStatus );
+
+	TUnblockPINInput unblockPINInput;
+	unblockPINInput.iOperation = EUnblockPINInClear;
+	if ( aRetry )
+		{
+		unblockPINInput.iOperation |= EPINValueIncorrect;
+		}
+	unblockPINInput.iPIN = aBlockedPINParams;
+	unblockPINInput.iUnblockPIN = aUnblockingPINParams;
+	TUnblockPINInputBuf unblockPINInputBuf( unblockPINInput );
+
+	iClientUnblockPINValuePtr = &aUnblockingPINValue;
+	iClientSecondPINValuePtr = &aNewPINValue;
+	iUnblockPINInputBuf.Copy( unblockPINInputBuf );
+	iRequester->RequestDialog( iUnblockPINInputBuf, iUnblockPINInClearOutputBuf );
+	}
+
+void CRefSecurityDialog::Cancel()
+	{
+	iRequester->Cancel();
+	if (iClientStatus)
+		{
+		User::RequestComplete(iClientStatus, KErrCancel);
+		}
+	}
+
+void CRefSecurityDialog::PINBlocked( const TPINParams& aPINParams,
+											  TRequestStatus& aStatus )
+	{
+	iCurrentOperation = EPINBlocked;
+	TPckg<TPINValue> pinValueBuf( KNullDesC() );
+	DoBasicPINOperation( EPINBlocked, aPINParams, EFalse, pinValueBuf, aStatus );
+	}
+
+
+void CRefSecurityDialog::TotalBlocked( const TPINParams& aPINParams,
+											  TRequestStatus& aStatus )
+	{
+	iCurrentOperation = ETotalBlocked;
+	TPckg<TPINValue> pinValueBuf( KNullDesC() );
+	DoBasicPINOperation( ETotalBlocked, aPINParams, EFalse, pinValueBuf, aStatus );
+	}
+
+
+
+void CRefSecurityDialog::EstablishSecureConnection( const TDesC8& aCertData,
+						const RArray<TCTTokenObjectHandle>& aCertHandleList,
+						MSecurityDialog::TConnectionType aConnectionType,
+						TBool& aDoClientAuthentication, TCTTokenObjectHandle& aCertHandle,
+						TRequestStatus& aStatus )
+	{
+	iCurrentOperation = ESecureConnection;
+	InitClientStatus( aStatus );
+	
+	TInt certDataSize = aCertData.Size();
+	TSignInput signInput;
+	signInput.iOperation = ESecureConnection;
+	signInput.iVariableDataSize = certDataSize;
+	signInput.iCertHandleArrayTotal = aCertHandleList.Count();
+	signInput.iDoClientAuthentication = aDoClientAuthentication;
+	signInput.iConnectionType = aConnectionType;
+	TPckgC<TSignInput> signInputBufPtr( signInput );
+	// iSignInputBuf is persistent because further input processing occurs in the AO before
+	// calling the notifier.
+	iSignInputBuf.Copy( signInputBufPtr );
+	iVariableDataPtr.Set( aCertData );
+
+	iClientDoClientAuthenticationPtr = &aDoClientAuthentication;
+	iClientCertInfoHandlePtr = &aCertHandle;
+	
+	iRequester->RequestVariableBufferDialog( iSignInputBuf, iVariableDataPtr,
+											aCertHandleList, iCertInfoHandleBuf );
+	}
+
+
+
+void CRefSecurityDialog::SignText( const TDesC& aTextToSign,
+									const RArray<TCTTokenObjectHandle>& aCertHandleList, 
+									TCTTokenObjectHandle& aCertHandle,
+									TRequestStatus& aStatus )
+	{
+	iCurrentOperation = ESignText;
+	InitClientStatus( aStatus );
+
+	TInt textSize = aTextToSign.Size();
+	TSignInput signInput;
+	signInput.iOperation = ESignText;
+	signInput.iVariableDataSize = textSize;
+	signInput.iCertHandleArrayTotal = aCertHandleList.Count();
+	TPckgC<TSignInput> signInputBufPtr( signInput );
+	// iSignInputBuf is persistent because further input processing occurs in the AO before
+	// calling the notifier.
+	iSignInputBuf.Copy( signInputBufPtr );
+	const TUint8* textToSignPtr = reinterpret_cast<const TUint8*>( aTextToSign.Ptr() );
+	iVariableDataPtr.Set( textToSignPtr, textSize );
+
+	iClientCertInfoHandlePtr = &aCertHandle;
+
+	iRequester->RequestVariableBufferDialog( iSignInputBuf, iVariableDataPtr,
+											aCertHandleList, iCertInfoHandleBuf );
+	}
+
+void CRefSecurityDialog::ServerAuthenticationFailure(const TDesC8& aServerName,const TValidationError& aFailureReason, const TDesC8& aEncodedCert,TRequestStatus& aStatus )
+	{
+	iCurrentOperation = EServerAuthenticationFailure;
+	InitClientStatus( aStatus );
+
+	CServerAuthenticationFailureInput* serverAuthenticationFailureInput = NULL;
+	TRAPD(err, serverAuthenticationFailureInput = CServerAuthenticationFailureInput::NewL(aServerName, aFailureReason, aEncodedCert));
+
+	// Ownership of the inputBuffer will pass to the requester.
+	HBufC8* inputBuffer = NULL;
+	if (err == KErrNone)
+		TRAP(err, inputBuffer = serverAuthenticationFailureInput->PackBufferL());
+
+	delete serverAuthenticationFailureInput;
+
+	if (err == KErrNone)
+		iRequester->RequestDialog(inputBuffer, iServerAuthenticationOutputBuf);
+	else
+		HandleResponse(err);
+	}
+
+void CRefSecurityDialog::DoBasicPINOperation( TSecurityDialogOperation aOperation,
+								const TPINParams& aPINParams, TBool aRetry, TDes8& aPINValue,
+								TRequestStatus& aStatus )
+	{
+	iCurrentOperation = aOperation;
+	InitClientStatus( aStatus );
+	TPINInput pinInput;
+	pinInput.iOperation = aOperation;
+	if ( aRetry )
+		{
+		pinInput.iOperation |= EPINValueIncorrect;
+		}
+	pinInput.iPIN = aPINParams;
+	TPINInputBuf pinInputBuf( pinInput );
+	iPINInputBuf.Copy( pinInputBuf );
+	iRequester->RequestDialog( iPINInputBuf, aPINValue );
+	}
+
+
+
+void CRefSecurityDialog::InitClientStatus( TRequestStatus& aStatus )
+	{
+	iClientStatus = &aStatus;
+	*iClientStatus = KRequestPending;
+	}
+
+
+
+void CRefSecurityDialog::HandleResponse( TInt aResult )
+	{
+	if ( aResult >= KErrNone )
+		{
+		switch ( iCurrentOperation )
+			{
+			case EServerAuthenticationFailure:
+				{
+				TServerAuthenticationFailureDialogResult serverAuthenticationOutput = iServerAuthenticationOutputBuf();
+							
+				if(serverAuthenticationOutput == EContinue)
+					{
+					aResult 	   = KErrNone;
+					}
+				else if(serverAuthenticationOutput == EStop)
+					{
+					aResult 	   = KErrAbort;	
+					}				
+				}
+				break;
+			case ESecureConnection:
+				{
+				if ( aResult == KClientAuthenticationRequested )
+					{
+					*iClientDoClientAuthenticationPtr = ETrue;
+					aResult = KErrNone;
+					}
+				else
+					{
+					*iClientDoClientAuthenticationPtr = EFalse;
+					}
+				*iClientCertInfoHandlePtr = iCertInfoHandleBuf();
+				break;
+				}
+			case ESignText:
+				{
+				*iClientCertInfoHandlePtr = iCertInfoHandleBuf();
+				break;
+				}
+			case EEnterPIN:
+			case EEnablePIN:
+			case EDisablePIN:
+				*iClientPINValuePtr = iPINValueBuf();
+				break;
+			case EChangePIN:
+			case EUnblockPIN:
+				{
+				TTwoPINOutput& twoPINOutput = iTwoPINOutputBuf();
+				*iClientPINValuePtr = twoPINOutput.iPINValueToCheck;
+				*iClientSecondPINValuePtr = twoPINOutput.iNewPINValue;
+				break;
+				}
+
+			case EUnblockPINInClear:
+				{
+				TUnblockPINInClearOutput& unblockPINOutput = iUnblockPINInClearOutputBuf();
+				*iClientUnblockPINValuePtr = unblockPINOutput.iPINValueToCheck;
+				*iClientSecondPINValuePtr = unblockPINOutput.iNewPINValue;
+				break;
+				}
+
+			case EPINBlocked:
+		case ETotalBlocked:
+				// No data to return
+				break;
+			default:
+				__ASSERT_DEBUG( EFalse, _L( "Invalid operation" ) );
+			}
+		}
+
+	User::RequestComplete( iClientStatus, aResult );
+	}
+
+
+
+// ----------------------------------------------------------------------------
+// CDialogRequester
+//
+
+CDialogRequester::CDialogRequester( CRefSecurityDialog& aSecDialog )
+	: CActive( EPriorityStandard ), iSecDialog( aSecDialog )
+	{
+	CActiveScheduler::Add( this );
+	}
+
+
+
+CDialogRequester::~CDialogRequester()
+	{
+	Cancel();
+	iNotifier.Close();
+	}
+
+
+
+CDialogRequester* CDialogRequester::NewL( CRefSecurityDialog& aSecDialog )
+	{
+	CDialogRequester* self = new (ELeave) CDialogRequester( aSecDialog );
+	CleanupStack::PushL( self );
+	self->ConstructL();
+	CleanupStack::Pop( self );
+	return self;
+	}
+
+
+
+void CDialogRequester::ConstructL()
+	{
+	User::LeaveIfError( iNotifier.Connect() );
+	}
+
+
+
+void CDialogRequester::RequestDialog( const TDesC8& aData, TDes8& aResponse )
+	{
+	iNotifier.StartNotifierAndGetResponse( iStatus, KUidSecurityDialogNotifier,
+											aData, aResponse );
+	iState = KMakingRequest;
+	SetActive();
+	}
+
+
+
+void CDialogRequester::DoCancel()
+	{
+	delete iInputBuffer;
+	iInputBuffer = NULL;
+	iNotifier.CancelNotifier( KUidSecurityDialogNotifier );
+	}
+
+
+
+void CDialogRequester::RequestVariableBufferDialog( const TDesC8& aOperationData,
+										const TDesC8& aVariableData,
+										const RArray<TCTTokenObjectHandle>& aCertHandleList,
+										TDes8& aResponse )
+	{
+	iOperationDataPtr = &aOperationData;
+	iVariableDataPtr = &aVariableData;
+	iCertHandleListPtr = &aCertHandleList;
+	iResponsePtr = &aResponse;
+	iState = KFillingVariableInputBuffer;
+	SetActive();
+	// Complete the AO immediately so that buffer processing can occur in RunL().
+	TRequestStatus* statusPtr = &iStatus;
+	User::RequestComplete( statusPtr, KErrNone );
+	}
+
+void CDialogRequester::RequestDialog(HBufC8* aInputBuffer, TDes8& aResponse)
+{
+iInputBuffer = aInputBuffer;
+RequestDialog(*iInputBuffer, aResponse);
+}
+
+
+void CDialogRequester::RunL()
+	{
+	switch ( iState )
+		{
+		case KFillingVariableInputBuffer:
+			{
+			TInt operationDataSize = iOperationDataPtr->Size();
+			TInt variableDataSize = iVariableDataPtr->Size();
+			TInt arraySize = sizeof( TCTTokenObjectHandle ) * iCertHandleListPtr->Count();
+			TInt bufferSize = operationDataSize + variableDataSize + arraySize;
+			iInputBuffer = HBufC8::NewL( bufferSize );
+			TPtr8 inputBufferPtr( iInputBuffer->Des() );
+			inputBufferPtr.Append( *iOperationDataPtr );
+			for ( TInt h = 0, total = iCertHandleListPtr->Count(); h < total; ++h )
+				{
+				const TCTTokenObjectHandle& certHandle = (*iCertHandleListPtr)[h];
+				TPckgC<TCTTokenObjectHandle> certHandleBuf( certHandle );
+				inputBufferPtr.Append( certHandleBuf );
+				}
+			inputBufferPtr.Append( *iVariableDataPtr );
+			RequestDialog( *iInputBuffer, *iResponsePtr );
+			break;
+			}
+		case KMakingRequest:
+			{
+			delete iInputBuffer;
+			iInputBuffer = NULL;
+			iSecDialog.HandleResponse( iStatus.Int() );
+			break;
+			}
+		default:
+			__ASSERT_DEBUG( EFalse, _L( "Invalid state" ) );
+		}
+	}
+
+
+
+/**
+ * RunError should only be called if the buffer allocation fails, in which case
+ * let client handle it.
+ */
+TInt CDialogRequester::RunError( TInt aError )
+	{
+	iSecDialog.HandleResponse( aError );
+	return KErrNone;
+	}
+
+// ----------------------------------------------------------------------------
+// CServerAuthenticationFailureInput
+//
+
+CServerAuthenticationFailureInput::CServerAuthenticationFailureInput()
+	{
+	}
+
+
+CServerAuthenticationFailureInput::~CServerAuthenticationFailureInput()
+	{
+	if(iServerName)
+		delete iServerName;
+	if(iEncodedCert)
+		delete iEncodedCert;
+	}
+
+CServerAuthenticationFailureInput* CServerAuthenticationFailureInput::NewL(const TDesC8& aServerName,const TValidationError& aFailureReason, const TDesC8& aEncodedCert, const TBool aCreateOwnBuffers)
+	{
+	CServerAuthenticationFailureInput* self = CServerAuthenticationFailureInput::NewLC(aServerName, aFailureReason, aEncodedCert, aCreateOwnBuffers);
+	CleanupStack::Pop(self);
+	return self;
+	}
+
+CServerAuthenticationFailureInput* CServerAuthenticationFailureInput::NewLC(const TDesC8& aServerName,const TValidationError& aFailureReason, const TDesC8& aEncodedCert, const TBool aCreateOwnBuffers)
+	{
+	CServerAuthenticationFailureInput* self = new(ELeave) CServerAuthenticationFailureInput();
+	CleanupStack::PushL(self);
+	self->ConstructL(aServerName, aFailureReason, aEncodedCert, aCreateOwnBuffers);
+	return self;
+	}
+
+EXPORT_C CServerAuthenticationFailureInput* CServerAuthenticationFailureInput::NewL(const TDesC8& aBuffer, const TBool aCreateOwnBuffers)
+	{
+	CServerAuthenticationFailureInput* self = CServerAuthenticationFailureInput::NewLC(aBuffer, aCreateOwnBuffers);
+	CleanupStack::Pop(self);
+	return self;
+	}
+
+EXPORT_C CServerAuthenticationFailureInput* CServerAuthenticationFailureInput::NewLC(const TDesC8& aBuffer, const TBool aCreateOwnBuffers)
+	{
+	CServerAuthenticationFailureInput* self = new(ELeave) CServerAuthenticationFailureInput();
+	CleanupStack::PushL(self);
+	self->ConstructL(aBuffer, aCreateOwnBuffers);
+	return self;
+	}
+
+void CServerAuthenticationFailureInput::ConstructL(const TDesC8& aServerName,const TValidationError& aFailureReason, const TDesC8& aEncodedCert, const TBool aCreateOwnBuffers)
+	{
+	iFailureReason = aFailureReason;
+	
+	if (aCreateOwnBuffers)
+		{
+		iServerName = aServerName.AllocL();
+		iServerNamePtr.Set(iServerName->Des());
+		iEncodedCert = aEncodedCert.AllocL();
+		iEncodedCertPtr.Set(iEncodedCert->Des());
+		}
+	else
+		{
+		iServerNamePtr.Set(aServerName);
+		iEncodedCertPtr.Set(aEncodedCert);
+		}
+	}
+
+
+void CServerAuthenticationFailureInput::ConstructL(const TDesC8& aBuffer, const TBool aCreateOwnBuffers)
+	{
+	const TServerAuthenticationFailureInput* srvAuthFail = 
+						reinterpret_cast<const TServerAuthenticationFailureInput*>
+							( aBuffer.Ptr() );
+
+	const TUint8* binaryDataPtr = aBuffer.Ptr() + sizeof(TServerAuthenticationFailureInput);
+	
+	iFailureReason = srvAuthFail->iFailureReason;
+
+	if(aCreateOwnBuffers)
+		{
+		TPtrC8 dataPtr(binaryDataPtr, srvAuthFail->iServerNameLength);
+		iServerName = dataPtr.AllocL();
+		iServerNamePtr.Set(iServerName->Des());
+		
+		dataPtr.Set(binaryDataPtr + srvAuthFail->iServerNameLength, srvAuthFail->iEncodedCertLength);
+		iEncodedCert = dataPtr.AllocL();
+		iEncodedCertPtr.Set(iEncodedCert->Des());
+		}
+	else
+		{
+		iServerNamePtr.Set(binaryDataPtr, srvAuthFail->iServerNameLength);
+		iEncodedCertPtr.Set(binaryDataPtr + srvAuthFail->iServerNameLength, srvAuthFail->iEncodedCertLength);
+		}
+	
+	}
+
+EXPORT_C TValidationError CServerAuthenticationFailureInput::FailureReason()
+	{
+	return iFailureReason;
+	}
+
+EXPORT_C void CServerAuthenticationFailureInput::GetServerName(TPtrC8& aServerNamePtr)
+	{
+	aServerNamePtr.Set(iServerNamePtr);
+	}
+
+EXPORT_C void CServerAuthenticationFailureInput::GetEncodedCert(TPtrC8& aEncodedCertPtr)
+	{
+	aEncodedCertPtr.Set(iEncodedCertPtr);
+	}
+
+EXPORT_C HBufC8* CServerAuthenticationFailureInput::PackBufferL() const
+	{
+	TServerAuthenticationFailureInput serverAuthenticationInput;
+	serverAuthenticationInput.iOperation     = EServerAuthenticationFailure;
+	serverAuthenticationInput.iFailureReason = iFailureReason;
+	serverAuthenticationInput.iServerNameLength = iServerNamePtr.Length(); 
+	serverAuthenticationInput.iEncodedCertLength = iEncodedCertPtr.Length();
+		
+	TServerAuthenticationFailureInputBuf serverAuthenticationInputBuf(serverAuthenticationInput);
+
+	TInt bufferSize = sizeof(serverAuthenticationInputBuf) + iServerNamePtr.Length() + iEncodedCertPtr.Length();
+	HBufC8* packedBuffer = HBufC8::NewL(bufferSize);
+	TPtr8 packedBufferPtr(packedBuffer->Des());
+
+	packedBufferPtr.Append(serverAuthenticationInputBuf);
+	packedBufferPtr.Append(iServerNamePtr);
+	packedBufferPtr.Append(iEncodedCertPtr);
+	
+	return packedBuffer;
+	}