[Feature]Upload Modem source code

Change-Id: Id4294f30faced84d3e6fd6d5e61e1111bf287a37
diff --git a/mcu/driver/devdrv/usim/src/usim_smt.c b/mcu/driver/devdrv/usim/src/usim_smt.c
new file mode 100644
index 0000000..7ebc59f
--- /dev/null
+++ b/mcu/driver/devdrv/usim/src/usim_smt.c
@@ -0,0 +1,1594 @@
+#include "kal_public_api.h"
+#include "drv_comm.h"
+#include "reg_base.h"
+
+#include "sim_hw_mtk.h"
+#include "sim_drv_HW_def_MTK.h"
+#include "sim_al.h"
+#include "sim_drv_SW_struct.h"
+#include "sim_drv_SW_API.h"
+
+#include "sim_drv_SW_function.h"
+
+#include "drv_rstctl.h"
+#include "drvpdn.h"
+#include "drv_gdma.h"
+#include "us_timer.h"
+
+
+#define	USIM_ATRSTA_OFF	0x0001
+
+#define USIM_3_3V KAL_TRUE
+#ifdef USIM_3_3V
+    #define	USIM_VOL_CFG	0x1
+#else
+    #define	USIM_VOL_CFG	0x0
+#endif
+
+#define	USIM_SMT_NO_ERROR		0x0
+#define	USIM_SMT_NO_TS			0x1
+#define	USIM_SMT_NO_TOUT		0x2
+#define	USIM_SMT_NO_T0END		0x3
+#define	USIM_SMT_NO_ATRSTA_OFF		0x4
+#define	USIM_SMT_SW_ERROR		0x5
+#define	USIM_SMT_COUNT_ERROR		0x6
+#define	USIM_SMT_HDMA_ERROR		0x7
+#define USIM_SMT_IFCLR_ERROR		0x8
+#define USIM_SMT_PPS_ERROR		0x9
+#define USIM_SMT_MT6306_ERROR		0xA
+#define	USIM_SMT_INVALID_TS		0xB
+#define USIM_SMT_TOO_MANY_ATR		0xC
+#define USIM_SMT_ATR_TIMEOUT		0xD
+#define USIM_SMT_UNEXPT_DATA		0xE
+#define USIM_SMT_INTERFACE_ERROR	0xF
+
+// macro
+#define	USIM_SMT_UPDATE_USIM_IF_FLAG(_if) do {					\
+        if((_if) == 0)								\
+        {									\
+            usim_base = SIM_base;						\
+        } else if((_if) == 1)							\
+        {									\
+            usim_base = SIM2_base;						\
+        } else SIM_DEBUG_ASSERT(0);							\
+    } while(0)
+
+#define	USIM_SMT_BASIC_SETTING(_if) do {					\
+        if((_if) == 0)								\
+        {									\
+            PDN_CLR(PDN_USIM1);						\
+            HDMA_PDN_CLR(0);						\
+        } else if((_if) == 1)							\
+        {									\
+            PDN_CLR(PDN_USIM2);						\
+            HDMA_PDN_CLR(1);						\
+        } else SIM_DEBUG_ASSERT(0);							\
+        usim_iftest_sw_reset_usim((_if));					\
+    } while(0)
+
+#ifdef __FPGA__
+#define	USIM_SMT_DEACTIVATION(_if)	do {		\
+        DRV_Reg32(usim_base + SIM_CTRL_MTK) = (DRV_Reg32(usim_base + SIM_CTRL_MTK) & (~SIM_CTRL_SIMON)); \
+    } while(0)
+#else
+#define	USIM_SMT_DEACTIVATION(_if)	do {		\
+        DRV_WriteReg32((usim_base + SIM_IRQEN_MTK), SIM_IRQEN_ALLOFF); \
+        DRV_WriteReg32((usim_base + SIM_CTRL_MTK), DRV_Reg32(usim_base + SIM_CTRL_MTK) | SIM_CTRL_IFCLR); \
+        DRV_Reg32(usim_base + SIM_CTRL_MTK) = (DRV_Reg32(usim_base + SIM_CTRL_MTK) & (~SIM_CTRL_SIMON)); \
+        while(!(DRV_Reg32(usim_base + SIM_ATRSTA_MTK) & 0x0001)); \
+        DRV_ICC_PMU_switch((_if), KAL_FALSE);	\
+    } while(0)
+#endif
+
+extern kal_uint32    sim_uncachedTxBuffer0[], sim_uncachedRxBuffer0[], sim_uncachedTxBuffer1[], sim_uncachedRxBuffer1[];
+
+int usim_iftest_for_smt(kal_uint32 hwInterfaceNo);
+void usim_iftest_sw_reset_usim(kal_uint32 hwInterfaceNo);
+
+extern kal_char sim_shared_dbgstr[];
+#if !defined(ATEST_DRV_ENABLE)
+extern void slt_dbg_print(char *fmt, ...);
+#else
+#define slt_dbg_print(...) dbg_print( __VA_ARGS__)
+#endif
+
+#ifdef SIM_DRV_SWITCH_MT6306
+#include "sim_mt6306.h"
+extern void MT6306_Writer_GPIO(kal_uint8 device_addr, kal_uint8 data_addr, kal_uint8 data_value);
+extern void MT6306_HW_I2C_writer(kal_uint8 addr, kal_uint8 data_addr, kal_uint8 data_value);
+extern kal_uint32 MT6306_geti2cInterface(kal_uint32 MT6306Interface);
+extern kal_uint8 MT6306_Reader_AL(kal_uint8 chipno, kal_uint16 addr);
+extern kal_bool MT6306_ShowReg(int chip);
+extern DCL_HANDLE clkHandle, datHandle;;
+
+static int MT6306_validateREG(kal_uint8 chipno, kal_uint8 reg, kal_uint8 writeVal)
+{
+    kal_uint8 readvalue = MT6306_Reader_AL(chipno, reg);
+    kal_uint32 log_size = 0;
+
+    if (readvalue != writeVal)
+    {
+        log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]MT6306 Error: chip:%d, reg:%x, Write:%x, Read:%x\n\r", chipno, reg, writeVal, readvalue);
+        if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+
+        return USIM_SMT_MT6306_ERROR;
+    }
+
+    return USIM_SMT_NO_ERROR;
+}
+
+int MT6306_blockRST(kal_uint8 chipno, kal_uint8 port, kal_uint8 level)
+{
+    kal_uint8 value = MT6306_Reader_AL(chipno, SIM_MT6306_REG_RST);
+
+    value |= (1 << port);
+    value &= ~(4 << port);
+    if (level) value |= (4 << port);
+    if (MT6306_geti2cInterface(0) == MT6306_I2C_USE_HW_I2C)
+        MT6306_HW_I2C_writer(0x64, SIM_MT6306_REG_RST + (chipno * 4), value);
+    else
+        MT6306_Writer_GPIO(0x64, SIM_MT6306_REG_RST + (chipno * 4), value);
+
+    return MT6306_validateREG(chipno, SIM_MT6306_REG_RST, value);
+}
+
+int MT6306_blockCLK(kal_uint8 chipno, kal_uint8 port)
+{
+    kal_uint8 value = MT6306_Reader_AL(chipno, SIM_MT6306_REG_CLK);
+
+    value &= ~(1 << port);
+    value &= ~(4 << port);
+    if (MT6306_geti2cInterface(0) == MT6306_I2C_USE_HW_I2C)
+        MT6306_HW_I2C_writer(0x64, SIM_MT6306_REG_CLK + (chipno * 4), value);
+    else
+        MT6306_Writer_GPIO(0x64, SIM_MT6306_REG_CLK + (chipno * 4), value);
+
+    return MT6306_validateREG(chipno, SIM_MT6306_REG_CLK, value);
+}
+
+int MT6306_blockDAT(kal_uint8 chipno, kal_uint8 port)
+{
+    kal_uint8 value = MT6306_Reader_AL(chipno, SIM_MT6306_REG_DAT);
+
+    value &= ~(1 << port);
+    value &= ~(4 << port);
+    if (MT6306_geti2cInterface(0) == MT6306_I2C_USE_HW_I2C)
+        MT6306_HW_I2C_writer(0x64, SIM_MT6306_REG_DAT + (chipno * 4), value);
+    else
+        MT6306_Writer_GPIO(0x64, SIM_MT6306_REG_DAT + (chipno * 4), value);
+
+    return MT6306_validateREG(chipno, SIM_MT6306_REG_DAT, value);
+}
+
+int MT6306_passRST(kal_uint8 chipno, kal_uint8 port)
+{
+    kal_uint8 value = MT6306_Reader_AL(chipno, SIM_MT6306_REG_RST);
+
+    value &= ~(1 << port);
+    if (MT6306_geti2cInterface(0) == MT6306_I2C_USE_HW_I2C)
+        MT6306_HW_I2C_writer(0x64, SIM_MT6306_REG_RST + (chipno * 4), value);
+    else
+        MT6306_Writer_GPIO(0x64, SIM_MT6306_REG_RST + (chipno * 4), value);
+
+    return MT6306_validateREG(chipno, SIM_MT6306_REG_RST, value);
+}
+
+int MT6306_passCLK(kal_uint8 chipno, kal_uint8 port)
+{
+    kal_uint8 value = MT6306_Reader_AL(chipno, SIM_MT6306_REG_CLK);
+
+    value |= (1 << port);
+    value &= ~(4 << port);
+
+    if (MT6306_geti2cInterface(0) == MT6306_I2C_USE_HW_I2C)
+        MT6306_HW_I2C_writer(0x64, SIM_MT6306_REG_CLK + (chipno * 4), value);
+    else
+        MT6306_Writer_GPIO(0x64, SIM_MT6306_REG_CLK + (chipno * 4), value);
+
+    return MT6306_validateREG(chipno, SIM_MT6306_REG_CLK, value);
+}
+
+int MT6306_passDAT(kal_uint8 chipno, kal_uint8 port)
+{
+    kal_uint8 value = MT6306_Reader_AL(chipno, SIM_MT6306_REG_DAT);
+
+    value |= (1 << port);
+    value &= ~(4 << port);
+    if (MT6306_geti2cInterface(0) == MT6306_I2C_USE_HW_I2C)
+        MT6306_HW_I2C_writer(0x64, SIM_MT6306_REG_DAT + (chipno * 4), value);
+    else
+        MT6306_Writer_GPIO(0x64, SIM_MT6306_REG_DAT + (chipno * 4), value);
+
+    return MT6306_validateREG(chipno, SIM_MT6306_REG_DAT, value);
+}
+
+int MT6306_setVCC(kal_uint8 chipno, kal_uint8 port, kal_uint32 onoff, kal_uint32 level)
+{
+    kal_uint8 value = MT6306_Reader_AL(chipno, SIM_MT6306_REG_VCC);
+
+    if (onoff == 0) value &= ~(4 << port);
+    else value |= (4 << port);
+
+    if (level == 0) value &= ~(1 << port);
+    else value |= (1 << port);
+
+    if (MT6306_geti2cInterface(0) == MT6306_I2C_USE_HW_I2C)
+        MT6306_HW_I2C_writer(0x64, SIM_MT6306_REG_VCC + (chipno * 4), value);
+    else
+        MT6306_Writer_GPIO(0x64, SIM_MT6306_REG_VCC + (chipno * 4), value);
+
+    return MT6306_validateREG(chipno, SIM_MT6306_REG_VCC, value);
+}
+
+int MT6306_passALLSignal(kal_uint8 chipno, kal_uint8 port)
+{
+    int result = USIM_SMT_NO_ERROR;
+
+    result |= MT6306_passRST(chipno, port);
+    result |= MT6306_passCLK(chipno, port);
+    result |= MT6306_passDAT(chipno, port);
+
+    return result;
+}
+
+int MT6306_blockALLSignal(kal_uint8 chipno, kal_uint8 port)
+{
+    int result = USIM_SMT_NO_ERROR;
+
+    result |= MT6306_blockRST(chipno, port, 0);
+    result |= MT6306_blockCLK(chipno, port);
+    result |= MT6306_blockDAT(chipno, port);
+
+    return result;
+}
+#endif // #ifdef SIM_DRV_SWITCH_MT6306
+
+#ifdef __FPGA__
+#else
+//    extern DCL_UINT32 DRV_Read_PMIC_Data(DCL_UINT32 pmic_addr);
+#endif
+
+static int usim_iftest_sim_activation_conv(kal_uint32 hwInterfaceNo, kal_uint32 class_b_or_c, usim_dir_enum conv)
+{
+    kal_uint32 usim_base = 0;
+    kal_uint16 reg_val = 0;
+
+    // 0. Update USIM interface flag
+    USIM_SMT_BASIC_SETTING(hwInterfaceNo);
+    USIM_SMT_UPDATE_USIM_IF_FLAG(hwInterfaceNo);
+
+    // 1. get ATR STR
+#ifdef __FPGA__
+#else
+    // 1.0 Deactivate SIM
+    DRV_ICC_PMU_switch(hwInterfaceNo, KAL_FALSE);
+    ust_us_busyloop(50000);
+#endif
+#if defined(DRV_SIM_6292_SERIES)|| defined(DRV_SIM_6293_SERIES)
+    DRV_Reg32(usim_base + SIM_BRR_MTK) = (372 << 2);
+#elif defined(SIM_DRV_3_71MHZ_SCLK)
+    DRV_Reg32(usim_base + SIM_BRR_MTK) = (DRV_Reg32(usim_base + SIM_BRR_MTK) & 0x0800) | (372 << 2);
+#else
+    DRV_Reg32(usim_base + SIM_BRR_MTK) = (DRV_Reg32(usim_base + SIM_BRR_MTK) & 0x3) | (372 << 2);
+#endif
+    DRV_Reg32(usim_base + SIM_TOUT_MTK) = (10000 >> 4) + 1;
+    DRV_Reg32(usim_base + SIM_CONF_MTK) = DRV_Reg32(usim_base + SIM_CONF_MTK) & ~(SIM_CONF_TOUTEN);
+    DRV_Reg32(usim_base + SIM_CTRL_MTK) = DRV_Reg32(usim_base + SIM_CTRL_MTK) & ~(SIM_CTRL_SIMON);
+
+    // 1.1 Set RXTIDE of SIM_TIDE to 0 and TXTIDE to 1
+    DRV_Reg32(usim_base + SIM_TIDE_MTK) = (DRV_Reg32(usim_base + SIM_TIDE_MTK) & (~SIM_TIDE_RXMASK) & (~SIM_TIDE_TXMASK)) | 0x0100;
+
+    // 1.2 Clear Interrupt
+    DRV_Reg32(usim_base + SIM_STS_MTK) = DRV_Reg32(usim_base + SIM_STS_MTK);
+
+    // 1.3 If TOUT = 1, T0EN/T1EN = 0
+    reg_val = (DRV_Reg32(usim_base + SIM_CONF_MTK) & ~(SIM_CONF_T0EN | SIM_CONF_T1EN | SIM_CONF_TOUTEN | USIM_VOL_CFG)) | (SIM_CONF_TOUTEN | USIM_VOL_CFG);
+    if (conv == USIM_DIRECT)
+    {
+        reg_val &= ~(SIM_CONF_CONV);
+    }
+    else
+    {
+        reg_val |= SIM_CONF_CONV;
+    }
+    DRV_Reg32(usim_base + SIM_CONF_MTK) = reg_val;
+#ifdef __FPGA__
+#else
+    DRV_ICC_PMU_setVolt(hwInterfaceNo, class_b_or_c);
+    DRV_ICC_PMU_switch(hwInterfaceNo, KAL_TRUE);
+#endif
+    // 1.4 Set SIMON, Activate SIM
+    DRV_Reg32(usim_base + SIM_CTRL_MTK) = (DRV_Reg32(usim_base + SIM_CTRL_MTK) & (~SIM_CTRL_SIMON)) | SIM_CTRL_SIMON;
+
+    return 0;
+}
+
+int usim_iftest_sim_activation(kal_uint32 hwInterfaceNo, kal_uint32 class_b_or_c)
+{
+    return usim_iftest_sim_activation_conv(hwInterfaceNo, class_b_or_c, USIM_DIRECT);
+}
+
+int usim_iftest_sim_activation_inverse(kal_uint32 hwInterfaceNo, kal_uint32 class_b_or_c)
+{
+    return usim_iftest_sim_activation_conv(hwInterfaceNo, class_b_or_c, USIM_INVERSE);
+}
+
+int usim_iftest_tout_test(kal_uint32 hwInterfaceNo) {
+    kal_uint32 usim_base = 0;
+    kal_uint32 orig_brr = 0;
+    kal_uint32 ret_val = USIM_SMT_NO_ERROR;
+    kal_uint32 etu_setting = 0, tout_setting = 0, int_sts = 0;
+
+    // 0. Update USIM interface flag
+    USIM_SMT_UPDATE_USIM_IF_FLAG(hwInterfaceNo);
+
+    // 1. Disable Interrupt & Clear Interrupt Status
+    DRV_Reg32(usim_base + SIM_IRQEN_MTK) = 0;
+    DRV_Reg32(usim_base + SIM_STS_MTK) = 0xFFFFFFFF;
+
+    // 2. Save BRR, will restore before case complete
+    orig_brr = DRV_Reg32(usim_base + SIM_BRR_MTK);
+
+    for (etu_setting = 16; etu_setting <= 32 && ret_val == USIM_SMT_NO_ERROR; etu_setting *= 2) {
+        //  Set 1ETU = etu_setting CLK
+        DRV_Reg32(usim_base + SIM_BRR_MTK) = (orig_brr & (~(0x1FF<<2))) | (16<<2);
+
+        for (tout_setting = 5; tout_setting < 10; tout_setting += 2) {
+            // 3. Set TOUT to (tout_setting+1)*16ETU
+            DRV_Reg32(usim_base + SIM_CONF_MTK) = DRV_Reg32(usim_base + SIM_CONF_MTK) & (~SIM_CONF_TOUTEN);
+            DRV_Reg32(usim_base + SIM_TOUT_MTK) = tout_setting;    // means (tout_setting+1)*16 ETU
+            DRV_Reg32(usim_base + SIM_CONF_MTK) = DRV_Reg32(usim_base + SIM_CONF_MTK) | (SIM_CONF_TOUTEN);
+
+            // 4. Wait TOUT Interrupt Status
+            kal_uint32 start_time = ust_get_current_time();
+            kal_uint32 duration;
+            while ((duration = ust_us_duration(start_time, ust_get_current_time())) < 10*1000) {
+                // TOUT should happen after ([6,8,10])*16*([16,32])=1536~5120 SIM CLKs@3.25MHz < 1.58ms
+                if ((int_sts = DRV_Reg32(usim_base + SIM_STS_MTK)) & SIM_STS_TOUT) {
+                    break;
+                }
+            }
+
+            DRV_Reg32(usim_base + SIM_STS_MTK) = int_sts;
+            if ((int_sts & SIM_STS_TOUT) == 0) {
+                ret_val = USIM_SMT_NO_TOUT;
+                slt_dbg_print("[SIM_SMT]: TOUT not happen when etu=%d tout=%d\r\n", etu_setting, tout_setting);
+                break;
+            }
+
+            // Check duration ???
+        }
+    }
+
+    // 5. Disable TOUT & Clear Interrupt Status & Restore BRR
+    DRV_Reg32(usim_base + SIM_CONF_MTK) = DRV_Reg32(usim_base + SIM_CONF_MTK) & (~SIM_CONF_TOUTEN);
+    DRV_Reg32(usim_base + SIM_STS_MTK) = 0xFFFFFFFF;
+    DRV_Reg32(usim_base + SIM_BRR_MTK) = orig_brr;
+
+    return ret_val;
+}
+
+void pmic_dump(void)
+{
+/*
+    int i, j = 0;
+    kal_uint32 val = 0;
+
+    for (i = 0; i < 0xff0; i += 2)
+    {
+        if (j % 5)  slt_dbg_print("[PMIC_DVT] ");
+#ifdef __FPGA__
+#else
+        val = DRV_Read_PMIC_Data(i);
+#endif
+
+        if (val != 0x5aa5)  slt_dbg_print("[0x%x]= 0x%x ", i, val);
+
+        j++;
+
+        if ((j % 5) == 0)   slt_dbg_print("\n\r");
+    }
+*/
+    return;
+}
+
+void sim_dump_reg_debug(kal_uint32 usim_base)
+{
+    slt_dbg_print("SIM Reg Dump: \n\r");
+    slt_dbg_print("%x, %x, %x, %x, %x\n\r", usim_base, DRV_Reg32(usim_base + SIM_VERSION_MTK),
+                  DRV_Reg32(usim_base + SIM_CTRL_MTK), DRV_Reg32(usim_base + SIM_CONF_MTK), DRV_Reg32(usim_base + SIM_CONFSTA_MTK));
+
+    slt_dbg_print("%x, %x, %x, %x, %x\n\r", DRV_Reg32(usim_base + SIM_BRR_MTK), DRV_Reg32(usim_base + SIM_IRQEN_MTK),
+                  DRV_Reg32(usim_base + SIM_STS_MTK), DRV_Reg32(usim_base + SIM_RETRY_MTK), DRV_Reg32(usim_base + SIM_TIDE_MTK));
+
+    slt_dbg_print("%x, %x, %x, %x, %x\n\r", 0, DRV_Reg32(usim_base + SIM_COUNT_MTK),
+                  DRV_Reg32(usim_base + SIM_ATIME_MTK), DRV_Reg32(usim_base + SIM_DTIME_MTK), DRV_Reg32(usim_base + SIM_TOUT_MTK));
+
+    slt_dbg_print("%x, %x, %x, %x, %x\n\r", DRV_Reg32(usim_base + SIM_GTIME_MTK), DRV_Reg32(usim_base + SIM_ETIME_MTK),
+                  DRV_Reg32(usim_base + SIM_EXT_TIME_MTK), DRV_Reg32(usim_base + SIM_CGTIME_MTK), DRV_Reg32(usim_base + SIM_COMDCTRL_MTK));
+
+    slt_dbg_print("%x, %x, %x, %x, %x\n\r", DRV_Reg32(usim_base + SIM_COMDLEN_MTK), DRV_Reg32(usim_base + SIM_LEFTLEN_MTK),
+                  DRV_Reg32(usim_base + SIM_SW1_MTK), DRV_Reg32(usim_base + SIM_SW2_MTK), DRV_Reg32(usim_base + SIM_ATRSTA_MTK));
+
+    return;
+}
+
+int usim_iftest_get_atr(kal_uint32 hwInterfaceNo, kal_uint8 atr_bytes[])
+{
+    kal_uint32 usim_base = 0, log_size = 0;
+    kal_uint8 *atr_ptr = atr_bytes + 1;
+    kal_uint8 TS, TDi, hist_cnt, next_cnt;
+    kal_uint32 start_time = 0;
+    kal_bool T0_Recved = KAL_FALSE, Hist_Recved = KAL_FALSE;
+    int ret_val = USIM_SMT_NO_ERROR;
+
+start:
+    
+    USIM_SMT_UPDATE_USIM_IF_FLAG(hwInterfaceNo);
+    start_time = ust_get_current_time();
+
+    // Wait first bytes of ATR
+    while (DRV_Reg32(usim_base + SIM_COUNT_MTK) == 0) {
+        if (DRV_Reg32(usim_base + SIM_STS_MTK) & SIM_STS_NATR) {
+            log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]: NO TS, %x, %d\n\r", usim_base, hwInterfaceNo);
+            if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+            ret_val = USIM_SMT_NO_TS;
+            goto end;
+        }
+    }
+
+    // Check if TS is valid
+    TS = DRV_Reg32(usim_base + SIM_DATA_MTK);
+    if (TS != 0x3B && TS != 0x3F) {
+        if (TS == 0x03) {
+            // Inverse Convention 0x3F will be decoded as 0x03  in Direct Convention
+            usim_iftest_sim_activation_inverse(hwInterfaceNo, CLASS_B_30V);
+            goto start;
+        } else {
+            log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]: Invalid TS, %x, %d, %x\n\r", usim_base, hwInterfaceNo, TS);
+            if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+            ret_val =  USIM_SMT_INVALID_TS;
+            goto end;
+        }
+    }
+
+
+    // Got Valid TS
+    *atr_ptr++ = TS;
+
+    // Receive other ATR bytes
+    next_cnt = 1;   // To read T0
+    for (;;) {
+        while (next_cnt > 0) {
+            if (DRV_Reg32(usim_base + SIM_COUNT_MTK) > 0) {
+                *atr_ptr++ = DRV_Reg32(usim_base + SIM_DATA_MTK);
+                next_cnt --;
+
+                if (atr_ptr - atr_bytes - 1 > 32) {
+                    ret_val = USIM_SMT_TOO_MANY_ATR;
+                    DRV_ICC_print_str("[SIM_SMT]: Received ATR data > 32 bytes");
+                    goto end;
+                }
+            }
+
+            if ((DRV_Reg32(usim_base + SIM_STS_MTK) & SIM_STS_TOUT) != 0
+                || ust_us_duration(start_time, ust_get_current_time()) > 2*1000*1000L ) {
+                // Actually TOUT should happen if it's functinality is OK
+                ret_val = USIM_SMT_ATR_TIMEOUT;
+                DRV_ICC_print_str("[SIM_SMT]: Timeout when receiving ATR data");
+                goto end;
+            }
+        }
+
+        if (Hist_Recved == KAL_TRUE) {
+            // All ATR bytes have been received, excluding the optional byte of TCK
+            kal_uint32 tck_poll_start = ust_get_current_time();
+            while(ust_us_duration(tck_poll_start, ust_get_current_time()) < 10*1000) {
+                // TCK will come in 12 ETU, 1.4ms@3.25MHz SIM CLK, if not coming TCK is not exist
+                if (DRV_Reg32(usim_base + SIM_COUNT_MTK) > 0) {
+                    *atr_ptr++ = DRV_Reg32(usim_base + SIM_DATA_MTK);   // TCK
+                    break;
+                }
+            }
+
+            // SIO should be idle now, Check TOUT function
+            if (usim_iftest_tout_test(hwInterfaceNo) != USIM_SMT_NO_ERROR) {
+                ret_val = USIM_SMT_NO_TOUT;
+                goto end;
+            }
+
+            // Check if more data in FIFO, it's error if there are more data
+            if (DRV_Reg32(usim_base + SIM_COUNT_MTK) > 0) {
+                ret_val = USIM_SMT_UNEXPT_DATA;
+                DRV_ICC_print_str("[SIM_SMT]: ATR received, but have unexpected data in FIFO");
+                goto end;
+            }
+
+            // Now, every thing should be good
+            atr_bytes[0] = atr_ptr - atr_bytes - 1;
+            goto end;
+        }
+        
+        TDi = atr_ptr[-1];      // T0, TD1, TD2, ...
+
+        if (T0_Recved == KAL_FALSE) {
+            T0_Recved = KAL_TRUE;
+            hist_cnt = TDi&0x0F;
+        }
+
+        next_cnt = 0;   // actually, it have already been 0
+        USIM_CAL_TD_COUNT(TDi, next_cnt);
+
+        if (TDi & TDMask) {
+            next_cnt ++;
+        } else {
+            next_cnt += hist_cnt;
+            Hist_Recved = KAL_TRUE;
+        }
+    }
+
+end:
+    if (ret_val != USIM_SMT_NO_ERROR) {
+        DRV_Reg32(usim_base + SIM_CONF_MTK) = DRV_Reg32(usim_base + SIM_CONF_MTK) & ~(SIM_CONF_TOUTEN);
+        DRV_Reg32(usim_base + SIM_STS_MTK) = DRV_Reg32(usim_base + SIM_STS_MTK);
+        
+        sim_dump_reg_debug(usim_base);
+        pmic_dump();
+        
+        USIM_SMT_DEACTIVATION(hwInterfaceNo);
+    }
+    return ret_val;
+}
+
+int usim_iftest_send_pps(kal_uint32 hwInterfaceNo, kal_uint8 atr_bytes[], kal_uint8 pps_buf[], kal_bool *need_pps)
+{
+    kal_uint32 usim_base = 0, j = 0, log_size = 0;
+    kal_uint32 cksum = 0xFF;
+
+    USIM_SMT_UPDATE_USIM_IF_FLAG(hwInterfaceNo);
+
+    if (atr_bytes[2] & 0x80) // TD1
+    {
+        j = 0;
+        if (atr_bytes[2] & 0x10) j++;
+        if (atr_bytes[2] & 0x20) j++;
+        if (atr_bytes[2] & 0x40) j++;
+        if (atr_bytes[2] & 0x80) j++;
+        if (atr_bytes[2 + j] & 0x10) // TA2
+        {
+            // TA1 && negotiable TA2
+            if ((atr_bytes[2] & 0x10) && (atr_bytes[2 + j + 1] & 0x80) == 0x0) *need_pps = KAL_TRUE;
+        }
+        else
+        {
+            // TA1 && TD1
+            if ((atr_bytes[2] & 0x10)) *need_pps = KAL_TRUE;
+        }
+    }
+    else if (atr_bytes[2] & 0x10)  // TA1 && no TD1
+    {
+        *need_pps = KAL_TRUE;
+    }
+
+    *need_pps = atr_bytes[3] != 0x01 && atr_bytes[3] != 0x11 && (atr_bytes[2] & 0x10) &&  *need_pps;
+
+    if (*need_pps)
+    {
+        // Set TOUT = 1
+        DRV_Reg32(usim_base + SIM_CONF_MTK) = (DRV_Reg32(usim_base + SIM_CONF_MTK) & ~(SIM_CONF_TOUTEN | USIM_VOL_CFG)) | (SIM_CONF_TOUTEN | USIM_VOL_CFG);
+        // Clear
+        DRV_Reg32(usim_base + SIM_COMDCTRL_MTK) = DRV_Reg32(usim_base + SIM_COMDCTRL_MTK) | SIM_CTRL_IFCLR;
+        j = 0;
+        while (DRV_Reg32(usim_base + SIM_CONFSTA_MTK) & SIM_CONFSTA_IFCLR_ON)
+        {
+            if (j > 0xFFFFFF)
+            {
+                USIM_SMT_DEACTIVATION(hwInterfaceNo);
+                log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]: IFCLR ERROR\n\r");
+                if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+                return USIM_SMT_IFCLR_ERROR;
+            }
+            j++;
+        }
+
+        // Set RXTIDE of SIM_TIDE to 0 and TXTIDE to 1
+        DRV_Reg32(usim_base + SIM_TIDE_MTK) = (DRV_Reg32(usim_base + SIM_TIDE_MTK) & (~SIM_TIDE_RXMASK) & (~SIM_TIDE_TXMASK)) | 0x0100;
+
+        j = 0;
+        // Send PPSS
+        DRV_Reg32(usim_base + SIM_DATA_MTK) = 0xFF;
+        pps_buf[j++] = 0xFF;
+        // Send PPS0
+        DRV_Reg32(usim_base + SIM_DATA_MTK) = 0x10;
+        cksum ^= 0x10;
+        pps_buf[j++] = 0x10;
+        // Send PPS1
+        // Propose new Fi, Di
+        DRV_Reg32(usim_base + SIM_DATA_MTK) = atr_bytes[3];
+        cksum ^= atr_bytes[3];
+        pps_buf[j++] = atr_bytes[3];
+
+        // Send PCK
+        DRV_Reg32(usim_base + SIM_DATA_MTK) = cksum;
+        pps_buf[j++] = cksum;
+
+        // Wait Until TX FIFO Empty
+        j = 0;
+        while (DRV_Reg32(usim_base + SIM_COUNT_MTK) != 0)
+        {
+            if (j > 0xFFFFFF)
+            {
+                USIM_SMT_DEACTIVATION(hwInterfaceNo);
+                log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]: COUNT ERROR\n\r");
+                if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+                return USIM_SMT_COUNT_ERROR;
+            }
+            j++;
+
+        }
+    }
+
+    return 0; // temp
+}
+
+int usim_iftest_get_pps(kal_uint32 hwInterfaceNo, kal_uint8 atr_bytes[], kal_uint8 pps_buf[], kal_bool need_pps)
+{
+    kal_uint32 usim_base = 0, i = 0, j = 0;
+    kal_uint32 data = 0, fifo_cnt = 0, log_size = 0;
+
+    if (need_pps == KAL_FALSE) return 0;
+
+    USIM_SMT_UPDATE_USIM_IF_FLAG(hwInterfaceNo);
+
+    // PPS Exchange RX
+    while (1)
+    {
+        fifo_cnt = DRV_Reg32(usim_base + SIM_COUNT_MTK);
+
+        // FIFO Non-Empty
+        if (fifo_cnt != 0x0)
+        {
+            for (i = 0; i < fifo_cnt; i++)
+            {
+                data = DRV_Reg32(usim_base + SIM_DATA_MTK);
+                if (pps_buf[j++] != data)
+                {
+                    log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]: not consistent:%x %x\n\r", data, pps_buf[j - 1]);
+                    if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+                    USIM_SMT_DEACTIVATION(hwInterfaceNo);
+                    return USIM_SMT_PPS_ERROR;
+                }
+            }
+        }
+
+        // TOUT status = 1
+        if ((DRV_Reg32(usim_base + SIM_STS_MTK) & SIM_STS_TOUT) || (j >= 4))
+        {
+            if (data == 0)
+            {
+                if (DRV_Reg32(usim_base + SIM_COUNT_MTK) == 0x0)
+                {
+                    log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]: USIM does not reply on time\n\r");
+                    if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+                    USIM_SMT_DEACTIVATION(hwInterfaceNo);
+                    return USIM_SMT_PPS_ERROR;
+                }
+            }
+
+            // Clear Interrupt
+            DRV_Reg32(usim_base + SIM_STS_MTK) = DRV_Reg32(usim_base + SIM_STS_MTK);
+            // Clear IP's Internal TOUT enable bit
+            DRV_Reg32(usim_base + SIM_CONF_MTK) = (DRV_Reg32(usim_base + SIM_CONF_MTK) & ~(SIM_CONF_TOUTEN | USIM_VOL_CFG)) | (USIM_VOL_CFG);
+            break;
+        }
+    }
+
+    if (atr_bytes[3] == ATR_TA1_64) DRV_Reg32(usim_base + SIM_BRR_MTK) = (DRV_Reg32(usim_base + SIM_BRR_MTK) & 0x3) | ((512 / 8) << 2);
+    else if (atr_bytes[3] == ATR_TA1_32) DRV_Reg32(usim_base + SIM_BRR_MTK) = (DRV_Reg32(usim_base + SIM_BRR_MTK) & 0x3) | ((512 / 16) << 2);
+    else if (atr_bytes[3] == ATR_TA1_16) DRV_Reg32(usim_base + SIM_BRR_MTK) = (DRV_Reg32(usim_base + SIM_BRR_MTK) & 0x3) | ((512 / 32) << 2);
+    else if (atr_bytes[3] == ATR_TA1_8) DRV_Reg32(usim_base + SIM_BRR_MTK) = (DRV_Reg32(usim_base + SIM_BRR_MTK) & 0x3) | ((512 / 64) << 2);
+    else SIM_DEBUG_ASSERT(0);
+
+    return 0;
+}
+
+
+
+int usim_iftest_send_sim_command(kal_uint32 hwInterfaceNo, kal_uint8 tx_buf[], kal_uint32 tx_len, kal_uint32 rx_len)
+{
+    kal_uint32 usim_base = 0, i = 0, j = 0, log_size = 0;
+
+    USIM_SMT_UPDATE_USIM_IF_FLAG(hwInterfaceNo);
+
+    // clear
+    DRV_Reg32(usim_base + SIM_CTRL_MTK) = DRV_Reg32(usim_base + SIM_CTRL_MTK) | SIM_CTRL_IFCLR;
+    j = 0;
+    while (DRV_Reg32(usim_base + SIM_CONFSTA_MTK) & SIM_CONFSTA_IFCLR_ON)
+    {
+        if (j > 0xFFFFFF)
+        {
+            USIM_SMT_DEACTIVATION(hwInterfaceNo);
+            log_size = kal_sprintf(sim_shared_dbgstr, " [SIM_SMT]: IFCLR ERROR\n\r");
+            if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+            return USIM_SMT_IFCLR_ERROR ;
+        }
+        j++;
+    }
+    // 2.0 Select File of ICCID
+    // 2.0 set file id
+
+    // 2.1 Set RXTIDE of SIM_TIDE to 0 and TXTIDE to 1 (Note: TXTIDE cannot be 0 for DMA)
+    DRV_Reg32(usim_base + SIM_TIDE_MTK) = (DRV_Reg32(usim_base + SIM_TIDE_MTK) & (~SIM_TIDE_RXMASK) & (~SIM_TIDE_TXMASK)) | 0x0100;
+
+    // 2.2 Enable T0
+    DRV_Reg32(usim_base + SIM_CONF_MTK) = DRV_Reg32(usim_base + SIM_CONF_MTK) | SIM_CONF_T0EN;
+
+    // 2.3 Directly Write File ID to USIM FIFO
+    DRV_Reg32(usim_base + SIM_DATA_MTK) = tx_buf[0];
+    DRV_Reg32(usim_base + SIM_DATA_MTK) = tx_buf[1];
+    DRV_Reg32(usim_base + SIM_DATA_MTK) = tx_buf[2];
+    DRV_Reg32(usim_base + SIM_DATA_MTK) = tx_buf[3];
+    DRV_Reg32(usim_base + SIM_DATA_MTK) = tx_buf[4];
+
+    if (tx_len > 5)
+    {
+        if (hwInterfaceNo)
+        {
+            // HDMA TX (Memory to Device), USIM's Bus Width is Fixed to 8 bits
+            for (i = 5; i < tx_len; i++)
+                DRV_Reg8(((kal_uint32) sim_uncachedTxBuffer1) + i - 5) = tx_buf[i];
+
+	    MM_Sync();
+
+            DRV_Reg32(REG_HDMA_HDCTRR1) = HDCTRR_RX_SEL0(0) | HDCTRR_BST_SIZE(HDCTRR_BST_SIZE_16) | HDCTRR_DEV_BUS_WIDTH(HDCTRR_BUS_WIDTH_8) | HDCTRR_MEM_BUS_WIDTH(HDCTRR_BUS_WIDTH_32);
+            DRV_Reg32(REG_HDMA_HPRGA0R1) = (kal_uint32) sim_uncachedTxBuffer1;
+            DRV_Reg32(REG_HDMA_HDC0R1) = HDCR_XFER_SIZE0(tx_buf[4]) | HDCR_START0;
+        }
+        else
+        {
+            // HDMA TX (Memory to Device), USIM's Bus Width is Fixed to 8 bits
+            for (i = 5; i < tx_len; i++)
+                DRV_Reg8(((kal_uint32) sim_uncachedTxBuffer0) + i - 5) = tx_buf[i];
+
+	    MM_Sync();
+
+            DRV_Reg32(REG_HDMA_HDCTRR0) = HDCTRR_RX_SEL0(0) | HDCTRR_BST_SIZE(HDCTRR_BST_SIZE_16) | HDCTRR_DEV_BUS_WIDTH(HDCTRR_BUS_WIDTH_8) | HDCTRR_MEM_BUS_WIDTH(HDCTRR_BUS_WIDTH_32);
+            DRV_Reg32(REG_HDMA_HPRGA0R0) = (kal_uint32) sim_uncachedTxBuffer0;
+            DRV_Reg32(REG_HDMA_HDC0R0) = HDCR_XFER_SIZE0(tx_buf[4]) | HDCR_START0;
+        }
+    }
+
+    // for Get Responseo
+    if (rx_len && tx_len <= 5)
+    {
+        if (hwInterfaceNo)
+        {
+            // HDMA RX (Memory to Device), USIM's Bus Width is Fixed to 8 bits
+            DRV_Reg32(REG_HDMA_HDCTRR1) = HDCTRR_RX_SEL0(1) | HDCTRR_BST_SIZE(HDCTRR_BST_SIZE_16) | HDCTRR_DEV_BUS_WIDTH(HDCTRR_BUS_WIDTH_8) | HDCTRR_MEM_BUS_WIDTH(HDCTRR_BUS_WIDTH_32);
+            DRV_Reg32(REG_HDMA_HPRGA0R1) = (kal_uint32) sim_uncachedRxBuffer1;
+            DRV_Reg32(REG_HDMA_HDC0R1) = HDCR_XFER_SIZE0(rx_len) | HDCR_START0;
+        }
+        else
+        {
+            // HDMA RX (Memory to Device), USIM's Bus Width is Fixed to 8 bits
+            DRV_Reg32(REG_HDMA_HDCTRR0) = HDCTRR_RX_SEL0(1) | HDCTRR_BST_SIZE(HDCTRR_BST_SIZE_16) | HDCTRR_DEV_BUS_WIDTH(HDCTRR_BUS_WIDTH_8) | HDCTRR_MEM_BUS_WIDTH(HDCTRR_BUS_WIDTH_32);
+            DRV_Reg32(REG_HDMA_HPRGA0R0) = (kal_uint32) sim_uncachedRxBuffer0;
+            DRV_Reg32(REG_HDMA_HDC0R0) = HDCR_XFER_SIZE0(rx_len) | HDCR_START0;
+        }
+    }
+
+    DRV_Reg32(usim_base + SIM_COMDLEN_MTK) = tx_buf[4];
+
+    if (tx_len > 5)
+    {
+        DRV_Reg32(usim_base + SIM_COMDCTRL_MTK) = SIM_INS_START | SIM_INS_INSD | tx_buf[1]; // Expect to Send
+    }
+    else if (rx_len && tx_len <= 5)
+    {
+        DRV_Reg32(usim_base + SIM_COMDCTRL_MTK) = SIM_INS_START | tx_buf[1]; // Expect to Send
+    }
+
+    MO_Sync();
+
+    return 0;
+}
+
+int usim_iftest_get_sim_response(kal_uint32 hwInterfaceNo, kal_bool rx_data, kal_uint32 *sw1, kal_uint32 *sw2)
+{
+    kal_uint32 usim_base = 0, log_size = 0;
+    kal_uint32 j = 0;
+
+    USIM_SMT_UPDATE_USIM_IF_FLAG(hwInterfaceNo);
+
+    // Wait Until TX FIFO Empty
+    j = 0;
+    while (DRV_Reg32(usim_base + SIM_COUNT_MTK) != 0)
+    {
+        if (j > 0xFFFFFF)
+        {
+            USIM_SMT_DEACTIVATION(hwInterfaceNo);
+            log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]: COUNT ERROR\n\r");
+            if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+            return USIM_SMT_COUNT_ERROR;
+        }
+        j++;
+    }
+
+    // 2.4 Wait for Operation Done (Including Response)
+    j = 0;
+    while (!(DRV_Reg32(usim_base + SIM_STS_MTK) & SIM_STS_T0END))
+    {
+        if (j > 0xFFFFFF)
+        {
+            USIM_SMT_DEACTIVATION(hwInterfaceNo);
+            log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT:%d]: NO T0END\n\r", __LINE__);
+            if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+            return USIM_SMT_NO_T0END;
+        }
+        j++;
+    }
+
+    if (rx_data)
+    {
+        j = 0;
+        if (hwInterfaceNo)
+        {
+            while ((DRV_Reg32(REG_HDMA_HDSR) & HDMA_STAT0_1))
+            {
+                if (j > 0xFFFFFF)
+                {
+                    USIM_SMT_DEACTIVATION(hwInterfaceNo);
+                    log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]: HDMA ERROR\n\r");
+                    if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+                    return USIM_SMT_HDMA_ERROR;
+                }
+                j++;
+            }
+            /*
+            kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]: Get %x %x %x %x %x  %x %x %x %x %x  %x %x %x %x %x\n\r",
+                        sim_uncachedRxBuffer1[0], sim_uncachedRxBuffer1[1], sim_uncachedRxBuffer1[2], sim_uncachedRxBuffer1[3], sim_uncachedRxBuffer1[4],
+                        sim_uncachedRxBuffer1[5], sim_uncachedRxBuffer1[6], sim_uncachedRxBuffer1[7], sim_uncachedRxBuffer1[8], sim_uncachedRxBuffer1[9],
+                        sim_uncachedRxBuffer1[10], sim_uncachedRxBuffer1[11], sim_uncachedRxBuffer1[12], sim_uncachedRxBuffer1[13], sim_uncachedRxBuffer1[14]);
+                    */
+
+            for (j=0;j<15;j++)
+            {
+                 log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]: Get %d:%x\r\n", j, *(((kal_uint8 *) sim_uncachedRxBuffer1) + j));
+                 if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+            }
+                
+        }
+        else
+        {
+            while ((DRV_Reg32(REG_HDMA_HDSR) & HDMA_STAT0_0))
+            {
+                if (j > 0xFFFFFF)
+                {
+                    USIM_SMT_DEACTIVATION(hwInterfaceNo);
+                    log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]: HDMA ERROR\n\r");
+                    if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+                    return USIM_SMT_HDMA_ERROR;
+                }
+                j++;
+            }
+            /*
+            kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]: Get %x %x %x %x %x  %x %x %x %x %x  %x %x %x %x %x\n\r",
+                        sim_uncachedRxBuffer0[0], sim_uncachedRxBuffer0[1], sim_uncachedRxBuffer0[2], sim_uncachedRxBuffer0[3], sim_uncachedRxBuffer0[4],
+                        sim_uncachedRxBuffer0[5], sim_uncachedRxBuffer0[6], sim_uncachedRxBuffer0[7], sim_uncachedRxBuffer0[8], sim_uncachedRxBuffer0[9],
+                        sim_uncachedRxBuffer0[10], sim_uncachedRxBuffer0[11], sim_uncachedRxBuffer0[12], sim_uncachedRxBuffer0[13], sim_uncachedRxBuffer0[14]);
+                        */
+            for (j=0;j<15;j++)
+            {
+                 log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]: Get %d:%x\r\n", j, *(((kal_uint8 *) sim_uncachedRxBuffer0) + j));
+                 if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+            }                        
+        }
+        //DRV_ICC_print_str(sim_shared_dbgstr);
+    }
+
+    // 2.5 Clear Interrupt
+    DRV_Reg32(usim_base + SIM_STS_MTK) = DRV_Reg32(usim_base + SIM_STS_MTK);
+
+    // 2.6 Check Returned Status Bytes
+    *sw1 = DRV_Reg32(usim_base + SIM_SW1_MTK);
+    *sw2 = DRV_Reg32(usim_base + SIM_SW2_MTK);
+
+    if ((*sw1 & 0xF0) != 0x90 && *sw1 != 0x69)
+    {
+        log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]: SW ERROR %x %x\n\r", *sw1, *sw2);
+        if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+        return USIM_SMT_SW_ERROR;
+    }
+
+    return 0;
+}
+
+int usim_iftest_sim_deactivation(kal_uint32 hwInterfaceNo)
+{
+    kal_uint32 usim_base = 0, log_size = 0;
+    kal_uint32 j = 0;
+
+    USIM_SMT_UPDATE_USIM_IF_FLAG(hwInterfaceNo);
+
+    // 3. Deactivation
+    // 3.0 If SIM Aleady Activated, Deactivate it
+    DRV_Reg32(usim_base + SIM_CTRL_MTK) = DRV_Reg32(usim_base + SIM_CTRL_MTK) & (~SIM_CTRL_SIMON);
+    j = 0;
+    while (!(DRV_Reg32(usim_base + SIM_ATRSTA_MTK) & USIM_ATRSTA_OFF))
+    {
+        if (j > 0xFFFFFF)
+        {
+            USIM_SMT_DEACTIVATION(hwInterfaceNo);
+            log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]: NO ATRSTA OFF\n\r");
+            if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+            return USIM_SMT_NO_ATRSTA_OFF;
+        }
+        j++;
+    }
+#ifdef __FPGA__
+#else
+    DRV_ICC_PMU_switch(hwInterfaceNo, KAL_FALSE);
+#endif
+
+    return 0;
+}
+
+#if defined(__SIM_DRV_CO_LOAD_MT6306__) && defined(SIM_DRV_SWITCH_MT6306)
+    extern kal_bool sim_connectMT6306;
+#endif
+int usim_iftest_for_smt(kal_uint32 interfaceNo)
+{
+    kal_uint32 func_status = 0;
+    kal_uint8 atr_bytes[50] = {0}, tx_buf[25] = {0}, pps_buf[10] = {0};
+    kal_uint32 sw1 = 0, sw2 = 0;
+    kal_bool need_pps = KAL_FALSE, forced_18v = KAL_FALSE;
+    kal_uint32 class_b_or_c = CLASS_B_30V, hwInterfaceNo = interfaceNo & 0xF, log_size = 0;
+
+    if (interfaceNo & 0xF0)
+        forced_18v = KAL_TRUE;
+
+    interfaceNo = interfaceNo & 0xF;
+
+    // for 3-SIM project, check sim_connectMT6306
+    if (interfaceNo == 4)
+    {
+#if defined(SIM_DRV_SWITCH_MT6306) && defined(__SIM_DRV_CO_LOAD_MT6306__)
+        return (kal_uint32) sim_connectMT6306;
+#elif defined(SIM_DRV_SWITCH_MT6306) && !defined(__SIM_DRV_CO_LOAD_MT6306__)
+        return (kal_uint32) KAL_TRUE;
+#else
+        return (kal_uint32) KAL_FALSE;
+#endif
+    }
+
+#ifdef SIM_DRV_SWITCH_MT6306
+    // for 3-SIM project, interfaceNo != hwInterfaceNo
+    kal_uint8 port = 0, chip = 0;
+#if defined(__SIM_DRV_CO_LOAD_MT6306__)
+    if(sim_connectMT6306 == KAL_TRUE)
+    {
+#endif
+        // hwInterfaceNo will be 0, 1, 2
+        hwInterfaceNo = interfaceNo / 2;
+        port = interfaceNo % 2;
+        chip = hwInterfaceNo;
+        log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]hwInterfaceNo:%d, chip:%d, port:%d", hwInterfaceNo, chip, port);
+        if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+#if defined(__SIM_DRV_CO_LOAD_MT6306__)
+    }
+#endif
+#endif
+
+    // check hwInterfaceNo
+    if (hwInterfaceNo > 1)
+    {
+        log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]: Invalid Interface:%d\n\r",hwInterfaceNo);
+        if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+        return USIM_SMT_INTERFACE_ERROR;
+    }
+
+    // Cards may be activated by other AT+CMD
+    usim_dcb_struct *usim_dcb;
+    usim_dcb = GET_USIM_CB(interfaceNo);
+    if (usim_dcb->present)
+    {
+        log_size = kal_sprintf(sim_shared_dbgstr, "[SIM_SMT]: driver status is correct\n\r");
+        if (log_size > 0) DRV_ICC_print_str(sim_shared_dbgstr);
+        return USIM_SMT_NO_ERROR;
+    }
+
+    // adjust VCC (default 3V)
+#if defined(SIM_DRV_SWITCH_MT6306) && defined(__SIM_DRV_CO_LOAD_MT6306__)
+        if(sim_connectMT6306 == KAL_TRUE) class_b_or_c = CLASS_C_18V;
+#elif defined(SIM_DRV_SWITCH_MT6306) && !defined(__SIM_DRV_CO_LOAD_MT6306__)
+        class_b_or_c = CLASS_C_18V;
+#else
+        if (forced_18v) class_b_or_c = CLASS_C_18V;
+#endif
+
+#ifdef SIM_DRV_SWITCH_MT6306
+#if defined(__SIM_DRV_CO_LOAD_MT6306__)
+    if(sim_connectMT6306 == KAL_TRUE)
+    {
+#endif
+        //Block all chip, all port
+        if (USIM_SMT_NO_ERROR != MT6306_blockALLSignal(0, 0))
+            return USIM_SMT_MT6306_ERROR;
+        if (USIM_SMT_NO_ERROR != MT6306_blockALLSignal(0, 1))
+            return USIM_SMT_MT6306_ERROR;
+        if (USIM_SMT_NO_ERROR != MT6306_blockALLSignal(1, 0))
+            return USIM_SMT_MT6306_ERROR;
+        if (USIM_SMT_NO_ERROR != MT6306_blockALLSignal(1, 1))
+            return USIM_SMT_MT6306_ERROR;
+        if (USIM_SMT_NO_ERROR != MT6306_setVCC(chip, 0, 0, 0))//turn off port 0
+            return USIM_SMT_MT6306_ERROR;
+        if (USIM_SMT_NO_ERROR != MT6306_setVCC(chip, 1, 0, 0))//turn off port 1
+            return USIM_SMT_MT6306_ERROR;
+
+        // adjsut VCC
+        if (forced_18v == KAL_TRUE)
+	{
+            // CLASS_C_18V
+            MT6306_setVCC(hwInterfaceNo, port, 1, 0);
+        }
+        else
+        {
+            // CLASS_B_30V
+            MT6306_setVCC(hwInterfaceNo, port, 1, 1);
+        }
+
+        // pass all signals of (chip, port)
+	MT6306_passALLSignal(chip, port);
+#if defined(__SIM_DRV_CO_LOAD_MT6306__)
+    }
+#endif
+#endif
+
+    usim_iftest_sim_activation(hwInterfaceNo, class_b_or_c);
+
+    func_status = usim_iftest_get_atr(hwInterfaceNo, atr_bytes);
+    if (func_status) return func_status;
+
+    func_status = usim_iftest_send_pps(hwInterfaceNo, atr_bytes, pps_buf, &need_pps);
+    if (func_status) return func_status;
+    func_status = usim_iftest_get_pps(hwInterfaceNo, atr_bytes, pps_buf, need_pps);
+    if (func_status) return func_status;
+    if (need_pps) kal_sleep_task(KAL_TICKS_50_MSEC);
+
+#define	EF_ICCID	0x2FE2
+    tx_buf[0] = 0xA0;
+    tx_buf[1] = 0xA4;
+    tx_buf[2] = 0x00;
+    tx_buf[3] = 0x00;
+    tx_buf[4] = 0x02;
+    tx_buf[5] = 0x2F;
+    tx_buf[6] = 0xE2;
+    func_status = usim_iftest_send_sim_command(hwInterfaceNo, tx_buf, 7, 0);
+    if (func_status) return func_status;
+    func_status = usim_iftest_get_sim_response(hwInterfaceNo, KAL_FALSE, &sw1, &sw2);
+    if (func_status) return func_status;
+// --
+    tx_buf[0] = 0xA0;
+    tx_buf[1] = 0xC0;
+    tx_buf[2] = 0x00;
+    tx_buf[3] = 0x00;
+    tx_buf[4] = sw2;
+    func_status = usim_iftest_send_sim_command(hwInterfaceNo, tx_buf, 5, tx_buf[4]);
+    if (func_status) return func_status;
+    func_status = usim_iftest_get_sim_response(hwInterfaceNo, KAL_TRUE, &sw1, &sw2);
+    if (func_status) return func_status;
+// --
+    tx_buf[0] = 0xA0;
+    tx_buf[1] = 0xB0;
+    tx_buf[2] = 0x00;
+    tx_buf[3] = 0x00;
+    tx_buf[4] = 10;
+    func_status = usim_iftest_send_sim_command(hwInterfaceNo, tx_buf, 5, tx_buf[4]);
+    if (func_status) return func_status;
+    func_status = usim_iftest_get_sim_response(hwInterfaceNo, KAL_TRUE, &sw1, &sw2);
+    if (func_status) return func_status;
+
+    func_status = usim_iftest_sim_deactivation(hwInterfaceNo);
+
+#ifdef SIM_DRV_SWITCH_MT6306
+#if defined(__SIM_DRV_CO_LOAD_MT6306__)
+    if(sim_connectMT6306 == KAL_TRUE)
+    {
+#endif
+        // patch for 3-SIM USIMSMT
+        MT6306_blockALLSignal(chip, port);
+        MT6306_setVCC(hwInterfaceNo, port, 0, 0); //Turn off VSIM
+#if defined(__SIM_DRV_CO_LOAD_MT6306__)
+    }
+#endif
+#endif
+
+    if (func_status) return func_status;
+
+    return USIM_SMT_NO_ERROR;
+}
+
+void usim_iftest_sw_reset_usim(kal_uint32 hwInterfaceNo)
+{
+#if   defined(MT6752)
+#endif
+    return;
+}
+#if defined(__IC_SLT__)
+typedef enum
+{
+    REG_GROUP_HDMA = 0,
+    REG_GROUP_USIM,
+    REG_GROUP_USIM2,
+    REG_GROUP_NUM,
+} REG_GROUP;
+typedef struct
+{
+    kal_uint32 addr;
+    kal_char attr[32];
+    kal_char reset_val[32];
+} usim_reg_desc_t;
+#define BASE_HDMA          BASE_ADDR_MDGDMA
+#define REG_HDMA_HDCSR0        (BASE_HDMA + 0x0100)
+#define HDMA_MODE_0             (1 << 9)        //channel 0
+#define HDMA_MODE_1             (1 << 25)       //channel 1
+#define REG_HDMA_HDSR          (BASE_HDMA + 0x0120) // shared
+#define HDMA_STAT0_0            (1 << 0)   // buffer 0, channel 0
+#define HDMA_STAT0_1            (1 << 1)   // buffer 0, channel 1
+#define HDMA_STAT1_0            (1 << 16)  // buffer 1, channel 0
+#define HDMA_STAT1_1            (1 << 17)  // buffer 1, channel 1
+#define REG_HDMA_HDCPR         (BASE_HDMA + 0x0124) // shared
+#define HDMA_HCURR_PTR_0        (1 << 0)   // channel 0
+#define HDMA_HCURR_PTR_1        (1 << 1)   // channel 1
+#define REG_HDMA_HDCTRR0       (BASE_HDMA + 0x0140) // channel 0
+#define REG_HDMA_HDCTRR1       (BASE_HDMA + 0x0160) // channel 1
+#define HDCTRR_STOP             (1 << 2)
+#define HDCTRR_MEM_BUS_WIDTH(n) ((n) << 4)
+#define HDCTRR_DEV_BUS_WIDTH(n) ((n) << 6)
+#define HDCTRR_BUS_WIDTH_8          0
+#define HDCTRR_BUS_WIDTH_16         1
+#define HDCTRR_BUS_WIDTH_32         2
+#define HDCTRR_BST_SIZE(n)      ((n) << 12)
+#define HDCTRR_BST_SIZE_4           2
+#define HDCTRR_BST_SIZE_8           3
+#define HDCTRR_BST_SIZE_16          4
+#define HDCTRR_BST_SIZE_32          5 // reserved
+#define HDCTRR_BST_SIZE_64          6 // reserved
+#define HDCTRR_BST_SIZE_128         7 // reserved
+#define HDCTRR_RX_SEL0(n)       ((n) << 30)
+#define HDCTRR_RX_SEL1(n)       ((n) << 31)
+#define REG_HDMA_HDC0R0        (BASE_HDMA + 0x0144) // channel 0
+#define REG_HDMA_HDC0R1        (BASE_HDMA + 0x0164) // channel 1
+#define HDCR_XFER_SIZE0(n)      ((n) << 16)
+#define HDCR_START0             (1 << 0)
+#define REG_HDMA_HDC1R0        (BASE_HDMA + 0x0148) // channel 0
+#define REG_HDMA_HDC1R1        (BASE_HDMA + 0x0168) // channel 1
+#define HDCR_XFER_SIZE1(n)      ((n) << 16)
+#define HDCR_START1             (1 << 0)
+#define REG_HDMA_HPRGA0R0      (BASE_HDMA + 0x014C) // channel 0
+#define REG_HDMA_HPRGA0R1      (BASE_HDMA + 0x016C) // channel 1
+#define REG_HDMA_HPRGA1R0      (BASE_HDMA + 0x0150) // channel 0
+#define REG_HDMA_HPRGA1R1      (BASE_HDMA + 0x0170) // channel 1
+#define REG_HDMA_HCCR0         (BASE_HDMA + 0x0154) // channel 0
+#define REG_HDMA_HCCR1         (BASE_HDMA + 0x0174) // channel 1
+#define HDMA_HCURR_CNT0         0x0000FFFF
+#define HDMA_HCURR_CNT1         0xFFFF0000
+#define REG_HDMA_HDCPR0        (BASE_HDMA + 0x0158) // channel 0
+#define REG_HDMA_HDCPR1        (BASE_HDMA + 0x0178) // channel 1
+#define REG_GDMA_GISAR2        (BASE_HDMA + 0x608)
+#define HDMA_DONE_0x        (1<<0)
+#define HDMA_DONE_1x        (1<<1)
+#define REG_GDMA_GIMRK4        (BASE_HDMA + 0x630)
+
+
+#define UT_USIM_BASE_ADDR_USIM1 BASE_ADDR_USIM1
+#define UT_USIM_BASE_ADDR_USIM2 BASE_ADDR_USIM2
+
+usim_reg_desc_t hdma_reg[] =
+{
+    //                          8   4   0   6   2   8   4   0            8   4   0   6   2   8   4   0
+    {REG_HDMA_HDCSR0,      {"axxxxaaaxxxxxxxxaxxxxaaaxxxxxxxx"},    {"0xxxx010xxxxxxxx0xxxx010xxxxxxxx"}},
+    {REG_HDMA_HDSR,        {"xxxxxxxxxxxxxxrrxxxxxxxxxxxxxxrr"},    {"xxxxxxxxxxxxxx00xxxxxxxxxxxxxx00"}},
+    {REG_HDMA_HDCPR,       {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxrr"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxxx00"}},
+
+    {REG_HDMA_HDCTRR0,     {"aaxxxxxxxxxxxxxxaaaaxxxxaaaaxfxx"},    {"00xxxxxxxxxxxxxx0100xxxx0010x0xx"}},
+    {REG_HDMA_HDCTRR1,     {"aaxxxxxxxxxxxxxxaaaaxxxxaaaaxfxx"},    {"00xxxxxxxxxxxxxx0100xxxx0010x0xx"}},
+    {REG_HDMA_HDC0R0,      {"aaaaaaaaaaaaaaaaxxxxxxxxxxxxxxff"},    {"0000000000000000xxxxxxxxxxxxxx00"}},
+    {REG_HDMA_HDC0R1,      {"aaaaaaaaaaaaaaaaxxxxxxxxxxxxxxff"},    {"0000000000000000xxxxxxxxxxxxxx00"}},
+    {REG_HDMA_HDC1R0,      {"aaaaaaaaaaaaaaaaxxxxxxxxxxxxxxff"},    {"0000000000000000xxxxxxxxxxxxxx00"}},
+    {REG_HDMA_HDC1R1,      {"aaaaaaaaaaaaaaaaxxxxxxxxxxxxxxff"},    {"0000000000000000xxxxxxxxxxxxxx00"}},
+
+    {REG_HDMA_HPRGA0R0,    {"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"},    {"00000000000000000000000000000000"}},
+    {REG_HDMA_HPRGA0R1,    {"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"},    {"00000000000000000000000000000000"}},
+    {REG_HDMA_HPRGA1R0,    {"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"},    {"00000000000000000000000000000000"}},
+    {REG_HDMA_HPRGA1R1,    {"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"},    {"00000000000000000000000000000000"}},
+    {REG_HDMA_HCCR0,       {"rrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrr"},    {"00000000000000000000000000000000"}},
+    {REG_HDMA_HCCR1,       {"rrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrr"},    {"00000000000000000000000000000000"}},
+    {REG_HDMA_HDCPR0,      {"rrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrr"},    {"00000000000000000000000000000000"}},
+    {REG_HDMA_HDCPR1,      {"rrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrr"},    {"00000000000000000000000000000000"}},
+
+    {REG_GDMA_GISAR2,      {"xxccxxccxxxxxxccxxxxxxccxxxxxxcc"},    {"xx00xx00xxxxxx00xxxxxx00xxxxxx00"}},
+    {REG_GDMA_GIMRK4,      {"xxaaxxaaxxxxxxaaxxxxxxaaxxxxxxaa"},    {"xx11xx11xxxxxx11xxxxxx11xxxxxx11"}}, //97 Change
+
+};
+
+// USIM IP
+usim_reg_desc_t usim_reg[] =
+{
+    //                                         8   4   0   6   2   8   4   0            8   4   0   6   2   8   4   0
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0000,    {"rrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrr"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"}}, //REG_USIM_CODA_VERSION
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0010,    {"xxxxxxxxxxxxxxxxxxxxxxxxxxpaapaa"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxx000000"}}, //REG_USIM_CTRL
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0014,    {"xxxxxxxxxxxxxxxxxxxxaaaaaaaaaaaa"},	   {"xxxxxxxxxxxxxxxxxxxx000000000000"}}, //REG_USIM_CONF
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0018,    {"xxxxxxxxxxxxxxxxxxxxxuxxxxxxxxxu"},    {"xxxxxxxxxxxxxxxxxxxxx0xxxxxxxxx0"}}, //REG_USIM_CONFSTA
+    {UT_USIM_BASE_ADDR_USIM1 + 0x001C,    {"xxxxxxxxxxxxxxxxxxaaaaaaaaaaaaaa"},    {"xxxxxxxxxxxxxxxxxx00010111010000"}}, //REG_USIM_BRR
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0020,    {"xxxxxxxxxxxxxxxxxxxxaaaaaaaaaaaa"},    {"xxxxxxxxxxxxxxxxxxxx000000000000"}}, //REG_USIM_IRQEN
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0024,    {"xxxxxxxxxxxxxxxxxxxxccccccccccuu"},    {"xxxxxxxxxxxxxxxxxxxx000000000000"}}, //REG_USIM_STS
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0030,    {"xxxxxxxxxxxxxxxxxxxxaaaaxxxxaaaa"},    {"xxxxxxxxxxxxxxxxxxxx0011xxxx0011"}}, //REG_USIM_RETRY
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0034,    {"xxxxxxxxxxxxxxxxxxxxaaaaxxxxaaaa"},    {"xxxxxxxxxxxxxxxxxxxx0000xxxx0000"}}, //REG_USIM_TIDE
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0040,    {"xxxxxxxxxxxxxxxxxxxxxxxxffffffff"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"}}, //REG_USIM_DATA: special, FIFO type
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0044,    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxuuuuu"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxxx00000"}}, //REG_USIM_COUNT
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0054,    {"xxxxxxxxxxxxxxxxxxxxxxxxxxaaaaaa"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxx001111"}}, //REG_USIM_DTIME
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0058,    {"xxxxxxxxxxaaaaaaaaaaaaaaaaaaaaaa"},    {"xxxxxxxxxx0000000000001001100000"}}, //REG_USIM_WTIME
+    {UT_USIM_BASE_ADDR_USIM1 + 0x005C,    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxaaaa"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxx1010"}}, //REG_USIM_GTIME
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0060,    {"xxxxxxxxxxxxxxxxxxxxxxxxxxaaaaaa"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxx001111"}}, //REG_USIM_ETIME
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0064,    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxaaaa"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxx0001"}}, //REG_USIM_EXT_TIME
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0068,    {"xxxxxxxxxxxxxxxxxxxxxxxxaaaaaaaa"},    {"xxxxxxxxxxxxxxxxxxxxxxxx00000010"}}, //REG_USIM_CGTIME
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0070,    {"xxxxxxxxxxxxxxxxpxxxxxxaaaaaaaaa"},    {"xxxxxxxxxxxxxxxx0xxxxxx000000000"}}, //REG_USIM_COMDCTRL
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0074,    {"xxxxxxxxxxxxxxxxxxxxxxxxaaaaaaaa"},    {"xxxxxxxxxxxxxxxxxxxxxxxx00000000"}}, //REG_USIM_COMDLEN
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0078,    {"xxxxxxxxxxxxxxxxxxxxxxxuuuuuuuuu"},    {"xxxxxxxxxxxxxxxxxxxxxxx000000000"}}, //REG_USIM_LEFTLEN
+    {UT_USIM_BASE_ADDR_USIM1 + 0x007C,    {"xxxxxxxxxxxxxxxxxxxxxxxxuuuuuuuu"},    {"xxxxxxxxxxxxxxxxxxxxxxxx00000000"}}, //REG_USIM_LATCH1
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0080,    {"xxxxxxxxxxxxxxxxxxxxxxxxuuuuuuuu"},    {"xxxxxxxxxxxxxxxxxxxxxxxx00000000"}}, //REG_USIM_LATCH2
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0090,    {"xxxxxxxxxxxxxxxxxxxxxxxuuxxxxxxu"},    {"xxxxxxxxxxxxxxxxxxxxxxx00xxxxxx1"}}, //REG_USIM_ATRSTA
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0094,    {"xxxxxxxxxxxxxxxxxxxxxxxxxuuuuuuu"},	   {"xxxxxxxxxxxxxxxxxxxxxxxxx0000001"}}, //REG_USIM_T0PTLSTA
+    {UT_USIM_BASE_ADDR_USIM1 + 0x0098,    {"xxxxuuuuxxxuuuuuxxxuuuuuxxxuuuuu"},    {"xxxx0000xxx00000xxx00000xxx00000"}}, //REG_USIM_DBG
+    {UT_USIM_BASE_ADDR_USIM1 + 0x009C,    {"xxxxxxxxxxxxxxxxxxxxuuuuffffffff"},    {"xxxxxxxxxxxxxxxxxxxx0000xxxxxxxx"}}, //REG_USIM_DBGDATA: special, read will cause side effect
+    {UT_USIM_BASE_ADDR_USIM1 + 0x00A0,    {"xxxxxxxxxxxxxxxxxxxxxxxxffffffff"},	   {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"}}, //REG_USIM_DMADATA: special, FIFO type
+    {UT_USIM_BASE_ADDR_USIM1 + 0x00A8,    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxa"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx0"}}, //REG_USIM_RPTR_LOCK_EN
+    {UT_USIM_BASE_ADDR_USIM1 + 0x00B0,    {"xxxxxxxxxxxxaaaaaaaaaaaaaaaaaaaa"},    {"xxxxxxxxxxxx00000000001010111110"}}, //REG_USIM_ATIME1
+    {UT_USIM_BASE_ADDR_USIM1 + 0x00B4,    {"xxxxxxxxxxxxaaaaaaaaaaaaaaaaaaaa"},    {"xxxxxxxxxxxx00000000001010111110"}}, //REG_USIM_ATIME2
+    {UT_USIM_BASE_ADDR_USIM1 + 0x00B8,    {"xxxxxxxxxxxxaaaaaaaaaaaaaaaaaaaa"},    {"xxxxxxxxxxxx00000000001010111110"}}, //REG_USIM_ATIME3
+    {UT_USIM_BASE_ADDR_USIM1 + 0x00BC,    {"xxxxxxxxxxxxaaaaaaaaaaaaaaaaaaaa"},    {"xxxxxxxxxxxx00000000001010111110"}}, //REG_USIM_ATIME4
+    {UT_USIM_BASE_ADDR_USIM1 + 0x00C0,    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxa"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx0"}}, //REG_USIM_SIMOE_MODE
+    {UT_USIM_BASE_ADDR_USIM1 + 0x00D0,    {"uuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuu"},    {"00000000000000000000000000000000"}}, //REG_USIM_DEBUG1
+    {UT_USIM_BASE_ADDR_USIM1 + 0x00D4,    {"uuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuu"},    {"00000000000000000000000000000000"}}, //REG_USIM_DEBUG2
+
+};
+
+usim_reg_desc_t usim_reg2[] =
+{
+    //                                         8   4   0   6   2   8   4   0            8   4   0   6   2   8   4   0
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0000,    {"rrrrrrrrrrrrrrrrrrrrrrrrrrrrrrrr"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"}}, //REG_USIM_CODA_VERSION
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0010,    {"xxxxxxxxxxxxxxxxxxxxxxxxxxpaapaa"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxx000000"}}, //REG_USIM_CTRL
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0014,    {"xxxxxxxxxxxxxxxxxxxxaaaaaaaaaaaa"},	   {"xxxxxxxxxxxxxxxxxxxx000000000000"}}, //REG_USIM_CONF
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0018,    {"xxxxxxxxxxxxxxxxxxxxxuxxxxxxxxxu"},    {"xxxxxxxxxxxxxxxxxxxxx0xxxxxxxxx0"}}, //REG_USIM_CONFSTA
+    {UT_USIM_BASE_ADDR_USIM2 + 0x001C,    {"xxxxxxxxxxxxxxxxxxaaaaaaaaaaaaaa"},    {"xxxxxxxxxxxxxxxxxx00010111010000"}}, //REG_USIM_BRR
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0020,    {"xxxxxxxxxxxxxxxxxxxxaaaaaaaaaaaa"},    {"xxxxxxxxxxxxxxxxxxxx000000000000"}}, //REG_USIM_IRQEN
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0024,    {"xxxxxxxxxxxxxxxxxxxxccccccccccuu"},    {"xxxxxxxxxxxxxxxxxxxx000000000000"}}, //REG_USIM_STS
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0030,    {"xxxxxxxxxxxxxxxxxxxxaaaaxxxxaaaa"},    {"xxxxxxxxxxxxxxxxxxxx0011xxxx0011"}}, //REG_USIM_RETRY
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0034,    {"xxxxxxxxxxxxxxxxxxxxaaaaxxxxaaaa"},    {"xxxxxxxxxxxxxxxxxxxx0000xxxx0000"}}, //REG_USIM_TIDE
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0040,    {"xxxxxxxxxxxxxxxxxxxxxxxxffffffff"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"}}, //REG_USIM_DATA: special, FIFO type
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0044,    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxuuuuu"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxxx00000"}}, //REG_USIM_COUNT
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0054,    {"xxxxxxxxxxxxxxxxxxxxxxxxxxaaaaaa"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxx001111"}}, //REG_USIM_DTIME
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0058,    {"xxxxxxxxxxaaaaaaaaaaaaaaaaaaaaaa"},    {"xxxxxxxxxx0000000000001001100000"}}, //REG_USIM_WTIME
+    {UT_USIM_BASE_ADDR_USIM2 + 0x005C,    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxaaaa"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxx1010"}}, //REG_USIM_GTIME
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0060,    {"xxxxxxxxxxxxxxxxxxxxxxxxxxaaaaaa"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxx001111"}}, //REG_USIM_ETIME
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0064,    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxaaaa"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxx0001"}}, //REG_USIM_EXT_TIME
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0068,    {"xxxxxxxxxxxxxxxxxxxxxxxxaaaaaaaa"},    {"xxxxxxxxxxxxxxxxxxxxxxxx00000010"}}, //REG_USIM_CGTIME
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0070,    {"xxxxxxxxxxxxxxxxpxxxxxxaaaaaaaaa"},    {"xxxxxxxxxxxxxxxx0xxxxxx000000000"}}, //REG_USIM_COMDCTRL
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0074,    {"xxxxxxxxxxxxxxxxxxxxxxxxaaaaaaaa"},    {"xxxxxxxxxxxxxxxxxxxxxxxx00000000"}}, //REG_USIM_COMDLEN
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0078,    {"xxxxxxxxxxxxxxxxxxxxxxxuuuuuuuuu"},    {"xxxxxxxxxxxxxxxxxxxxxxx000000000"}}, //REG_USIM_LEFTLEN
+    {UT_USIM_BASE_ADDR_USIM2 + 0x007C,    {"xxxxxxxxxxxxxxxxxxxxxxxxuuuuuuuu"},    {"xxxxxxxxxxxxxxxxxxxxxxxx00000000"}}, //REG_USIM_LATCH1
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0080,    {"xxxxxxxxxxxxxxxxxxxxxxxxuuuuuuuu"},    {"xxxxxxxxxxxxxxxxxxxxxxxx00000000"}}, //REG_USIM_LATCH2
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0090,    {"xxxxxxxxxxxxxxxxxxxxxxxuuxxxxxxu"},    {"xxxxxxxxxxxxxxxxxxxxxxx00xxxxxx1"}}, //REG_USIM_ATRSTA
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0094,    {"xxxxxxxxxxxxxxxxxxxxxxxxxuuuuuuu"},	   {"xxxxxxxxxxxxxxxxxxxxxxxxx0000001"}}, //REG_USIM_T0PTLSTA
+    {UT_USIM_BASE_ADDR_USIM2 + 0x0098,    {"xxxxuuuuxxxuuuuuxxxuuuuuxxxuuuuu"},    {"xxxx0000xxx00000xxx00000xxx00000"}}, //REG_USIM_DBG
+    {UT_USIM_BASE_ADDR_USIM2 + 0x009C,    {"xxxxxxxxxxxxxxxxxxxxuuuuffffffff"},    {"xxxxxxxxxxxxxxxxxxxx0000xxxxxxxx"}}, //REG_USIM_DBGDATA: special, read will cause side effect
+    {UT_USIM_BASE_ADDR_USIM2 + 0x00A0,    {"xxxxxxxxxxxxxxxxxxxxxxxxffffffff"},	   {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"}}, //REG_USIM_DMADATA: special, FIFO type
+    {UT_USIM_BASE_ADDR_USIM2 + 0x00A8,    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxa"},    {"xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx0"}}, //REG_USIM_RPTR_LOCK_EN
+    {UT_USIM_BASE_ADDR_USIM2 + 0x00B0,    {"xxxxxxxxxxxxaaaaaaaaaaaaaaaaaaaa"},    {"xxxxxxxxxxxx00000000001010111110"}}, //REG_USIM_ATIME1
+    {UT_USIM_BASE_ADDR_USIM2 + 0x00B4,    {"xxxxxxxxxxxxaaaaaaaaaaaaaaaaaaaa"},    {"xxxxxxxxxxxx00000000001010111110"}}, //REG_USIM_ATIME2
+    {UT_USIM_BASE_ADDR_USIM2 + 0x00B8,    {"xxxxxxxxxxxxaaaaaaaaaaaaaaaaaaaa"},    {"xxxxxxxxxxxx00000000001010111110"}}, //REG_USIM_ATIME3
+    {UT_USIM_BASE_ADDR_USIM2 + 0x00BC,    {"xxxxxxxxxxxxaaaaaaaaaaaaaaaaaaaa"},    {"xxxxxxxxxxxx00000000001010111110"}}, //REG_USIM_ATIME4
+    {UT_USIM_BASE_ADDR_USIM2 + 0x00D0,    {"uuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuu"},    {"00000000000000000000000000000000"}}, //REG_USIM_DEBUG1
+    {UT_USIM_BASE_ADDR_USIM2 + 0x00D4,    {"uuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuu"},    {"00000000000000000000000000000000"}}, //REG_USIM_DEBUG2
+
+};
+#define GET_FIELD(val, bit_offset, bit_len) \
+    (((val) >> (bit_offset)) & (~(0xFFFFFFFF << (bit_len))))
+#define SET_FIELD(val, bit_offset, bit_len, field_val) \
+    ((val) = ((val) & ~((1 << ((bit_offset) + (bit_len))) - (1 << ((bit_offset))))) | ( ((field_val) << (bit_offset)) & ((1 << ((bit_offset) + (bit_len))) - (1 << ((bit_offset))))))
+
+
+kal_bool USIM_SLT_reg_read_write_test()
+{
+
+    kal_bool ut_usim_breset_status = KAL_TRUE;
+    kal_uint32 reg_index, reg_group_index, bit_index;
+
+    kal_uint32 reg_addr, expected_val, i;
+    kal_char *reset_val, *attr;
+    kal_uint32 reg_num;
+    kal_char bypass_items[] = { 0x40, 0x9C, 0xA0};
+    
+    for (reg_group_index = 0; reg_group_index < REG_GROUP_NUM; reg_group_index++)
+    {
+        switch (reg_group_index)
+        {
+            case REG_GROUP_HDMA:
+                slt_dbg_print( " ---- %s ----\r\n", "HDMA");
+                reg_num = sizeof(hdma_reg) / sizeof(usim_reg_desc_t);
+                break;
+            case REG_GROUP_USIM:
+                slt_dbg_print( " ---- %s ----\r\n", "USIM0");
+                reg_num = sizeof(usim_reg) / sizeof(usim_reg_desc_t);
+                break;
+            case REG_GROUP_USIM2:
+                slt_dbg_print( " ---- %s ----\r\n", "USIM1");
+                reg_num = sizeof(usim_reg2) / sizeof(usim_reg_desc_t);
+                break;
+            default:
+                ASSERT(0);
+        }
+
+        /*
+         * Check Default Values
+         */         
+        for (reg_index = 0; reg_index < reg_num; reg_index++)
+        {
+            switch (reg_group_index)
+            {
+                case REG_GROUP_HDMA:
+                    reg_addr = hdma_reg[reg_index].addr;
+                    reset_val = hdma_reg[reg_index].reset_val;
+                    break;
+                case REG_GROUP_USIM:
+                    reg_addr = usim_reg[reg_index].addr;
+                    reset_val = usim_reg[reg_index].reset_val;
+                    break;
+                case REG_GROUP_USIM2:
+                    reg_addr = usim_reg2[reg_index].addr;
+                    reset_val = usim_reg2[reg_index].reset_val;
+                    break;
+                default:
+                    ASSERT(0);
+            }
+
+            if (reg_group_index == REG_GROUP_USIM || reg_group_index == REG_GROUP_USIM2)
+            {
+                for (i = 0; i < (sizeof(bypass_items) / sizeof(kal_char)); i++)
+                    if ((reg_addr & 0xFF) ==  bypass_items[i])
+                        break;
+                if (i < (sizeof(bypass_items) / sizeof(kal_char)))
+                    continue;
+            }
+
+            expected_val = DRV_Reg32(reg_addr);
+            //slt_dbg_print("Check default Value, addr:%x, expected value:%x\r\n",reg_addr,expected_val);
+
+            for (bit_index = 0; bit_index < 32; bit_index++)
+            {
+                kal_uint32 expected_bit_type = reset_val[bit_index];
+                kal_uint32 expected_bit_val = GET_FIELD(expected_val, 32 - 1 - bit_index, 1);
+
+                switch (expected_bit_type)
+                {
+                    case '0':
+                        if (expected_bit_val != 0)
+                        {
+                            slt_dbg_print("[ERR] FILE: %s, FUNC: %s, LINE: %d\r\n", __FILE__, __FUNCTION__, __LINE__);
+                            slt_dbg_print("Reg Address: 0x%08X\r\n", reg_addr);
+                            slt_dbg_print("Bit[%d] is not '0'\r\n", 32 - 1 - bit_index);
+                            slt_dbg_print("Reg Val: 0x%08X\r\n", expected_val);
+
+                            ut_usim_breset_status = KAL_FALSE;
+                        }
+                        break;
+                    case '1':
+                        if (expected_bit_val != 1)
+                        {
+                            slt_dbg_print("[ERR] FILE: %s, FUNC: %s, LINE: %d\r\n", __FILE__, __FUNCTION__, __LINE__);
+                            slt_dbg_print("Reg Address: 0x%08X\r\n", reg_addr);
+                            slt_dbg_print("Bit[%d] is not '1'\r\n", 32 - 1 - bit_index);
+
+                            ut_usim_breset_status = KAL_FALSE;
+                        }
+                        break;
+                    case 'x':
+                        break;
+                    default:
+                        break;
+                }
+            }
+        }
+
+        /*
+         * Check Types That Cause No Side Effects
+         */
+        for (reg_index = 0; reg_index < reg_num; reg_index++)
+        {
+            switch (reg_group_index)
+            {
+                case REG_GROUP_HDMA:
+                    reg_addr = hdma_reg[reg_index].addr;
+                    attr = hdma_reg[reg_index].attr;
+                    break;
+                case REG_GROUP_USIM:
+                    reg_addr = usim_reg[reg_index].addr;
+                    attr = usim_reg[reg_index].attr;
+                    break;
+                case REG_GROUP_USIM2:
+                    reg_addr = usim_reg2[reg_index].addr;
+                    attr = usim_reg2[reg_index].attr;
+                    break;
+                default:
+                    ASSERT(0);
+            }
+
+            if (reg_group_index == REG_GROUP_USIM || reg_group_index == REG_GROUP_USIM2)
+            {
+                for (i = 0; i < (sizeof(bypass_items) / sizeof(kal_char)); i++)
+                    if ((reg_addr & 0xFF) ==  bypass_items[i])
+                        break;
+                if (i < (sizeof(bypass_items) / sizeof(kal_char)))
+                    continue;
+            }
+            //slt_dbg_print("Check default Attr, addr:%x,0x98:%x_%x\r\n",reg_addr,DRV_Reg32(0xB0040098)>>16,DRV_Reg32(0xB0040098)&0xFFFF);
+            for (bit_index = 0; bit_index < 32; bit_index++)
+            {
+                kal_uint32 expected_bit_attr = attr[bit_index];
+                kal_uint32 expected_bit_val = GET_FIELD(DRV_Reg32(reg_addr), 32 - 1 - bit_index, 1);
+
+                switch (expected_bit_attr)
+                {
+                    /*
+                     * Check if '0' & '1'' Write-able
+                     */
+                    case 'a':
+                        // Set Bit to '0' and Check
+                        DRV_WriteReg32(reg_addr, SET_FIELD(DRV_Reg32(reg_addr), 32 - 1 - bit_index, 1, 0));
+
+                        if (GET_FIELD(DRV_Reg32(reg_addr), 32 - 1 - bit_index, 1) != 0)
+                        {
+                            slt_dbg_print("[ERR] FILE: %s, FUNC: %s, LINE: %d\r\n", __FILE__, __FUNCTION__, __LINE__);
+                            slt_dbg_print("Reg Address: 0x%08X\r\n", reg_addr);
+                            slt_dbg_print("Bit[%d] is not '0' Write-able\r\n", 32 - 1 - bit_index);
+
+                            ut_usim_breset_status = KAL_FALSE;
+                        }
+
+                        // Set Bit to '1' and Check
+                        DRV_WriteReg32(reg_addr, SET_FIELD(DRV_Reg32(reg_addr), 32 - 1 - bit_index, 1, 1));
+
+                        if (GET_FIELD(DRV_Reg32(reg_addr), 32 - 1 - bit_index, 1) != 1)
+                        {
+                            slt_dbg_print("[ERR] FILE: %s, FUNC: %s, LINE: %d\r\n", __FILE__, __FUNCTION__, __LINE__);
+                            slt_dbg_print("Reg Address: 0x%08X\r\n", reg_addr);
+                            slt_dbg_print("Bit[%d] is not '1' Write-able\r\n", 32 - 1 - bit_index);
+
+                            ut_usim_breset_status = KAL_FALSE;
+                        }
+                   
+                        // Set Bit to Default Value
+                        DRV_WriteReg32(reg_addr, SET_FIELD(DRV_Reg32(reg_addr), 32 - 1 - bit_index, 1, expected_bit_val));
+                        break;
+                    case 'k':
+                    case 'p':
+                    case 'c':
+                        // Set 1 and Check if Bit is 0
+                        DRV_WriteReg32(reg_addr, SET_FIELD(DRV_Reg32(reg_addr), 32 - 1 - bit_index, 1, 1));
+
+                        if (GET_FIELD(DRV_Reg32(reg_addr), 32 - 1 - bit_index, 1) != 0)
+                        {
+                            slt_dbg_print("[ERR] FILE: %s, FUNC: %s, LINE: %d\r\n", __FILE__, __FUNCTION__, __LINE__);
+                            slt_dbg_print("Reg Address: 0x%08X\r\n", reg_addr);
+                            slt_dbg_print("Bit[%d] is Write-one-clear, but currently read to be 1\r\n", 32 - 1 - bit_index);
+
+                            ut_usim_breset_status = KAL_FALSE;
+                        }
+                        break;
+                    case 'r':
+                        // Set Bit to Inverse of Default Value and Check if Bit Changed
+                        DRV_WriteReg32(reg_addr, SET_FIELD(DRV_Reg32(reg_addr), 32 - 1 - bit_index, 1, ~expected_bit_val));
+
+                        if (GET_FIELD(DRV_Reg32(reg_addr), 32 - 1 - bit_index, 1) != expected_bit_val)
+                        {
+                            slt_dbg_print("[ERR] FILE: %s, FUNC: %s, LINE: %d\r\n", __FILE__, __FUNCTION__, __LINE__);
+                            slt_dbg_print("Reg Address: 0x%08X\r\n", reg_addr);
+                            slt_dbg_print("Bit[%d] is write-able, but expected to be read-only\r\n", 32 - 1 - bit_index);
+
+                            // Set Bit to Default Value For Future Tests
+                            DRV_WriteReg32(reg_addr, SET_FIELD(DRV_Reg32(reg_addr), 32 - 1 - bit_index, 1, expected_bit_val));
+
+                            ut_usim_breset_status = KAL_FALSE;
+                        }
+                        break;
+                    /*
+                     * Bypass Don't Care Bit
+                     */
+                    case 'u': /* May Update by Design */
+                    case 'f': /* Special Type */
+                    case 'x':
+                        break;
+                    default:
+                        break;
+                }
+            }
+        }       
+
+        /*
+         * Check Types That Cause Side Effects
+         */
+        for (reg_index = 0; reg_index < reg_num; reg_index++)
+        {
+            switch (reg_group_index)
+            {
+                case REG_GROUP_HDMA:
+                    reg_addr = hdma_reg[reg_index].addr;
+                    attr = hdma_reg[reg_index].attr;
+                    break;
+                case REG_GROUP_USIM:
+                    reg_addr = usim_reg[reg_index].addr;
+                    attr = usim_reg[reg_index].attr;
+                    break;
+                case REG_GROUP_USIM2:
+                    reg_addr = usim_reg2[reg_index].addr;
+                    attr = usim_reg2[reg_index].attr;
+                    break;
+                default:
+                    ASSERT(0);
+            }
+
+            if (reg_group_index == REG_GROUP_USIM || reg_group_index == REG_GROUP_USIM2)
+            {
+                for (i = 0; i < (sizeof(bypass_items) / sizeof(kal_char)); i++)
+                    if ((reg_addr & 0xFF) ==  bypass_items[i])
+                        break;
+                if (i < (sizeof(bypass_items) / sizeof(kal_char)))
+                    continue;
+            }
+
+            for (bit_index = 0; bit_index < 32; bit_index++)
+            {
+                kal_uint32 expected_bit_attr = attr[bit_index];
+
+                switch (expected_bit_attr)
+                {
+                    case 's':
+                        // Set Bit to 1 and Check if Bit Changed
+                        DRV_WriteReg32(reg_addr, SET_FIELD(DRV_Reg32(reg_addr), 32 - 1 - bit_index, 1, 1));
+
+                        if (GET_FIELD(DRV_Reg32(reg_addr), 32 - 1 - bit_index, 1) == 1)
+                        {
+                            slt_dbg_print("[ERR] FILE: %s, FUNC: %s, LINE: %d\r\n", __FILE__, __FUNCTION__, __LINE__);
+                            slt_dbg_print("Reg Address: 0x%08X\r\n", reg_addr);
+                            slt_dbg_print("Bit[%d] is write-able, but expected to be read-only\r\n", 32 - 1 - bit_index);
+
+                            ut_usim_breset_status = KAL_FALSE;
+                        }
+                        break;
+                    /*
+                     * Bypass All Others
+                     */
+                    default:
+                        break;
+                }
+            }
+        }
+
+    }
+    //Reset Interface
+    for (i=0;i<2;i++)
+    {
+        if (i==0)
+            reg_addr = UT_USIM_BASE_ADDR_USIM1;
+        else
+            reg_addr = UT_USIM_BASE_ADDR_USIM2;        
+
+        DRV_WriteReg32(reg_addr + SIM_CTRL_MTK,SIM_CTRL_SIMON|SIM_CTRL_IFCLR);
+        while ((DRV_Reg32(reg_addr +SIM_ATRSTA_MTK) & (SIM_ATRSTA_IR | SIM_ATRSTA_AL)) == 0);        
+        while (DRV_Reg32(reg_addr+SIM_CONFSTA_MTK) & SIM_CONFSTA_IFCLR_ON);
+        DRV_WriteReg32(reg_addr + SIM_CTRL_MTK,0x0);  //SIM
+    }
+    return ut_usim_breset_status;
+}
+#endif