diff options
author | Eric Yilun Lin <yllin@chromium.org> | 2021-10-14 17:00:38 +0800 |
---|---|---|
committer | Commit Bot <commit-bot@chromium.org> | 2021-10-15 02:26:08 +0000 |
commit | 537def8417e4cdf7f381474c57ec93f6cb963a3c (patch) | |
tree | 58e1ae34b0358bd2fce96a768199674f1c1017b3 | |
parent | 4438e19d17265fad22e51f2c597cb16f055703ed (diff) | |
download | chrome-ec-537def8417e4cdf7f381474c57ec93f6cb963a3c.tar.gz |
charge: respect PDO current maximum limit
The current input limit setting doesn't respect the PDO's
current limit (e.g. when the current limit is less than
CONFIG_INPUT_CURRENT_LIMIT) and this might cause the over-draining
the charger.
BUG=b:172878439
TEST=1) make buildall
2) modified servo-v4 which only broadcast PDOs with 250mA current
limit and ensure the goroh won't sink more than 250mA.
(while the CONFIG_INPUT_CURRENT_LIMIT is 512mA)
BRANCH=main
Change-Id: I09f8e6fb39a072ee38ea09a5c9898984f4122513
Signed-off-by: Eric Yilun Lin <yllin@chromium.org>
Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/platform/ec/+/3220037
Commit-Queue: Eric Yilun Lin <yllin@google.com>
Tested-by: Eric Yilun Lin <yllin@google.com>
Reviewed-by: Aseda Aboagye <aaboagye@chromium.org>
Reviewed-by: Diana Z <dzigterman@chromium.org>
-rw-r--r-- | common/charge_manager.c | 15 | ||||
-rw-r--r-- | common/charge_state_v2.c | 13 | ||||
-rw-r--r-- | include/charge_manager.h | 9 |
3 files changed, 37 insertions, 0 deletions
diff --git a/common/charge_manager.c b/common/charge_manager.c index 862bb28725..14c869c3b2 100644 --- a/common/charge_manager.c +++ b/common/charge_manager.c @@ -107,6 +107,7 @@ static int charge_current = CHARGE_CURRENT_UNINITIALIZED; static int charge_current_uncapped = CHARGE_CURRENT_UNINITIALIZED; static int charge_voltage; static int charge_supplier = CHARGE_SUPPLIER_NONE; +static int charge_pd_current_uncapped = CHARGE_CURRENT_UNINITIALIZED; static int override_port = OVERRIDE_OFF; static int delayed_override_port = OVERRIDE_OFF; @@ -267,6 +268,11 @@ static int charge_manager_is_seeded(void) return 1; } +int charge_manager_get_pd_current_uncapped(void) +{ + return charge_pd_current_uncapped; +} + #ifndef TEST_BUILD /** * Get the maximum charge current for a port. @@ -828,6 +834,15 @@ static void charge_manager_refresh(void) available_charge[new_supplier][new_port].voltage; } + /* + * Record the PD current limit to prevent from over-sinking + * the charger. + */ + if (new_supplier == CHARGE_SUPPLIER_PD) + charge_pd_current_uncapped = new_charge_current_uncapped; + else + charge_pd_current_uncapped = CHARGE_CURRENT_UNINITIALIZED; + /* Change the charge limit + charge port/supplier if modified. */ if (new_port != charge_port || new_charge_current != charge_current || new_supplier != charge_supplier) { diff --git a/common/charge_state_v2.c b/common/charge_state_v2.c index 59f38edee8..abfabda7a3 100644 --- a/common/charge_state_v2.c +++ b/common/charge_state_v2.c @@ -2694,6 +2694,19 @@ int charge_set_input_current_limit(int ma, int mv) /* Limit input current limit to max limit for this board */ ma = MIN(ma, CONFIG_CHARGER_MAX_INPUT_CURRENT); #endif + + if (IS_ENABLED(CONFIG_CHARGE_MANAGER)) { + int pd_current_uncapped = + charge_manager_get_pd_current_uncapped(); + + /* + * clamp the input current to not exceeded the PD's limitation. + */ + if (pd_current_uncapped != CHARGE_CURRENT_UNINITIALIZED && + ma > pd_current_uncapped) + ma = pd_current_uncapped; + } + curr.desired_input_current = ma; #ifdef CONFIG_EC_EC_COMM_BATTERY_CLIENT /* Wake up charger task to allocate current between lid and base. */ diff --git a/include/charge_manager.h b/include/charge_manager.h index cb6591df3b..2cded28295 100644 --- a/include/charge_manager.h +++ b/include/charge_manager.h @@ -231,6 +231,15 @@ enum charge_supplier charge_manager_get_supplier(void); */ int charge_manager_get_vbus_voltage(int port); +/** + * Get the current limit of CHARGE_PD_SUPPLIER. + * + * @return The CHARGE_SUPPLIER_PD current limit in mA or + * CHARGE_CURRENT_UNINITIALIZED if the supplier is not + * CHARGE_SUPPLIER_PD. + */ +int charge_manager_get_pd_current_uncapped(void); + #ifdef CONFIG_USB_PD_LOGGING /* Save power state log entry for the given port */ void charge_manager_save_log(int port); |