1 /* 2 * (C) Copyright 2010 3 * Texas Instruments, <www.ti.com> 4 * 5 * SPDX-License-Identifier: GPL-2.0+ 6 */ 7 #include <config.h> 8 #ifdef CONFIG_TWL6030_POWER 9 10 #include <twl6030.h> 11 12 static int twl6030_gpadc_read_channel(u8 channel_no) 13 { 14 u8 lsb = 0; 15 u8 msb = 0; 16 int ret = 0; 17 18 ret = twl6030_i2c_read_u8(TWL6030_CHIP_ADC, 19 GPCH0_LSB + channel_no * 2, &lsb); 20 if (ret) 21 return ret; 22 23 ret = twl6030_i2c_read_u8(TWL6030_CHIP_ADC, 24 GPCH0_MSB + channel_no * 2, &msb); 25 if (ret) 26 return ret; 27 28 return (msb << 8) | lsb; 29 } 30 31 static int twl6030_gpadc_sw2_trigger(void) 32 { 33 u8 val; 34 int ret = 0; 35 36 ret = twl6030_i2c_write_u8(TWL6030_CHIP_ADC, CTRL_P2, CTRL_P2_SP2); 37 if (ret) 38 return ret; 39 40 /* Waiting until the SW1 conversion ends*/ 41 val = CTRL_P2_BUSY; 42 43 while (!((val & CTRL_P2_EOCP2) && (!(val & CTRL_P2_BUSY)))) { 44 ret = twl6030_i2c_read_u8(TWL6030_CHIP_ADC, CTRL_P2, &val); 45 if (ret) 46 return ret; 47 udelay(1000); 48 } 49 50 return 0; 51 } 52 53 void twl6030_stop_usb_charging(void) 54 { 55 twl6030_i2c_write_u8(TWL6030_CHIP_CHARGER, CONTROLLER_CTRL1, 0); 56 57 return; 58 } 59 60 void twl6030_start_usb_charging(void) 61 { 62 twl6030_i2c_write_u8(TWL6030_CHIP_CHARGER, 63 CHARGERUSB_VICHRG, CHARGERUSB_VICHRG_1500); 64 twl6030_i2c_write_u8(TWL6030_CHIP_CHARGER, 65 CHARGERUSB_CINLIMIT, CHARGERUSB_CIN_LIMIT_NONE); 66 twl6030_i2c_write_u8(TWL6030_CHIP_CHARGER, 67 CONTROLLER_INT_MASK, MBAT_TEMP); 68 twl6030_i2c_write_u8(TWL6030_CHIP_CHARGER, 69 CHARGERUSB_INT_MASK, MASK_MCHARGERUSB_THMREG); 70 twl6030_i2c_write_u8(TWL6030_CHIP_CHARGER, 71 CHARGERUSB_VOREG, CHARGERUSB_VOREG_4P0); 72 twl6030_i2c_write_u8(TWL6030_CHIP_CHARGER, 73 CHARGERUSB_CTRL2, CHARGERUSB_CTRL2_VITERM_400); 74 twl6030_i2c_write_u8(TWL6030_CHIP_CHARGER, CHARGERUSB_CTRL1, TERM); 75 /* Enable USB charging */ 76 twl6030_i2c_write_u8(TWL6030_CHIP_CHARGER, 77 CONTROLLER_CTRL1, CONTROLLER_CTRL1_EN_CHARGER); 78 return; 79 } 80 81 int twl6030_get_battery_current(void) 82 { 83 int battery_current = 0; 84 u8 msb = 0; 85 u8 lsb = 0; 86 87 twl6030_i2c_read_u8(TWL6030_CHIP_CHARGER, FG_REG_11, &msb); 88 twl6030_i2c_read_u8(TWL6030_CHIP_CHARGER, FG_REG_10, &lsb); 89 battery_current = ((msb << 8) | lsb); 90 91 /* convert 10 bit signed number to 16 bit signed number */ 92 if (battery_current >= 0x2000) 93 battery_current = (battery_current - 0x4000); 94 95 battery_current = battery_current * 3000 / 4096; 96 printf("Battery Current: %d mA\n", battery_current); 97 98 return battery_current; 99 } 100 101 int twl6030_get_battery_voltage(void) 102 { 103 int battery_volt = 0; 104 int ret = 0; 105 106 /* Start GPADC SW conversion */ 107 ret = twl6030_gpadc_sw2_trigger(); 108 if (ret) { 109 printf("Failed to convert battery voltage\n"); 110 return ret; 111 } 112 113 /* measure Vbat voltage */ 114 battery_volt = twl6030_gpadc_read_channel(7); 115 if (battery_volt < 0) { 116 printf("Failed to read battery voltage\n"); 117 return ret; 118 } 119 battery_volt = (battery_volt * 25 * 1000) >> (10 + 2); 120 printf("Battery Voltage: %d mV\n", battery_volt); 121 122 return battery_volt; 123 } 124 125 void twl6030_init_battery_charging(void) 126 { 127 u8 stat1 = 0; 128 int battery_volt = 0; 129 int ret = 0; 130 131 /* Enable VBAT measurement */ 132 twl6030_i2c_write_u8(TWL6030_CHIP_PM, MISC1, VBAT_MEAS); 133 134 /* Enable GPADC module */ 135 ret = twl6030_i2c_write_u8(TWL6030_CHIP_CHARGER, TOGGLE1, FGS | GPADCS); 136 if (ret) { 137 printf("Failed to enable GPADC\n"); 138 return; 139 } 140 141 battery_volt = twl6030_get_battery_voltage(); 142 if (battery_volt < 0) 143 return; 144 145 if (battery_volt < 3000) 146 printf("Main battery voltage too low!\n"); 147 148 /* Check for the presence of USB charger */ 149 twl6030_i2c_read_u8(TWL6030_CHIP_CHARGER, CONTROLLER_STAT1, &stat1); 150 151 /* check for battery presence indirectly via Fuel gauge */ 152 if ((stat1 & VBUS_DET) && (battery_volt < 3300)) 153 twl6030_start_usb_charging(); 154 155 return; 156 } 157 158 void twl6030_power_mmc_init() 159 { 160 /* set voltage to 3.0 and turnon for APP */ 161 twl6030_i2c_write_u8(TWL6030_CHIP_PM, VMMC_CFG_VOLTATE, 0x15); 162 twl6030_i2c_write_u8(TWL6030_CHIP_PM, VMMC_CFG_STATE, 0x21); 163 } 164 165 void twl6030_usb_device_settings() 166 { 167 u8 data = 0; 168 169 /* Select APP Group and set state to ON */ 170 twl6030_i2c_write_u8(TWL6030_CHIP_PM, VUSB_CFG_STATE, 0x21); 171 172 twl6030_i2c_read_u8(TWL6030_CHIP_PM, MISC2, &data); 173 data |= 0x10; 174 175 /* Select the input supply for VBUS regulator */ 176 twl6030_i2c_write_u8(TWL6030_CHIP_PM, MISC2, data); 177 } 178 #endif 179