diff options
-rw-r--r-- | board/coral/battery.c | 93 |
1 files changed, 87 insertions, 6 deletions
diff --git a/board/coral/battery.c b/board/coral/battery.c index 4f4896c868..608590ebf7 100644 --- a/board/coral/battery.c +++ b/board/coral/battery.c @@ -25,6 +25,8 @@ #define SHIP_MODE_WRITES 2 enum battery_type { + BATTERY_LGC15, + BATTERY_LGC203, BATTERY_SANYO, BATTERY_SONY, BATTERY_PANASONIC, @@ -43,6 +45,7 @@ struct ship_mode_info { }; struct fet_info { + const int mfgacc_support; const uint8_t reg_addr; const uint16_t reg_mask; const uint16_t disconnect_val; @@ -50,6 +53,7 @@ struct fet_info { struct fuel_gauge_info { const char *manuf_name; + const char *device_name; const struct ship_mode_info ship_mode; const struct fet_info fet; }; @@ -91,6 +95,65 @@ static int disch_on_ac; * address, mask, and disconnect value need to be provided. */ static const struct board_batt_params info[] = { + /* LGC AC15A8J Battery Information */ + [BATTERY_LGC15] = { + .fuel_gauge = { + .manuf_name = "LGC", + .device_name = "AC15A8J", + .ship_mode = { + .reg_addr = 0x3A, + .reg_data = { 0xC574, 0xC574 }, + }, + .fet = { + .mfgacc_support = 1, + .reg_addr = 0x0, + .reg_mask = 0x0002, + .disconnect_val = 0x0, + } + }, + .batt_info = { + .voltage_max = TARGET_WITH_MARGIN(13200, 5), + .voltage_normal = 11520, /* mV */ + .voltage_min = 9000, /* mV */ + .precharge_current = 256, /* mA */ + .start_charging_min_c = 0, + .start_charging_max_c = 50, + .charging_min_c = 0, + .charging_max_c = 60, + .discharging_min_c = 0, + .discharging_max_c = 60, + }, + }, + + /* LGC C203-36J Battery Information */ + [BATTERY_LGC203] = { + .fuel_gauge = { + .manuf_name = "AS1GXXc3KB", + .ship_mode = { + .reg_addr = 0x00, + .reg_data = { 0x0010, 0x0010 }, + }, + .fet = { + .mfgacc_support = 1, + .reg_addr = 0x0, + .reg_mask = 0x0002, + .disconnect_val = 0x0, + } + }, + .batt_info = { + .voltage_max = TARGET_WITH_MARGIN(13200, 5), + .voltage_normal = 11520, /* mV */ + .voltage_min = 9000, /* mV */ + .precharge_current = 256, /* mA */ + .start_charging_min_c = 0, + .start_charging_max_c = 45, + .charging_min_c = 0, + .charging_max_c = 60, + .discharging_min_c = 0, + .discharging_max_c = 60, + }, + }, + /* SANYO AC15A3J Battery Information */ [BATTERY_SANYO] = { .fuel_gauge = { @@ -355,14 +418,24 @@ static inline const struct board_batt_params *board_get_batt_params(void) /* Get type of the battery connected on the board */ static int board_get_battery_type(void) { - char name[32]; + char manu_name[32], device_name[32]; int i; - if (!battery_manufacturer_name(name, sizeof(name))) { + if (!battery_manufacturer_name(manu_name, sizeof(manu_name))) { for (i = 0; i < BATTERY_TYPE_COUNT; i++) { - if (!strcasecmp(name, info[i].fuel_gauge.manuf_name)) { - board_battery_type = i; - break; + if (!strcasecmp(manu_name, + info[i].fuel_gauge.manuf_name)) { + if (info[i].fuel_gauge.device_name == NULL) { + board_battery_type = i; + break; + } else if (!battery_device_name(device_name, + sizeof(device_name))) { + if (!strcasecmp(device_name, + info[i].fuel_gauge.device_name)) { + board_battery_type = i; + break; + } + } } } } @@ -508,6 +581,7 @@ static int battery_check_disconnect(void) { int rv; int reg; + uint8_t data[6]; /* If battery type is not known, can't check CHG/DCHG FETs */ if (board_battery_type == BATTERY_TYPE_COUNT) { @@ -519,7 +593,14 @@ static int battery_check_disconnect(void) } /* Read the status of charge/discharge FETs */ - rv = sb_read(info[board_battery_type].fuel_gauge.fet.reg_addr, ®); + if (info[board_battery_type].fuel_gauge.fet.mfgacc_support == 1) { + rv = sb_read_mfgacc(PARAM_OPERATION_STATUS, + SB_ALT_MANUFACTURER_ACCESS, data, sizeof(data)); + /* Get the lowest 16bits of the OperationStatus() data */ + reg = data[2] | data[3] << 8; + } else + rv = sb_read(info[board_battery_type].fuel_gauge.fet.reg_addr, + ®); if (rv) return BATTERY_DISCONNECT_ERROR; |