summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAyushee <ayushee.shah@intel.com>2020-10-08 16:31:53 -0700
committerCommit Bot <commit-bot@chromium.org>2020-10-14 20:33:13 +0000
commite4c3ec56c5002ce4ed425495eaa50379d9eb3b96 (patch)
tree153bc7d0ea9f2b688e6b38b9c23c04d8b93fc324
parent913b68e8e43d5700e3432148b33428e1e1ce0d79 (diff)
downloadchrome-ec-e4c3ec56c5002ce4ed425495eaa50379d9eb3b96.tar.gz
TCPMv2: Avoid alt mode files from changing DPM states
USB4 mode: Added a function to check if the USB4 entry is completed Thunderbolt mode: Added 2 flags TBT_RETRY_DONE, TBT_EXIT_DONE to track the Thunderbolt mode's exit and if retry is needed and a new function to check if if the Thunderbolt mode entry is completed DisplayPort mode: Added a function to check if the DisplayPort entry is completed BUG=b:169169804 BRANCH=None TEST=1. Able to enter alternate mode on hotplug and reboot 2. Able to exit the alternate mode on chipset transition and on DPM's exit mode request. Change-Id: I09662449143ad8d94b30ae102ed5ce79db852687 Signed-off-by: Ayushee <ayushee.shah@intel.com> Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/platform/ec/+/2421425 Reviewed-by: Abe Levkoy <alevkoy@chromium.org>
-rw-r--r--common/mock/usb_pd_dpm_mock.c4
-rw-r--r--common/usbc/dp_alt_mode.c9
-rw-r--r--common/usbc/tbt_alt_mode.c53
-rw-r--r--common/usbc/usb_mode.c8
-rw-r--r--common/usbc/usb_pd_dpm.c12
-rw-r--r--include/usb_dp_alt_mode.h10
-rw-r--r--include/usb_mode.h9
-rw-r--r--include/usb_pd_dpm.h8
-rw-r--r--include/usb_tbt_alt_mode.h16
9 files changed, 87 insertions, 42 deletions
diff --git a/common/mock/usb_pd_dpm_mock.c b/common/mock/usb_pd_dpm_mock.c
index 344d53576d..bf1f191c07 100644
--- a/common/mock/usb_pd_dpm_mock.c
+++ b/common/mock/usb_pd_dpm_mock.c
@@ -36,10 +36,6 @@ void dpm_vdm_naked(int port, enum tcpm_transmit_type type, uint16_t svid,
{
}
-void dpm_set_mode_entry_done(int port)
-{
-}
-
void dpm_set_mode_exit_request(int port)
{
}
diff --git a/common/usbc/dp_alt_mode.c b/common/usbc/dp_alt_mode.c
index cd5eec1650..b53c448a8a 100644
--- a/common/usbc/dp_alt_mode.c
+++ b/common/usbc/dp_alt_mode.c
@@ -15,7 +15,6 @@
#include "usb_common.h"
#include "usb_dp_alt_mode.h"
#include "usb_pd.h"
-#include "usb_pd_dpm.h"
#include "usb_pd_tcpm.h"
#ifdef CONFIG_COMMON_RUNTIME
@@ -62,11 +61,16 @@ void dp_init(int port)
dp_state[port] = DP_START;
}
+bool dp_entry_is_done(int port)
+{
+ return dp_state[port] == DP_ACTIVE ||
+ dp_state[port] == DP_INACTIVE;
+}
+
static void dp_entry_failed(int port)
{
CPRINTS("C%d: DP alt mode protocol failed!", port);
dp_state[port] = DP_INACTIVE;
- dpm_set_mode_entry_done(port);
}
static bool dp_response_valid(int port, enum tcpm_transmit_type type,
@@ -116,7 +120,6 @@ void dp_vdm_acked(int port, enum tcpm_transmit_type type, int vdo_count,
case DP_STATUS_ACKED:
if (modep && modep->opos && modep->fx->post_config)
modep->fx->post_config(port);
- dpm_set_mode_entry_done(port);
dp_state[port] = DP_ACTIVE;
CPRINTS("C%d: Entered DP mode", port);
break;
diff --git a/common/usbc/tbt_alt_mode.c b/common/usbc/tbt_alt_mode.c
index 4e65e7eff7..1319263e74 100644
--- a/common/usbc/tbt_alt_mode.c
+++ b/common/usbc/tbt_alt_mode.c
@@ -8,6 +8,7 @@
* Refer to USB Type-C Cable and Connector Specification Release 2.0 Section F
*/
+#include "atomic.h"
#include <stdbool.h>
#include <stdint.h>
#include "compile_time_macros.h"
@@ -16,7 +17,6 @@
#include "usb_common.h"
#include "usb_mux.h"
#include "usb_pd.h"
-#include "usb_pd_dpm.h"
#include "usb_pd_tbt.h"
#include "usb_pe_sm.h"
#include "usb_tbt_alt_mode.h"
@@ -69,9 +69,14 @@
* with a partner. It may be fixed in b/159495742, in which case this
* logic is unneeded.
*/
-/* TODO:b/169169804 :Add entry, exit and retry flags for individual port */
-static bool retry_done;
-static bool exit_request;
+#define TBT_FLAG_RETRY_DONE BIT(0)
+#define TBT_FLAG_EXIT_DONE BIT(1)
+
+static uint8_t tbt_flags[CONFIG_USB_PD_PORT_MAX_COUNT];
+
+#define TBT_SET_FLAG(port, flag) (tbt_flags[port] |= (flag))
+#define TBT_CLR_FLAG(port, flag) (tbt_flags[port] &= (~flag))
+#define TBT_CHK_FLAG(port, flag) (tbt_flags[port] & (flag))
static int tbt_prints(const char *string, int port)
{
@@ -108,7 +113,8 @@ static const uint8_t state_vdm_cmd[TBT_STATE_COUNT] = {
void tbt_init(int port)
{
tbt_state[port] = TBT_START;
- retry_done = false;
+ TBT_CLR_FLAG(port, TBT_FLAG_RETRY_DONE);
+ TBT_SET_FLAG(port, TBT_FLAG_EXIT_DONE);
}
bool tbt_is_active(int port)
@@ -117,24 +123,30 @@ bool tbt_is_active(int port)
tbt_state[port] != TBT_START;
}
+bool tbt_entry_is_done(int port)
+{
+ return tbt_state[port] == TBT_ACTIVE ||
+ tbt_state[port] == TBT_INACTIVE;
+}
+
static void tbt_exit_done(int port)
{
tbt_state[port] = TBT_INACTIVE;
+ TBT_CLR_FLAG(port, TBT_FLAG_RETRY_DONE);
- if (exit_request) {
+ if (!TBT_CHK_FLAG(port, TBT_FLAG_EXIT_DONE)) {
+ TBT_SET_FLAG(port, TBT_FLAG_EXIT_DONE);
tbt_prints("Exited alternate mode", port);
return;
}
- retry_done = false;
tbt_prints("alt mode protocol failed!", port);
- dpm_set_mode_entry_done(port);
}
-void tbt_exit_mode_request(void)
+void tbt_exit_mode_request(int port)
{
- retry_done = true;
- exit_request = true;
+ TBT_SET_FLAG(port, TBT_FLAG_RETRY_DONE);
+ TBT_CLR_FLAG(port, TBT_FLAG_EXIT_DONE);
}
static bool tbt_response_valid(int port, enum tcpm_transmit_type type,
@@ -161,7 +173,7 @@ static bool tbt_response_valid(int port, enum tcpm_transmit_type type,
static void tbt_retry_enter_mode(int port)
{
tbt_state[port] = TBT_START;
- retry_done = true;
+ TBT_SET_FLAG(port, TBT_FLAG_RETRY_DONE);
}
/* Send Exit Mode to SOP''(if supported), or SOP' */
@@ -201,10 +213,9 @@ void intel_vdm_acked(int port, enum tcpm_transmit_type type, int vdo_count,
break;
case TBT_ENTER_SOP:
set_tbt_compat_mode_ready(port);
- dpm_set_mode_entry_done(port);
tbt_state[port] = TBT_ACTIVE;
- retry_done = true;
tbt_prints("enter mode SOP", port);
+ TBT_SET_FLAG(port, TBT_FLAG_RETRY_DONE);
break;
case TBT_ACTIVE:
tbt_prints("exit mode SOP", port);
@@ -219,7 +230,7 @@ void intel_vdm_acked(int port, enum tcpm_transmit_type type, int vdo_count,
/*
* Exit Mode process is complete; go to inactive state.
*/
- retry_done = false;
+ TBT_CLR_FLAG(port, TBT_FLAG_RETRY_DONE);
}
break;
case TBT_EXIT_SOP:
@@ -227,7 +238,7 @@ void intel_vdm_acked(int port, enum tcpm_transmit_type type, int vdo_count,
if (get_usb_pd_cable_type(port) == IDH_PTYPE_ACABLE)
tbt_active_cable_exit_mode(port);
else {
- if (retry_done)
+ if (TBT_CHK_FLAG(port, TBT_FLAG_RETRY_DONE))
/* retried enter mode, still failed, give up */
tbt_exit_done(port);
else
@@ -241,7 +252,7 @@ void intel_vdm_acked(int port, enum tcpm_transmit_type type, int vdo_count,
break;
case TBT_EXIT_SOP_PRIME:
tbt_prints("exit mode SOP'", port);
- if (retry_done) {
+ if (TBT_CHK_FLAG(port, TBT_FLAG_RETRY_DONE)) {
/*
* Exit mode process is complete; go to inactive state.
*/
@@ -299,7 +310,7 @@ void intel_vdm_naked(int port, enum tcpm_transmit_type type, uint8_t vdm_cmd)
else {
tbt_prints("exit mode SOP failed", port);
tbt_state[port] = TBT_INACTIVE;
- retry_done = false;
+ TBT_CLR_FLAG(port, TBT_FLAG_RETRY_DONE);
}
break;
case TBT_EXIT_SOP:
@@ -308,7 +319,7 @@ void intel_vdm_naked(int port, enum tcpm_transmit_type type, uint8_t vdm_cmd)
if (get_usb_pd_cable_type(port) == IDH_PTYPE_ACABLE)
tbt_active_cable_exit_mode(port);
else {
- if (retry_done)
+ if (TBT_CHK_FLAG(port, TBT_FLAG_RETRY_DONE))
/* Retried enter mode, still failed, give up */
tbt_exit_done(port);
else
@@ -322,7 +333,7 @@ void intel_vdm_naked(int port, enum tcpm_transmit_type type, uint8_t vdm_cmd)
break;
case TBT_EXIT_SOP_PRIME:
set_usb_mux_with_current_data_role(port);
- if (retry_done) {
+ if (TBT_CHK_FLAG(port, TBT_FLAG_RETRY_DONE)) {
/*
* Exit mode process is complete; go to inactive state.
*/
@@ -381,7 +392,7 @@ int tbt_setup_next_vdm(int port, int vdo_count, uint32_t *vdm,
if (!tbt_mode_is_supported(port, vdo_count))
return 0;
- if (!retry_done)
+ if (!TBT_CHK_FLAG(port, TBT_FLAG_RETRY_DONE))
tbt_prints("attempt to enter mode", port);
else
tbt_prints("retry to enter mode", port);
diff --git a/common/usbc/usb_mode.c b/common/usbc/usb_mode.c
index fcbb58cd6f..c48002f0d1 100644
--- a/common/usbc/usb_mode.c
+++ b/common/usbc/usb_mode.c
@@ -50,6 +50,12 @@ static void usb4_debug_prints(int port, enum usb4_mode_status usb4_status)
usb4_status);
}
+bool enter_usb_entry_is_done(int port)
+{
+ return usb4_state[port] == USB4_ACTIVE ||
+ usb4_state[port] == USB4_INACTIVE;
+}
+
void enter_usb_init(int port)
{
usb4_state[port] = USB4_ENTER_SOP;
@@ -110,8 +116,6 @@ void enter_usb_accepted(int port, enum tcpm_transmit_type type)
if (IS_ENABLED(CONFIG_USBC_PPC_SBU))
ppc_set_sbu(port, 1);
- dpm_set_mode_entry_done(port);
-
usb4_state[port] = USB4_ACTIVE;
/* Set usb mux to USB4 mode */
diff --git a/common/usbc/usb_pd_dpm.c b/common/usbc/usb_pd_dpm.c
index 5e65873e31..e6224efff5 100644
--- a/common/usbc/usb_pd_dpm.c
+++ b/common/usbc/usb_pd_dpm.c
@@ -37,7 +37,7 @@ void dpm_init(int port)
dpm[port].mode_exit_request = false;
}
-void dpm_set_mode_entry_done(int port)
+static void dpm_set_mode_entry_done(int port)
{
dpm[port].mode_entry_done = true;
}
@@ -122,6 +122,14 @@ static void dpm_attempt_mode_entry(int port)
pd_get_modes_discovery(port, TCPC_TX_SOP) != PD_DISC_COMPLETE)
return;
+ if (dp_entry_is_done(port) ||
+ (IS_ENABLED(CONFIG_USB_PD_TBT_COMPAT_MODE) &&
+ tbt_entry_is_done(port)) ||
+ (IS_ENABLED(CONFIG_USB_PD_USB4) && enter_usb_entry_is_done(port))) {
+ dpm_set_mode_entry_done(port);
+ return;
+ }
+
/* Check if the device and cable support USB4. */
if (IS_ENABLED(CONFIG_USB_PD_USB4) && enter_usb_is_capable(port)) {
pd_dpm_request(port, DPM_REQUEST_ENTER_USB);
@@ -178,7 +186,7 @@ static void dpm_attempt_mode_exit(int port)
if (IS_ENABLED(CONFIG_USB_PD_TBT_COMPAT_MODE) &&
tbt_is_active(port)) {
CPRINTS("C%d: TBT teardown", port);
- tbt_exit_mode_request();
+ tbt_exit_mode_request(port);
vdo_count = tbt_setup_next_vdm(port, VDO_MAX_SIZE, &vdm,
&tx_type);
} else if (dp_is_active(port)) {
diff --git a/include/usb_dp_alt_mode.h b/include/usb_dp_alt_mode.h
index 5a063e63a2..273ac9b25f 100644
--- a/include/usb_dp_alt_mode.h
+++ b/include/usb_dp_alt_mode.h
@@ -33,6 +33,16 @@ void dp_init(int port);
bool dp_is_active(int port);
/*
+ * Checks weather the mode entry sequence for DisplayPort alternate mode is
+ * done for a port.
+ *
+ * @param port USB-C port number
+ * @return True if entry sequence for DisplayPort mode is completed
+ * False otherwise
+ */
+bool dp_entry_is_done(int port);
+
+/*
* Handles received DisplayPort VDM ACKs.
*
* @param port USB-C port number
diff --git a/include/usb_mode.h b/include/usb_mode.h
index a479c36d5c..7c125e1406 100644
--- a/include/usb_mode.h
+++ b/include/usb_mode.h
@@ -24,6 +24,15 @@
void enter_usb_init(int port);
/*
+ * Checks weather the mode entry sequence for USB4 is done for a port.
+ *
+ * @param port USB-C port number
+ * @return True if entry sequence for USB4 is completed
+ * False otherwise
+ */
+bool enter_usb_entry_is_done(int port);
+
+/*
* Resets USB4 state and mux state.
*
* @param port USB-C port number
diff --git a/include/usb_pd_dpm.h b/include/usb_pd_dpm.h
index 2948fd3fbd..d1c029bc03 100644
--- a/include/usb_pd_dpm.h
+++ b/include/usb_pd_dpm.h
@@ -19,14 +19,6 @@
void dpm_init(int port);
/*
- * Informs the DPM that the mode entry sequence (including appropriate
- * configuration) is done for a port.
- *
- * @param port USB-C port number
- */
-void dpm_set_mode_entry_done(int port);
-
-/*
* Informs the DPM that Exit Mode request is received
*
* @param port USB-C port number
diff --git a/include/usb_tbt_alt_mode.h b/include/usb_tbt_alt_mode.h
index 11ad95f673..73a776e3dc 100644
--- a/include/usb_tbt_alt_mode.h
+++ b/include/usb_tbt_alt_mode.h
@@ -23,9 +23,21 @@
void tbt_init(int port);
/*
- * Sets exit_mode and retry_done bits to true
+ * Requests to exit the Thunderbolt alternate mode
+ *
+ * @param port USB-C port number
+ */
+void tbt_exit_mode_request(int port);
+
+/*
+ * Checks whether the mode entry sequence for Thunderbolt alternate mode is
+ * done for a port.
+ *
+ * @param port USB-C port number
+ * @return True if entry sequence for Thunderbolt mode is completed
+ * False otherwise
*/
-void tbt_exit_mode_request(void);
+bool tbt_entry_is_done(int port);
/*
* Returns True if Thunderbolt mode is not in inactive state