Hi Jules, On 12/16/2020 20:59, Jules Maselbas wrote: > On probe the dwc2 driver tries two path to get an usb phy, first calling > devm_phy_get() and secondly with devm_usb_get_phy(). > > However the current implementation of devm_phy_get() never return a valid > phy for usb-nop-xceiv. And the current implementation of devm_usb_get_phy > only check for phy that's has already been registered. > > During boot, I see the dwc2 driver being probed before the usb-nop-xceiv > probe, this means that during the dwc2 probe the function devm_usb_get_phy > never finds the a phy (because it hasn't been registered yet) but never > cause the dwc2 probe to defer. > > I tried to follow what is done by dwc3_core_get_phy(): if the current > device has an of_node then try to get the usb_phy by phandle instead of > using devm_usb_get_phy(). This way when the probe order is not good the > devm_usb_get_phy_by_phandle() function will return -EPROBE_DEFER. > > Signed-off-by: Jules Maselbas <jmaselbas@xxxxxxxxx> > --- 8< --- > > A snippet of the device-tree source I am using: > &usb0 { > phys = <&usb_phy0>; > phy-names = "usb2-phy"; > }; > &usb_phy0 { > #phy-cells = <0>; > compatible = "usb-nop-xceiv"; > reset-gpios = <&gpio 0 GPIO_ACTIVE_LOW>; > }; > --- > drivers/usb/dwc2/platform.c | 7 ++++++- > 1 file changed, 6 insertions(+), 1 deletion(-) > > diff --git a/drivers/usb/dwc2/platform.c b/drivers/usb/dwc2/platform.c > index db9fd4bd1a38..b58ce996add7 100644 > --- a/drivers/usb/dwc2/platform.c > +++ b/drivers/usb/dwc2/platform.c > @@ -251,7 +251,12 @@ static int dwc2_lowlevel_hw_init(struct dwc2_hsotg *hsotg) > } > > if (!hsotg->phy) { > - hsotg->uphy = devm_usb_get_phy(hsotg->dev, USB_PHY_TYPE_USB2); > + if (hsotg->dev->of_node) > + i = of_property_match_string(hsotg->dev->of_node, "phy-names", "usb2-phy"); According the device tree you have provided the value of "i" will always be "0". > + if (hsotg->dev->of_node && i >= 0) > + hsotg->uphy = devm_usb_get_phy_by_phandle(hsotg->dev, "phys", i); Why do you use the value of "i" while in "<&usb_phy0>" you have only one phy. If you had several phy-names and the value of "i" gets more than 0, then based on your usb_phy0 "devm_usb_get_phy_by_phandle" function will return error. So, maybe it would be more correct (based on your device tree), to use below command hsotg->uphy = devm_usb_get_phy_by_phandle(hsotg->dev, "phys", 0); > + else > + hsotg->uphy = devm_usb_get_phy(hsotg->dev, USB_PHY_TYPE_USB2); > if (IS_ERR(hsotg->uphy)) { > ret = PTR_ERR(hsotg->uphy); > switch (ret) { > Regards, Artur