diff options
author | Diana Z <dzigterman@chromium.org> | 2019-05-31 15:36:37 -0600 |
---|---|---|
committer | Commit Bot <commit-bot@chromium.org> | 2019-08-18 03:26:53 +0000 |
commit | 5a3365d52885e8d37954442f0b8ea3268f6e2443 (patch) | |
tree | 05a87d0830d90a53caea5b37ade0c2a4c0d225d3 | |
parent | 3e2a2fd797fa61e7c8783c0cd03da56164a96932 (diff) | |
download | chrome-ec-5a3365d52885e8d37954442f0b8ea3268f6e2443.tar.gz |
USB PD: Only maintain contracts over sysjump when sinking
Currently, the pd_task will attempt to maintain both source and sink
contracts after an unlocked sysjump or unlocked EC reset. However, the
pd_task will disable Vbus to any partners it was sourcing, causing the
soft reset process to lead to a hard reset and disconnection.
Since the port partner will be without Vbus and unable to respond, treat
the contract as terminated and the port as the default state.
BUG=b:132110509
BRANCH=octopus
TEST=unlocked sysjumps with a display port dongle and hoho to ensure
they were treated as disconnected, unlocked sysjumps with charger to
ensure it was soft reset
Change-Id: Ie477f393ea828a4e880c8e8ccbe72539e8be721a
Signed-off-by: Diana Z <dzigterman@chromium.org>
Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/platform/ec/+/1639212
Reviewed-by: Jett Rink <jettrink@chromium.org>
Reviewed-by: Aseda Aboagye <aaboagye@chromium.org>
Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/platform/ec/+/1693156
Commit-Queue: Zhuohao Lee <zhuohao@chromium.org>
Tested-by: Zhuohao Lee <zhuohao@chromium.org>
-rw-r--r-- | common/usb_pd_protocol.c | 27 |
1 files changed, 18 insertions, 9 deletions
diff --git a/common/usb_pd_protocol.c b/common/usb_pd_protocol.c index f9c38d3c16..b49c63a043 100644 --- a/common/usb_pd_protocol.c +++ b/common/usb_pd_protocol.c @@ -2680,8 +2680,10 @@ void pd_task(void *u) * still be valid. */ if (pd_comm_is_enabled(port) && - (pd_get_saved_port_flags(port, &saved_flgs) == EC_SUCCESS)) { - if (saved_flgs & PD_BBRMFLG_EXPLICIT_CONTRACT) { + (pd_get_saved_port_flags(port, &saved_flgs) == EC_SUCCESS) && + (saved_flgs & PD_BBRMFLG_EXPLICIT_CONTRACT)) { + /* Only attempt to maintain previous sink contracts */ + if ((saved_flgs & PD_BBRMFLG_POWER_ROLE) == PD_ROLE_SINK) { pd_set_power_role(port, (saved_flgs & PD_BBRMFLG_POWER_ROLE) ? PD_ROLE_SOURCE : PD_ROLE_SINK); @@ -2705,16 +2707,23 @@ void pd_task(void *u) * alternate modes can work after reset. */ pd[port].flags |= PD_FLAGS_CHECK_IDENTITY; - + } else { /* - * Set the TCPC reset event such that we can set our CC - * terminations, determine polarity, and enable RX so we - * can hear back from our port partner. + * Vbus was turned off during the power supply reset + * earlier, so clear the contract flag and re-start as + * default role */ - task_set_event(task_get_current(), - PD_EVENT_TCPC_RESET, - 0); + pd_update_saved_port_flags(port, + PD_BBRMFLG_EXPLICIT_CONTRACT, 0); + } + /* + * Set the TCPC reset event such that we can set our CC + * terminations, determine polarity, and enable RX so we + * can hear back from our port partner if maintaining our old + * connection. + */ + task_set_event(task_get_current(), PD_EVENT_TCPC_RESET, 0); } #endif /* defined(CONFIG_USB_PD_DUAL_ROLE) */ /* Set the power role if we haven't already. */ |