diff options
Diffstat (limited to 'firmware/e300/rev_b/bq24190.c')
-rw-r--r-- | firmware/e300/rev_b/bq24190.c | 335 |
1 files changed, 335 insertions, 0 deletions
diff --git a/firmware/e300/rev_b/bq24190.c b/firmware/e300/rev_b/bq24190.c new file mode 100644 index 000000000..029beacf6 --- /dev/null +++ b/firmware/e300/rev_b/bq24190.c @@ -0,0 +1,335 @@ +/* + * bq24190.c + * + * Created: 11/12/2012 4:58:12 PM + * Author: Balint Seeber + */ + +#ifdef CHARGER_TI + +#include "config.h" +#include "bq24190.h" + +#include <util/delay.h> + +#include "io.h" +#include "i2c.h" +#include "debug.h" +#include "global.h" +#include "error.h" + +#ifndef I2C_REWORK +#include "power.h" +#endif // I2C_REWORK + +static io_pin_t USBPM_IRQ = IO_PB(1); + +#ifdef ATTINY88_DIP + +static io_pin_t CHRG_SDA = IO_PC(2); +static io_pin_t CHRG_SCL = IO_PC(3); + +#else + +#ifdef I2C_REWORK + +static io_pin_t CHRG_SDA = IO_PC(4); +static io_pin_t CHRG_SCL = IO_PC(5); + +#else + +#define CHRG_SDA PWR_SDA +#define CHRG_SCL PWR_SCL + +#endif // I2C_REWORK + +#endif // ATTINY88_DIP + +const bool _bq24190_pull_up = false; + +#define BQ24190_BASE_ADDRESS (0x6B << 1) +#define BQ24190_WRITE_ADDRESS (BQ24190_BASE_ADDRESS + 0) +#define BQ24190_READ_ADDRESS (BQ24190_BASE_ADDRESS + 1) + +enum BQ24190Registers +{ + BQ24190_REG_INPUT_SOURCE_CTL= 0, + BQ24190_REG_PWR_ON_CONFIG = 1, + BQ24190_REG_CHARGE_CURRENT = 2, + BQ24190_REG_PRE_TERM_CURRENT= 3, + BQ24190_REG_CHARGE_VOLTAGE = 4, + BQ24190_REG_TIMER_CONTROL = 5, + BQ24190_REG_SYSTEM_STATUS = 8, + BQ24190_REG_FAULT = 9 +}; +/* +enum BQ24190TimerControl +{ + +}; +*/ +enum BQ24190Shifts +{ + BQ24190_SHIFTS_CHARGER_CONFIG = 4, + BQ24190_SHIFTS_I2C_WATCHDOG = 4, + BQ24190_SHIFTS_CHARGER_STATUS = 4, + BQ24190_SHIFTS_CHARGER_FAULT = 4, +}; + +enum BQ24190VBusStatus +{ + BQ24190_VBUS_UNKNOWN, + BQ24190_VBUS_USB, + BQ24190_VBUS_ADAPTER, + BQ24190_VBUS_OTG +}; + +enum BQ24190ChargerStatus +{ + BQ24190_CHRG_STAT_NOT_CHARGING, + BQ24190_CHRG_STAT_PRE_CHARGE, + BQ24190_CHRG_STAT_FAST_CHARGING, + BQ24190_CHRG_STAT_CHARGE_TERMINATION_DONE, + BQ24190_CHRG_STAT_MASK = BQ24190_CHRG_STAT_CHARGE_TERMINATION_DONE +}; + +enum BQ24190SystemStatus +{ + BQ24190_STATUS_DPM = 0x08, + BQ24190_STATUS_POWER_GOOD = 0x04, + BQ24190_STATUS_THERMAL_REGULATION = 0x02, + BQ24190_STATUS_VSYSMIN_REGULATION = 0x01 +}; + +enum BQ24190Faults +{ + BQ24190_FAULT_WATCHDOG_EXPIRED = 0x80, + BQ24190_FAULT_VBUS_OVERLOADED = 0x40, + BQ24190_FAULT_BATOVP = 0x08 +}; + +enum BQ24190ChargerFaults +{ + BQ24190_CHRGFAULT_NORMAL, + BQ24190_CHRGFAULT_INPUT, + BQ24190_CHRGFAULT_THERMAL, + BQ24190_CHRGFAULT_SAFETY_TIMER +}; + +enum BQ24190NTCFaults +{ + BQ24190_NTCFAULT_NORMAL, + BQ24190_NTCFAULT_TS1_COLD, + BQ24190_NTCFAULT_TS1_HOT, + BQ24190_NTCFAULT_TS2_COLD, + BQ24190_NTCFAULT_TS2_HOT, + BQ24190_NTCFAULT_BOTH_COLD, + BQ24190_NTCFAULT_BOTH_HOT +}; + +bool bq24190_toggle_charger(bool on) +{ + uint8_t config = 0; + if (i2c_read2_ex(CHRG_SDA, CHRG_SCL, BQ24190_READ_ADDRESS, BQ24190_REG_PWR_ON_CONFIG, &config, _bq24190_pull_up) == false) + return false; + + debug_log_ex("BQPC ", false); + debug_log_hex(config); + + config &= ~(0x3 << BQ24190_SHIFTS_CHARGER_CONFIG); + if (on) + config |= (0x01 << BQ24190_SHIFTS_CHARGER_CONFIG); // Enable charger + + if (i2c_write_ex(CHRG_SDA, CHRG_SCL, BQ24190_WRITE_ADDRESS, BQ24190_REG_PWR_ON_CONFIG, config, _bq24190_pull_up) == false) + return false; + + //////// +/* + if (i2c_read2_ex(CHRG_SDA, CHRG_SCL, BQ24190_READ_ADDRESS, BQ24190_REG_PWR_ON_CONFIG, &config, _bq24190_pull_up) == false) + return false; + + debug_log_ex("BQPC ", false); + debug_log_hex(config); +*/ + //////// + + return true; +} + +bool bq24190_init(bool disable_charger) +{ +#ifdef I2C_REWORK + i2c_init_ex(CHRG_SDA, CHRG_SCL, _bq24190_pull_up); +#endif // I2C_REWORK + io_input_pin(USBPM_IRQ); +#if !defined(DEBUG) && !defined(ATTINY88_DIP) + //io_set_pin(USBPM_IRQ); // [Enable pull-up for Open Drain] AVR pull-up not enough +#endif // DEBUG + if (disable_charger) + { + if (bq24190_toggle_charger(false) == false) + return false; + } + + /////////////////////////////////// + + uint8_t timer_control = 0; + if (i2c_read2_ex(CHRG_SDA, CHRG_SCL, BQ24190_READ_ADDRESS, BQ24190_REG_TIMER_CONTROL, &timer_control, _bq24190_pull_up) == false) + return false; + + debug_log_ex("BQTC ", false); + debug_log_hex(timer_control); + + timer_control &= ~(0x3 << BQ24190_SHIFTS_I2C_WATCHDOG); + timer_control |= (0x00 << BQ24190_SHIFTS_I2C_WATCHDOG); // Disable I2C watch dog + + if (i2c_write_ex(CHRG_SDA, CHRG_SCL, BQ24190_WRITE_ADDRESS, BQ24190_REG_TIMER_CONTROL, timer_control, _bq24190_pull_up) == false) + return false; + + /////////////////////////////////// + + //BQ24190_REG_PWR_ON_CONFIG + // Minimum System Voltage Limit: (default) 101 3.5V + + //BQ24190_REG_CHARGE_CURRENT + // Fast Charge Current Limit: (default) 011000 2048mA + + //BQ24190_REG_PRE_TERM_CURRENT + // Pre-charge current limit: (default) 0001 256mA + // Termination current limit: (default) 0001 256mA + + //BQ24190_REG_CHARGE_VOLTAGE + // Charge voltage limit: (default) 101100 4.208V + + /////////////////////////////////// + + uint8_t input_src_ctl = 0; + if (i2c_read2_ex(CHRG_SDA, CHRG_SCL, BQ24190_READ_ADDRESS, BQ24190_REG_INPUT_SOURCE_CTL, &input_src_ctl, _bq24190_pull_up) == false) + return false; + + debug_log_ex("BQIS ", false); + debug_log_hex(input_src_ctl); + + // Input voltage limit: (default) 0110 4.36V + + //input_src_ctl &= ~(0x07); + input_src_ctl |= (0x07); // Set 3A limit + + if (i2c_write_ex(CHRG_SDA, CHRG_SCL, BQ24190_WRITE_ADDRESS, BQ24190_REG_INPUT_SOURCE_CTL, input_src_ctl, _bq24190_pull_up) == false) + return false; + + return true; +} + +bool bq24190_has_interrupt(void) +{ + //bool state = io_test_pin(USBPM_IRQ); + //debug_log_ex("BQIRQ", false); + //debug_log_byte(state); + //return (state != 1); + return (io_test_pin(USBPM_IRQ) == false); +} + +static uint8_t _bq24190_last_status, _bq24190_last_fault; + +bool _bq24190_handle_irq(void) +{ + uint8_t val = 0x00; + bool result = false; + + if (i2c_read2_ex(CHRG_SDA, CHRG_SCL, BQ24190_READ_ADDRESS, BQ24190_REG_SYSTEM_STATUS, &val, _bq24190_pull_up) == false) + goto _bq24190_handle_fail; + + debug_log_ex("BQST ", false); + debug_log_hex(val); + + if (i2c_read2_ex(CHRG_SDA, CHRG_SCL, BQ24190_READ_ADDRESS, BQ24190_REG_SYSTEM_STATUS, &val, _bq24190_pull_up) == false) + goto _bq24190_handle_fail; + + _bq24190_last_status = val; + + debug_log_ex("BQST ", false); + debug_log_hex(val); + + /*if (val & LTC4155_WALLSNS_GOOD) + { + uint8_t wall_state = 0; + if (i2c_read2_ex(CHRG_SDA, CHRG_SCL, LTC4155_READ_ADDRESS, LTC4155_REG_WALL, &wall_state, _ltc4155_pull_up) == false) + goto _bq24190_handle_fail; + + wall_state &= ~0x1E; + wall_state |= 0x0E; + + if (i2c_write_ex(CHRG_SDA, CHRG_SCL, LTC4155_WRITE_ADDRESS, LTC4155_REG_WALL, wall_state, _ltc4155_pull_up) == false) + goto _bq24190_handle_fail; + + debug_log("I+"); + }*/ + + if (i2c_read2_ex(CHRG_SDA, CHRG_SCL, BQ24190_READ_ADDRESS, BQ24190_REG_FAULT, &val, _bq24190_pull_up) == false) + goto _bq24190_handle_fail; + + debug_log_ex("BQF ", false); + debug_log_hex(val); + + if (i2c_read2_ex(CHRG_SDA, CHRG_SCL, BQ24190_READ_ADDRESS, BQ24190_REG_FAULT, &val, _bq24190_pull_up) == false) + goto _bq24190_handle_fail; + + _bq24190_last_fault = val; + + debug_log_ex("BQF ", false); + debug_log_hex(val); + + val = (_bq24190_last_status >> BQ24190_SHIFTS_CHARGER_STATUS) & BQ24190_CHRG_STAT_MASK; + + if (_state.blink_error == BlinkError_None) + { + switch (val) + { + case BQ24190_CHRG_STAT_PRE_CHARGE: + case BQ24190_CHRG_STAT_FAST_CHARGING: + //case BQ24190_CHRG_STAT_CHARGE_TERMINATION_DONE: + { + if ((_state.battery_not_present == false)/* && + (_ltc4155_last_good & (LTC4155_WALLSNS_GOOD | LTC4155_USBSNS_GOOD))*/) + { + //charge_set_led(true); + charge_notify(true); + break; + } + } + //case BQ24190_CHRG_STAT_NOT_CHARGING: + default: + //charge_set_led(false); + charge_notify(false); + } + } + +// bq24190_dump(); + + result = true; +_bq24190_handle_fail: + return result; +} + +bool bq24190_handle_irq(void) // IRQ is pulsed (not held) +{ + pmc_mask_irqs(true); + + //_delay_ms(250); // [Wait for registers to update] + + bool result = _bq24190_handle_irq(); + + pmc_mask_irqs(false); + + return result; +} + +//void bq24190_dump(void) +/* +bool bq24190_set_charge_current_limit(uint8_t deciamps) +{ + return true; +} +*/ +#endif // CHARGER_TI |