Odd 'unable to find transceiver' messages from USB with v3.13-3260-g03d11a0 and later

Message ID 20140124190831.GA6449@saruman.home
State New
Headers show

Commit Message

Felipe Balbi Jan. 24, 2014, 7:08 p.m.
Hi,

On Fri, Jan 24, 2014 at 08:47:07AM -0500, Josh Boyer wrote:
> We've had a report [1] of the USB layer throwing out 'unable to find
> transceiver' messages during boot with the 3.14 merge window kernels.
> I've seen this on my personal machine as well and included the dmesg
> section below.  This does not happen with the 3.13 kernel.
> 
> There are only a handful of files in git that have that error, but I
> haven't seen anything that immediately strikes me as causing this.
> From the dmesg output it looks like it is spit out right before a host
> controller is registered?  USB seems to be still working OK in my
> minimal testing, so the error message is confusing.
> 
> Thoughts?

looks like it was caused because of this commit:

commit 1ae5799ef63176cc75ec10e545cb65f620a82747
Author: Valentine Barshak <valentine.barshak@cogentembedded.com>
Date:   Wed Dec 4 01:42:22 2013 +0400

    usb: hcd: Initialize USB phy if needed
    
    This adds external USB phy support to USB HCD driver that
    allows to find and initialize external USB phy, bound to
    the HCD, when the HCD is added.
    The usb_add_hcd function returns -EPROBE_DEFER if the USB
    phy, bound to the HCD, is not ready.
    If no USB phy is bound, the HCD is initialized as usual.
    
    Signed-off-by: Valentine Barshak <valentine.barshak@cogentembedded.com>
    Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>


usb_get_phy_device() will pr_err() when a PHY isn't found. Looks like
that should be pr_debug() since everything still works even without a
PHY.

Patch

diff --git a/drivers/usb/core/hcd.c b/drivers/usb/core/hcd.c
index 7527c8e..d3a9bcd 100644
--- a/drivers/usb/core/hcd.c
+++ b/drivers/usb/core/hcd.c
@@ -2589,6 +2589,24 @@  int usb_add_hcd(struct usb_hcd *hcd,
 	int retval;
 	struct usb_device *rhdev;
 
+	if (IS_ENABLED(CONFIG_USB_PHY) && !hcd->phy) {
+		struct usb_phy *phy = usb_get_phy_dev(hcd->self.controller, 0);
+
+		if (IS_ERR(phy)) {
+			retval = PTR_ERR(phy);
+			if (retval == -EPROBE_DEFER)
+				return retval;
+		} else {
+			retval = usb_phy_init(phy);
+			if (retval) {
+				usb_put_phy(phy);
+				return retval;
+			}
+			hcd->phy = phy;
+			hcd->remove_phy = 1;
+		}
+	}
+
 	dev_info(hcd->self.controller, "%s\n", hcd->product_desc);
 
 	/* Keep old behaviour if authorized_default is not in [0, 1]. */