diff options
author | Daisuke Nojiri <dnojiri@chromium.org> | 2017-05-09 16:35:48 -0700 |
---|---|---|
committer | chrome-bot <chrome-bot@chromium.org> | 2017-05-11 17:15:47 -0700 |
commit | bb1b65a17754e7e38d52720db3ad68e95e5d905e (patch) | |
tree | cad45b0b21308ce48fcecd781551264d7dea2d39 | |
parent | 1c929523a2f8077c25cf650ddff983aea4e8ef10 (diff) | |
download | chrome-ec-bb1b65a17754e7e38d52720db3ad68e95e5d905e.tar.gz |
charger: Add dedicated (non-type-c) charger
This patch adds a dedicated charge port. The number of such ports
is specified by CONFIG_DEDICATED_CHARGE_PORT_COUNT. It works as a
sink only. The total number of charge ports is represented by
CHARGE_PORT_COUNT.
BUG=chromium:721383
BRANCH=none
TEST=make buildall. Boot Fizz off of barrel jack.
Change-Id: Ibbb11f3e1c66e35b5abe190e49161eeaa2009994
Signed-off-by: Daisuke Nojiri <dnojiri@chromium.org>
Reviewed-on: https://chromium-review.googlesource.com/501468
Reviewed-by: Vincent Palatin <vpalatin@chromium.org>
-rw-r--r-- | board/kevin/board.h | 1 | ||||
-rw-r--r-- | common/charge_manager.c | 81 | ||||
-rw-r--r-- | include/charge_manager.h | 3 | ||||
-rw-r--r-- | include/config.h | 3 |
4 files changed, 57 insertions, 31 deletions
diff --git a/board/kevin/board.h b/board/kevin/board.h index 28a54b5f65..8a9a5e5611 100644 --- a/board/kevin/board.h +++ b/board/kevin/board.h @@ -189,6 +189,7 @@ #undef CONFIG_CMD_CHARGER_PSYS #undef CONFIG_CMD_FLASH #undef CONFIG_CMD_HASH +#undef CONFIG_CMD_HCDEBUG #undef CONFIG_CMD_I2C_SCAN #undef CONFIG_CMD_MD #undef CONFIG_CMD_MMAPINFO diff --git a/common/charge_manager.c b/common/charge_manager.c index 908d82281c..7b119da347 100644 --- a/common/charge_manager.c +++ b/common/charge_manager.c @@ -43,10 +43,10 @@ BUILD_ASSERT(ARRAY_SIZE(supplier_priority) == CHARGE_SUPPLIER_COUNT); /* Keep track of available charge for each charge port. */ static struct charge_port_info available_charge[CHARGE_SUPPLIER_COUNT] - [CONFIG_USB_PD_PORT_COUNT]; + [CHARGE_PORT_COUNT]; /* Keep track of when the supplier on each port is registered. */ -static timestamp_t registration_time[CONFIG_USB_PD_PORT_COUNT]; +static timestamp_t registration_time[CHARGE_PORT_COUNT]; /* * Charge current ceiling (mA) for ports. This can be set to temporarily limit @@ -54,14 +54,14 @@ static timestamp_t registration_time[CONFIG_USB_PD_PORT_COUNT]; * The ceiling can be set independently from several requestors, with the * minimum ceiling taking effect. */ -static int charge_ceil[CONFIG_USB_PD_PORT_COUNT][CEIL_REQUESTOR_COUNT]; +static int charge_ceil[CHARGE_PORT_COUNT][CEIL_REQUESTOR_COUNT]; /* Dual-role capability of attached partner port */ -static enum dualrole_capabilities dualrole_capability[CONFIG_USB_PD_PORT_COUNT]; +static enum dualrole_capabilities dualrole_capability[CHARGE_PORT_COUNT]; #ifdef CONFIG_USB_PD_LOGGING /* Mark port as dirty when making changes, for later logging */ -static int save_log[CONFIG_USB_PD_PORT_COUNT]; +static int save_log[CHARGE_PORT_COUNT]; #endif /* Store current state of port enable / charge current. */ @@ -85,6 +85,29 @@ enum charge_manager_change_type { CHANGE_DUALROLE, }; +static int is_pd_port(int port) +{ + return 0 <= port && port < CONFIG_USB_PD_PORT_COUNT; +} + +static int is_sink(int port) +{ + if (!is_pd_port(port)) + /* Dedicated port is sink-only */ + return 1; + return pd_get_role(port) == PD_ROLE_SINK; +} + +#ifndef TEST_BUILD +static int is_connected(int port) +{ + if (!is_pd_port(port)) + /* Dedicated port is always connected */ + return 1; + return pd_is_connected(port); +} +#endif + /** * In certain cases we need to override the default behavior of not charging * from non-dedicated chargers. If the system is in RO and locked, we have no @@ -117,7 +140,7 @@ static void charge_manager_init(void) int i, j; int spoof_capability = charge_manager_spoof_dualrole_capability(); - for (i = 0; i < CONFIG_USB_PD_PORT_COUNT; ++i) { + for (i = 0; i < CHARGE_PORT_COUNT; ++i) { for (j = 0; j < CHARGE_SUPPLIER_COUNT; ++j) { available_charge[j][i].current = CHARGE_CURRENT_UNINITIALIZED; @@ -126,9 +149,10 @@ static void charge_manager_init(void) } for (j = 0; j < CEIL_REQUESTOR_COUNT; ++j) charge_ceil[i][j] = CHARGE_CEIL_NONE; - dualrole_capability[i] = spoof_capability ? CAP_DEDICATED : - CAP_UNKNOWN; - source_port_last_rp[i] = CONFIG_USB_PD_PULLUP; + if (spoof_capability || !is_pd_port(i)) + dualrole_capability[i] = CAP_DEDICATED; + if (is_pd_port(i)) + source_port_last_rp[i] = CONFIG_USB_PD_PULLUP; } } DECLARE_HOOK(HOOK_INIT, charge_manager_init, HOOK_PRIO_CHARGE_MANAGER_INIT); @@ -149,7 +173,7 @@ static int charge_manager_is_seeded(void) return 1; for (i = 0; i < CHARGE_SUPPLIER_COUNT; ++i) - for (j = 0; j < CONFIG_USB_PD_PORT_COUNT; ++j) + for (j = 0; j < CHARGE_PORT_COUNT; ++j) if (available_charge[i][j].current == CHARGE_CURRENT_UNINITIALIZED || available_charge[i][j].voltage == @@ -169,6 +193,8 @@ static int charge_manager_is_seeded(void) */ static int charge_manager_get_source_current(int port) { + ASSERT(is_pd_port(port)); + switch (source_port_last_rp[port]) { case TYPEC_RP_3A0: return 3000; @@ -206,14 +232,13 @@ static void charge_manager_fill_power_info(int port, (supplier_priority[i] == supplier_priority[sup] && POWER(available_charge[i][port]) > - POWER(available_charge[sup] - [port])))) + POWER(available_charge[sup][port])))) sup = i; /* Fill in power role */ if (charge_port == port) r->role = USB_PD_PORT_POWER_SINK; - else if (pd_is_connected(port) && pd_get_role(port) == PD_ROLE_SOURCE) + else if (is_connected(port) && !is_sink(port)) r->role = USB_PD_PORT_POWER_SOURCE; else if (sup != CHARGE_SUPPLIER_NONE) r->role = USB_PD_PORT_POWER_SINK_NOT_CHARGING; @@ -337,7 +362,7 @@ void charge_manager_save_log(int port) uint16_t flags = 0; struct ec_response_usb_pd_power_info pinfo; - if (port < 0 || port >= CONFIG_USB_PD_PORT_COUNT) + if (!is_pd_port(port)) return; save_log[port] = 0; @@ -364,12 +389,11 @@ void charge_manager_save_log(int port) */ static void charge_manager_switch_to_source(int port) { - if (port < 0 || port >= CONFIG_USB_PD_PORT_COUNT) + if (!is_pd_port(port)) return; /* If connected to dual-role device, then ask for a swap */ - if (dualrole_capability[port] == CAP_DUALROLE && - pd_get_role(port) == PD_ROLE_SINK) + if (dualrole_capability[port] == CAP_DUALROLE && is_sink(port)) pd_request_power_swap(port); } @@ -422,7 +446,7 @@ static void charge_manager_get_best_charge_port(int *new_port, * so make no assumptions about its consistency. */ for (i = 0; i < CHARGE_SUPPLIER_COUNT; ++i) - for (j = 0; j < CONFIG_USB_PD_PORT_COUNT; ++j) { + for (j = 0; j < CHARGE_PORT_COUNT; ++j) { /* * Skip this supplier if there is no * available charge. @@ -646,9 +670,9 @@ static void charge_manager_refresh(void) #endif /* New power requests must be set only after updating the globals. */ - if (updated_new_port != CHARGE_PORT_NONE) + if (is_pd_port(updated_new_port)) pd_set_new_power_request(updated_new_port); - if (updated_old_port != CHARGE_PORT_NONE) + if (is_pd_port(updated_old_port)) pd_set_new_power_request(updated_old_port); if (power_changed) @@ -769,7 +793,7 @@ static void charge_manager_make_change(enum charge_manager_change_type change, * the deadline, make it our override port. */ if (port == delayed_override_port && charge->current > 0 && - pd_get_role(delayed_override_port) == PD_ROLE_SINK && + is_sink(delayed_override_port) && get_time().val < delayed_override_deadline.val) { delayed_override_port = OVERRIDE_OFF; hook_call_deferred(&charge_override_timeout_data, -1); @@ -796,7 +820,6 @@ void charge_manager_update_charge(int supplier, void charge_manager_update_dualrole(int port, enum dualrole_capabilities cap) { - if (charge_manager_spoof_dualrole_capability()) cap = CAP_DEDICATED; @@ -818,8 +841,6 @@ void charge_manager_set_ceil(int port, enum ceil_requestor requestor, int ceil) void charge_manager_force_ceil(int port, int ceil) { - ASSERT(port >= 0 && port < CONFIG_USB_PD_PORT_COUNT); - /* * Force our input current to ceil if we're exceeding it, without * waiting for our deferred task to run. @@ -852,7 +873,7 @@ int charge_manager_set_override(int port) return EC_ERROR_BUSY; /* Set the override port if it's a sink. */ - if (port < 0 || pd_get_role(port) == PD_ROLE_SINK) { + if (port < 0 || is_sink(port)) { if (override_port != port) { override_port = port; if (charge_manager_is_seeded()) @@ -864,8 +885,7 @@ int charge_manager_set_override(int port) * If the attached device is capable of being a sink, request a * power swap and set the delayed override for swap completion. */ - else if (pd_get_role(port) != PD_ROLE_SINK && - dualrole_capability[port] == CAP_DUALROLE) { + else if (!is_sink(port) && dualrole_capability[port] == CAP_DUALROLE) { delayed_override_deadline.val = get_time().val + POWER_SWAP_TIMEOUT; delayed_override_port = port; @@ -933,8 +953,7 @@ void charge_manager_source_port(int port, int enable) source_port_last_rp[p] = rp; #ifdef CONFIG_USB_PD_LOGGING - if (pd_is_connected(p) && - pd_get_role(p) == PD_ROLE_SOURCE) + if (is_connected(p) && !is_sink(p)) charge_manager_save_log(p); #endif @@ -988,7 +1007,7 @@ static int hc_charge_port_override(struct host_cmd_handler_args *args) const int16_t override_port = p->override_port; if (override_port < OVERRIDE_DONT_CHARGE || - override_port >= CONFIG_USB_PD_PORT_COUNT) + override_port >= CHARGE_PORT_COUNT) return EC_RES_INVALID_PARAM; return charge_manager_set_override(override_port) == EC_SUCCESS ? @@ -1007,7 +1026,7 @@ static int command_charge_port_override(int argc, char **argv) if (argc >= 2) { port = strtoi(argv[1], &e, 0); if (*e || port < OVERRIDE_DONT_CHARGE || - port >= CONFIG_USB_PD_PORT_COUNT) + port >= CHARGE_PORT_COUNT) return EC_ERROR_PARAM1; ret = charge_manager_set_override(port); } diff --git a/include/charge_manager.h b/include/charge_manager.h index 64c8272886..2137899a13 100644 --- a/include/charge_manager.h +++ b/include/charge_manager.h @@ -81,6 +81,9 @@ enum ceil_requestor { CEIL_REQUESTOR_COUNT, }; +#define CHARGE_PORT_COUNT \ + (CONFIG_USB_PD_PORT_COUNT + CONFIG_DEDICATED_CHARGE_PORT_COUNT) + /** * Update charge ceiling for a given port. The ceiling can be set independently * for several requestors, and the min. ceil will be enforced. diff --git a/include/config.h b/include/config.h index 8ecabb0809..9248b5185c 100644 --- a/include/config.h +++ b/include/config.h @@ -385,6 +385,9 @@ /* Compile charge manager */ #undef CONFIG_CHARGE_MANAGER +/* Number of charge ports excluding type-c ports */ +#define CONFIG_DEDICATED_CHARGE_PORT_COUNT 0 + /* Allow charge manager to default to charging from dual-role partners */ #undef CONFIG_CHARGE_MANAGER_DRP_CHARGING |