diff -r 000000000000 -r 63b37f68c1ce adaptationlayer/tsy/nokiatsy_dll/src/cmmcustommesshandler.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/adaptationlayer/tsy/nokiatsy_dll/src/cmmcustommesshandler.cpp Fri Nov 06 17:28:23 2009 +0000 @@ -0,0 +1,8365 @@ +/* +* Copyright (c) 2007-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 FILES + +#include "cmmcustommesshandler.h" +#include "cmmsecuritymesshandler.h" +#include "cmmstaticutility.h" +#include "cmmnetmesshandler.h" +#include "cmmnetoperatornamehandler.h" +#include "cmmcallmesshandler.h" +#include "cmmphonetsender.h" +#include "cmmmessagerouter.h" +#include "tsylogger.h" + +#include +#include +#include +#include + +#ifdef INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING +// Removed for Bridge camp! +#include +#endif + +#include +#include +#include +#include +// #include To be done in CPS +#include + +#include +#include +#include + +#include +#include + +#include "osttracedefinitions.h" +#ifdef OST_TRACE_COMPILER_IN_USE +#include "cmmcustommesshandlertraces.h" +#endif + +// EXTERNAL DATA STRUCTURES + //None + +// EXTERNAL FUNCTION PROTOTYPES + //None + +// CONSTANTS +// hard-coded transaction id for ISI messages +const TUint8 KCustomTransId = 6; +// const TUint8 KCustomWimTransId = 7; + +// Max length for HSXPA message request +const TUint KHSxPAMaxMessageSize = 2; + +// Uicc Card Status Byte (hardcoded). Values are derived from APDU server +// interface documentation. Bitfield READER_STATUS_BYTE +const TUint8 KUiccCardStatusCardNotPresentOrPoweredOff = 0x10; //0001 0000 +const TUint8 KUiccCardStatusCardPresentAndPoweredOn = 0xD0; //1101 0000 (0001 0000|0x40|0x80) + +// Consts needed when constructing APDU's going to be sent to the UICC +const TUint8 KEvenInstructionCode = 0x88; +const TUint8 KOddInstructionCode = 0x89; + +const TUint8 KFirstBlockOfAuthenticationData = 0x80; +const TUint8 KFirstBlockOfAuthenticationResponseData = 0xA0; + +const TUint8 KGsmAuthenticationContext = 0x80; // 1000 0000 +const TUint8 K3GAuthenticationContext = 0x81; // 1000 0001 +const TUint8 KGBAAuthenticationContext = 0x84; // 1000 0100 +const TUint8 KMBMSAuthenticationContext = 0x85; // 1000 0101 + +const TUint8 KMaximumLenOfDataExpected = 0x00; +const TUint8 KRunGsmAlgorithmRespLen = 0x0C; +const TUint8 KClaNoSm = 0x00; +const TUint8 KClaIcc = 0xA0; + +const TUint8 KSw1Position = 0x02; +const TUint8 KSw2Position = 0x01; + +const TUint8 KNormalCommandEnding = 0x00; +const TUint8 KAppAuthErrorIncorrectMac = 0x01; +const TUint8 KCmdNotAllowedConditionsNotSatisfied = 0x02; +const TUint8 KWarningAuthRespAvailable = 0x03; +const TUint8 KWarningMoreDataAvailable = 0x04; +const TUint8 KAppErrorAuthMbmsKeyFresh = 0x05; +const TUint8 KAppErrorAuthMbmsOutOfMemMsk = 0x06; +const TUint8 KAppErrorAuthMbmsOutOfMemMuk = 0x07; +const TUint8 KWrongParametersDataNotFound = 0x08; +const TUint8 KCmdNotAllowedSecurityStatusNotSatisfied = 0x09; +const TUint8 KUnknownCommandEnding = 0xFF; + +const TUint8 KApduOk = 0x00; +const TUint8 KApduNok = 0x01; + +const TUint8 KMinLenOfRes = 0x04; +const TUint8 KMaxLenOfRes = 0x10; +const TUint8 KLenOfSRes = 0x04; +const TUint8 KLenOfIk = 0x10; +const TUint8 KLenOfCk = 0x10; +const TUint8 KLenOfKc = 0x08; +const TUint8 KLenOfAuts = 0x0E; +const TUint8 KMaxMbmsMikeyLen = 0xFB; +const TUint8 KMaxMbmsSaltLen = 0xFB; +const TUint8 KMaxApduSize = 0xFF; +const TUint8 KMaxParentalRatingDataSize = 0x02; +const TUint8 KMaxSpeSize = 0x01; + +const TUint8 KSuccessfull3GAuthTag = 0xDB; +const TUint8 KSyncFailureTag = 0xDC; +const TUint8 KGBABootstappingModeTag = 0xDD; +const TUint8 KGBANAFDerivationModeTag = 0xDE; +const TUint8 KMBMSDataObjectTag = 0x53; + +const TUint8 KMskUpdateMode = 0x01; +const TUint8 KMtkGenerationMode = 0x02; +const TUint8 KMskDeletionMode = 0x03; +const TUint8 KSuccessfullMbmsOperationTag = 0xDB; +const TUint8 KMbmsOperationResponseTag53 = 0x53; +const TUint8 KMbmsOperationResponseTag73 = 0x73; +const TUint8 KOMABcastOperationResponseTag = 0xAE; +const TUint8 KBcastManagementDataTag = 0x80; +const TUint8 KParentalRatingDataTag = 0x8A; +const TUint8 KSPETypeNotSupportedTag = 0x8B; +const TUint8 KMikeyMessageTag = 0x8C; +const TUint8 KTekDataTag = 0x86; +const TUint8 KSaltDataTag = 0x87; +const TUint8 KParentalControlTag = 0x88; + +const TUint8 KServiceGBA = 0x44; // service no 68 +const TUint8 KServiceMBMSsecurity = 0x45; // service no 69 + + +// MACROS + //None + +// LOCAL CONSTANTS AND MACROS + //None + +// MODULE DATA STRUCTURES + //None + +// LOCAL FUNCTION PROTOTYPES + //None + +// ============================= LOCAL FUNCTIONS =============================== + //None + +// ============================ MEMBER FUNCTIONS =============================== + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::CMmCustomMessHandler +// C++ default constructor +// ----------------------------------------------------------------------------- +// +CMmCustomMessHandler::CMmCustomMessHandler() + { +TFLOGSTRING("TSY: CMmCustomMessHandler::CMmCustomMessHandler.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_CMMCUSTOMMESSHANDLER, "CMmCustomMessHandler::CMmCustomMessHandler" ); + iSimCBTopicToBeDeleted = KUnusedCbMsgId; + // Set to true because it doesn't delete topic at start up + iTopicInSimMemoryDelete = ETrue; + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::~CMmCustomMessHandler +// Destructor, deletes all allocated resources. +// ----------------------------------------------------------------------------- +// +CMmCustomMessHandler::~CMmCustomMessHandler() + { +TFLOGSTRING("TSY: CMmCustomMessHandler::~CMmCustomMessHandler.\n" ); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_CMMCUSTOMMESSHANDLER, "CMmCustomMessHandler::~CMmCustomMessHandler" ); + + if( iListOfCiphValues ) + { + //close the array of ciphering values + iListOfCiphValues->Close(); + //delete the list of ciphering values + delete iListOfCiphValues; + } + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::NewL +// Two-phased constructor. +// ----------------------------------------------------------------------------- +// +CMmCustomMessHandler* CMmCustomMessHandler::NewL + ( + CMmPhoNetSender* aPhoNetSender, // pointer to the phonet sender + CMmPhoNetReceiver* aPhoNetReceiver, // pointer to the phonet sender + CMmNetMessHandler* aNetMessHandler, // pointer to the Net messHandler + CMmSecurityMessHandler* aSecurityMessHandler, // pointer to the security + CMmMessageRouter* aMessageRouter, //pointer to the message router + CMmUiccMessHandler* aUiccMessHandler + ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::NewL.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_NEWL, "CMmCustomMessHandler::NewL" ); + + CMmCustomMessHandler* customMessHandler = + new( ELeave ) CMmCustomMessHandler(); + + CleanupStack::PushL( customMessHandler ); + customMessHandler->iPhoNetSender = aPhoNetSender; + customMessHandler->iNetMessHandler = aNetMessHandler; + customMessHandler->iSecurityMessHandler = aSecurityMessHandler; + customMessHandler->iMessageRouter = aMessageRouter; + customMessHandler->iMmUiccMessHandler = aUiccMessHandler; + + customMessHandler->ConstructL(); + + // CALL + aPhoNetReceiver->RegisterL( + customMessHandler, + PN_MODEM_CALL ); + + // NETWORK + aPhoNetReceiver->RegisterL( + customMessHandler, + PN_MODEM_NETWORK ); + +#ifdef INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING + +// TO BE DONE WITH INFO_PP_DATA_READ_RESP + aPhoNetReceiver->RegisterL( + customMessHandler, + PN_INFO, + INFO_PP_READ_RESP ); +#endif /* INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING */ + // SS + aPhoNetReceiver->RegisterL( + customMessHandler, + PN_SS, + SS_SERVICE_COMPLETED_IND ); + aPhoNetReceiver->RegisterL( + customMessHandler, + PN_SS, + SS_SERVICE_FAILED_RESP ); + aPhoNetReceiver->RegisterL( + customMessHandler, + PN_SS, + SS_GSM_USSD_SEND_RESP ); + + // GSS + aPhoNetReceiver->RegisterL( + customMessHandler, + PN_GSS, + GSS_CS_SERVICE_RESP ); + aPhoNetReceiver->RegisterL( + customMessHandler, + PN_GSS, + GSS_CS_SERVICE_FAIL_RESP ); + aPhoNetReceiver->RegisterL( + customMessHandler, + PN_GSS, + GSS_HSXPA_USER_SETTING_READ_RESP ); + aPhoNetReceiver->RegisterL( + customMessHandler, + PN_GSS, + GSS_HSXPA_USER_SETTING_WRITE_RESP ); + aPhoNetReceiver->RegisterL( + customMessHandler, + PN_GSS, + GSS_HSXPA_USER_SETTING_IND ); + +#ifdef INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING + // MTC + // Removed for Bridge camp + aPhoNetReceiver->RegisterL( + customMessHandler, + PN_MTC, + MTC_RAT_QUERY_RESP ); +#endif + + // PMM + /* To be done in CPS + aPhoNetReceiver->RegisterL( customMessHandler, + PN_PERMANENT_DATA, + PERM_PM_RECORD_READ_RESP ); + + aPhoNetReceiver->RegisterL( customMessHandler, + PN_PERMANENT_DATA, + PERM_PM_RECORD_WRITE_RESP );*/ + + // UICC + aPhoNetReceiver->RegisterL( + customMessHandler, + PN_UICC, + UICC_CARD_IND); + + CleanupStack::Pop( customMessHandler ); + + // Send PERM_PM_RECORD_READ_REQ and update + // iCallLifeTimer. + customMessHandler->ReadLifeTimerFromPermanentMemory ( KCustomTransId ); + + return customMessHandler; + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::ConstructL +// Symbian 2nd phase constructor can leave. +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::ConstructL() + { +TFLOGSTRING("TSY: CMmCustomMessHandler::ConstructL.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_CONSTRUCTL, "CMmCustomMessHandler::ConstructL" ); + + // Initialize iListOfCiphValues + iListOfCiphValues = new ( ELeave ) RArray( 1 ); + + // Initialize refresh indication boolean + iIsRefresh = EFalse; + + // Initialize ECID boolean + iECIDInfoRequested = EFalse; + + // Initialize ECID information + iECIDInfo.iMCC = 0; // Mobile Country Code + iECIDInfo.iMNC = 0; // Mobile Network Code + iECIDInfo.iCID = 0; // Cell identity + iECIDInfo.iLAC = 0; // Location area code + + // Initialize Call Life Timer value. + iCallLifeTimer = KCallLifeTimerNotSet; + + // initialize ISim application activation status + iIsimApplActivated = EFalse; + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::ReceiveMessageL +// Entry point for messages received from Domestic OS. Switches the message +// to the correct method. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::ReceiveMessageL + ( + const TIsiReceiveC& aIsiMessage // ISI-message received + ) + { + TInt resource( aIsiMessage.Get8bit( ISI_HEADER_OFFSET_RESOURCEID ) ); + TInt messageId( aIsiMessage.Get8bit( ISI_HEADER_OFFSET_MESSAGEID ) ); + +TFLOGSTRING3("TSY: CMmCustomMessHandler::ReceiveMessageL, Resource: %d, Message: %d", resource, messageId); +OstTraceExt2( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_RECEIVEMESSAGEL, "CMmCustomMessHandler::ReceiveMessageL;resource=%d;messageId=%d", resource, messageId ); + + switch( resource ) + { + case PN_MODEM_CALL: + { + // switch according to the message id + // and call the appropriate messagehandler method + switch( messageId ) + { + case CALL_MODEM_RELEASE_RESP: + { + CallReleaseResp( aIsiMessage ); + break; + } + case CALL_MODEM_NOTIFICATION_IND: + { + CallGsmNotificationInd( aIsiMessage ); + break; + } + case CALL_MODEM_MO_ALERT_IND: + { + CallMoAlertInd( aIsiMessage ); + break; + } + case CALL_MODEM_TERMINATED_IND: + { + CallTerminateInd( aIsiMessage ); + break; + } + case CALL_MODEM_RELEASE_IND: + { + CallReleaseInd( aIsiMessage ); + break; + } + case CALL_MODEM_BLACKLIST_CLEAR_RESP: + { + CallGsmBlackListClearResp(); + break; + } + case CALL_MODEM_EMERG_NBR_CHECK_RESP: + { + CallEmergencyNbrCheckResp( aIsiMessage ); + break; + } + default: + { +TFLOGSTRING("TSY: CMmCustomMessHandler::ReceiveMessageL - switch resource - case PN_MODEM_CALL, switch messageId - default"); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_RECEIVEMESSAGEL, "CMmCustomMessHandler::ReceiveMessageL- switch resource - case PN_CALL, switch messageId - default" ); + break; + } + } + break; + } + case PN_GSS: + { + // switch according to the message id + // and call the appropriate messagehandler method + switch( messageId ) + { + case GSS_CS_SERVICE_RESP: + { + GssCsServiceResp( aIsiMessage ); + break; + } + case GSS_CS_SERVICE_FAIL_RESP: + { + GssCsServiceFailResp( aIsiMessage ); + break; + } + case GSS_HSXPA_USER_SETTING_READ_RESP: + { + ReadHSxPAStatusResp( aIsiMessage ); + break; + } + case GSS_HSXPA_USER_SETTING_WRITE_RESP: + { + WriteHSxPAStatusResp( aIsiMessage ); + break; + } + case GSS_HSXPA_USER_SETTING_IND: + { + HSxPASettingInd( aIsiMessage ); + break; + } + default: + { +TFLOGSTRING("TSY: CMmCustomMessHandler::ReceiveMessageL - switch resource - case PN_GSS, switch messageId - default"); +OstTrace0( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_RECEIVEMESSAGEL, "CMmCustomMessHandler::ReceiveMessageL- switch resource - case PN_GSS, switch messageId - default" ); + break; + } + } + break; // end case PN_GSS + } + case PN_MODEM_NETWORK: + { + // switch according to the message id + // and call the appropriate messagehandler method + switch( messageId ) + { + case NET_CS_WAKEUP_RESP: + { + NetCsWakeupResp(); + break; + } + case NET_MODEM_REG_STATUS_IND: + { + NetModemRegStatusInd( aIsiMessage ); + break; + } + case NET_CIPHERING_IND: + { + NetCipheringInd( aIsiMessage ); + break; + } + case NET_MODEM_REG_STATUS_GET_RESP: + { + NetModemRegStatusGetResp( aIsiMessage ); + break; + } + case NET_SET_RESP: + { + NetSetResp( aIsiMessage ); + break; + } + case NET_RAT_RESP: + { + NetRatResp( aIsiMessage ); + break; + } + case NET_NEIGHBOUR_CELLS_RESP: + { + NetNeighbourCellsResp( aIsiMessage ); + break; + } + default: + { +TFLOGSTRING("TSY: CMmCustomMessHandler::ReceiveMessageL - switch resource - case PN_MODEM_NETWORK, switch messageId - default"); +OstTrace0( TRACE_NORMAL, DUP4_CMMCUSTOMMESSHANDLER_RECEIVEMESSAGEL, "CMmCustomMessHandler::ReceiveMessageL- switch resource - case PN_MODEM_NETWORK, switch messageId - default" ); + break; + } + } + break; + } +#ifdef INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING + // Removed for Bridge camp + case PN_MTC: + { + switch( messageId ) + { + case MTC_RAT_QUERY_RESP: + { + MtcRatQueryResp( aIsiMessage ); + break; + } + default: + { +TFLOGSTRING("TSY: CMmCustomMessHandler::ReceiveMessageL - switch resource - case PN_MTC, switch messageId - default"); +OstTrace0( TRACE_NORMAL, DUP5_CMMCUSTOMMESSHANDLER_RECEIVEMESSAGEL, "CMmCustomMessHandler::ReceiveMessageL- switch resource - case PN_MTC, switch messageId - default" ); + break; + } + } + break; + } +#endif /* INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING */ + +#ifdef INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING + case PN_INFO: +#else /* INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING */ + case PN_MODEM_INFO: +#endif /* INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING */ + { + // switch according to the message id + // and call the appropriate messagehandler method + switch( messageId ) + { +#ifdef INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING + // TO BE DONE WITH INFO_PP_DATA_READ_RESP + case INFO_PP_READ_RESP: + { + InfoPpReadResp( aIsiMessage ); + break; + } +#endif /* INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING */ + default: + { +TFLOGSTRING("TSY: CMmCustomMessHandler::ReceiveMessageL - switch resource - case PN_INFO, switch messageId - default"); +OstTrace0( TRACE_NORMAL, DUP6_CMMCUSTOMMESSHANDLER_RECEIVEMESSAGEL, "CMmCustomMessHandler::ReceiveMessageL- switch resource - case PN_INFO, switch messageId - default" ); + break; + } + } + break; + } + case PN_SS: + { + switch( messageId ) + { + case SS_SERVICE_COMPLETED_IND: + { + SsServiceCompletedInd( aIsiMessage ); + break; + } + case SS_SERVICE_FAILED_RESP: + { + SsServiceFailedResp( aIsiMessage ); + break; + } + case SS_GSM_USSD_SEND_RESP: + { + SsGsmUssdSendResp( aIsiMessage ); + break; + } + default: + { +TFLOGSTRING("TSY: CMmCustomMessHandler::ReceiveMessageL - switch resource - case PN_SS, switch messageId - default"); +OstTrace0( TRACE_NORMAL, DUP12_CMMCUSTOMMESSHANDLER_RECEIVEMESSAGEL, "CMmCustomMessHandler::ReceiveMessageL- switch resource - case PN_SS, switch messageId - default" ); + break; + } + } + break; + } + /* To be done in CPS + case PN_PERMANENT_DATA: + { + if ( KCustomTransId == aIsiMessage.Get8bit( ISI_HEADER_OFFSET_TRANSID ) ) + { + switch( messageId ) + { + case PERM_PM_RECORD_READ_RESP: + { + LifeTimerFromPermanentMemoryReadResponse( aIsiMessage ); + break; + } + + case PERM_PM_RECORD_WRITE_RESP: + { + LifeTimerToPermanentMemoryWriteResponse( aIsiMessage ); + break; + } + + default: + { + TFLOGSTRING("TSY: CMmCustomMessHandler::ReceiveMessageL\ + - switch resource - case PN_PERMANENT_DATA, switch messageId - default.\n"); +OstTrace0( TRACE_NORMAL, DUP16_CMMCUSTOMMESSHANDLER_RECEIVEMESSAGEL, "CMmCustomMessHandler::ReceiveMessageL - switch resource - case PN_PERMANENT_DATA, switch messageId - default." ); + break; + } + } + TFLOGSTRING("TSY: CMmCustomMessHandler::ReceiveMessageL\ + - switch resource - case PN_PERMANENT_DATA, transaction id is not KCustomTransId\n"); +OstTrace0( TRACE_NORMAL, DUP14_CMMCUSTOMMESSHANDLER_RECEIVEMESSAGEL, "CMmCustomMessHandler::ReceiveMessageL - switch resource - case PN_PERMANENT_DATA, transaction id is not KCustomTransId" ); + } + break; + }*/ + + case PN_UICC: + { + if( UICC_CARD_IND == messageId ) + { + UiccCardInd( aIsiMessage ); + } + break; + } + default: + { +TFLOGSTRING("TSY: CMmCustomMessHandler::ReceiveMessageL - switch resource - default" ); +OstTrace0( TRACE_NORMAL, DUP13_CMMCUSTOMMESSHANDLER_RECEIVEMESSAGEL, "CMmCustomMessHandler::ReceiveMessageL- switch resource - default" ); + break; // server not known + } + } // end of switch + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::CallReleaseReq +// Constructs CALL_MODEM_RELEASE_REQ ISI message from input parameters and sends +// it through phonet. HangUp request message. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::CallReleaseReq + ( + TUint8 aTransactionId, //transaction id + TUint8 aCallId, //call id + TUint8 aCause //cause value for releasing the call + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallReleaseReq.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_CALLRELEASEREQ, "CMmCustomMessHandler::CallReleaseReq" ); + + iReleaseCauseValueSent = aCause; + + //Append data for ISI message + TBuf8< 2 + SIZE_CALL_MODEM_SB_CAUSE > messageBuf; + + messageBuf.Append( aCallId ); + messageBuf.Append( 1 ); // Num of Subblocks + + //Call_Release_Req sub block + messageBuf.Append( CALL_MODEM_SB_CAUSE ); + messageBuf.Append( SIZE_CALL_MODEM_SB_CAUSE ); + messageBuf.Append( CALL_MODEM_CAUSE_TYPE_CLIENT ); + messageBuf.Append( aCause ); + + //send message via phonet + return iPhoNetSender->Send( PN_MODEM_CALL, aTransactionId, CALL_MODEM_RELEASE_REQ, + messageBuf ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::CallReleaseResp +// Breaks response to the HangUp request. In case of failure, HangUp is +// completed to the Symbian OS layer. Otherwise HangUp handle the success case. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::CallReleaseResp + ( + const TIsiReceiveC& aIsiMsg //received ISI message + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallReleaseResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_CALLRELEASERESP, "CMmCustomMessHandler::CallReleaseResp" ); + + //initialize the causeType and causeValue + TUint8 causeType = 0; + TUint8 causeValue = 0; + TInt ret = KErrNone; + + TUint sbStartOffSet( 0 ); + + //get cause sub block + //if subblock is present + if( KErrNone == aIsiMsg.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_CALL_MODEM_RELEASE_RESP, CALL_MODEM_SB_CAUSE, + EIsiSubBlockTypeId8Len8, sbStartOffSet ) ) + { + //get cause type + causeType = aIsiMsg.Get8bit( sbStartOffSet + + CALL_MODEM_SB_CAUSE_OFFSET_CAUSETYPE ); + + //get cause value + causeValue = aIsiMsg.Get8bit( sbStartOffSet + + CALL_MODEM_SB_CAUSE_OFFSET_CAUSE ); + + if( iReleaseCauseValueSent != causeValue ) + { + //map error value to ETEL error value + ret = CMmStaticUtility::CSCauseToEpocError ( PN_MODEM_CALL, + causeType, causeValue ); + } + } + // no packed parameters for completion + iMessageRouter->Complete( ECustomTerminateCallIPC, ret ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::CallMoAlertInd +// This method breaks the CallMo alerting indication message. +// Trying to find Remote alerting information. In success case +// send LocalRemoteAlertToneRequired value to SOS layer. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::CallMoAlertInd + ( + const TIsiReceiveC& aIsiMsg //received ISI message + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallMoAlertInd."); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_CALLMOALERTIND, "CMmCustomMessHandler::CallMoAlertInd" ); + + TBool playRemoteAlertToneLocally( EFalse ); + TUint sbStartOffSet( 0 ); + + // Get call alerting info sub block + // if subblock was found + if( KErrNone == aIsiMsg.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_CALL_MODEM_MO_ALERT_IND, + CALL_MODEM_SB_ALERTING_INFO, + EIsiSubBlockTypeId8Len8, + sbStartOffSet ) ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallMoAlertInd,\ + - CALL_MODEM_SB_ALERTING_INFO sub block found."); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_CALLMOALERTIND, "CMmCustomMessHandler::CallMoAlertInd, CALL_MODEM_SB_ALERTING_INFO sub block found" ); + + // Get alerting info + TUint8 callAlertingInfo( aIsiMsg.Get8bit( + sbStartOffSet + CALL_MODEM_SB_ALERTING_INFO_OFFSET_ALERTINGINFO ) ); + + // If LSB is "1" inform that remote alerting tone + // should be generated locally. + if ( callAlertingInfo & 0x01 ) + { + playRemoteAlertToneLocally = ETrue; + } + } + + // Complete remote alerting tone notification + // parameter for SOS layer: a TBool playRemoteAlertToneLocally + CMmDataPackage dataPackage; + dataPackage.PackData( &playRemoteAlertToneLocally ); + iMessageRouter->Complete( ECustomGetRemoteAlertingToneStatusIPC, + &dataPackage, + KErrNone ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccReadCiReq +// Read ciphering indicator status from UICC +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccReadCiReq( TInt aTrId ) + { +TFLOGSTRING2("TSY: CMmCustomMessHandler::UiccReadCiReq, transaction ID: %d", aTrId ); +OstTrace1( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCREADCIREQ, "CMmCustomMessHandler::UiccReadCiReq;aTrId=%d", aTrId ); + + // Set parameters for UICC_APPL_CMD_REQ message + TUiccReadTransparent params; + params.messHandlerPtr = static_cast( this ); + params.trId = static_cast( aTrId ); + // We need to know the CI status info which is located in byte 3 in EF AD + // b1=0: ciphering indicator feature disabled + // b1=1: ciphering indicator feature enabled + params.dataAmount = 1; + params.dataOffset = 2; + params.fileId = KElemFileAdministrativeData; + params.fileIdSfi = 3; + params.serviceType = UICC_APPL_READ_TRANSPARENT; + + // File id path + params.filePath.Append( KMasterFileId >> 8 ); + params.filePath.Append( KMasterFileId ); + params.filePath.Append( iMmUiccMessHandler->GetApplicationFileId() ); + + return iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccReadCiResp +// Complete ciphering indicator status +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccReadCiResp( + TInt aStatus, + TInt aTrId, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccReadCiResp" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCREADCIRESP, "CMmCustomMessHandler::UiccReadCiResp" ); + + TInt ret( KErrNone ); + TBool cipherIndicatorStatus( EFalse ); + + if( UICC_STATUS_OK == aStatus ) + { + // Get ciphering indicator info ( bit 0) + TUint8 cipheringIndicator(aFileData[0] & 0x01 ); + if ( cipheringIndicator ) + { + cipherIndicatorStatus = ETrue; + } + } + else + { + ret = KErrNotFound; + } + + if ( ETrIdReadCipheringIndicatorStatusCustom == aTrId ) + { + // Complete GetCipheringInfo + // packed parameter: TBool (ciphering indicator required/not required) + CMmDataPackage dataPackage; + dataPackage.PackData( &cipherIndicatorStatus ); + iMessageRouter->Complete( + ECustomGetCipheringInfoIPC, + &dataPackage, + ret ); + } + else if( ETrIdNotifyCipheringIndicatorStatusCustom == aTrId ) + { + CMmDataPackage dataPackage; + TCiphListEntry chiplistentry; + chiplistentry.iTraId = aTrId; + + // Find the right value of ciphering for this resp message + TInt index ( iListOfCiphValues->Find( chiplistentry, Match ) ); + + // If the right value is found + if ( KErrNotFound != index ) + { + TBool cipheringOn( ( *iListOfCiphValues )[index ].iCiphStatus ); + dataPackage.PackData( &cipherIndicatorStatus, &cipheringOn ); + + // Delete the used ciphering value from the list + iListOfCiphValues->Remove( index ); + // Compress the list + iListOfCiphValues->Compress(); + } + else + { + TBool constantFalse( EFalse ); + dataPackage.PackData( &constantFalse, &constantFalse ); + ret = KErrGeneral; + } + + iMessageRouter->Complete( + ECustomNotifyCipheringInfoChangeIPC, + &dataPackage, + ret ); + } + //No else + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::NetCsWakeupReq +// Constructs NET_CS_WAKEUP_REQ ISI message from input parameters and sends +// it through phonet. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::NetCsWakeupReq( TUint8 aTransId ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::NetCsWakeupReq.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_NETCSWAKEUPREQ, "CMmCustomMessHandler::NetCsWakeupReq" ); + + //Data buffer length is 2 + TBuf8<2> data; + data.Append( aTransId ); + data.Append( NET_CS_WAKEUP_REQ ); + + TIsiSend isimsg( iPhoNetSender->SendBufferDes() ); + isimsg.Set8bit( ISI_HEADER_OFFSET_RESOURCEID, PN_MODEM_NETWORK ); + isimsg.CopyData( ISI_HEADER_SIZE, data ); + + return( iPhoNetSender->Send( isimsg.Complete() ) ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::NetCsWakeupResp +// Breaks a NET_CS_WAKEUP_RESP ISI message and complete NetWakeup with +// KErrNone to SOS layer +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::NetCsWakeupResp() + { + TFLOGSTRING("TSY: CMmCustomMessHandler::NetCsWakeupResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_NETCSWAKEUPRESP, "CMmCustomMessHandler::NetCsWakeupResp" ); + + //getting this message indicates that the wakeup was successful + //complete NetWakeup method (no packed parameters) + iMessageRouter->Complete( ECustomNetWakeupIPC, KErrNone ); + + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::NetCipheringInd +// This method breaks the ciphering indication message. +// This indication saves the ciphering status and calls SimReadCiReq to get the +// status of the ciphering indicator +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::NetCipheringInd( + const TIsiReceiveC &aIsiMsg ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::NetCipheringInd.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_NETCIPHERINGIND, "CMmCustomMessHandler::NetCipheringInd" ); + + //set chipering to False + TBool cipher( EFalse ); + + //get the ciphering status + TUint8 cipheringStatus( aIsiMsg.Get8bit( ISI_HEADER_SIZE + + NET_CIPHERING_IND_OFFSET_CIPHERINGSTATUS ) ); + + //check the value of the ciphering status + if ( NET_CIPHERING_INDICATOR_ON == cipheringStatus ) + { + cipher = ETrue; + } + + TUint8 traId( ETrIdNotifyCipheringIndicatorStatusCustom ); + + //save the ciphering information for later completion in the list. + //this method has to request the sim to complete, so new indication + //might come, values must be buffered. + TCiphListEntry chiplistentry; + chiplistentry.iTraId = traId; + chiplistentry.iCiphStatus = cipher; + iListOfCiphValues->Append( chiplistentry ); + + //get the ciphering indicator information from SIM card + //the response of this method will call the completion for the + //notification + UiccReadCiReq( ETrIdNotifyCipheringIndicatorStatusCustom ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::NetModemRegStatusInd +// This method breaks the NET_MODEM_REG_STATUS_IND message. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::NetModemRegStatusInd + ( + const TIsiReceiveC& aIsiMsg + ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::NetModemRegStatusInd"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_NETMODEMREGSTATUSIND, "CMmCustomMessHandler::NetModemRegStatusInd" ); + + if ( 0 != aIsiMsg.Get8bit( + ISI_HEADER_SIZE + + NET_MODEM_REG_STATUS_IND_OFFSET_SUBBLOCKCOUNT ) ) + { + TUint sbStartOffSet( 0 ); + + TInt retValue( aIsiMsg.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_NET_MODEM_REG_STATUS_IND, + NET_MODEM_REG_INFO_COMMON, + EIsiSubBlockTypeId8Len8, + sbStartOffSet ) ); + + // Check if NET_MODEM_REG_INFO_COMMON sub block is present. + if ( KErrNone == retValue ) + { + // Get registration status + TUint8 registrationStatus( aIsiMsg.Get8bit( + sbStartOffSet + + NET_MODEM_REG_INFO_COMMON_OFFSET_REGISTRATIONSTATUS ) ); + + TBool nspsIsOn( EFalse ); + + switch ( registrationStatus ) + { + case NET_REG_STATUS_NSPS: + case NET_REG_STATUS_NSPS_NO_COVERAGE: + { + nspsIsOn = ETrue; + break; + } + case NET_REG_STATUS_NOSERV_NOSIM: + case NET_REG_STATUS_NOSERV_SIM_REJECTED_BY_NW: + { +TFLOGSTRING("TSY: CMmCustomMessHandler::NetModemRegStatusInd, No SIM"); +OstTrace0( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_NETMODEMREGSTATUSIND, "CMmCustomMessHandler::NetModemRegStatusInd, No SIM" ); + // Complete NetworkConnectionFailure notification + // (no packed parameters). + // If puk code is required notification shouldn't + // be completed. + TBool pukCodeRequired( iSecurityMessHandler->GetPukCodeReq() ); + if( !pukCodeRequired ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::NetModemRegStatusInd - Complete network connection failure"); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_NETMODEMREGSTATUSIND, "CMmCustomMessHandler::NetModemRegStatusInd - Complete network connection failure" ); + + iMessageRouter->Complete( + ECustomNotifyNetworkConnectionFailureIPC, + KErrNone ); + } + break; + } + default: + { +TFLOGSTRING("TSY: CMmCustomMessHandler::NetModemRegStatusInd, switch registrationStatus - default"); +OstTrace0( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_NETMODEMREGSTATUSIND, "CMmCustomMessHandler::NetModemRegStatusInd, switch registrationStatus - default" ); + break; + } + } + + // Inform of the status of NSPS. + // Packed parameter: TBool nspsIsOn. + CMmDataPackage dataPackage; + dataPackage.PackData( &nspsIsOn ); + + iMessageRouter->Complete( + ECustomNotifyNSPSStatusIPC, + &dataPackage, + KErrNone ); + } + // No else + + // Check if ECID info needs to be updated. + CheckECIDInfo( aIsiMsg ); + } + // No else + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccReadDynamic2FlagsReq +// Read dynamic 2 flags from UICC +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccReadDynamic2FlagsReq() + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccReadDynamic2FlagsReq"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCREADDYNAMIC2FLAGSREQ, "CMmCustomMessHandler::UiccReadDynamic2FlagsReq" ); + // Set parameters for UICC_APPL_CMD_REQ message + TUiccWriteTransparent params; + params.messHandlerPtr = static_cast( this ); + params.trId = ETrIdReadDynamic2Flags; + params.dataOffset = 0; + params.dataAmount = 0; + params.fileId = KElemFileDyn2FlagsOrange; + params.fileIdSfi = UICC_SFI_NOT_PRESENT; + params.serviceType = UICC_APPL_READ_TRANSPARENT; + // File id path + params.filePath.Append( KMasterFileId >> 8 ); + params.filePath.Append( KMasterFileId ); + params.filePath.Append( KOrangeDedicatedFile >> 8 ); + params.filePath.Append( KOrangeDedicatedFile ); + return iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccReadDynamic2FlagsResp +// Complete dynamic 2 flags +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccReadDynamic2FlagsResp( + TInt aStatus, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccReadDynamic2FlagsResp"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCREADDYNAMIC2FLAGSRESP, "CMmCustomMessHandler::UiccReadDynamic2FlagsResp" ); + + TInt ret( KErrNone ); + RMmCustomAPI::TGetAlsBlockStatus blockStatus + ( RMmCustomAPI::EBlockStatusUnknown ); + + if ( UICC_STATUS_OK == aStatus ) + { + // The value of the block status is in the LSB byte + if ( aFileData[0] & 0x01 ) + { + blockStatus = RMmCustomAPI::EBlockStatusActive; + } + else + { + blockStatus = RMmCustomAPI::EBlockStatusInactive; + } + } + else + { + blockStatus = RMmCustomAPI::EBlockStatusNotSupported; + ret = KErrNotFound; + } + + // Complete, packed parameter: TGetAlsBlockStatus (block status) + CMmDataPackage dataPackage; + dataPackage.PackData( &blockStatus ); + iMessageRouter->Complete( + ECustomGetAlsBlockedIPC, + &dataPackage, + ret ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccWriteDynamic2FlagsReq +// Write dynamic 2 flags to UICC +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccWriteDynamic2FlagsReq( TUint8 aInfo ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccWriteDynamic2FlagsReq"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCWRITEDYNAMIC2FLAGSREQ, "CMmCustomMessHandler::UiccWriteDynamic2FlagsReq" ); + + // Set parameters for UICC_APPL_CMD_REQ message + TUiccWriteTransparent params; + params.messHandlerPtr = static_cast( this ); + params.trId = ETrIdWriteDynamic2Flags; + params.dataOffset = 0; + params.fileId = KElemFileDyn2FlagsOrange; + params.fileIdSfi = UICC_SFI_NOT_PRESENT; + params.serviceType = UICC_APPL_UPDATE_TRANSPARENT; + + // File id path + params.filePath.Append( KMasterFileId >> 8 ); + params.filePath.Append( KMasterFileId ); + params.filePath.Append( KOrangeDedicatedFile >> 8 ); + params.filePath.Append( KOrangeDedicatedFile ); + + params.fileData.Append( aInfo ); + return iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccWriteDynamic2FlagsResp +// Complete write dynamic flags request ro UICC +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccWriteDynamic2FlagsResp( TInt aStatus ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccWriteDynamic2FlagsReq"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCWRITEDYNAMIC2FLAGSRESP, "CMmCustomMessHandler::UiccWriteDynamic2FlagsResp" ); + + TInt ret( KErrNone ); + + if ( UICC_STATUS_OK != aStatus ) + { + ret = KErrGeneral; + } + + iMessageRouter->Complete( ECustomSetAlsBlockedIPC, ret ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::CallTerminateInd +// This method breaks the CALL_MODEM_TERMINATE_IND +// indication message. Gets CALL_MODEM_SB_SS_DIAGNOSTICS sub blocks and sets +// information into a call object. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::CallTerminateInd + ( + const TIsiReceiveC& aIsiMsg //received ISI message + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallTerminateInd.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_CALLTERMINATEIND, "CMmCustomMessHandler::CallTerminateInd" ); + + //unique call id (without possible generic id) + TInt callId = static_cast( aIsiMsg.Get8bit( ISI_HEADER_SIZE + + CALL_MODEM_TERMINATED_IND_OFFSET_CALLID ) & 0x07 ); + + if ( CALL_MODEM_ID_NONE != callId ) + { + TUint sbStartOffSet( 0 ); + + TUint8 ssDiagnostics = 0; + + //find sub block + if( KErrNone == aIsiMsg.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_CALL_MODEM_TERMINATED_IND, CALL_MODEM_SB_SS_DIAGNOSTICS, + EIsiSubBlockTypeId8Len8, sbStartOffSet ) ) + { + //get ss diagnostics + ssDiagnostics = aIsiMsg.Get8bit( sbStartOffSet + + CALL_MODEM_SB_SS_DIAGNOSTICS_OFFSET_DIAGNOSTICS ); + + // Set highest bit to 1 if there is some diagnostic information + // (This is in accordance with 3GPP TS 24.008 "Mobile radio + // interface Layer 3 specification; Core network protocols" and with + // Series 60 Supplementary Services UI Specification) + if ( 0 != ssDiagnostics ) + { + ssDiagnostics |= 0x80; // binary 10000000 + TFLOGSTRING3("TSY:CMmCustomMessHandler::CallTerminatedInd: Diagnostic octet=%d received for call id=%d", + ssDiagnostics, callId ); +OstTraceExt2( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_CALLTERMINATEIND, "CMmCustomMessHandler::CallTerminateInd;Diagnostic octet==%hhu received for call id=%d", ssDiagnostics, callId ); + } + } + + // set the diagnostics in call object (might be zero) + // parameters for SOS layer: Call id and TUint8 with diagnostics + CMmDataPackage dataPackage; + dataPackage.PackData( &callId, &ssDiagnostics ); + iMessageRouter->Complete( ECustomGetDiagnosticOctetsIPC, &dataPackage, + KErrNone ); + + } + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::CallReleaseInd +// This method breaks the CALL_MODEM_RELEASE_IND. +// indication message. Gets CALL_MODEM_SB_SS_DIAGNOSTICS sub blocks and sets +// information into a call object. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::CallReleaseInd + ( + const TIsiReceiveC& aIsiMsg //received ISI message + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallReleaseInd.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_CALLRELEASEIND, "CMmCustomMessHandler::CallReleaseInd" ); + + //unique call id (without possible generic id) + TInt callId = static_cast( aIsiMsg.Get8bit( ISI_HEADER_SIZE + + CALL_MODEM_RELEASE_IND_OFFSET_CALLID ) & 0x07 ); + + if ( CALL_MODEM_ID_NONE != callId ) + { + TUint sbStartOffSet( 0 ); + + TUint8 ssDiagnostics = 0; + + //get call operation sub block + if( KErrNone == aIsiMsg.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_CALL_MODEM_RELEASE_IND, CALL_MODEM_SB_SS_DIAGNOSTICS, + EIsiSubBlockTypeId8Len8, sbStartOffSet ) ) + { + //get ss diagnostics + ssDiagnostics = aIsiMsg.Get8bit( sbStartOffSet + + CALL_MODEM_SB_SS_DIAGNOSTICS_OFFSET_DIAGNOSTICS ); + + // Set highest bit to 1 if there is some diagnostic information + // (This is in accordance with 3GPP TS 24.008 "Mobile radio + // interface Layer 3 specification; Core network protocols" and with + // Series 60 Supplementary Services UI Specification) + if ( 0 != ssDiagnostics ) + { + ssDiagnostics |= 0x80; // binary 10000000 + TFLOGSTRING3("TSY:CMmCustomMessHandler::CallReleaseInd: Diagnostic octet=%d received for call id=%d", + ssDiagnostics, callId ); +OstTraceExt2( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_CALLRELEASEIND, "CMmCustomMessHandler::CallReleaseInd;Diagnostic octet==%hhu received for call id=%d", ssDiagnostics, callId ); + } + } + + // set the diagnostics in call object (might be zero) + // parameters for SOS layer: Call id and TUint8 with diagnostics + CMmDataPackage dataPackage; + dataPackage.PackData( &callId, &ssDiagnostics ); + iMessageRouter->Complete( ECustomGetDiagnosticOctetsIPC, &dataPackage, + KErrNone ); + + } + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::InfoPpReadReq +// Constructs INFO_PP_READ_REQ ISI message from input parameters and sends +// it through phonet. This message can be used to read ALS or Two Digit Dialling +// support status in the product profiles from INFO server. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::InfoPpReadReq + ( + TProductProfileRequestType aReqType // request type, used as + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::InfoPpReadReq.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_INFOPPREADREQ, "CMmCustomMessHandler::InfoPpReadReq" ); + +#ifdef INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING + //create the buffer for SB_PP subblock + TBuf8 sbPPSubBlockBuf( 0 ); + TIsiSubBlock sbPPSubBlock( sbPPSubBlockBuf, INFO_SB_PP, EIsiSubBlockTypeId8Len8 ); + //add 0x00 as the Dynamic Value ID, not needed cause we want to get + //a static value + sbPPSubBlockBuf.Append( 0x00 ); + + //add 0x01 as the length of the product profile, we want only als + //profile, thus lenght is 1 + sbPPSubBlockBuf.Append( 0x01 ); + + //add the product profile number + if ( EGetAlsPPSupport == aReqType ) + { + sbPPSubBlockBuf.Append( INFO_PP_ALS ); + } + else if ( ECheckTwoDigitDialSupport == aReqType ) + { + sbPPSubBlockBuf.Append( KinfoPpTwoDigitDial ); + } + else + { + // not supported + return KErrArgument; + } + + //value of the product profile is 0x00, not need cause we are reading + sbPPSubBlockBuf.Append( 0x00 ); + + // Construct INFO_PP_READ_REQ message (1 data byte + + // sub block count + INFO_SB_PP sub block) + TBuf8< 2 + SIZE_INFO_SB_PP > infoPpReadReq; + + //set pp batch reading to read specific product profile, thus 0. + infoPpReadReq.Append( INFO_PP_PROD_PROFILE_FEATURE ); + + // add sub block + infoPpReadReq.Append( 1 ); // number of sub blocks + infoPpReadReq.Append( sbPPSubBlock.CompleteSubBlock() ); + + //create the isi message + //transaction id = request type + TUint8 transId = static_cast( aReqType ); + + return iPhoNetSender->Send( PN_INFO, transId, INFO_PP_READ_REQ, infoPpReadReq ); + +#endif /* INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING */ + return KErrNone; + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::InfoPpReadResp +// Breaks a INFO_PP_READ_RESP ISI message. This method +// gets the status of the ALS or two digit support. +// Complete with packed parameter RMmCustomAPI::TAlsSupport or +// RMmCustomAPI::TTwoDigitDialSupport to SOS layer. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::InfoPpReadResp + ( + const TIsiReceiveC& aIsiMessage //received ISI message + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::InfoPpReadResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_INFOPPREADRESP, "CMmCustomMessHandler::InfoPpReadResp" ); +#ifdef INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING + TInt errorValue( KErrGeneral ); + + // Get Status + TUint8 status = aIsiMessage.Get8bit( ISI_HEADER_SIZE + INFO_PP_READ_RESP_OFFSET_STATUS ); + + //initialize the als support with off + RMmCustomAPI::TAlsSupport alsSupport( RMmCustomAPI::EAlsSupportOff ); + + //initialize two digit support with off + RMmCustomAPI::TTwoDigitDialSupport twoDigitDialSupport( + RMmCustomAPI::ETwoDigitDialSupportOff ); + + TFLOGSTRING2("TSY: CMmCustomMessHandler::InfoPpReadResp - Status: %d", + status ); +OstTraceExt1( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_INFOPPREADRESP, "CMmCustomMessHandler::InfoPpReadResp;status=%hhu", status ); + + switch ( status ) + { + case INFO_OK: + { + + TUint sbInfoPpReadStartOffset( 0 ); + + + if ( KErrNone == aIsiMessage.FindSubBlockOffsetById( ISI_HEADER_SIZE + SIZE_INFO_PP_READ_RESP, + INFO_SB_PP, EIsiSubBlockTypeId8Len8, sbInfoPpReadStartOffset ) ) + + { + + TInt length = aIsiMessage.Get8bit( sbInfoPpReadStartOffset + INFO_SB_PP_OFFSET_STRLEN ); + + TFLOGSTRING2("TSY: CMmCustomMessHandler::InfoPpReadResp - Info length: %d", + length ); +OstTrace1( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_INFOPPREADRESP, "CMmCustomMessHandler::InfoPpReadResp - Info length=%d", length ); + + if ( 1 == length ) + { + //introduce the pPFeatures buffer to hold the feature value, + //buffer size is 2 + TBuf8 pPFeatures; + + //copy the 2 bytes from product profile + pPFeatures.Copy( aIsiMessage.GetData( sbInfoPpReadStartOffset + + INFO_SB_PP_OFFSET_PRODUCTPROFILE, KTwo ) ); + + TFLOGSTRING2("TSY: CMmCustomMessHandler::InfoPpReadResp - Info data: %S", + &pPFeatures ); +OstTraceExt1( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_INFOPPREADRESP, "CMmCustomMessHandler::InfoPpReadResp;pPfeatures=%s", pPFeatures ); + + //check that product profile is requested one + if ( INFO_PP_ALS == pPFeatures [0] ) + { + //Get the value of the Als feature + if ( 0 != pPFeatures [1] ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::InfoPpReadResp - EAlsSupportOn"); +OstTrace0( TRACE_NORMAL, DUP4_CMMCUSTOMMESSHANDLER_INFOPPREADRESP, "CMmCustomMessHandler::InfoPpReadResp - EAlsSupportOn" ); + alsSupport = RMmCustomAPI::EAlsSupportOn; + } + //set the error value to KErrNone + errorValue = KErrNone; + } + else if ( KinfoPpTwoDigitDial == pPFeatures [0] ) + { + //Get the value of the two digit dial feature + if ( 0 != pPFeatures [1] ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::InfoPpReadResp - EAlsSupportOff"); +OstTrace0( TRACE_NORMAL, DUP5_CMMCUSTOMMESSHANDLER_INFOPPREADRESP, "CMmCustomMessHandler::InfoPpReadResp - EAlsSupportOff" ); + twoDigitDialSupport = + RMmCustomAPI::ETwoDigitDialSupportOn; + } + //set the error value to KErrNone + errorValue = KErrNone; + } + + //No else + + } + } + break; + } + case INFO_FAIL: + { + //error in operation + errorValue = KErrGeneral; + break; + } + case INFO_NO_NUMBER: + { + //information is not found + errorValue = KErrNotFound; + break; + } + default: + { + TFLOGSTRING("TSY: CMmCustomMessHandler::InfoPpReadResp, switch status - default.\n" ); +OstTrace0( TRACE_NORMAL, DUP6_CMMCUSTOMMESSHANDLER_INFOPPREADRESP, "CMmCustomMessHandler::InfoPpReadResp, switch status - default" ); + errorValue = KErrNotSupported; + break; + } + } + + TUint8 traId = aIsiMessage.Get8bit( ISI_HEADER_SIZE + INFO_PP_READ_RESP_OFFSET_TRANSID ); + if ( EGetAlsPPSupport == traId ) + { + // complete with packed parameter RMmCustomAPI::TAlsSupport + CMmDataPackage dataPackage; + dataPackage.PackData( &alsSupport ); + iMessageRouter->Complete( ECustomCheckAlsPpSupportIPC, + &dataPackage, errorValue ); + } + else if ( ECheckTwoDigitDialSupport == traId ) + { + // complete with packed parameter RMmCustomAPI::TTwoDigitDialSupport + CMmDataPackage dataPackage; + dataPackage.PackData( &twoDigitDialSupport ); + iMessageRouter->Complete( ECustomCheckTwoDigitDialSupportIPC, + &dataPackage, errorValue ); + } + + //No else +#endif /* INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING */ + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::CallGsmBlackListClearReq +// Constructs CALL_MODEM_BLACKLIST_CLEAR_REQ ISI message from input parameters and +// sends it through phonet. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::CallGsmBlackListClearReq + ( + TUint8 aTransId // Transaction Id + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallGsmBlackListClearReq.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_CALLGSMBLACKLISTCLEARREQ, "CMmCustomMessHandler::CallGsmBlackListClearReq" ); + + // Construct CALL_MODEM_BLACKLIST_CLEAR_REQ message (1 data byte + + // sub block count) + TBuf8<2> blackListClearReq; + + blackListClearReq.Append( KCustomPadding ); + blackListClearReq.Append( 0x00 ); // sub block count + + //Send message via PhoNet + return iPhoNetSender->Send( PN_MODEM_CALL, aTransId, CALL_MODEM_BLACKLIST_CLEAR_REQ, + blackListClearReq ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::CallGsmBlackListClearResp +// Breaks a CALL_MODEM_BLACKLIST_CLEAR_RESP ISI message. This method +// gets indicates that the clear blacklist was successful. +// Complete CallGsmBlackListClear with KErrNone to SOS layer. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::CallGsmBlackListClearResp + ( +// const TIsiReceiveC& aIsiMsg // Received isi messge + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallGsmBlackListClearResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_CALLGSMBLACKLISTCLEARRESP, "CMmCustomMessHandler::CallGsmBlackListClearResp" ); + + // call server response + //getting this message indicates that the clear blacklist was successful + //complete SOS layer method + iMessageRouter->Complete( ECustomClearCallBlackListIPC, KErrNone ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::SsServiceCompletedInd +// This method breaks the SS_SERVICE_COMPLETED_IND ISI message. +// Complete SsRequestCompleteNotification method from custom api or +// Complete NotifySsAdditionalInfo to SOS layer. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::SsServiceCompletedInd + ( + const TIsiReceiveC& aIsiMessage //received ISI message + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::SsServiceCompletedInd"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_SSSERVICECOMPLETEDIND, "CMmCustomMessHandler::SsServiceCompletedInd" ); + + if ( 0 < aIsiMessage.Get8bit( ISI_HEADER_SIZE + + SS_SERVICE_COMPLETED_IND_OFFSET_SUBBLOCKCOUNT ) ) + { + TUint ssStatus( 0 ); + TUint8 sbSsStatus( 0 ); + TUint sbForwardingFeatureOffset( 0 ); + TUint sbBarringFeatureOffset( 0 ); + + TUint sbStartOffset(0); + // SS_STATUS_RESULT sub block + if ( KErrNone == aIsiMessage.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_SS_SERVICE_COMPLETED_IND, + SS_STATUS_RESULT, + EIsiSubBlockTypeId8Len8, + sbStartOffset ) ) + { + sbSsStatus = aIsiMessage.Get8bit( sbStartOffset + + SS_STATUS_RESULT_OFFSET_SSSTATUS ); + } + + // SS_GSM_FORWARDING_INFO sub block + if ( KErrNone == aIsiMessage.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_SS_SERVICE_COMPLETED_IND, + SS_GSM_FORWARDING_INFO, + EIsiSubBlockTypeId8Len8, + sbStartOffset ) ) + { + // Sub block's sub block SS_GSM_FORWARDING_FEATURE: + if ( KErrNone == aIsiMessage.FindSubBlockOffsetById( + sbStartOffset + SIZE_SS_GSM_FORWARDING_INFO, + SS_GSM_FORWARDING_FEATURE, + EIsiSubBlockTypeId8Len8, + sbForwardingFeatureOffset + ) ) + { + sbSsStatus = aIsiMessage.Get8bit( sbForwardingFeatureOffset + + SS_GSM_FORWARDING_FEATURE_OFFSET_SSSTATUS ); + } + //Cases which don't return the other sub block should still be ok. + else + { + // This simulates successfull SS case, where the info subblock + // is received, but the forwarding feature isn't(the real status + // cannot be read). + sbSsStatus = SS_GSM_ACTIVE; + } + } + + // SS_GSM_BARRING_INFO sub block + if ( 0 == sbSsStatus && KErrNone == aIsiMessage.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_SS_SERVICE_COMPLETED_IND, + SS_GSM_BARRING_INFO, + EIsiSubBlockTypeId8Len8, + sbStartOffset + ) ) + { + // Sub block's sub block SS_GSM_BARRING_FEATURE + if ( KErrNone == aIsiMessage.FindSubBlockOffsetById( + sbStartOffset + SIZE_SS_GSM_BARRING_FEATURE, + SS_GSM_BARRING_FEATURE, + EIsiSubBlockTypeId8Len8, + sbBarringFeatureOffset + ) ) + { + + sbSsStatus = aIsiMessage.Get8bit( sbBarringFeatureOffset + + SS_GSM_BARRING_FEATURE_OFFSET_SSSTATUS ); + } + } + + + // SS_GSM_GENERIC_SERVICE_INFO sub block + if ( 0 == sbSsStatus && KErrNone == aIsiMessage.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_SS_SERVICE_COMPLETED_IND, + SS_GSM_GENERIC_SERVICE_INFO, + EIsiSubBlockTypeId8Len8, + sbStartOffset + ) ) + { + sbSsStatus = aIsiMessage.Get8bit( sbStartOffset + + SS_GSM_GENERIC_SERVICE_INFO_OFFSET_SSSTATUS ); + } + + // SS_GSM_DATA sub block + if ( 0 == sbSsStatus && KErrNone == aIsiMessage.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_SS_SERVICE_COMPLETED_IND, + SS_GSM_DATA, + EIsiSubBlockTypeId8Len8, + sbStartOffset + ) ) + { + sbSsStatus = aIsiMessage.Get8bit( sbStartOffset + + SS_GSM_DATA_OFFSET_SSSTATUS ); + } + + if ( 0 != sbSsStatus ) + { + //Found SS status info from SS_SERVICE_COMPLETED_IND + if ( SS_GSM_ACTIVE & sbSsStatus ) + { + ssStatus = KCustomApiSsGsmActive; + } + else if ( SS_GSM_REGISTERED & sbSsStatus ) + { + ssStatus = KCustomApiSsGsmRegistered; + } + else if ( SS_GSM_PROVISIONED & sbSsStatus ) + { + ssStatus = KCustomApiSsGsmProvisioned; + } + else + { + ssStatus = KCustomApiSsGsmQuiescent; + } + TFLOGSTRING2("TSY: CMmCustomMessHandler::SsServiceCompletedInd: Complete SsRequestCompleteNotification ssStatus:%d", + ssStatus ); +OstTrace1( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_SSSERVICECOMPLETEDIND, "CMmCustomMessHandler::SsServiceCompletedInd;Complete SsRequestCompleteNotification ssStatus=%u", ssStatus ); + + CMmDataPackage dataPackage; + // pack parameter: a TInt with SS status + dataPackage.PackData( &ssStatus ); + iMessageRouter->Complete( ECustomNotifySsRequestCompleteIPC, + &dataPackage, KErrNone ); + + } + + if ( KErrNone == aIsiMessage.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_SS_SERVICE_COMPLETED_IND, + SS_GSM_ADDITIONAL_INFO, + EIsiSubBlockTypeId8Len8, + sbStartOffset ) ) + { + //create SsAdditionalInfo structure + RMmCustomAPI::TSsAdditionalInfo additionalInfo; + + additionalInfo.iOperationCode = + aIsiMessage.Get8bit( ISI_HEADER_SIZE + + SS_SERVICE_COMPLETED_IND_OFFSET_OPERATION ); + + TUint8 length = aIsiMessage.Get8bit( sbStartOffset + + SS_GSM_ADDITIONAL_INFO_OFFSET_RETURNRESULTLEN ); + + additionalInfo.iAdditionalInfo.Copy( aIsiMessage.GetData( + sbStartOffset + SS_GSM_ADDITIONAL_INFO_OFFSET_RETURNRESULT, + length ) ); + + TFLOGSTRING("TSY: CMmCustomMessHandler::SsServiceCompletedInd: Complete SsAdditionalInfoNotification"); +OstTrace0( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_SSSERVICECOMPLETEDIND, "CMmCustomMessHandler::SsServiceCompletedInd - Complete SsAdditionalInfoNotification" ); + + // complete notification + CMmDataPackage dataPackage; + // pack parameter: pointer to RMmCustomAPI::TSsAdditionalInfo + RMmCustomAPI::TSsAdditionalInfo* additionalInfoPtr = + &additionalInfo; + dataPackage.PackData( &additionalInfoPtr ); + iMessageRouter->Complete( ECustomSsAdditionalInfoNotificationIPC, + &dataPackage, KErrNone ); + + } + } + else // No subblock found, e.g. in AlterEgo functionality + { + TInt ssStatus( KCustomApiSsGsmQuiescent ); + + CMmDataPackage dataPackage; + // pack parameter: a TInt with SS status + dataPackage.PackData( &ssStatus ); + iMessageRouter->Complete( ECustomNotifySsRequestCompleteIPC, + &dataPackage, KErrNone ); + } + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::SsServiceFailedResp +// Breaks a SS_SERVICE_FAILED_RESP ISI message. This method +// triggers SsRequestCompleteNotification notification. +// Completes SsRequestCompleteNotification method from custom tsy with +// status value 0xFFFF to SOS layer. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::SsServiceFailedResp + ( + const TIsiReceiveC& aIsiMessage //received ISI message + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::SsServiceFailedResp"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_SSSERVICEFAILEDRESP, "CMmCustomMessHandler::SsServiceFailedResp" ); + + TInt ssStatus( RMmCustomAPI::KSsStatusReturnError ); + + CMmDataPackage dataPackage; + + TUint sbStartOffset( 0 ); + + //create SsAdditionalInfo structure + RMmCustomAPI::TSsAdditionalInfo additionalInfo; + + // this data is not available, set to 0 just in case + additionalInfo.iOperationCode = 0x00; + + //if sub block exists + if ( KErrNone == aIsiMessage.FindSubBlockOffsetByIndex( + ISI_HEADER_SIZE + SIZE_SS_SERVICE_FAILED_RESP, + 1, + EIsiSubBlockTypeId8Len8, + sbStartOffset ) ) + { + TUint8 subBlockId( aIsiMessage.Get8bit( sbStartOffset ) ); + switch ( subBlockId ) + { + case SS_GSM_INDICATE_PASSWORD_ERROR: + { + // Set error code to additional info. No mapping needed because + // client wants error code as it was received from network. + additionalInfo.iAdditionalInfo.Append( + aIsiMessage.Get8bit( sbStartOffset + + SS_GSM_INDICATE_PASSWORD_ERROR_OFFSET_GUIDANCEINFO ) ); + break; + } + case SS_GSM_INDICATE_ERROR: + { + additionalInfo.iAdditionalInfo.Append( aIsiMessage.Get8bit( + sbStartOffset + SS_GSM_INDICATE_ERROR_OFFSET_ERRORCODE ) ); + // If additional indication is not default, add it to buffer + TUint8 addIndication( + aIsiMessage.Get8bit( sbStartOffset + + SS_GSM_INDICATE_ERROR_OFFSET_ADDITIONALINDICATION ) ); + // Just to keep previous functionality, the default value + // not added to buffer + if ( SS_DEFAULT_VALUE != addIndication ) + { + additionalInfo.iAdditionalInfo.Append( addIndication ); + } + break; + } + case SS_GSM_INDICATE_PROBLEM: + { + // Problem code is added to additional info only if RELEASE + // COMPLETE message from network includes Return Result + // component + if ( SS_GSM_RETURN_RESULT_PROBLEM == + aIsiMessage.Get8bit( sbStartOffset + + SS_GSM_INDICATE_PROBLEM_OFFSET_PROBLEMTYPE ) ) + { + additionalInfo.iAdditionalInfo.Append( + aIsiMessage.Get8bit( sbStartOffset + + SS_GSM_INDICATE_PROBLEM_OFFSET_PROBLEMCODE ) ); + } + break; + } + case SS_GSM_INDICATE_MSG_ERROR: + { + additionalInfo.iAdditionalInfo.Append( + aIsiMessage.Get8bit( sbStartOffset + + SS_GSM_INDICATE_MSG_ERROR_OFFSET_MESSAGEERRORCODE ) ); + break; + } + case SS_OTHER_ERROR: + { + additionalInfo.iAdditionalInfo.Append( aIsiMessage.Get8bit( + sbStartOffset + SS_OTHER_ERROR_OFFSET_ERRORCODE ) ); + break; + } + case SS_GSM_MM_RELEASED: + { + // This subblock occurs when network has released SS request, + // therefore SS status is set accordingly + ssStatus = RMmCustomAPI::KSsStatusNetworkFailure; + + additionalInfo.iAdditionalInfo.Append( aIsiMessage.Get8bit( + sbStartOffset + SS_GSM_MM_RELEASED_OFFSET_CAUSE ) ); + break; + } + default: + { + // unknown error sub block + additionalInfo.iAdditionalInfo.Append( 0x00 ); + break; + } + } + TFLOGSTRING2("TSY: CMmCustomMessHandler::SsServiceFailedResp: Ss Status: %d", ssStatus ); +OstTrace1( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_SSSERVICEFAILEDRESP, "CMmCustomMessHandler::SsServiceFailedResp;Ss Status=%d", ssStatus ); + // pack parameter: a TInt with SS status + dataPackage.PackData( &ssStatus ); + + // To complete outstanding SsRequestCompleteNotification + iMessageRouter->Complete( + ECustomNotifySsRequestCompleteIPC, + &dataPackage, + KErrNone ); + + TFLOGSTRING2("TSY: CMmCustomMessHandler::SsServiceFailedResp: SB ID: 0x%x",subBlockId ); +OstTraceExt1( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_SSSERVICEFAILEDRESP, "CMmCustomMessHandler::SsServiceFailedResp;subBlockId=%hhx", subBlockId ); + // pack parameter: pointer to RMmCustomAPI::TSsAdditionalInfo + RMmCustomAPI::TSsAdditionalInfo* additionalInfoPtr = &additionalInfo; + dataPackage.PackData( &additionalInfoPtr ); + + // To complete outstanding SsAdditionalInfoNotification + iMessageRouter->Complete( + ECustomSsAdditionalInfoNotificationIPC, + &dataPackage, + KErrNone ); + } + else + { + TFLOGSTRING("TSY: CMmCustomMessHandler::SsServiceFailedResp: No subblock's"); +OstTrace0( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_SSSERVICEFAILEDRESP, "CMmCustomMessHandler::SsServiceFailedResp - No subblock's" ); + + dataPackage.PackData( &ssStatus ); + + // No subblocks, complete with default values + iMessageRouter->Complete( ECustomNotifySsRequestCompleteIPC, + &dataPackage, + KErrNone ); + // No additional info given, no need to complete + // ECustomSsAdditionalInfoNotificationIPC + } + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::CallEmergencyNbrCheckReq +// Constructs CALL_MODEM_EMERGENCY_NBR_CHECK_REQ ISI message from input parameters +// and sends it through phonet. This message can be used to check if given +// number is an emrgency number. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::CallEmergencyNbrCheckReq + ( + TUint8 aTransId, // Transaction Id + RMmCustomAPI::TMobileTelNumber& aNumber, // Telnumber + RMmCustomAPI::TCheckMode aCheckMode // Check mode + ) + { + TFLOGSTRING( "TSY: CMmCustomMessHandler::CallEmergencyNbrCheckReq" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_CALLEMERGENCYNBRCHECKREQ, "CMmCustomMessHandler::CallEmergencyNbrCheckReq" ); + + //save the information to match it when the response is got + iUsedEmergencyNbrCheckMode = aCheckMode; + iEmergencyNumberLength = aNumber.Length(); + + // Construct CALL_MODEM_EMERG_NBR_CHECK_REQ message (1 filler + + // sub block count + bytes for CALL_MODEM_SB_DESTINATION_ADDRESS sub block) + TBuf8< 2 + SIZE_CALL_MODEM_SB_DESTINATION_ADDRESS + + ( RMobilePhone::KMaxMobileTelNumberSize * 2 ) > callEmergencyNbrCheckReq; + + // Filler + callEmergencyNbrCheckReq.Append( KCustomPadding ); + // Sub block count + callEmergencyNbrCheckReq.Append( 1 ); + + //create the CALL_MODEM_DESTINATION_ADDRESS subblock + TBuf8 + destinationAddressBuf( 0 ); + TIsiSubBlock destinationAddressSb( destinationAddressBuf, + CALL_MODEM_SB_DESTINATION_ADDRESS, EIsiSubBlockTypeId8Len8 ); + + //add the Address type, not needed because this is not checked on ISA side + destinationAddressBuf.Append( CALL_MODEM_NBR_PLAN_UNKNOWN ); + + //add padding bytes + destinationAddressBuf.Append( KCustomPadding ); + destinationAddressBuf.Append( KCustomPadding ); + + //add number length + //lint -e{732} Warning about "loss of sign". Root cause is that + //TDesC::Length() returns a signed TInt + destinationAddressBuf.Append( aNumber.Length() ); + + //add the number string + TIsiUtility::CopyToBigEndian( aNumber, destinationAddressBuf ); + + // add the CALL_MODEM_DESTINATION_ADDRESS subblock + callEmergencyNbrCheckReq.Append( destinationAddressSb.CompleteSubBlock() ); + + // Sending message to phonet + return iPhoNetSender->Send( PN_MODEM_CALL, aTransId, CALL_MODEM_EMERG_NBR_CHECK_REQ, + callEmergencyNbrCheckReq ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::CallEmergencyNbrCheckResp +// Breaks a CALL_EMERGENCY_CHECK_RESP ISI message. This method +// provides information whether the given number was an emergency number or not. +// Complete CompleteCheckEmergencyNumber with status and errorValue to SOS layer +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// + +void CMmCustomMessHandler::CallEmergencyNbrCheckResp + ( + const TIsiReceiveC& aIsiMsg // Received ISI message + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallEmergencyNbrCheckResp" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_CALLEMERGENCYNBRCHECKRESP, "CMmCustomMessHandler::CallEmergencyNbrCheckResp" ); + + // Get Status + TUint8 status( aIsiMsg.Get8bit( ISI_HEADER_SIZE + + CALL_MODEM_EMERG_NBR_CHECK_RESP_OFFSET_STATUS )); + + RMmCustomAPI::TMobileTelNumber telNumber; + + //Using the advance checking of the call server forces us to make sure + //that the call server is not is not misleading us... + if ( CALL_MODEM_EMERG_NBR_CHECK_PASS == status ) + { + TUint sbStartOffSet( 0 ); + + if ( KErrNone == aIsiMsg.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_CALL_MODEM_EMERG_NBR_CHECK_RESP, + CALL_MODEM_SB_EMERG_NUMBER, EIsiSubBlockTypeId8Len8, sbStartOffSet ) ) + { + //get length of returned number (number of Unicode characters) + TUint8 numberLength( aIsiMsg.Get8bit( sbStartOffSet + + CALL_MODEM_SB_EMERG_NUMBER_OFFSET_ADDRLEN )); + + //copy 8-bit number to the 16-bit target using correct endianess + //ISI message contains one Unicode digit in two bytes ==> multiply length by 2 + TIsiUtility::CopyFromBigEndian( aIsiMsg.GetData( sbStartOffSet + + CALL_MODEM_SB_EMERG_NUMBER_OFFSET_ADDR, + numberLength * 2 ), telNumber ); + + //Check that the Number length returned by call server doesn't + //differ from original phone number. + //Call server uses advanced mode while checking + //numbers. For example 2112 is valid emergency number for + //call server -> server returns number 112. However 2112 is not + //emergency number. + if ( RMmCustomAPI::EEmerNumberCheckNormal == + iUsedEmergencyNbrCheckMode && numberLength != + iEmergencyNumberLength ) + { + status = CALL_MODEM_EMERG_NBR_CHECK_FAIL; + } + } + else + { + //acording to call server feature description, in case of succesful + //checking the sub block should be present. Therefore we consider + //this case as a failure. + status = CALL_MODEM_EMERG_NBR_CHECK_FAIL; + } + } + + // map to result: failed is 0, successful is ptr to number + RMmCustomAPI::TMobileTelNumber* result = + ( ( CALL_MODEM_EMERG_NBR_CHECK_FAIL == status ) ? + 0 : &telNumber ); + + // packed parameter: TBool result + CMmDataPackage dataPackage; + dataPackage.PackData( &result ); + + TFLOGSTRING2( "TSY: TSY: CMmCustomMessHandler::CallEmergencyNbrCheckResp status: %d", status); + TFLOGSTRING2( "TSY: TSY: CMmCustomMessHandler::CallEmergencyNbrCheckResp emergency number: %S", &telNumber); + //we complete with KErrNone as there is always a value to return + iMessageRouter->Complete( ECustomCheckEmergencyNumberIPC, &dataPackage, + KErrNone ); + + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccOperatorReq +// Read operator name from UICC +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccOperatorReq() + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccOperatorReq" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCOPERATORREQ, "CMmCustomMessHandler::UiccOperatorReq" ); + + // Set parameters for UICC_APPL_CMD_REQ message + TUiccReadTransparent params; + params.messHandlerPtr = static_cast( this ); + params.trId = ETrIdReadOperatorNameCustom; + params.dataOffset = 0; + params.dataAmount = 0; + params.fileId = KElemFileOperatorName; + params.fileIdSfi = UICC_SFI_NOT_PRESENT; + params.serviceType = UICC_APPL_READ_TRANSPARENT; + + // File id path + params.filePath.Append( KMasterFileId >> 8 ); + params.filePath.Append( KMasterFileId ); + params.filePath.Append( iMmUiccMessHandler->GetApplicationFileId() ); + + return iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccOperatorResp +// Complete operator name +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccOperatorResp( + TInt aStatus, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccOperatorResp" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCOPERATORRESP, "CMmCustomMessHandler::UiccOperatorResp" ); + + TInt errorValue( KErrGeneral ); + + // Network provider name + TBuf name; + + if ( KErrNone == aStatus ) + { + errorValue = KErrNone; + name.Copy( aFileData ); + } + + // Packed parameter: TDes* (network provider name) + CMmDataPackage dataPackage; + TDes* namePtr( &name ); + dataPackage.PackData( &namePtr ); + + iMessageRouter->Complete( + ECustomGetNetworkProviderNameIPC, + &dataPackage, + errorValue ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::SsGsmUssdSendReq +// Constructs SS_GSM_USSD_SEND_REQ ISI message from input parameters +// and sends it through phonet. +// This message can be used only to cancel ussd session. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::SsGsmUssdSendReq + ( + TUint8 aTransId //transaction Id + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::SsGsmUssdSendReq" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_SSGSMUSSDSENDREQ, "CMmCustomMessHandler::SsGsmUssdSendReq" ); + + // create buffer for isi msg data + TBuf8<2> data; + data.Append( SS_GSM_USSD_END ); + //number of sub blocks + data.Append( 0 ); + + // Message sent via Phonet and return + return iPhoNetSender->Send( PN_SS, aTransId, SS_GSM_USSD_SEND_REQ, data ); + + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::SsGsmUssdSendResp +// Breaks a SS_USSD_SEND_RESP ISI message. +// This method gets USSD type information from message and completes cancelling +// of ussd session. Complete CancelUssdSession with KErrNone to SOS layer. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::SsGsmUssdSendResp + ( + const TIsiReceiveC& aIsiMessage //received ISI message + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::SsGsmUssdSendResp" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_SSGSMUSSDSENDRESP, "CMmCustomMessHandler::SsGsmUssdSendResp" ); + + + TUint ussdType( aIsiMessage.Get8bit( + ISI_HEADER_SIZE + + SS_GSM_USSD_SEND_RESP_OFFSET_USSDTYPE ) ); + + if ( SS_GSM_USSD_END == ussdType ) + { + // no packed parameters for completion + iMessageRouter->Complete( ECustomCancelUssdSessionIPC, KErrNone ); + } + + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::Match +// This method can be checks if two TCiphListEntry entries are same. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TBool CMmCustomMessHandler::Match + ( + const TCiphListEntry& aArg1, //first argument + const TCiphListEntry& aArg2 //second argument + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::Match.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_MATCH, "CMmCustomMessHandler::Match" ); + + TBool ret ( EFalse ); + + //we are interested only in the traId value + if ( aArg1.iTraId == aArg2.iTraId ) + { + ret = ETrue; + } + + return ret; + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::NetModemRegStatusGetReq +// Constructs NET_MODEM_REG_STATUS_GET_REQ ISI message from input parameters +// and sends it through phonet. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::NetModemRegStatusGetReq + ( + const TUint8 aTransactionId + ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::NetModemRegStatusGetReq." ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_NETMODEMREGSTATUSGETREQ, "CMmCustomMessHandler::NetModemRegStatusGetReq" ); + + // Data length buffer is 2. + TBuf8<2> data; + data.Append( aTransactionId ); + data.Append( NET_MODEM_REG_STATUS_GET_REQ ); + + TIsiSend isimsg( iPhoNetSender->SendBufferDes() ); + isimsg.Set8bit( ISI_HEADER_OFFSET_RESOURCEID, PN_MODEM_NETWORK ); + isimsg.CopyData( ISI_HEADER_SIZE, data ); + + return( iPhoNetSender->Send( isimsg.Complete() ) ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::NetModemRegStatusGetResp +// NET_MODEM_REG_STATUS_GET_RESP message is handled in queue functionality +// in cmmnetmesshandler/cmmnetoperatornamehandler and will be completed +// there after handling. +// This method check if ECID info needs to be updated. +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::NetModemRegStatusGetResp( + const TIsiReceiveC& aIsiMsg ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::NetModemRegStatusGetResp" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_NETMODEMREGSTATUSGETRESP, "CMmCustomMessHandler::NetModemRegStatusGetResp" ); + + // Get the success code. + TUint8 successCode( aIsiMsg.Get8bit( + ISI_HEADER_SIZE + + NET_MODEM_REG_STATUS_GET_RESP_OFFSET_SUCCESSCODE ) ); + + if ( NET_CAUSE_OK == successCode ) + { + // Check if ECID info needs to be updated. + CheckECIDInfo( aIsiMsg ); + } + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::CallGsmNotificationInd +// This method breaks the CALL_MODEM_NOTIFICATION_IND ISI message. +// Complete: ECustomNotifySsNetworkEventIPC to SOS layer. +// If CALL_MODEM_SB_ALERTING_INFO sub block exist ECustomGetRemoteAlertingToneStatusIPC +// is completed to SOS layer. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::CallGsmNotificationInd + ( + const TIsiReceiveC& aIsiMsg // received ISI message + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallGsmNotificationInd"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_CALLGSMNOTIFICATIONIND, "CMmCustomMessHandler::CallGsmNotificationInd" ); + + TInt ret( KErrNone ); + + // For packaging + CMmDataPackage dataPackage; + + RMmCustomAPI::TSsTypeAndMode ssTypeAndMode; + RMmCustomAPI::TSsInfo ssInfo; + + // Initialize the default values + ssInfo.iCallHold = RMmCustomAPI::ESsHoldNotActive; + ssInfo.iEctCallState = RMmCustomAPI::ESsEctNotActive; + ssInfo.iCallWait = EFalse; + ssInfo.iConfInd = EFalse; + ssInfo.iClirSuppReject = EFalse; + ssInfo.iForwMode = RMmCustomAPI::EForwNotActive; + ssInfo.iCugIndex = CALL_MODEM_CUG_DEFAULT; + ssInfo.iChoice = RMmCustomAPI::ESsChoiceUnknown; + ssInfo.iRemoteAddress.FillZ(); + ssTypeAndMode.iSsMode = RMmCustomAPI::ESsModeUnknown; + ssTypeAndMode.iSsType = RMmCustomAPI::ESsAllSs; + + TUint sbStartOffSet( 0 ); + + // Get CALL_MODEM_SB_SS_CODE sub block + if ( KErrNone == aIsiMsg.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_CALL_MODEM_NOTIFICATION_IND, + CALL_MODEM_SB_SS_CODE, + EIsiSubBlockTypeId8Len8, + sbStartOffSet ) ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallGsmNotificationInd,\ + - CALL_MODEM_SB_SS_CODE sub block founded"); +OstTrace0( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_CALLGSMNOTIFICATIONIND, "CMmCustomMessHandler::CallGsmNotificationInd, CALL_MODEM_SB_SS_CODE sub block found" ); + + TUint16 ssCode( aIsiMsg.Get16bit( + sbStartOffSet + CALL_MODEM_SB_SS_CODE_OFFSET_MMISSCODE ) ); + + switch ( ssCode ) + { + case CALL_MODEM_SSC_ALL_FWDS: + case CALL_MODEM_SSC_CFU: + case CALL_MODEM_SSC_CFB: + case CALL_MODEM_SSC_CFNRY: + case CALL_MODEM_SSC_CFGNC: + case CALL_MODEM_SSC_ALL_COND_FWD: + { + HandleForwarding( ssCode, aIsiMsg, ssTypeAndMode ); + break; + } + case CALL_MODEM_SSC_OUTGOING_BARR_SERV: + case CALL_MODEM_SSC_INCOMING_BARR_SERV: + { + HandleBarring( ssCode, aIsiMsg, ssTypeAndMode ); + break; + } + case CALL_MODEM_SSC_CALL_WAITING: + { + ssTypeAndMode.iSsType = RMmCustomAPI::ESsCallWaiting; + break; + } + case CALL_MODEM_SSC_CLIP: + { + ssTypeAndMode.iSsType = RMmCustomAPI::ESsClip; + break; + } + case CALL_MODEM_SSC_CLIR: + { + ssTypeAndMode.iSsType = RMmCustomAPI::ESsClir; + break; + } + case CALL_MODEM_SSC_COLP: + { + ssTypeAndMode.iSsType = RMmCustomAPI::ESsColp; + break; + } + case CALL_MODEM_SSC_COLR: + { + ssTypeAndMode.iSsType = RMmCustomAPI::ESsColr; + break; + } + default: + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallGsmNotificationInd,\ + switch ssCode - default."); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_CALLGSMNOTIFICATIONIND, "CMmCustomMessHandler::CallGsmNotificationInd, switch ssCode - default" ); + break; + } + } + } + + // Get CALL_GSM_SS_NOTIFY sub block + if ( KErrNone == aIsiMsg.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_CALL_MODEM_NOTIFICATION_IND, + CALL_MODEM_SB_SS_NOTIFY, + EIsiSubBlockTypeId8Len8, + sbStartOffSet ) ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallGsmNotificationInd,\ + - CALL_MODEM_SB_SS_NOTIFY sub block founded"); +OstTrace0( TRACE_NORMAL, DUP4_CMMCUSTOMMESSHANDLER_CALLGSMNOTIFICATIONIND, "CMmCustomMessHandler::CallGsmNotificationInd, CALL_MODEM_SB_SS_NOTIFY sub block found" ); + + // Get the SsNotifyIndictor + TUint8 ssNotify( aIsiMsg.Get8bit( + sbStartOffSet + CALL_MODEM_SB_SS_NOTIFY_OFFSET_SSNOTIFICATION ) ); + + // Mask the value + // Incoming call is a forwarded call + if ( CALL_MODEM_SSN_INCOMING_IS_FWD == ssNotify ) + { + ssInfo.iForwMode = RMmCustomAPI::ESsIncCallIsForw; + } + // Incoming call has been forwarded to C + else if ( CALL_MODEM_SSN_INCOMING_FWD == ssNotify ) + { + ssInfo.iForwMode = RMmCustomAPI::ESsIncCallForwToC; + } + //Outgoing call is fowarded to C + else if ( CALL_MODEM_SSN_OUTGOING_FWD == ssNotify ) + { + ssInfo.iForwMode = RMmCustomAPI::ESsOutCallForwToC; + } + // No else + } + + // Get CALL_MODEM_SB_SS_NOTIFY_INDICATOR sub block + if ( KErrNone == aIsiMsg.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_CALL_MODEM_NOTIFICATION_IND, + CALL_MODEM_SB_SS_NOTIFY_INDICATOR, + EIsiSubBlockTypeId8Len8, + sbStartOffSet ) ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallGsmNotificationInd,\ + - CALL_MODEM_SB_SS_NOTIFY_INDICATOR sub block founded"); +OstTrace0( TRACE_NORMAL, DUP5_CMMCUSTOMMESSHANDLER_CALLGSMNOTIFICATIONIND, "CMmCustomMessHandler::CallGsmNotificationInd, CALL_MODEM_SB_SS_NOTIFY_INDICATOR sub block found" ); + + // Get the SsNotifyIndictor + TUint8 ssNotifyIndicator( aIsiMsg.Get8bit( sbStartOffSet + + CALL_MODEM_SB_SS_NOTIFY_INDICATOR_OFFSET_SSINDICATOR ) ); + + // Mask the value of the Indicator + if ( CALL_MODEM_SSI_CALL_IS_WAITING == ssNotifyIndicator ) // Call waiting + { + ssInfo.iCallWait = ETrue; + } + else if ( CALL_MODEM_SSI_MPTY == ssNotifyIndicator ) // Conference call + { + ssInfo.iConfInd = ETrue; + } + // CLIR suppresion rejected + else if ( CALL_MODEM_SSI_CLIR_SUPPR_REJ == ssNotifyIndicator ) + { + ssInfo.iClirSuppReject = ETrue; + } + // No else + } + + // Get CALL_MODEM_SB_SS_HOLD_INDICATOR sub block + if ( KErrNone == aIsiMsg.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_CALL_MODEM_NOTIFICATION_IND, + CALL_MODEM_SB_SS_HOLD_INDICATOR, + EIsiSubBlockTypeId8Len8, + sbStartOffSet ) ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallGsmNotificationInd,\ + - CALL_MODEM_SB_SS_HOLD_INDICATOR sub block founded"); +OstTrace0( TRACE_NORMAL, DUP6_CMMCUSTOMMESSHANDLER_CALLGSMNOTIFICATIONIND, "CMmCustomMessHandler::CallGsmNotificationInd, CALL_MODEM_SB_SS_HOLD_INDICATOR sub block found" ); + + // Get the ectIndictor + TUint8 holdIndicator( aIsiMsg.Get8bit( sbStartOffSet + + CALL_MODEM_SB_SS_HOLD_INDICATOR_OFFSET_SSHOLDINDICATOR ) ); + + // If hold indicator is 1 + if ( holdIndicator ) + { + ssInfo.iCallHold = RMmCustomAPI::ESsHoldActive; + } + else // hold indicator is 0 + { + ssInfo.iCallHold = RMmCustomAPI::ESsHoldResume; + } + } + + // Get CALL_MODEM_SB_CUG_INFO sub block + if ( KErrNone == aIsiMsg.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_CALL_MODEM_NOTIFICATION_IND, + CALL_MODEM_SB_CUG_INFO, + EIsiSubBlockTypeId8Len8, + sbStartOffSet ) ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallGsmNotificationInd,\ + - CALL_MODEM_SB_CUG_INFO sub block founded"); +OstTrace0( TRACE_NORMAL, DUP7_CMMCUSTOMMESSHANDLER_CALLGSMNOTIFICATIONIND, "CMmCustomMessHandler::CallGsmNotificationInd, CALL_MODEM_SB_CUG_INFO sub block found" ); + + // Get the CUG index + ssInfo.iCugIndex = aIsiMsg.Get16bit( + sbStartOffSet + CALL_MODEM_SB_CUG_INFO_OFFSET_CUGIND ); + } + + // Get CALL_MODEM_SB_SS_ECT_INDICATOR sub block + if ( KErrNone == aIsiMsg.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_CALL_MODEM_NOTIFICATION_IND, + CALL_MODEM_SB_SS_ECT_INDICATOR, + EIsiSubBlockTypeId8Len8, + sbStartOffSet ) ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallGsmNotificationInd,\ + - CALL_MODEM_SB_SS_ECT_INDICATOR sub block founded"); +OstTrace0( TRACE_NORMAL, DUP8_CMMCUSTOMMESSHANDLER_CALLGSMNOTIFICATIONIND, "CMmCustomMessHandler::CallGsmNotificationInd, CALL_MODEM_SB_SS_ECT_INDICATOR sub block found" ); + + // Get the ectIndictor + TUint8 ectIndicator( aIsiMsg.Get8bit( + sbStartOffSet + CALL_MODEM_SB_SS_ECT_INDICATOR_OFFSET_SSECTINDICATOR ) ); + + // If ect is 1 + if ( ectIndicator ) + { + ssInfo.iEctCallState = RMmCustomAPI::ESsEctActive; + } + else // ect is 0 + { + ssInfo.iEctCallState = RMmCustomAPI::ESsEctAlerting; + } + } + + // Get CALL_MODEM_SB_REMOTE_ADDRESS sub block + if ( KErrNone == aIsiMsg.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_CALL_MODEM_NOTIFICATION_IND, + CALL_MODEM_SB_REMOTE_ADDRESS, + EIsiSubBlockTypeId8Len8, + sbStartOffSet ) ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallGsmNotificationInd,\ + - CALL_MODEM_SB_REMOTE_ADDRESS sub block founded"); +OstTrace0( TRACE_NORMAL, DUP9_CMMCUSTOMMESSHANDLER_CALLGSMNOTIFICATIONIND, "CMmCustomMessHandler::CallGsmNotificationInd, CALL_MODEM_SB_REMOTE_ADDRESS sub block found" ); + + // Get the presentation + + TUint8 presentationIndicator( aIsiMsg.Get8bit( + sbStartOffSet + CALL_MODEM_SB_REMOTE_ADDRESS_OFFSET_PRESENTATION ) ); + // Mask with 0110 0000 to get bits 6-7 + presentationIndicator &= 0x60; + + switch ( presentationIndicator ) + { + case CALL_MODEM_PRESENTATION_ALLOWED: + { + ssInfo.iChoice = RMmCustomAPI::ESsPresAllowed; + break; + } + case CALL_MODEM_PRESENTATION_RESTRICTED: + { + ssInfo.iChoice = RMmCustomAPI::ESsPresRestricted; + break; + } + case CALL_MODEM_PRESENTATION_UNAVAILABLE: + { + ssInfo.iChoice = RMmCustomAPI::ESsNumberNotAvailable; + break; + } + default: + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallGsmNotificationInd,\ + - CALL_MODEM_SB_REMOTE_ADDRESS sub block\ + - switch presentationIndicator - default."); +OstTrace0( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_CALLGSMNOTIFICATIONIND, "CMmCustomMessHandler::CallGsmNotificationInd, switch presentationIndicator - default" ); + // The variable already has a default value + break; + } + } + + // Copy the number with rigth endianess + TUint8 remoteAddressLength( aIsiMsg.Get8bit( + sbStartOffSet + CALL_MODEM_SB_REMOTE_ADDRESS_OFFSET_ADDRLEN ) ); + + // Copy 8-bit name to the 16-bit target using correct endianess + TIsiUtility::CopyFromBigEndian( aIsiMsg.GetData( + sbStartOffSet + CALL_MODEM_SB_REMOTE_ADDRESS_OFFSET_ADDR, + remoteAddressLength ), + ssInfo.iRemoteAddress ); + } + + // Get CALL_MODEM_SB_ALERTING_INFO sub block + if ( KErrNone == aIsiMsg.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_CALL_MODEM_NOTIFICATION_IND, + CALL_MODEM_SB_ALERTING_INFO, + EIsiSubBlockTypeId8Len8, + sbStartOffSet ) ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CallGsmNotificationInd,\ + - CALL_MODEM_SB_ALERTING_INFO sub block founded"); +OstTrace0( TRACE_NORMAL, DUP10_CMMCUSTOMMESSHANDLER_CALLGSMNOTIFICATIONIND, "CMmCustomMessHandler::CallGsmNotificationInd, CALL_MODEM_SB_ALERTING_INFO sub block found" ); + + TBool playRemoteAlertToneLocally( EFalse ); + + // Get alerting info + TUint8 callAlertingInfo( aIsiMsg.Get8bit( + sbStartOffSet + CALL_MODEM_SB_ALERTING_INFO_OFFSET_ALERTINGINFO ) ); + + // If LSB is "1" inform that remote alerting tone + // should be generated locally. + if ( callAlertingInfo & 0x01 ) + { + playRemoteAlertToneLocally = ETrue; + } + + // Complete remote alerting tone notification + // Parameter for SOS layer: a TBool playRemoteAlertToneLocally + dataPackage.PackData( &playRemoteAlertToneLocally ); + iMessageRouter->Complete( ECustomGetRemoteAlertingToneStatusIPC, + &dataPackage, + KErrNone ); + } + + // Complete SsNetworkEvent notification + // Pack parameter: a RMmCustomAPI::TSsTypeAndMode and + // a RMmCustomAPI::TSsInfo + dataPackage.PackData( &ssTypeAndMode, &ssInfo ); + iMessageRouter->Complete( ECustomNotifySsNetworkEventIPC, + &dataPackage, + ret ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::HandleForwarding +// Breaks a CALL_MODEM_NOTIFICATION_IND ISI message. +// Gets forwardfing related information from message and sets it in +// aSsTypeAndMode for further completion in the method CallGsmNotificationIndL2 +// to SOS layer. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::HandleForwarding + ( + TUint16 aSsCode, //SS code + const TIsiReceiveC& aIsiMsg, //Isi message + RMmCustomAPI::TSsTypeAndMode& aSsTypeAndMode //ss type and mode + ) const + { + TFLOGSTRING("TSY: CMmCustomMessHandler::HandleForwarding.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_HANDLEFORWARDING, "CMmCustomMessHandler::HandleForwarding" ); + + //identify the kind of forwarding + switch ( aSsCode ) + { + case CALL_MODEM_SSC_ALL_FWDS: + aSsTypeAndMode.iSsType = RMmCustomAPI::ESsAllForwardings; + break; + case CALL_MODEM_SSC_CFU: + aSsTypeAndMode.iSsType = RMmCustomAPI::ESsForwUncond; + break; + case CALL_MODEM_SSC_CFB: + aSsTypeAndMode.iSsType = RMmCustomAPI::ESsForwBusy; + break; + case CALL_MODEM_SSC_CFNRY: + aSsTypeAndMode.iSsType = RMmCustomAPI::ESsForwNoReply; + break; + case CALL_MODEM_SSC_CFGNC: + aSsTypeAndMode.iSsType = RMmCustomAPI::ESsForwNoReach; + break; + case CALL_MODEM_SSC_ALL_COND_FWD: + aSsTypeAndMode.iSsType = RMmCustomAPI::ESsAllCondForwardings; + break; + default: + TFLOGSTRING("TSY: CMmCustomMessHandler::HandleForwarding, switch aSsCode - default.\n" ); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_HANDLEFORWARDING, "CMmCustomMessHandler::HandleForwarding, switch aSsCode - default" ); + //this case is imposible, added due code convention + break; + } + + TUint sbStartOffSet( 0 ); + + //get call gsm ss status sub block + if ( KErrNone == aIsiMsg.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_CALL_MODEM_NOTIFICATION_IND, + CALL_MODEM_SB_SS_STATUS, EIsiSubBlockTypeId8Len8, sbStartOffSet ) ) + { + //get the ss status + TUint8 ssStatus ( aIsiMsg.Get8bit( sbStartOffSet + + CALL_MODEM_SB_SS_STATUS_OFFSET_SSSTATUS ) ); + + //set the right status for the bit configuration of ssStatus + if ( CALL_MODEM_SS_STATUS_ACTIVE & ssStatus ) //if active is present + { + aSsTypeAndMode.iSsMode = RMmCustomAPI::ESsModeActive; + } + // if quiescent is present + else if ( CALL_MODEM_SS_STATUS_QUIESCENT & ssStatus ) + { + //if registered and provisioned, and not active or quiescent + aSsTypeAndMode.iSsMode = RMmCustomAPI::ESsModeNotAvailable; + } + //if registered and provisioned, and not active or quiescent + else if ( ( CALL_MODEM_SS_STATUS_REGISTERED | CALL_MODEM_SS_STATUS_PROVISIONED ) + == ssStatus ) + { + aSsTypeAndMode.iSsMode = RMmCustomAPI::ESsModeNotActive; + } + else if ( CALL_MODEM_SS_STATUS_PROVISIONED == ssStatus ) //only provisioned + { + aSsTypeAndMode.iSsMode = RMmCustomAPI::ESsModeNotRegistered; + } + else //not provisioned + { + aSsTypeAndMode.iSsMode = RMmCustomAPI::ESsModeNotProvisioned; + } + } + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::HandleBarring +// Breaks a CALL_MODEM_NOTIFICATION_IND ISI message. +// Gets barring related information from message and sets it in +// aSsTypeAndMode for further completion in the method CallGsmNotificationIndL2. +// to SOS layer. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::HandleBarring + ( + TUint16 aSsCode, //SS code + const TIsiReceiveC& aIsiMsg, //ISI message + RMmCustomAPI::TSsTypeAndMode& aSsTypeAndMode //Ss type and mode + ) const + { + TFLOGSTRING("TSY: CMmCustomMessHandler::HandleBarring.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_HANDLEBARRING, "CMmCustomMessHandler::HandleBarring" ); + + //identify the kind of barring + switch ( aSsCode ) + { + case CALL_MODEM_SSC_OUTGOING_BARR_SERV: + aSsTypeAndMode.iSsType = RMmCustomAPI::ESsOutgoingBarrServ; + break; + case CALL_MODEM_SSC_INCOMING_BARR_SERV: + aSsTypeAndMode.iSsType = RMmCustomAPI::ESsIncomingBarrServ; + break; + default: + TFLOGSTRING("TSY: CMmCustomMessHandler::HandleBarring, switch aSsCode - default.\n" ); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_HANDLEBARRING, "CMmCustomMessHandler::HandleBarring, switch aSsCode - default" ); + //this case is imposible, added due code convention + break; + } + + TUint sbStartOffSet( 0 ); + + //get call gsm ss status sub block + if ( KErrNone == aIsiMsg.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_CALL_MODEM_NOTIFICATION_IND, + CALL_MODEM_SB_SS_STATUS, EIsiSubBlockTypeId8Len8, sbStartOffSet ) ) + { + //get the ss status + TUint8 ssStatus ( aIsiMsg.Get8bit( sbStartOffSet + + CALL_MODEM_SB_SS_STATUS_OFFSET_SSSTATUS ) ); + + //set the right status for the bit configuration of ssStatus + if ( CALL_MODEM_SS_STATUS_ACTIVE & ssStatus ) //if active is present + { + aSsTypeAndMode.iSsMode = RMmCustomAPI::ESsModeActive; + } + //if quiescent is present + else if ( CALL_MODEM_SS_STATUS_QUIESCENT & ssStatus ) + { + aSsTypeAndMode.iSsMode = RMmCustomAPI::ESsModeNotAvailable; + } + else if ( CALL_MODEM_SS_STATUS_PROVISIONED == ssStatus ) //only provisioned + { + aSsTypeAndMode.iSsMode = RMmCustomAPI::ESsModeNotRegistered; + } + else + { + aSsTypeAndMode.iSsMode = RMmCustomAPI::ESsModeNotProvisioned; + } + } + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::NetSetReq +// Constructs NET_SET_REQ ISI message from input parameters +// and sends it through phonet. +// This message is created for reseting the network server +// to previous registered network when the user doesn't select +// a network from the network list got in a search +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::NetSetReq( TUint8 aTransId ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::NetSetReq"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_NETSETREQ, "CMmCustomMessHandler::NetSetReq" ); + + // Data for ISI message, buffer size is one + TBuf8<2 + SIZE_NET_OPERATOR_INFO_COMMON> netSetReq; + // Registered in another protocol is set to 0 + netSetReq.Append ( 0 ); + + // 1 SubBlock + netSetReq.Append ( 1 ); + + TBuf8 netGsmOperatorInfoCommonBuf; + TIsiSubBlock netGsmOperatorInfoCommonSb( + netGsmOperatorInfoCommonBuf, + NET_OPERATOR_INFO_COMMON, + EIsiSubBlockTypeId8Len8 ); + + netGsmOperatorInfoCommonBuf.Append( NET_SELECT_MODE_NO_SELECTION ); + netGsmOperatorInfoCommonBuf.Append( NET_INDEX_NOT_USED ); + + netSetReq.Append( netGsmOperatorInfoCommonSb.CompleteSubBlock() ); + + // Send message via Phonet + return iPhoNetSender->Send( + PN_MODEM_NETWORK, + aTransId, + NET_SET_REQ, + netSetReq ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::NetSetResp +// Breaks a NET_SERVER_RESP ISI message. +// This message maps the CS cause value to ETel error value and complete +// CompleteResetNetServer to SOS layer. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::NetSetResp( const TIsiReceiveC& aIsiMsg ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::NetSetResp"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_NETSETRESP, "CMmCustomMessHandler::NetSetResp" ); + + // Get the cause + TUint8 cause( aIsiMsg.Get8bit( + ISI_HEADER_SIZE + + NET_SET_RESP_OFFSET_SUCCESSCODE ) ); + + // Map the cs error as symbian value + TInt error( CMmStaticUtility::CSCauseToEpocError( + PN_MODEM_NETWORK, + KTsyNetCauseCommon, + cause ) ); + + // Completion ResetNetServer method (no packed parameters) + iMessageRouter->Complete( ECustomResetNetServerIPC, error ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::NetRatResp +// Breaks a NET_SERVER_RESP ISI message. +// This method get RatName sub blocks maps the CS cause value to ETel error +// value and complete ResetNetServer to SOS layer. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::NetRatResp( const TIsiReceiveC& aIsiMsg ) + { +TFLOGSTRING( "TSY: CMmCustomMessHandler::NetRatResp"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_NETRATRESP, "CMmCustomMessHandler::NetRatResp" ); + + // Get the success code + TUint8 successCode( aIsiMsg.Get8bit( + ISI_HEADER_SIZE + NET_RAT_RESP_OFFSET_SUCCESSCODE ) ); + + TInt ret( KErrNone ); + + TUint32 supportedNetworkModes( 0 ); + +TFLOGSTRING2( "TSY: CMmCustomMessHandler::NetRatResp successCode : %d", successCode); +OstTraceExt1( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_NETRATRESP, "CMmCustomMessHandler::NetRatResp;successCode=%hhu", successCode ); + + // Check if we have sub blocks in the message + if ( aIsiMsg.Get8bit( ISI_HEADER_SIZE + NET_RAT_RESP_OFFSET_SUBBLOCKCOUNT ) + != 0 && NET_CAUSE_OK == successCode ) + { + TUint8 subBlockIndex( 1 ); + TUint sbStartOffSet( 0 ); + + // NET_RAT_INFO sub block + while ( KErrNone == aIsiMsg.FindSubBlockOffsetByIndex( + ISI_HEADER_SIZE + SIZE_NET_RAT_RESP, + subBlockIndex, + EIsiSubBlockTypeId8Len8, + sbStartOffSet ) ) + { + // Get ratName + TUint8 ratName( aIsiMsg.Get8bit( + sbStartOffSet + NET_RAT_INFO_OFFSET_RATNAME ) ); + + switch ( ratName ) + { + case NET_GSM_RAT: + { + supportedNetworkModes += RMmCustomAPI::KCapsNetworkModeGsm; + break; + } + case NET_UMTS_RAT: + { + supportedNetworkModes += RMmCustomAPI::KCapsNetworkModeUmts; + break; + } + } + subBlockIndex++; + } + } + else + { + // Map the cs error as symbian value + ret = CMmStaticUtility::CSCauseToEpocError( + PN_MODEM_NETWORK, + KTsyNetCauseCommon, + successCode ); + } + + CMmDataPackage dataPackage; + dataPackage.PackData( &supportedNetworkModes ); + +TFLOGSTRING2( "TSY: CMmCustomMessHandler::NetRatResp - ret: %d", ret); +OstTrace1( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_NETRATRESP, "CMmCustomMessHandler::NetRatResp;ret=%d", ret ); + + // Completion ResetNetServer method (packed parameters) + iMessageRouter->Complete( + ECustomGetSystemNetworkModesIPC, + &dataPackage, + ret ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::GssCsServiceResp +// Breaks a GSS_CS_SERVICE_RESP ISI message. +// completes ECustomSetSystemNetworkModeIPC, ECustomSetBandSelectionIPC or +// ECustomGetBandSelectionIPC with KErrNone to SOS layer. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::GssCsServiceResp ( + const TIsiReceiveC& aIsiMessage ) // Received isi message + { + TFLOGSTRING( "TSY: CMmCustomMessHandler::GssCsServiceResp" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_GSSCSSERVICERESP, "CMmCustomMessHandler::GssCsServiceResp" ); + + TUint8 transactId ( aIsiMessage.Get8bit( + ISI_HEADER_SIZE + GSS_CS_SERVICE_RESP_OFFSET_TRANSID ) ); + + TUint8 operation ( aIsiMessage.Get8bit( + ISI_HEADER_SIZE + GSS_CS_SERVICE_RESP_OFFSET_OPERATION ) ); + + // GSS_SELECTED_RAT_WRITE (0x0E) + if ( KCustomTransId == transactId && GSS_SELECTED_RAT_WRITE == operation ) + { + //completion ResetGssServer method (no packed parameters) + TFLOGSTRING("TSY: CMmCustomMessHandler::GssCsServiceResp - Complete ECustomSetSystemNetworkModeIPC"); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_GSSCSSERVICERESP, "CMmCustomMessHandler::GssCsServiceResp - Complete ECustomSetSystemNetworkModeIPC" ); + iMessageRouter->Complete( ECustomSetSystemNetworkModeIPC, KErrNone ); + } + +// not suppoted for S60 ver 3.2 +#if ( NCP_COMMON_S60_VERSION_SUPPORT != S60_VERSION_32 ) + + // GSS_SELECTED_BANDS_WRITE (0x9D) + else if ( GSS_SELECTED_BANDS_WRITE == operation ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::GssCsServiceResp - Complete ECustomSetBandSelectionIPC"); +OstTrace0( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_GSSCSSERVICERESP, "CMmCustomMessHandler::GssCsServiceResp - Complete ECustomSetBandSelectionIPC" ); + iMessageRouter->Complete( ECustomSetBandSelectionIPC, KErrNone ); + } + // GSS_SELECTED_BANDS_READ (0x9E) + else if ( GSS_SELECTED_BANDS_READ == operation ) + { + CompleteGetBandSelection( aIsiMessage ); + } +#endif // NCP_COMMON_S60_VERSION_SUPPORT + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::GssCsServiceFailResp +// Breaks a GSS_CS_SERVICE_FAIL_RESP ISI message. +// completes ECustomSetSystemNetworkModeIPC, ECustomSetBandSelectionIPC +// or ECustomGetBandSelectionIPC with error value to SOS layer. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::GssCsServiceFailResp ( + const TIsiReceiveC& aIsiMessage ) // Received isi message + { + TFLOGSTRING( "TSY: CMmCustomMessHandler::GssCsServiceFailResp" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_GSSCSSERVICEFAILRESP, "CMmCustomMessHandler::GssCsServiceFailResp" ); + + TUint8 transactId ( aIsiMessage.Get8bit( ISI_HEADER_SIZE + + GSS_CS_SERVICE_FAIL_RESP_OFFSET_TRANSID ) ); + TUint8 operation ( aIsiMessage.Get8bit( ISI_HEADER_SIZE + + GSS_CS_SERVICE_FAIL_RESP_OFFSET_OPERATION ) ); + + // GSS_SELECTED_RAT_WRITE (0x0E) + if ( KCustomTransId == transactId && GSS_SELECTED_RAT_WRITE == operation ) + { + //completion ResetGssServer method (no packed parameters) + TFLOGSTRING("TSY: CMmCustomMessHandler::GssCsServiceFailResp - ECustomSetSystemNetworkModeIPC"); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_GSSCSSERVICEFAILRESP, "CMmCustomMessHandler::GssCsServiceFailResp - ECustomSetSystemNetworkModeIPC" ); + iMessageRouter->Complete( ECustomSetSystemNetworkModeIPC, KErrGeneral ); + } +// not suppoted for S60 ver 3.2 +#if ( NCP_COMMON_S60_VERSION_SUPPORT != S60_VERSION_32 ) + + else if ( GSS_SELECTED_BANDS_WRITE == operation ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::GssCsServiceFailResp - ECustomSetBandSelectionIPC"); +OstTrace0( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_GSSCSSERVICEFAILRESP, "CMmCustomMessHandler::GssCsServiceFailResp - ECustomSetBandSelectionIPC" ); + iMessageRouter->Complete( ECustomSetBandSelectionIPC, KErrGeneral ); + } + else if ( GSS_SELECTED_BANDS_READ == operation ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::GssCsServiceFailResp - ECustomGetBandSelectionIPC"); +OstTrace0( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_GSSCSSERVICEFAILRESP, "CMmCustomMessHandler::GssCsServiceFailResp - ECustomGetBandSelectionIPC" ); + iMessageRouter->Complete( ECustomGetBandSelectionIPC, KErrGeneral ); + } +#endif // NCP_COMMON_S60_VERSION_SUPPORT + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccReadFieldReq +// Read given file from UICC +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccReadFieldReq( + RMmCustomAPI::TSimFileInfo& aSimFileInfo ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccReadFieldReq" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCREADFIELDREQ, "CMmCustomMessHandler::UiccReadFieldReq" ); + + // We have received only file path, file ID is two last bytes of path + TInt length( aSimFileInfo.iPath.Length() ); + TBuf8<2> temp; + if ( 2 <= length ) + { + temp.Append( aSimFileInfo.iPath.Mid( length - 2 ) ); + } + TUint16 fileId( static_cast ( (temp[0] << 8 ) | temp[1] ) ); + + // Set parameters for UICC_APPL_CMD_REQ message + TUiccReadTransparent params; + params.messHandlerPtr = static_cast( this ); + params.trId = ETrIdReadField; + params.dataAmount = aSimFileInfo.iSize; + params.dataOffset = aSimFileInfo.iOffSet; + params.fileId = fileId; + params.serviceType = UICC_APPL_READ_TRANSPARENT; + params.filePath = aSimFileInfo.iPath.Mid( 0, length - 2 ); + + return iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccReadFieldResp +// Complete read file +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccReadFieldResp( + TInt aStatus, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccReadFieldResp" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCREADFIELDRESP, "CMmCustomMessHandler::UiccReadFieldResp" ); + + TInt error( KErrNone ); + if ( aStatus != KErrNone ) + { + error = KErrNotFound; + } + + // Packed parameter for completion: pointer to TDesC8 with data + const TDesC8* dataPtr = &aFileData; + CMmDataPackage dataPackage; + dataPackage.PackData( &dataPtr ); + iMessageRouter->Complete( ECustomReadSimFileIPC, &dataPackage, error); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::NetRatReq +// Constructs NET_RAT_REQ ISI message from input parameters and +// sends it through phonet.This message is created to read Supported Net Rats +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::NetRatReq + ( + TUint8 aTransId, // transaction Id + TBool aUseCurrentRats // use current rats setting + ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::NetRatReq"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_NETRATREQ, "CMmCustomMessHandler::NetRatReq" ); + +TFLOGSTRING3( "TSY: CCMmCustomMessHandler::NetRatReq - aTransId: %d, aUseCurrentRats: %d", aTransId, aUseCurrentRats ); +OstTraceExt2( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_NETRATREQ, "CMmCustomMessHandler::NetRatReq;aTransId=%hhu;aUseCurrentRats=%hhu", aTransId, aUseCurrentRats ); + + // Create message data buffer for service type, buffer size is 1 + TBuf8<1> messageData; + // Append service type + if ( aUseCurrentRats ) + { + messageData.Append( NET_CURRENT_RAT ); + } + else + { + messageData.Append( NET_SUPPORTED_RATS ); + } + + // Sending message to phonet + return iPhoNetSender->Send( + PN_MODEM_NETWORK, + aTransId, + NET_RAT_REQ, + messageData ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::GssCsServiceReq +// Constructs GSS_CS_SERVICE_REQ ISI message from input parameters and +// sends it through phonet.This message is created to set System network mode +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::GssCsServiceReq + ( + TUint8 aTransId, //transaction Id + RMmCustomAPI::TNetworkModeCaps aNetworkModeCaps //network mode caps + ) + { + + TFLOGSTRING2( "TSY: CMmCustomMessHandler::GssCsServiceReq - aTransId: %d", + aTransId ); +OstTraceExt1( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_GSSCSSERVICEREQ, "CMmCustomMessHandler::GssCsServiceReq;aTransId=%hhu", aTransId ); + + // create message data buffer for service type, buffer size is 6 + TBuf8< KGssCsBufferSize > messageData; + + // append service type, GSS_SELECTED_RAT_WRITE (0x0E) + messageData.Append( GSS_SELECTED_RAT_WRITE ); + + // Number of sub blocks + messageData.Append( 1 ); + + // add the GSS_RAT_INFO (0x0B) subblock into ISI + messageData.Append( GSS_RAT_INFO ); + + // Length of sub block is 4 (SIZE_GSS_RAT_INFO) + messageData.Append( SIZE_GSS_RAT_INFO ); + + //Sub block for GSS_RAT_INFO_FUNCTIONS + if ( RMmCustomAPI::KCapsNetworkModeGsm == aNetworkModeCaps ) + { + // GSS_GSM_RAT (0x01) is GSM mode + messageData.Append( GSS_GSM_RAT ); + } + else if ( RMmCustomAPI::KCapsNetworkModeUmts == aNetworkModeCaps ) + { + // GSS_UMTS_RAT (0x02) is Umts mode + messageData.Append( GSS_UMTS_RAT ); + } + else + { + // GSS_DUAL_RAT (0x00) is Dual mode + messageData.Append( GSS_DUAL_RAT ); + } + + // Padding byte + messageData.Append( KCustomPadding ); + + // Sending message to phonet + return iPhoNetSender->Send( PN_GSS, aTransId, GSS_CS_SERVICE_REQ, messageData ); + + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::ExtFuncL +// Forwards requests coming from the Symbian OS layer to the +// specific method. +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::ExtFuncL + ( + TInt aIpc, //Ipc + const CMmDataPackage* aDataPackage //data package + ) + { + + //*************************************************************// + // NOTE + // + // LICENSEE SPECIFIC MESSAGE HANDLER IMPLEMENTATION STARTS HERE + // + //*************************************************************// + + TInt ret( KErrNone ); + + TUint8 transId = KCustomTransId; + + TFLOGSTRING2("TSY: CMmCustomMessHandler::ExtFuncL -- aIpc -- (%d)", aIpc ); +OstTrace1( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_EXTFUNCL, "CMmCustomMessHandler::ExtFuncL;aIpc=%d", aIpc ); + + switch ( aIpc ) + { + case ECustomCancelUssdSessionIPC: + { + //no packed parameters + ret = SsGsmUssdSendReq( transId ); + break; + } + case ECustomClearCallBlackListIPC: + { + //no packed parameters + ret = CallGsmBlackListClearReq( transId ); + break; + } + case ECustomCheckEmergencyNumberIPC: + { + // packed parameter: a RMmCustomAPI::TEmerNumberCheckMode + RMmCustomAPI::TEmerNumberCheckMode checkMode; + aDataPackage->UnPackData( checkMode ); + ret = CallEmergencyNbrCheckReq( transId, checkMode.iNumber, + checkMode.iCheckMode ); + break; + } + case ECustomTerminateCallIPC: + { + // packed parameters: pointer to an array of TInt (Call Id) + // and TBool isError + TInt callId; + TBool isError; + aDataPackage->UnPackData( callId, isError ); + + // map Custom API values to ISA values + // cause Value (error or user request) + TUint8 causeValue = + ( isError ? CALL_MODEM_CAUSE_ERROR_REQUEST : CALL_MODEM_CAUSE_RELEASE_BY_USER ); + + // call Id + TUint8 callIdISA = 0; + // martpiir 27-May-2004: This cannot remain, must be checked + // jlof 29-Sep-2004: "all calls" id was originally -2, but now + // negative or zero + // call id means all calls. Taking absolute value of it gives + // alerting call id. + if ( 0 >= callId ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::ExtFuncL -- ECustomTerminateCallIPC -- (hold+active+alerting)"); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_EXTFUNCL, "CMmCustomMessHandler::ExtFuncL - ECustomTerminateCallIPC - (hold+active+alerting)" ); + // alerting call (if any) is included as negated value.. + callIdISA = TUint8( CALL_MODEM_ID_HOLD | CALL_MODEM_ID_ACTIVE | ( -callId )); + } + else if ( 1 <= callId && 7 >= callId ) + { + TFLOGSTRING2("TSY: CMmCustomMessHandler::ExtFuncL -- ECustomTerminateCallIPC -- (%d)", TInt(callId) ); +OstTrace1( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_EXTFUNCL, "CMmCustomMessHandler::ExtFuncL;callId=%d", callId ); + callIdISA = static_cast( callId ); + } + else + { + // no call found + ret = KErrArgument; + } + + if ( KErrNone == ret ) + { + ret = CallReleaseReq( transId, callIdISA, causeValue ); + } + break; + } + case ECustomGetAlsBlockedIPC: + { + ret = UiccReadDynamic2FlagsReq(); + break; + } + case ECustomSetAlsBlockedIPC: + { + // Packed parameter: TSetAlsBlock (block status) + RMmCustomAPI::TSetAlsBlock blockStatus; + aDataPackage->UnPackData( blockStatus ); + + // Map Custom API values to ISA values + TUint8 blockStatusISA = static_cast( blockStatus ); + ret = UiccWriteDynamic2FlagsReq( blockStatusISA ); + break; + } + case ECustomCheckAlsPpSupportIPC: + { + //no packed parameters + // request type is used as transaction id. needed for + // completion. + ret = InfoPpReadReq( EGetAlsPPSupport ); + break; + } + case ECustomCheckTwoDigitDialSupportIPC: + { + //no packed parameters + // request type is used as transaction id. needed for + // completion. + ret = InfoPpReadReq( ECheckTwoDigitDialSupport ); + break; + } + case ECustomGetCipheringInfoIPC: + { + //no packed parameters + ret = UiccReadCiReq( ETrIdReadCipheringIndicatorStatusCustom ); + break; + } + case ECustomNetWakeupIPC: + { + //no packed parameters + ret = NetCsWakeupReq( transId ); + break; + } + case ECustomGetOperatorNameIPC: + { + //no packed parameters + ret = NetModemRegStatusGetReq( transId ); + break; + } + case ECustomResetNetServerIPC: + { + //no packed parameters + ret = NetSetReq( transId ); + break; + } + case ECustomGetNetworkProviderNameIPC: + { + ret = UiccOperatorReq(); + break; + } + case ECustomReadSimFileIPC: + { + //packed parameter: RMmCustomAPI::TSimFileInfo + RMmCustomAPI::TSimFileInfo simFileInfo; + aDataPackage->UnPackData( simFileInfo ); + ret = UiccReadFieldReq( simFileInfo ); + break; + } + case EMobilePhoneIMSAuthenticate: + { + ret = UiccHandleImsAuthentication( *aDataPackage ); + break; + } + case ECustomGetSimAuthenticationDataIPC: + { + ret = UiccSendAuthenticateApdu( *aDataPackage ); + break; + } + // Supported network modes + case ECustomGetSystemNetworkModesIPC: + { + TBool useCurrentRats; + aDataPackage->UnPackData( useCurrentRats ); + ret = NetRatReq( transId, useCurrentRats ); + break; + } + // Set system network mode + case ECustomSetSystemNetworkModeIPC: + { + RMmCustomAPI::TNetworkModeCaps networkModeCaps; + aDataPackage->UnPackData( networkModeCaps ); + ret = GssCsServiceReq( transId, networkModeCaps ); + break; + } +#ifdef INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING + // Current network modes + // Removed for Bridge camp! + case ECustomGetCurrentSystemNetworkModesIPC: + { + ret = MtcRatQueryReq( transId ); + break; + } +#endif /* INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING */ + + // Get GSM/WCDMA cell info + case ECustomGetCellInfoIPC: + { + iECIDInfoRequested = ETrue; + ret = NetNeighbourCellsReq( transId ); + break; + } + + case ECustomSimWarmResetIPC: + { + ret = UiccSimWarmResetReq(); + break; + } + + case ECustomGetATRIPC: + { + ret = UiccSimGetAtrReq(); + break; + } + + case ECustomGetSimCardReaderStatusIPC: + { + ret = UiccCardReaderStatusReq(); + break; + } + + case ECustomSendAPDUReqV2IPC: + { + // packed parameter: RMmCustomAPI::TApduParameters + RMmCustomAPI::TApduParameters apduParameters; + TInt traId( ETrIdSendAPDUv2 ); + + //Unpack aDataPackage + aDataPackage->UnPackData( apduParameters ); + + ret = UiccSendAPDUReq( apduParameters, traId); + break; + } + case ECustomPowerSimOnIPC: + { + ret = UiccSimPowerOnReq(); + break; + } + case ECustomPowerSimOffIPC: + { + ret = UiccSimPowerOffReq(); + break; + } + + case ECustomSendAPDUReqIPC: + { + // packed parameter: RMmCustomAPI::TApdu + RMmCustomAPI::TApdu apduData; + RMmCustomAPI::TApduParameters apduParameters; + TInt traId( ETrIdSendAPDU ); + + //Unpack aDataPackage + aDataPackage->UnPackData( apduData ); + + apduParameters.iCmdData.Append(*apduData.iData); + + ret = UiccSendAPDUReq( apduParameters, traId ); + break; + } + + //from MmSIMMessHandler + case ECustomStartSimCbTopicBrowsingIPC: + { + ret = UiccReadCbMsgIdsReq( ETrIdReadCbMsgIds ); + break; + } + case ECustomDeleteSimCbTopicIPC: + { + // packed parameter: TUint with topic id + aDataPackage->UnPackData( iSimCBTopicToBeDeleted, + iTopicInSimMemoryDelete ); + ret = UiccReadCbMsgIdsReq( ETrIdUpdateCbMsgIdsPhase1 ); + break; + } + case EReadViagHomeZoneParamsIPC: + { + ret = UiccReadViagHomeZoneParametersReq(); + break; + } + case EReadViagHomeZoneCacheIPC: + { + // packed parameter: RMmCustomAPI::TViagCacheRecordId + RMmCustomAPI::TViagCacheRecordId recordId; + aDataPackage->UnPackData( recordId ); + ret = UiccReadViagHomeZoneCacheReq( recordId ); + break; + } + case EWriteViagHomeZoneCacheIPC: + { + // packed parameters: RMmCustomAPI::TViagCacheRecordId + // and RMmCustomAPI::TViagCacheRecordContent + RMmCustomAPI::TViagCacheRecordId recordId; + RMmCustomAPI::TViagCacheRecordContent recordContent; + aDataPackage->UnPackData( recordId, recordContent ); + ret = UiccWriteViagHomeZoneCacheReq( recordId, recordContent ); + break; + } + //WCDMA HZ + case EWriteViagHomeZoneUHZIUESettingsIPC: + { + //Unpack the packed settings data + RMmCustomAPI::TViagUHZIUESettings settingUhziui; + aDataPackage->UnPackData( settingUhziui ); + ret = UiccWriteViagHomeZoneUhziueSettingsReq( settingUhziui ); + break; + } + case ECustomWriteHSxPAStatusIPC: + { + RMmCustomAPI::THSxPAStatus aStatus; + aDataPackage->UnPackData( aStatus ); + ret = WriteHSxPAStatusReq( transId, aStatus ); + break; + } + + case ECustomReadHSxPAStatusIPC: + { + ret = ReadHSxPAStatusReq( transId ); + break; + } + +// not suppoted for S60 ver 3.2 +#if ( NCP_COMMON_S60_VERSION_SUPPORT != S60_VERSION_32 ) + + // Set custom band selection + case ECustomSetBandSelectionIPC: + { + RMmCustomAPI::TNetworkModeCaps networkModeCaps; + RMmCustomAPI::TBandSelection bandSelection; + aDataPackage->UnPackData( bandSelection, networkModeCaps ); + + ret = GssCsServiceSetBandReq( transId, + networkModeCaps, + bandSelection ); + break; + } + + // Get custom band selection + case ECustomGetBandSelectionIPC: + { + ret = GssCsServiceGetBandReq( transId ); + break; + } + +#endif // NCP_COMMON_S60_VERSION_SUPPORT + + case EMmTsyUpdateLifeTimeIPC: + { + TTimeIntervalSeconds time; + aDataPackage->UnPackData( time ); + + ret = WriteLifeTimerToPermanentMemory( transId, time ); + + break; + } + + case ECustomGetLifeTimeIPC: + { + //no packed parameters + ret = GetTotalLifeTimerValue(); + break; + } + + default: + { + // this method should only be called for Custom Tsy cases + TFLOGSTRING2("TSY: CMmCustomMessHandler::ExtFuncL - Unknown IPC: %d", aIpc); +OstTrace1( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_EXTFUNCL, "CMmCustomMessHandler::ExtFuncL;aIpc=%d", aIpc ); + ret = KErrArgument; + break; + } + } + + return ret; + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::ProcessUiccMsg +// Handles data received from UICC server +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::ProcessUiccMsg( + TInt aTraId, + TInt aStatus, + const TDesC8& aFileData ) + { +TFLOGSTRING3("TSY: CMmCustomMessHandler::ProcessUiccMsg, transaction ID: %d, status: %d", aTraId, aStatus ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_PROCESSUICCMSG, "CMmCustomMessHandler::ProcessUiccMsg" ); + + TInt ret( KErrNone ); + + switch( aTraId ) + { + case ETrIdReadField: + { + UiccReadFieldResp( aStatus, aFileData ); + break; + } + case ETrIdReadCbMsgIds: + case ETrIdUpdateCbMsgIdsPhase1: + { + UiccReadCbMsgIdsResp( aStatus, aTraId, aFileData ); + break; + } + case ETrIdUpdateCbMsgIdsPhase2: + { + UiccDeleteCbMsgIdResp( aStatus ); + break; + } + case ETrIdReadCipheringIndicatorStatusCustom: + case ETrIdNotifyCipheringIndicatorStatusCustom: + { + UiccReadCiResp( aStatus, aTraId, aFileData ); + break; + } + case ETrIdReadOperatorNameCustom: + { + UiccOperatorResp( aStatus, aFileData ); + break; + } + case ETrIdReadViagHomeZoneParamsCustom: + { + UiccReadViagHomeZoneParametersResp( aStatus, aFileData ); + break; + } + case ETrIdReadViagHomeZoneCacheCustom: + { + UiccReadViagHomeZoneCacheResp( aStatus, aFileData ); + break; + } + case ETrIdWriteViagHomeZoneCacheCustom: + { + UiccWriteViagHomeZoneCacheResp( aStatus ); + break; + } + case ETrIdWriteViagHomeZoneUhziueSettingsCustom: + { + UiccWriteViagHomeZoneUhziueSettingsResp( aStatus ); + break; + } + case ETrIdReadDynamic2Flags: + { + UiccReadDynamic2FlagsResp( aStatus, aFileData ); + break; + } + case ETrIdWriteDynamic2Flags: + { + UiccWriteDynamic2FlagsResp( aStatus ); + break; + } + + case ETrIdSimPowerOff: + { + UiccSimPowerOffResp( aStatus ); + break; + } + + case ETrIdSimWarmReset: + { + UiccSimWarmResetResp( aStatus ); + break; + } + + case ETrIdSimGetATR: + { + UiccSimGetAtrResp( aStatus, aFileData ); + break; + } + + case ETrIdSimPowerOn: + { + UiccSimPowerOnResp( aStatus ); + break; + } + + case ETrIdSendAPDUv2: + case ETrIdSendAPDU: + { + UiccSendAPDUResp( aStatus, aFileData, aTraId ); + break; + } + + case ETrIdCardReaderStatus: + { + UiccCardReaderStatusResp( aStatus, aFileData ); + break; + } + case ETrIdEEapSimAuthenticate: + { + UiccGsmSecurityContextApduResp( aTraId, aStatus, aFileData ); + break; + } + case ETrIdEEapAkaAuthenticate: + case ETrIdEEapAkaAuthenticateIms: + { + Uicc3GSecurityContextApduResp( aTraId, aStatus, aFileData ); + break; + } + case ETrIdEGbaBootstrap: + { + UiccGBABootstrappingApduResp( aTraId, aStatus, aFileData ); + break; + } + case ETrIdEGbaBootstrapRead: + { + UiccGBABootstrapReadResp( aStatus, aFileData ); + break; + } + case ETrIdEGbaBootstrapUpdate: + { + UiccGBABootstrapUpdateResp( aStatus ); + break; + } + case ETrIdEGbaNafDerivation: + { + UiccGBANafDerivationApduResp( aTraId, aStatus, aFileData ); + break; + } + case ETrIdEMbmsMskUpdate: + { + UiccMbmsMskUpdateApduResp( aStatus, aFileData ); + break; + } + case ETrIdEMbmsMtkGeneration: + { + UiccMbmsMtkGenerationApduResp( aStatus, aFileData ); + break; + } + case ETrIdEMbmsMskDeletion: + { + UiccMbmsMskDeletionApduResp( aStatus, aFileData ); + break; + } + case ETrIdRunGsmAlgorithmSim: + case ETrIdRunGsmAlgorithmAka: + case ETrIdRunGsmAlgorithmIms: + { + UiccRunGsmAlgorithmApduResp( aTraId, aStatus, aFileData ); + break; + } + case ETrIdActivateIsimApplication: + { + UiccHandleIsimActivationResp( aStatus ); + break; + } + default: + { +TFLOGSTRING("TSY: CMmNetMessHandler::ProcessUiccMsg - unknown transaction ID" ); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_PROCESSUICCMSG, "CMmCustomMessHandler::ProcessUiccMsg - unknown transaction ID" ); + + break; + } + } + return ret; + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::MtcRatQueryReq +// Constructs MTC_RAT_QUERY_REQ ISI message from input parameters and +// sends it through phonet. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +#ifdef INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING +// Removed for Bridge camp +TInt CMmCustomMessHandler::MtcRatQueryReq + ( + TUint8 aTransId //transaction Id + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::MtcRatQueryReq.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_MTCRATQUERYREQ, "CMmCustomMessHandler::MtcRatQueryReq" ); + + TBuf8 messageData; + + //append padding bytes + messageData.Append( 0 ); + messageData.Append( 0 ); + + // Sending message to phonet + return iPhoNetSender->Send( PN_MTC, aTransId, MTC_RAT_QUERY_REQ, messageData ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::MtcRatQueryResp +// Breaks a MTC_RAT_QUERY_RESP ISI message. +// This method get the ratMode and complete the request with error value +// to SOS layer. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +// Removed for Bridge camp +void CMmCustomMessHandler::MtcRatQueryResp + ( + const TIsiReceiveC& aIsiMessage // Received isi message + ) + { + TInt ret ( KErrNone ); + + TUint32 ratMode ( RMmCustomAPI::KCapsNetworkModeDual ); + TUint8 mode = aIsiMessage.Get8bit( ISI_HEADER_SIZE + MTC_RAT_QUERY_RESP_OFFSET_RAT ); + +TFLOGSTRING3("TSY: CMmCustomMessHandler::MtcRatQueryResp. RatMode:%d, mode:%d", ratMode, mode); +OstTraceExt2( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_MTCRATQUERYRESP, "CMmCustomMessHandler::MtcRatQueryResp;mode=%hhu;ratMode=%u", mode, ratMode ); + + switch ( mode ) + { + case MTC_GSM_RAT: + { + ratMode = RMmCustomAPI::KCapsNetworkModeGsm; + break; + } + case MTC_UMTS_RAT: + { + ratMode = RMmCustomAPI::KCapsNetworkModeUmts; + break; + } + case MTC_NO_RAT_SELECTION: //this means dual mode + { + //value already initalized to dual + break; + } + default: // MTC_UNKNOWN_RAT + { + TFLOGSTRING("TSY: CMmCustomMessHandler::MtcRatQueryResp, switch mode - default.\n" ); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_MTCRATQUERYRESP, "CMmCustomMessHandler::MtcRatQueryResp, switch mode - default" ); + ret = KErrGeneral; + break; + } + } + + CMmDataPackage dataPackage; + dataPackage.PackData( &ratMode ); + + //completion ResetNetServer method (packed parameters) + iMessageRouter->Complete( ECustomGetCurrentSystemNetworkModesIPC, + &dataPackage, ret ); + + } +#endif /* INTERNAL_TESTING_OLD_IMPLEMENTATION_FOR_UICC_TESTING */ + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccReadViagHomeZoneParametersReq +// Read home zone parameters from UICC +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccReadViagHomeZoneParametersReq() + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccReadViagHomeZoneParametersReq" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCREADVIAGHOMEZONEPARAMETERSREQ, "CMmCustomMessHandler::UiccReadViagHomeZoneParametersReq" ); + + // Set parameters for UICC_APPL_CMD_REQ message + TUiccReadTransparent params; + params.messHandlerPtr = static_cast( this ); + params.trId = ETrIdReadViagHomeZoneParamsCustom; + params.dataAmount = 0; + params.dataOffset = 0; + params.fileId = KElemFileHomeZone; + params.serviceType = UICC_APPL_READ_TRANSPARENT; + + // File id path + params.filePath.Append( KMasterFileId >> 8 ); + params.filePath.Append( KMasterFileId ); + params.filePath.Append( KO2DedicatedFile >> 8 ); + params.filePath.Append( KO2DedicatedFile ); + + return iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccReadViagHomeZoneParametersResp +// Complete home zone parameters +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccReadViagHomeZoneParametersResp( + TInt aStatus, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccReadViagHomeZoneParametersResp" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCREADVIAGHOMEZONEPARAMETERSRESP, "CMmCustomMessHandler::UiccReadViagHomeZoneParametersResp" ); + + TInt error( KErrNone ); + if ( KErrNone == aStatus ) + { + TUint8 length( 0 ); + TUint8 i( 0 ); + TUint8 j( 0 ); + TUint8 index( 2 ); + + // Viag params, reset + iViagParams.iScp.Zero(); + iViagParams.iSmsC.Zero(); + iViagParams.iSubscribedZoneAndVersion = 0; + + // Set homezone subscription and version ( byte 1 ) + iViagParams.iSubscribedZoneAndVersion = aFileData[0]; + + // Set SMSC number ( 7 bytes, not include length ) + length = aFileData[1]; + for ( i = 0; i < length; i++ ) + { + iViagParams.iSmsC.Append( aFileData[index++] ); + } + + // Set SCP number + length = aFileData[9]; + index = 10; + for ( i = 0; i < length; i++ ) + { + iViagParams.iScp.Append( aFileData[index++] ); + } + + // Viag elements + RMmCustomAPI::TViagElements* viagElems( + new (ELeave) RMmCustomAPI::TViagElements + ( RMmCustomAPI::KViagElementCount ) ); + CleanupStack::PushL( viagElems ); + TUint8 elemDataIndex( 17 ); // Home zone elements stars from byte 18 + TUint32 tempCoordinate( 0 ); + + TUint8 byte1( 0 ); + TUint8 byte2( 0 ); + TUint8 byte3( 0 ); + TUint8 byte4( 0 ); + + // Set viag elements + for ( ; j < RMmCustomAPI::KViagElementCount; j++ ) + { + RMmCustomAPI::TViagElement elem; + // Set zone id + elem.iCoordinates.iZoneId = aFileData[ elemDataIndex ]; + + // Next four bytes are for x coordinate + byte1 = aFileData[++elemDataIndex]; + byte2 = aFileData[++elemDataIndex]; + byte3 = aFileData[++elemDataIndex]; + byte4 = aFileData[++elemDataIndex]; + + tempCoordinate = ( byte1 << 24 ) | + ( byte2 << 16 ) | + ( byte3 << 8 ) | + ( byte4 ); + elem.iCoordinates.iX = tempCoordinate; + + // Next four bytes are for y coordinate + byte1 = aFileData[++elemDataIndex]; + byte2 = aFileData[++elemDataIndex]; + byte3 = aFileData[++elemDataIndex]; + byte4 = aFileData[++elemDataIndex]; + + tempCoordinate = ( byte1 << 24 ) | + ( byte2 << 16 ) | + ( byte3 << 8 ) | + ( byte4 ); + elem.iCoordinates.iY = tempCoordinate; + + // Next four bytes are for r2 + byte1 = aFileData[++elemDataIndex]; + byte2 = aFileData[++elemDataIndex]; + byte3 = aFileData[++elemDataIndex]; + byte4 = aFileData[++elemDataIndex]; + + tempCoordinate = ( byte1 << 24 ) | + ( byte2 << 16 ) | + ( byte3 << 8 ) | + ( byte4 ); + elem.iCoordinates.iR2 = tempCoordinate; + + // Set active flag + // Bit 1 indicates homzone active + TBool isActive( + ( aFileData[++elemDataIndex] & KHomeZoneActiveBit ) ); + + if ( isActive ) + { + // Bit 2 indicates if an active homezone is marked as a cityzone + TBool isCityZone( + ( aFileData[elemDataIndex] & KCityZoneActiveBit ) ); + if ( isCityZone ) + { + elem.iActiveFlag = RMmCustomAPI::ECityZone; + } + else + { + elem.iActiveFlag = RMmCustomAPI::EHomeZone; + } + } + else + { + elem.iActiveFlag = RMmCustomAPI::ENotActive; + } + + // Set name (12 bytes) + elem.iName.Zero(); + for ( i = 0; i < 12; i++ ) + { + elem.iName.Append( aFileData[++elemDataIndex] ); + } + + viagElems->AppendL( elem ); + elemDataIndex++; + } + + // Complete + CMmDataPackage dataPackage; + dataPackage.PackData( &iViagParams, &viagElems ); + iMessageRouter->Complete( EReadViagHomeZoneParamsIPC, + &dataPackage, error ); + + //delete iViagElems; + CleanupStack::PopAndDestroy(viagElems); + } + else + { + // Complete with error value + iMessageRouter->Complete( + EReadViagHomeZoneParamsIPC, + KErrAccessDenied ); + } + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccReadVIAGHomeZoneCacheReq +// Read home zone cache +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccReadViagHomeZoneCacheReq( + const RMmCustomAPI::TViagCacheRecordId& aRecordId ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccReadViagHomeZoneCacheReq" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCREADVIAGHOMEZONECACHEREQ, "CMmCustomMessHandler::UiccReadViagHomeZoneCacheReq" ); + + TUint8 cacheId( aRecordId.iCacheId ); + TUint8 recordId( aRecordId.iRecordId ); + TUint16 fileId( 0 ); + + // The record numbers in SIM Server range from 1 to 21. Client's record + // numbers range from 0 to 20. We have to increase the index by one. + recordId++; + + // Define file ID according to cache ID + switch( cacheId ) + { + case 1: + { + fileId = KElemFileHomeZoneCache1; + break; + } + case 2: + { + fileId = KElemFileHomeZoneCache2; + break; + } + case 3: + { + fileId = KElemFileHomeZoneCache3; + break; + } + case 4: + { + fileId = KElemFileHomeZoneCache4; + break; + } + default: + { + break; + } + } + + // Set parameters for UICC_APPL_CMD_REQ message + TUiccReadLinearFixed params; + params.messHandlerPtr = static_cast( this ); + params.trId = ETrIdReadViagHomeZoneCacheCustom; + params.dataOffset = 0; + params.dataAmount = 0; + params.record = recordId; + + params.fileId = fileId; + params.fileIdSfi = UICC_SFI_NOT_PRESENT; + params.serviceType = UICC_APPL_READ_LINEAR_FIXED; + + // File id path + params.filePath.Append( KMasterFileId >> 8 ); + params.filePath.Append( KMasterFileId ); + params.filePath.Append( KO2DedicatedFile >> 8 ); + params.filePath.Append( KO2DedicatedFile ); + + return iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccReadViagHomeZoneCacheResp +// Complete home zone cache +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccReadViagHomeZoneCacheResp( + TInt aStatus, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccReadViagHomeZoneCacheResp" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCREADVIAGHOMEZONECACHERESP, "CMmCustomMessHandler::UiccReadViagHomeZoneCacheResp" ); + + TInt ret( KErrAccessDenied ); + + RMmCustomAPI::TViagCacheRecordContent viagRecord; + + if ( KErrNone == aStatus ) + { + viagRecord.iLac = ( aFileData[0] << 8 ) | aFileData[1]; + viagRecord.iCellId = ( aFileData[2] << 8 ) | aFileData[3]; + ret = KErrNone; + } + else + { + viagRecord.iLac = NULL; + viagRecord.iCellId = NULL; + } + + // Complete, packed parameter: RMmCustomAPI::TViagCacheRecordContent + CMmDataPackage dataPackage; + dataPackage.PackData( &viagRecord ); + iMessageRouter->Complete( EReadViagHomeZoneCacheIPC, &dataPackage, ret ); + + return; + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccWriteVIAGHomeZoneCacheReq +// Write home zone cache +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccWriteViagHomeZoneCacheReq( + const RMmCustomAPI::TViagCacheRecordId& aRecordId, + const RMmCustomAPI::TViagCacheRecordContent& aViagRecordContent ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccWriteViagHomeZoneCacheReq" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCWRITEVIAGHOMEZONECACHEREQ, "CMmCustomMessHandler::UiccWriteViagHomeZoneCacheReq" ); + + TUint8 cacheId( (TUint8)aRecordId.iCacheId ); + TUint8 recordId( (TUint8)aRecordId.iRecordId ); + TUint16 lac( (TUint16)aViagRecordContent.iLac ); + TUint16 cellId( (TUint16)aViagRecordContent.iCellId ); + TUint16 fileId( 0 ); + + // The record numbers in SIM Server range from 1 to 21. Client's record + // numbers range from 0 to 20. We have to shift the index by one. + recordId++; + + // Define file ID according to cache ID + switch( cacheId ) + { + case 1: + { + fileId = KElemFileHomeZoneCache1; + break; + } + case 2: + { + fileId = KElemFileHomeZoneCache2; + break; + } + case 3: + { + fileId = KElemFileHomeZoneCache3; + break; + } + case 4: + { + fileId = KElemFileHomeZoneCache4; + break; + } + default: + { + break; + } + } + + // Set parameters for UICC_APPL_CMD_REQ message + TUiccWriteLinearFixed params; + params.messHandlerPtr = static_cast( this ); + params.trId = ETrIdWriteViagHomeZoneCacheCustom; + params.dataOffset = 0; + params.dataAmount = 0; + params.record = recordId; + + params.fileId = fileId; + params.fileIdSfi = UICC_SFI_NOT_PRESENT; + params.serviceType = UICC_APPL_UPDATE_LINEAR_FIXED; + + // File id path + params.filePath.Append( KMasterFileId >> 8 ); + params.filePath.Append( KMasterFileId ); + params.filePath.Append( KO2DedicatedFile >> 8 ); + params.filePath.Append( KO2DedicatedFile ); + + // File data to be updated. + TBuf8<4> fileDataBuf; + fileDataBuf.Append( lac >> 8 ); + fileDataBuf.Append( lac & 0x00FF ); + fileDataBuf.Append( cellId >> 8); + fileDataBuf.Append( cellId & 0x00FF ); + params.fileData.Append( fileDataBuf ); + + return iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccWriteViagHomeZoneCacheResp +// Complete home zone cache +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccWriteViagHomeZoneCacheResp( TInt aStatus ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccWriteViagHomeZoneCacheResp" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCWRITEVIAGHOMEZONECACHERESP, "CMmCustomMessHandler::UiccWriteViagHomeZoneCacheResp" ); + + if ( KErrNone == aStatus ) + { + iMessageRouter->Complete( EWriteViagHomeZoneCacheIPC, KErrNone ); + } + else + { + iMessageRouter->Complete( EWriteViagHomeZoneCacheIPC, KErrGeneral ); + } + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccWriteViagHomeZoneUhziueSettingsReq +// Write home zone settings to UICC +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccWriteViagHomeZoneUhziueSettingsReq( + const RMmCustomAPI::TViagUHZIUESettings& aUhziuiSettings ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccWriteViagHomeZoneUhziueSettingsReq" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCWRITEVIAGHOMEZONEUHZIUESETTINGSREQ, "CMmCustomMessHandler::UiccWriteViagHomeZoneUhziueSettingsReq" ); + + TUint8 settingsField( aUhziuiSettings.iSettings ); + TUint8 versionField( aUhziuiSettings.iVersion ); + + // Set parameters for UICC_APPL_CMD_REQ message + TUiccWriteTransparent params; + params.messHandlerPtr = static_cast( this ); + params.trId = ETrIdWriteViagHomeZoneUhziueSettingsCustom; + params.dataOffset = 0; + + params.fileId = KElemFileUhziueSettings; + params.fileIdSfi = UICC_SFI_NOT_PRESENT; + params.serviceType = UICC_APPL_UPDATE_TRANSPARENT; + + // File id path + params.filePath.Append( KMasterFileId >> 8 ); + params.filePath.Append( KMasterFileId ); + params.filePath.Append( KO2DedicatedFile >> 8 ); + params.filePath.Append( KO2DedicatedFile ); + + // File data to be updated. + TBuf8<2> fileDataBuf; + fileDataBuf.Append( settingsField ); + fileDataBuf.Append( versionField); + params.fileData.Append( fileDataBuf ); + + return iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccWriteViagHomeZoneUhziueSettingsResp +// Complete home zone settings +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccWriteViagHomeZoneUhziueSettingsResp( + TInt aStatus ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccWriteViagHomeZoneUhziueSettingsResp" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCWRITEVIAGHOMEZONEUHZIUESETTINGSRESP, "CMmCustomMessHandler::UiccWriteViagHomeZoneUhziueSettingsResp" ); + + TInt status( KErrAccessDenied ); + + if ( KErrNone == aStatus ) + { + status = KErrNone; + } + iMessageRouter->Complete( EWriteViagHomeZoneUHZIUESettingsIPC, status ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccReadCbMsgIdsReq +// Read CB message IDs from UICC +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccReadCbMsgIdsReq( TUiccTrId aTrId ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccReadCbMsgIdsReq" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCREADCBMSGIDSREQ, "CMmCustomMessHandler::UiccReadCbMsgIdsReq" ); + + // Set parameters for UICC_APPL_CMD_REQ message + TUiccReadTransparent params; + params.messHandlerPtr = static_cast( this ); + params.trId = aTrId; + params.dataOffset = 0; + params.dataAmount = 0; + params.fileId = KElemFileCellBroadcastMessId; + params.fileIdSfi = UICC_SFI_NOT_PRESENT; + params.serviceType = UICC_APPL_READ_TRANSPARENT; + + // File id path + params.filePath.Append( KMasterFileId >> 8 ); + params.filePath.Append( KMasterFileId ); + params.filePath.Append( iMmUiccMessHandler->GetApplicationFileId() ); + + return iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccReadCbMsgIdsResp +// Complete CB message IDs +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccReadCbMsgIdsResp( + TInt aStatus, + TInt aTraId, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccReadCbMsgIdsResp" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCREADCBMSGIDSRESP, "CMmCustomMessHandler::UiccReadCbMsgIdsResp" ); + + TInt numOfCbIds( 0 ); + // File data in bytes + TInt length( aFileData.Length() ); + // Divide by two to get number of 16-bit CB ids + numOfCbIds = length >> 1; + // Buffer for 16 bits CB identifiers + TBuf16 cbIds; + TInt i( 0 ); + TInt j( 0 ); + // Loop all the bytes and append 16 bit id to buffer + for ( ; i < length && j < numOfCbIds; i += 2, j++ ) + { + TUint16 cbId ( ( aFileData[i] << 8 ) | ( aFileData[i+1] ) ); + cbIds.Append( cbId ); + } + // Read request, complete CB topic list to CTSY + if ( KErrNone == aStatus && ETrIdReadCbMsgIds == aTraId && numOfCbIds > 0 ) + { + CArrayFixFlat* simCbTopics = new ( ELeave ) + CArrayFixFlat ( numOfCbIds ); + + for ( i = 0; i < numOfCbIds; i++ ) + { + if ( KUnusedCbMsgId != cbIds[i] ) + { + RMmCustomAPI::TSimCbTopic simCbTopic; + // CB ID + simCbTopic.iNumber = cbIds[i]; + // Topic names are not stored on the SIM + simCbTopic.iName.Zero(); + // Add CB topic to array + simCbTopics->AppendL( simCbTopic ); + } + } + simCbTopics->Compress(); + + // Complete to SOS layer with packed parameter: + // pointer to array with CB topics + CMmDataPackage dataPackage; + dataPackage.PackData( &simCbTopics ); + + iMessageRouter->Complete( + ECustomStartSimCbTopicBrowsingIPC, + &dataPackage, + KErrNone ); + } + // Delete request, update EF CBMI with new topic list + else if ( KErrNone == aStatus && ETrIdUpdateCbMsgIdsPhase1 == aTraId && + numOfCbIds > 0 && iTopicInSimMemoryDelete ) + { + // Set parameters for UICC_APPL_CMD_REQ message + TUiccWriteTransparent params; + params.messHandlerPtr = static_cast( this ); + params.trId = ETrIdUpdateCbMsgIdsPhase2; + params.dataOffset = 0; + params.fileId = KElemFileCellBroadcastMessId; + params.fileIdSfi = UICC_SFI_NOT_PRESENT; + params.serviceType = UICC_APPL_UPDATE_TRANSPARENT; + + // File id path + params.filePath.Append( KMasterFileId >> 8 ); + params.filePath.Append( KMasterFileId ); + params.filePath.Append( iMmUiccMessHandler->GetApplicationFileId() ); + + // File data to be updated. + TBuf8 fileDataBuf; + for ( i = 0; i < numOfCbIds; i++ ) + { + if ( cbIds[ i ] != iSimCBTopicToBeDeleted ) + { + fileDataBuf.Append( cbIds[ i ] >> 8 ); // MSB + fileDataBuf.Append( cbIds[ i ] & 0x00FF ); // LSB + } + else // This CB id is deleted-> set unused + { + fileDataBuf.Append( 0xFF ); + fileDataBuf.Append( 0xFF ); + } + } + iSimCBTopicToBeDeleted = KUnusedCbMsgId; + params.fileData.Append( fileDataBuf ); + iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + else // Complete error values + { + if ( ETrIdReadCbMsgIds == aTraId ) + { + iMessageRouter->Complete( + ECustomStartSimCbTopicBrowsingIPC, + KErrNotFound ); + } + else // Delete request + { + iMessageRouter->Complete( + ECustomDeleteSimCbTopicIPC, + KErrNotFound ); + } + iTopicInSimMemoryDelete = ETrue; + } + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccDeleteCbMsgIdResp +// Delete CB message ID +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccDeleteCbMsgIdResp( TInt aStatus ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccDeleteCbMsgIdResp" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCDELETECBMSGIDRESP, "CMmCustomMessHandler::UiccDeleteCbMsgIdResp" ); + + TInt err( KErrNone ); + if ( KErrNone != aStatus ) + { + err = KErrAccessDenied; + } + + iMessageRouter->Complete( ECustomDeleteSimCbTopicIPC, err ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::WriteHSxPAStatusReq +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::WriteHSxPAStatusReq + ( + TUint8 aTraId, // Transaction identification + RMmCustomAPI::THSxPAStatus status // HSxPA status + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::WriteHSxPAStatusReq"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_WRITEHSXPASTATUSREQ, "CMmCustomMessHandler::WriteHSxPAStatusReq" ); + + TBuf8 data; + TUint8 value(0); + + if ( RMmCustomAPI::EHSxPAEnabled == status ) + { + value = GSS_HSXPA_ALLOWED; + } + else // ( RMmCustomAPI::EHSxPADisabled == status ) + { + value = GSS_HSXPA_DISABLED; + } + + data.Append( value ); + data.Append( KCustomPadding ); //Filler + + return iPhoNetSender->Send( PN_GSS, + aTraId, + GSS_HSXPA_USER_SETTING_WRITE_REQ, + data ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::WriteHSxPAStatusResp +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::WriteHSxPAStatusResp + ( + const TIsiReceiveC& aIsiMessage // an ISI message + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::WriteHSxPAStatusResp"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_WRITEHSXPASTATUSRESP, "CMmCustomMessHandler::WriteHSxPAStatusResp" ); + + TInt epocError( KErrWrite ); + + TUint8 writeStatus = aIsiMessage.Get8bit( + ISI_HEADER_SIZE + GSS_HSXPA_USER_SETTING_WRITE_RESP_OFFSET_WRITESTATUS ); + + TUint8 reason = aIsiMessage.Get8bit( + ISI_HEADER_SIZE + GSS_HSXPA_USER_SETTING_WRITE_RESP_OFFSET_FAILCAUSE ); + + if ( GSS_OK == writeStatus ) + { + epocError = KErrNone; + } + // GSS_FAIL == writeStatus and PP bit is disabled + else if ( GSS_HSXPA_DISABLED_VIA_PP == reason ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::WriteHSxPAStatusResp. KErrNotSupported"); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_WRITEHSXPASTATUSRESP, "CMmCustomMessHandler::WriteHSxPAStatusResp, KErrNotSupported" ); + epocError = KErrNotSupported; + } + + iMessageRouter->Complete( ECustomWriteHSxPAStatusIPC, epocError ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::ReadHSxPAStatusReq +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::ReadHSxPAStatusReq + ( + TUint8 aTraId // Transaction identification + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::ReadHSxPAStatusReq"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_READHSXPASTATUSREQ, "CMmCustomMessHandler::ReadHSxPAStatusReq" ); + + TBuf8 data; + data.Append( KCustomPadding ); //Filler + data.Append( KCustomPadding ); //Filler + + return iPhoNetSender->Send( PN_GSS, + aTraId, + GSS_HSXPA_USER_SETTING_READ_REQ, + data ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::ReadHSxPAStatusResp +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::ReadHSxPAStatusResp + ( + const TIsiReceiveC& aIsiMessage // an ISI message + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::ReadHSxPAStatusResp"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_READHSXPASTATUSRESP, "CMmCustomMessHandler::ReadHSxPAStatusResp" ); + + CMmDataPackage dataPackage; + + TUint8 state = aIsiMessage.Get8bit( + ISI_HEADER_SIZE + GSS_HSXPA_USER_SETTING_READ_RESP_OFFSET_HSXPAUSERSETTING ); + TUint8 causeBit = aIsiMessage.Get8bit( + ISI_HEADER_SIZE + GSS_HSXPA_USER_SETTING_READ_RESP_OFFSET_CAUSE ); + + RMmCustomAPI::THSxPAStatus hsxpaStatus; + TInt epocError( KErrNone ); + + if ( GSS_HSXPA_DISABLED_VIA_PP != causeBit ) + { + + if ( GSS_HSXPA_ALLOWED == state ) + { + hsxpaStatus = RMmCustomAPI::EHSxPAEnabled; + } + else if ( GSS_HSXPA_DISABLED == state ) + { + hsxpaStatus = RMmCustomAPI::EHSxPADisabled; + } + else //default -> general error occurs + { + epocError = KErrGeneral; + } + + // complete with packed parameter + dataPackage.PackData( &hsxpaStatus ); + } + else // PPbit is disabled -> not supported + { + epocError = KErrNotSupported; + } + + iMessageRouter->Complete( ECustomReadHSxPAStatusIPC, &dataPackage, epocError ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::HSxPASettingInd +// This method breaks the GSS_HSXPA_SETTING_IND ISI. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::HSxPASettingInd + ( + const TIsiReceiveC& aIsiMessage // an ISI message + ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::HSxPASettingInd"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_HSXPASETTINGIND, "CMmCustomMessHandler::HSxPASettingInd" ); + + CMmDataPackage dataPackage; + RMmCustomAPI::THSxPAStatus hsxpaStatus; + + TUint8 currentState = aIsiMessage.Get8bit( + ISI_HEADER_SIZE + GSS_HSXPA_USER_SETTING_IND_OFFSET_HSXPAUSERSETTING ); + + if ( GSS_HSXPA_ALLOWED == currentState ) + { + hsxpaStatus = RMmCustomAPI::EHSxPAEnabled; + } + else // ( GSS_HSXPA_DISABLED == currentState ) + { + hsxpaStatus = RMmCustomAPI::EHSxPADisabled; + } + + // complete with packed parameter + dataPackage.PackData( &hsxpaStatus ); + iMessageRouter->Complete( ECustomNotifyHSxPAStatusIPC, &dataPackage, KErrNone ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::NetNeighbourCellsReq +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::NetNeighbourCellsReq( const TUint8 aTraId ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::NetNeighbourCellsReq"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_NETNEIGHBOURCELLSREQ, "CMmCustomMessHandler::NetNeighbourCellsReq" ); + + // Add NET_NEIGHBOUR_CELL_INFO_TYPE + // (data size is allways 1) + TBuf8<1> data; + data.Append( NET_ECID_INFORMATION ); + + return iPhoNetSender->Send( + PN_MODEM_NETWORK, + aTraId, + NET_NEIGHBOUR_CELLS_REQ, + data ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::NetNeighbourCellsResp +// This method breaks the NET_NEIGHBOUR_CELLS_RESP message. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::NetNeighbourCellsResp( + const TIsiReceiveC& aIsiMessage ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::NetNeighbourCellsResp"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_NETNEIGHBOURCELLSRESP, "CMmCustomMessHandler::NetNeighbourCellsResp" ); + + TECIDInfo tempECIDInfo; + TInt ret( KErrNone ); + + // Get the success code. + TUint8 successCode( aIsiMessage.Get8bit( + ISI_HEADER_SIZE + + NET_NEIGHBOUR_CELLS_RESP_OFFSET_SUCCESSCODE ) ); + + if ( NET_CAUSE_OK == successCode ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::NetNeighbourCellsResp - NET_CAUSE_OK"); +OstTrace0( TRACE_NORMAL, DUP5_CMMCUSTOMMESSHANDLER_NETNEIGHBOURCELLSRESP, "CMmCustomMessHandler::NetNeighbourCellsResp, NET_CAUSE_OK" ); + + TUint sbOffset( 0 ); + + if ( KErrNone == aIsiMessage.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_NET_NEIGHBOUR_CELLS_RESP, + NET_ECID_GERAN_INFO, + EIsiSubBlockTypeId8Len8, + sbOffset ) ) + { + // GSM cell info. +TFLOGSTRING("TSY: CMmCustomMessHandler::NetNeighbourCellsResp - NET_ECID_GERAN_INFO found"); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_NETNEIGHBOURCELLSRESP, "CMmCustomMessHandler::NetNeighbourCellsResp - NET_ECID_GERAN_INFO found" ); + // Set mode + tempECIDInfo.iCellInfo.iMode = RMmCustomAPI::TMmCellInfo::EGSM; + + // Set Current MCC. + tempECIDInfo.iMCC = aIsiMessage.Get16bit( + sbOffset + NET_ECID_GERAN_INFO_OFFSET_CURRENTMCC ); + + // Set Current MNC. + tempECIDInfo.iMNC = aIsiMessage.Get16bit( + sbOffset + NET_ECID_GERAN_INFO_OFFSET_CURRENTMNC ); + + // Set Current LAC. + tempECIDInfo.iLAC = aIsiMessage.Get16bit( + sbOffset + NET_ECID_GERAN_INFO_OFFSET_CURRENTLAC ); + + // Set Current Cell ID. + tempECIDInfo.iCID = aIsiMessage.Get16bit( + sbOffset + NET_ECID_GERAN_INFO_OFFSET_CURRENTCELLID ); + + // Set Current TA. + TUint8 temp8bitUVal( aIsiMessage.Get8bit( + sbOffset + NET_ECID_GERAN_INFO_OFFSET_CURRENTTA ) ); + + if ( NET_ECID_TA_UNDEFINED != temp8bitUVal ) + { + tempECIDInfo.iCellInfo.iGsmCellInfo.iTA = temp8bitUVal; + } + // No else. + + // Get Number of Neighbours included. + TUint8 nmrCount( aIsiMessage.Get8bit( + sbOffset + NET_ECID_GERAN_INFO_OFFSET_NNMR ) ); + + // Set NMR list. + for ( TUint8 i = 0; i < nmrCount; i++ ) + { + // Set Carrier number. + tempECIDInfo.iCellInfo.iGsmCellInfo.iNmr[ i ].iARFCN = + aIsiMessage.Get16bit( + sbOffset + NET_ECID_GERAN_INFO_OFFSET_GSMNMRLIST + + ( i * SIZE_NET_GSM_NMR_LIST_SEQ ) + + NET_GSM_NMR_LIST_SEQ_OFFSET_ARFCN ); + // Set BSIC. + tempECIDInfo.iCellInfo.iGsmCellInfo.iNmr[ i ].iBSIC = + aIsiMessage.Get8bit( + sbOffset + NET_ECID_GERAN_INFO_OFFSET_GSMNMRLIST + + ( i * SIZE_NET_GSM_NMR_LIST_SEQ ) + + NET_GSM_NMR_LIST_SEQ_OFFSET_BSIC ); + // Set RX level. + tempECIDInfo.iCellInfo.iGsmCellInfo.iNmr[ i ].iRxLEV = + aIsiMessage.Get8bit( + sbOffset + NET_ECID_GERAN_INFO_OFFSET_GSMNMRLIST + + ( i * SIZE_NET_GSM_NMR_LIST_SEQ ) + + NET_GSM_NMR_LIST_SEQ_OFFSET_RXLEVEL ); + } + } + else if ( KErrNone == aIsiMessage.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_NET_NEIGHBOUR_CELLS_RESP, + NET_ECID_UTRAN_FDD_INFO, + EIsiSubBlockTypeId8Len16, + sbOffset ) ) + { + // WCDMA cell info. +TFLOGSTRING("TSY: CMmCustomMessHandler::NetNeighbourCellsResp - NET_ECID_UTRAN_FDD_INFO found"); +OstTrace0( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_NETNEIGHBOURCELLSRESP, "CMmCustomMessHandler::NetNeighbourCellsResp - NET_ECID_UTRAN_FDD_INFO found" ); + // Set mode. + tempECIDInfo.iCellInfo.iMode = RMmCustomAPI::TMmCellInfo::EWCDMA; + + // Set UCID. + tempECIDInfo.iCID = aIsiMessage.Get32bit( + sbOffset + NET_ECID_UTRAN_FDD_INFO_OFFSET_UCID ); + + // Set current MCC. + tempECIDInfo.iMCC = aIsiMessage.Get16bit( + sbOffset + NET_ECID_UTRAN_FDD_INFO_OFFSET_CURRENTMCC ); + + // Set current MNC. + tempECIDInfo.iMNC = aIsiMessage.Get16bit( + sbOffset + NET_ECID_UTRAN_FDD_INFO_OFFSET_CURRENTMNC ); + + // Set current LAC (new value not received here). + tempECIDInfo.iLAC = iECIDInfo.iLAC; + + // Set primary scrambling code. + tempECIDInfo.iCellInfo.iWcdmaCellInfo.iPrimaryScrambilingCode = + aIsiMessage.Get16bit( + sbOffset + NET_ECID_UTRAN_FDD_INFO_OFFSET_PRISCRAMBLING ); + + // Set Frequency Info. + // Set frequency Info (Uplink UARFCN and UARFCN-Nt not available) + // Downlink UARFCN. + tempECIDInfo.iCellInfo.iWcdmaCellInfo.iFrequencyInfo.iFddDL = + aIsiMessage.Get16bit( + sbOffset + NET_ECID_UTRAN_FDD_INFO_OFFSET_UARFCNDL ); + + // Get number of neighbours included. + TUint8 nmrCount( aIsiMessage.Get8bit( + sbOffset + NET_ECID_UTRAN_FDD_INFO_OFFSET_NNMR ) ); + + // Set nmrListOffset to starting position of first NMR list. + TUint nmrListOffset( + sbOffset + NET_ECID_UTRAN_FDD_INFO_OFFSET_WCDMANMRLIST ); + + // Handle NMR lists. + for ( TUint8 i( 0 ); i < nmrCount; i++ ) + { + // Set Frequency Info: Downlink UARFCN. + tempECIDInfo.iCellInfo.iWcdmaCellInfo. + iNwkMeasureReport[i].iFrequencyInfo.iFddDL = + aIsiMessage.Get16bit( nmrListOffset ); + + // Uplink UARFCN and UARFCN-Nt not available, set to -1. + tempECIDInfo.iCellInfo.iWcdmaCellInfo. + iNwkMeasureReport[i].iFrequencyInfo.iFddUL = -1; + tempECIDInfo.iCellInfo.iWcdmaCellInfo. + iNwkMeasureReport[i].iFrequencyInfo.iTddNt = -1; + + // Set UTRA Carrier RSSI. + tempECIDInfo.iCellInfo.iWcdmaCellInfo. + iNwkMeasureReport[i].iCarrierRSSI = + aIsiMessage.Get8bit( + nmrListOffset + + NET_UTRAN_NEIGH_LIST_SEQ_OFFSET_UCRSSI ); + + // Get number of cells included. + TUint8 cellCount( aIsiMessage.Get8bit( + nmrListOffset + NET_UTRAN_NEIGH_LIST_SEQ_OFFSET_NCELL ) ); + + // Set nmrListOffset to starting position of first 'detailed + // cell information'. + nmrListOffset += 4; + + // Handle detailed cell information. + for ( TUint8 f( 0 ); f < cellCount; f++ ) + { + // Set UCID. + TUint32 temp32bitUVal( + aIsiMessage.Get32bit( nmrListOffset ) ); + + if ( NET_ECID_UCID_UNDEFINED != temp32bitUVal ) + { + tempECIDInfo.iCellInfo.iWcdmaCellInfo. + iNwkMeasureReport[i].iCellMeasuredResult[f].iCID = + temp32bitUVal; + } + // No else. + + // Set Primary CPICH. + tempECIDInfo.iCellInfo.iWcdmaCellInfo. + iNwkMeasureReport[i].iCellMeasuredResult[f]. + iFddInfo.iPrimaryCPICH = aIsiMessage.Get16bit( + nmrListOffset + + NET_UTRAN_CELL_LIST_SEQ_OFFSET_PCPICH ); + + // Set CPICH Ec NO. + TUint8 temp8bitUVal( aIsiMessage.Get8bit( + nmrListOffset + + NET_UTRAN_CELL_LIST_SEQ_OFFSET_CPICHECNO ) ); + + if ( NET_ECID_CPICH_ECNO_UNDEFINED != temp8bitUVal ) + { + tempECIDInfo.iCellInfo.iWcdmaCellInfo. + iNwkMeasureReport[i].iCellMeasuredResult[f]. + iFddInfo.iCpichEcN0 = temp8bitUVal; + } + // No else. + + // Set CPICH RSCP. + tempECIDInfo.iCellInfo.iWcdmaCellInfo. + iNwkMeasureReport[i].iCellMeasuredResult[f]. + iFddInfo.iCpichRscp = aIsiMessage.Get8bit( + nmrListOffset + + NET_UTRAN_CELL_LIST_SEQ_OFFSET_CPICHRSCP ); + + // Set Pathloss. + temp8bitUVal = aIsiMessage.Get8bit( + nmrListOffset + + NET_UTRAN_CELL_LIST_SEQ_OFFSET_PATHLOSS ); + + if ( NET_ECID_PATHLOSS_UNDEFINED != temp8bitUVal ) + { + tempECIDInfo.iCellInfo.iWcdmaCellInfo. + iNwkMeasureReport[i].iCellMeasuredResult[f]. + iFddInfo.iPathloss = temp8bitUVal; + } + // No else. + + // Increase nmrListOffset to starting point of the next + // element of 'detailed cell information'. + nmrListOffset += SIZE_NET_UTRAN_CELL_LIST_SEQ; + } + } + } + else + { +TFLOGSTRING("TSY: CMmCustomMessHandler::NetNeighbourCellsResp - No ECID data found"); +OstTrace0( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_NETNEIGHBOURCELLSRESP, "CMmCustomMessHandler::NetNeighbourCellsResp - No ECID data found" ); + ret = KErrNotFound; + } + } + else + { +TFLOGSTRING2("TSY: CMmCustomMessHandler::NetNeighbourCellsResp - NET Server Error, Success Code: %d", successCode); +OstTraceExt1( TRACE_NORMAL, DUP4_CMMCUSTOMMESSHANDLER_NETNEIGHBOURCELLSRESP, "CMmCustomMessHandler::NetNeighbourCellsResp;NET Server Error, Success Code=%hhu", successCode ); + + // Map cause to symbian error value. + ret = CMmStaticUtility::CSCauseToEpocError( + PN_MODEM_NETWORK, + KTsyNetCauseCommon, + successCode ); + } + + // Complete get request. + if ( iECIDInfoRequested ) + { + iECIDInfoRequested = EFalse; + + // Complete with packed parameter. + CMmDataPackage dataPackage; + dataPackage.PackData( &tempECIDInfo.iCellInfo ); + + iMessageRouter->Complete( + ECustomGetCellInfoIPC, + &dataPackage, + ret ); + } + // No else. + + // If info received, save and complete change notification. + if ( KErrNone == ret ) + { + if ( iECIDInfo.iCellInfo.iMode != tempECIDInfo.iCellInfo.iMode || + iECIDInfo.iMCC != tempECIDInfo.iMCC || + iECIDInfo.iMNC != tempECIDInfo.iMNC || + iECIDInfo.iCID != tempECIDInfo.iCID || + iECIDInfo.iLAC != tempECIDInfo.iLAC ) + { + // Complete with packed parameter. + CMmDataPackage dataPackage; + dataPackage.PackData( &tempECIDInfo.iCellInfo ); + + iMessageRouter->Complete( + ECustomNotifyCellInfoChangeIPC, + &dataPackage, + KErrNone ); + } + // No else. + + // Save ECID information. + iECIDInfo = tempECIDInfo; + } + // No else. + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::CheckECIDInfo +// This method breaks received NET_MODEM_REG_STATUS_IND or +// NET_MODEM_REG_STATUS_GET_RESP message and checks if enhanced cell +// information is chaged ( => needs to be requested/updated ). +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::CheckECIDInfo( + const TIsiReceiveC& aIsiMessage ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::CheckECIDInfo"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_CHECKECIDINFO, "CMmCustomMessHandler::CheckECIDInfo" ); + + TUint8 msgId( aIsiMessage.Get8bit( ISI_HEADER_OFFSET_MESSAGEID ) ); + + if ( NET_MODEM_REG_STATUS_IND == msgId || + NET_MODEM_REG_STATUS_GET_RESP == msgId ) + { + // Check if cell information needs to be updated. + TBool isNetRetStatusInd( NET_MODEM_REG_STATUS_IND == msgId ); + +TFLOGSTRING("TSY:CMmCustomMessHandler::CheckECIDInfo - Find NET_MODEM_CURRENT_CELL_INFO SubBlock"); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_CHECKECIDINFO, "CMmCustomMessHandler::CheckECIDInfo - Find NET_MODEM_CURRENT_CELL_INFO SubBlock" ); + // Get NET_MODEM_CURRENT_CELL_INFO sub block + // (should be always used when exists (coming when in 3G/RRC + // connected mode), otherwise NET_MODEM_GSM_REG_INFO is used). + + TUint sbStartOffSet( 0 ); + TInt retValue( KErrNone ); + + if ( isNetRetStatusInd ) + { + retValue = aIsiMessage.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_NET_MODEM_REG_STATUS_IND, + NET_MODEM_CURRENT_CELL_INFO, + EIsiSubBlockTypeId8Len8, + sbStartOffSet ); + } + else + { + retValue = aIsiMessage.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_NET_MODEM_REG_STATUS_GET_RESP, + NET_MODEM_CURRENT_CELL_INFO, + EIsiSubBlockTypeId8Len8, + sbStartOffSet ); + } + + // Get NET_MODEM_GSM_REG_INFO sub block. + if ( KErrNone != retValue ) + { +TFLOGSTRING("TSY:CMmCustomMessHandler::CheckECIDInfo - Find NET_MODEM_GSM_REG_INFO SubBlock"); +OstTrace0( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_CHECKECIDINFO, "CMmCustomMessHandler::CheckECIDInfo - Find NET_MODEM_GSM_REG_INFO SubBlock" ); + + sbStartOffSet = 0; + + if ( isNetRetStatusInd ) + { + retValue = aIsiMessage.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_NET_MODEM_REG_STATUS_IND, + NET_MODEM_GSM_REG_INFO, + EIsiSubBlockTypeId8Len8, + sbStartOffSet ); + } + else + { + retValue = aIsiMessage.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_NET_MODEM_REG_STATUS_GET_RESP, + NET_MODEM_GSM_REG_INFO, + EIsiSubBlockTypeId8Len8, + sbStartOffSet ); + } + } + // No else. + + // If subblock found. + if ( KErrNone == retValue ) + { +TFLOGSTRING("TSY:CMmCustomMessHandler::CheckECIDInfo - SubBlock Found"); +OstTrace0( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_CHECKECIDINFO, "CMmCustomMessHandler::CheckECIDInfo, SubBlock Found" ); + TUint tempMCC( 0 ); // Mobile Country Code. + TUint tempMNC( 0 ); // Mobile Network Code. + TUint tempCID( 0 ); // Cell identity. + TUint tempLAC( 0 ); // Location area code. + + // Get the Location Area Code. + tempLAC = aIsiMessage.Get16bit( + sbStartOffSet + + NET_MODEM_CURRENT_CELL_INFO_OFFSET_CURRENTLAC ); + // Get the Cell Id. + tempCID = aIsiMessage.Get32bit( + sbStartOffSet + + NET_MODEM_CURRENT_CELL_INFO_OFFSET_CURRENTCELLID ); + + // Get the operator code. Size is 3 bytes. + TPtrC8 operatorCode( aIsiMessage.GetData( + sbStartOffSet + + NET_MODEM_CURRENT_CELL_INFO_OFFSET_OPERATORCODE, + 3 ) ); + + // Map the operator code to symbian values (MCC and MNC). + RMobilePhone::TMobilePhoneNetworkIdentity networkId; + RMobilePhone::TMobilePhoneNetworkCountryCode countryCode; + iNetMessHandler->MapOperatorAndCountryCode( + operatorCode, + networkId, + countryCode ); + // Convert descriptor contained number to integer. + CMmStaticUtility::GetIntFromDescriptor( + tempMCC, + countryCode ); + CMmStaticUtility::GetIntFromDescriptor( + tempMNC, + networkId ); + + // If changed, request new ECID information. + if ( iECIDInfo.iMCC != tempMCC || + iECIDInfo.iMNC != tempMNC || + iECIDInfo.iCID != tempCID || + iECIDInfo.iLAC != tempLAC ) + { + TUint8 transId( KCustomTransId ); + NetNeighbourCellsReq( transId ); + // Save current LAC. + // (not received in NetNeighbourCellsResp when in 3G). + iECIDInfo.iLAC = tempLAC; + } + // No else. + } + // No else. + } + // No else. + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::HandleError +// Handles CMmCustomMessHandler's errors that comes +// via PhoNetReceiver RunError method. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::HandleError + ( + const TIsiReceiveC& aIsiMessage, TInt aError + ) + { + TFLOGSTRING2( "TSY: CMmCustomMessHandler::HandleError - Error: %d", aError ); +OstTrace1( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_HANDLEERROR, "CMmCustomMessHandler::HandleError;aError=%d", aError ); + + TInt resource( aIsiMessage.Get8bit( ISI_HEADER_OFFSET_RESOURCEID ) ); + TInt messageId( aIsiMessage.Get8bit( ISI_HEADER_OFFSET_MESSAGEID ) ); + TUint8 transId( aIsiMessage.Get8bit( ISI_HEADER_OFFSET_TRANSID ) ); + TUint8 serviceType( aIsiMessage.Get8bit( ISI_HEADER_OFFSET_SUBMESSAGEID ) ); + + switch( resource ) + { + default: + { + TFLOGSTRING("TSY: CMmCustomMessHandler::HandleError, switch resource - default.\n" ); +OstTrace0( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_HANDLEERROR, "CMmCustomMessHandler::HandleError, switch resource - default" ); + // Nothing to do here. + break; + } + } // end switch ( resource ) + } + +// not suppoted for S60 ver 3.2 +#if ( NCP_COMMON_S60_VERSION_SUPPORT != S60_VERSION_32 ) + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::GssCsServiceSetBandReq +// Creates and sends via phonet a GSS_CS_SERVICE_REQ including +// selected band mode (ENetworkBandAny, ENetworkBandUmts850, ENetworkBandUmts2100). +// Affects only in Umts or Dual mode. +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::GssCsServiceSetBandReq( TUint8 aTransId, // transaction Id + RMmCustomAPI::TNetworkModeCaps aNetworkModeCaps, // network mode caps + RMmCustomAPI::TBandSelection aBandSelection ) // band selection + { + TFLOGSTRING2( "TSY: CMmCustomMessHandler::GssCsServiceSetBandReq - aTransId: %d", aTransId ); +OstTraceExt1( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_GSSCSSERVICESETBANDREQ, "CMmCustomMessHandler::GssCsServiceSetBandReq;aTransId=%hhu", aTransId ); + + if ( RMmCustomAPI::KCapsNetworkModeUmts == aNetworkModeCaps || + RMmCustomAPI::KCapsNetworkModeDual == aNetworkModeCaps ) + { + TFLOGSTRING3( "TSY: CMmCustomMessHandler::GssCsServiceSetBandReq - NWModeCaps: %d - Band: %d", + aNetworkModeCaps, aBandSelection ); +OstTraceExt2( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_GSSCSSERVICESETBANDREQ, "CMmCustomMessHandler::GssCsServiceSetBandReq; - NWModeCaps=%d - Band=%d", aNetworkModeCaps, aBandSelection ); + + // create message data buffer + TBuf8< 20 > messageData; + messageData.Append( GSS_SELECTED_BANDS_WRITE ); // append service type + messageData.Append( 1 ); // number of subblocks + + // subblock + messageData.Append( GSS_SELECTED_UMTS_BAND_INFO ); // append band info + messageData.Append( 0x08 ); // subblock length + messageData.Append( KCustomPadding ); + messageData.Append( KCustomPadding ); + + if ( RMmCustomAPI::ENetworkBandUmts850 == aBandSelection ) + { + messageData.Append( TUint8( GSS_UMTS_BAND_V_MASK >> 24 ) ); + messageData.Append( TUint8( GSS_UMTS_BAND_V_MASK >> 16 ) ); + messageData.Append( TUint8( GSS_UMTS_BAND_V_MASK >> 8 ) ); + messageData.Append( TUint8( GSS_UMTS_BAND_V_MASK ) ); + } + else if ( RMmCustomAPI::ENetworkBandUmts2100 == aBandSelection ) + { + messageData.Append( TUint8( GSS_UMTS_BAND_I_MASK >> 24 ) ); + messageData.Append( TUint8( GSS_UMTS_BAND_I_MASK >> 16 ) ); + messageData.Append( TUint8( GSS_UMTS_BAND_I_MASK >> 8 ) ); + messageData.Append( TUint8( GSS_UMTS_BAND_I_MASK ) ); + } + else // ENetworkBandAny + { + messageData.Append( TUint8( GSS_UMTS_ALL_BANDS >> 24 ) ); + messageData.Append( TUint8( GSS_UMTS_ALL_BANDS >> 16 ) ); + messageData.Append( TUint8( GSS_UMTS_ALL_BANDS >> 8 ) ); + messageData.Append( TUint8( GSS_UMTS_ALL_BANDS ) ); + } + + return iPhoNetSender->Send( PN_GSS, aTransId, GSS_CS_SERVICE_REQ, messageData ); + } + + return KErrNotSupported; + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::GssCsServiceGetBandReq +// Creates request to get current band. +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::GssCsServiceGetBandReq( TUint8 aTransId ) //transaction Id + { + TFLOGSTRING2( "TSY: CMmCustomMessHandler::GssCsServiceGetBandReq - aTransId: %d", aTransId ); +OstTraceExt1( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_GSSCSSERVICEGETBANDREQ, "CMmCustomMessHandler::GssCsServiceGetBandReq;aTransId=%hhu", aTransId ); + + // create message data buffer + TBuf8< 4 > messageData; + messageData.Append( GSS_SELECTED_BANDS_READ ); // append service type + messageData.Append( 0 ); // No subblocks + + return iPhoNetSender->Send( PN_GSS, aTransId, GSS_CS_SERVICE_REQ, messageData ); + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::CompleteGetBandSelection +// Completes and breaks Get band selection request via PhoNetReceiver method. +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::CompleteGetBandSelection( const TIsiReceiveC& aIsiMessage ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CompleteGetBandSelection"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_COMPLETEGETBANDSELECTION, "CMmCustomMessHandler::CompleteGetBandSelection" ); + + RMmCustomAPI::TNetworkModeCaps nwModeCaps; // network mode caps + RMmCustomAPI::TBandSelection bandSelection; // band selection + bandSelection = RMmCustomAPI::ENetworkBandAny; // set "any" as a default + + TUint8 nrOfSubblocks ( aIsiMessage.Get8bit( ISI_HEADER_SIZE + + GSS_CS_SERVICE_RESP_OFFSET_NBROFSUBBLOCKS ) ); + + // first subblocks start from 'GSS_CS_SERVICE_RESP_OFFSET_NBROFSUBBLOCKS' + 1 + TUint8 sbOffset ( ISI_HEADER_SIZE + + GSS_CS_SERVICE_RESP_OFFSET_NBROFSUBBLOCKS + 1 ); + + TUint8 firstSubblock ( aIsiMessage.Get8bit( sbOffset ) ); + + TFLOGSTRING2("TSY: CMmCustomMessHandler::CompleteGetBandSelection - ECustomGetBandSelectionIPC. NrOfSubblocks:%d", nrOfSubblocks); +OstTraceExt1( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_COMPLETEGETBANDSELECTION, "CMmCustomMessHandler::CompleteGetBandSelection;nrOfSubblocks=%hhu", nrOfSubblocks ); + + // In 2G only products only sub block GSS_SELECTED_GSM_BANDS_INFO is returned. + if ( 1 == nrOfSubblocks && firstSubblock == GSS_SELECTED_GSM_BAND_INFO ) + { + nwModeCaps = RMmCustomAPI::KCapsNetworkModeGsm; + } + else // 1 < nrOfSubblocks || GSS_SELECTED_UMTS_BAND_INFO + { + //Band info offsets for reading + TUint8 gsmBandInfoOffset = 0; + TUint8 umtsBandInfoOffset = 0; + + // first SB is GSS_SELECTED_GSM_BAND_INFO + if ( GSS_SELECTED_GSM_BAND_INFO == firstSubblock ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CompleteGetBandSelection - 1st SB = GSM BAND INFO"); +OstTrace0( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_COMPLETEGETBANDSELECTION, "CMmCustomMessHandler::CompleteGetBandSelection - 1st SB = GSM BAND INFO" ); + + // calculate offsets + gsmBandInfoOffset = sbOffset + + GSS_SELECTED_GSM_BAND_INFO_OFFSET_SELECTEDGSMBANDS; + + // if there are more than one subblock read offset for second one + if ( 1 < nrOfSubblocks ) + { + umtsBandInfoOffset = sbOffset + + SIZE_GSS_SELECTED_GSM_BAND_INFO + + GSS_SELECTED_UMTS_BAND_INFO_OFFSET_SELECTEDUMTSBANDS; + } + } + else if ( GSS_SELECTED_UMTS_BAND_INFO == firstSubblock ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CompleteGetBandSelection - 1st SB = UMTS BAND INFO"); +OstTrace0( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_COMPLETEGETBANDSELECTION, "CMmCustomMessHandler::CompleteGetBandSelection - 1st SB = UMTS BAND INFO" ); + + // calculate offsets + umtsBandInfoOffset = sbOffset + + GSS_SELECTED_UMTS_BAND_INFO_OFFSET_SELECTEDUMTSBANDS; + + // if there are more than one subblock read offset for second one + if ( 1 < nrOfSubblocks ) + { + gsmBandInfoOffset = sbOffset + + SIZE_GSS_SELECTED_UMTS_BAND_INFO + + GSS_SELECTED_GSM_BAND_INFO_OFFSET_SELECTEDGSMBANDS; + } + } + + //If phone is forced to GSM, value in GSS_SELECTED_UMTS_BAND_INFO shall be GSS_UMTS_NO_BANDS + if ( GSS_UMTS_NO_BANDS == aIsiMessage.Get32bit( umtsBandInfoOffset ) ) // forced GSM + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CompleteGetBandSelection - umtsBandInfo==GSS_UMTS_NO_BANDS => Forced GSM"); +OstTrace0( TRACE_NORMAL, DUP4_CMMCUSTOMMESSHANDLER_COMPLETEGETBANDSELECTION, "CMmCustomMessHandler::CompleteGetBandSelection - umtsBandInfo==GSS_UMTS_NO_BANDS => Forced GSM" ); + nwModeCaps = RMmCustomAPI::KCapsNetworkModeGsm; + } + else + { + //If phone is forced to GSM, value in GSS_SELECTED_UMTS_BAND_INFO shall be GSS_UMTS_NO_BANDS. + if ( 0 < gsmBandInfoOffset && GSS_GSM_NO_BANDS == aIsiMessage.Get8bit( gsmBandInfoOffset ) ) // forced UMTS + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CompleteGetBandSelection - gsmBandInfo==GSS_GSM_NO_BANDS => Forced UMTS"); +OstTrace0( TRACE_NORMAL, DUP5_CMMCUSTOMMESSHANDLER_COMPLETEGETBANDSELECTION, "CMmCustomMessHandler::CompleteGetBandSelection - gsmBandInfo==GSS_GSM_NO_BANDS => Forced UMTS" ); + nwModeCaps = RMmCustomAPI::KCapsNetworkModeUmts; + } + else // dual mode + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CompleteGetBandSelection - Dual mode"); +OstTrace0( TRACE_NORMAL, DUP6_CMMCUSTOMMESSHANDLER_COMPLETEGETBANDSELECTION, "CMmCustomMessHandler::CompleteGetBandSelection - Dual mode" ); + nwModeCaps = RMmCustomAPI::KCapsNetworkModeDual; + } + + // Set network band + if ( GSS_UMTS_BAND_V_MASK == aIsiMessage.Get32bit( umtsBandInfoOffset ) ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CompleteGetBandSelection - UMTS850"); +OstTrace0( TRACE_NORMAL, DUP7_CMMCUSTOMMESSHANDLER_COMPLETEGETBANDSELECTION, "CMmCustomMessHandler::CompleteGetBandSelection - UMTS850" ); + bandSelection = RMmCustomAPI::ENetworkBandUmts850; + } + else if( GSS_UMTS_BAND_I_MASK == aIsiMessage.Get32bit( umtsBandInfoOffset ) ) + { + TFLOGSTRING("TSY: CMmCustomMessHandler::CompleteGetBandSelection - UMTS2100"); +OstTrace0( TRACE_NORMAL, DUP8_CMMCUSTOMMESSHANDLER_COMPLETEGETBANDSELECTION, "CMmCustomMessHandler::CompleteGetBandSelection - UMTS2100" ); + bandSelection = RMmCustomAPI::ENetworkBandUmts2100; + } + } + } + + CMmDataPackage dataPackage; + dataPackage.PackData( &bandSelection, &nwModeCaps ); + return iMessageRouter->Complete( ECustomGetBandSelectionIPC, &dataPackage, KErrNone ); + } + +#endif // NCP_COMMON_S60_VERSION_SUPPORT + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::ReadLifeTimerFromPermanentMemory +// Constructs PERM_PM_RECORD_READ_REQ ISI message from input parameters and send +// it through phonet. +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::ReadLifeTimerFromPermanentMemory + ( + const TUint8 //aTransId + ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::ReadLifeTimerFromPermanentMemory.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_READLIFETIMERFROMPERMANENTMEMORY, "CMmCustomMessHandler::ReadLifeTimerFromPermanentMemory" ); + + // Group ID 2 + Index 2 + Filler 2 + Offset 4 + Data amount to be read 4 = 14 + TBuf8<14> data; + + // Append Group ID + data.Append( static_cast( KPmmGroupNokiaTsy >> 8 ) ); + data.Append( static_cast( KPmmGroupNokiaTsy ) ); + + // Append Call Life Timer Index + data.Append( static_cast( KCallLifeTimerPmmIndexValue >> 8 ) ); + data.Append( static_cast( KCallLifeTimerPmmIndexValue ) ); + + // Append Filler + data.AppendFill( KCustomPadding, KTwo ); + + // Append Offset + data.AppendFill( KCustomPadding, KFour ); + + // Append Data amount to be read + data.Append( static_cast( KCallLifeTimerDataAmount >> 24 ) ); + data.Append( static_cast( KCallLifeTimerDataAmount >> 16 ) ); + data.Append( static_cast( KCallLifeTimerDataAmount >> 8 ) ); + data.Append( static_cast( KCallLifeTimerDataAmount ) ); + + /* To be done in CPS + return iPhoNetSender->Send( PN_PERMANENT_DATA, + aTransId, + PERM_PM_RECORD_READ_REQ, + data );*/ + return KErrNone; + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::LifeTimerFromPermanentMemoryReadResponse +// Breaks PERM_PM_RECORD_READ_RESP message. +// ----------------------------------------------------------------------------- +// +/* To be done in CPS +void CMmCustomMessHandler::LifeTimerFromPermanentMemoryReadResponse + ( + const TIsiReceiveC& aIsiMessage // an ISI message + ) + { +TFLOGSTRING("TSY: CCMmCustomMessHandler::LifeTimerFromPermanentMemoryReadResponse.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_LIFETIMERFROMPERMANENTMEMORYREADRESPONSE, "CMmCustomMessHandler::LifeTimerFromPermanentMemoryReadResponse" ); + + TInt ret( KErrNone ); + + TUint8 pmmStatus = aIsiMessage.Get8bit( + ISI_HEADER_SIZE + + PERM_PM_RECORD_READ_RESP_OFFSET_PMMSTATUS ); + + if ( PMM_OK == pmmStatus ) + { + iPMMReadRetryCounter = 0; // NUL trial counter + TUint sbStartOffSet( 0 ); + ret = aIsiMessage.FindSubBlockOffsetById( + ISI_HEADER_SIZE + SIZE_PERM_PM_RECORD_READ_RESP, + PERM_SB_PM_DATA, + EIsiSubBlockTypeId8Len8, sbStartOffSet ); + + if ( KErrNone == ret ) + { + TUint32 dataSize( aIsiMessage.Get32bit( sbStartOffSet + + PERM_SB_PM_DATA_OFFSET_SIZE ) ); + // Timer value size in message is 4 bytes. If some else length + // has been returned error code KErrGeneral is set and + // assert is done. + if ( KCallLifeTimerDataAmount == dataSize ) + { + iCallLifeTimer = aIsiMessage.Get32bit( sbStartOffSet + + PERM_SB_PM_DATA_OFFSET_DATA ); +TFLOGSTRING2( "TSY: CMmCustomMessHandler::LifeTimerFromPermanentMemoryReadResponse - iCallLifeTimer: %d", iCallLifeTimer ); +OstTrace1( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_LIFETIMERFROMPERMANENTMEMORYREADRESPONSE, "CMmCustomMessHandler::LifeTimerFromPermanentMemoryReadResponse;iCallLifeTimer=%d", iCallLifeTimer ); + } + else + { +TFLOGSTRING2( "TSY: CMmCustomMessHandler::LifeTimerFromPermanentMemoryReadResponse - Incorrect data size: %d", dataSize ); +OstTrace1( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_LIFETIMERFROMPERMANENTMEMORYREADRESPONSE, "CMmCustomMessHandler::LifeTimerFromPermanentMemoryReadResponse - Incorrect data size=%u", dataSize ); + TF_ASSERT( KCallLifeTimerDataAmount != dataSize ); + ret = KErrGeneral; + } + } + } + else + { + if ( PMM_NOT_READY == pmmStatus ) + { + // Send request again max 3 times +TFLOGSTRING("TSY: CMmCustomMessHandler::LifeTimerFromPermanentMemoryReadResponse - PMM not ready. Send request again\n" ); +OstTrace0( TRACE_NORMAL, DUP4_CMMCUSTOMMESSHANDLER_LIFETIMERFROMPERMANENTMEMORYREADRESPONSE, "CMmCustomMessHandler::LifeTimerFromPermanentMemoryReadResponse - PMM not ready. Send request again" ); + iPMMReadRetryCounter++; + if ( KMaxPMMReadRequests > iPMMReadRetryCounter ) + { + ReadLifeTimerFromPermanentMemory ( KCustomTransId ); + } + } + else if ( PMM_RECORD_NOT_FOUND == pmmStatus ) + { + // The first boot of the phone. +TFLOGSTRING("TSY: CMmCustomMessHandler::LifeTimerFromPermanentMemoryReadResponse - The first boot. Set iCallLifeTimer 0\n" ); + OstTrace0( TRACE_NORMAL, DUP5_CMMCUSTOMMESSHANDLER_LIFETIMERFROMPERMANENTMEMORYREADRESPONSE, "CMmCustomMessHandler::LifeTimerFromPermanentMemoryReadResponse - The first boot. Set iCallLifeTimer 0" ); + iCallLifeTimer = 0; + } + else + { +TFLOGSTRING2( "TSY: CMmCustomMessHandler::LifeTimerFromPermanentMemoryReadResponse - PMM Status NOT OK: %d", pmmStatus ); +OstTraceExt1( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_LIFETIMERFROMPERMANENTMEMORYREADRESPONSE, "CMmCustomMessHandler::LifeTimerFromPermanentMemoryReadResponse - PMM Status NOT OK=%hhu", pmmStatus ); + } + } + }*/ + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::WriteLifeTimerToPermanentMemory +// Constructs PERM_PM_RECORD_WRITE_REQ ISI message from input parameters and send +// it through phonet. +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::WriteLifeTimerToPermanentMemory + ( + const TUint8 /*aTransId*/, + TTimeIntervalSeconds aTime + ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::WriteLifeTimerToPermanentMemory.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_WRITELIFETIMERTOPERMANENTMEMORY, "CMmCustomMessHandler::WriteLifeTimerToPermanentMemory" ); + + // Group ID 2 + Index 2 + Filler 2 + Offset 4 + Data amount to be read 4 = 14 + TBuf8<14> data; + + // Append Group ID + data.Append( static_cast( KPmmGroupNokiaTsy >> 8 ) ); + data.Append( static_cast( KPmmGroupNokiaTsy ) ); + + // Append Call Life Timer Index + data.Append( static_cast( KCallLifeTimerPmmIndexValue >> 8 ) ); + data.Append( static_cast( KCallLifeTimerPmmIndexValue ) ); + + // Append Filler + data.AppendFill( KCustomPadding, KTwo ); + + // Append Data amount to be written + data.Append( static_cast( KCallLifeTimerDataAmount >> 24 ) ); + data.Append( static_cast( KCallLifeTimerDataAmount >> 16 ) ); + data.Append( static_cast( KCallLifeTimerDataAmount >> 8 ) ); + data.Append( static_cast( KCallLifeTimerDataAmount ) ); + + if ( KCallLifeTimerNotSet == iCallLifeTimer ) + { +TFLOGSTRING( "TSY: CMmCustomMessHandler::WriteLifeTimerToPermanentMemory - Call Life Timer is not set from PMM ret KErrNotReady\n" ); +TFLOGSTRING("TSY: CMmCustomMessHandler::WriteLifeTimerToPermanentMemory - PERM_PM_RECORD_WRITE_REQ is NOT send\n" ); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_WRITELIFETIMERTOPERMANENTMEMORY, "CMmCustomMessHandler::WriteLifeTimerToPermanentMemory - Call Life Timer is not set from PMM ret KErrNotReady" ); +OstTrace0( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_WRITELIFETIMERTOPERMANENTMEMORY, "CMmCustomMessHandler::WriteLifeTimerToPermanentMemory - PERM_PM_RECORD_WRITE_REQ is NOT send" ); + + // Return request with KErrNotReady + return ( KErrNotReady ); + } + else + { + // Update Life Timer Value + iCallLifeTimer += aTime.Int(); + + // Append Data + data.Append( static_cast( iCallLifeTimer >> 24 ) ); + data.Append( static_cast( iCallLifeTimer >> 16 ) ); + data.Append( static_cast( iCallLifeTimer >> 8 ) ); + data.Append( static_cast( iCallLifeTimer ) ); + + /* To be done in CPS + return iPhoNetSender->Send( PN_PERMANENT_DATA, + aTransId, + PERM_PM_RECORD_WRITE_REQ, + data );*/ + return KErrNone; + } + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::LifeTimerToPermanentMemoryWriteResponse +// Breaks PERM_PM_RECORD_WRITE_RESP message. +// ----------------------------------------------------------------------------- +// +/* To be done in CPS +void CMmCustomMessHandler::LifeTimerToPermanentMemoryWriteResponse + ( + const TIsiReceiveC& aIsiMessage // an ISI message + ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::LifeTimerToPermanentMemoryWriteResponse.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_LIFETIMERTOPERMANENTMEMORYWRITERESPONSE, "CMmCustomMessHandler::LifeTimerToPermanentMemoryWriteResponse" ); + + TInt ret( KErrNone ); + + TUint8 pmmStatus = aIsiMessage.Get8bit( + ISI_HEADER_SIZE + + PERM_PM_RECORD_WRITE_RESP_OFFSET_PMMSTATUS ); +TFLOGSTRING2( "TSY: CMmCustomMessHandler::LifeTimerToPermanentMemoryWriteResponse - pmmStatus: %d", pmmStatus ); +OstTraceExt1( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_LIFETIMERTOPERMANENTMEMORYWRITERESPONSE, "CMmCustomMessHandler::LifeTimerToPermanentMemoryWriteResponse;pmmStatus=%hhu", pmmStatus ); + + if ( PMM_OK != pmmStatus ) + { + ret = KErrNotReady; + TF_ASSERT( PMM_OK != pmmStatus ); +TFLOGSTRING2( "TSY: CMmCustomMessHandler::LifeTimerToPermanentMemoryWriteResponse - Call Life Timer is not updated / error from PMM ret: %d", ret ); +OstTrace1( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_LIFETIMERTOPERMANENTMEMORYWRITERESPONSE, "CMmCustomMessHandler::LifeTimerToPermanentMemoryWriteResponse - Call Life Timer is not updated / error from PMM ret=%d", ret ); + } + + return iMessageRouter->Complete( EMmTsyUpdateLifeTimeIPC, ret ); + }*/ + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::GetTotalLifeTimerValue +// Breaks PERM_PM_RECORD_WRITE_RESP message. +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::GetTotalLifeTimerValue + ( + ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::GetTotalLifeTimerValue.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_GETTOTALLIFETIMERVALUE, "CMmCustomMessHandler::GetTotalLifeTimerValue" ); + + TInt ret( KErrNone ); + RMmCustomAPI::TLifeTimeData timeInfo; + + timeInfo.iHours = 0; + timeInfo.iMinutes = 0; + + if ( KCallLifeTimerNotSet == iCallLifeTimer ) + { + ret = KErrNotReady; +TFLOGSTRING( "TSY: CMmCustomMessHandler::GetTotalLifeTimerValue - PMM has not been able to be read ret: KErrNotReady\n" ); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_GETTOTALLIFETIMERVALUE, "CMmCustomMessHandler::GetTotalLifeTimerValue - PMM has not been able to be read ret: KErrNotReady" ); + } + else + { + //set the data into timeInfo class, one hour is 3600 seconds. + timeInfo.iHours = iCallLifeTimer / KSecsInHour ; + timeInfo.iMinutes = + static_cast( ( iCallLifeTimer % KSecsInHour ) / + KMinsInHour ); + //update the caps + timeInfo.iCaps |= + RMmCustomAPI::TLifeTimeData::ELifeTimeDataCapsLifeTime; +TFLOGSTRING2( "TSY: TSY: CMmCustomMessHandler::GetTotalLifeTimerValue - iCallLifeTimer: %d", iCallLifeTimer ); +TFLOGSTRING2( "TSY: TSY: CMmCustomMessHandler::GetTotalLifeTimerValue - timeInfo.iHours: %d", timeInfo.iHours ); +TFLOGSTRING2( "TSY: TSY: CMmCustomMessHandler::GetTotalLifeTimerValue - timeInfo.iMinutes: %d", timeInfo.iMinutes ); +OstTrace1( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_GETTOTALLIFETIMERVALUE, "CMmCustomMessHandler::GetTotalLifeTimerValue;iCallLifeTimer=%d", iCallLifeTimer ); +OstTrace1( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_GETTOTALLIFETIMERVALUE, "CMmCustomMessHandler::GetTotalLifeTimerValue;timeInfo.iHours=%u", timeInfo.iHours ); +OstTraceExt1( TRACE_NORMAL, DUP4_CMMCUSTOMMESSHANDLER_GETTOTALLIFETIMERVALUE, "CMmCustomMessHandler::GetTotalLifeTimerValue;timeInfo.iMinutes=%hhu", timeInfo.iMinutes ); + } + + CMmDataPackage dataPackage; + dataPackage.PackData( &timeInfo ); + iMessageRouter->Complete( ECustomGetLifeTimeIPC, &dataPackage, ret ); + + return( ret ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccSimPowerOffReq +// Disconnects UICC server from smartcard and activates UICC SAP APDU interface +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccSimPowerOffReq() + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccSimPowerOffReq.\n"); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCSIMPOWEROFFREQ, "CMmCustomMessHandler::UiccSimPowerOffReq" ); + + iSapApduIfState = EUiccSapIfStatus1; + // Set parameters for UICC_CONNECTION_REQ message + TUiccParamsBase params; + params.messHandlerPtr = static_cast( this ); + params.trId = ETrIdSimPowerOff; + params.serviceType = UICC_DISCONNECT; + + return iMmUiccMessHandler->CreateUiccConnectorReq( params ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccSimPowerOffResp +// +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccSimPowerOffResp( TInt aStatus ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccSimPowerOffResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCSIMPOWEROFFRESP, "CMmCustomMessHandler::UiccSimPowerOffResp" ); + + TInt err ( KErrNone ); + + if( aStatus == UICC_STATUS_OK ) + { + switch( iSapApduIfState ) + { + case EUiccSapIfStatus1: + { + // Set parameters for UICC_APDU_REQ message + TUiccParamsApduReq params; + params.messHandlerPtr = static_cast( + this ); + params.trId = ETrIdSimPowerOff; + params.serviceType = UICC_APDU_CONTROL; + params.action = UICC_CONTROL_CARD_ACTIVATE; + + err = iMmUiccMessHandler->CreateUiccApduReq( params ); + + iSapApduIfState = EUiccSapIfStatus2; + break; + } + + case EUiccSapIfStatus2: + { + // No handling for UICC_APDU_RESP, + // wait for UICC_APDU_RESET_IND + iSapApduIfState = EUiccSapIfStatus3; + break; + } + + case EUiccSapIfStatus3: + { + // UICC_APDU_RESET_IND, UICC_READY, SAP IF active + iMessageRouter->Complete( ECustomPowerSimOffIPC, err ); + break; + } + } + } + else + { + if( aStatus == UICC_STATUS_SHUTTING_DOWN ) + { + err = CMmStaticUtility::EpocErrorCode( KErrNotReady, KErrNotFound ); + } + else + { + // UICC_STATUS_FAIL + err = CMmStaticUtility::EpocErrorCode( KErrGeneral, KErrNotFound ); + } + iMessageRouter->Complete( ECustomPowerSimOffIPC, err ); + } + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccSimWarmResetReq +// +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccSimWarmResetReq() + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccSimWarmResetReq.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCSIMWARMRESETREQ, "CMmCustomMessHandler::UiccSimWarmResetReq" ); + + TUiccParamsApduReq params; + params.messHandlerPtr = static_cast( this ); + params.trId = ETrIdSimWarmReset; + params.serviceType = UICC_APDU_CONTROL; + params.action = UICC_CONTROL_WARM_RESET; + + return iMmUiccMessHandler->CreateUiccApduReq( params ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccSimWarmResetResp +// +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccSimWarmResetResp( TInt aStatus ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccSimWarmResetResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCSIMWARMRESETRESP, "CMmCustomMessHandler::UiccSimWarmResetResp" ); + + TInt err ( KErrNone ); + + if( aStatus != UICC_STATUS_OK ) + { + if( aStatus == UICC_STATUS_SHUTTING_DOWN ) + { + err = CMmStaticUtility::EpocErrorCode( KErrNotReady, KErrNotFound ); + } + else + { + // UICC_STATUS_FAIL + err = CMmStaticUtility::EpocErrorCode( KErrGeneral, KErrNotFound ); + } + } + iMessageRouter->Complete( ECustomSimWarmResetIPC, err ); + + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccSimGetAtrReq +// +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccSimGetAtrReq() + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccSimGetAtrReq.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCSIMGETATRREQ, "CMmCustomMessHandler::UiccSimGetAtrReq" ); + + TUiccParamsApduReq params; + params.messHandlerPtr = static_cast( this ); + params.trId = ETrIdSimGetATR; + params.serviceType = UICC_APDU_ATR_GET; + + return iMmUiccMessHandler->CreateUiccApduReq( params ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccSimGetAtrResp +// +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccSimGetAtrResp( + TInt aStatus, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccSimGetAtrResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCSIMGETATRRESP, "CMmCustomMessHandler::UiccSimGetAtrResp" ); + + TInt err( KErrNone ); + const TDesC8* dataPtr = &aFileData; + CMmDataPackage dataPackage; + dataPackage.PackData( &dataPtr ); + + if( aStatus != UICC_STATUS_OK ) + { + if( aStatus == UICC_STATUS_SHUTTING_DOWN ) + { + err = CMmStaticUtility::EpocErrorCode( KErrNotReady, KErrNotFound ); + } + else + { + // UICC_STATUS_FAIL + err = CMmStaticUtility::EpocErrorCode( KErrGeneral, KErrNotFound ); + } + } + + iMessageRouter->Complete( ECustomGetATRIPC, &dataPackage, err ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccSimPowerOnReq +// Connects UICC server to smartcard and deactivates UICC SAP APDU interface +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccSimPowerOnReq() + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccSimPowerOnReq.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCSIMPOWERONREQ, "CMmCustomMessHandler::UiccSimPowerOnReq" ); + + //Set APDU interface state + iSapApduIfState = EUiccSapIfStatus1; + + // Set parameters for UICC_CONNECTION_REQ message + TUiccParamsBase params; + params.messHandlerPtr = static_cast( this ); + params.trId = ETrIdSimPowerOn; + params.serviceType = UICC_CONNECT; + + return iMmUiccMessHandler->CreateUiccConnectorReq( params ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccSimPowerOnResp +// +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccSimPowerOnResp( TInt aStatus ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccSimPowerOnResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCSIMPOWERONRESP, "CMmCustomMessHandler::UiccSimPowerOnResp" ); + + TInt err( KErrNone ); + + if( aStatus == UICC_STATUS_OK ) + { + switch( iSapApduIfState ) + { + case EUiccSapIfStatus1: + { + // No handling for UICC_CONNECTOR_RESP + // wait for UICC_APPLICATION_IND + iSapApduIfState = EUiccSapIfStatus2; + break; + } + + case EUiccSapIfStatus2: + { + // UICC_APPLICATION_IND (UICC_APPL_ACTIVATED) received + // SAP IF deactivated + iMessageRouter->Complete( ECustomPowerSimOnIPC, err ); + break; + } + } + } + else + { + if( aStatus == UICC_STATUS_SHUTTING_DOWN ) + { + err = CMmStaticUtility::EpocErrorCode( KErrNotReady, KErrNotFound ); + } + else + { + // UICC_STATUS_FAIL + err = CMmStaticUtility::EpocErrorCode( KErrGeneral, KErrNotFound ); + } + iMessageRouter->Complete( ECustomPowerSimOnIPC, err ); + } + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccSimSendAPDUReq +// +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccSendAPDUReq( + const RMmCustomAPI::TApduParameters& aApduParameters, + TInt aTraId ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccSimSendAPDUReq.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCSIMSENAPDUREQ, "CMmCustomMessHandler::UiccSendAPDUReq" ); + + TUiccParamsApduReq params; + params.messHandlerPtr = static_cast( this ); + params.trId = ( TUiccTrId )aTraId; + params.serviceType = UICC_APDU_SEND; + params.apduData.Append( aApduParameters.iCmdData ); + + return iMmUiccMessHandler->CreateUiccApduReq( params ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccSendAPDUResp +// +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccSendAPDUResp( + TInt aStatus, + const TDesC8& aFileData, + TInt aTraId ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccSendAPDUResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCSIMSENAPDURESP, "CMmCustomMessHandler::UiccSendAPDUResp" ); + + TInt err( KErrNone ); + const TDesC8* dataPtr = &aFileData; + CMmDataPackage dataPackage; + dataPackage.PackData( &dataPtr ); + + if( aStatus != UICC_STATUS_OK ) + { + if( aStatus == UICC_STATUS_SHUTTING_DOWN ) + { + err = CMmStaticUtility::EpocErrorCode( KErrNotReady, KErrNotFound ); + } + else + { + // UICC_STATUS_FAIL + err = CMmStaticUtility::EpocErrorCode( KErrGeneral, KErrNotFound ); + } + } + + if( aTraId == ETrIdSendAPDUv2 ) + { + iMessageRouter->Complete( + ECustomSendAPDUReqV2IPC, + &dataPackage, + err ); + } + else + { + iMessageRouter->Complete( + ECustomSendAPDUReqIPC, + &dataPackage, + err ); + } + + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccCardReaderStatusReq +// +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccCardReaderStatusReq() + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccCardReaderStatusReq.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCCARDREADERSTATUSREQ, "CMmCustomMessHandler::UiccCardReaderStatusReq" ); + + TUiccParamsApduReq params; + params.messHandlerPtr = static_cast( this ); + params.trId = ETrIdCardReaderStatus; + params.serviceType = UICC_CARD_STATUS_GET; + + // Current UICC IF implementatation does not support getting + // READER_STATUS_BYTE. However, apdu server uses hard coded values + // for READER STATUS BYTE bits 1 to 6 + // and information contained in bits 7 and 8 can be acquired with + // UICC_CARD_REQ request. + + return iMmUiccMessHandler->CreateUiccCardReq( params ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccCardReaderStatusResp +// +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccCardReaderStatusResp( + TInt aStatus, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccCardReaderStatusResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCCARDREADERSTATUSRESP, "CMmCustomMessHandler::UiccCardReaderStatusResp" ); + + TInt err ( KErrNone ); + CMmDataPackage dataPackage; + TUint8 cardStatus( 0 ); + TBuf8<1> statusByte; + + cardStatus = aFileData[0]; + + if( aStatus == UICC_STATUS_OK ) + { + switch( cardStatus ) + { + case UICC_STATUS_CARD_READY: + { + // UICC Card Status: UICC_STATUS_CARD_READY -> + // Card reader status byte: B1101_0000 + statusByte.Append(KUiccCardStatusCardPresentAndPoweredOn); + break; + } + + case UICC_STATUS_CARD_DISCONNECTED: + case UICC_STATUS_CARD_NOT_PRESENT: + { + // UICC Card Status: UICC_STATUS_CARD_DISCONNECTED or + // UICC_STATUS_CARD_NOT_PRESENT -> + // Card reader status byte: B0001_0000 + statusByte.Append(KUiccCardStatusCardNotPresentOrPoweredOff); + break; + } + + default: + break; + } + dataPackage.PackData( &statusByte ); + + } + else + { + if( aStatus == UICC_STATUS_SHUTTING_DOWN ) + { + err = CMmStaticUtility::EpocErrorCode( KErrNotReady, KErrNotFound ); + } + else + { + // UICC_STATUS_FAIL + err = CMmStaticUtility::EpocErrorCode( KErrGeneral, KErrNotFound ); + } + } + + iMessageRouter->Complete( + ECustomGetSimCardReaderStatusIPC, + &dataPackage, + err ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccCardInd +// Breaks UICC_CARD_IND ISI-message and completes " Notify SimCard Status" +// to CommonTSY. +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccCardInd( const TIsiReceiveC& aIsiMessage ) + { + // Get service type + TUint8 serviceType( aIsiMessage.Get8bit( + ISI_HEADER_SIZE + UICC_IND_OFFSET_SERVICETYPE ) ); + +TFLOGSTRING2("TSY: CMmCustomMessHandler::UiccCardInd, service type: %d", serviceType ); +OstTraceExt1( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCIND, "CMmCustomMessHandler::UiccCardInd;serviceType=%hhu", serviceType ); + + RMmCustomAPI::TSIMCardStatus returnStatus; + returnStatus = RMmCustomAPI::SimCardUnknowError; + + switch ( serviceType ) + { + case UICC_CARD_READY : + { + returnStatus = RMmCustomAPI::SimCardInserted; + break; + } + case UICC_CARD_DISCONNECTED: + { + returnStatus = RMmCustomAPI::SimCardRemoved; + break; + } + default: + { + break; + } + } + + CMmDataPackage dataPackage; + dataPackage.PackData( &returnStatus ); + iMessageRouter->Complete( + ECustomNotifySimCardStatusIPC, + &dataPackage, + KErrNone ); + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccSendAuthenticateApdu +// Constructs and sends AUTHENTICATE APDU to the UICC server +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccSendAuthenticateApdu( + const CMmDataPackage& aDataPackage ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccSendAuthenticateApdu.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCSENDAUTHENTICATEAPDU, "CMmCustomMessHandler::UiccSendAuthenticateApdu" ); + + TInt ret( KErrNone ); + TBool apduSendNeeded( EFalse ); + + // Let's construct AUTHENTICATE APDU based on authenticate type + RMmCustomAPI::TSimAuthenticationBase authBase; + aDataPackage.UnPackData( authBase ); + TUint8 simAuthType( authBase.ExtensionId() ); + + // Fill parameters to instance created from TUiccSendApdu + // needed for APDU sending + TUiccSendApdu params; + params.messHandlerPtr = static_cast( this ); + params.serviceType = UICC_APPL_APDU_SEND; + params.fileId = UICC_EF_ID_NOT_PRESENT; + params.fileIdSfi = UICC_SFI_NOT_PRESENT; + params.filePath.Append( KMasterFileId >> 8 ); + params.filePath.Append( KMasterFileId ); + params.filePath.Append( iMmUiccMessHandler->GetApplicationFileId() ); + + TUint8 cardType( iMmUiccMessHandler->GetCardType() ); + TBool serviceStatus( EFalse ); + + switch( simAuthType ) + { + case RMmCustomAPI::TSimAuthenticationBase::EEapSim: + { + if( UICC_CARD_TYPE_ICC == cardType ) + { + RMmCustomAPI::TSimAuthenticationEapSim eapSim; + aDataPackage.UnPackData( eapSim ); + + // In 2G we need to send command RUN GSM ALGORITHM to the ICC + UiccCreateRunGsmAlgorithmApdu( params, eapSim.iRandomParameters, ETrIdRunGsmAlgorithmSim ); + apduSendNeeded = ETrue; + } + else if( UICC_CARD_TYPE_UICC == cardType ) + { + // In 3G we need to send command AUTHENTICATE to the UICC + UiccCreateGsmSecurityContextApdu( params, aDataPackage ); + apduSendNeeded = ETrue; + } + break; + } + case RMmCustomAPI::TSimAuthenticationBase::EEapAka: + { + RMmCustomAPI::TSimAuthenticationEapAka eapAka; + aDataPackage.UnPackData( eapAka ); + + if( UICC_CARD_TYPE_ICC == cardType ) + { + // In 2G we need to send command RUN GSM ALGORITHM to the ICC + UiccCreateRunGsmAlgorithmApdu( params, eapAka.iRandomParameters, ETrIdRunGsmAlgorithmAka ); + apduSendNeeded = ETrue; + } + else if( UICC_CARD_TYPE_UICC == cardType ) + { + // In 3G we need to send command AUTHENTICATE to the UICC + UiccCreate3GSecurityContextApdu( + params, + eapAka.iRandomParameters, + eapAka.iAUTN, + ETrIdEEapAkaAuthenticate ); + apduSendNeeded = ETrue; + } + break; + } + case RMmCustomAPI::TSimAuthenticationBase::EGbaBootstrap: + { + serviceStatus = iMmUiccMessHandler->GetServiceStatus( KServiceGBA ); + + if( UICC_CARD_TYPE_UICC == cardType && + EFalse != serviceStatus ) + { + UiccCreateGBABootstrappingApdu( params, aDataPackage ); + apduSendNeeded = ETrue; + } + else + { + // GBA not supported if card type is ICC or GBA not supported in EFust +TFLOGSTRING3("TSY: CMmCustomMessHandler::UiccSendAuthenticateApdu: GBA not supported (card type: 0x%x, ss: 0x%x)\n", cardType, serviceStatus ); +OstTraceExt2( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_UICCSENDAUTHENTICATEAPDU, "CMmCustomMessHandler::UiccSendAuthenticateApdu: GBA not supported (card type: %x, ss: 0x%x)", cardType, serviceStatus ); + ret = KErrGeneral; + } + break; + } + case RMmCustomAPI::TSimAuthenticationBase::EGbaBootstrapUpdate: + { + serviceStatus = iMmUiccMessHandler->GetServiceStatus( KServiceGBA ); + + if( UICC_CARD_TYPE_UICC == cardType && + EFalse != serviceStatus ) + { + UiccGBABootstrapUpdate( aDataPackage ); + } + else + { + // GBA not supported if card type is ICC or GBA not supported in EFust +TFLOGSTRING3("TSY: CMmCustomMessHandler::UiccSendAuthenticateApdu: GBA not supported (card type: 0x%x, ss: 0x%x)\n", cardType, serviceStatus ); +OstTraceExt2( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_UICCSENDAUTHENTICATEAPDU, "CMmCustomMessHandler::UiccSendAuthenticateApdu: GBA not supported (card type: 0x%x, ss: 0x%x)", cardType, serviceStatus ); + ret = KErrGeneral; + } + break; + } + case RMmCustomAPI::TSimAuthenticationBase::EGbaBootstrapNafDerivation: + { + serviceStatus = iMmUiccMessHandler->GetServiceStatus( KServiceGBA ); + + if( UICC_CARD_TYPE_UICC == cardType && + EFalse != serviceStatus ) + { + UiccCreateGBABootstrapNafDerivationApdu( params, aDataPackage ); + apduSendNeeded = ETrue; + } + else + { + // GBA not supported if card type is ICC or GBA not supported in EFust +TFLOGSTRING3("TSY: CMmCustomMessHandler::UiccSendAuthenticateApdu: GBA not supported (card type: 0x%x, ss: 0x%x)\n", cardType, serviceStatus ); +OstTraceExt2( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_UICCSENDAUTHENTICATEAPDU, "CMmCustomMessHandler::UiccSendAuthenticateApdu: GBA not supported (card type: 0x%x, ss: 0x%x)", cardType, serviceStatus ); + ret = KErrGeneral; + } + break; + } + case RMmCustomAPI::TSimAuthenticationBase::EMgvMskUpdate: + { + serviceStatus = iMmUiccMessHandler->GetServiceStatus( KServiceMBMSsecurity ); + + if( UICC_CARD_TYPE_UICC == cardType && + EFalse != serviceStatus ) + { + UiccCreateMbmsMskUpdateApdu( params, aDataPackage ); + apduSendNeeded = ETrue; + } + else + { + // MBMS not supported if card type is ICC or MBMS not supported in EFust +TFLOGSTRING3("TSY: CMmCustomMessHandler::UiccSendAuthenticateApdu: MBMS security not supported (card type: 0x%x, ss: 0x%x)\n", cardType, serviceStatus ); +OstTraceExt2( TRACE_NORMAL, DUP4_CMMCUSTOMMESSHANDLER_UICCSENDAUTHENTICATEAPDU, "CMmCustomMessHandler::UiccSendAuthenticateApdu: MBMS security not supported (card type: 0x%x, ss: 0x%x)", cardType, serviceStatus ); + ret = KErrGeneral; + } + break; + } + case RMmCustomAPI::TSimAuthenticationBase::EMgvMtkGeneration: + { + serviceStatus = iMmUiccMessHandler->GetServiceStatus( KServiceMBMSsecurity ); + + if( UICC_CARD_TYPE_UICC == cardType && + EFalse != serviceStatus ) + { + UiccCreateMbmsMtkGenerationApdu( params, aDataPackage ); + apduSendNeeded = ETrue; + } + else + { + // MBMS not supported if card type is ICC or MBMS not supported in EFust +TFLOGSTRING3("TSY: CMmCustomMessHandler::UiccSendAuthenticateApdu: MBMS security not supported (card type: 0x%x, ss: 0x%x)\n", cardType, serviceStatus ); +OstTraceExt2( TRACE_NORMAL, DUP5_CMMCUSTOMMESSHANDLER_UICCSENDAUTHENTICATEAPDU, "CMmCustomMessHandler::UiccSendAuthenticateApdu: MBMS security not supported (card type: 0x%x, ss: 0x%x)", cardType, serviceStatus ); + ret = KErrGeneral; + } + break; + } + case RMmCustomAPI::TSimAuthenticationBase::EMgvMskDeletion: + { + serviceStatus = iMmUiccMessHandler->GetServiceStatus( KServiceMBMSsecurity ); + + if( UICC_CARD_TYPE_UICC == cardType && + EFalse != serviceStatus ) + { + UiccCreateMbmsMskDeletionApdu( params, aDataPackage ); + apduSendNeeded = ETrue; + } + else + { + // MBMS not supported if card type is ICC or MBMS not supported in EFust +TFLOGSTRING3("TSY: CMmCustomMessHandler::UiccSendAuthenticateApdu: MBMS security not supported (card type: 0x%x, ss: 0x%x)\n", cardType, serviceStatus ); +OstTraceExt2( TRACE_NORMAL, DUP6_CMMCUSTOMMESSHANDLER_UICCSENDAUTHENTICATEAPDU, "CMmCustomMessHandler::UiccSendAuthenticateApdu: MBMS security not supported (card type: 0x%x, ss: 0x%x)", cardType, serviceStatus ); + ret = KErrGeneral; + } + break; + } + default: + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccSendAuthenticateApdu: Unknown APDU\n" ); +OstTrace0( TRACE_NORMAL, DUP7_CMMCUSTOMMESSHANDLER_UICCSENDAUTHENTICATEAPDU, "CMmCustomMessHandler::UiccSendAuthenticateApdu: Unknown APDU" ); + break; + } + } + + if( EFalse != apduSendNeeded ) + { + // send the apdu to the UICC server + ret = iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + else + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccSendAuthenticateApdu: APDU not sent\n" ); +OstTrace0( TRACE_NORMAL, DUP8_CMMCUSTOMMESSHANDLER_UICCSENDAUTHENTICATEAPDU, "CMmCustomMessHandler::UiccSendAuthenticateApduu: APDU not sent" ); + } + return ret; + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccCreateRunGsmAlgorithmApdu +// Constructs GSM context AUTHENTICATE APDU +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccCreateRunGsmAlgorithmApdu( + TUiccSendApdu& aParams, + const TDesC8& aRand, + TUiccTrId aTraId ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccCreateRunGsmAlgorithmApdu.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCCREATERUNGSMALGORITHMAPDU, "CMmCustomMessHandler::UiccCreateRunGsmAlgorithmApdu" ); + + aParams.trId = aTraId; + aParams.apdu.Append( KClaIcc ); // CLA + aParams.apdu.Append( KEvenInstructionCode ); // INS + aParams.apdu.Append( 0 ); // P1 is set to 0 in case of RUN GSM ALGORITH + aParams.apdu.Append( 0 ); // P2 is set to 0 in case of RUN GSM ALGORITH + aParams.apdu.Append( aRand.Size() ); // Lc + aParams.apdu.Append( aRand ); // Data + aParams.apdu.Append( KRunGsmAlgorithmRespLen ); // Le + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccRunGsmAlgorithmApduResp +// Handles response APDU for RUN GSM ALGORITHM +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccRunGsmAlgorithmApduResp( + TInt aTraId, + TInt aStatus, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccRunGsmAlgorithmApduResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCRUNGSMALGORITHMAPDURESP, "CMmCustomMessHandler::UiccRunGsmAlgorithmApduResp" ); + + TInt ret( KErrNone ); + TInt ipc( ETrIdRunGsmAlgorithmIms == aTraId ? EMobilePhoneIMSAuthenticate : ECustomGetSimAuthenticationDataIPC ); + RMmCustomAPI::TSimAuthenticationEapSim eapSim; + RMmCustomAPI::TSimAuthenticationEapAka eapAka; + RMobilePhone::TImsAuthenticateDataV5 ims; + + if( UICC_STATUS_OK == aStatus ) + { + // get SW1 and SW2 + TUint8 sw1( aFileData[aFileData.Length() - KSw1Position] ); + TUint8 sw2( aFileData[aFileData.Length() - KSw2Position] ); + + TUint8 result( MapSw1Sw2ToAuthenticateResult( sw1, sw2 ) ); + + if( KNormalCommandEnding == result ) + { + if( KApduOk == ValidateReceivedAuthenticateApdu( aTraId, aFileData ) ) + { + // At the momen UICC server get the response from ICC, but in the + // future it may be removed from UICC. So then we should get the + // response from ICC. + TUint8 index = 0; + + if( ETrIdRunGsmAlgorithmSim == aTraId ) // EAP SIM + { + // get the SRES + eapSim.iSRES.Copy( aFileData.Mid(index, KLenOfSRes) ); + index += KLenOfSRes; + + // get the Kc + eapSim.iKC.Copy( aFileData.Mid(index, KLenOfKc ) ); + } + else if( ETrIdRunGsmAlgorithmIms == aTraId ) // IMS + { + // get the SRES + ims.iRES.Copy( aFileData.Mid(index, KLenOfSRes) ); + index += KLenOfSRes; + + // let's calculate ck and ik from kc + DeriveCkFromKc( ims.iCK, aFileData.Mid(index, KLenOfKc ) ); + DeriveIkFromKc( ims.iIK, aFileData.Mid(index, KLenOfKc ) ); + } + else // EAP AKA + { + // get the SRES + eapAka.iRES.Copy( aFileData.Mid(index, KLenOfSRes) ); + index += KLenOfSRes; + + // let's calculate ck and ik from kc + DeriveCkFromKc( eapAka.iCK, aFileData.Mid(index, KLenOfKc ) ); + DeriveIkFromKc( eapAka.iIK, aFileData.Mid(index, KLenOfKc ) ); + } + } + else + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccRunGsmAlgorithmApduResp. APDU validation fails\n" ); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_UICCRUNGSMALGORITHMAPDURESP, "CMmCustomMessHandler::UiccRunGsmAlgorithmApduResp. APDU validation fails" ); + ret = KErrMMEtelAuthenticateFailed; + } + } + else if( KCmdNotAllowedSecurityStatusNotSatisfied == result ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccRunGsmAlgorithmApduResp: Security conditions not satisfied\n" ); +OstTrace0( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_UICCRUNGSMALGORITHMAPDURESP, "CMmCustomMessHandler::UiccRunGsmAlgorithmApduResp: Security conditions not satisfied" ); + ret = CMmStaticUtility::EpocErrorCode( + KErrAccessDenied, + KErrGsm0707SimPin1Required ); + } + else + { +TFLOGSTRING2("TSY: CMmCustomMessHandler::UiccRunGsmAlgorithmApduResp. unknown result: 0x%X\n", result ); +OstTrace1( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_UICCRUNGSMALGORITHMAPDURESP, "CMmCustomMessHandler::UiccRunGsmAlgorithmApduResp. unknown result: 0x%x", result ); + ret = KErrMMEtelAuthenticateFailed; + } + } + else + { +TFLOGSTRING2("TSY: CMmCustomMessHandler::UiccRunGsmAlgorithmApduResp: UICC status not ok: 0x%x\n", aStatus ); +OstTrace1( TRACE_NORMAL, DUP4_CMMCUSTOMMESSHANDLER_UICCRUNGSMALGORITHMAPDURESP, "CMmCustomMessHandler::UiccRunGsmAlgorithmApduResp: UICC status not ok: 0x%x", aStatus ); + ret = KErrMMEtelAuthenticateFailed; + } + + if( KErrNone != ret ) + { + iMessageRouter->Complete( + ipc, + ret ); + } + else + { + CMmDataPackage dataPackage; + if( ETrIdRunGsmAlgorithmSim == aTraId ) // EAP SIM + { + dataPackage.PackData( &eapSim ); + } + else if( ETrIdRunGsmAlgorithmIms == aTraId ) + { + dataPackage.PackData( &ims ); + } + else + { + dataPackage.PackData( &eapAka ); + } + + iMessageRouter->Complete( + ipc, + &dataPackage, + ret ); + } + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccCreateGsmSecurityContextApdu +// Constructs GSM context AUTHENTICATE APDU +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccCreateGsmSecurityContextApdu( + TUiccSendApdu& params, + const CMmDataPackage& aDataPackage ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccCreateGsmSecurityContextApdu.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCCREATEGSMSECURITYCONTEXTAPDU, "CMmCustomMessHandler::UiccCreateGsmSecurityContextApdu" ); + + RMmCustomAPI::TSimAuthenticationEapSim eapSim; + aDataPackage.UnPackData( eapSim ); + + params.trId = ETrIdEEapSimAuthenticate; + params.apdu.Append( KClaNoSm ); // CLA + params.apdu.Append( KEvenInstructionCode ); // INS + params.apdu.Append( 0 ); // P1 is set to 0 in case of even instruction + params.apdu.Append( KGsmAuthenticationContext ); // P2 + params.apdu.Append( eapSim.iRandomParameters.Size() + 1 ); // Lc + params.apdu.Append( eapSim.iRandomParameters.Size() ); // Data + params.apdu.Append( eapSim.iRandomParameters ); // Data + params.apdu.Append( KMaximumLenOfDataExpected ); // Le + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccGsmSecurityContextApduResp +// Handles response APDU for GSM context AUTHENTICATE APDU +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccGsmSecurityContextApduResp( + TInt aTraId, + TInt aStatus, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccGsmSecurityContextApduResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCGSMSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::UiccGsmSecurityContextApduResp" ); + + TInt ret( KErrNone ); + RMmCustomAPI::TSimAuthenticationEapSim eapSim; + + if( UICC_STATUS_OK == aStatus ) + { + // get SW1 and SW2 + TUint8 sw1( aFileData[aFileData.Length() - KSw1Position] ); + TUint8 sw2( aFileData[aFileData.Length() - KSw2Position] ); + + TUint8 result( MapSw1Sw2ToAuthenticateResult( sw1, sw2 ) ); + + if( KNormalCommandEnding == result ) + { + if( KApduOk == ValidateReceivedAuthenticateApdu( aTraId, aFileData ) ) + { + // get the SRES + TUint8 index( 0 ); + TUint8 len( aFileData[index++] ); + eapSim.iSRES.Copy( aFileData.Mid( index , len ) ); + index += len; + + // get the Kc + len = aFileData[index++]; + eapSim.iKC.Copy( aFileData.Mid( index , len ) ); + } + else + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccGsmSecurityContextApduResp: APDU validation failed\n" ); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_UICCGSMSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::UiccGsmSecurityContextApduResp: APDU validation failed" ); + ret = KErrMMEtelAuthenticateFailed; + } + } + else + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccGsmSecurityContextApduResp: unknown result\n" ); +OstTrace0( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_UICCGSMSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::UiccGsmSecurityContextApduResp: unknown result" ); + ret = KErrMMEtelAuthenticateFailed; + } + } + else + { +TFLOGSTRING2("TSY: CMmCustomMessHandler::UiccGsmSecurityContextApduResp: UICC status not ok: 0x%x\n", aStatus ); +OstTrace1( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_UICCGSMSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::UiccGsmSecurityContextApduResp: UICC status not ok: 0x%x", aStatus ); + ret = KErrMMEtelAuthenticateFailed; + } + + if( KErrNone != ret ) + { + iMessageRouter->Complete( + ECustomGetSimAuthenticationDataIPC, + ret ); + } + else + { + CMmDataPackage dataPackage; + dataPackage.PackData( &eapSim ); + + iMessageRouter->Complete( + ECustomGetSimAuthenticationDataIPC, + &dataPackage, + ret ); + } + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccCreate3GSecurityContextApdu +// Constructs 3G security context AUTHENTICATE APDU +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccCreate3GSecurityContextApdu( + TUiccSendApdu& aParams, + const TDesC8& aRand, + const TDesC8& aAuth, + TUiccTrId aTraId ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccCreate3GSecurityContextApdu.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCCREATE3GSECURITYCONTEXTAPDU, "CMmCustomMessHandler::UiccCreate3GSecurityContextApdu" ); + + // len of data is sizeof RAND + sizeof AUTN + two length fields + // (one for RAND len and one for AUTN len) + TUint8 lc( aRand.Size() + aAuth.Size() + 2 ); + + aParams.trId = aTraId; + aParams.apdu.Append( KClaNoSm ); // CLA + aParams.apdu.Append( KEvenInstructionCode ); // INS + aParams.apdu.Append( 0 ); // P1 is set to 0 in case of even instruction + aParams.apdu.Append( K3GAuthenticationContext ); // P2 + aParams.apdu.Append( lc ); // Lc + aParams.apdu.Append( aRand.Size() ); // len of RAND + aParams.apdu.Append( aRand ); // RAND + aParams.apdu.Append( aAuth.Size() ); // len of AUTN + aParams.apdu.Append( aAuth ); // AUTN + aParams.apdu.Append( KMaximumLenOfDataExpected ); // Le + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::Uicc3GSecurityContextApduResp +// Handles response APDU for 3G security context AUTHENTICATE APDU +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::Uicc3GSecurityContextApduResp( + TInt aTraId, + TInt aStatus, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::Uicc3GSecurityContextApduResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICC3GSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::Uicc3GSecurityContextApduResp" ); + + TInt ret( KErrNone ); + TInt ipc( ETrIdEEapAkaAuthenticateIms == aTraId ? EMobilePhoneIMSAuthenticate : ECustomGetSimAuthenticationDataIPC ); + RMmCustomAPI::TSimAuthenticationEapAka eapAka; + RMobilePhone::TImsAuthenticateDataV5 ims; + + if( UICC_STATUS_OK == aStatus ) + { + // get SW1 and SW2 + TUint8 sw1( aFileData[aFileData.Length() - KSw1Position] ); + TUint8 sw2( aFileData[aFileData.Length() - KSw2Position] ); + + TUint8 result( MapSw1Sw2ToAuthenticateResult( sw1, sw2 ) ); + + if( KNormalCommandEnding == result ) + { + if( KApduOk == ValidateReceivedAuthenticateApdu( aTraId, aFileData ) ) + { + TUint32 index( 0 ); + + if( KSuccessfull3GAuthTag == aFileData[index] ) + { + index++; + + if( ETrIdEEapAkaAuthenticate == aTraId ) + { + // get the RES + TUint8 len( aFileData[index++] ); + eapAka.iRES.Copy( aFileData.Mid( index, len ) ); + index += len; + + // get the CK + len = aFileData[index++]; + eapAka.iCK.Copy( aFileData.Mid( index, len ) ); + index += len; + + // get the IK + len = aFileData[index++]; + eapAka.iIK.Copy( aFileData.Mid( index, len ) ); + index += len; + + // Kc is not supported at the moment because of + // RMmCustomAPI::TSimAuthenticationEapAka doesn't + // have parameter for that + } + else + { + // get the RES + TUint8 len( aFileData[index++] ); + ims.iRES.Copy( aFileData.Mid( index, len ) ); + index += len; + + // get the CK + len = aFileData[index++]; + ims.iCK.Copy( aFileData.Mid( index, len ) ); + index += len; + + // get the IK + len = aFileData[index++]; + ims.iIK.Copy( aFileData.Mid( index, len ) ); + index += len; + } + } + else if( KSyncFailureTag == aFileData[index] ) + { + index++; + + if( ETrIdEEapAkaAuthenticate == aTraId ) + { + // get the AUTS + TUint8 len( aFileData[index++] ); + eapAka.iAUTS.Copy( aFileData.Mid( index, len ) ); + } + else + { + // get the AUTS + TUint8 len( aFileData[index++] ); + ims.iAUTS.Copy( aFileData.Mid( index, len ) ); + } + ret = KErrMMEtelSqnVerificationFailed; + } + } + else + { +TFLOGSTRING("TSY: CMmCustomMessHandler::Uicc3GSecurityContextApduResp: APDU validation failed\n" ); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_UICC3GSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::Uicc3GSecurityContextApduResp: APDU validation failed" ); + ret = KErrMMEtelAuthenticateFailed; + } + } + else if( KAppAuthErrorIncorrectMac == result ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::Uicc3GSecurityContextApduResp: incorrect MAC\n" ); +OstTrace0( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_UICC3GSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::Uicc3GSecurityContextApduResp: incorrect MAC" ); + // no parameters in this case + ret = KErrMMEtelMacVerificationFailed; + } + else if( KCmdNotAllowedSecurityStatusNotSatisfied == result ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::Uicc3GSecurityContextApduResp: Security conditions not satisfied\n" ); +OstTrace0( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_UICC3GSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::Uicc3GSecurityContextApduResp: Security conditions not satisfied" ); + ret = CMmStaticUtility::EpocErrorCode( + KErrAccessDenied, + KErrGsm0707SimPin1Required ); + } + else + { +TFLOGSTRING("TSY: CMmCustomMessHandler::Uicc3GSecurityContextApduResp: unknown result\n" ); +OstTrace0( TRACE_NORMAL, DUP4_CMMCUSTOMMESSHANDLER_UICC3GSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::Uicc3GSecurityContextApduResp: unknown result" ); + ret = KErrMMEtelAuthenticateFailed; + } + } + else + { +TFLOGSTRING2("TSY: CMmCustomMessHandler::Uicc3GSecurityContextApduResp: UICC status not ok: 0x%x\n", aStatus ); +OstTrace1( TRACE_NORMAL, DUP5_CMMCUSTOMMESSHANDLER_UICC3GSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::Uicc3GSecurityContextApduResp: UICC status not ok: 0x%x", aStatus ); + ret = ETrIdEEapAkaAuthenticateIms == aTraId ? KErrGeneral : KErrMMEtelAuthenticateFailed; + } + + if( KErrNone == ret || + KErrMMEtelSqnVerificationFailed == ret || + KErrMMEtelMacVerificationFailed == ret ) + { + CMmDataPackage dataPackage; + + if( ETrIdEEapAkaAuthenticate == aTraId ) + { + dataPackage.PackData( &eapAka ); + } + else + { + dataPackage.PackData( &ims ); + } + + iMessageRouter->Complete( + ipc, + &dataPackage, + ret ); + } + else + { + iMessageRouter->Complete( + ipc, + ret ); + } + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccCreateGBABootstrappingApdu +// Constructs GBA security context AUTHENTICATE APDU (bootstrapping mode) +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccCreateGBABootstrappingApdu( + TUiccSendApdu& aParams, + const CMmDataPackage& aDataPackage ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccCreateGBABootstrappingApdu.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCCREATEGBABOOTSTRAPPINGAPDU, "CMmCustomMessHandler::UiccCreateGBABootstrappingApdu" ); + + RMmCustomAPI::TSimAuthenticationGbaBootstrap gbaBootstrap; + aDataPackage.UnPackData( gbaBootstrap ); + + // len of data is GBA bootstrapping mode tag (1 byte) + sizeof RAND + // + sizeof AUTN + two length fields (one for RAND len and one for AUTN len) + TUint8 lc( 1 + gbaBootstrap.iRandomParameters.Size() + gbaBootstrap.iAUTN.Size() + 2 ); + + aParams.trId = ETrIdEGbaBootstrap; + aParams.apdu.Append( KClaNoSm ); // CLA + aParams.apdu.Append( KEvenInstructionCode ); // INS + aParams.apdu.Append( 0 ); // P1 is set to 0 in case of even instruction + aParams.apdu.Append( KGBAAuthenticationContext ); // P2 + aParams.apdu.Append( lc ); // Lc + aParams.apdu.Append( KGBABootstappingModeTag ); // GBA bootstrapping mode tag + aParams.apdu.Append( gbaBootstrap.iRandomParameters.Size() ); // len of RAND + aParams.apdu.Append( gbaBootstrap.iRandomParameters ); // RAND + aParams.apdu.Append( gbaBootstrap.iAUTN.Size() ); // len of AUTN + aParams.apdu.Append( gbaBootstrap.iAUTN ); // AUTN + aParams.apdu.Append( KMaximumLenOfDataExpected ); // Le + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccGBABootstrappingApduResp +// Handles response APDU for GBA security context AUTHENTICATE APDU +// (bootstrapping mode) +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccGBABootstrappingApduResp( + TInt aTraId, + TInt aStatus, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccGBABootstrappingApduResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCGBABOOTSTRAPPINGAPDURESP, "CMmCustomMessHandler::UiccGBABootstrappingApduResp" ); + + TInt ret( KErrNone ); + RMmCustomAPI::TSimAuthenticationGbaBootstrap gbaBootstrap; + + if( UICC_STATUS_OK == aStatus ) + { + // get SW1 and SW2 + TUint8 sw1( aFileData[aFileData.Length() - KSw1Position] ); + TUint8 sw2( aFileData[aFileData.Length() - KSw2Position] ); + + TUint8 result( MapSw1Sw2ToAuthenticateResult( sw1, sw2 ) ); + + if( KNormalCommandEnding == result ) + { + if( KApduOk == ValidateReceivedAuthenticateApdu( aTraId, aFileData ) ) + { + TUint32 index( 0 ); + + if( KSuccessfull3GAuthTag == aFileData[index] ) + { + index++; + + // get the RES + TUint8 len( aFileData[index++] ); + gbaBootstrap.iRES.Copy( aFileData.Mid( index, len ) ); + } + + else if( KSyncFailureTag == aFileData[index] ) + { + index++; + + // get the AUTS + TUint8 len( aFileData[index++] ); + gbaBootstrap.iAUTS.Copy( aFileData.Mid( index, len ) ); + + ret = KErrMMEtelSqnVerificationFailed; + } + } + else + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccGBABootstrappingApduResp: APDU validation failed\n" ); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_UICCGBABOOTSTRAPPINGAPDURESP, "CMmCustomMessHandler::UiccGBABootstrappingApduResp: APDU validation failed" ); + ret = KErrGeneral; + } + } + else if( KAppAuthErrorIncorrectMac == result ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccGBABootstrappingApduResp: incorrect MAC\n" ); +OstTrace0( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_UICCGBABOOTSTRAPPINGAPDURESP, "CMmCustomMessHandler::UiccGBABootstrappingApduResp: incorrect MAC" ); + // no parameters in this case + ret = KErrMMEtelMacVerificationFailed; + } + else + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccGBABootstrappingApduResp: unknown result\n" ); +OstTrace0( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_UICCGBABOOTSTRAPPINGAPDURESP, "CMmCustomMessHandler::UiccGBABootstrappingApduResp: unknown result" ); + ret = KErrGeneral; + } + } + else + { +TFLOGSTRING2("TSY: CMmCustomMessHandler::UiccGBABootstrappingApduResp: UICC status not ok: 0x%x\n", aStatus ); +OstTrace1( TRACE_NORMAL, DUP4_CMMCUSTOMMESSHANDLER_UICCGBABOOTSTRAPPINGAPDURESP, "CMmCustomMessHandler::UiccGBABootstrappingApduResp: UICC status not ok: 0x%x", aStatus ); + ret = KErrMMEtelAuthenticateFailed; + } + + if( KErrNone == ret || + KErrMMEtelSqnVerificationFailed == ret || + KErrMMEtelMacVerificationFailed == ret ) + { + CMmDataPackage dataPackage; + dataPackage.PackData( &gbaBootstrap ); + + iMessageRouter->Complete( + ECustomGetSimAuthenticationDataIPC, + &dataPackage, + ret ); + } + else + { + iMessageRouter->Complete( + ECustomGetSimAuthenticationDataIPC, + ret ); + } + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccGBABootstrapUpdate +// starts GBA bootstrap update operation +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccGBABootstrapUpdate( + const CMmDataPackage& aDataPackage ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccGBABootstrapUpdate.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCGBABOOTSTRAPUPDATE, "CMmCustomMessHandler::UiccGBABootstrapUpdate" ); + + // GBA bootstrap update is done by first reading of elementary file EFgba. + // After that RAND is stored temporarily and B-Tid and keylifetime is written + // to EFgba. After write operation, RAND is completed to the client. + + RMmCustomAPI::TSimAuthenticationGbaBootstrapUpdate gbaBootstrapUpdate; + aDataPackage.UnPackData( gbaBootstrapUpdate ); + + iBTidBuf.Zero(); + iKeyLifetimeBuf.Zero(); + + // Store B-TID temporarily + iBTidBuf.Append( gbaBootstrapUpdate.iBTid ); + + // Store Key lifetime temporarily + iKeyLifetimeBuf.Append( gbaBootstrapUpdate.iKeyLifeTime ); + + // Set parameters for UICC_APPL_CMD_REQ message + TUiccReadTransparent params; + params.messHandlerPtr = static_cast( this ); + params.trId = ETrIdEGbaBootstrapRead; + + params.dataAmount = 0; + params.dataOffset = 0; + params.fileId = KElemGba; + params.fileIdSfi = UICC_SFI_NOT_PRESENT; + params.serviceType = UICC_APPL_READ_TRANSPARENT; + + // File id path + params.filePath.Append( KMasterFileId >> 8 ); + params.filePath.Append( KMasterFileId ); + params.filePath.Append( iMmUiccMessHandler->GetApplicationFileId() ); + + iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccGBABootstrapReadResp +// Handles response to elementary file EFgba read operation +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccGBABootstrapReadResp( + TInt aStatus, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccGBABootstrapReadResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCGBABOOTSTRAPREADRESP, "CMmCustomMessHandler::UiccGBABootstrapReadResp" ); + + iRandBuf.Zero(); + + if( UICC_STATUS_OK == aStatus) + { + // Get the rand len + TUint32 index( 0 ); + TUint8 randLen( aFileData[index++] ); + + if( aFileData.Length() >= randLen + + iBTidBuf.Length() + + iKeyLifetimeBuf.Length() + + 3 ) + { + // store rand temporarily so that we can complete it + // when B-Tid and keylifetime is updated to the EFgba. + iRandBuf.Copy( aFileData.Mid( index, randLen ) ); + + // Set parameters for UICC_APPL_CMD_REQ message + TUiccWriteTransparent params; + params.messHandlerPtr = static_cast( this ); + params.trId = ETrIdEGbaBootstrapUpdate; + params.dataOffset = randLen + 1; + params.fileId = KElemGba; + params.fileIdSfi = UICC_SFI_NOT_PRESENT; + params.serviceType = UICC_APPL_UPDATE_TRANSPARENT; + + // File id path + params.filePath.Append( KMasterFileId >> 8 ); + params.filePath.Append( KMasterFileId ); + params.filePath.Append( iMmUiccMessHandler->GetApplicationFileId() ); + + // fill file data + params.fileData.Append( iBTidBuf.Length() ); + params.fileData.Append( iBTidBuf ); + params.fileData.Append( iKeyLifetimeBuf.Length() ); + params.fileData.Append( iKeyLifetimeBuf ); + + iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + else + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccGBABootstrapReadResp. File too small for update\n" ); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_UICCGBABOOTSTRAPREADRESP, "CMmCustomMessHandler::UiccGBABootstrapReadResp. File too small for update" ); + iMessageRouter->Complete( + ECustomGetSimAuthenticationDataIPC, + KErrArgument ); + } + } + else + { +TFLOGSTRING2("TSY: CMmCustomMessHandler::UiccGBABootstrapReadResp. EFgba reading failed (0x%x)\n", aStatus ); +OstTrace1( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_UICCGBABOOTSTRAPREADRESP, "CMmCustomMessHandler::UiccGBABootstrapReadResp. EFgba reading failed (%x)", aStatus ); + iMessageRouter->Complete( + ECustomGetSimAuthenticationDataIPC, + KErrMMEtelAuthenticateFailed ); + } + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccGBABootstrapUpdateResp +// Handles response to elementary file EFgba write operation +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccGBABootstrapUpdateResp( TInt aStatus ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccGBABootstrapUpdateResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCGBABOOTSTRAPUPDATERESP, "CMmCustomMessHandler::UiccGBABootstrapUpdateResp" ); + + TInt ret( KErrGeneral ); + RMmCustomAPI::TSimAuthenticationGbaBootstrapUpdate gbaBootstrapUpdate; + + if( UICC_STATUS_OK == aStatus ) + { + ret = KErrNone; + gbaBootstrapUpdate.iRandomParameters.Copy( iRandBuf ); + } + else + { + ret = KErrMMEtelAuthenticateFailed; + } + + if( KErrNone == ret ) + { + CMmDataPackage dataPackage; + dataPackage.PackData( &gbaBootstrapUpdate ); + iMessageRouter->Complete( + ECustomGetSimAuthenticationDataIPC, + &dataPackage, + ret ); + } + else + { + iMessageRouter->Complete( + ECustomGetSimAuthenticationDataIPC, + ret ); + } + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccCreateGBABootstrapNafDerivationApdu +// Constructs GBA security context AUTHENTICATE APDU (NAF derivation mode) +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccCreateGBABootstrapNafDerivationApdu( + TUiccSendApdu& aParams, + const CMmDataPackage& aDataPackage ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccCreateGBABootstrapNafDerivationApdu.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCCREATEGBABOOTSTRAPNAFDERIVATIONAPDU, "CMmCustomMessHandler::UiccCreateGBABootstrapNafDerivationApdu" ); + + RMmCustomAPI::TSimAuthenticationGbaNafDerivation gbaBootstrapNafDerivation; + aDataPackage.UnPackData( gbaBootstrapNafDerivation ); + + // len of data is GBA NAF derivation mode tag (1 byte) + sizeof NAFId + // + sizeof IMPI + two length fields (one for NAFId len and one for IMPI len) + TUint8 lc( 1 + + gbaBootstrapNafDerivation.iNafId.Size() + + gbaBootstrapNafDerivation.iImpi.Size() + + 2 ); + + aParams.trId = ETrIdEGbaNafDerivation; + aParams.apdu.Append( KClaNoSm ); // CLA + aParams.apdu.Append( KEvenInstructionCode ); // INS + aParams.apdu.Append( 0 ); // P1 is set to 0 in case of even instruction + aParams.apdu.Append( KGBAAuthenticationContext ); // P2 + aParams.apdu.Append( lc ); // Lc + aParams.apdu.Append( KGBANAFDerivationModeTag ); // GBA bootstrapping mode tag + aParams.apdu.Append( gbaBootstrapNafDerivation.iNafId.Size() ); // len of NAFId + aParams.apdu.Append( gbaBootstrapNafDerivation.iNafId ); // NAFId + aParams.apdu.Append( gbaBootstrapNafDerivation.iImpi.Size() ); // len of IMPI + aParams.apdu.Append( gbaBootstrapNafDerivation.iImpi ); // IMPI + aParams.apdu.Append( KMaximumLenOfDataExpected ); // Le + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccGBABootstrapNafDerivationApduResp +// Handles response APDU for GBA security context AUTHENTICATE APDU +// (NAF derivation mode) +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccGBANafDerivationApduResp( + TInt aTraId, + TInt aStatus, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccGBABootstrapNafDerivationApduResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCGBANAFDERIVATIONAPDURESP, "CMmCustomMessHandler::UiccGBANafDerivationApduResp" ); + + TInt ret( KErrNone ); + RMmCustomAPI::TSimAuthenticationGbaNafDerivation gbaNafDerivation; + + if( UICC_STATUS_OK == aStatus ) + { + // get SW1 and SW2 + TUint8 sw1( aFileData[aFileData.Length() - KSw1Position] ); + TUint8 sw2( aFileData[aFileData.Length() - KSw2Position] ); + + TUint8 result( MapSw1Sw2ToAuthenticateResult( sw1, sw2 ) ); + + if( KNormalCommandEnding == result ) + { + if( KApduOk == ValidateReceivedAuthenticateApdu( aTraId, aFileData ) ) + { + // Let's skip "Successful GBA operation" tag + // and start with Length of Length of Ks ext NAF + TUint32 index( 1 ); + + // get the Ks ext NAF + TUint8 len( aFileData[index++] ); + gbaNafDerivation.iKsExtNaf.Copy( aFileData.Mid( index, len ) ); + } + else + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccGBABootstrapNafDerivationApduResp: APDU validation failed\n" ); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_UICCGBANAFDERIVATIONAPDURESP, "CMmCustomMessHandler::UiccGBANafDerivationApduResp: APDU validation failed" ); + ret = KErrGeneral; + } + } + else if( KCmdNotAllowedConditionsNotSatisfied == result ) + { + ret = KErrNotSupported; + } + else + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccGBABootstrapNafDerivationApduResp: unknown result\n" ); +OstTrace0( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_UICCGBANAFDERIVATIONAPDURESP, "CMmCustomMessHandler::UiccGBANafDerivationApduResp: unknown result" ); + ret = KErrGeneral; + } + } + else + { +TFLOGSTRING2("TSY: CMmCustomMessHandler::UiccGBABootstrapNafDerivationApduResp: UICC status not ok: 0x%x\n", aStatus ); +OstTrace1( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_UICCGBANAFDERIVATIONAPDURESP, "CMmCustomMessHandler::UiccGBANafDerivationApduResp: UICC status not ok: 0x%x", aStatus ); + ret = KErrMMEtelAuthenticateFailed; + } + + if( KErrNone == ret ) + { + CMmDataPackage dataPackage; + dataPackage.PackData( &gbaNafDerivation ); + + iMessageRouter->Complete( + ECustomGetSimAuthenticationDataIPC, + &dataPackage, + ret ); + } + else + { + iMessageRouter->Complete( + ECustomGetSimAuthenticationDataIPC, + ret ); + } + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccCreateMbmsMskUpdateApdu +// Constructs MBMS security context AUTHENTICATE APDU (MSK Update Mode) +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccCreateMbmsMskUpdateApdu( + TUiccSendApdu& params, + const CMmDataPackage& aDataPackage ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccCreateMbmsMskUpdateApdu.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCCREATEMBMSMSKUPDATEAPDU, "CMmCustomMessHandler::UiccCreateMbmsMskUpdateApdu" ); + + // Note. MBMS functionality is not tested in real hardware and in real environmen + // because of there is no users for this authentication type. So this is implemented + // with the best knowledge at the moment and it can contain some bugs which + // can be found when this is tested in real environment. + + RMmCustomAPI::TSimAuthenticationMgvMskUpdate mskUpdate; + aDataPackage.UnPackData( mskUpdate ); + + // len of data is MBMS Data Object tag (1 byte) + + // MBMS Data Object length (1 byte) + + // MBMS Security Context Mode (1 byte) + size of Mikey + TUint8 lc( 1 + 1 + 1 + mskUpdate.iMikey.Size() ); + + params.trId = ETrIdEMbmsMskUpdate; + params.apdu.Append( KClaNoSm ); // CLA + params.apdu.Append( KOddInstructionCode ); // INS + params.apdu.Append( KFirstBlockOfAuthenticationData ); // P1 + params.apdu.Append( KMBMSAuthenticationContext ); // P2 + params.apdu.Append( lc ); // Lc + params.apdu.Append( KMBMSDataObjectTag ); // MBMS Data object tag + params.apdu.Append( mskUpdate.iMikey.Size() + 1 ); // MBMS data obj len + params.apdu.Append( KMskUpdateMode ); // MBMS Security Context Mode + params.apdu.Append( mskUpdate.iMikey ); // Mikey + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccMbmsMskUpdateApduResp +// Handles response APDU for MBMS security context AUTHENTICATE APDU +// (MSK Update Mode) +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccMbmsMskUpdateApduResp( + TInt aStatus, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccMbmsMskUpdateApduResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCMBMSMSKUPDATEAPDURESP, "CMmCustomMessHandler::UiccMbmsMskUpdateApduResp" ); + + // Note. MBMS functionality is not tested in real hardware and in real environment + // because of at the moment there is no users for this authentication type. + // So this is implemented with the best knowledge at the moment and it can contain + // some bugs which can be found when this is tested in real environment. + + TInt ret( KErrGeneral ); + RMmCustomAPI::TSimAuthenticationMgvMskUpdate mskUpdate; + TBool completeNeeded( ETrue ); + + if( UICC_STATUS_OK == aStatus ) + { + // get SW1 and SW2 + TUint8 sw1( aFileData[aFileData.Length() - KSw1Position] ); + TUint8 sw2( aFileData[aFileData.Length() - KSw2Position] ); + + TUint8 result( MapSw1Sw2ToAuthenticateResult( sw1, sw2 ) ); + + switch( result ) + { + case KNormalCommandEnding: + case KWarningMoreDataAvailable: + { + TBuf8 mbmsOperationData; + + if( FindTlvObject( KMbmsOperationResponseTag53, aFileData.Mid( 0, aFileData.Length() - 2 ), mbmsOperationData ) || + FindTlvObject( KMbmsOperationResponseTag73, aFileData.Mid( 0, aFileData.Length() - 2 ), mbmsOperationData ) ) + { + ret = KErrNone; + mskUpdate.iMikey.Zero(); + if( KSuccessfullMbmsOperationTag == mbmsOperationData[0] ) + { + UiccMskUpdateHandleMbmsOperationData( mskUpdate, mbmsOperationData ); + } + else + { + UiccMskUpdateHandleOMABcastOperationData( mskUpdate, mbmsOperationData ); + } + } + break; + } + case KWarningAuthRespAvailable: + { + UiccCreateFirstBlockOfAuthRespApdu( ETrIdEMbmsMskUpdate ); + completeNeeded = EFalse; + break; + } + case KCmdNotAllowedConditionsNotSatisfied: + { + ret = KErrCustomSCCondOfuseNotSatisfied; + break; + } + case KAppErrorAuthMbmsOutOfMemMuk: + { + ret = KErrCustomSCNoMemSpaceAvailableMukAuthError; + break; + } + case KAppErrorAuthMbmsOutOfMemMsk: + { + ret = KErrCustomSCNoMemSpaceAvailableAuthError; + break; + } + case KAppAuthErrorIncorrectMac: + { + ret = KErrCustomSCIncorrectMACAuthError; + break; + } + case KWrongParametersDataNotFound: + { + ret = KErrCustomSCRefDataNotFound; + break; + } + default: + { + ret = KErrGeneral; + break; + } + } + } + else + { +TFLOGSTRING2("TSY: CMmCustomMessHandler::UiccMbmsMskUpdateApduResp: UICC status not ok: 0x%x\n", aStatus ); +OstTrace1( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_UICCMBMSMSKUPDATEAPDURESP, "CMmCustomMessHandler::UiccMbmsMskUpdateApduResp: UICC status not ok: 0x%x", aStatus ); + ret = KErrMMEtelAuthenticateFailed; + } + + if( completeNeeded ) + { + if( KErrNone == ret ) + { + CMmDataPackage dataPackage; + dataPackage.PackData( &mskUpdate ); + + iMessageRouter->Complete( + ECustomGetSimAuthenticationDataIPC, + &dataPackage, + ret ); + } + else + { + iMessageRouter->Complete( + ECustomGetSimAuthenticationDataIPC, + ret ); + } + } + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccMskUpdateHandleMbmsOperationData +// Handles MBMS operation data from MSK Update authenticate APDU +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccMskUpdateHandleMbmsOperationData( + RMmCustomAPI::TSimAuthenticationMgvMskUpdate& aMskUpdate, + TDesC8& aMbmsData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccMskUpdateHandleMbmsOperationData.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCMSKUPDATEHANDLEMBMSOPERATIONDATA, "CMmCustomMessHandler::UiccMskUpdateHandleMbmsOperationData" ); + + TUint8 index( 0 ); + TUint32 objLen( aMbmsData.Length() ); + + if( KSuccessfullMbmsOperationTag == aMbmsData[index] && + 1 <= objLen && + ( KMaxMbmsMikeyLen + 1 ) >= objLen ) // + 1 for 0xDB TLV tag + { + index++; + + // len of MIKEY is obj len - 1 because of + // obj data contains 1 byte for + // Successfull Mbms Operation Tag + TUint8 mikeyLen = objLen - 1; + if( 0 < mikeyLen ) + { + aMskUpdate.iMikey.Copy( aMbmsData.Mid( index, mikeyLen ) ); + } + } + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccMskUpdateHandleMbmsOperationData +// Handles OMA BCAST operation data from authenticate APDU +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccMskUpdateHandleOMABcastOperationData( + RMmCustomAPI::TSimAuthenticationMgvMskUpdate& aMskUpdate, + TDesC8& aMbmsData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccMskUpdateHandleOMABcastOperationData.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCMSKUPDATEHANDLEOMABCASTOPERATIONDATA, "CMmCustomMessHandler::UiccMskUpdateHandleOMABcastOperationData" ); + + TBuf8 omaBcastData; + + if( FindTlvObject( KOMABcastOperationResponseTag, aMbmsData, omaBcastData ) ) + { + TBuf8 bcastManagementData; + TBuf8 parentalRatingData; + TBuf8 speTypeNotSupportedData; + TBuf8 mikeyData; + + if( FindTlvObject( KBcastManagementDataTag, omaBcastData, bcastManagementData ) ) + { + aMskUpdate.iBCASTManagement.Copy( bcastManagementData ); + } + if( FindTlvObject( KParentalRatingDataTag, omaBcastData, parentalRatingData ) ) + { + aMskUpdate.iParentalRating.Copy( parentalRatingData ); + } + if( FindTlvObject( KSPETypeNotSupportedTag, omaBcastData, speTypeNotSupportedData ) ) + { + aMskUpdate.iSecurityPolicyExt.Copy( speTypeNotSupportedData ); + } + + if( FindTlvObject( KMikeyMessageTag, omaBcastData, mikeyData ) ) + { + aMskUpdate.iMikey.Copy( mikeyData ); + } + } + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccCreateMbmsMtkGenerationApdu +// Constructs MBMS security context AUTHENTICATE APDU (MTK Generation Mode) +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccCreateMbmsMtkGenerationApdu( + TUiccSendApdu& params, + const CMmDataPackage& aDataPackage ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccCreateMbmsMtkGenerationApdu.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCCREATEMBMSMTKGENERATIONAPDU, "CMmCustomMessHandler::UiccCreateMbmsMtkGenerationApdu" ); + + // Note. MBMS functionality is not tested in real hardware and in real environment + // because of at the moment there is no users for this authentication type. + // So this is implemented with the best knowledge at the moment and it can contain + // some bugs which can be found when this is tested in real environment. + + RMmCustomAPI::TSimAuthenticationMgvMtkGeneration mtkGen; + aDataPackage.UnPackData( mtkGen ); + + // len of data is MBMS Data Object tag (1 byte) + + // MBMS Data Object length (1 byte) + + // MBMS Security Context Mode (1 byte) + size of Mikey + TUint8 lc( 1 + 1 + 1 + mtkGen.iMikey.Size() ); + + params.trId = ETrIdEMbmsMtkGeneration; + params.apdu.Append( KClaNoSm ); // CLA + params.apdu.Append( KOddInstructionCode ); // INS + params.apdu.Append( KFirstBlockOfAuthenticationData ); // P1 + params.apdu.Append( KMBMSAuthenticationContext ); // P2 + params.apdu.Append( lc ); // Lc + params.apdu.Append( KMBMSDataObjectTag ); // MBMS Data object tag + params.apdu.Append( mtkGen.iMikey.Size() + 1 ); // MBMS data obj len + params.apdu.Append( KMtkGenerationMode ); // MBMS Security Context Mode + params.apdu.Append( mtkGen.iMikey ); // Mikey + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccMbmsMtkGenerationApduResp +// Handles response APDU for MBMS security context AUTHENTICATE APDU +// (MTK Generation Mode) +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccMbmsMtkGenerationApduResp( + TInt aStatus, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccMbmsMtkGenerationApduResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCMBMSMTKGENERATIONAPDURESP, "CMmCustomMessHandler::UiccMbmsMtkGenerationApduResp" ); + + // Note. MBMS functionality is not tested in real hardware and in real environment + // because of at the moment there is no users for this authentication type. + // So this is implemented with the best knowledge at the moment and it can contain + // some bugs which can be found when this is tested in real environment. + + TInt ret( KErrGeneral ); + RMmCustomAPI::TSimAuthenticationMgvMtkGeneration mtkGen; + TBool completeNeeded( ETrue ); + + if( UICC_STATUS_OK == aStatus ) + { + // get SW1 and SW2 + TUint8 sw1( aFileData[aFileData.Length() - KSw1Position] ); + TUint8 sw2( aFileData[aFileData.Length() - KSw2Position] ); + + TUint8 result( MapSw1Sw2ToAuthenticateResult( sw1, sw2 ) ); + + switch( result ) + { + case KNormalCommandEnding: + case KWarningMoreDataAvailable: + { + TBuf8 mbmsOperationData; + + if( FindTlvObject( KMbmsOperationResponseTag53, aFileData.Mid( 0, aFileData.Length() - 2 ), mbmsOperationData ) || + FindTlvObject( KMbmsOperationResponseTag73, aFileData.Mid( 0, aFileData.Length() - 2 ), mbmsOperationData ) ) + { + ret = KErrNone; + if( KSuccessfullMbmsOperationTag == mbmsOperationData[0] ) + { + UiccMtkGenHandleMbmsOperationData( mtkGen, mbmsOperationData ); + } + else + { + UiccMtkGenHandleOMABcastOperationData( mtkGen, mbmsOperationData ); + } + } + break; + } + case KWarningAuthRespAvailable: + { + UiccCreateFirstBlockOfAuthRespApdu( ETrIdEMbmsMtkGeneration ); + completeNeeded = EFalse; + break; + } + case KCmdNotAllowedConditionsNotSatisfied: + { + ret = KErrCustomSCCondOfuseNotSatisfied; + break; + } + case KAppErrorAuthMbmsKeyFresh: + { + ret = KErrCustomSCKeyRefreshFail; + break; + } + case KAppAuthErrorIncorrectMac: + { + ret = KErrCustomSCIncorrectMACAuthError; + break; + } + case KWrongParametersDataNotFound: + { + ret = KErrCustomSCRefDataNotFound; + break; + } + default: + { + ret = KErrGeneral; + break; + } + } + } + else + { +TFLOGSTRING2("TSY: CMmCustomMessHandler::UiccMbmsMtkGenerationApduResp: UICC status not ok: 0x%x\n", aStatus ); +OstTrace1( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_UICCMBMSMTKGENERATIONAPDURESP, "CMmCustomMessHandler::UiccMbmsMtkGenerationApduResp: UICC status not ok: 0x%x", aStatus ); + ret = KErrMMEtelAuthenticateFailed; + } + + if( completeNeeded ) + { + if( KErrNone == ret ) + { + CMmDataPackage dataPackage; + dataPackage.PackData( &mtkGen ); + + iMessageRouter->Complete( + ECustomGetSimAuthenticationDataIPC, + &dataPackage, + ret ); + } + else + { + iMessageRouter->Complete( + ECustomGetSimAuthenticationDataIPC, + ret ); + } + } + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccMtkGenHandleMbmsOperationData +// Handles MBMS operation data from MTK Generation authenticate APDU +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccMtkGenHandleMbmsOperationData( + RMmCustomAPI::TSimAuthenticationMgvMtkGeneration& aMtkGen, + TDesC8& aMbmsData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccMtkGenHandleMbmsOperationData.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCMTKGENHANDLEMBMSOPERATIONDATA, "CMmCustomMessHandler::UiccMtkGenHandleMbmsOperationData" ); + + TUint8 index( 0 ); + TUint32 objLen( aMbmsData.Length() ); + + if( KSuccessfullMbmsOperationTag == aMbmsData[index] && + 1 <= objLen && + ( KMaxMbmsSaltLen + 1 ) >= objLen ) // + 1 for 0xDB TLV tag + { + index++; + + // len of SALT is obj len - 1 because of + // obj data contains 1 byte for + // Successfull Mbms Operation Tag + TUint8 saltLen( objLen - 1 ); + if( 0 < saltLen ) + { + aMtkGen.iMtkSalt.Copy( aMbmsData.Mid( index, saltLen ) ); + } + } + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccMtkGenHandleOMABcastOperationData +// Handles OMA BCAST operation data from authenticate APDU +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccMtkGenHandleOMABcastOperationData( + RMmCustomAPI::TSimAuthenticationMgvMtkGeneration& aMtkGen, + TDesC8& aMbmsData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccMtkGenHandleOMABcastOperationData.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCMTKGENHANDLEOMABCASTOPERATIONDATA, "CMmCustomMessHandler::UiccMtkGenHandleOMABcastOperationData" ); + + TBuf8 omaBcastData; + + if( FindTlvObject( KOMABcastOperationResponseTag, aMbmsData, omaBcastData ) ) + { + TBuf8 bcastManagementData; + TBuf8 tekData; + TBuf8 saltData; + TBuf8 parentalControlData; + + if( FindTlvObject( KBcastManagementDataTag, omaBcastData, bcastManagementData ) ) + { + aMtkGen.iBCASTManagement.Copy( bcastManagementData ); + } + if( FindTlvObject( KTekDataTag, omaBcastData, tekData ) ) + { + aMtkGen.iTrafficEncryptionKey.Copy( tekData ); + } + if( FindTlvObject( KParentalControlTag, omaBcastData, parentalControlData ) ) + { + // first parameter of parental control data is "key reference for second + // application PIN defined for parental contol" but it's not supported + // at the moment + aMtkGen.iParentalControl.Append( parentalControlData[1] ); // rating type + aMtkGen.iParentalControl.Append( parentalControlData[2] ); // rating value + aMtkGen.iParentalControl.Append( parentalControlData[3] ); // level granted value + } + if( FindTlvObject( KSaltDataTag, omaBcastData, saltData ) ) + { + aMtkGen.iMtkSalt.Copy( saltData ); + } + } + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccCreateMbmsMskDeletionApdu +// Constructs MBMS security context AUTHENTICATE APDU (MSK Deletion Mode) +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccCreateMbmsMskDeletionApdu( + TUiccSendApdu& params, + const CMmDataPackage& aDataPackage ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccCreateMbmsMskDeletionApdu.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCCREATEMBMSMSKDELETIONAPDU, "CMmCustomMessHandler::UiccCreateMbmsMskDeletionApdu" ); + + // Note. MBMS functionality is not tested in real hardware and in real environment + // because of at the moment there is no users for this authentication type. + // So this is implemented with the best knowledge at the moment and it can contain + // some bugs which can be found when this is tested in real environment. + + RMmCustomAPI::TSimAuthenticationMgvMskDeletion mskDel; + aDataPackage.UnPackData( mskDel ); + + // len of data is MBMS Data Object tag (1 byte) + + // MBMS Data Object length (1 byte) + + // MBMS Security Context Mode (1 byte) + + // size of Key Domain Id + size of Key Group Id Part + TUint8 lc( 1 + + 1 + + 1 + + mskDel.iKeyDomainId.Size() + + mskDel.iKeyGroupIdPart.Size() ); + + // data size in MBMS Data Object Tag is: + // MBMS Security Context Mode (1 byte) + + // size of Key Domain Id + size of Key Group Id Part + TUint8 dataSize( 1 + + mskDel.iKeyDomainId.Size() + + mskDel.iKeyGroupIdPart.Size() ); + + params.trId = ETrIdEMbmsMskDeletion; + params.apdu.Append( KClaNoSm ); // CLA + params.apdu.Append( KOddInstructionCode ); // INS + params.apdu.Append( KFirstBlockOfAuthenticationData ); // P1 + params.apdu.Append( KMBMSAuthenticationContext ); // P2 + params.apdu.Append( lc ); // Lc + params.apdu.Append( KMBMSDataObjectTag ); // MBMS Data object tag + params.apdu.Append( dataSize ); // MBMS data obj len + params.apdu.Append( KMskDeletionMode ); // MBMS Security Context Mode + params.apdu.Append( mskDel.iKeyDomainId ); // Key Domain Id + params.apdu.Append( mskDel.iKeyGroupIdPart ); // Key Group Id + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccMbmsMskDeletionApduResp +// Handles response APDU for MBMS security context AUTHENTICATE APDU +// (MSK Deletion Mode) +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccMbmsMskDeletionApduResp( + TInt aStatus, + const TDesC8& aFileData ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccMbmsMskDeletionApduResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCMBMSMSKDELETIONAPDURESP, "CMmCustomMessHandler::UiccMbmsMskDeletionApduResp" ); + + // Note. MBMS functionality is not tested in real hardware and in real environment + // because of at the moment there is no users for this authentication type. + // So this is implemented with the best knowledge at the moment and it can contain + // some bugs which can be found when this is tested in real environment. + + TInt ret( KErrGeneral ); + RMmCustomAPI::TSimAuthenticationMgvMskDeletion mskDel; + TBool completeNeeded( ETrue ); + + if( UICC_STATUS_OK == aStatus ) + { + // get SW1 and SW2 + TUint8 sw1( aFileData[aFileData.Length() - KSw1Position] ); + TUint8 sw2(aFileData[aFileData.Length() - KSw2Position] ); + + TUint8 result( MapSw1Sw2ToAuthenticateResult( sw1, sw2 ) ); + + switch( result ) + { + case KNormalCommandEnding: + { + TBuf8 mbmsOperationData; + + if( FindTlvObject( KMbmsOperationResponseTag53, aFileData.Mid( 0, aFileData.Length() - 2 ), mbmsOperationData ) ) + { + if( KSuccessfullMbmsOperationTag == mbmsOperationData[0] ) + { + ret = KErrNone; + } + } + break; + } + case KWarningAuthRespAvailable: + { + UiccCreateFirstBlockOfAuthRespApdu( ETrIdEMbmsMskDeletion ); + completeNeeded = EFalse; + break; + } + case KWrongParametersDataNotFound: + { + ret = KErrCustomSCRefDataNotFound; + break; + } + default: + { + ret = KErrGeneral; + break; + } + } + } + else + { +TFLOGSTRING2("TSY: CMmCustomMessHandler::UiccMbmsMskDeletionApduResp: UICC status not ok: 0x%x\n", aStatus ); +OstTrace1( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_UICCMBMSMSKDELETIONAPDURESP, "CMmCustomMessHandler::UiccMbmsMskDeletionApduResp: UICC status not ok: 0x%x", aStatus ); + ret = KErrMMEtelAuthenticateFailed; + } + + if( completeNeeded ) + { + if( KErrNone == ret ) + { + CMmDataPackage dataPackage; + dataPackage.PackData( &mskDel ); + + iMessageRouter->Complete( + ECustomGetSimAuthenticationDataIPC, + &dataPackage, + ret ); + } + else + { + iMessageRouter->Complete( + ECustomGetSimAuthenticationDataIPC, + ret ); + } + } + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccCreateFirstBlockOfAuthRespApdu +// Constructs APDU to get authenticate response data in case of odd ins code +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccCreateFirstBlockOfAuthRespApdu( TUiccTrId aTrId ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccCreateFirstBlockOfAuthRespApdu.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCCREATEFIRSTBLOCKOFAUTHRESPAPDU, "CMmCustomMessHandler::UiccCreateFirstBlockOfAuthRespApdu" ); + + // Fill parameters to instance created from TUiccSendApdu + // needed for APDU sending + TUiccSendApdu params; + params.messHandlerPtr = static_cast( this ); + params.serviceType = UICC_APPL_APDU_SEND; + params.fileId = UICC_EF_ID_NOT_PRESENT; + params.fileIdSfi = UICC_SFI_NOT_PRESENT; + params.filePath.Append( KMasterFileId >> 8 ); + params.filePath.Append( KMasterFileId ); + params.filePath.Append( iMmUiccMessHandler->GetApplicationFileId() ); + + params.trId = aTrId; + params.apdu.Append( KClaNoSm ); // CLA + params.apdu.Append( KOddInstructionCode ); // INS + params.apdu.Append( KFirstBlockOfAuthenticationResponseData ); // P1 + params.apdu.Append( 0x00 ); // P2 + params.apdu.Append( 0x00 ); // Le + + iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::MapSw1Sw2ToAuthenticateResult +// Maps sw1 and sw2 from response authenticate apdu to result +// ----------------------------------------------------------------------------- +// +TUint8 CMmCustomMessHandler::MapSw1Sw2ToAuthenticateResult( TUint8 sw1, TUint8 sw2 ) + { +TFLOGSTRING3("TSY: CMmCustomMessHandler::MapSw1Sw2ToAuthenticateResult. sw1: 0x%x sw2: 0x%x\n", sw1, sw2 ); +OstTraceExt2( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_MAPSW1SW2TOAUTHENTICATERESULT, "CMmCustomMessHandler::MapSw1Sw2ToAuthenticateResult. sw1: 0x%x sw2: 0x%x", sw1, sw2 ); + + TUint8 ret( KUnknownCommandEnding ); + + switch( sw1 ) + { + case 0x90: + { + if( 0x00 == sw2 ) + { + ret = KNormalCommandEnding; + } + break; + } + case 0x62: + { + if( 0x00 == sw2 ) + { + ret = KNormalCommandEnding; + } + else if( 0xF1 == sw2 || + 0xF2 == sw2 ) + { + ret = KWarningMoreDataAvailable; + } + else if( 0xF3 == sw2 ) + { + ret = KWarningAuthRespAvailable; + } + break; + } + case 0x91: + { + ret = KNormalCommandEnding; + break; + } + case 0x98: + { + if( 0x62 == sw2 ) + { + ret = KAppAuthErrorIncorrectMac; + } + else if( 0x65 == sw2 ) + { + ret = KAppErrorAuthMbmsKeyFresh; + } + else if( 0x66 == sw2 ) + { + ret = KAppErrorAuthMbmsOutOfMemMsk; + } + else if( 0x67 == sw2 ) + { + ret = KAppErrorAuthMbmsOutOfMemMuk; + } + break; + } + case 0x69: + { + if( 0x82 == sw2 ) + { + ret = KCmdNotAllowedSecurityStatusNotSatisfied; + } + else if( 0x85 == sw2 ) + { + ret = KCmdNotAllowedConditionsNotSatisfied; + } + break; + } + case 0x6A: + { + if( 0x88 == sw2 ) + { + ret = KWrongParametersDataNotFound; + } + break; + } + default: + { + break; + } + } + + return ret; + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::ValidateReceivedAuthenticateApdu +// Validates received apdu +// ----------------------------------------------------------------------------- +// +TUint8 CMmCustomMessHandler::ValidateReceivedAuthenticateApdu( + TInt aTraId, + const TDesC8& aApdu ) + { + TUint8 ret( KApduOk ); + + switch( aTraId ) + { + case ETrIdEEapSimAuthenticate: + { + ret = ValidateGsmSecurityContextApduResp( aApdu ); + break; + } + case ETrIdEEapAkaAuthenticate: + case ETrIdEEapAkaAuthenticateIms: + { + ret = Validate3GSecurityContextApduResp( aApdu ); + break; + } + case ETrIdEGbaBootstrap: + { + ret = ValidateGBABootstrappingApduResp( aApdu ); + break; + } + case ETrIdEGbaNafDerivation: + { + ret = ValidateGBANafDerivationApduResp( aApdu ); + break; + } + case ETrIdRunGsmAlgorithmSim: + case ETrIdRunGsmAlgorithmAka: + case ETrIdRunGsmAlgorithmIms: + { + ret = ValidateRunGsmAlgorithmApduResp( aApdu ); + break; + } + default: + { +TFLOGSTRING("TSY: CMmCustomMessHandler::ValidateReceivedAuthenticateApdu: unknown APDU\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_VALIDATERECEIVEDAUTHENTICATEAPDU, "CMmCustomMessHandler::ValidateReceivedAuthenticateApdu: unknown APDU" ); + ret = KApduNok; + break; + } + } + return ret; + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::ValidateGsmSecurityContextApduResp +// Validates received apdu +// ----------------------------------------------------------------------------- +// +TUint8 CMmCustomMessHandler::ValidateGsmSecurityContextApduResp( const TDesC8& aApdu ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::ValidateGsmSecurityContextApduResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_VALIDATEGSMSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::ValidateGsmSecurityContextApduResp" ); + TUint8 ret( KApduNok ); + + // apdu len is len of aApdu - 2 (because of + // aApdu contains sw1 and sw2) + TUint apduLen( aApdu.Length() - 2 ); + TUint32 index( 0 ); + + index += aApdu[index] + 1; + TUint8 lenOfKc = aApdu[index++]; + + if( KLenOfKc == lenOfKc && index + lenOfKc == apduLen ) + { + ret = KApduOk; + } + + return ret; + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::Validate3GSecurityContextApduResp +// Validates received apdu +// ----------------------------------------------------------------------------- +// +TUint8 CMmCustomMessHandler::Validate3GSecurityContextApduResp( const TDesC8& aApdu ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::Validate3GSecurityContextApduResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_VALIDATE3GSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::Validate3GSecurityContextApduResp" ); + + TUint8 ret( KApduOk ); + + // Let's calculate total APDU data len in aApdu. Length is + // decremented by 2 because of aApdu contains also sw1 and sw2 + // and these are total 2 bytes long. + TUint8 apduLen( aApdu.Length() - 2 ); + TUint32 index( 0 ); + TUint8 tag( aApdu[index++] ); + + if( KSuccessfull3GAuthTag == tag ) + { + // check the len of RES + if( KMinLenOfRes > aApdu[index] || KMaxLenOfRes < aApdu[index] ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::Validate3GSecurityContextApduResp: invalid RES\n" ); +OstTrace0( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_VALIDATE3GSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::Validate3GSecurityContextApduResp: invalid RES" ); + ret = KApduNok; + } + else + { + // move pointer to field length of CK + index += aApdu[index] + 1; + } + + // check the len of CK + if( KApduNok == ret || + KLenOfCk != aApdu[index] ) + { + if( KApduNok != ret ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::Validate3GSecurityContextApduResp: invalid CK\n" ); +OstTrace0( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_VALIDATE3GSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::Validate3GSecurityContextApduResp: invalid CK" ); + ret = KApduNok; + } + } + else + { + // move pointer to field length of IK + index += aApdu[index] + 1; + } + + // check the len of IK + if( KApduNok == ret || + KLenOfIk != aApdu[index] ) + { + if( KApduNok != ret ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::Validate3GSecurityContextApduResp: invalid IK\n" ); +OstTrace0( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_VALIDATE3GSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::Validate3GSecurityContextApduResp: invalid IK" ); + ret = KApduNok; + } + } + else + { + // move pointer to end of IK + index += aApdu[index]; + } + + // check the len of Kc if present. + // This parameter is only present + // when service nro 27 is available + if( KApduOk == ret && index < apduLen - 1 ) + { + // move pointer to field length of Kc + index++; + + // check the len of Kc + if( KLenOfKc != aApdu[index] ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::Validate3GSecurityContextApduResp: invalid Kc\n" ); +OstTrace0( TRACE_NORMAL, DUP4_CMMCUSTOMMESSHANDLER_VALIDATE3GSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::Validate3GSecurityContextApduResp: invalid Kc" ); + ret = KApduNok; + } + else + { + // move pointer to end of Kc + index += aApdu[index]; + } + } + + // let's check that pointer doesn't go over + // aApdu's limits. + if( KApduOk == ret && index > apduLen - 1 ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::Validate3GSecurityContextApduResp: error, APDU buffer overflow\n" ); +OstTrace0( TRACE_NORMAL, DUP5_CMMCUSTOMMESSHANDLER_VALIDATE3GSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::Validate3GSecurityContextApduResp: error, APDU buffer overflow" ); + ret = KApduNok; + } + } + + else if(KSyncFailureTag == tag) + { + // check the len of AUTS + if( KLenOfAuts != aApdu[index]) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::Validate3GSecurityContextApduResp: invalid AUTS\n" ); +OstTrace0( TRACE_NORMAL, DUP6_CMMCUSTOMMESSHANDLER_VALIDATE3GSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::Validate3GSecurityContextApduResp: invalid AUTS" ); + ret = KApduNok; + } + else + { + // move pointer to end of AUTS + index += aApdu[index]; + } + + // let's check that pointer doesn't go over + // aApdu's limits. + if( KApduOk == ret && index > apduLen - 1 ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::Validate3GSecurityContextApduResp: error, APDU buffer overflow\n" ); +OstTrace0( TRACE_NORMAL, DUP7_CMMCUSTOMMESSHANDLER_VALIDATE3GSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::Validate3GSecurityContextApduResp: error, APDU buffer overflow" ); + ret = KApduNok; + } + } + else + { +TFLOGSTRING("TSY: CMmCustomMessHandler::Validate3GSecurityContextApduResp: error, unknown tag\n" ); +OstTrace0( TRACE_NORMAL, DUP8_CMMCUSTOMMESSHANDLER_VALIDATE3GSECURITYCONTEXTAPDURESP, "CMmCustomMessHandler::Validate3GSecurityContextApduResp: error, unknown tag" ); + ret = KApduNok; + } + + return ret; + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::ValidateGBABootstrappingApduResp +// Validates received apdu +// ----------------------------------------------------------------------------- +// +TUint8 CMmCustomMessHandler::ValidateGBABootstrappingApduResp( const TDesC8& aApdu ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::ValidateGBABootstrappingApduResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_VALIDATEGBABOOTSTRAPPINGAPDURESP, "CMmCustomMessHandler::ValidateGBABootstrappingApduResp" ); + + TUint8 ret( KApduNok ); + + // Let's calculate total APDU data len in aApdu. Length is + // decremented by 2 because of aApdu contains also sw1 and sw2 + // and these are total 2 bytes long. + TUint8 apduLen( aApdu.Length() - 2 ); + TUint32 index( 0 ); + TUint8 tag( aApdu[index++] ); + + if( apduLen > 1 ) + { + if( KSuccessfull3GAuthTag == tag || + KSyncFailureTag == tag ) + { + if( apduLen >= aApdu[index] ) + { + ret = KApduOk; + } + } + } + return ret; + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::ValidateGBANafDerivationApduResp +// Validates received apdu +// ----------------------------------------------------------------------------- +// +TUint8 CMmCustomMessHandler::ValidateGBANafDerivationApduResp( const TDesC8& aApdu ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::ValidateGBANafDerivationApduResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_VALIDATEGBANAFDERIVATIONAPDURESP, "CMmCustomMessHandler::ValidateGBANafDerivationApduResp" ); + + TUint8 ret = KApduNok; + + // Let's calculate total APDU data len in aApdu. Length is + // decremented by 2 because of aApdu contains also sw1 and sw2 + // and these are total 2 bytes long. + TUint8 apduLen( aApdu.Length() - 2 ); + TUint32 index( 0 ); + TUint8 tag( aApdu[index++] ); + + if( apduLen > 1 ) + { + if( KSuccessfull3GAuthTag == tag ) + { + // response apdu contains only parameter Ks Ext NAF + // so, let's check that apdu len contains parameter + // correctly. So apduLen should be len of Ks Ext NAF + // + 2 ("Successful GBA operation" field + + // Length of Ks_ext_NAF field) + if( apduLen == aApdu[index] + 2 ) + { + ret = KApduOk; + } + } + } + return ret; + } + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::ValidateRunGsmAlgorithmApduResp +// Validates received apdu +// ----------------------------------------------------------------------------- +// +TUint8 CMmCustomMessHandler::ValidateRunGsmAlgorithmApduResp( const TDesC8& aApdu ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::ValidateRunGsmAlgorithmApduResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_VALIDATERUNGSMALGORITHMAPDURESP, "CMmCustomMessHandler::ValidateRunGsmAlgorithmApduResp" ); + + TUint8 ret( KApduNok ); + + if( aApdu.Length() == KRunGsmAlgorithmRespLen + 2 ) + { + ret = KApduOk; + } + return ret; + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::FindTlvObject +// Finds TLV object +// ----------------------------------------------------------------------------- +// +TBool CMmCustomMessHandler::FindTlvObject( + TUint8 aTlvTag, + const TDesC8& aBerTlv, + TDes8& aTlvObject ) + { +TFLOGSTRING2("TSY: CMmCustomMessHandler::FindTlvObject (tag: 0x%x)\n", aTlvTag ); +OstTrace1( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_FINDTLVOBJECT, "CMmCustomMessHandler::FindTlvObject (tag: 0x%x)", aTlvTag ); + + TBool ret( EFalse ); + TUint32 index( 0 ); + TUint8 tag( 0 ); + TUint32 tlvLength( 0 ); + + while( index + 2 < aBerTlv.Length() ) + { + tag = aBerTlv[index++]; + tlvLength = aBerTlv[index++]; + + // let's check if len of tlv object is coded + // with one or two bytes + if( 0x81 == tlvLength || + 0x82 == tlvLength ) + { + TUint8 byteCount( tlvLength & 0x7F ); + TUint8 ind( 0 ); + tlvLength = 0; + do + { + tlvLength = tlvLength << 8; + tlvLength = tlvLength + aBerTlv[index++]; + ind++; + } + while ( ind < byteCount ); + } + + if( tag == aTlvTag ) + { + if( index + tlvLength <= aBerTlv.Length() ) + { + if( tlvLength <= aTlvObject.MaxSize() ) + { + // tlv object found +TFLOGSTRING2("TSY: CMmCustomMessHandler::FindTlvObject: tag: 0x%x found\n", aTlvTag ); +OstTrace1( TRACE_NORMAL, DUP1_CMMCUSTOMMESSHANDLER_FINDTLVOBJECT, "CMmCustomMessHandler::FindTlvObject: tag: 0x%x found", aTlvTag ); + aTlvObject.Copy( aBerTlv.Mid( index , tlvLength ) ); + ret = ETrue; + } + else + { +TFLOGSTRING3("TSY: CMmCustomMessHandler::FindTlvObject: length of aTlvObject is not enough, needed: %d max size: %d \n", tlvLength, aTlvObject.MaxSize() ); +OstTrace0( TRACE_NORMAL, DUP2_CMMCUSTOMMESSHANDLER_FINDTLVOBJECT, "CMmCustomMessHandler::FindTlvObject: length of aTlvObject is not enough" ); +OstTrace1( TRACE_NORMAL, DUP3_CMMCUSTOMMESSHANDLER_FINDTLVOBJECT, "CMmCustomMessHandler::FindTlvObject: needed: %d", tlvLength ); +OstTrace1( TRACE_NORMAL, DUP4_CMMCUSTOMMESSHANDLER_FINDTLVOBJECT, "CMmCustomMessHandler::FindTlvObject: max size: %d", aTlvObject.MaxSize() ); + } + } + else + { +TFLOGSTRING("TSY: CMmCustomMessHandler::FindTlvObject: buffer overflow \n" ); +OstTrace0( TRACE_NORMAL, DUP5_CMMCUSTOMMESSHANDLER_FINDTLVOBJECT, "CMmCustomMessHandler::FindTlvObject: buffer overflow" ); + } + break; + } + else + { + index += tlvLength; + } + } + + return ret; + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::DeriveCkFromKc +// derives Ck from Kc +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::DeriveCkFromKc( + TDes8& aCk, + const TDesC8& aKc ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::DeriveCkFromKc.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_DERIVECKFROMKC, "CMmCustomMessHandler::DeriveCkFromKc" ); + + /* This operation calculates the UMTS Ciphering Key (CK) from the GSM + Ciphering Key (Kc). This is done by using the c4 algorithm defined in + 3GPP TS 33.102 v3.8.0 (Release 1999). + + c4: CK = Kc || Kc; + where || means concatination. + + The resulting CK is as follows: + ----------------------------------------------------------------- + |kc1|kc2|kc3|kc4|kc5|kc6|kc7|kc8|kc1|kc2|kc3|kc4|kc5|kc6|kc7|kc8| + ----------------------------------------------------------------- */ + aCk.Copy( aKc ); + aCk.Append( aKc ); + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::DeriveIkFromKc +// derives Ck from Kc +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::DeriveIkFromKc( + TDes8& aIk, + const TDesC8& aKc ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::DeriveIkFromKc.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_DERIVEIKFROMKC, "CMmCustomMessHandler::DeriveIkFromKc" ); + + /* This operation derives the UMTS Integrity Key (IK) from the GSM + Ciphering Key (Kc). This is done by using the c5 algorithm defined in + 3GPP TS 33.102 v3.8.0 (release 1999). + + c5: IK = Kc1 xor Kc2 || Kc || Kc1 xor Kc2; + where Kc1 and Kc2 are both 4 bytes long and || means concatination. + + |--------------> Kc 8 bytes <-----------| + ----------------------------------------- + | B1 | B2 | B3 | B4 | B5 | B6 | B7 | B8 | + ----------------------------------------- + |--> Kc1,4 bytes <--|--> Kc2,4 bytes <--| + + Kx = Kc1 xor Kc2 + + The resulting IK is as follows: + + |-----------------------> IK, 16 bytes <------------------------| + ----------------------------------------------------------------- + |Kx1|Kx2|Kx3|Kx4|Kc1|Kc2|Kc3|Kc4|Kc5|Kc6|Kc7|Kc8|Kx1|Kx2|Kx3|Kx4| + ----------------------------------------------------------------- + |----> Kx <-----|------------> Kc <-------------|-----> Kx <----| */ + + TBuf8 kc1; + TBuf8 kc2; + TBuf8 kx; + + kc1.Copy( aKc.Mid( 0, 4 ) ); + kc2.Copy( aKc.Mid( 4, 4 ) ); + + for ( TUint8 i = 0; i < 4; i++ ) + { + kx.Append( kc1[i] ^ kc2[i] ); + } + + aIk.Append( kx ); + aIk.Append( aKc ); + aIk.Append( kx ); + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::DeriveIkFromKc +// derives Ck from Kc +// ----------------------------------------------------------------------------- +// +TInt CMmCustomMessHandler::UiccHandleImsAuthentication( + const CMmDataPackage& aDataPackage ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccHandleImsAuthentication.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCHANDLEIMSAUTHENTICATION, "CMmCustomMessHandler::UiccHandleImsAuthentication" ); + TInt ret( KErrNone ); + + // IMS authentication: + // If card type is ICC, we just send the RUN GSM ALGORITHM to the ICC + // If card type is UICC, we check is ISIM application activated: + // * If ISIM application is activated, we send 3G security context + // to the ISIM application. + // * If ISIM application is NOT activated, we try to activate it. + // * If actication succeeded, we send 3G security context to the + // ISIM application + // * If activation fails, we send 3G security context to the USIM + // application + + RMobilePhone::TImsAuthenticateDataV5 authenticationData; + aDataPackage.UnPackData( authenticationData ); + + TUiccSendApdu params; + params.messHandlerPtr = static_cast( this ); + params.serviceType = UICC_APPL_APDU_SEND; + params.fileId = UICC_EF_ID_NOT_PRESENT; + params.fileIdSfi = UICC_SFI_NOT_PRESENT; + params.filePath.Append( KMasterFileId >> 8 ); + params.filePath.Append( KMasterFileId ); + params.filePath.Append( iMmUiccMessHandler->GetApplicationFileId() ); + + TUint8 cardType( iMmUiccMessHandler->GetCardType() ); + + if( UICC_CARD_TYPE_ICC == cardType ) + { + // no need to activate ISIM application, + // let's just send the authentication APDU + UiccCreateRunGsmAlgorithmApdu( + params, + authenticationData.iRAND, + ETrIdRunGsmAlgorithmIms ); + + ret = iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + else if( UICC_CARD_TYPE_UICC == cardType ) + { + // let's store RAND and AUTN while we try to acticate + // ISIM application + RMobilePhone::TImsAuthenticateDataV5 authenticationData; + aDataPackage.UnPackData( authenticationData ); + + if( iMmUiccMessHandler->IsIsimApplicationFound() ) + { + // let's check is ISIM application already tried to activate + if( iIsimApplActivated ) + { + UiccCreate3GSecurityContextApdu( + params, + authenticationData.iRAND, + authenticationData.iAUTN, + ETrIdEEapAkaAuthenticateIms ); + + ret = iMmUiccMessHandler->CreateUiccApplCmdReq( params, UICC_APPL_TYPE_UICC_ISIM ); + } + else + { + iRandBuf.Zero(); + iAutnBuf.Zero(); + + iRandBuf.Append( authenticationData.iRAND ); + iAutnBuf.Append( authenticationData.iAUTN ); + + TUiccParamsBase activationParams; + activationParams.messHandlerPtr = static_cast( this ); + activationParams.trId = ETrIdActivateIsimApplication; + + ret = iMmUiccMessHandler->CreateUiccApplicationReq( + activationParams, + UICC_APPL_HOST_ACTIVATE, + UICC_APPL_TYPE_UICC_ISIM ); + } + } + else + { + // no ISim application, let's send authenticate apdu to the Uicc application + UiccCreate3GSecurityContextApdu( + params, + authenticationData.iRAND, + authenticationData.iAUTN, + ETrIdEEapAkaAuthenticateIms ); + + ret = iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + } + else + { + ret = KErrGeneral; + } + return ret; + } + + +// ----------------------------------------------------------------------------- +// CMmCustomMessHandler::UiccHandleIsimActivationResp +// handles repsonse for ISim application activation +// ----------------------------------------------------------------------------- +// +void CMmCustomMessHandler::UiccHandleIsimActivationResp( TInt aStatus ) + { +TFLOGSTRING("TSY: CMmCustomMessHandler::UiccHandleIsimActivationResp.\n" ); +OstTrace0( TRACE_NORMAL, CMMCUSTOMMESSHANDLER_UICCHANDLEISIMACTIVATIONRESP, "CMmCustomMessHandler::UiccHandleIsimActivationResp" ); + + TUiccSendApdu params; + params.messHandlerPtr = static_cast( this ); + params.serviceType = UICC_APPL_APDU_SEND; + params.fileId = UICC_EF_ID_NOT_PRESENT; + params.fileIdSfi = UICC_SFI_NOT_PRESENT; + params.filePath.Append( KMasterFileId >> 8 ); + params.filePath.Append( KMasterFileId ); + params.filePath.Append( iMmUiccMessHandler->GetApplicationFileId() ); + + UiccCreate3GSecurityContextApdu( + params, + iRandBuf, + iAutnBuf, + ETrIdEEapAkaAuthenticateIms ); + + if( UICC_STATUS_OK == aStatus ) + { + iIsimApplActivated = ETrue; + + // ISim application activated successfully, let's send authentication apdu + // to the ISim application + iMmUiccMessHandler->CreateUiccApplCmdReq( params, UICC_APPL_TYPE_UICC_ISIM ); + } + else + { + // ISim application activation fails, le'ts send authentication apdu + // to the USim application + iMmUiccMessHandler->CreateUiccApplCmdReq( params ); + } + } + +// ========================== OTHER EXPORTED FUNCTIONS ========================= + //None + +// End of File