--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/genericservices/activebackupclient/src/abachandler.cpp Tue Feb 02 02:01:42 2010 +0200
@@ -0,0 +1,346 @@
+// 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 "Eclipse Public License v1.0"
+// which accompanies this distribution, and is available
+// at the URL "http://www.eclipse.org/legal/epl-v10.html".
+//
+// Initial Contributors:
+// Nokia Corporation - initial contribution.
+//
+// Contributors:
+//
+// Description:
+// Implementation of CActiveBackupClient class.
+//
+//
+
+/**
+ @file
+*/
+
+#include "abachandler.h"
+#include "abclientsession.h"
+#include "panic.h"
+
+namespace conn
+ {
+ CActiveBackupCallbackHandler* CActiveBackupCallbackHandler::NewL(MActiveBackupDataClient* aABDC,
+ RABClientSession& aClientSession)
+ /**
+ Symbian first phase constructor
+ @param aABDC pointer to the client's callback implementation
+ @param aClientSession reference to the client's session
+ @return Pointer to a created CActiveBackupCallbackHandler object
+ */
+ {
+ CActiveBackupCallbackHandler* self = new (ELeave) CActiveBackupCallbackHandler(aABDC, aClientSession);
+ CleanupStack::PushL(self);
+ self->ConstructL();
+ CleanupStack::Pop(self);
+ return self;
+ }
+
+ CActiveBackupCallbackHandler::CActiveBackupCallbackHandler(MActiveBackupDataClient* aABDC,
+ RABClientSession& aClientSession) : CActive(EPriorityNormal), iActiveBackupDataClient(aABDC),
+ iClientSession(aClientSession), iTransferBuffer(NULL)
+ /**
+ C++ Constructor
+ @param aABDC pointer to the client's callback implementation
+ @param aClientSession reference to the client's session
+ @panic KErrArgument if the pointer aABDC is NULL
+ */
+ {
+ __ASSERT_DEBUG(aABDC, Panic(KErrArgument));
+ }
+
+ CActiveBackupCallbackHandler::~CActiveBackupCallbackHandler()
+ /**
+ C++ Destructor
+ */
+ {
+ // Cancel any outstanding Async requests (i.e. close down the callback interface)
+ Cancel();
+ delete iTransferBuffer;
+ }
+
+ void CActiveBackupCallbackHandler::RunL()
+ /**
+ Handle messages "initiated" by the server. Because of IPC limitations, the client primes the
+ server with a message containing modifiable package buffers that are filled with identifiers
+ and arguments for the callback interface
+ */
+ {
+ if (iStatus == KErrNone)
+ {
+ switch(iCallbackCommand())
+ {
+ case EABCallbackAllSnapshotsSupplied:
+ {
+ iActiveBackupDataClient->AllSnapshotsSuppliedL();
+
+ PrimeServerForCallbackL();
+ } break;
+ case EABCallbackReceiveSnapshotData:
+ {
+ TDriveNumber driveNum = EDriveC; // Initialise to keep the compiler happy
+
+ HBufC8* pReceivedData = iClientSession.GetDataFromServerLC(iCallbackArg1(),
+ EABCallbackReceiveSnapshotData, driveNum);
+
+ // Call the client method for handling receipt of the snapshot
+ iActiveBackupDataClient->ReceiveSnapshotDataL(driveNum,
+ *pReceivedData, static_cast<TBool>(iCallbackArg2()));
+
+ // Reprime the server
+ PrimeServerForCallbackL();
+
+ CleanupStack::PopAndDestroy(pReceivedData);
+ } break;
+ case EABCallbackGetExpectedDataSize:
+ {
+ TUint dataSize = iActiveBackupDataClient->GetExpectedDataSize(static_cast<TDriveNumber>(iCallbackArg1()));
+
+ // Reprime the server
+ PrimeServerForCallbackWithResponseL(dataSize);
+ } break;
+ case EABCallbackGetSnapshotData:
+ {
+ // Create an empty TPtr8 to point at the buffer to fill
+ TPtr8 bufferToSend(CreateFixedBufferL());
+
+ TBool finished = ETrue;
+
+ // Zero our descriptor so that it can be refilled
+ bufferToSend.Zero();
+
+ // Callback the AB client to populate our descriptor
+ iActiveBackupDataClient->GetSnapshotDataL(static_cast<TDriveNumber>(iCallbackArg1()),
+ bufferToSend, finished);
+
+ // Send the length and some other info to the server to allow it to prepare for the actual transfer
+ iClientSession.SendDataLengthToServerL(bufferToSend, finished, EABCallbackGetSnapshotData);
+
+ iTransferBuffer->Des().SetLength(bufferToSend.Length());
+
+ // Send the actual data back to the server and prime for the next callback
+ PrimeServerForCallbackWithResponseL(*iTransferBuffer);
+ } break;
+ case EABCallbackInitialiseGetBackupData:
+ {
+ iActiveBackupDataClient->InitialiseGetBackupDataL(static_cast<TDriveNumber>(iCallbackArg1()));
+
+ // Reprime the server
+ PrimeServerForCallbackL();
+ } break;
+ case EABCallbackGetBackupDataSection:
+ {
+ // Create an empty TPtr8 to point at the buffer to fill
+ TPtr8 bufferToSend(CreateFixedBufferL());
+
+ TBool finished = ETrue;
+
+ // Zero our descriptor so that it can be refilled
+ bufferToSend.Zero();
+
+ // Callback the AB client to populate our descriptor
+ iActiveBackupDataClient->GetBackupDataSectionL(bufferToSend, finished);
+
+ // Send the length and some other info to the server to allow it to prepare for the actual transfer
+ iClientSession.SendDataLengthToServerL(bufferToSend, finished, EABCallbackGetBackupDataSection);
+
+ iTransferBuffer->Des().SetLength(bufferToSend.Length());
+
+ // Send the actual data back to the server and prime for the next callback
+ PrimeServerForCallbackWithResponseL(*iTransferBuffer);
+ } break;
+ case EABCallbackInitialiseRestoreBaseDataSection:
+ {
+ iActiveBackupDataClient->InitialiseRestoreBaseDataL(static_cast<TDriveNumber>(iCallbackArg1()));
+
+ // Reprime the server
+ PrimeServerForCallbackL();
+ } break;
+ case EABCallbackRestoreBaseDataSection:
+ {
+ HBufC8* pReceivedData = iClientSession.GetDataFromServerLC(iCallbackArg1(),
+ EABCallbackRestoreBaseDataSection);
+
+ // Call the client method for handling receipt of the snapshot
+ iActiveBackupDataClient->RestoreBaseDataSectionL(*pReceivedData,
+ static_cast<TBool>(iCallbackArg2()));
+
+ // Reprime the server
+ PrimeServerForCallbackL();
+
+ CleanupStack::PopAndDestroy(pReceivedData);
+ } break;
+ case EABCallbackInitialiseRestoreIncrementData:
+ {
+ iActiveBackupDataClient->InitialiseRestoreIncrementDataL(static_cast<TDriveNumber>(iCallbackArg1()));
+
+ // Reprime the server
+ PrimeServerForCallbackL();
+ } break;
+ case EABCallbackRestoreIncrementDataSection:
+ {
+ HBufC8* pReceivedData = iClientSession.GetDataFromServerLC(iCallbackArg1(),
+ EABCallbackRestoreIncrementDataSection);
+
+ // Call the client method for handling receipt of the snapshot
+ iActiveBackupDataClient->RestoreIncrementDataSectionL(*pReceivedData,
+ static_cast<TBool>(iCallbackArg2()));
+
+ // Reprime the server
+ PrimeServerForCallbackL();
+
+ CleanupStack::PopAndDestroy(pReceivedData);
+ } break;
+ case EABCallbackRestoreComplete:
+ {
+ iActiveBackupDataClient->RestoreComplete(static_cast<TDriveNumber>(iCallbackArg1()));
+
+ // Reprime the server
+ PrimeServerForCallbackL();
+ } break;
+ case EABCallbackTerminateMultiStageOperation:
+ {
+ iActiveBackupDataClient->TerminateMultiStageOperation();
+
+ // Reprime the server
+ PrimeServerForCallbackL();
+ } break;
+ case EABCallbackGetDataChecksum:
+ {
+ iActiveBackupDataClient->GetDataChecksum(static_cast<TDriveNumber>(iCallbackArg1()));
+
+ // Reprime the server
+ PrimeServerForCallbackL();
+ } break;
+ case EABCallbackInitialiseGetProxyBackupData:
+ {
+ iActiveBackupDataClient->InitialiseGetProxyBackupDataL(static_cast<TSecureId>(iCallbackArg1()),
+ static_cast<TDriveNumber>(iCallbackArg2()));
+
+ // Reprime the server
+ PrimeServerForCallbackL();
+ } break;
+ case EABCallbackInitialiseRestoreProxyBaseData:
+ {
+ iActiveBackupDataClient->InitialiseRestoreProxyBaseDataL(static_cast<TSecureId>(
+ iCallbackArg1()), static_cast<TDriveNumber>(iCallbackArg2()));
+
+ // Reprime the server
+ PrimeServerForCallbackL();
+ } break;
+ default:
+ {
+ // Call the server to leave with KErrNotSupported
+ User::Leave(KErrNotSupported);
+ }
+ }
+
+ // Set us up for another call
+ SetActive();
+
+ }
+ }
+
+ void CActiveBackupCallbackHandler::PrimeServerForCallbackL()
+ /**
+ Reprime the server with a new IPC message to respond to
+ */
+ {
+ iClientSession.PrimeServerForCallbackL(iCallbackCommand, iCallbackArg1, iCallbackArg2, iStatus);
+ }
+
+ void CActiveBackupCallbackHandler::PrimeServerForCallbackWithResponseL(TInt aResponse)
+ /**
+ Reprime the server with a new IPC message to respond to, sending the result of the previous callback
+
+ @param aResponse The response to send back to the server i.e. the result of the last callback made
+ */
+ {
+ iClientSession.PrimeServerForCallbackWithResponseL(iCallbackCommand, iCallbackArg1, iCallbackArg2, aResponse, iStatus);
+ }
+
+ void CActiveBackupCallbackHandler::PrimeServerForCallbackWithResponseL(TDesC8& aResponse)
+ /**
+ Reprime the server with a new IPC message to respond to, sending the result of the previous callback
+
+ @param aResponse The response to send back to the server i.e. the result of the last callback made
+ */
+ {
+ iClientSession.PrimeServerForCallbackWithResponseL(iCallbackCommand, iCallbackArg1, iCallbackArg2, aResponse, iStatus);
+ }
+
+ TInt CActiveBackupCallbackHandler::RunError(TInt aError)
+ /**
+ Handle any leaves that occur from within the RunL and hence from the callback methods. In order
+ to propagate leaves over to the PC client, they must be sent to the backup engine to leave to the
+ client
+
+ @param aError The leave code that has been trapped from within the RunL. Propagate this code to the engine
+ @return Any unhandled leave code
+ */
+ {
+ iClientSession.PropagateLeave(aError);
+
+ PrimeServerForCallbackL();
+ SetActive();
+
+ return KErrNone; // Is this correct or do we return the error code even though it's been handled?
+ }
+
+ void CActiveBackupCallbackHandler::DoCancel()
+ /**
+ Immediately cancel any outstanding calls to the backup engine
+ */
+ {
+ // we can't do anything with the error code here
+ TRAP_IGNORE(iClientSession.CancelServerCallbackL());
+ }
+
+ void CActiveBackupCallbackHandler::ConstructL()
+ /**
+ Add this object to the scheduler
+
+ @panic KErrNotFound Debug only - If an ActiveScheduler is not installed
+ @leave Release only - If an ActiveScheduler is not installed
+ */
+ {
+ if (!CActiveScheduler::Current())
+ {
+ __ASSERT_DEBUG(0, Panic(KErrNotFound));
+ }
+
+ // Add this AO to the scheduler
+ CActiveScheduler::Add(this);
+ SetActive();
+ }
+
+ void CActiveBackupCallbackHandler::StartListeningForServerMessagesL()
+ /**
+ Send an asynchronous IPC message to the server in order that it has a vehicle for "initiating"
+ a callback on iActiveBackupDataClient. This should only be called once as it will start the
+ active scheduler
+ */
+ {
+ // Prime the server with the first prime for callback IPC message
+ PrimeServerForCallbackL();
+ }
+
+ TPtr8 CActiveBackupCallbackHandler::CreateFixedBufferL()
+ /**
+ Creates a buffer of the exact size.
+ */
+ {
+ delete iTransferBuffer;
+ iTransferBuffer = NULL;
+
+ iTransferBuffer = HBufC8::NewL(iCallbackArg1());
+
+ return TPtr8(const_cast<TUint8*>(iTransferBuffer->Ptr()), iCallbackArg1());
+ }
+ }
+