FreeCalypso > hg > fc-magnetite
view src/g23m-gsm/sim/uicc_fkt.c @ 632:d968a3216ba0
new tangomdm build target
TCS211/Magnetite built for target leonardo runs just fine on the Tango-based
Caramel board, but a more proper tangomdm build target is preferable in order
to better market these Tango modems to prospective commercial customers. The
only differences are in GPIO and MCSI config:
* MCSI is enabled in the tangomdm build config.
* GPIO 1 is loudspeaker amplifier control on Leonardo, but on Tango platforms
it can be used for anything. On Caramel boards this GPIO should be
configured as an output driving high.
* GPIO 2 needs to be configured as Calypso input on Leonardo, but on Tango
platforms it can be used for anything. On Caramel boards this GPIO should be
configured as an output, either high or low is OK.
author | Mychaela Falconia <falcon@freecalypso.org> |
---|---|
date | Sat, 04 Jan 2020 19:27:41 +0000 |
parents | 27a4235405c6 |
children |
line wrap: on
line source
/* +----------------------------------------------------------------------------- | Project : GSM-F&D (8411) | Modul : SIM_FKT +----------------------------------------------------------------------------- | 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 modul defines the wrapping functions for the | SIM application. +----------------------------------------------------------------------------- */ #ifndef SIM_FKT_C #define SIM_FKT_C #define ENTITY_SIM /*==== INCLUDES ===================================================*/ #include <string.h> #include "typedefs.h" #include "pconst.cdg" #include "message.h" #include "ccdapi.h" #include "vsi.h" #include "custom.h" #include "gsm.h" #include "cnf_sim.h" #include "mon_sim.h" #include "prim.h" #include "pei.h" #include "tok.h" #include "sim.h" #include "sim_em.h" #include "8010_136_SIMDRV_SAP_inline.h" /*==== EXPORT =====================================================*/ /*==== PRIVAT =====================================================*/ /*==== VARIABLES ==================================================*/ GLOBAL USHORT stk_l_cmd = 0; /*==== FUNCTIONS ===================================================*/ /* Implements Measure# 13 */ /* +---------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_ChangeCHV_n_UnblockCHV | +---------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_ChangeCHV and SIM_UnblockCHV */ LOCAL USHORT FKT_ChangeCHV_n_UnblockCHV ( UBYTE * oldPin_UnblkCHV, UBYTE * newPin_CHV, UBYTE pinId_chvType, UBYTE inst_code) { USHORT size = 0; USHORT sw1sw2; U8 reader_id; U8 i; U8 data[2*MAX_PIN_LEN]; UBYTE response[SIMDRV_MAX_RESULT]; T_SIMDRV_cmd_header cmd_header; T_SIMDRV_data_info data_info; T_SIMDRV_result_info result_info; TRACE_FUNCTION ("FKT_ChangeCHV_n_UnblockCHV()"); reader_id = SIMDRV_VAL_READER_ID__RANGE_MIN; cmd_header.cla = SIMDRV_GSM_CLASS_BYTE; cmd_header.ins = inst_code; cmd_header.p1 = 0; cmd_header.p2 = pinId_chvType; for (i=0;i<2*MAX_PIN_LEN;i++) { if (i < MAX_PIN_LEN) data[i] = oldPin_UnblkCHV[i]; else data[i] = newPin_CHV[i-MAX_PIN_LEN]; } data_info.data = (U8 *)data; data_info.c_data = sizeof(data); result_info.result = response; result_info.c_result = size; result_info.len = NOT_PRESENT_16BIT; sw1sw2 = simdrv_xch_apdu(reader_id, cmd_header, data_info, &result_info); return FKT_convert_error (sw1sw2,result_info.c_result); } /* Implements Measure# 16 */ /* +------------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_Invalidate_n_Rehabilitate | +------------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_Invalidate and SIM_Rehabilitate. */ LOCAL USHORT FKT_Invalidate_n_Rehabilitate ( UBYTE inst_code) { USHORT size = 0; USHORT sw1sw2; U8 reader_id; UBYTE response[SIMDRV_MAX_RESULT]; T_SIMDRV_cmd_header cmd_header; T_SIMDRV_data_info data_info; T_SIMDRV_result_info result_info; TRACE_FUNCTION ("FKT_Invalidate_n_Rehabilitate()"); reader_id = SIMDRV_VAL_READER_ID__RANGE_MIN; cmd_header.cla = SIMDRV_GSM_CLASS_BYTE; cmd_header.ins = inst_code; cmd_header.p1 = 0; cmd_header.p2 = 0; data_info.data = NULL; data_info.c_data = 0; result_info.result = response; result_info.c_result = size; result_info.len = NOT_PRESENT_16BIT; sw1sw2 = simdrv_xch_apdu(reader_id,cmd_header,data_info,&result_info); if (sw1sw2 EQ 0x9810) /* already invalidated */ return SIM_NO_ERROR; return FKT_convert_error (sw1sw2,result_info.c_result); } /* Implements Measure# 17 */ /* +----------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_DisableCHV_n_EnableCHV | +----------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_DisableCHV and SIM_EnableCHV */ LOCAL USHORT FKT_DisableCHV_n_EnableCHV (UBYTE * pin, UBYTE inst_code) { USHORT size = 0; USHORT sw1sw2; U8 reader_id; T_SIMDRV_cmd_header cmd_header; T_SIMDRV_data_info data_info; T_SIMDRV_result_info result_info; UBYTE response[SIMDRV_MAX_RESULT]; TRACE_FUNCTION ("FKT_DisableCHV_n_EnableCHV()"); reader_id = SIMDRV_VAL_READER_ID__RANGE_MIN; cmd_header.cla = SIMDRV_GSM_CLASS_BYTE; cmd_header.ins = inst_code; cmd_header.p1 = 0; cmd_header.p2 = 1; data_info.data = (U8 *)pin; data_info.c_data = MAX_PIN_LEN; result_info.result = response; result_info.c_result = size; result_info.len = NOT_PRESENT_16BIT; sw1sw2 = simdrv_xch_apdu(reader_id, cmd_header, data_info, &result_info); return FKT_convert_error (sw1sw2,result_info.c_result); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_check_pin_count | +--------------------------------------------------------------------+ PURPOSE : PIN/PUK count is checked for secret code initialisation. count is set to zero, if not initialised, otherwise the initialisation flag (most significant bit) is reset. */ GLOBAL UBYTE FKT_check_pin_count (UBYTE count) { if ((count & 0x80) EQ 0) return 0; return count & 0x0F; } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_convert_error | +--------------------------------------------------------------------+ PURPOSE : Converts sw1 and sw2 to an unique error code for the SIM application. */ /* * PIN/PUK is wrong, remaining attempts */ static const USHORT sim_inv_chv_A [6] = { /* last requested PIN no error code */ /* none */ SIM_CAUSE_OTHER_ERROR, /* PIN 1 */ SIM_CAUSE_PIN1_EXPECT, /* PIN 2 */ SIM_CAUSE_PIN2_EXPECT, /* PUK 1 */ SIM_CAUSE_PUK1_EXPECT, /* PUK 2 */ SIM_CAUSE_PUK2_EXPECT, /* NEVER */ SIM_CAUSE_ACCESS_PROHIBIT }; /* * PIN/PUK is wrong, no remaining attempts */ static const USHORT sim_inv_chv_B [6] = { /* last requested PIN no error code */ /* none */ SIM_CAUSE_OTHER_ERROR, /* PIN 1 */ SIM_CAUSE_PIN1_BLOCKED, /* PIN 2 */ SIM_CAUSE_PIN2_BLOCKED, /* PUK 1 */ SIM_CAUSE_PUK1_BLOCKED, /* PUK 2 */ SIM_CAUSE_PUK2_BLOCKED, /* NEVER */ SIM_CAUSE_OTHER_ERROR }; GLOBAL USHORT FKT_convert_error (USHORT sw1sw2, USHORT size) { TRACE_FUNCTION ("FKT_convert_error()"); sim_data.sw1 = (UBYTE)(sw1sw2 >> 8); sim_data.sw2 = (UBYTE)sw1sw2; TRACE_EVENT_P1 ("Data returned from SIM, Size =%X", size); TRACE_EVENT_P2 ("SW1=%02X SW2=%02X", sim_data.sw1, sim_data.sw2); switch (sim_data.sw1) { case 0x00: /* * SIM driver error */ if (SIM_IS_FLAG_CLEARED(SIM_INSERT)) { return SIM_CAUSE_CARD_REMOVED; } if (sim_data.sw2 EQ 14) { SIM_SET_FLAG(DRV_FAILED_RETRY); return SIM_CAUSE_DRV_TEMPFAIL; } return CAUSE_MAKE(DEFBY_CONDAT, ORIGSIDE_MS, SIM_ORIGINATING_ENTITY, sim_data.sw2); #if defined SIM_TOOLKIT case 0x9E: /* * use SW2 as length indicator for * the following get response */ if (sim_data.sim_phase >= 3) /* Phase 2+ or higher */ { if (sim_data.stk_profile[0] & SAT_TP1_9E_XX) { sim_data.sim_data_len = (sim_data.sw2 EQ 0)? 0x100: (USHORT)sim_data.sw2; return SIM_CAUSE_DNL_ERROR; } else return SIM_CAUSE_SAT_BUSY; } else return SIM_CAUSE_OTHER_ERROR; case 0x93: if (sim_data.sim_phase >= 3) /* Phase 2+ or higher */ { return SIM_CAUSE_SAT_BUSY; } else return SIM_CAUSE_OTHER_ERROR; case 0x91: if (sim_data.sim_phase >= 3) /* Phase 2+ or higher */ { sim_data.proactive_sim_data_len = (sim_data.sw2 EQ 0)? 0x100: (SHORT)sim_data.sw2; return SIM_NO_ERROR; } else return SIM_CAUSE_OTHER_ERROR; #endif case 0x92: if (sim_data.sw2 > 0xF) { #ifdef REL99 if (sim_data.sw2 EQ SW2_MEMORY_PROBLEM) { return SIM_CAUSE_MEM_PROBLEM; } #endif /* end of ifdef REL99 */ return SIM_CAUSE_OTHER_ERROR; } /* no break (otherwise the command was successful)*/ case 0x90: if( (size>0) AND (size <= 0x100) ) { sim_data.sim_data_len = size; TRACE_EVENT_P1 ("sim_data.sim_data_len updated size =%X ", size); } return SIM_NO_ERROR; case 0x9F: /* * use SW2 as length indicator for * the following get response */ sim_data.sim_data_len = (sim_data.sw2 EQ 0)? 0x100: (USHORT)sim_data.sw2; return SIM_NO_ERROR; case 0x94: switch (sim_data.sw2) { case 0: return SIM_CAUSE_NO_SELECT; case 2: return SIM_CAUSE_ADDR_WRONG; case 4: return SIM_CAUSE_UNKN_FILE_ID; case 8: return SIM_CAUSE_CMD_INCONSIST; default: break; } break; case 0x98: TRACE_EVENT_P1 ("LRP = %d", (int)sim_data.last_requested_pin_no); switch (sim_data.sw2) { case 2: return SIM_CAUSE_CHV_NOTSET; case 8: return SIM_CAUSE_CHV_VALIDATED; case 0x10: return SIM_CAUSE_EF_INVALID; /* contradiction cases */ case 4: //TISH, patch for OMAPS00115342&OMAPS00123717 //start #if 0 /* Check whether PIN1 is entered/Verified */ if (SIM_IS_FLAG_SET(PIN1_VERIFIED)) return SIM_CAUSE_ACCESS_PROHIBIT; else #endif //end return sim_inv_chv_A [sim_data.last_requested_pin_no]; case 0x40: return sim_inv_chv_B [sim_data.last_requested_pin_no]; case 0x50: return SIM_CAUSE_MAX_INCREASE; default: break; } break; } return SIM_CAUSE_OTHER_ERROR; } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_ChangeCHV | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_ChangeCHV. */ GLOBAL USHORT FKT_ChangeCHV (UBYTE * old_pin, UBYTE * new_pin, UBYTE pin_id) { /* Implements Measure# 13 */ return (FKT_ChangeCHV_n_UnblockCHV (old_pin, new_pin, pin_id, SIMDRV_INS_CHANGE_CHV)); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_DisableCHV | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_DisableCHV. */ GLOBAL USHORT FKT_DisableCHV (UBYTE * pin) { /* Implements Measure# 17 */ return (FKT_DisableCHV_n_EnableCHV (pin, SIMDRV_INS_DISABLE_CHV)); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_EnableCHV | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_EnableCHV. */ GLOBAL USHORT FKT_EnableCHV (UBYTE * pin) { /* Implements Measure# 17 */ return (FKT_DisableCHV_n_EnableCHV (pin, SIMDRV_INS_ENABLE_CHV)); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_Increase | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_Increase. */ GLOBAL USHORT FKT_Increase (UBYTE * data) { USHORT sw1sw2; USHORT size = 0; U8 reader_id; T_SIMDRV_cmd_header cmd_header; T_SIMDRV_data_info data_info; T_SIMDRV_result_info result_info; UBYTE response[SIMDRV_MAX_RESULT]; TRACE_FUNCTION ("FKT_Increase()"); reader_id = SIMDRV_VAL_READER_ID__RANGE_MIN; cmd_header.cla = SIMDRV_GSM_CLASS_BYTE ; cmd_header.ins = SIMDRV_INS_INCREASE; cmd_header.p1 = 0; cmd_header.p2 = 0; data_info.data = (U8 *)data; data_info.c_data = 3; result_info.result = response; result_info.c_result = size; result_info.len = NOT_PRESENT_16BIT; sw1sw2 = simdrv_xch_apdu(reader_id,cmd_header,data_info,&result_info); return FKT_convert_error (sw1sw2,result_info.c_result); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_Invalidate | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_Invalidate. */ GLOBAL USHORT FKT_Invalidate (void) { /* Implements Measure# 16 */ return (FKT_Invalidate_n_Rehabilitate(SIMDRV_INS_INVALIDATE)); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_ReadBinary | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_ReadBinary. */ GLOBAL USHORT FKT_ReadBinary (UBYTE * data, USHORT offset, USHORT length) { USHORT sw1sw2; USHORT size = 0; U8 reader_id; T_SIMDRV_cmd_header cmd_header; T_SIMDRV_data_info data_info; T_SIMDRV_result_info result_info; U8 offset_high; U8 offset_low; TRACE_FUNCTION ("FKT_ReadBinary()"); offset_high = (U8)((offset &0x7F00)>>8); /* to make the 8th bit 0 as per 102.221 */ offset_low = (U8)(offset & 0x00FF); reader_id = SIMDRV_VAL_READER_ID__RANGE_MIN; cmd_header.cla = SIMDRV_GSM_CLASS_BYTE; cmd_header.ins = SIMDRV_INS_READ_BINARY; cmd_header.p1 =offset_high ; cmd_header.p2 =offset_low ; data_info.data = NULL; data_info.c_data = 0; result_info.result = (U8 *)data; result_info.c_result = size; result_info.len = (USHORT)length; sw1sw2= simdrv_xch_apdu (reader_id,cmd_header,data_info,&result_info); return FKT_convert_error (sw1sw2,result_info.c_result); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_ReadRecord | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_ReadRecord. */ GLOBAL USHORT FKT_ReadRecord (UBYTE * data, UBYTE mode, USHORT record, USHORT length) { USHORT sw1sw2; USHORT size = 0; U8 reader_id; T_SIMDRV_cmd_header cmd_header; T_SIMDRV_data_info data_info; T_SIMDRV_result_info result_info; #if !defined NTRACE /* Implements Measure#32: Row 37 */ TRACE_EVENT_P1("FKT_ReadRecord(): Nr. %hu", record); #endif reader_id = SIMDRV_VAL_READER_ID__RANGE_MIN; cmd_header.cla = SIMDRV_GSM_CLASS_BYTE; cmd_header.ins = SIMDRV_INS_READ_RECORD; cmd_header.p1 = (U8)record; cmd_header.p2 = (U8)mode; data_info.data = NULL; data_info.c_data = 0; result_info.result = (U8 *)data ; result_info.c_result = size; result_info.len =(USHORT)length; sw1sw2= simdrv_xch_apdu (reader_id,cmd_header,data_info,&result_info); return FKT_convert_error (sw1sw2,result_info.c_result); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_Rehabilitate | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_Rehabilitate. */ GLOBAL USHORT FKT_Rehabilitate (void) { /* Implements Measure# 16 */ return (FKT_Invalidate_n_Rehabilitate(SIMDRV_INS_REHABILITATE)); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_Status | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_Status. */ GLOBAL USHORT FKT_Status (UBYTE * pin_cnt, UBYTE * pin2_cnt, UBYTE * puk_cnt, UBYTE * puk2_cnt) { USHORT size = 0; USHORT sw1sw2; U8 reader_id; T_SIMDRV_cmd_header cmd_header; T_SIMDRV_data_info data_info; T_SIMDRV_result_info result_info; USHORT cause; USHORT fileid; union { T_DIR_STATUS status; UBYTE response [40]; } dir; TRACE_FUNCTION ("FKT_Status()"); memset (dir.response, 0, sizeof(dir.response)); reader_id = SIMDRV_VAL_READER_ID__RANGE_MIN; cmd_header.cla = SIMDRV_GSM_CLASS_BYTE; cmd_header.ins = SIMDRV_INS_STATUS; cmd_header.p1 = 0; cmd_header.p2 = 0; data_info.data = NULL; data_info.c_data = 0; result_info.result = (U8 *)dir.response; result_info.c_result = size; result_info.len = sim_data.dir_status_len; sw1sw2 = simdrv_xch_apdu(reader_id, cmd_header, data_info, &result_info); cause = FKT_convert_error (sw1sw2,result_info.c_result); *pin_cnt = 0; *puk_cnt = 0; *pin2_cnt = 0; *puk2_cnt = 0; if (cause EQ SIM_NO_ERROR) { /* * Check file id on active call: if different from last directory * indicate failure during SIM Presence Detection (27.20). * A selection of a non-existent DF (possible with SIM_ACCESS_REQ) * leads to the loss of the current DF: this confuses the SIM * Presence Detection, therefore the validity of the actual DF * stored in 'sim_data.act_directory' must be considered. */ fileid = (dir.status.fileid[0] << 8) | dir.status.fileid[1]; if (SIM_IS_FLAG_SET (CALL_ACTIVE) AND /* call active */ sim_data.act_directory NEQ NOT_PRESENT_16BIT /* actual DF known? */ AND fileid NEQ sim_data.act_directory) /* compare DF */ return SIM_CAUSE_CARD_REMOVED; else { if (SIM_TI_DRV_X_BYTES > 0) /* discard SW1, SW2 from response! */ memset (&dir.response[sim_data.dir_status_len], 0, SIM_TI_DRV_X_BYTES); /* * Directory status is available */ *pin_cnt = FKT_check_pin_count (dir.status.pinstatus); *puk_cnt = FKT_check_pin_count (dir.status.unbstatus); *pin2_cnt = FKT_check_pin_count (dir.status.pin2status); *puk2_cnt = FKT_check_pin_count (dir.status.unb2status); } } return cause; } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_RunGSMAlgo | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_RunGSMAlgo. */ GLOBAL USHORT FKT_RunGSMAlgo (UBYTE * rand, UBYTE * data, USHORT len) { USHORT sw1sw2; USHORT size = 0; U8 reader_id; T_SIMDRV_cmd_header cmd_header; T_SIMDRV_data_info data_info; T_SIMDRV_result_info result_info; TRACE_FUNCTION ("FKT_RunGSMAlgo()"); reader_id = SIMDRV_VAL_READER_ID__RANGE_MIN; cmd_header.cla = SIMDRV_GSM_CLASS_BYTE ; cmd_header.ins = SIMDRV_INS_AUTHENTICATE; cmd_header.p1 = 0; cmd_header.p2 = 0; data_info.data = (U8*)rand; data_info.c_data = MAX_RAND; result_info.result = data; result_info.c_result = size; result_info.len = len; sw1sw2= simdrv_xch_apdu (reader_id,cmd_header,data_info,&result_info); return FKT_convert_error (sw1sw2,result_info.c_result); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_Select | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_Select. */ LOCAL USHORT fkt_select_one (USHORT id, UBYTE * data, USHORT len) { USHORT size = 0; USHORT sw1sw2; U8 reader_id; T_SIMDRV_cmd_header cmd_header; U8 field[2]; T_SIMDRV_data_info data_info; T_SIMDRV_result_info result_info; TRACE_EVENT_P1 ("fkt_select_one() : File id =%X ", id); reader_id = SIMDRV_VAL_READER_ID__RANGE_MIN; cmd_header.cla = SIMDRV_GSM_CLASS_BYTE; cmd_header.ins = SIMDRV_INS_SELECT; cmd_header.p1 = 0; cmd_header.p2 = 0; field[0] =(U8) (id>>8); /* high byte */ field[1] =(U8) id; /* low byte */ data_info.data = field; data_info.c_data = sizeof(field); result_info.result = data; result_info.c_result = size; result_info.len = len; TRACE_EVENT_P1 ("Expected result size from SIM =%X ", result_info.len); sw1sw2 = simdrv_xch_apdu(reader_id, cmd_header, data_info, &result_info); return FKT_convert_error (sw1sw2,result_info.c_result); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : sim_select_df | +--------------------------------------------------------------------+ PURPOSE : Function to select the directory given the path. */ LOCAL USHORT sim_select_df(U16 dir_level,UBYTE *data,USHORT len) { USHORT result = SIM_NO_ERROR; result = fkt_select_one (dir_level, data, len); if (result NEQ SIM_NO_ERROR) { sim_data.act_directory = NOT_PRESENT_16BIT; sim_data.act_field = NOT_PRESENT_16BIT; } else { sim_data.act_directory = dir_level; } return result; } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_Select | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_Select. */ GLOBAL USHORT FKT_Select (USHORT id, BOOL path_info_present, T_path_info * path_info_ptr, UBYTE * data, USHORT len) { USHORT result; USHORT directory = (SIM_IS_FLAG_SET (GSM_DATAFIELD))? SIM_DF_GSM: SIM_DF_1800; /* default parent directory */ #if !defined NTRACE /* Implements Measure#32: Row 39 */ TRACE_EVENT_P1("FKT_Select(): id = %04X", id); #endif switch (id & 0xFF00) /* selecting DF deselects EF */ { case 0x3F00: case 0x7F00: case 0x5F00: sim_data.act_field = NOT_PRESENT_16BIT; break; } if( path_info_present NEQ FALSE ) { if((sim_data.act_directory & 0xFF00) NEQ 0x5F00 AND sim_data.act_directory NEQ NOT_PRESENT_16BIT) { /* Currently selected df is MF or a first level directory */ if(sim_data.act_directory NEQ path_info_ptr->df_level1) { result = sim_select_df(path_info_ptr->df_level1,data,len); if(result NEQ SIM_NO_ERROR) return result; } } /* Currently selected df is a second level directory */ else { result = sim_select_df(SIM_MF,data,len); if(result NEQ SIM_NO_ERROR) return result; result = sim_select_df(path_info_ptr->df_level1,data,len); if(result NEQ SIM_NO_ERROR) return result; } if(path_info_ptr->v_df_level2) { result = sim_select_df(path_info_ptr->df_level2,data,len); if(result NEQ SIM_NO_ERROR) return result; } result = fkt_select_one (id, data, len); if (result NEQ SIM_NO_ERROR) { sim_data.act_field = NOT_PRESENT_16BIT; } else { sim_data.act_field = id; } return result; } else { switch (id) { case SIM_MF: result = fkt_select_one (SIM_MF, data, len); if (result NEQ SIM_NO_ERROR) sim_data.act_directory = NOT_PRESENT_16BIT; else { sim_data.dir_status_len = sim_data.sim_data_len; sim_data.act_directory = id; } return result; default: /* All the standard defined EFs would be handled before coming to this * point. Complete path information should be given for non-standard 2nd level EFs * and they also would be handled before coming to this point. * This statement will be hit for non-standard files * without path information. Hence returning error */ return SIM_CAUSE_UNKN_FILE_ID; /* continue here in case of any first level directory */ case SIM_DF_GSM: case SIM_DF_1800: case SIM_DF_TELECOM: case SIM_DF_VI: if (sim_data.act_directory EQ id) return SIM_NO_ERROR; /* already selected */ else { /* If current directory has not been selected or it is a 2nd level and under another 1st level DF */ if (((sim_data.act_directory & 0xFF00) EQ 0x5F00 AND ! SIM_IS_DF_LEVEL2_UNDER_DF_LEVEL1(sim_data.act_directory,id)) OR sim_data.act_directory EQ NOT_PRESENT_16BIT) { /* MF has to be selected first */ result = sim_select_df(SIM_MF,data,len); if(result NEQ SIM_NO_ERROR) return result; } result = fkt_select_one (id, data, len); if (result NEQ SIM_NO_ERROR) { sim_data.act_directory = NOT_PRESENT_16BIT; sim_data.act_field = NOT_PRESENT_16BIT; } else { sim_data.dir_status_len = sim_data.sim_data_len; sim_data.act_directory = id; } return result; } case SIM_DF_GRAPHICS: directory = SIM_DF_TELECOM; /* parent directory */ /* no break */ /*lint -fallthrough*/ case SIM_DF_SOLSA: case SIM_DF_MEXE: if (sim_data.act_directory EQ id) return SIM_NO_ERROR; /* already selected */ if (sim_data.act_directory NEQ directory) { /* not the parent directory */ /* If current directory is MF or first level OR if the 2nd level directory is under another 1st level df, select the parent directory */ if((sim_data.act_directory & 0xFF00) NEQ 0x5F00 || (!SIM_IS_DF_LEVEL2_UNDER_DF_LEVEL1(sim_data.act_directory,directory)) ) { result = FKT_Select (directory, FALSE, NULL, data, len); if (result NEQ SIM_NO_ERROR) { sim_data.act_directory = NOT_PRESENT_16BIT; return result; } } } result = fkt_select_one (id, data, len); if (result NEQ SIM_NO_ERROR) { sim_data.act_directory = NOT_PRESENT_16BIT; sim_data.act_field = NOT_PRESENT_16BIT; } else { sim_data.dir_status_len = sim_data.sim_data_len; sim_data.act_directory = id; } return result; case SIM_ICCID: case SIM_ELP: /* * Access to Root Directory */ directory = SIM_MF; break; case SIM_ADN: case SIM_FDN: case SIM_SMS: case SIM_CCP: case SIM_MSISDN: case SIM_SMSP: case SIM_SMSS: case SIM_LND: case SIM_SMSR: case SIM_SDN: case SIM_EXT1: case SIM_EXT2: case SIM_EXT3: case SIM_BDN: case SIM_EXT4: /* VO temp PATCH: Needed for reading CPHS info num from old SIMs */ case SIM_CPHS_INFN2: /* VO temp PATCH end */ /* * Access to Telecom Directory */ directory = SIM_DF_TELECOM; break; case SIM_LP: case SIM_IMSI: case SIM_KC: case SIM_PLMNSEL: case SIM_HPLMN: case SIM_ACMMAX: case SIM_SST: case SIM_ACM: case SIM_GID1: case SIM_GID2: case SIM_PUCT: case SIM_CBMI: case SIM_SPN: case SIM_CBMID: case SIM_BCCH: case SIM_ACC: case SIM_FPLMN: case SIM_LOCI: case SIM_AD: case SIM_PHASE: case SIM_VGCS: case SIM_VGCSS: case SIM_VBS: case SIM_VBSS: case SIM_EMLPP: case SIM_AAEM: case SIM_ECC: case SIM_CBMIR: case SIM_DCK: case SIM_CNL: case SIM_NIA: case SIM_KCGPRS: case SIM_LOCGPRS: case SIM_SUME: case SIM_CPHS_VMW: case SIM_CPHS_SST: case SIM_CPHS_CFF: case SIM_CPHS_ONSTR: case SIM_CPHS_CSP: case SIM_CPHS_CINF: case SIM_CPHS_MBXN: case SIM_CPHS_ONSHF: case SIM_CPHS_INFN: #ifdef REL99 case SIM_UCPS_ACTEC: case SIM_OCPS_ACTEC: case SIM_HPLMN_ACT: case SIM_CPBCCH: case SIM_INV_SCAN: case SIM_RPLMN_ACT: #endif case SIM_PNN: case SIM_OPL: /* * Access to GSM */ directory = (SIM_IS_FLAG_SET (GSM_DATAFIELD))? SIM_DF_GSM: SIM_DF_1800; break; case SIM_MEXE_ST: case SIM_ORPK: case SIM_ARPK: case SIM_TPRPK: /* * Access to MExE Directory */ directory = SIM_DF_MEXE; break; case SIM_IMG: /* * Access to Icon Directory */ directory = SIM_DF_GRAPHICS; break; case SIM_SAI: case SIM_SLL: /* * Access to SoLSA Directory */ directory = SIM_DF_SOLSA; break; } } if (sim_data.act_directory NEQ directory) { /* * select directory */ result = FKT_Select (directory, FALSE, NULL, data, len); if (result NEQ SIM_NO_ERROR) /* directory selection fails */ { sim_data.act_directory = NOT_PRESENT_16BIT; sim_data.act_field = NOT_PRESENT_16BIT; return result; } } if (sim_data.act_field NEQ id) { /* * secondly select elementary field */ result = fkt_select_one (id, data, len); if (result NEQ SIM_NO_ERROR) /* EF selection fails */ { sim_data.act_field = NOT_PRESENT_16BIT; #ifdef __INVALID /* more sophisticated SELECT error handling */ sw1 = (UBYTE)(SIM_Status_Extended ((UBYTE *)response, 6, &size) >> 8); if (sw1 NEQ 0x90 AND sw1 NEQ 0x91) /* * SIM Status request failed */ sim_data.act_directory = NOT_PRESENT_16BIT; else if (((response[4] << 8) | response[5]) NEQ sim_data.act_directory) /* * SIM Presence Detection indicates invalid SIM */ sim_data.act_directory = NOT_PRESENT_16BIT; #endif } else { sim_data.act_directory = directory; sim_data.act_field = id; } return result; } else /* * field is already selected */ return SIM_NO_ERR_FILE_ALREADY_SELECTED; } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_UnblockCHV | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_UnblockCHV. */ GLOBAL USHORT FKT_UnblockCHV (UBYTE * unblockCHV, UBYTE * new_CHV, UBYTE chvType) { /* Implements Measure# 13 */ return (FKT_ChangeCHV_n_UnblockCHV (unblockCHV, new_CHV, chvType, SIMDRV_INS_UNBLOCK_CHV)); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_UpdateBinary | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_UpdateBinary. */ GLOBAL USHORT FKT_UpdateBinary (UBYTE * data, USHORT length, USHORT offset) { USHORT size = 0; USHORT sw1sw2; U8 reader_id; T_SIMDRV_cmd_header cmd_header; T_SIMDRV_data_info data_info; T_SIMDRV_result_info result_info; U8 offset_high; U8 offset_low; UBYTE response[SIMDRV_MAX_RESULT]; TRACE_FUNCTION ("FKT_UpdateBinary()"); offset_high = (U8)((offset &0x7F00)>>8);/*to make the 8th bit 0 as per 102.221*/ offset_low = (U8)(offset & 0x00FF); reader_id = SIMDRV_VAL_READER_ID__RANGE_MIN; cmd_header.cla = SIMDRV_GSM_CLASS_BYTE ; cmd_header.ins = SIMDRV_INS_UPDATE_BINARY; cmd_header.p1 = offset_high; cmd_header.p2 = offset_low; data_info.data = (U8 *)data; data_info.c_data = (U8)length; result_info.result = response; result_info.c_result = size; result_info.len = NOT_PRESENT_16BIT; sw1sw2= simdrv_xch_apdu (reader_id,cmd_header,data_info,&result_info); return FKT_convert_error (sw1sw2,result_info.c_result); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_UpdateRecord | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_UpdateRecord. */ GLOBAL USHORT FKT_UpdateRecord (UBYTE * data, USHORT length, UBYTE mode, USHORT record) { USHORT size = 0; USHORT sw1sw2; U8 reader_id; T_SIMDRV_cmd_header cmd_header; T_SIMDRV_data_info data_info; T_SIMDRV_result_info result_info; UBYTE response[SIMDRV_MAX_RESULT]; #if !defined NTRACE /* Implements Measure#32: Row 40 */ TRACE_EVENT_P1("FKT_UpdateRecord(): Nr. %hu", record); #endif reader_id = SIMDRV_VAL_READER_ID__RANGE_MIN; cmd_header.cla = SIMDRV_GSM_CLASS_BYTE ; cmd_header.ins = SIMDRV_INS_UPDATE_RECORD; cmd_header.p1 = (U8)record; cmd_header.p2 = (U8)mode; data_info.data = (U8*)data; data_info.c_data = (U8)length; result_info.result = response; result_info.c_result = size; result_info.len = NOT_PRESENT_16BIT; sw1sw2= simdrv_xch_apdu (reader_id,cmd_header,data_info,&result_info); return FKT_convert_error (sw1sw2,result_info.c_result); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (6302) MODULE : SIM_FKT | | STATE : code ROUTINE : FKT_VerifyCHV | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_VerifyCHV. */ GLOBAL USHORT FKT_VerifyCHV (UBYTE * pin, UBYTE pin_id) { USHORT size = 0; USHORT sw1sw2; U8 reader_id; T_SIMDRV_cmd_header cmd_header; T_SIMDRV_data_info data_info; T_SIMDRV_result_info result_info; UBYTE response[SIMDRV_MAX_RESULT]; TRACE_FUNCTION ("FKT_VerifyCHV()"); reader_id = SIMDRV_VAL_READER_ID__RANGE_MIN; cmd_header.cla = SIMDRV_GSM_CLASS_BYTE; cmd_header.ins = SIMDRV_INS_VERIFY_CHV; cmd_header.p1 = 0x00; cmd_header.p2 = pin_id; data_info.data = (U8 *)pin; data_info.c_data = MAX_PIN_LEN; result_info.result = response; result_info.c_result = size; result_info.len = NOT_PRESENT_16BIT; sw1sw2 = simdrv_xch_apdu(reader_id, cmd_header, data_info, &result_info); return FKT_convert_error (sw1sw2,result_info.c_result); } /* +********************************************************************+ | Moved from sim_stk.c - for CQ 34109 under feature flag SIM_TOOLKIT | +********************************************************************+ */ #ifdef SIM_TOOLKIT /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (8419) MODULE : SIM_STK | | STATE : code ROUTINE : FKT_TerminalResponse | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_TerminalResponse */ static const UBYTE timer_env[] = { STK_TIMER_EXPIRATION_TAG, STK_DEVICE_IDENTITY_LEN+STK_TIMER_ID_LEN+STK_TIMER_VALUE_LEN+6, STK_DEVICE_IDENTITY_TAG|STK_COMPREHENSION_REQUIRED, STK_DEVICE_IDENTITY_LEN, 0x82, 0x81, STK_TIMER_ID_TAG|STK_COMPREHENSION_REQUIRED, STK_TIMER_ID_LEN, 0, STK_TIMER_VALUE_TAG|STK_COMPREHENSION_REQUIRED, STK_TIMER_VALUE_LEN, 0, 0, 0 }; UBYTE pending_timers[9] = {0,0,0,0,0,0,0,0,0}; UBYTE next_pos_to_fill = 0; UBYTE next_pos_to_send = 0; GLOBAL USHORT FKT_TerminalResponse (UBYTE * data, USHORT length) { USHORT size = 0; USHORT sw1sw2; U8 reader_id; T_SIMDRV_cmd_header cmd_header; T_SIMDRV_data_info data_info; T_SIMDRV_result_info result_info; UBYTE response[SIMDRV_MAX_RESULT]; UBYTE env[sizeof(timer_env)]; USHORT index; UBYTE dummy[4]; USHORT error; USHORT i; TRACE_FUNCTION ("FKT_TerminalResponse()"); reader_id = SIMDRV_VAL_READER_ID__RANGE_MIN; cmd_header.cla = SIMDRV_GSM_CLASS_BYTE ; cmd_header.ins = SIMDRV_INS_TERMINAL_RESPONSE; cmd_header.p1 = 0; cmd_header.p2 = 0; data_info.data = data; data_info.c_data = (U8)length; result_info.result = response; result_info.c_result = size; result_info.len = NOT_PRESENT_16BIT; sw1sw2 = simdrv_xch_apdu(reader_id,cmd_header,data_info,&result_info); sim_data.term_resp_sent = TRUE; SIM_EM_TERMINAL_RESPONSE; /* * if SIM response is OK, try resending pending timer expiry envelopes (send updated envelopes) */ if( 0x9000 == sw1sw2 ) { for(i=0;i<8;i++) { if (next_pos_to_fill != next_pos_to_send) { /* * some timer expiry envelopes are pending */ index = pending_timers[next_pos_to_send]; memcpy (env, timer_env, sizeof(timer_env)); env[8] = (UBYTE)(index + 1); /* Timer number range is 1..8 */ env[11] = sim_data.timer[index].hour; env[12] = sim_data.timer[index].minute; env[13] = sim_data.timer[index].second; error = FKT_Envelope (dummy, env, sizeof(timer_env),0); if(8 == next_pos_to_send) { next_pos_to_send = 0; } else { next_pos_to_send++; } if (error NEQ SIM_NO_ERROR) { break; } } } } return FKT_convert_error (sw1sw2,result_info.c_result); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (8419) MODULE : SIM_STK | | STATE : code ROUTINE : FKT_Envelope | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_Envelope */ GLOBAL USHORT FKT_Envelope (UBYTE * data_out, UBYTE * data_in, USHORT in_length, USHORT out_length) { USHORT size = 0; USHORT sw1sw2; USHORT error; U8 reader_id; T_SIMDRV_cmd_header cmd_header; T_SIMDRV_data_info data_info; T_SIMDRV_result_info result_info; TRACE_FUNCTION ("FKT_Envelope()"); reader_id = SIMDRV_VAL_READER_ID__RANGE_MIN; cmd_header.cla = SIMDRV_GSM_CLASS_BYTE; cmd_header.ins = SIMDRV_INS_ENVELOPE; cmd_header.p1 = 0; cmd_header.p2 = 0; data_info.data = data_in; data_info.c_data = (U8)in_length; result_info.result = data_out; result_info.c_result = size; result_info.len = out_length; sw1sw2 = simdrv_xch_apdu(reader_id,cmd_header,data_info,&result_info); SIM_EM_ENVELOPE; sim_data.sim_data_len = 0; TRACE_EVENT("sim_data.sim_data_len initialised as 0"); /* for debug only - to be removed */ error = FKT_convert_error (sw1sw2,result_info.c_result); stk_l_cmd = sim_data.sim_data_len << 3; return error; } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (8419) MODULE : SIM_STK | | STATE : code ROUTINE : FKT_TerminalProfile | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_TerminalProfile */ GLOBAL USHORT FKT_TerminalProfile (UBYTE * data, USHORT length) { USHORT size = 0; USHORT sw1sw2; U8 reader_id; T_SIMDRV_cmd_header cmd_header; T_SIMDRV_data_info data_info; T_SIMDRV_result_info result_info; UBYTE response[SIMDRV_MAX_RESULT]; TRACE_FUNCTION ("FKT_TerminalProfile()"); reader_id = SIMDRV_VAL_READER_ID__RANGE_MIN; cmd_header.cla = SIMDRV_GSM_CLASS_BYTE; cmd_header.ins = SIMDRV_INS_TERMINAL_PROFILE; cmd_header.p1 = 0; cmd_header.p2 = 0; data_info.data = data; data_info.c_data = (U8)length; result_info.result = response; result_info.c_result = size; result_info.len = NOT_PRESENT_16BIT; sw1sw2= simdrv_xch_apdu(reader_id,cmd_header,data_info,&result_info); return FKT_convert_error (sw1sw2,result_info.c_result); } /* +--------------------------------------------------------------------+ | PROJECT : GSM-PS (8419) MODULE : SIM_STK | | STATE : code ROUTINE : FKT_Fetch | +--------------------------------------------------------------------+ PURPOSE : Wrapping function for the SIM driver call SIM_Fetch */ GLOBAL USHORT FKT_Fetch (UBYTE * cmd, USHORT length) { USHORT size = 0; USHORT sw1sw2; U8 reader_id; T_SIMDRV_cmd_header cmd_header; T_SIMDRV_data_info data_info; T_SIMDRV_result_info result_info; TRACE_FUNCTION ("FKT_Fetch()"); reader_id = SIMDRV_VAL_READER_ID__RANGE_MIN; cmd_header.cla = SIMDRV_GSM_CLASS_BYTE; cmd_header.ins = SIMDRV_INS_FETCH; cmd_header.p1 = 0; cmd_header.p2 = 0; data_info.data = NULL; data_info.c_data = 0; result_info.result = cmd; result_info.c_result = size; result_info.len = (USHORT)length; sw1sw2 = simdrv_xch_apdu(reader_id,cmd_header,data_info,&result_info); return FKT_convert_error (sw1sw2,result_info.c_result); } #endif /* SIM_TOOLKIT */ #endif