summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKyle Tso <kyletso@google.com>2023-03-06 17:49:44 +0800
committerKyle Tso <kyletso@google.com>2023-03-07 15:11:09 +0800
commitd33c526a0a4c9b669fa2fecbba865a34bec091df (patch)
tree5814628522497ed63507155e99153eaf67ffd7e5
parentb20ffdf4e53099d9348444a9247ac42786652e28 (diff)
downloadtangorpro-d33c526a0a4c9b669fa2fecbba865a34bec091df.tar.gz
pogo_transport: Update the orientation before enabling USB Data
There is a possibility that when doing the phy restart due to orientation change, the USB phy is being turned on so that the memory access causes Asychronous SError Interrupt. Fix this by moving the orientation updating to a dedicated function and call it prior to the enabling of the USB phy. Also remove the phy restart during switch_to_usbc_locked as the updated orientation will be adopted in the phy in enable_data_path_locked automatically. Bug: 271689070 Change-Id: I68d95a3f0b0e200bb6503c073ebe708a2102502e Signed-off-by: Kyle Tso <kyletso@google.com> (cherry picked from commit bb175cd05c76ba1951ed2c257b110c1d425baeb4)
-rw-r--r--pogo/pogo_transport.c71
1 files changed, 42 insertions, 29 deletions
diff --git a/pogo/pogo_transport.c b/pogo/pogo_transport.c
index 86ce2da..ddd863e 100644
--- a/pogo/pogo_transport.c
+++ b/pogo/pogo_transport.c
@@ -225,6 +225,29 @@ static void ssphy_restart_control(struct pogo_transport *pogo_transport, bool en
gvotable_cast_long_vote(pogo_transport->ssphy_restart_votable, POGO_VOTER, enable, enable);
}
+/*
+ * Update the polarity to EXTCON_USB_HOST. If @sync is true, use the sync version to set the
+ * property.
+ */
+static void pogo_transport_update_polarity(struct pogo_transport *pogo_transport, int polarity,
+ bool sync)
+{
+ union extcon_property_value prop = {.intval = polarity};
+ struct max77759_plat *chip = pogo_transport->chip;
+ int ret;
+
+ if (sync)
+ ret = extcon_set_property_sync(chip->extcon, EXTCON_USB_HOST,
+ EXTCON_PROP_USB_TYPEC_POLARITY,
+ prop);
+ else
+ ret = extcon_set_property(chip->extcon, EXTCON_USB_HOST,
+ EXTCON_PROP_USB_TYPEC_POLARITY,
+ prop);
+ logbuffer_log(pogo_transport->log, "%sset polarity to %d sync %u", ret ? "failed to " : "",
+ prop.intval, sync);
+}
+
static void disable_and_bypass_hub(struct pogo_transport *pogo_transport)
{
int ret;
@@ -273,6 +296,15 @@ static void switch_to_usbc_locked(struct pogo_transport *pogo_transport)
logbuffer_log(pogo_transport->log, "POGO: data-mux:%d",
gpio_get_value(pogo_transport->pogo_data_mux_gpio));
data_alt_path_active(chip, false);
+
+ /*
+ * Calling extcon_set_state_sync to turn off the host resets the orientation of USB-C and
+ * the USB phy was also reset to the default value CC1.
+ * Update the orientation for superspeed phy if USB-C is connected and CC2 is active.
+ */
+ if (pogo_transport->polarity == TYPEC_POLARITY_CC2)
+ pogo_transport_update_polarity(pogo_transport, TYPEC_POLARITY_CC2, false);
+
enable_data_path_locked(chip);
}
@@ -363,6 +395,13 @@ static void switch_to_hub_locked(struct pogo_transport *pogo_transport)
/* wait for the host mode to be turned off completely */
mdelay(60);
+ /*
+ * The polarity was reset to 0 when Host Mode was disabled for USB-C or POGO. If current
+ * polarity is CC2, update it to ssphy before enabling the Host Mode for hub.
+ */
+ if (pogo_transport->polarity == TYPEC_POLARITY_CC2)
+ pogo_transport_update_polarity(pogo_transport, pogo_transport->polarity, false);
+
ret = extcon_set_state_sync(chip->extcon, EXTCON_USB_HOST, 1);
logbuffer_log(pogo_transport->log, "%s: %s turning on host for hub", __func__, ret < 0 ?
"Failed" : "Succeeded");
@@ -474,28 +513,8 @@ static void update_pogo_transport(struct pogo_transport *pogo_transport,
}
break;
case EVENT_MOVE_DATA_TO_USB:
- if (pogo_transport->pogo_usb_active) {
+ if (pogo_transport->pogo_usb_active)
switch_to_usbc_locked(pogo_transport);
-
- /*
- * During the function call "switch_to_usbc_locked", the USB controller
- * restarted and the orientation of the USB phy was reset to the default
- * value CC1 because Type-C drivers had no chance to update the real
- * orientation. Update and restart the superspeed phy if CC2 is connected.
- */
- if (pogo_transport->polarity == TYPEC_POLARITY_CC2) {
- union extcon_property_value prop;
- prop.intval = (int)TYPEC_POLARITY_CC2;
- ret = extcon_set_property_sync(chip->extcon, EXTCON_USB_HOST,
- EXTCON_PROP_USB_TYPEC_POLARITY,
- prop);
- if (ret)
- logbuffer_log(pogo_transport->log,
- "Failed to set polarity, ret %d", ret);
-
- ssphy_restart_control(pogo_transport, true);
- }
- }
break;
case EVENT_MOVE_DATA_TO_POGO:
/* Currently this event is bundled to force_pogo. This case is unreachable. */
@@ -657,14 +676,8 @@ static void update_pogo_transport(struct pogo_transport *pogo_transport,
case EVENT_ORIENTATION_CHANGED:
/* Update the orientation and restart the ssphy if hub is enabled */
if (pogo_transport->pogo_hub_active) {
- union extcon_property_value prop;
- prop.intval = (int)pogo_transport->polarity;
- ret = extcon_set_property_sync(chip->extcon, EXTCON_USB_HOST,
- EXTCON_PROP_USB_TYPEC_POLARITY, prop);
- if (ret)
- logbuffer_log(pogo_transport->log, "Failed to set polarity, ret %d",
- ret);
-
+ pogo_transport_update_polarity(pogo_transport, pogo_transport->polarity,
+ true);
ssphy_restart_control(pogo_transport, true);
}
break;