IMPSengine/engsrv/src/impsapplauncherproxy.cpp
changeset 0 094583676ce7
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/IMPSengine/engsrv/src/impsapplauncherproxy.cpp	Thu Dec 17 08:41:52 2009 +0200
@@ -0,0 +1,411 @@
+/*
+* Copyright (c) 2004 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: Proxy class for Im app launcher.
+*
+*/
+
+
+
+// INCLUDE FILES
+#include    <E32Math.h>
+#include    "impsapplauncherproxy.h"
+#include    "impsutils.h"
+
+// CONSTANTS
+
+// MACROS
+#ifndef _DEBUG
+#define _NO_IMPS_LOGGING_
+#endif
+
+
+// ============================ MEMBER FUNCTIONS ===============================
+
+// -----------------------------------------------------------------------------
+// CImpsAppLauncherProxy::CImpsAppLauncherProxy
+// C++ default constructor can NOT contain any code, that
+// might leave.
+// -----------------------------------------------------------------------------
+//
+CImpsAppLauncherProxy::CImpsAppLauncherProxy( MImpsAppLaunchHandler* aLaunchObserver )
+        :   CActive( EPriorityStandard ),
+        iLaunchObserver( aLaunchObserver ),
+        iRequestList( _FOFF( CLaunchRequest, iLink ) )
+    {
+    CActiveScheduler::Add( this );
+    }
+
+// -----------------------------------------------------------------------------
+// CImpsAppLauncherProxy::ConstructL
+// Symbian 2nd phase constructor can leave.
+// -----------------------------------------------------------------------------
+//
+void CImpsAppLauncherProxy::ConstructL()
+    {
+    }
+
+// -----------------------------------------------------------------------------
+// CImpsAppLauncherProxy::NewL
+// Two-phased constructor.
+// -----------------------------------------------------------------------------
+//
+CImpsAppLauncherProxy* CImpsAppLauncherProxy::NewL(
+    MImpsAppLaunchHandler* aLaunchObserver )
+    {
+    CImpsAppLauncherProxy* self = new( ELeave ) CImpsAppLauncherProxy(
+        aLaunchObserver );
+
+    CleanupStack::PushL( self );
+    self->ConstructL();
+    CleanupStack::Pop();
+
+    return self;
+    }
+
+
+// Destructor
+CImpsAppLauncherProxy::~CImpsAppLauncherProxy()
+    {
+    // Free the request queue
+    TDblQueIter<CLaunchRequest> iter( iRequestList );
+    iter.SetToFirst();
+    while ( iter )
+        {
+        CLaunchRequest* request = iter;
+        iter++;
+        request->Destroy();
+        }
+
+    Cancel();
+    delete iCurrentRequest; // just in case
+    }
+
+
+// -----------------------------------------------------------------------------
+// CImpsAppLauncherProxy::LaunchApplication
+// The request function. Launches the application which is registered with
+// the given ApplicationID.
+// -----------------------------------------------------------------------------
+//
+TInt CImpsAppLauncherProxy::LaunchApplicationL( const TDesC& aApplicationId,
+                                                const TDesC& aSAP,
+                                                const TDesC& aUserID )
+    {
+#ifndef _NO_IMPS_LOGGING_
+    CImpsClientLogger::Log( _L( "CImpsAppLauncherProxy: LaunchApplication (appId: %S, SAP: %S, user: %S)" ), &aApplicationId, &aSAP, &aUserID );
+#endif
+
+    CLaunchRequest* launchRequest = CLaunchRequest::NewL( aApplicationId, aSAP, aUserID );
+
+
+    if ( IsActive() )
+        {
+        if ( !iCurrentRequest )
+            {
+            delete launchRequest;
+            User::Leave( KErrCorrupt );
+            }
+
+        if ( !( *iCurrentRequest == *launchRequest ) )
+            {
+            // Different request
+            // Queue this aApplicationId it for later handling
+#ifndef _NO_IMPS_LOGGING_
+            CImpsClientLogger::Log( _L( "CImpsAppLauncherProxy: Active with different request " ) );
+#endif
+            QueueRequest( *launchRequest );
+            }
+        else
+            {
+#ifndef _NO_IMPS_LOGGING_
+            CImpsClientLogger::Log( _L( "CImpsAppLauncherProxy: Active with same request " ) );
+#endif
+
+            }
+        }
+    else // not active
+        {
+#ifndef _NO_IMPS_LOGGING_
+        CImpsClientLogger::Log( _L( "CImpsAppLauncherProxy: Not active. Starting." ) );
+#endif
+        // Assign a new request to current
+        delete iCurrentRequest;
+        iCurrentRequest = NULL;
+        iCurrentRequest = launchRequest;
+
+        // return ImLauncher process starting error code
+        TInt err = DoStartProcess( *iCurrentRequest );
+        if ( err )
+            {
+            delete iCurrentRequest;
+            iCurrentRequest = NULL;
+            }
+
+        return err;
+        }
+    return KErrNone;
+    }
+
+// -----------------------------------------------------------------------------
+// CImpsAppLauncherProxy::RunL
+// Called when the launcher process exited
+// -----------------------------------------------------------------------------
+//
+void CImpsAppLauncherProxy::RunL()
+    {
+    // Here comes the control when the ImLauncher.exe (or dll) finished
+#ifndef _NO_IMPS_LOGGING_
+    CImpsClientLogger::Log( _L( "CImpsAppLauncherProxy: RunL %d" ), iStatus.Int() );
+#endif
+
+    // Notify the observer if any
+    if ( iLaunchObserver != NULL )
+        {
+        iLaunchObserver->HandleAppLaunch( iCurrentRequest->ApplicationId(), iStatus.Int() );
+        }
+
+    // Delete the current Client ID
+    delete iCurrentRequest;
+    iCurrentRequest = NULL;
+
+    ProcessNextRequestL();
+    }
+
+// -----------------------------------------------------------------------------
+// CImpsAppLauncherProxy::DoCancel
+// -----------------------------------------------------------------------------
+//
+void CImpsAppLauncherProxy::DoCancel()
+    {
+    }
+
+// -----------------------------------------------------------------------------
+// CImpsAppLauncherProxy::RunError
+// Called when the RunL leaved
+// -----------------------------------------------------------------------------
+//
+TInt CImpsAppLauncherProxy::RunError( TInt /*aError*/ )
+    {
+    return KErrNone;
+    }
+
+// -----------------------------------------------------------------------------
+// CImpsAppLauncherProxy::DoStartProcess
+// Starts the ImLauncher process
+// -----------------------------------------------------------------------------
+//
+TInt CImpsAppLauncherProxy::DoStartProcess( CLaunchRequest& aRequest )
+    {
+    TInt result;
+
+    RProcess launcher;
+    const TDesC& appId = aRequest.ApplicationId();
+    const TDesC& sap = aRequest.Sap();
+    const TDesC& userId = aRequest.UserId();
+    TImpsLaunchParams params( appId, sap, userId );
+    _LIT( KLauncherFilenameExe, "ImLauncher.exe" );
+    TPtrC paramsDes = params.Get();
+    result = launcher.Create( KLauncherFilenameExe, paramsDes );
+    if ( result != KErrNone )
+        {
+#ifndef _NO_IMPS_LOGGING_
+        CImpsClientLogger::Log( _L( "CImpsAppLauncherProxy: Create process failed: %d " ), result );
+#endif
+        return result;
+        }
+
+    // When the launcher exits we'll get the exit code in iStatus
+    iStatus = KRequestPending;
+    SetActive();
+    launcher.Logon( iStatus );
+
+    launcher.Resume();
+    launcher.Close();
+
+#ifndef _NO_IMPS_LOGGING_
+    CImpsClientLogger::Log( _L( "CImpsAppLauncherProxy: Create process success" ) );
+#endif
+    return KErrNone;
+    }
+
+
+// -----------------------------------------------------------------------------
+// CImpsAppLauncherProxy::QueueRequest
+// Adds the request to the queue. No duplicates are queued.
+// -----------------------------------------------------------------------------
+//
+void CImpsAppLauncherProxy::QueueRequest( CLaunchRequest& aRequest )
+    {
+    // Check for duplicate requests
+    if ( !IsDuplicate( aRequest ) )
+        {
+#ifndef _NO_IMPS_LOGGING_
+        CImpsClientLogger::Log( _L( "Queued" ) );
+#endif
+        iRequestList.AddLast( aRequest );
+        }
+    else
+        {
+#ifndef _NO_IMPS_LOGGING_
+        CImpsClientLogger::Log( _L( "Request already exists" ) );
+#endif
+        }
+    }
+
+// -----------------------------------------------------------------------------
+// CImpsAppLauncherProxy::ProcessNextRequest
+// Gets the next request from the queue and processes it.
+// -----------------------------------------------------------------------------
+//
+void CImpsAppLauncherProxy::ProcessNextRequestL()
+    {
+    // Check for queued
+    TDblQueIter<CLaunchRequest> iter ( iRequestList );
+    iter.SetToFirst();
+    if ( iter )
+        {
+        // There is request to handle
+        CLaunchRequest* request = iter;
+        delete iCurrentRequest;
+        iCurrentRequest = NULL;
+        iCurrentRequest = request;
+        request->iLink.Deque(); // remove it from the queue
+
+#ifndef _NO_IMPS_LOGGING_
+        CImpsClientLogger::Log(
+            _L( "CImpsAppLauncherProxy: Processing the next request: \"%S\"" ),
+            &( iCurrentRequest->ApplicationId() ) );
+#endif
+
+        TInt err( DoStartProcess( *iCurrentRequest ) );
+        if ( ( err != KErrNone ) )
+            {
+            // if starting failed notify the observer
+            if ( iLaunchObserver != NULL )
+                {
+                iLaunchObserver->HandleAppLaunch( iCurrentRequest->ApplicationId(), err );
+                }
+            }
+
+        }
+    else
+        {
+#ifndef _NO_IMPS_LOGGING_
+        CImpsClientLogger::Log(
+            _L( "CImpsAppLauncherProxy: No more requests to process" ) );
+#endif
+
+        }
+    }
+
+
+// -----------------------------------------------------------------------------
+// CImpsAppLauncherProxy::IsDuplicate
+// Checks if the given ApplicationID is already in the queue.
+// -----------------------------------------------------------------------------
+//
+TBool CImpsAppLauncherProxy::IsDuplicate( CLaunchRequest& aRequest )
+    {
+    TDblQueIter<CLaunchRequest> iter ( iRequestList );
+    iter.SetToFirst();
+    while ( iter )
+        {
+        CLaunchRequest* request = iter++;
+        if ( aRequest == *request )
+            {
+            return ETrue;
+            }
+        }
+
+    return EFalse;
+    }
+
+//////////////////////////////////////////////////////////////////////////
+
+// -----------------------------------------------------------------------------
+// CLaunchRequest::CLaunchRequest
+// -----------------------------------------------------------------------------
+
+CLaunchRequest::CLaunchRequest( )
+    {
+    }
+
+
+CLaunchRequest* CLaunchRequest::NewL( const TDesC& aCID,
+                                      const TDesC& aSAP,
+                                      const TDesC& aUserId )
+    {
+    CLaunchRequest* self = new( ELeave ) CLaunchRequest();
+
+    CleanupStack::PushL( self );
+    self->ConstructL( aCID, aSAP, aUserId );
+    CleanupStack::Pop();
+
+    return self;
+
+    }
+
+void CLaunchRequest::ConstructL( const TDesC& aCID,
+                                 const TDesC& aSAP,
+                                 const TDesC& aUserId )
+    {
+    iCID = aCID.AllocL();
+    iSAP = aSAP.AllocL();
+    iUserId = aUserId.AllocL();
+    }
+
+CLaunchRequest::~CLaunchRequest()
+    {
+    delete iCID;
+    delete iSAP;
+    delete iUserId;
+    } //lint !e1540 iFields freed in Destroy
+
+void CLaunchRequest::Destroy()
+    {
+    iLink.Deque();
+    delete this;
+    }
+
+
+const TDesC& CLaunchRequest::ApplicationId()
+    {
+    return *iCID;
+    }
+
+const TDesC& CLaunchRequest::Sap()
+    {
+    return *iSAP;
+    }
+
+const TDesC& CLaunchRequest::UserId()
+    {
+    return *iUserId;
+    }
+
+bool CLaunchRequest::operator==( CLaunchRequest& rhs )
+    {
+    if ( this->ApplicationId().Compare( rhs.ApplicationId() ) ||
+         this->Sap().Compare( rhs.Sap() ) ||
+         this->UserId().Compare( rhs.UserId() ) )
+        {
+        return true;
+        }
+    else
+        {
+        return false;
+        }
+    }
+
+//  End of File