FreeCalypso > hg > fc-magnetite
view src/aci2/aci/cmh_sims.c @ 478:5e39123540e6
hybrid fw: Openmoko-mimicking AT@BAND command implemented
author | Mychaela Falconia <falcon@freecalypso.org> |
---|---|
date | Thu, 14 Jun 2018 06:04:54 +0000 |
parents | 93999a60b835 |
children |
line wrap: on
line source
/* +----------------------------------------------------------------------------- | Project : GSM-PS (6147) | Modul : CMH_SIMS +----------------------------------------------------------------------------- | Copyright 2002 Texas Instruments Berlin, AG | All rights reserved. | | This file is confidential and a trade secret of Texas | Instruments Berlin, AG | The receipt of or possession of this file does not convey | any rights to reproduce or disclose its contents or to | manufacture, use, or sell anything it may describe, in | whole, or in part, without the specific written consent of | Texas Instruments Berlin, AG. +----------------------------------------------------------------------------- | Purpose : This module provides the set functions related to the | protocol stack adapter for the subscriber identity | module. +----------------------------------------------------------------------------- */ #ifndef CMH_SIMS_C #define CMH_SIMS_C #endif #include "aci_all.h" /*==== INCLUDES ===================================================*/ #include "aci_cmh.h" #ifdef UART #include "dti.h" /* functionality of the dti library */ #include "dti.h" #include "dti_conn_mng.h" #endif #include "ati_cmd.h" #ifdef FF_ATI #include "aci_io.h" #endif /* of #ifdef FF_ATI */ #ifdef FAX_AND_DATA #include "aci_fd.h" #endif /* of #ifdef FAX_AND_DATA */ #include "psa.h" #include "psa_sim.h" #include "psa_mm.h" #include "cmh.h" #include "cmh_sim.h" #include "cmh_mm.h" #ifdef GPRS #include "dti_cntrl_mng.h" #include "gaci.h" #include "gaci_cmh.h" #include "psa_gmm.h" #include "cmh_gmm.h" #endif /* #include "m_fac.h" */ #include "aoc.h" #include "ati_cmd.h" #include "aci_cmd.h" #include "phb.h" #include "aci_ext_pers.h" #include "aci_slock.h" #include "cl_imei.h" #ifdef SIM_PERS #include "general.h" // included for compilation error UNIT8 in sec_drv.h #include "sec_drv.h" #include "cmh.h" #include "aci_cmh.h" EXTERN T_SIM_MMI_INSERT_IND *last_sim_mmi_insert_ind; EXTERN T_SEC_DRV_CATEGORY *personalisation_nw; EXTERN T_SEC_DRV_CATEGORY *personalisation_ns; EXTERN T_SEC_DRV_CATEGORY *personalisation_sp; EXTERN T_SEC_DRV_CATEGORY *personalisation_cp; EXTERN T_SEC_DRV_CATEGORY *personalisation_sim; EXTERN T_SEC_DRV_CONFIGURATION *cfg_data ; #endif /*==== CONSTANTS ==================================================*/ /*==== EXPORT =====================================================*/ /*==== VARIABLES ==================================================*/ /*==== FUNCTIONS ==================================================*/ /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6147) MODULE : CMH_SIMS | | STATE : code ROUTINE : sAT_PlusCFUN | +--------------------------------------------------------------------+ PURPOSE : This is the functional counterpart to the +CFUN AT command which is responsible to set the phone functionality. <fun>: defines the level of functionality to switch to. <rst>: reset mode */ GLOBAL T_ACI_RETURN sAT_PlusCFUN ( T_ACI_CMD_SRC srcId, T_ACI_CFUN_FUN fun, T_ACI_CFUN_RST rst ) { T_SIM_SET_PRM * pSIMSetPrm; /* points to MM parameter set */ T_ACI_RETURN retCd; /* holds return code */ UBYTE idx; /* holds index value */ /* variables for IMEI control mechanism */ #ifndef _SIMULATION_ BYTE retVal; /* holds return value */ UBYTE dummyIMEIBuf[CL_IMEI_SIZE]; /* dummy IMEI buffer */ #endif /* if NOT defined windows simulation */ TRACE_FUNCTION ("sAT_PlusCFUN()"); #ifndef _SIMULATION_ /* *------------------------------------------------------------------- * check IMEI *------------------------------------------------------------------- */ retVal = cl_get_imeisv(CL_IMEI_SIZE, dummyIMEIBuf, CL_IMEI_CONTROL_IMEI); if( retVal NEQ CL_IMEI_OK ) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_IMEICheck ); TRACE_EVENT("IMEI not valid"); simShrdPrm.imei_blocked = TRUE; /*return( AT_FAIL ); We dont return here to enable the stack to go to the state of "Limited Service' to enable emergency calls. */ } #endif /* if NOT defined windows simulation */ /* *------------------------------------------------------------------- * check command source *------------------------------------------------------------------- */ if(!cmh_IsVldCmdSrc (srcId)) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } pSIMSetPrm = &simShrdPrm.setPrm[srcId]; /* *------------------------------------------------------------------- * check entity status *------------------------------------------------------------------- */ if( simEntStat.curCmd NEQ AT_CMD_NONE ) { TRACE_EVENT("Entity SIM is busy: cannot proceed command..."); return( AT_BUSY ); } /* *------------------------------------------------------------------- * process the <rst> parameter *------------------------------------------------------------------- */ switch( rst ) { case( CFUN_RST_NotPresent ): /* default value */ case( CFUN_RST_NoReset ): break; default: /* unexpected parameter */ ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } /* *------------------------------------------------------------------- * process the <fun> parameter *------------------------------------------------------------------- */ if( fun EQ CFUN_FUN_NotPresent ) fun = CFUNfun; switch( fun ) { case( CFUN_FUN_Minimum ): /* set ME to minimum functionality */ CFUNfun = fun; simEntStat.curCmd = AT_CMD_CFUN; simEntStat.entOwn = simShrdPrm.owner = srcId; /* Turn off all possible ringing */ #ifdef FF_ATI io_setRngInd ( IO_RING_OFF, CRING_TYP_NotPresent, CRING_TYP_NotPresent ); /* V.24 Ring Indicator Line */ #endif for( idx = 0; idx < CMD_SRC_MAX; idx++ ) { R_AT( RAT_CRING_OFF, idx )( 0 ); /* Turn of all ringing */ } /* We have to wait for both entities to finish in CFUN. So both EntStat are set to AT_CMD_CFUN and when a certain entity finished it also emits AT_OK if the other entity has already finished */ simEntStat.curCmd = AT_CMD_CFUN; simEntStat.entOwn = simShrdPrm.owner = srcId; mmEntStat.curCmd = AT_CMD_CFUN; mmEntStat.entOwn = mmShrdPrm.owner = srcId; pb_exit(); /* simShrdPrm.synCs = SYNC_DEACTIVATE; */ /* This is moved to pb_exit */ /* psaSIM_SyncSIM(); */ #if defined (GPRS) AND defined (DTI) mmShrdPrm.nrgCs = GMMREG_DT_POWER_OFF; if( psaG_MM_CMD_DEREG ( mmShrdPrm.nrgCs ) < 0 ) /* deregister from network */ #else mmShrdPrm.nrgCs = CS_POW_OFF; if( psaMM_DeRegistrate () < 0 ) /* deregister from network */ #endif { TRACE_EVENT( "FATAL RETURN psaMM_DeRegistrate in +COPS" ); ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Internal ); return( AT_FAIL ); } percentCSTAT_indication(STATE_MSG_SMS, ENTITY_STATUS_NotReady); retCd = AT_EXCT; break; case( CFUN_FUN_Full ): /* set ME to full functionality */ if ( (CFUNfun EQ CFUN_FUN_Minimum) OR (simShrdPrm.PINStat NEQ PS_RDY) ) { CFUNfun = fun; pSIMSetPrm -> actProc = SIM_INITIALISATION; simEntStat.curCmd = AT_CMD_CFUN; simEntStat.entOwn = simShrdPrm.owner = srcId; if( psaSIM_ActivateSIM() < 0 ) /* activate SIM card */ { TRACE_EVENT( "FATAL RETURN psaSIM in +CFUN" ); ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Internal ); return( AT_FAIL ); } retCd = AT_EXCT; } #ifdef SIM_PERS else if (CFUNfun EQ CFUN_FUN_Full ) { TRACE_EVENT("This is for if MMI calls sAT_PlusCFUN repetedly for verification of LOCKS"); CFUNfun = fun; pSIMSetPrm -> actProc = SIM_INITIALISATION; simEntStat.curCmd = AT_CMD_CFUN; simEntStat.entOwn = simShrdPrm.owner = srcId; if( psaSIM_ActivateSIM() < 0 ) /* activate SIM card */ { TRACE_EVENT( "FATAL RETURN psaSIM in +CFUN" ); ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Internal ); return( AT_FAIL ); } retCd = AT_EXCT; } #endif else { TRACE_EVENT("Switch mobile back on after radio low (CFUN=4)"); CFUNfun = fun; retCd = AT_CMPL; } break; case (CFUN_FUN_Disable_TX_RX_RF): if (CFUNfun EQ CFUN_FUN_Minimum) { TRACE_EVENT("Not possible to proceed when mobile is switched off"); ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_OpNotAllow ); return (AT_FAIL); } CFUNfun = fun; /* Turn off all possible ringing */ #ifdef FF_ATI io_setRngInd ( IO_RING_OFF, CRING_TYP_NotPresent, CRING_TYP_NotPresent ); /* V.24 Ring Indicator Line */ #endif for( idx = 0; idx < CMD_SRC_MAX; idx++ ) { R_AT( RAT_CRING_OFF, idx )( 0 ); /* Turn of all ringing */ } if( mmEntStat.curCmd NEQ AT_CMD_BAND ) { /* If sAT_PlusCFUN has been called by sAT_PercentBAND !!! */ mmEntStat.curCmd = AT_CMD_CFUN; } mmEntStat.entOwn = mmShrdPrm.owner = srcId; #if defined (GPRS) AND defined (DTI) mmShrdPrm.nrgCs = GMMREG_DT_SOFT_OFF; if( psaG_MM_CMD_DEREG ( mmShrdPrm.nrgCs ) < 0 ) /* deregister from network */ #else mmShrdPrm.nrgCs = CS_SOFT_OFF; if( psaMM_DeRegistrate () < 0 ) /* deregister from network */ #endif { TRACE_EVENT( "FATAL RETURN psaMM_DeRegistrate in +COPS" ); ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Internal ); return( AT_FAIL ); } retCd = AT_EXCT; break; default: /* unexpected parameter */ ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } /* *------------------------------------------------------------------- * log command execution *------------------------------------------------------------------- */ #if defined SMI OR defined MFW OR defined FF_MMI_RIV if( mmEntStat.curCmd NEQ AT_CMD_BAND AND simEntStat.curCmd NEQ AT_CMD_BAND ) { T_ACI_CLOG cmdLog; /* holds logging info */ cmdLog.atCmd = AT_CMD_CFUN; cmdLog.cmdType = CLOG_TYPE_Set; cmdLog.retCode = retCd; cmdLog.cId = ACI_NumParmNotPresent; cmdLog.sId = ACI_NumParmNotPresent; cmdLog.cmdPrm.sCFUN.srcId = srcId; cmdLog.cmdPrm.sCFUN.fun = fun; cmdLog.cmdPrm.sCFUN.rst = rst; rAT_PercentCLOG( &cmdLog ); } #endif return( retCd ); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6147) MODULE : CMH_SIMS | | STATE : code ROUTINE : sAT_PercentSECP | +--------------------------------------------------------------------+ PURPOSE : This is the functional counterpart to the %SEC AT command which is responsible to enter a PIN. <pin>: string of PIN chars. <newpin>: string of PIN chars required if requested PIN is SIM PUK */ GLOBAL T_ACI_RETURN sAT_PercentSECP ( T_ACI_CMD_SRC srcId, CHAR * pin, CHAR * newpin ) { T_SIMLOCK_STATUS result; TRACE_FUNCTION ("sAT_PercentSECP()"); /* *------------------------------------------------------------------- * check command source *------------------------------------------------------------------- */ if(!cmh_IsVldCmdSrc (srcId)) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } /* Check validity of pin str*/ if( pin EQ NULL) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } /* Try to set new pin */ result = aci_ext_personalisation_CS_change_password( pin, newpin ); switch (result) { case SIMLOCK_ENABLED: case SIMLOCK_DISABLED: /* success */ return AT_CMPL; case SIMLOCK_BLOCKED: /* password tried too many times, phone blocked */ ACI_ERR_DESC(ACI_ERR_CLASS_Cme, CME_ERR_PhoneFail); return AT_FAIL; case SIMLOCK_LOCKED: /* password wrong */ ACI_ERR_DESC(ACI_ERR_CLASS_Cme, CME_ERR_WrongPasswd); return AT_FAIL; default: /* other error */ ACI_ERR_DESC(ACI_ERR_CLASS_Cme, CME_ERR_Unknown); return AT_FAIL; } } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6147) MODULE : CMH_SIMS | | STATE : code ROUTINE : sAT_PercentSECS | +--------------------------------------------------------------------+ PURPOSE : This is the functional counterpart to the %SECS? AT command which is responsible to set the status of the Security Code. <securityStatus>: Status of the security code. <code>: Security code required to change the status. */ GLOBAL T_ACI_RETURN sAT_PercentSECS ( T_ACI_CMD_SRC srcId, T_ACI_SECS_STA securityState, CHAR * code ) { T_SIMLOCK_STATUS result; TRACE_FUNCTION ("sAT_PercentSECS()"); /* *------------------------------------------------------------------- * check command source *------------------------------------------------------------------- */ if(!cmh_IsVldCmdSrc (srcId)) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } /* *------------------------------------------------------------------- * check status value *------------------------------------------------------------------- */ switch (securityState) { case( SECS_STA_Enable ): result = aci_ext_personalisation_CS_set_status(SIMLOCK_ENABLED, code); break; case( SECS_STA_Disable ): result = aci_ext_personalisation_CS_set_status(SIMLOCK_DISABLED, code); break; default: return( AT_FAIL ); } /* *------------------------------------------------------------------- * analyze answer *------------------------------------------------------------------- */ switch (result) { case SIMLOCK_ENABLED: case SIMLOCK_DISABLED: /* success */ return AT_CMPL; case SIMLOCK_BLOCKED: /* password tried too many times, phone blocked */ ACI_ERR_DESC(ACI_ERR_CLASS_Cme, CME_ERR_PhoneFail); return AT_FAIL; case SIMLOCK_LOCKED: /* password wrong */ ACI_ERR_DESC(ACI_ERR_CLASS_Cme, CME_ERR_WrongPasswd); return AT_FAIL; default: /* other error */ ACI_ERR_DESC(ACI_ERR_CLASS_Cme, CME_ERR_Unknown); return AT_FAIL; } } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6147) MODULE : CMH_SIMS | | STATE : code ROUTINE : sAT_PlusCPIN | +--------------------------------------------------------------------+ PURPOSE : This is the functional counterpart to the +CPIN AT command which is responsible to enter a PIN. <pin>: string of PIN chars. <newpin>: string of PIN chars required if requested PIN is SIM PUK */ GLOBAL T_ACI_RETURN sAT_PlusCPIN ( T_ACI_CMD_SRC srcId, CHAR * pin, CHAR * newpin ) { T_SIM_SET_PRM * pSIMSetPrm; /* points to SIM parameter set */ T_ACI_RETURN retCd; /* holds return code */ T_SIMLOCK_STATUS retSlStatus; /* holds return code */ TRACE_FUNCTION ("sAT_PlusCPIN()"); /* *------------------------------------------------------------------- * check command source *------------------------------------------------------------------- */ if(!cmh_IsVldCmdSrc (srcId)) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } pSIMSetPrm = &simShrdPrm.setPrm[srcId]; /* *------------------------------------------------------------------- * check entity status *------------------------------------------------------------------- */ if( simEntStat.curCmd NEQ AT_CMD_NONE ) return( AT_BUSY ); /* *------------------------------------------------------------------- * check for PIN status *------------------------------------------------------------------- */ switch( simShrdPrm.PINStat ) { case( PS_RDY ): /* *--------------------------------------------------------------- * Not a SIM PIN State, but a ME personalisation PIN *--------------------------------------------------------------- */ #ifdef SIM_PERS if (AciSLockShrd.blocked) { retSlStatus = aci_slock_authenticate(AciSLockShrd.current_lock, pin); if ( retSlStatus NEQ SIMLOCK_DISABLED) { TRACE_EVENT( "Wrong PIN given for SIM lock." ); if (retSlStatus EQ SIMLOCK_BLOCKED) { switch (AciSLockShrd.current_lock) { case SIMLOCK_NETWORK: ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_NetworkPersPukReq); break; case SIMLOCK_NETWORK_SUBSET: ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_NetworkSubsetPersPukReq); break; case SIMLOCK_SERVICE_PROVIDER: ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_ProviderPersPukReq); break; case SIMLOCK_CORPORATE: ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_CorporatePersPukReq); break; case SIMLOCK_SIM: ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_PhoneFail); break; /* for SIMLOCK_SIM there is no PUK available. Instead the phone is blocked and can only be unblocked by the manufacturer as an anti-theft protection. (See manual of several competitor phones ...) */ case SIMLOCK_FIRST_SIM: ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_PhFSimPukReq); break; default: ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_WrongPasswd ); break; } } else ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_WrongPasswd ); return( AT_FAIL ); } else { simEntStat.curCmd = AT_CMD_CPIN; aci_slock_set_CFG(); if(cfg_data EQ NULL) { ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_Unknown ); return( AT_FAIL ); } aci_slock_init(); retSlStatus = SIMLOCK_ENABLED; if(AciSLockShrd.current_lock < SIMLOCK_SIM) { AciSLockShrd.current_lock= AciSLockShrd.current_lock +1; AciSLockShrd.check_lock = SIMLOCK_CHECK_PERS; retSlStatus = aci_slock_checkpersonalisation(AciSLockShrd.current_lock); } switch(retSlStatus) { case SIMLOCK_ENABLED : return( AT_CMPL); case SIMLOCK_BLOCKED : return( AT_FAIL); case SIMLOCK_WAIT : return (AT_EXCT); } } } #endif /* *--------------------------------------------------------------- * no PIN input is required *--------------------------------------------------------------- */ retCd = AT_FAIL; break; case( NO_VLD_PS ): /* *--------------------------------------------------------------- * PIN Status is unknown *--------------------------------------------------------------- */ /* invoke SIM activate and enter PIN if needed ???? */ ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_OpNotAllow ); return( AT_FAIL ); case( PS_PIN1 ): /* *--------------------------------------------------------------- * PIN 1 input is required *--------------------------------------------------------------- */ if( pin EQ NULL OR strlen( pin ) < MIN_PIN_LEN OR strlen( pin ) > PIN_LEN ) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } cmhSIM_FillInPIN ( pin, pSIMSetPrm -> curPIN, PIN_LEN ); pSIMSetPrm -> PINType = PHASE_2_PIN_1; simEntStat.curCmd = AT_CMD_CPIN; simEntStat.entOwn = simShrdPrm.owner = srcId; if( psaSIM_VerifyPIN() < 0 ) /* verify PIN */ { TRACE_EVENT( "FATAL RETURN psaSIM in +CPIN" ); ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Internal ); return( AT_FAIL ); } retCd = AT_EXCT; break; case( PS_PIN2 ): /* *--------------------------------------------------------------- * PIN 2 input is required *--------------------------------------------------------------- */ if( pin EQ NULL OR strlen( pin ) < MIN_PIN_LEN OR strlen( pin ) > PIN_LEN ) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } cmhSIM_FillInPIN ( pin, pSIMSetPrm -> curPIN, PIN_LEN ); pSIMSetPrm -> PINType = PHASE_2_PIN_2; simEntStat.curCmd = AT_CMD_CPIN; simEntStat.entOwn = simShrdPrm.owner = srcId; if( psaSIM_VerifyPIN() < 0 ) /* verify PIN */ { TRACE_EVENT( "FATAL RETURN psaSIM in +CPIN" ); ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Internal ); return( AT_FAIL ); } retCd = AT_EXCT; break; case( PS_PUK1 ): /* *--------------------------------------------------------------- * PUK 1 input is required *--------------------------------------------------------------- */ if( newpin EQ NULL OR strlen( newpin ) EQ 0) { ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_SimPukReq ); /* inform about needed PUK */ return( AT_FAIL ); } if( pin EQ NULL OR newpin EQ NULL OR strlen( pin ) NEQ PUK_LEN OR strlen( newpin ) < MIN_PIN_LEN OR strlen( newpin ) > PIN_LEN ) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } cmhSIM_FillInPIN ( pin, pSIMSetPrm -> unblkKey, PUK_LEN ); cmhSIM_FillInPIN ( newpin, pSIMSetPrm -> curPIN, PIN_LEN ); pSIMSetPrm -> PINType = PHASE_2_PUK_1; simEntStat.curCmd = AT_CMD_CPIN; simEntStat.entOwn = simShrdPrm.owner = srcId; if( psaSIM_UnblockCard( ) < 0 ) /* verify PIN */ { TRACE_EVENT( "FATAL RETURN psaSIM in +CPIN" ); ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Internal ); return( AT_FAIL ); } retCd = AT_EXCT; break; case( PS_PUK2 ): /* *--------------------------------------------------------------- * PUK 2 input is required *--------------------------------------------------------------- */ if( newpin EQ NULL OR strlen( newpin ) EQ 0) { ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_SimPuk2Req ); /* inform about needed PUK2 */ return( AT_FAIL ); } if( pin EQ NULL OR newpin EQ NULL OR strlen( pin ) NEQ PUK_LEN OR strlen( newpin ) < MIN_PIN_LEN OR strlen( newpin ) > PIN_LEN ) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } cmhSIM_FillInPIN ( pin, pSIMSetPrm -> unblkKey, PUK_LEN ); cmhSIM_FillInPIN ( newpin, pSIMSetPrm -> curPIN, PIN_LEN ); pSIMSetPrm -> PINType = PHASE_2_PUK_2; simEntStat.curCmd = AT_CMD_CPIN; simEntStat.entOwn = simShrdPrm.owner = srcId; if( psaSIM_UnblockCard( ) < 0 ) /* verify PIN */ { TRACE_EVENT( "FATAL RETURN psaSIM in +CPIN" ); ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Internal ); return( AT_FAIL ); } retCd = AT_EXCT; break; default: /* *--------------------------------------------------------------- * unexpected PIN state *--------------------------------------------------------------- */ ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_DataCorrupt ); return( AT_FAIL ); } /* *------------------------------------------------------------------- * log command execution *------------------------------------------------------------------- */ #if defined SMI OR defined MFW OR defined FF_MMI_RIV { T_ACI_CLOG cmdLog; /* holds logging info */ cmdLog.atCmd = AT_CMD_CPIN; cmdLog.cmdType = CLOG_TYPE_Set; cmdLog.retCode = retCd; cmdLog.cId = ACI_NumParmNotPresent; cmdLog.sId = ACI_NumParmNotPresent; cmdLog.cmdPrm.sCPIN.srcId = srcId; cmdLog.cmdPrm.sCPIN.pin = pin; cmdLog.cmdPrm.sCPIN.newpin = newpin; rAT_PercentCLOG( &cmdLog ); } #endif return( retCd ); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6147) MODULE : CMH_SIMS | | STATE : code ROUTINE : sAT_PlusCAMM | +--------------------------------------------------------------------+ PURPOSE : This is the functional counterpart to the +CAMM AT command which is responsible to set the ACMMax. */ GLOBAL T_ACI_RETURN sAT_PlusCAMM ( T_ACI_CMD_SRC srcId, LONG acmmax, CHAR * pwd) { T_ACI_RETURN ret = AT_FAIL; TRACE_FUNCTION ("sAT_PlusCAMM()"); /* *------------------------------------------------------------------- * check command source *------------------------------------------------------------------- */ if(!cmh_IsVldCmdSrc (srcId)) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } /* *------------------------------------------------------------------- * send parameters to advice of charge module. *------------------------------------------------------------------- */ simEntStat.curCmd = AT_CMD_CAMM; simEntStat.entOwn = simShrdPrm.owner = srcId; ret = aoc_set_values (srcId, AOC_ACMMAX, (void *) acmmax, (UBYTE *) pwd); /* *------------------------------------------------------------------- * Check return value of aoc_set_values() equal to AT_FAIL, * resets simEntStat.curcmd and simEntStat.entown. *------------------------------------------------------------------- */ if( ret EQ AT_FAIL ) { simEntStat.curCmd = AT_CMD_NONE; simEntStat.entOwn = simShrdPrm.owner = OWN_NONE; } return( ret ); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6147) MODULE : CMH_SIMS | | STATE : code ROUTINE : sAT_PlusCPUC | +--------------------------------------------------------------------+ PURPOSE : This is the functional counterpart to the +CPUC AT command which is responsible to set the PUCT values. */ GLOBAL T_ACI_RETURN sAT_PlusCPUC ( T_ACI_CMD_SRC srcId, CHAR * currency, CHAR * ppu, CHAR * pwd) { T_puct puct; T_ACI_RETURN ret = AT_FAIL; TRACE_FUNCTION ("sAT_PlusCPUC()"); /* *------------------------------------------------------------------- * check command source *------------------------------------------------------------------- */ if(!cmh_IsVldCmdSrc (srcId)) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } /* *------------------------------------------------------------------- * send parameters to advice of charge module. *------------------------------------------------------------------- */ strcpy ((char *) puct.currency, currency); strcpy ((char *) puct.value, ppu); simEntStat.curCmd = AT_CMD_CPUC; simEntStat.entOwn = simShrdPrm.owner = srcId; ret = aoc_set_values (srcId, AOC_PUCT, (void *)&puct, (UBYTE *) pwd); /* *------------------------------------------------------------------- * Check return value of aoc_set_values() equal to AT_FAIL, * resets simEntStat.curcmd and simEntStat.entown. *------------------------------------------------------------------- */ if( ret EQ AT_FAIL ) { simEntStat.curCmd = AT_CMD_NONE; simEntStat.entOwn = simShrdPrm.owner = OWN_NONE; } return( ret ); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6147) MODULE : CMH_SIMS | | STATE : code ROUTINE : sAT_PlusCACM | +--------------------------------------------------------------------+ PURPOSE : This is the functional counterpart to the +CACM AT command which is responsible to reset the ACM value. */ GLOBAL T_ACI_RETURN sAT_PlusCACM ( T_ACI_CMD_SRC srcId, CHAR * pwd) { T_ACI_RETURN ret = AT_FAIL; TRACE_FUNCTION ("sAT_PlusCACM()"); /* *------------------------------------------------------------------- * check command source *------------------------------------------------------------------- */ if(!cmh_IsVldCmdSrc (srcId)) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } /* *------------------------------------------------------------------- * send parameters to advice of charge module. *------------------------------------------------------------------- */ simEntStat.curCmd = AT_CMD_CACM; simEntStat.entOwn = simShrdPrm.owner = srcId; ret = aoc_set_values (srcId, AOC_ACM, (void *) NULL, (UBYTE *) pwd); /* *------------------------------------------------------------------- * Check return value of aoc_set_values() equal to AT_FAIL, * resets simEntStat.curcmd and simEntStat.entown. *------------------------------------------------------------------- */ if( ret EQ AT_FAIL ) { simEntStat.curCmd = AT_CMD_NONE; simEntStat.entOwn = simShrdPrm.owner = OWN_NONE; } return( ret ); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6147) MODULE : CMH_SIMS | | STATE : code ROUTINE : sAT_PlusCPOL | +--------------------------------------------------------------------+ PURPOSE : This is the functional counterpart to the +CPOL AT command which is responsible to access the preferred PLMN list. <index>: PLMN list index <format>: PLMN format <oper>: PLMN name <index2>: second PLMN list index for exchange operation <mode>: supplemental mode information */ GLOBAL T_ACI_RETURN sAT_PlusCPOL ( T_ACI_CMD_SRC srcId, SHORT index, T_ACI_CPOL_FRMT format, CHAR * oper, SHORT index2, T_ACI_CPOL_MOD mode ) { T_SIM_CMD_PRM * pSIMCmdPrm; /* points to SIM command parameters */ T_SIM_SET_PRM * pSIMSetPrm; /* points to SIM parameter set */ UBYTE plmn[ACI_LEN_PLMN_SEL_NTRY];/* holds coded plmn id */ TRACE_FUNCTION ("sAT_PlusCPOL()"); /* *------------------------------------------------------------------- * check command source *------------------------------------------------------------------- */ if(!cmh_IsVldCmdSrc (srcId)) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } pSIMSetPrm = &simShrdPrm.setPrm[srcId]; pSIMCmdPrm = &cmhPrm[srcId].simCmdPrm; /* *------------------------------------------------------------------- * check mode parameter *------------------------------------------------------------------- */ switch( mode ) { case( CPOL_MOD_CompactList ): case( CPOL_MOD_Insert ): case( CPOL_MOD_NotPresent ): break; default: ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } /* *------------------------------------------------------------------- * check format parameter *------------------------------------------------------------------- */ switch( format ) { case( CPOL_FRMT_Long ): case( CPOL_FRMT_Short ): case( CPOL_FRMT_Numeric ): if( index EQ ACI_NumParmNotPresent AND !oper ) { pSIMCmdPrm->CPOLfrmt = format; return( AT_CMPL ); } break; case( CPOL_FRMT_NotPresent ): format = pSIMCmdPrm->CPOLfrmt; break; default: { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } } /* *------------------------------------------------------------------- * check for write entry *------------------------------------------------------------------- */ if( oper ) { /* code plmn id */ if( ! cmhSIM_GetCodedPLMN( oper, format, plmn )) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } /* if EF is already read */ if( EfPLMNselStat EQ EF_STAT_READ ) { if( mode EQ CPOL_MOD_CompactList ) { cmhSIM_CmpctPlmnSel( CPOLSimEfDataLen, CPOLSimEfData ); } if( index NEQ ACI_NumParmNotPresent ) { if( index > (CPOLSimEfDataLen / ACI_LEN_PLMN_SEL_NTRY)) { ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_InvIdx ); return( AT_FAIL ); } return cmhSIM_UpdPlmnSel( srcId, index, plmn, mode ); } else return cmhSIM_FndEmptyPlmnSel( srcId, plmn ); } else { if( simEntStat.curCmd NEQ AT_CMD_NONE ) return( AT_BUSY ); pSIMCmdPrm->CPOLidx = (UBYTE)(index EQ ACI_NumParmNotPresent)? NOT_PRESENT_8BIT:index; pSIMCmdPrm->CPOLmode = mode; pSIMCmdPrm->CPOLact = CPOL_ACT_Write; memcpy( pSIMCmdPrm->CPOLplmn, plmn, ACI_LEN_PLMN_SEL_NTRY ); simEntStat.curCmd = AT_CMD_CPOL; simEntStat.entOwn = srcId; return cmhSIM_ReqPlmnSel ( srcId ); } } /* *------------------------------------------------------------------- * check for delete entry *------------------------------------------------------------------- */ else { /* check presence of index */ if( index EQ ACI_NumParmNotPresent ) { ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_InvIdx ); return( AT_FAIL ); } /* if EF is already read */ if( EfPLMNselStat EQ EF_STAT_READ ) { if( mode EQ CPOL_MOD_CompactList ) { cmhSIM_CmpctPlmnSel( CPOLSimEfDataLen, CPOLSimEfData ); } if( index > (CPOLSimEfDataLen / ACI_LEN_PLMN_SEL_NTRY) OR (index2 > (CPOLSimEfDataLen / ACI_LEN_PLMN_SEL_NTRY) AND index2 NEQ ACI_NumParmNotPresent)) { ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_InvIdx ); return( AT_FAIL ); } if( index2 EQ ACI_NumParmNotPresent ) return cmhSIM_DelPlmnSel( srcId, index, mode ); else return cmhSIM_ChgPlmnSel( srcId, index, index2 ); } else { if( simEntStat.curCmd NEQ AT_CMD_NONE ) return( AT_BUSY ); pSIMCmdPrm->CPOLidx = (UBYTE)index; pSIMCmdPrm->CPOLidx2 = (index2 NEQ ACI_NumParmNotPresent)? (UBYTE)index2:NOT_PRESENT_8BIT; pSIMCmdPrm->CPOLmode = mode; pSIMCmdPrm->CPOLact = CPOL_ACT_Delete; simEntStat.curCmd = AT_CMD_CPOL; simEntStat.entOwn = srcId; return cmhSIM_ReqPlmnSel ( srcId ); } } } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6147) MODULE : CMH_SIMS | | STATE : code ROUTINE : sAT_PlusCRSM | +--------------------------------------------------------------------+ PURPOSE : This is the functional counterpart to the +CRSM AT command which is responsible for restricted SIM access. <cmd>: access command. <fileId>: file identifier <p1>: parameter 1 <p2>: parameter 2 <p3>: parameter 3 <dataLen>: length of data <data>: pointer to data */ T_ACI_RETURN sAT_PlusCRSM ( T_ACI_CMD_SRC srcId, T_ACI_CRSM_CMD cmd, SHORT fileId, SHORT p1, SHORT p2, SHORT p3, SHORT dataLen, UBYTE *data ) { T_SIM_TRNS_ACC_PRM prm; /* holds access parameter */ TRACE_FUNCTION ("sAT_PlusCRSM()"); /* *------------------------------------------------------------------- * check command source *------------------------------------------------------------------- */ if(!cmh_IsVldCmdSrc (srcId)) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } /* *------------------------------------------------------------------- * check entity status *------------------------------------------------------------------- */ if( simEntStat.curCmd NEQ AT_CMD_NONE ) return( AT_BUSY ); /* *------------------------------------------------------------------- * check command, data, p1, p2 and p3 parameters *------------------------------------------------------------------- */ switch( cmd ) { case( CRSM_CMD_UpdBin ): case( CRSM_CMD_UpdRec ): if( !data OR !dataLen ) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } /*lint -fallthrough*/ case( CRSM_CMD_ReadBin ): case( CRSM_CMD_ReadRec ): if( p1 EQ ACI_NumParmNotPresent OR p2 EQ ACI_NumParmNotPresent OR p3 EQ ACI_NumParmNotPresent ) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } break; case( CRSM_CMD_GetResp ): case( CRSM_CMD_Status ): if( p3 EQ ACI_NumParmNotPresent ) p3 = 0; break; case( CRSM_CMD_NotPresent ): default: { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } } /* *------------------------------------------------------------------- * check fileId parameter *------------------------------------------------------------------- */ if( fileId EQ ACI_NumParmNotPresent AND cmd NEQ CRSM_CMD_Status ) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } /* *------------------------------------------------------------------- * convert command *------------------------------------------------------------------- */ switch( cmd ) { case( CRSM_CMD_UpdBin ): prm.cmd = SIM_UPDATE_BINARY;break; case( CRSM_CMD_UpdRec ): prm.cmd = SIM_UPDATE_RECORD;break; case( CRSM_CMD_ReadBin ): prm.cmd = SIM_READ_BINARY;break; case( CRSM_CMD_ReadRec ): prm.cmd = SIM_READ_RECORD;break; case( CRSM_CMD_GetResp ): prm.cmd = SIM_GET_RESPONSE;break; case( CRSM_CMD_Status ): prm.cmd = SIM_STATUS;break; } /* *------------------------------------------------------------------- * access SIM *------------------------------------------------------------------- */ simEntStat.curCmd = AT_CMD_CRSM; simEntStat.entOwn = srcId; prm.reqDataFld = (USHORT)fileId; prm.p1 = (UBYTE)p1; prm.p2 = (UBYTE)p2; prm.p3 = (UBYTE)p3; prm.dataLen = (UBYTE)dataLen; prm.transData = data; psaSIM_TrnsSIMAccess( &prm ); return( AT_EXCT ); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6147) MODULE : CMH_SIMS | | STATE : code ROUTINE : sAT_PlusCSIM | +--------------------------------------------------------------------+ PURPOSE : This is the functional counterpart to the +CSIM AT command which is responsible for generic SIM access. */ T_ACI_RETURN sAT_PlusCSIM ( T_ACI_CMD_SRC srcId, USHORT dataLen, UBYTE *data ) { T_SIM_TRNS_ACC_PRM prm; /* holds access parameter */ TRACE_FUNCTION ("sAT_PlusCSIM()"); /* *------------------------------------------------------------------- * check command source *------------------------------------------------------------------- */ if(!cmh_IsVldCmdSrc (srcId)) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } /* *------------------------------------------------------------------- * check entity status *------------------------------------------------------------------- */ if( simEntStat.curCmd NEQ AT_CMD_NONE ) { return( AT_BUSY ); } #if 0 // Dmitriy: for EAP-SIM we need to run the GSM algorithm if (data[0] EQ GSM_CLASS) { /* GSM instruction class is not allowed */ TRACE_EVENT("GSM instruction class is not allowed"); ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_OpNotAllow ); return( AT_FAIL ); } #endif #if 0 /* do we really need the check for the ATP source ? */ #ifdef _TARGET_ if (ati_is_src_type((UBYTE)srcId, ATI_SRC_TYPE_RIV) EQ FALSE) { /* don't allow other source type than RIV */ TRACE_EVENT("other src type than RIV is not allowed"); ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_OpNotAllow ); return( AT_FAIL ); } #endif /*_TARGET_*/ #endif /* */ if (dataLen > MAX_SIM_TRANSP) { /* wrong length value */ TRACE_EVENT("wrong length value"); ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } /* *------------------------------------------------------------------- * access SIM *------------------------------------------------------------------- */ simEntStat.curCmd = AT_CMD_CSIM; simEntStat.entOwn = srcId; prm.cmd = SIM_TRANSP_CMD; prm.dataLen = dataLen; prm.transData = data; psaSIM_TrnsSIMAccess( &prm ); return( AT_EXCT ); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6147) MODULE : CMH_SIMS | | STATE : code ROUTINE : sAT_PercentPVRF | +--------------------------------------------------------------------+ PURPOSE : This is the functional counterpart to the %PVRF AT command which is responsible to verify a specific PIN. <pin>: string of PIN chars. <newpin>: string of PIN chars required if requested PIN is SIM PUK */ GLOBAL T_ACI_RETURN sAT_PercentPVRF( T_ACI_CMD_SRC srcId, T_ACI_PVRF_TYPE type, CHAR * pin, CHAR * newpin ) { T_SIM_SET_PRM * pSIMSetPrm; /* points to SIM parameter set */ T_ACI_RETURN retCd; /* holds return code */ TRACE_FUNCTION ("sAT_PercentPVRF()"); /* *------------------------------------------------------------------- * check command source *------------------------------------------------------------------- */ if(!cmh_IsVldCmdSrc (srcId)) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } pSIMSetPrm = &simShrdPrm.setPrm[srcId]; /* *------------------------------------------------------------------- * check entity status *------------------------------------------------------------------- */ if( simEntStat.curCmd NEQ AT_CMD_NONE ) return( AT_BUSY ); /* *------------------------------------------------------------------- * check for PIN type *------------------------------------------------------------------- */ switch( type ) { case( PVRF_TYPE_Pin1 ): case( PVRF_TYPE_Pin2 ): /* *--------------------------------------------------------------- * PIN 1/2 verify is required *--------------------------------------------------------------- */ if( pin EQ NULL OR strlen( pin ) < MIN_PIN_LEN OR strlen( pin ) > PIN_LEN ) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } cmhSIM_FillInPIN ( pin, pSIMSetPrm -> curPIN, PIN_LEN ); pSIMSetPrm -> PINType = (type EQ PVRF_TYPE_Pin1)? PHASE_2_PIN_1:PHASE_2_PIN_2; simEntStat.curCmd = AT_CMD_PVRF; simEntStat.entOwn = simShrdPrm.owner = srcId; if( psaSIM_VerifyPIN() < 0 ) /* verify PIN */ { TRACE_EVENT( "FATAL RETURN psaSIM in %%PVRF" ); ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Internal ); return( AT_FAIL ); } retCd = AT_EXCT; break; case( PVRF_TYPE_Puk1 ): case( PVRF_TYPE_Puk2 ): /* *--------------------------------------------------------------- * PUK 1/2 verify is required *--------------------------------------------------------------- */ if( pin EQ NULL OR newpin EQ NULL OR strlen( pin ) NEQ PUK_LEN OR strlen( newpin ) < MIN_PIN_LEN OR strlen( newpin ) > PIN_LEN ) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } cmhSIM_FillInPIN ( pin, pSIMSetPrm -> unblkKey, PUK_LEN ); cmhSIM_FillInPIN ( newpin, pSIMSetPrm -> curPIN, PIN_LEN ); pSIMSetPrm -> PINType = (type EQ PVRF_TYPE_Puk1)? PHASE_2_PUK_1:PHASE_2_PUK_2; simEntStat.curCmd = AT_CMD_PVRF; simEntStat.entOwn = simShrdPrm.owner = srcId; if( psaSIM_UnblockCard( ) < 0 ) /* verify PIN */ { TRACE_EVENT( "FATAL RETURN psaSIM in %%PVRF" ); ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Internal ); return( AT_FAIL ); } retCd = AT_EXCT; break; default: /* *--------------------------------------------------------------- * unexpected PIN state *--------------------------------------------------------------- */ ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_DataCorrupt ); return( AT_FAIL ); } /* *------------------------------------------------------------------- * log command execution *------------------------------------------------------------------- */ #if defined SMI OR defined MFW OR defined FF_MMI_RIV { T_ACI_CLOG cmdLog; /* holds logging info */ cmdLog.atCmd = AT_CMD_PVRF; cmdLog.cmdType = CLOG_TYPE_Set; cmdLog.retCode = retCd; cmdLog.cId = ACI_NumParmNotPresent; cmdLog.sId = ACI_NumParmNotPresent; cmdLog.cmdPrm.sPVRF.srcId = srcId; cmdLog.cmdPrm.sPVRF.type = type; cmdLog.cmdPrm.sPVRF.pin = pin; cmdLog.cmdPrm.sPVRF.newpin = newpin; rAT_PercentCLOG( &cmdLog ); } #endif return( retCd ); } /* +-------------------------------------------------------------------+ | PROJECT : GSM-PS (6147) MODULE : CMH_SIMS | | ROUTINE : sAT_PercentCPRI | +-------------------------------------------------------------------+ PURPOSE : set the CPRI mode for displaying/not displaying ciphering indications */ GLOBAL T_ACI_RETURN sAT_PercentCPRI( T_ACI_CMD_SRC srcId, UBYTE mode ) { TRACE_FUNCTION ("sAT_PercentCPRI()"); if( !cmh_IsVldCmdSrc( srcId ) ) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } if (simShrdPrm.ciSIMEnabled NEQ FALSE) /* Since this function is used by MMI,it just returns AT_CMPL */ { return( AT_CMPL ); /* If CPRI is enabled in the SIM,it just returns AT_CMPL */ } else { ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_OpNotAllow ); return( AT_FAIL ); } } #ifdef FF_DUAL_SIM /* +-------------------------------------------------------------------+ | PROJECT : GSM-PS (6147) MODULE : CMH_SIMS | | ROUTINE : sAT_PercentSIM | +-------------------------------------------------------------------+ PURPOSE : Select the SIM to be powered on */ GLOBAL T_ACI_RETURN sAT_PercentSIM( T_ACI_CMD_SRC srcId, UBYTE sim_num ) { T_SIM_SET_PRM * pSIMSetPrm; /* points to SIM parameter set */ TRACE_FUNCTION ("sAT_PercentSIM()"); if( !cmh_IsVldCmdSrc( srcId ) ) { ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Parameter ); return( AT_FAIL ); } pSIMSetPrm = &simShrdPrm.setPrm[srcId]; if( simEntStat.curCmd NEQ AT_CMD_NONE ) { TRACE_EVENT("Entity SIM is busy: cannot proceed command..."); return( AT_BUSY ); } if(CFUNfun EQ CFUN_FUN_Full) { ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_OpNotAllow ); return( AT_FAIL ); } if(sim_num < SIM_NUM_0 OR sim_num > SIM_NUM_2) { ACI_ERR_DESC( ACI_ERR_CLASS_Cme, CME_ERR_OpNotAllow ); return( AT_FAIL ); } pSIMSetPrm->SIM_Selected = sim_num; simEntStat.curCmd = AT_CMD_SIM; simEntStat.entOwn = simShrdPrm.owner = srcId; if( psaSIM_SelectSIM() < 0 ) /* select SIM card */ { TRACE_EVENT( "FATAL RETURN psaSIM in %SIM" ); ACI_ERR_DESC( ACI_ERR_CLASS_Ext, EXT_ERR_Internal ); return( AT_FAIL ); } return(AT_EXCT); } #endif /*FF_DUAL_SIM*/ /*==== EOF ========================================================*/