diff --git a/drivers/usb/dwc3/dwc3-msm.c b/drivers/usb/dwc3/dwc3-msm.c index 5d53a2142680..e0122b85ab6a 100644 --- a/drivers/usb/dwc3/dwc3-msm.c +++ b/drivers/usb/dwc3/dwc3-msm.c @@ -484,6 +484,7 @@ struct dwc3_msm { struct usb_role_switch *role_switch; bool ss_release_called; + int orientation_override; }; #define USB_HSPHY_3P3_VOL_MIN 3050000 /* uV */ @@ -3070,9 +3071,11 @@ static int dwc3_msm_resume(struct dwc3_msm *mdwc) if (dwc->maximum_speed >= USB_SPEED_SUPER && mdwc->lpm_flags & MDWC3_SS_PHY_SUSPEND) { mdwc->ss_phy->flags &= ~(PHY_LANE_A | PHY_LANE_B); - if (mdwc->typec_orientation == ORIENTATION_CC1) + if (mdwc->orientation_override) + mdwc->ss_phy->flags |= mdwc->orientation_override; + else if (mdwc->typec_orientation == ORIENTATION_CC1) mdwc->ss_phy->flags |= PHY_LANE_A; - if (mdwc->typec_orientation == ORIENTATION_CC2) + else if (mdwc->typec_orientation == ORIENTATION_CC2) mdwc->ss_phy->flags |= PHY_LANE_B; usb_phy_set_suspend(mdwc->ss_phy, 0); mdwc->ss_phy->flags &= ~DEVICE_IN_SS_MODE; @@ -3744,6 +3747,36 @@ static struct usb_role_switch_desc role_desc = { .allow_userspace_control = true, }; +static ssize_t orientation_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct dwc3_msm *mdwc = dev_get_drvdata(dev); + + if (mdwc->orientation_override == PHY_LANE_A) + return scnprintf(buf, PAGE_SIZE, "A\n"); + if (mdwc->orientation_override == PHY_LANE_B) + return scnprintf(buf, PAGE_SIZE, "B\n"); + + return scnprintf(buf, PAGE_SIZE, "none\n"); +} + +static ssize_t orientation_store(struct device *dev, + struct device_attribute *attr, const char *buf, size_t count) +{ + struct dwc3_msm *mdwc = dev_get_drvdata(dev); + + if (sysfs_streq(buf, "A")) + mdwc->orientation_override = PHY_LANE_A; + else if (sysfs_streq(buf, "B")) + mdwc->orientation_override = PHY_LANE_B; + else + mdwc->orientation_override = ORIENTATION_NONE; + + return count; +} + +static DEVICE_ATTR_RW(orientation); + static ssize_t mode_show(struct device *dev, struct device_attribute *attr, char *buf) { @@ -4392,6 +4425,7 @@ static int dwc3_msm_probe(struct platform_device *pdev) dwc3_ext_event_notify(mdwc); } + device_create_file(&pdev->dev, &dev_attr_orientation); device_create_file(&pdev->dev, &dev_attr_mode); device_create_file(&pdev->dev, &dev_attr_speed); device_create_file(&pdev->dev, &dev_attr_bus_vote);