import PULS_20160108
[GitHub/mt8127/android_kernel_alcatel_ttab.git] / drivers / misc / mediatek / power / mt8127 / charging_hw_bq24297.c
diff --git a/drivers/misc/mediatek/power/mt8127/charging_hw_bq24297.c b/drivers/misc/mediatek/power/mt8127/charging_hw_bq24297.c
new file mode 100644 (file)
index 0000000..d0062bb
--- /dev/null
@@ -0,0 +1,926 @@
+/*****************************************************************************
+ *
+ * Filename:
+ * ---------
+ *    charging_pmic.c
+ *
+ * Project:
+ * --------
+ *   ALPS_Software
+ *
+ * Description:
+ * ------------
+ *   This file implements the interface between BMT and ADC scheduler.
+ *
+ * Author:
+ * -------
+ *  Oscar Liu
+ *
+ *============================================================================
+  * $Revision:   1.0  $
+ * $Modtime:   11 Aug 2005 10:28:16  $
+ * $Log:   //mtkvs01/vmdata/Maui_sw/archives/mcu/hal/peripheral/inc/bmt_chr_setting.h-arc  $
+ *             HISTORY
+ * Below this line, this part is controlled by PVCS VM. DO NOT MODIFY!!
+ *------------------------------------------------------------------------------
+ *------------------------------------------------------------------------------
+ * Upper this line, this part is controlled by PVCS VM. DO NOT MODIFY!!
+ *============================================================================
+ ****************************************************************************/
+#include <mach/charging.h>
+#include "bq24297.h"
+#include <mach/upmu_common.h>
+#include <mach/mt_gpio.h>
+#include <cust_gpio_usage.h>
+#include <mach/upmu_hw.h>
+#include <linux/xlog.h>
+#include <linux/delay.h>
+#include <mach/mt_sleep.h>
+#include <mach/mt_boot.h>
+#include <mach/system.h>
+#include <cust_charging.h>
+
+#if 1
+#include <mach/mt_clkmgr.h>
+#include <mach/mt_pm_ldo.h>
+#endif
+ // ============================================================ //
+ //define
+ // ============================================================ //
+#define STATUS_OK      0
+#define STATUS_UNSUPPORTED     -1
+#define GETARRAYNUM(array) (sizeof(array)/sizeof(array[0]))
+
+
+ // ============================================================ //
+ //global variable
+ // ============================================================ //
+#ifdef GPIO_SWCHARGER_EN_PIN 
+#define GPIO_CHR_CE_PIN GPIO_SWCHARGER_EN_PIN
+#else
+#define  GPIO_CHR_CE_PIN (19 | 0x80000000)
+#endif
+int gpio_off_dir  = GPIO_DIR_OUT;
+int gpio_off_out  = GPIO_OUT_ONE;
+int gpio_on_dir   = GPIO_DIR_OUT;
+int gpio_on_out   = GPIO_OUT_ZERO;
+
+kal_bool charging_type_det_done = KAL_TRUE;
+
+const kal_uint32 VBAT_CV_VTH[]=
+{
+       3504000,    3520000,    3536000,    3552000,
+       3568000,    3584000,    3600000,    3616000,
+       3632000,    3648000,    3664000,    3680000,
+       3696000,    3712000,    3728000,    3744000,
+       3760000,    3776000,    3792000,    3808000,
+       3824000,    3840000,    3856000,    3872000,
+       3888000,    3904000,    3920000,    3936000,
+       3952000,    3968000,    3984000,    4000000,
+       4016000,    4032000,    4048000,    4064000,
+       4080000,    4096000,    4112000,    4128000,
+       4144000,    4160000,    4176000,    4192000,    
+       4208000,    4224000,    4240000,    4256000             
+};
+
+const kal_uint32 CS_VTH[]=
+{
+       51200,  57600,  64000,  70400,
+       76800,  83200,  89600,  96000,
+       102400, 108800, 115200, 121600,
+       128000, 134400, 140800, 147200,
+       153600, 160000, 166400, 172800,
+       179200, 185600, 192000, 198400,
+       204800, 211200, 217600, 224000
+}; 
+
+ const kal_uint32 INPUT_CS_VTH[]=
+ {
+        CHARGE_CURRENT_100_00_MA,  CHARGE_CURRENT_150_00_MA,   CHARGE_CURRENT_500_00_MA,  CHARGE_CURRENT_900_00_MA,
+        CHARGE_CURRENT_1200_00_MA, CHARGE_CURRENT_1500_00_MA,  CHARGE_CURRENT_2000_00_MA,  CHARGE_CURRENT_MAX
+ }; 
+
+ const kal_uint32 VCDT_HV_VTH[]=
+ {
+         BATTERY_VOLT_04_200000_V, BATTERY_VOLT_04_250000_V,     BATTERY_VOLT_04_300000_V,   BATTERY_VOLT_04_350000_V,
+         BATTERY_VOLT_04_400000_V, BATTERY_VOLT_04_450000_V,     BATTERY_VOLT_04_500000_V,   BATTERY_VOLT_04_550000_V,
+         BATTERY_VOLT_04_600000_V, BATTERY_VOLT_06_000000_V,     BATTERY_VOLT_06_500000_V,   BATTERY_VOLT_07_000000_V,
+         BATTERY_VOLT_07_500000_V, BATTERY_VOLT_08_500000_V,     BATTERY_VOLT_09_500000_V,   BATTERY_VOLT_10_500000_V            
+ };
+
+ // ============================================================ //
+ // function prototype
+ // ============================================================ //
+ // ============================================================ //
+ //extern variable
+ // ============================================================ //
+ // ============================================================ //
+ //extern function
+ // ============================================================ //
+ extern kal_uint32 upmu_get_reg_value(kal_uint32 reg);
+ extern bool mt_usb_is_device(void);
+ extern void Charger_Detect_Init(void);
+ extern void Charger_Detect_Release(void);
+ extern void mt_power_off(void);
+  
+ // ============================================================ //
+ kal_uint32 charging_value_to_parameter(const kal_uint32 *parameter, const kal_uint32 array_size, const kal_uint32 val)
+{
+       if (val < array_size)
+       {
+               return parameter[val];
+       }
+       else
+       {
+               battery_xlog_printk(BAT_LOG_CRTI, "Can't find the parameter \r\n");     
+               return parameter[0];
+       }
+}
+
+ kal_uint32 charging_parameter_to_value(const kal_uint32 *parameter, const kal_uint32 array_size, const kal_uint32 val)
+{
+       kal_uint32 i;
+
+    battery_xlog_printk(BAT_LOG_CRTI, "array_size = %d \r\n", array_size);
+    
+       for(i=0;i<array_size;i++)
+       {
+               if (val == *(parameter + i))
+               {
+                               return i;
+               }
+       }
+
+    battery_xlog_printk(BAT_LOG_CRTI, "NO register value match. val=%d\r\n", val);
+       //TODO: ASSERT(0);      // not find the value
+       return 0;
+}
+
+
+ static kal_uint32 bmt_find_closest_level(const kal_uint32 *pList,kal_uint32 number,kal_uint32 level)
+ {
+        kal_uint32 i;
+        kal_uint32 max_value_in_last_element;
+        if(pList[0] < pList[1])
+                max_value_in_last_element = KAL_TRUE;
+        else
+                max_value_in_last_element = KAL_FALSE;
+        if(max_value_in_last_element == KAL_TRUE)
+        {
+                for(i = (number-1); i != 0; i--)        //max value in the last element
+                {
+                        if(pList[i] <= level)
+                        {
+                                return pList[i];
+                        }        
+                }
+
+                battery_xlog_printk(BAT_LOG_CRTI, "Can't find closest level, small value first \r\n");
+                return pList[0];
+                //return CHARGE_CURRENT_0_00_MA;
+        }
+        else
+        {
+                for(i = 0; i< number; i++)  // max value in the first element
+                {
+                        if(pList[i] <= level)
+                        {
+                                return pList[i];
+                        }        
+                }
+
+                battery_xlog_printk(BAT_LOG_CRTI, "Can't find closest level, large value first \r\n");          
+                return pList[number -1];
+                //return CHARGE_CURRENT_0_00_MA;
+        }
+ }
+
+#if 0
+static void hw_bc11_dump_register(void)
+{
+       kal_uint32 reg_val = 0;
+       kal_uint32 reg_num = CHR_CON18;
+       kal_uint32 i = 0;
+
+       for(i=reg_num ; i<=CHR_CON19 ; i+=2)
+       {
+               reg_val = upmu_get_reg_value(i);
+               battery_xlog_printk(BAT_LOG_FULL, "Chr Reg[0x%x]=0x%x \r\n", i, reg_val);
+       }
+}
+
+
+ static void hw_bc11_init(void)
+ {
+        Charger_Detect_Init();
+                
+        //RG_BC11_BIAS_EN=1    
+        upmu_set_rg_bc11_bias_en(0x1);
+        //RG_BC11_VSRC_EN[1:0]=00
+        upmu_set_rg_bc11_vsrc_en(0x0);
+        //RG_BC11_VREF_VTH = [1:0]=00
+        upmu_set_rg_bc11_vref_vth(0x0);
+        //RG_BC11_CMP_EN[1.0] = 00
+        upmu_set_rg_bc11_cmp_en(0x0);
+        //RG_BC11_IPU_EN[1.0] = 00
+        upmu_set_rg_bc11_ipu_en(0x0);
+        //RG_BC11_IPD_EN[1.0] = 00
+        upmu_set_rg_bc11_ipd_en(0x0);
+        //BC11_RST=1
+        upmu_set_rg_bc11_rst(0x1);
+        //BC11_BB_CTRL=1
+        upmu_set_rg_bc11_bb_ctrl(0x1);
+        //msleep(10);
+        mdelay(50);
+
+        if(Enable_BATDRV_LOG == BAT_LOG_FULL)
+        {
+               battery_xlog_printk(BAT_LOG_FULL, "hw_bc11_init() \r\n");
+               hw_bc11_dump_register();
+        }      
+        
+ }
+ static U32 hw_bc11_DCD(void)
+ {
+        U32 wChargerAvail = 0;
+        //RG_BC11_IPU_EN[1.0] = 10
+        upmu_set_rg_bc11_ipu_en(0x2);
+        //RG_BC11_IPD_EN[1.0] = 01
+        upmu_set_rg_bc11_ipd_en(0x1);
+        //RG_BC11_VREF_VTH = [1:0]=01
+        upmu_set_rg_bc11_vref_vth(0x1);
+        //RG_BC11_CMP_EN[1.0] = 10
+        upmu_set_rg_bc11_cmp_en(0x2);
+        //msleep(20);
+        mdelay(80);
+
+        wChargerAvail = upmu_get_rgs_bc11_cmp_out();
+        
+        if(Enable_BATDRV_LOG == BAT_LOG_FULL)
+        {
+               battery_xlog_printk(BAT_LOG_FULL, "hw_bc11_DCD() \r\n");
+               hw_bc11_dump_register();
+        }
+        
+        //RG_BC11_IPU_EN[1.0] = 00
+        upmu_set_rg_bc11_ipu_en(0x0);
+        //RG_BC11_IPD_EN[1.0] = 00
+        upmu_set_rg_bc11_ipd_en(0x0);
+        //RG_BC11_CMP_EN[1.0] = 00
+        upmu_set_rg_bc11_cmp_en(0x0);
+        //RG_BC11_VREF_VTH = [1:0]=00
+        upmu_set_rg_bc11_vref_vth(0x0);
+        return wChargerAvail;
+ }
+ static U32 hw_bc11_stepA1(void)
+ {
+       U32 wChargerAvail = 0;
+         
+       //RG_BC11_IPU_EN[1.0] = 10
+       upmu_set_rg_bc11_ipu_en(0x2);
+       //RG_BC11_VREF_VTH = [1:0]=10
+       upmu_set_rg_bc11_vref_vth(0x2);
+       //RG_BC11_CMP_EN[1.0] = 10
+       upmu_set_rg_bc11_cmp_en(0x2);
+       //msleep(80);
+       mdelay(80);
+       wChargerAvail = upmu_get_rgs_bc11_cmp_out();
+       if(Enable_BATDRV_LOG == BAT_LOG_FULL)
+       {
+               battery_xlog_printk(BAT_LOG_FULL, "hw_bc11_stepA1() \r\n");
+               hw_bc11_dump_register();
+       }
+       //RG_BC11_IPU_EN[1.0] = 00
+       upmu_set_rg_bc11_ipu_en(0x0);
+       //RG_BC11_CMP_EN[1.0] = 00
+       upmu_set_rg_bc11_cmp_en(0x0);
+       return  wChargerAvail;
+ }
+ static U32 hw_bc11_stepB1(void)
+ {
+       U32 wChargerAvail = 0;
+         
+       //RG_BC11_IPU_EN[1.0] = 01
+       //upmu_set_rg_bc11_ipu_en(0x1);
+       upmu_set_rg_bc11_ipd_en(0x1);      
+       //RG_BC11_VREF_VTH = [1:0]=10
+       //upmu_set_rg_bc11_vref_vth(0x2);
+       upmu_set_rg_bc11_vref_vth(0x0);
+       //RG_BC11_CMP_EN[1.0] = 01
+       upmu_set_rg_bc11_cmp_en(0x1);
+       //msleep(80);
+       mdelay(80);
+       wChargerAvail = upmu_get_rgs_bc11_cmp_out();
+       if(Enable_BATDRV_LOG == BAT_LOG_FULL)
+       {
+               battery_xlog_printk(BAT_LOG_FULL, "hw_bc11_stepB1() \r\n");
+               hw_bc11_dump_register();
+       }
+       //RG_BC11_IPU_EN[1.0] = 00
+       upmu_set_rg_bc11_ipu_en(0x0);
+       //RG_BC11_CMP_EN[1.0] = 00
+       upmu_set_rg_bc11_cmp_en(0x0);
+       //RG_BC11_VREF_VTH = [1:0]=00
+       upmu_set_rg_bc11_vref_vth(0x0);
+       return  wChargerAvail;
+ }
+ static U32 hw_bc11_stepC1(void)
+ {
+       U32 wChargerAvail = 0;
+         
+       //RG_BC11_IPU_EN[1.0] = 01
+       upmu_set_rg_bc11_ipu_en(0x1);
+       //RG_BC11_VREF_VTH = [1:0]=10
+       upmu_set_rg_bc11_vref_vth(0x2);
+       //RG_BC11_CMP_EN[1.0] = 01
+       upmu_set_rg_bc11_cmp_en(0x1);
+       //msleep(80);
+       mdelay(80);
+       wChargerAvail = upmu_get_rgs_bc11_cmp_out();
+       if(Enable_BATDRV_LOG == BAT_LOG_FULL)
+       {
+               battery_xlog_printk(BAT_LOG_FULL, "hw_bc11_stepC1() \r\n");
+               hw_bc11_dump_register();
+       }
+       //RG_BC11_IPU_EN[1.0] = 00
+       upmu_set_rg_bc11_ipu_en(0x0);
+       //RG_BC11_CMP_EN[1.0] = 00
+       upmu_set_rg_bc11_cmp_en(0x0);
+       //RG_BC11_VREF_VTH = [1:0]=00
+       upmu_set_rg_bc11_vref_vth(0x0);
+       return  wChargerAvail;
+ }
+ static U32 hw_bc11_stepA2(void)
+ {
+       U32 wChargerAvail = 0;
+         
+       //RG_BC11_VSRC_EN[1.0] = 10 
+       upmu_set_rg_bc11_vsrc_en(0x2);
+       //RG_BC11_IPD_EN[1:0] = 01
+       upmu_set_rg_bc11_ipd_en(0x1);
+       //RG_BC11_VREF_VTH = [1:0]=00
+       upmu_set_rg_bc11_vref_vth(0x0);
+       //RG_BC11_CMP_EN[1.0] = 01
+       upmu_set_rg_bc11_cmp_en(0x1);
+       //msleep(80);
+       mdelay(80);
+       wChargerAvail = upmu_get_rgs_bc11_cmp_out();
+       if(Enable_BATDRV_LOG == BAT_LOG_FULL)
+       {
+               battery_xlog_printk(BAT_LOG_FULL, "hw_bc11_stepA2() \r\n");
+               hw_bc11_dump_register();
+       }
+       //RG_BC11_VSRC_EN[1:0]=00
+       upmu_set_rg_bc11_vsrc_en(0x0);
+       //RG_BC11_IPD_EN[1.0] = 00
+       upmu_set_rg_bc11_ipd_en(0x0);
+       //RG_BC11_CMP_EN[1.0] = 00
+       upmu_set_rg_bc11_cmp_en(0x0);
+       return  wChargerAvail;
+ }
+ static U32 hw_bc11_stepB2(void)
+ {
+       U32 wChargerAvail = 0;
+       //RG_BC11_IPU_EN[1:0]=10
+       upmu_set_rg_bc11_ipu_en(0x2);
+       //RG_BC11_VREF_VTH = [1:0]=10
+       upmu_set_rg_bc11_vref_vth(0x1);
+       //RG_BC11_CMP_EN[1.0] = 01
+       upmu_set_rg_bc11_cmp_en(0x1);
+       //msleep(80);
+       mdelay(80);
+       wChargerAvail = upmu_get_rgs_bc11_cmp_out();
+       if(Enable_BATDRV_LOG == BAT_LOG_FULL)
+       {
+               battery_xlog_printk(BAT_LOG_FULL, "hw_bc11_stepB2() \r\n");
+               hw_bc11_dump_register();
+       }
+       //RG_BC11_IPU_EN[1.0] = 00
+       upmu_set_rg_bc11_ipu_en(0x0);
+       //RG_BC11_CMP_EN[1.0] = 00
+       upmu_set_rg_bc11_cmp_en(0x0);
+       //RG_BC11_VREF_VTH = [1:0]=00
+       upmu_set_rg_bc11_vref_vth(0x0);
+       return  wChargerAvail;
+ }
+ static void hw_bc11_done(void)
+ {
+       //RG_BC11_VSRC_EN[1:0]=00
+       upmu_set_rg_bc11_vsrc_en(0x0);
+       //RG_BC11_VREF_VTH = [1:0]=0
+       upmu_set_rg_bc11_vref_vth(0x0);
+       //RG_BC11_CMP_EN[1.0] = 00
+       upmu_set_rg_bc11_cmp_en(0x0);
+       //RG_BC11_IPU_EN[1.0] = 00
+       upmu_set_rg_bc11_ipu_en(0x0);
+       //RG_BC11_IPD_EN[1.0] = 00
+       upmu_set_rg_bc11_ipd_en(0x0);
+       //RG_BC11_BIAS_EN=0
+       upmu_set_rg_bc11_bias_en(0x0); 
+       Charger_Detect_Release();
+
+       if(Enable_BATDRV_LOG == BAT_LOG_FULL)
+       {
+               battery_xlog_printk(BAT_LOG_FULL, "hw_bc11_done() \r\n");
+               hw_bc11_dump_register();
+       }
+    
+ }
+#endif
+
+ static kal_uint32 charging_hw_init(void *data)
+ {
+       kal_uint32 status = STATUS_OK;
+       
+       upmu_set_rg_bc11_bb_ctrl(1);    //BC11_BB_CTRL    
+    upmu_set_rg_bc11_rst(1);        //BC11_RST
+       
+#ifdef GPIO_CHR_CE_PIN
+    //pull CE low
+    mt_set_gpio_mode(GPIO_CHR_CE_PIN,GPIO_MODE_GPIO);  
+    mt_set_gpio_dir(GPIO_CHR_CE_PIN,GPIO_DIR_OUT);
+    mt_set_gpio_out(GPIO_CHR_CE_PIN,GPIO_OUT_ZERO);    
+#endif
+    //battery_xlog_printk(BAT_LOG_FULL, "gpio_number=0x%x,gpio_on_mode=%d,gpio_off_mode=%d\n", gpio_number, gpio_on_mode, gpio_off_mode);      
+
+    bq24297_set_en_hiz(0x0);
+    //bq24297_set_vindpm(0xA); //VIN DPM check 4.68V
+    bq24297_set_vindpm(0x7); //VIN DPM check 4.44V
+    bq24297_set_reg_rst(0x0);
+       bq24297_set_wdt_rst(0x1); //Kick watchdog       
+    bq24297_set_sys_min(0x5); //Minimum system voltage 3.5V    
+       bq24297_set_iprechg(0x3); //Precharge current 512mA
+       bq24297_set_iterm(0x0); //Termination current 128mA
+
+#if defined(HIGH_BATTERY_VOLTAGE_SUPPORT)
+    bq24297_set_vreg(0x32); //VREG 4.304V
+#else
+    bq24297_set_vreg(0x2C); //VREG 4.208V
+#endif    
+  
+    bq24297_set_batlowv(0x1); //BATLOWV 3.0V
+    bq24297_set_vrechg(0x0); //VRECHG 0.1V (4.108V)
+    bq24297_set_en_term(0x1); //Enable termination
+    bq24297_set_term_stat(0x0); //Match ITERM
+    bq24297_set_watchdog(0x1); //WDT 40s
+    bq24297_set_en_timer(0x0); //Disable charge timer
+    bq24297_set_int_mask(0x0); //Disable fault interrupt
+    
+    return status;
+ }
+
+
+ static kal_uint32 charging_dump_register(void *data)
+ {
+       kal_uint32 status = STATUS_OK;
+
+    battery_xlog_printk(BAT_LOG_CRTI, "charging_dump_register\r\n");
+
+       bq24297_dump_register();
+       
+       return status;
+ }     
+
+
+ static kal_uint32 charging_enable(void *data)
+ {
+       kal_uint32 status = STATUS_OK;
+       kal_uint32 enable = *(kal_uint32*)(data);
+
+       if(KAL_TRUE == enable)
+       {
+               bq24297_set_en_hiz(0x0);                        
+        bq24297_set_chg_config(0x1); // charger enable
+       }
+       else
+       {
+#if defined(CONFIG_USB_MTK_HDRC_HCD)
+               if(mt_usb_is_device())
+#endif                         
+       {
+               bq24297_set_chg_config(0x0);
+               
+       }
+       }
+               
+       return status;
+ }
+
+
+ static kal_uint32 charging_set_cv_voltage(void *data)
+ {
+       kal_uint32 status = STATUS_OK;
+       kal_uint16 register_value;
+       kal_uint32 cv_value = *(kal_uint32 *)(data);    
+       
+       if(cv_value == BATTERY_VOLT_04_200000_V)
+       {
+#if defined(HIGH_BATTERY_VOLTAGE_SUPPORT)
+        //highest of voltage will be 4.3V, because powerpath limitation
+               cv_value = 4304000;             
+#else
+           //use nearest value
+               cv_value = 4208000;
+#endif     
+       }
+       register_value = charging_parameter_to_value(VBAT_CV_VTH, GETARRAYNUM(VBAT_CV_VTH), cv_value);
+       bq24297_set_vreg(register_value); 
+
+       return status;
+ }     
+
+
+ static kal_uint32 charging_get_current(void *data)
+ {
+    kal_uint32 status = STATUS_OK;
+    //kal_uint32 array_size;
+    //kal_uint8 reg_value;
+    
+    kal_uint8 ret_val=0;    
+    kal_uint8 ret_force_20pct=0;
+           
+    //Get current level
+    bq24297_read_interface(bq24297_CON2, &ret_val, CON2_ICHG_MASK, CON2_ICHG_SHIFT);
+    
+    //Get Force 20% option
+    bq24297_read_interface(bq24297_CON2, &ret_force_20pct, CON2_FORCE_20PCT_MASK, CON2_FORCE_20PCT_SHIFT);
+    
+    //Parsing
+    ret_val = (ret_val*64) + 512;
+    
+    if (ret_force_20pct == 0)
+    {
+        //Get current level
+        //array_size = GETARRAYNUM(CS_VTH);
+        //*(kal_uint32 *)data = charging_value_to_parameter(CS_VTH,array_size,reg_value);
+        *(kal_uint32 *)data = ret_val;
+    }   
+    else
+    {
+        //Get current level
+        //array_size = GETARRAYNUM(CS_VTH_20PCT);
+        //*(kal_uint32 *)data = charging_value_to_parameter(CS_VTH,array_size,reg_value);
+        //return (int)(ret_val<<1)/10;
+        *(kal_uint32 *)data = (int)(ret_val<<1)/10;
+    }   
+       
+    return status;
+ }  
+  
+
+
+ static kal_uint32 charging_set_current(void *data)
+ {
+       kal_uint32 status = STATUS_OK;
+       
+#if 0  
+       kal_uint32 set_chr_current;
+       kal_uint32 array_size;
+       kal_uint32 register_value;
+       kal_uint32 current_value = *(kal_uint32 *)data;
+       
+       array_size = GETARRAYNUM(CS_VTH);
+       set_chr_current = bmt_find_closest_level(CS_VTH, array_size, current_value);
+       register_value = charging_parameter_to_value(CS_VTH, array_size ,set_chr_current);
+       bq24297_set_ichg(register_value);
+#else
+    battery_xlog_printk(BAT_LOG_FULL, "skip charging_set_current()\r\n");
+#endif 
+       
+       return status;
+ }     
+
+static kal_uint32 charging_set_input_current(void *data)
+{
+       kal_uint32 status = STATUS_OK;
+
+#if 0  
+       kal_uint32 set_chr_current;
+       kal_uint32 array_size;
+       kal_uint32 register_value;
+    
+       array_size = GETARRAYNUM(INPUT_CS_VTH);
+       set_chr_current = bmt_find_closest_level(INPUT_CS_VTH, array_size, *(kal_uint32 *)data);
+       register_value = charging_parameter_to_value(INPUT_CS_VTH, array_size ,set_chr_current);        
+        
+    bq24297_set_iinlim(register_value);
+#else    
+    battery_xlog_printk(BAT_LOG_CRTI, "skip charging_set_input_current()\r\n");
+#endif    
+
+       return status;
+}      
+
+
+ static kal_uint32 charging_get_charging_status(void *data)
+ {
+       kal_uint32 status = STATUS_OK;
+       kal_uint32 ret_val;
+
+       ret_val = bq24297_get_chrg_stat();
+       
+       if(ret_val == 0x3)
+               *(kal_uint32 *)data = KAL_TRUE;
+       else
+               *(kal_uint32 *)data = KAL_FALSE;
+       
+       return status;
+ }     
+
+
+ static kal_uint32 charging_reset_watch_dog_timer(void *data)
+ {
+        kal_uint32 status = STATUS_OK;
+     battery_xlog_printk(BAT_LOG_CRTI, "charging_reset_watch_dog_timer\r\n");
+        bq24297_set_wdt_rst(0x1); //Kick watchdog
+        
+        return status;
+ }
+  static kal_uint32 charging_set_hv_threshold(void *data)
+  {
+        kal_uint32 status = STATUS_OK;
+        kal_uint32 set_hv_voltage;
+        kal_uint32 array_size;
+        kal_uint16 register_value;
+        kal_uint32 voltage = *(kal_uint32*)(data);
+        
+        array_size = GETARRAYNUM(VCDT_HV_VTH);
+        set_hv_voltage = bmt_find_closest_level(VCDT_HV_VTH, array_size, voltage);
+        register_value = charging_parameter_to_value(VCDT_HV_VTH, array_size ,set_hv_voltage);
+        upmu_set_rg_vcdt_hv_vth(register_value);
+        return status;
+  }
+  static kal_uint32 charging_get_hv_status(void *data)
+  {
+          kal_uint32 status = STATUS_OK;
+          *(kal_bool*)(data) = upmu_get_rgs_vcdt_hv_det();
+          
+          return status;
+  }
+
+
+ static kal_uint32 charging_get_battery_status(void *data)
+ {
+          kal_uint32 status = STATUS_OK;
+          upmu_set_baton_tdet_en(1);   
+          upmu_set_rg_baton_en(1);
+          *(kal_bool*)(data) = upmu_get_rgs_baton_undet();
+          
+          return status;
+ }
+
+
+ static kal_uint32 charging_get_charger_det_status(void *data)
+ {
+          kal_uint32 status = STATUS_OK;
+          *(kal_bool*)(data) = upmu_get_rgs_chrdet();
+          
+          return status;
+ }
+
+
+kal_bool charging_type_detection_done(void)
+{
+        return charging_type_det_done;
+}
+
+extern CHARGER_TYPE hw_charger_type_detection(void);
+
+static kal_uint32 charging_get_charger_type(void *data)
+{
+    kal_uint32 status = STATUS_OK;
+    CHARGER_TYPE charger_type = CHARGER_UNKNOWN;
+    kal_uint32 ret_val;
+    kal_uint8 reg_val=0;
+    kal_uint32 count = 0;
+    unsigned int USB_U2PHYACR6_2     = 0xF122081A;
+    
+#if defined(CONFIG_POWER_EXT)
+       *(CHARGER_TYPE*)(data) = STANDARD_HOST;
+#else
+
+       charging_type_det_done = KAL_FALSE;
+    
+#if 0    
+    charger_type = hw_charger_type_detection();
+#else
+    battery_xlog_printk(BAT_LOG_CRTI, "use BQ24297 charger detection\r\n");
+    
+    enable_pll(UNIVPLL, "USB_PLL");
+    hwPowerOn(MT65XX_POWER_LDO_VUSB,VOL_DEFAULT,"VUSB_LDO");
+    SETREG16(USB_U2PHYACR6_2,0x80); //bit 7 = 1 : switch to PMIC
+    
+    ret_val = bq24297_get_vbus_stat();
+    
+    if (ret_val == 0x0)
+    {
+        bq24297_set_dpdm_en(1);
+        while(bq24297_get_dpdm_status() == 1)
+        {
+            count++;
+            mdelay(1);
+            battery_xlog_printk(BAT_LOG_CRTI, "polling BQ24297 charger detection\r\n");
+            if (count > 1000)
+                break;
+        }
+    }
+   
+    ret_val = bq24297_get_vbus_stat();
+    switch (ret_val)
+    {
+        case 0x1:
+            charger_type = STANDARD_HOST;
+            break;
+        case 0x2:
+            charger_type = STANDARD_CHARGER;
+            break;
+        default:
+            charger_type = NONSTANDARD_CHARGER;//CHARGER_UNKNOWN;
+            break;
+    }
+    
+    if (charger_type == STANDARD_CHARGER)
+    {
+        bq24297_read_interface(bq24297_CON0, &reg_val, CON0_IINLIM_MASK, CON0_IINLIM_SHIFT);
+        if (reg_val < 0x4)
+        {
+            battery_xlog_printk(BAT_LOG_CRTI, "Set to Non-standard charger due to 1A input limit.\r\n");
+            charger_type = NONSTANDARD_CHARGER;            
+        }
+    }
+    
+    CLRREG16(USB_U2PHYACR6_2,0x80); //bit 7 = 0 : switch to USB
+    hwPowerDown(MT65XX_POWER_LDO_VUSB,"VUSB_LDO");
+    disable_pll(UNIVPLL,"USB_PLL");
+#endif    
+    battery_xlog_printk(BAT_LOG_CRTI, "charging_get_charger_type = %d\r\n", charger_type);
+        
+    *(CHARGER_TYPE*)(data) = charger_type;
+
+       charging_type_det_done = KAL_TRUE;
+#endif
+        return status;
+}
+
+static kal_uint32 charging_get_is_pcm_timer_trigger(void *data)
+{
+    kal_uint32 status = STATUS_OK;
+
+    if(slp_get_wake_reason() == WR_PCM_TIMER)
+        *(kal_bool*)(data) = KAL_TRUE;
+    else
+        *(kal_bool*)(data) = KAL_FALSE;
+
+    battery_xlog_printk(BAT_LOG_CRTI, "slp_get_wake_reason=%d\n", slp_get_wake_reason());
+       
+    return status;
+}
+
+static kal_uint32 charging_set_platform_reset(void *data)
+{
+    kal_uint32 status = STATUS_OK;
+
+    battery_xlog_printk(BAT_LOG_CRTI, "charging_set_platform_reset\n");
+    arch_reset(0,NULL);
+        
+    return status;
+}
+
+static kal_uint32 charging_get_platfrom_boot_mode(void *data)
+{
+    kal_uint32 status = STATUS_OK;
+  
+    *(kal_uint32*)(data) = get_boot_mode();
+
+    battery_xlog_printk(BAT_LOG_CRTI, "get_boot_mode=%d\n", get_boot_mode());
+         
+    return status;
+}
+
+static kal_uint32 charging_set_power_off(void *data)
+{
+    kal_uint32 status = STATUS_OK;
+  
+    battery_xlog_printk(BAT_LOG_CRTI, "charging_set_power_off=%d\n");
+    mt_power_off();
+         
+    return status;
+}
+
+ static kal_uint32 (* const charging_func[CHARGING_CMD_NUMBER])(void *data)=
+ {
+         charging_hw_init
+       ,charging_dump_register         
+       ,charging_enable
+       ,charging_set_cv_voltage
+       ,charging_get_current
+       ,charging_set_current
+       ,charging_set_input_current
+       ,charging_get_charging_status
+       ,charging_reset_watch_dog_timer
+       ,charging_set_hv_threshold
+       ,charging_get_hv_status
+       ,charging_get_battery_status
+       ,charging_get_charger_det_status
+       ,charging_get_charger_type
+       ,charging_get_is_pcm_timer_trigger
+       ,charging_set_platform_reset
+       ,charging_get_platfrom_boot_mode
+       ,charging_set_power_off 
+ };
+
+ /*
+ * FUNCTION
+ *             Internal_chr_control_handler
+ *
+ * DESCRIPTION                                                                                                                  
+ *              This function is called to set the charger hw
+ *
+ * CALLS  
+ *
+ * PARAMETERS
+ *             None
+ *      
+ * RETURNS
+ *             
+ *
+ * GLOBALS AFFECTED
+ *        None
+ */
+ kal_int32 chr_control_interface(CHARGING_CTRL_CMD cmd, void *data)
+ {
+        kal_int32 status;
+        if(cmd < CHARGING_CMD_NUMBER)
+                status = charging_func[cmd](data);
+        else
+                return STATUS_UNSUPPORTED;
+        return status;
+ }
+
+