satengine/SatServer/Commands/SetUpCallCmd/src/CSetUpCallHandler.cpp
changeset 0 ff3b6d0fd310
child 6 1b9ee3c7442d
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/satengine/SatServer/Commands/SetUpCallCmd/src/CSetUpCallHandler.cpp	Tue Feb 02 01:11:09 2010 +0200
@@ -0,0 +1,1355 @@
+/*
+* Copyright (c) 2002-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:  Handles SetUpCall command
+*
+*/
+
+
+#include    <aiwinternaldialdata.h>
+#include    <aiwdialdataext.h>
+
+#include    <exterror.h>
+#include    <ccpdefs.h>
+
+#include    "MSatApi.h"
+#include    "MSatUtils.h"
+#include    "MSatSystemState.h"
+#include    "MSatUiSession.h"
+#include    "SatSOpcodes.h"
+#include    "MSatSUiClientHandler.h"
+#include    "CSetUpCallHandler.h"
+#include    "TSatExtErrorUtils.h"
+#include    "SatLog.h"
+
+const TUint8 KBCDAsterisk( 0x0A );
+const TUint8 KBCDDash( 0x0B );
+const TUint8 KBCDDTMF( 0x0C );
+const TUint8 KBCDWild( 0x0D );
+const TUint8 KBCDExpansion( 0x0E );
+
+const TUint8 KAsteriskChar( 0x2A );
+const TUint8 KDashChar( 0x23 );
+const TUint8 KDTMFChar( 0x70 );
+const TUint8 KWildChar( 0x77 );
+const TUint8 KExpansionChar( 0x2E );
+
+_LIT( KFixedSimEmergencyNumber, "112" );
+_LIT8( KContentType, "*" );
+// 3GPP TS 24.008
+const TInt KMaximumPhoneNumberLength( 80 );
+
+// ======== MEMBER FUNCTIONS ========
+
+// -----------------------------------------------------------------------------
+// Two-phased constructor.
+// -----------------------------------------------------------------------------
+//
+CSetUpCallHandler* CSetUpCallHandler::NewL( MSatUtils* aUtils )
+    {
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::NewL calling" )
+
+    CSetUpCallHandler* self = new( ELeave ) CSetUpCallHandler;
+
+    CleanupStack::PushL( self );
+    self->BaseConstructL( aUtils );
+    self->ConstructL();
+    CleanupStack::Pop( self );
+
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::NewL exiting" )
+    return self;
+    }
+
+// -----------------------------------------------------------------------------
+// Destructor.
+// -----------------------------------------------------------------------------
+//
+CSetUpCallHandler::~CSetUpCallHandler()
+    {
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::~CSetUpCallHandler calling" )
+
+    Cancel();
+
+    if ( iServiceHandler )
+        {
+        delete iServiceHandler;
+        iServiceHandler = NULL;
+        }
+
+    if ( iEmergencyCallApi )
+        {
+        delete iEmergencyCallApi;
+        iEmergencyCallApi = NULL;
+        }
+
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::~CSetUpCallHandler exiting" )
+    }
+
+// -----------------------------------------------------------------------------
+// From class MSatEventObserver.
+// Event notification.
+// -----------------------------------------------------------------------------
+//
+void CSetUpCallHandler::Event( TInt aEvent )
+    {
+    LOG2( SIMPLE, "SETUPCALL: CSetUpCallHandler::Event calling,aEvent: %i",
+          aEvent )
+
+    if ( MSatUtils::ECallControlExecuting == aEvent )
+        {
+        LOG( SIMPLE,
+            "SETUPCALL: CSetUpCallHandler::Event: ECallControlExecuting" )
+        iCallControlActive = ETrue;
+        }
+    else if ( MSatUtils::ECallControlDone == aEvent )
+        {
+        LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::Event: ECallControlDone" )
+        iCallControlActive = EFalse;
+
+        // Check if SetUpCall command has arrived from SIM during CC execution
+        // Emergency call is made immediate regardless of call control.
+        if ( !IsActive() && iPCmdPending && !iEmergencyCall )
+            {
+            LOG( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::Event: setupcall" )
+            iPCmdPending = EFalse;
+            // Execute the setupcall.
+            DoHandleCommand();
+            }
+        }
+
+    CSatCommandHandler::Event( aEvent );
+
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::Event exiting" )
+    }
+
+// -----------------------------------------------------------------------------
+// From class MSatCommand.
+// Response from the client.
+// -----------------------------------------------------------------------------
+//
+void CSetUpCallHandler::ClientResponse()
+    {
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::ClientResponse calling" )
+
+    if ( iQueryRsp.iAccepted )
+        {
+        // User accepted the call, make the call
+        TRAPD( error, DoSetupCallL() );
+
+        if ( KErrNone != error )
+            {
+            LOG2( NORMAL, 
+            "SETUPCALL: CSetUpCallHandler::ClientResponse Dial failed: %i", 
+            error )
+
+            CompleteSetupCall( RSat::KCmdDataNotUnderstood );
+            }
+        }
+    else
+        {
+        LOG( NORMAL, 
+        "SETUPCALL: CSetUpCallHandler::ClientResponse User Cancel" )
+
+        if ( iQueryRsp.iSessionTerminatedByUser )
+            {
+            LOG( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::ClientResponse TerminatedByUser" )
+            // Notify sim session end command that next sim session end
+            // should close the ui session.
+            iUtils->NotifyEvent( MSatUtils::ESessionTerminatedByUser );
+            }
+
+        // End key is pressed during confirmation or user denied call setup,
+        // KPCmdNotAcceptedByUser is an expected response,
+        CompleteSetupCall( RSat::KPCmdNotAcceptedByUser );
+        }
+
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::ClientResponse exiting" )
+    }
+
+// -----------------------------------------------------------------------------
+// From class CActive.
+// Cancels the sat request.
+// -----------------------------------------------------------------------------
+//
+void CSetUpCallHandler::DoCancel()
+    {
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::DoCancel calling" )
+
+    iUtils->USatAPI().NotifySetUpCallCancel();
+
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::DoCancel exiting" )
+    }
+
+// -----------------------------------------------------------------------------
+// From class CSatCommandHandler.
+// Requests the command notification.
+// -----------------------------------------------------------------------------
+//
+void CSetUpCallHandler::IssueUSATRequest( TRequestStatus& aStatus )
+    {
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::IssueUSATRequest calling" )
+
+    // Clear the IPC package.
+    new (&iSetUpCallData) RSat::TSetUpCallV1();
+    iPCmdPending = EFalse;
+    iQueryRsp.iAccepted = EFalse;
+
+    iUtils->USatAPI().NotifySetUpCall( aStatus, iSetUpCallPckg );
+
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::IssueUSATRequest exiting" )
+    }
+
+// -----------------------------------------------------------------------------
+// From class CSatCommandHandler.
+// SetUpCall command is not allowed in following situations:
+//      - Phone is not registered to homenetwork and roaming.
+//      - phone is ringing, alerting or call is on and SetUpCall command
+//        is "make call only if not busy", "make call only if not busy wiht
+//        redial" or "Call type not set".
+// -----------------------------------------------------------------------------
+//
+TBool CSetUpCallHandler::CommandAllowed()
+    {
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::CommandAllowed calling" )
+    TBool commandAllowed( ETrue );
+
+    // Emergency call can newer be denied.
+    // The usage of constant emergency number is according to ETSI TS 31.111.
+    iEmergencyCall =
+        ( 0 == iSetUpCallData.iAddress.iTelNumber.Compare(
+            KFixedSimEmergencyNumber ) );
+
+    if ( !iEmergencyCall )
+        {
+        RMobilePhone::TMobilePhoneRegistrationStatus networkStatus(
+            iUtils->SystemState().GetNetworkRegistrationStatus() );
+
+        if ( ( ( RSat::EAlphaIdProvided !=
+                     iSetUpCallData.iAlphaIdConfirmationPhase.iStatus ) &&
+               ( ( RSat::ESelfExplanatory ==
+                       iSetUpCallData.iIconIdConfirmationPhase.iQualifier ) ||
+                 ( RSat::ENotSelfExplanatory ==
+                       iSetUpCallData.iIconIdConfirmationPhase.iQualifier ) ) )
+                 ||
+             ( ( RSat::EAlphaIdProvided !=
+                     iSetUpCallData.iAlphaIdCallSetUpPhase.iStatus ) &&
+               ( ( RSat::ESelfExplanatory ==
+                       iSetUpCallData.iIconIdCallSetUpPhase.iQualifier ) ||
+                 ( RSat::ENotSelfExplanatory ==
+                       iSetUpCallData.iIconIdCallSetUpPhase.iQualifier ) ) ) )
+            {
+            // Icon data is received without alpha id.
+            CompleteSetupCall( RSat::KCmdDataNotUnderstood );
+
+            commandAllowed = EFalse;
+            LOG( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::CommandAllowed Icon received \
+            without alpha id" )
+            }
+        else if ( ( RMobilePhone::ERegisteredOnHomeNetwork != networkStatus ) &&
+                  ( RMobilePhone::ERegisteredRoaming != networkStatus ) )
+            {
+            // Not registered to network.
+            CompleteSetupCall( RSat::KMeUnableToProcessCmd, RSat::KNoService );
+
+            commandAllowed = EFalse;
+            LOG( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::CommandAllowed Registration not \
+            valid" )
+            }
+        else
+            {
+            LOG( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::CommandAllowed others" )
+            // Call type
+            const RSat::TSetUpCallType callType( iSetUpCallData.iType );
+
+            // Command does not allow to make a call if busy
+            const TBool dontMakeCallIfBusy(
+                ( RSat::EOnlyIfNotBusy == callType ) ||
+                ( RSat::EOnlyIfNotBusyWithRedial == callType ) ||
+                ( RSat::ESetUpCallTypeNotSet == callType ) );
+
+            if ( dontMakeCallIfBusy )
+                {
+                LOG( SIMPLE, 
+                "SETUPCALL: CSetUpCallHandler::CommandAllowed \
+                dontMakeCallIfBusy true" )
+                // Is the call ongoing
+                const TBool callIsOngoing(
+                    iUtils->SystemState().IsCallActive() );
+
+                // Is the call incoming
+                const TBool callIsIncoming(
+                    iUtils->SystemState().IsCallIncoming() );
+
+                if ( callIsOngoing || callIsIncoming )
+                    {
+                    // Set the terminal response info.
+                    CompleteSetupCall(
+                        RSat::KMeUnableToProcessCmd,
+                        RSat::KMeBusyOnCall );
+
+                    commandAllowed = EFalse;
+                    LOG( SIMPLE, 
+                    "SETUPCALL: CSetUpCallHandler::CommandAllowed Busy" )
+                    }
+                }
+            }
+
+        if ( commandAllowed )
+            {
+            LOG( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::CommandAllowed Allowed to call" )
+
+            // Set icon command flag whether icon data was received and
+            // set qualifier to no icon id
+            // To be removed when icons are allowed in this command
+            if ( ( RSat::ESelfExplanatory ==
+                     iSetUpCallData.iIconIdConfirmationPhase.iQualifier ) ||
+                 ( RSat::ENotSelfExplanatory ==
+                     iSetUpCallData.iIconIdConfirmationPhase.iQualifier ) ||
+                 ( RSat::ESelfExplanatory ==
+                     iSetUpCallData.iIconIdCallSetUpPhase.iQualifier ) ||
+                 ( RSat::ENotSelfExplanatory ==
+                     iSetUpCallData.iIconIdCallSetUpPhase.iQualifier ) )
+                {
+                LOG( SIMPLE, "SETUPCALL:   ENoIconId" )
+                iIconCommand = ETrue;
+                iSetUpCallData.iIconIdConfirmationPhase.iQualifier =
+                    RSat::ENoIconId;
+                iSetUpCallData.iIconIdCallSetUpPhase.iQualifier =
+                    RSat::ENoIconId;
+                }
+            else
+                {
+                iIconCommand = EFalse;
+                }
+            }
+        }
+    else
+        {
+        LOG( SIMPLE, 
+        "SETUPCALL: CSetUpCallHandler::CommandAllowed Emergency call" )
+        }
+
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::CommandAllowed exiting" )
+    
+    return commandAllowed;
+    }
+
+// -----------------------------------------------------------------------------
+// From class CSatCommandHandler.
+// Need for ui session.
+// -----------------------------------------------------------------------------
+//
+TBool CSetUpCallHandler::NeedUiSession()
+    {
+    LOG( NORMAL, "SETUPCALL: CSetUpCallHandler::NeedUiSession calling" )
+
+    // Notify Cover UI if it's supported
+    if ( iUtils->CoverUiSupported() )
+        {
+        LOG( NORMAL, 
+        "SETUPCALL: CSetUpCallHandler::NeedUiSession CoverUiSupported" )
+        TSatCommandData medEventData;
+        medEventData.iPCmdNumber = RSat::ESetUpCall;
+        medEventData.iAlphaId = iSetUpCallData.iAlphaIdCallSetUpPhase;
+        medEventData.iDuration.iTimeUnit = RSat::ESeconds;
+        medEventData.iDuration.iNumOfUnits = KSatDefaultDuration;
+        medEventData.iIconID = iSetUpCallData.iIconIdCallSetUpPhase;
+        TSatCommandPckg tPckg( medEventData );
+        iUtils->RaiseSatEvent( tPckg );
+        }
+
+    LOG( NORMAL, "SETUPCALL: CSetUpCallHandler::NeedUiSession exiting" )
+    return ETrue;
+    }
+
+// -----------------------------------------------------------------------------
+// From class CSatCommandHandler.
+// Called when USAT API notifies that command.
+// -----------------------------------------------------------------------------
+//
+void CSetUpCallHandler::HandleCommand()
+    {
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::HandleCommand calling" )
+
+    if ( iEmergencyCall )
+        {
+        LOG( SIMPLE, 
+        "SETUPCALL: CSetUpCallHandler::HandleCommand iEmergencyCall true" )
+        TRAPD( err, CreateEmergencyCallL() );
+        if ( KErrNone != err )
+            {
+            LOG2( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::HandleCommand DialEmergencyCallL \
+            failed: %d", err )
+
+            iEmergencyCall = EFalse;
+
+            // Set the terminal response info.
+            CompleteSetupCall(
+                RSat::KMeUnableToProcessCmd,
+                RSat::KNoSpecificMeProblem );
+            }
+        }
+    else
+        {
+        const RSat::TAlphaIdStatus alphaIdStatus(
+            iSetUpCallData.iAlphaIdCallSetUpPhase.iStatus );
+
+        // If the alpha id is null, then use SAT name as a alpha identifier.
+        if ( ( RSat::EAlphaIdNull == alphaIdStatus )  ||
+             ( RSat::EAlphaIdNotPresent == alphaIdStatus ) )
+            {
+            LOG( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::HandleCommand set AlphaId" )
+            iSetUpCallData.iAlphaIdCallSetUpPhase.iAlphaId =
+                iUtils->SatAppName();
+            iSetUpCallData.iAlphaIdCallSetUpPhase.iStatus =
+                RSat::EAlphaIdProvided;
+            }
+
+        // Copy the data to package, which is sent to client.
+        iQueryData.iCommand = ESatSSetUpCallQuery;
+        iQueryData.iQueryText.Copy(
+            iSetUpCallData.iAlphaIdConfirmationPhase.iAlphaId );
+        iQueryData.iSimApplicationName.Copy( iUtils->SatAppName() );
+        iQueryData.iAlphaIdStatus = ESatAlphaIdNotNull; // Always
+        iQueryData.iIconId.iIdentifier =
+            iSetUpCallData.iIconIdConfirmationPhase.iIdentifier;
+
+        LOG2( SIMPLE, 
+        "SETUPCALL: iSetUpCallData.iIconIdConfirmationPhase.iQualifier: %d",
+        iSetUpCallData.iIconIdConfirmationPhase.iQualifier )
+        switch ( iSetUpCallData.iIconIdConfirmationPhase.iQualifier )
+            {
+            case RSat::ESelfExplanatory:
+                {
+                // Icon qualifier is self explanatory (to display instead
+                // of the alpha id or text string).
+                iQueryData.iIconId.iIconQualifier = ESatSelfExplanatory;
+                break;
+                }
+
+            case RSat::ENotSelfExplanatory:
+                {
+                // Icon qualifier is not self explanatory.
+                iQueryData.iIconId.iIconQualifier = ESatNotSelfExplanatory;
+                break;
+                }
+
+            default:
+                {
+                // Icon qualifier not present
+                iQueryData.iIconId.iIconQualifier = ESatENoIconId;
+                break;
+                }
+            }
+
+        // If call control is active, set up call is made
+        // after the call control note is showed in ui ie
+        // ECallControlDone event is notified.
+        if ( !iCallControlActive )
+            {
+            LOG( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::HandleCommand iCallControlActive \
+            false" )
+            iUtils->NotifyEvent( MSatUtils::ESetUpCallExecuting );
+
+            TRAPD( regErr, iUtils->RegisterServiceRequestL(
+                ESatSProactiveQuery,
+                ESatSProactiveQueryResponse,
+                this ) );
+            LOG2( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::HandleCommand regErr: %d", regErr )
+            if ( KErrNone != regErr )
+                {
+                // Possible memory allocation error. Send error terminal
+                // response
+                UiLaunchFailed();
+                }
+            else
+                {
+                // Send query to UI
+                iUtils->SatUiHandler().UiSession()->SendCommand(
+                    &iQueryPckg,
+                    &iQueryRspPckg,
+                    ESatSProactiveQuery );
+                }
+            }
+        else
+            {
+            LOG( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::HandleCommand iCallControlActive \
+            true" )
+            // Set pending flag on
+            iPCmdPending = ETrue;
+            }
+        }
+
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::HandleCommand exiting" )
+    }
+
+// -----------------------------------------------------------------------------
+// From class CSatCommandHandler.
+// Indication that UI lanching failed.
+// -----------------------------------------------------------------------------
+//
+void CSetUpCallHandler::UiLaunchFailed()
+    {
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::UiLaunchFailed calling" )
+
+    CompleteSetupCall( RSat::KMeUnableToProcessCmd, 
+                       RSat::KNoSpecificMeProblem );
+
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::UiLaunchFailed exiting" )
+    }
+
+// -----------------------------------------------------------------------------
+// From class MAiwNotifyCallback.
+// Called when dial request is completed.
+// -----------------------------------------------------------------------------
+//
+TInt CSetUpCallHandler::HandleNotifyL(
+    const TInt aCmdId,
+    const TInt aEventId,
+    CAiwGenericParamList& aEventParamList,
+    const CAiwGenericParamList& /*aInParamList*/ )
+    {
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::HandleNotifyL calling" )
+
+    if ( KAiwCmdCall == aCmdId )
+        {
+        LOG2( SIMPLE, 
+        "SETUPCALL: CSetUpCallHandler::HandleNotifyL  event: %d", aEventId )
+        switch ( aEventId )
+            {
+            case KAiwEventError:
+            case KAiwEventCompleted:
+            case EGenericParamError: // This is due CCaUiPlugin behaviour.
+                                     // Also overlaps event KAiwEventStarted.
+                {
+                LOG( SIMPLE, 
+                "SETUPCALL: CSetUpCallHandler::HandleNotifyL SetupCall \
+                Completed" )
+
+                // Fetch completion status.
+                TInt index( 0 );
+                const TAiwGenericParam* param = aEventParamList.FindFirst(
+                    index, EGenericParamError );
+
+                if ( param )
+                    {
+                    LOG( SIMPLE, 
+                    "SETUPCALL: CSetUpCallHandler::HandleNotifyL param true" )
+                    
+                    // Converts error number to symbian-formatted before 
+                    // calling CompleteSetupCallWithStatus.
+                    TInt error = TccpErrorToSymbianError( 
+                        param->Value().AsTInt32() );
+                    CompleteSetupCallWithStatus( error );
+                    }
+                else
+                    {
+                    CompleteSetupCall( RSat::KSuccess );
+                    }
+                }
+                break;
+
+            case KAiwEventCanceled:
+            case KAiwEventStopped:
+            case KAiwEventQueryExit:
+                {
+                LOG( SIMPLE, 
+                "SETUPCALL: CSetUpCallHandler::HandleNotifyL SetupCall \
+                cancelled" )
+
+                CompleteSetupCallWithStatus( KErrAbort );
+                }
+                break;
+
+            case KAiwEventOutParamCheck:
+            case KAiwEventInParamCheck:
+                {
+                LOG( SIMPLE, 
+                "SETUPCALL: CSetUpCallHandler::HandleNotifyL SetupCall param \
+                fail" )
+
+                CompleteSetupCall( RSat::KCmdDataNotUnderstood );
+                }
+                break;
+
+            default:
+                {
+                LOG( SIMPLE, 
+                "SETUPCALL: CSetUpCallHandler::HandleNotifyL Unknown event \
+                id" )
+                }
+                break;
+
+            }
+        }
+
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::HandleNotifyL exiting" )
+    return KErrNone;
+    }
+
+// -----------------------------------------------------------------------------
+// From class MAiwNotifyCallback.
+// Called when dial request is completed.
+// -----------------------------------------------------------------------------
+//
+void CSetUpCallHandler::HandleEmergencyDialL( const TInt aStatus )
+    {
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::HandleEmergencyDialL calling" )
+
+    iEmergencyCall = EFalse;
+
+    if ( KErrNone == aStatus )
+        {
+        // Set result
+        CompleteSetupCall( RSat::KSuccess );
+        }
+    else
+        {
+        CompleteSetupCall(
+            RSat::KNetworkUnableToProcessCmd,
+            RSat::KNoSpecificMeProblem );
+
+        LOG( SIMPLE, 
+        "SETUPCALL: CSetUpCallHandler::HandleEmergencyDialL Network unable \
+        to process this" )
+        }
+
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::HandleEmergencyDialL exiting" )
+    }
+
+// -----------------------------------------------------------------------------
+// C++ default constructor can NOT contain any code, that
+// might leave.
+// -----------------------------------------------------------------------------
+//
+//lint -e{1403, 1769} Can not be initialized, harmless.
+CSetUpCallHandler::CSetUpCallHandler() :
+    CSatCommandHandler(),
+    iSetUpCallData(),
+    iSetUpCallPckg( iSetUpCallData ),
+    iSetUpCallRsp(),
+    iSetUpCallRspPckg( iSetUpCallRsp ),
+    iQueryData(),
+    iQueryPckg( iQueryData ),
+    iQueryRsp(),
+    iQueryRspPckg( iQueryRsp ),
+    // To be removed when icons are allowed in this command
+    iIconCommand( EFalse )
+    {
+    LOG( SIMPLE,
+        "SETUPCALL: CSetUpCallHandler::CSetUpCallHandler calling - exiting" )
+    }
+
+// -----------------------------------------------------------------------------
+// Symbian 2nd phase constructor can leave.
+// -----------------------------------------------------------------------------
+//
+void CSetUpCallHandler::ConstructL()
+    {
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::ConstructL calling" )
+
+    // Create request handler. This is same that LaunchBrowser uses, so this
+    // is needed also in HandleCommand - function.
+    iUtils->RegisterServiceRequestL(
+        ESatSProactiveQuery,
+        ESatSProactiveQueryResponse,
+        this );
+
+    iUtils->RegisterL( this, MSatUtils::ECallControlExecuting );
+    iUtils->RegisterL( this, MSatUtils::ECallControlDone );
+
+    // Create service handler for normal call setup.
+    iServiceHandler = CAiwServiceHandler::NewL();
+
+    // Create dynamic resource to attach service handler.
+    RCriteriaArray interest;
+    CAiwCriteriaItem* item = CAiwCriteriaItem::NewLC(
+        KAiwCmdCall,
+        KAiwCmdCall,
+        KContentType );
+
+    TUid serviceClassBase;
+    serviceClassBase.iUid = KAiwClassBase;
+    item->SetServiceClass( serviceClassBase );
+
+    interest.AppendL( item );
+
+    // Attach to call service.
+    iServiceHandler->AttachL( interest );
+
+    CleanupStack::PopAndDestroy( item );
+
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::ConstructL exiting" )
+    }
+
+// -----------------------------------------------------------------------------
+// Performs the request to dial
+// -----------------------------------------------------------------------------
+//
+void CSetUpCallHandler::DoSetupCallL()
+    {
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::DoSetupCallL calling" )
+
+    RSat::TSetUpCallType callType( iSetUpCallData.iType );
+
+    TDes& telNumber( iSetUpCallData.iAddress.iTelNumber );
+    CheckNumber( telNumber );
+
+    // 80 is max length in SAT calls, AIW max length is 100
+    if ( telNumber.Length() > KMaximumPhoneNumberLength )
+        {
+        LOG( SIMPLE, 
+        "SETUPCALL: CSetUpCallHandler::DoSetupCallL telNumber too long" )
+        User::Leave( KErrArgument );
+        }
+
+    TBuf< AIWDialDataExt::KMaximumNameLength > name;
+    if ( RSat::EAlphaIdProvided ==
+         iSetUpCallData.iAlphaIdCallSetUpPhase.iStatus )
+        {
+        LOG( SIMPLE, 
+        "SETUPCALL: CSetUpCallHandler::DoSetupCallL EAlphaIdProvided" )
+        name = iSetUpCallData.iAlphaIdCallSetUpPhase.iAlphaId;
+        }
+    else
+        {
+        LOG( SIMPLE, 
+        "SETUPCALL: CSetUpCallHandler::DoSetupCallL set AlphaId" )
+        name = iUtils->SatAppName();
+        }
+
+    // Make the phone call parameters.
+    CAiwInternalDialData* dialData = CAiwInternalDialData::NewLC();
+
+    dialData->SetCallType( CAiwDialData::EAIWVoice );
+    dialData->SetWindowGroup( AIWDialData::KAiwGoToIdle );
+    dialData->SetPhoneNumberL( telNumber );
+    dialData->SetSATCall( ETrue );
+    dialData->SetShowNumber( EFalse );
+    dialData->SetNameL( name );
+    dialData->SetAllowMatch( EFalse );
+    // Remove the redial mechanism from S60 5.x.
+    dialData->SetRedial( AIWDialDataExt::KAIWRedialOff );
+
+    // check if we need to disconnect other calls
+    if ( ( RSat::EDisconnectOtherCalls == callType ) ||
+         ( RSat::EDisconnectOtherCallsWithRedial == callType ) )
+        {
+        LOG( SIMPLE, 
+        "SETUPCALL: CSetUpCallHandler::DoSetupCallL end other call" )
+        dialData->SetEndOtherCalls( ETrue );
+        }
+
+    if ( AIWInternalDialData::KAiwBearerLength >=
+         iSetUpCallData.iCapabilityConfigParams.Length() )
+        {
+        LOG( NORMAL, 
+        "SETUPCALL: CSetUpCallHandler::DoSetupCallL SetBearerL" )
+        dialData->SetBearerL( iSetUpCallData.iCapabilityConfigParams );
+        }
+
+    if ( AIWInternalDialData::KAiwSubAddressLength >=
+         iSetUpCallData.iSubAddress.Length() )
+        {
+        LOG( NORMAL, 
+        "SETUPCALL: CSetUpCallHandler::DoSetupCallL SetSubAddressL" )
+        dialData->SetSubAddressL( iSetUpCallData.iSubAddress );
+        }
+
+    CAiwGenericParamList& paramList = iServiceHandler->InParamListL();
+    dialData->FillInParamListL( paramList );
+
+    iServiceHandler->ExecuteServiceCmdL(
+        KAiwCmdCall,
+        paramList,
+        iServiceHandler->OutParamListL(),
+        0,
+        this );
+
+    CleanupStack::PopAndDestroy( dialData );
+
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::DoSetupCallL exiting" )
+    }
+
+// -----------------------------------------------------------------------------
+// Return terminal response filled according to dial result.
+// -----------------------------------------------------------------------------
+//
+void CSetUpCallHandler::CompleteSetupCallWithStatus(
+    const TInt32 aStatus )
+    {
+    LOG2( SIMPLE,
+        "SETUPCALL: CSetUpCallHandler::CompleteSetupCallWithStatus calling: \
+        %i", aStatus )
+
+    // Form Terminal Response
+    if ( KErrNone != aStatus )
+        {
+        switch ( aStatus )
+            {
+            case KErrGsmCCCallRejected:
+                {
+                LOG( SIMPLE, 
+                "SETUPCALL: CSetUpCallHandler::CompleteSetupCallWithStatus Call \
+                Control not allowed" )
+                // If SetUpCall is not allowed by SIM in Call Control, then
+                // give a correct response.
+                CompleteSetupCall(
+                    RSat::KInteractionWithCCPermanentError,
+                    RSat::KActionNotAllowed );
+                break;
+                }
+
+            case KErrGsmCCBearerCapabilityNotAuthorised:
+                {
+                LOG( SIMPLE, 
+                "SETUPCALL: CSetUpCallHandler::CompleteSetupCallWithStatus \
+                Beyond ME Capabilities" )
+                // If bearer capability is not authorized, return correct value
+                CompleteSetupCall( RSat::KCmdBeyondMeCapabilities );
+                break;
+                }
+
+            case KErrAbort:
+                {
+                LOG( SIMPLE, 
+                "SETUPCALL: CSetUpCallHandler::CompleteSetupCallWithStatus User \
+                abort" )
+                if ( iQueryRsp.iSessionTerminatedByUser )
+                    {
+                    LOG( SIMPLE, 
+                    "SETUPCALL: CSetUpCallHandler::CompleteSetupCallWithStatus \
+                    TerminatedByUser" )
+                    // Notify sim session end command that next sim session end
+                    // should close the ui session.
+                    iUtils->NotifyEvent( MSatUtils::ESessionTerminatedByUser );
+                    }
+
+                // User has ended redial mechanism.
+                CompleteSetupCall( RSat::KCallClearedBeforeConnectionOrReleased );
+                break;
+                }
+
+            case KErrGeneral:
+                {
+                LOG( SIMPLE, 
+                "SETUPCALL: CSetUpCallHandler::CompleteSetupCallWithStatus Data \
+                not understood" )
+                CompleteSetupCall( RSat::KCmdDataNotUnderstood );
+                break;
+                }
+
+            case KErrAccessDenied:
+                {
+                LOG( SIMPLE, 
+                "SETUPCALL: CSetUpCallHandler::CompleteSetupCallWithStatus \
+                Network unable to process this" )
+                CompleteSetupCall(
+                    RSat::KNetworkUnableToProcessCmd,
+                    RSat::KNoSpecificMeProblem );
+                break;
+                }
+                
+            case KErrSatControl:
+                {
+                LOG( SIMPLE, 
+                "SETUPCALL: CSetUpCallHandler::CompleteSetupCallWithStatus \
+                Call Command performed, but modified by Call Control" )
+                // Call control modified the type of request indicated in
+                // the proactive command, and the action requested by 
+                // call control was performed successfully.
+                CompleteSetupCall( RSat::KModifiedByCallControl );
+                break;
+                }
+                
+            default:
+                {
+                LOG( SIMPLE,
+                "SETUPCALL: CSetUpCallHandler::CompleteSetupCallWithStatus \
+                Network unable to process with error info" )
+
+                iSetUpCallRsp.iGeneralResult = RSat::KNetworkUnableToProcessCmd;
+                iSetUpCallRsp.iInfoType = RSat::KSatNetworkErrorInfo;
+
+                // Lower byte contains the error cause.
+                iSetUpCallRsp.iAdditionalInfo.SetLength( 1 );
+
+                // Get mapped additional info
+                TUint8 addInfo( TSatExtErrorUtils::MapError( aStatus ) );
+                iSetUpCallRsp.iAdditionalInfo[0] =
+                    static_cast<TUint16>( addInfo );
+
+                // Send terminal response
+                TerminalRsp( RSat::ESetUpCall, iSetUpCallRspPckg );
+                break;
+                }
+            }
+        }
+    else
+        {
+        // Convert terminal rsp if icon used
+        RSat::TIconQualifier qualifier1(
+            iSetUpCallData.iIconIdConfirmationPhase.iQualifier );
+        RSat::TIconQualifier qualifier2(
+            iSetUpCallData.iIconIdCallSetUpPhase.iQualifier );
+
+        RSat::TPCmdResult result( RSat::KSuccess );
+
+        // Icon support for call confirmtion phase not done.
+        if ( !iQueryRsp.iRequestedIconDisplayed &&
+           ( ( RSat::ESelfExplanatory == qualifier1 ) ||
+             ( RSat::ENotSelfExplanatory == qualifier1 ) ) )
+            {
+            result = RSat::KSuccessRequestedIconNotDisplayed;
+            LOG( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::CompleteSetupCallWithStatus \
+            Confirmation icon not shown" )
+            }
+        // Icon support for call setup phase not done.
+        else if ( ( RSat::ESelfExplanatory == qualifier2 ) ||
+                  ( RSat::ENotSelfExplanatory == qualifier2 ) )
+            {
+            result = RSat::KSuccessRequestedIconNotDisplayed;
+            LOG( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::CompleteSetupCallWithStatus Icon \
+            not shown" )
+            }
+        // If command had icon data and was done succesfully, report that icon
+        // was not shown.
+        // To be removed when icons are allowed in this command.
+        else
+            {
+            LOG( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::CompleteSetupCallWithStatus \
+            others" )
+            if ( iIconCommand )
+                {
+                LOG( SIMPLE, 
+                "SETUPCALL: CSetUpCallHandler::CompleteSetupCallWithStatus \
+                iIconCommand true" )
+                result = RSat::KSuccessRequestedIconNotDisplayed;
+                }
+            }
+
+        // Set result
+        CompleteSetupCall( result );
+        }
+
+    LOG( SIMPLE,
+        "SETUPCALL: CSetUpCallHandler::CompleteSetupCallWithStatus exiting" )
+    }
+
+// -----------------------------------------------------------------------------
+// Return terminal response filled according to result.
+// -----------------------------------------------------------------------------
+//
+void CSetUpCallHandler::CompleteSetupCall(
+    const RSat::TPCmdResult aGeneralResult )
+    {
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::CompleteSetupCall calling" )
+
+    // Fill Terminal Response.
+    iSetUpCallRsp.iGeneralResult = aGeneralResult;
+    iSetUpCallRsp.iInfoType = RSat::KNoAdditionalInfo;
+    iSetUpCallRsp.iAdditionalInfo.Zero();
+    iSetUpCallRsp.SetPCmdNumber( iSetUpCallData.PCmdNumber() );
+
+    // Send terminal response.
+    TerminalRsp( RSat::ESetUpCall, iSetUpCallRspPckg );
+
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::CompleteSetupCall exiting" )
+    }
+
+// -----------------------------------------------------------------------------
+// Return terminal response filled according to result.
+// -----------------------------------------------------------------------------
+//
+void CSetUpCallHandler::CompleteSetupCall(
+    const RSat::TPCmdResult aGeneralResult,
+    const TInt16 aAdditionalInfo )
+    {
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::CompleteSetupCall calling" )
+
+    // Fill Terminal Response.
+    iSetUpCallRsp.iGeneralResult = aGeneralResult;
+    iSetUpCallRsp.iInfoType = RSat::KMeProblem;
+    iSetUpCallRsp.iAdditionalInfo.SetLength( 1 );
+    iSetUpCallRsp.iAdditionalInfo[0] = aAdditionalInfo;
+    iSetUpCallRsp.SetPCmdNumber( iSetUpCallData.PCmdNumber() );
+
+    // Send terminal response.
+    TerminalRsp( RSat::ESetUpCall, iSetUpCallRspPckg );
+
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::CompleteSetupCall exiting" )
+    }
+
+// -----------------------------------------------------------------------------
+// Checks the dialling number string for extended BCD
+// values. Changes them to correct characters
+// see ETSI 11.11 10.5.1
+// -----------------------------------------------------------------------------
+//
+void CSetUpCallHandler::CheckNumber( TDes& aNumber ) const
+    {
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::CheckNumber calling" )
+
+    for ( TInt i = 0; i < aNumber.Length(); i++ )
+        {
+        // check values
+        if ( KBCDAsterisk == aNumber[i] )
+            {
+            LOG( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::CheckNumber KAsteriskChar" )
+            aNumber[i] = KAsteriskChar;
+            }
+
+        if ( KBCDDash == aNumber[i] )
+            {
+            LOG( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::CheckNumber KDashChar" )
+            aNumber[i] = KDashChar;
+            }
+
+        if ( KBCDDTMF == aNumber[i] )
+            {
+            LOG( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::CheckNumber KDTMFChar" )
+            aNumber[i] = KDTMFChar;
+            }
+
+        if ( KBCDWild == aNumber[i] )
+            {
+            LOG( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::CheckNumber KWildChar" )
+            aNumber[i] = KWildChar;
+            }
+
+        if ( KBCDExpansion == aNumber[i] )
+            {
+            LOG( SIMPLE, 
+            "SETUPCALL: CSetUpCallHandler::CheckNumber KExpansionChar" )
+            aNumber[i] = KExpansionChar;
+            }
+        }
+    LOG2( SIMPLE, 
+    "SETUPCALL: CSetUpCallHandler::CheckNumber length of aNumber: %d",
+     aNumber.Length() )
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::CheckNumber exiting" )
+    }
+
+// -----------------------------------------------------------------------------
+// Converts a TCCP error to the corresponding symbian error.
+// -----------------------------------------------------------------------------
+//
+TInt CSetUpCallHandler::TccpErrorToSymbianError( const TInt aTccpError ) const
+    {
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::TccpErrorToSymbianError \
+        calling" )
+    
+    // Error to be returned after mapped from aTccpError;
+    // Initialized with default value KErrAccessDenied.
+    TInt retValue( KErrAccessDenied );
+    
+    // Convert TCCP Error to Symbian Error in the switch braces.
+    switch ( aTccpError )
+        {
+        case ECCPErrorNone:
+        case ECCPErrorNotFound:
+        case ECCPErrorGeneral:
+        case ECCPErrorCancel:
+        case ECCPErrorNoMemory:
+        case ECCPErrorNotSupported:
+        case ECCPErrorAlreadyInUse:
+        case ECCPErrorNotReady:
+            {
+            retValue = aTccpError;
+            break;
+            }
+            
+        case ECCPErrorCCCallRejected:
+            {
+            retValue = KErrGsmCCCallRejected;
+            break;
+            }
+            
+        case ECCPRequestFailure:
+            {
+            retValue = KErrGsmMMCongestion;
+            break;
+            }
+            
+        case ECCPErrorCCBearerCapabilityNotAuthorised:
+        case ECCPErrorBadRequest:
+            {
+            retValue = KErrGsmCCBearerCapabilityNotAuthorised;
+            break;
+            }
+            
+        case ECCPErrorAccessDenied:
+            {
+            retValue = KErrAccessDenied;
+            break;
+            }
+        
+         //The following are KErrGsmCallControlBase group.
+        case ECCPErrorNotReached:
+            {
+            retValue = KErrGsmCCUnassignedNumber;
+            break;
+            }
+            
+        case ECCPErrorBusy:
+            {
+            retValue = KErrGsmCCUserBusy;
+            break;
+            }
+            
+        case ECCPErrorMovedPermanently:
+            {
+            retValue = KErrGsmCCNumberChanged;
+            break;
+            }
+            
+        case ECCPErrorInvalidURI:
+            {
+            retValue = KErrGsmCCInvalidNumberFormat;
+            break;
+            }
+            
+        case ECCPErrorNetworkOutOfOrder:
+            {
+            retValue = KErrGsmCCNetworkOutOfOrder;
+            break;
+            }
+            
+        case ECCPErrorCCNoRouteToDestination:
+            {
+            retValue = KErrGsmCCNoRouteToDestination;
+            break;
+            }
+
+        case ECCPErrorCCDestinationOutOfOrder:
+            {
+            retValue = KErrGsmCCDestinationOutOfOrder;
+            break;
+            }
+            
+        case ECCPErrorCCResourceNotAvailable:
+            {
+            retValue = KErrGsmCCResourceNotAvailable;
+            break;
+            }
+            
+
+        case ECCPErrorCCInvalidTransitNetworkSelection:
+            {
+            retValue = KErrGsmCCInvalidTransitNetworkSelection;
+            break;
+            }
+            
+        case ECCPErrorCCIncompatibleDestination:
+            {
+            retValue = KErrGsmCCIncompatibleDestination;
+            break;
+            }
+            
+        case ECCPErrorCCIncompatibleMessageInCallState:
+            {
+            retValue = KErrGsmCCIncompatibleMessageInCallState;
+            break;
+            }
+
+        case ECCPErrorCCIncompatibleMessageInProtocolState:
+            {
+            retValue = KErrGsmCCIncompatibleMessageInProtocolState;
+            break;
+            }
+            
+        case ECCPErrorCCNormalCallClearing:
+            {
+            retValue = KErrGsmCCNormalCallClearing;
+            break;
+            }
+            
+        case ECCPErrorCCUserAlertingNoAnswer:
+            {
+            retValue = KErrGsmCCUserAlertingNoAnswer;
+            break;
+            }
+
+        case ECCPErrorCCUserNotResponding:
+            {
+            retValue = KErrGsmCCUserNotResponding;
+            break;
+            }
+
+        case ECCPErrorCCPreemption:
+            {
+            retValue = KErrGsmCCPreemption;
+            break;
+            }
+            
+        case ECCPErrorCCFacilityRejected:
+            {
+            retValue = KErrGsmCCFacilityRejected;
+            break;
+            }
+
+        case ECCPErrorCCResponseToStatusEnquiry:
+            {
+            retValue = KErrGsmCCResponseToStatusEnquiry;
+            break;
+            }
+            
+        case ECCPErrorCCInvalidMandatoryInformation:
+            {
+            retValue = KErrGsmCCInvalidMandatoryInformation;
+            break;
+            }
+            
+        case ECCPErrorCCNonExistentMessageType:
+            {
+            retValue = KErrGsmCCNonExistentMessageType;
+            break;
+            }
+
+        case ECCPErrorCCNonExistentInformationElement:
+            {
+            retValue = KErrGsmCCNonExistentInformationElement;
+            break;
+            }
+
+        case ECCPErrorCCNoChannelAvailable:
+            {
+            retValue = KErrGsmCCNoChannelAvailable;
+            break;
+            }
+
+        case ECCPErrorCCRequestedFacilityNotSubscribed:
+            {
+            retValue = KErrGsmCCRequestedFacilityNotSubscribed;
+            break;
+            }
+
+        case ECCPErrorCCIncomingCallsBarredInCug:
+            {
+            retValue = KErrGsmCCIncomingCallsBarredInCug;
+            break;
+            }
+            
+        case ECCPErrorUserNotInCug:
+            {
+            retValue = KErrGsmCCUserNotInCug;
+            break;
+            }
+            
+        case ECCPErrorCCRecoveryOnTimerExpiry:
+            {
+            retValue = KErrGsmCCRecoveryOnTimerExpiry;
+            break;
+            }
+
+        case ECCPErrorCCBearerCapabilityNotCurrentlyAvailable:
+            {
+            retValue = KErrGsmCCBearerCapabilityNotCurrentlyAvailable;
+            break;
+            }
+
+        case ECCPErrorCCServiceNotAvailable:
+            {
+            retValue = KErrGsmCCServiceNotAvailable;
+            break;
+            }
+
+        case ECCPErrorCCBearerServiceNotImplemented:
+            {
+            retValue = KErrGsmCCBearerServiceNotImplemented;
+            break;
+            }
+
+        case ECCPErrorCCOnlyRestrictedDigitalInformationBCAvailable:
+            {
+            retValue = KErrGsmCCOnlyRestrictedDigitalInformationBCAvailable;
+            break;
+            }
+            
+        case ECCPErrorCCServiceNotImplemented:
+            {
+            retValue = KErrGsmCCServiceNotImplemented;
+            break;
+            }
+            
+        case ECCPErrorCCUnspecifiedInterworkingError:
+            {
+            retValue = KErrGsmCCUnspecifiedInterworkingError;
+            break;
+            }
+            
+        case ECCPErrorSatControl:
+            {
+            retValue = KErrSatControl;
+            break;
+            }
+                
+        default:
+            {
+            retValue = KErrAccessDenied;
+            break;
+            }
+        }
+        
+    LOG2( SIMPLE, 
+        "SETUPCALL: CSetUpCallHandler::TccpErrorToSymbianError TCCP error:%d",
+         aTccpError)
+    LOG2( SIMPLE, 
+        "SETUPCALL: CSetUpCallHandler::TccpErrorToSymbianError \
+        mapped Symbian Error:%d", retValue)
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::TccpErrorToSymbianError \
+        exiting" )
+    
+    return retValue;
+    }
+
+// -----------------------------------------------------------------------------
+// Create emergency call
+// -----------------------------------------------------------------------------
+//
+void CSetUpCallHandler::CreateEmergencyCallL()
+    {
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::CreateEmergencyCallL calling" )
+    
+    if( !iEmergencyCallApi )
+        {
+        // Create service handler for emergency call setup..
+        LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::CreateEmergencyCallL\
+         create emergency call handler" )
+        iEmergencyCallApi = CPhCltEmergencyCall::NewL( this );
+        }
+    
+    iEmergencyCallApi->DialEmergencyCallL( 
+        iSetUpCallData.iAddress.iTelNumber );
+    LOG( SIMPLE, "SETUPCALL: CSetUpCallHandler::CreateEmergencyCallL exiting" )    
+    }
+
+// End Of File