Add support of fwnode helper functions to MDIO bus driver. 1. fwnode_phy_find_device() to find phy_device associated to a fwnod 2. fwnode_phy_connect() to attach the mac to the phy
Signed-off-by: Vikas Singh <vikas.si...@puresoftware.com> --- drivers/net/phy/mdio_bus.c | 66 ++++++++++++++++++++++++++++++++++++++++++++++ include/linux/mdio.h | 4 +++ 2 files changed, 70 insertions(+) diff --git a/drivers/net/phy/mdio_bus.c b/drivers/net/phy/mdio_bus.c index 46b3370..ab8fcea 100644 --- a/drivers/net/phy/mdio_bus.c +++ b/drivers/net/phy/mdio_bus.c @@ -40,6 +40,72 @@ #include "mdio-boardinfo.h" +/* Helper function for fwnode_phy_find_device */ +static int fwnode_phy_match(struct device *dev, const void *phy_fwnode) +{ + return dev->fwnode == phy_fwnode; +} + +/** + * fwnode_phy_find_device - find the phy_device associated to fwnode + * @phy_fwnode: Pointer to the PHY's fwnode + * + * If successful, returns a pointer to the phy_device with the + * embedded struct device refcount incremented by one, NULL on + * failure. + */ +struct phy_device *fwnode_phy_find_device(struct fwnode_handle *phy_fwnode) +{ + struct device *d; + struct mdio_device *mdiodev; + + if (!phy_fwnode) + return NULL; + + d = bus_find_device(&mdio_bus_type, NULL, phy_fwnode, fwnode_phy_match); + if (d) { + mdiodev = to_mdio_device(d); + if (mdiodev->flags & MDIO_DEVICE_FLAG_PHY) + return to_phy_device(d); + put_device(d); + } + + return NULL; +} +EXPORT_SYMBOL(fwnode_phy_find_device); + +/** + * fwnode_phy_connect - Connect to the phy described in the device tree + * @dev: pointer to net_device claiming the phy + * @phy_fwnode: Pointer to fwnode for the PHY + * @hndlr: Link state callback for the network device + * @flags: flags to pass to the PHY + * @iface: PHY data interface type + * + * If successful, returns a pointer to the phy_device with the embedded + * struct device refcount incremented by one, or NULL on failure. The + * refcount must be dropped by calling phy_disconnect() or phy_detach(). + */ +struct phy_device *fwnode_phy_connect( + struct net_device *dev, struct fwnode_handle *phy_fwnode, + void (*hndlr)(struct net_device *), u32 flags, u32 iface) +{ + struct phy_device *phy_dev; + + phy_dev = fwnode_phy_find_device(phy_fwnode); + if (!phy_dev) + return NULL; + + phy_dev->dev_flags = flags; + + /* If in case we fail to attach to PHY,then phy_dev must be NULL */ + if (phy_connect_direct(dev, phy_dev, hndlr, iface)) + return NULL; + + return phy_dev; +} +EXPORT_SYMBOL(fwnode_phy_connect); + static int mdiobus_register_gpiod(struct mdio_device *mdiodev) { /* Deassert the optional reset signal */ diff --git a/include/linux/mdio.h b/include/linux/mdio.h index 898cbf0..501da6a 100644 --- a/include/linux/mdio.h +++ b/include/linux/mdio.h @@ -362,6 +362,10 @@ int mdiobus_register_device(struct mdio_device *mdiodev); int mdiobus_unregister_device(struct mdio_device *mdiodev); bool mdiobus_is_registered_device(struct mii_bus *bus, int addr); struct phy_device *mdiobus_get_phy(struct mii_bus *bus, int addr); +struct phy_device *fwnode_phy_find_device(struct fwnode_handle *phy_fwnode); +struct phy_device *fwnode_phy_connect( + struct net_device *dev, struct fwnode_handle *phy_fwnode, + void (*hndlr)(struct net_device *), u32 flags, u32 iface); /** * mdio_module_driver() - Helper macro for registering mdio drivers -- 2.7.4