brintos

brintos / linux-shallow public Read only

0
0
Text · 18.3 KiB · 03f9067 Raw
710 lines · c
1// SPDX-License-Identifier: GPL-2.0-only2/*******************************************************************************3  STMMAC Ethernet Driver -- MDIO bus implementation4  Provides Bus interface for MII registers5 6  Copyright (C) 2007-2009  STMicroelectronics Ltd7 8 9  Author: Carl Shaw <carl.shaw@st.com>10  Maintainer: Giuseppe Cavallaro <peppe.cavallaro@st.com>11*******************************************************************************/12 13#include <linux/gpio/consumer.h>14#include <linux/io.h>15#include <linux/iopoll.h>16#include <linux/mii.h>17#include <linux/of_mdio.h>18#include <linux/pm_runtime.h>19#include <linux/phy.h>20#include <linux/property.h>21#include <linux/slab.h>22 23#include "dwxgmac2.h"24#include "stmmac.h"25 26#define MII_BUSY 0x0000000127#define MII_WRITE 0x0000000228#define MII_DATA_MASK GENMASK(15, 0)29 30/* GMAC4 defines */31#define MII_GMAC4_GOC_SHIFT		232#define MII_GMAC4_REG_ADDR_SHIFT	1633#define MII_GMAC4_WRITE			(1 << MII_GMAC4_GOC_SHIFT)34#define MII_GMAC4_READ			(3 << MII_GMAC4_GOC_SHIFT)35#define MII_GMAC4_C45E			BIT(1)36 37/* XGMAC defines */38#define MII_XGMAC_SADDR			BIT(18)39#define MII_XGMAC_CMD_SHIFT		1640#define MII_XGMAC_WRITE			(1 << MII_XGMAC_CMD_SHIFT)41#define MII_XGMAC_READ			(3 << MII_XGMAC_CMD_SHIFT)42#define MII_XGMAC_BUSY			BIT(22)43#define MII_XGMAC_MAX_C22ADDR		344#define MII_XGMAC_C22P_MASK		GENMASK(MII_XGMAC_MAX_C22ADDR, 0)45#define MII_XGMAC_PA_SHIFT		1646#define MII_XGMAC_DA_SHIFT		2147 48static void stmmac_xgmac2_c45_format(struct stmmac_priv *priv, int phyaddr,49				     int devad, int phyreg, u32 *hw_addr)50{51	u32 tmp;52 53	/* Set port as Clause 45 */54	tmp = readl(priv->ioaddr + XGMAC_MDIO_C22P);55	tmp &= ~BIT(phyaddr);56	writel(tmp, priv->ioaddr + XGMAC_MDIO_C22P);57 58	*hw_addr = (phyaddr << MII_XGMAC_PA_SHIFT) | (phyreg & 0xffff);59	*hw_addr |= devad << MII_XGMAC_DA_SHIFT;60}61 62static void stmmac_xgmac2_c22_format(struct stmmac_priv *priv, int phyaddr,63				     int phyreg, u32 *hw_addr)64{65	u32 tmp = 0;66 67	if (priv->synopsys_id < DWXGMAC_CORE_2_20) {68		/* Until ver 2.20 XGMAC does not support C22 addr >= 4. Those69		 * bits above bit 3 of XGMAC_MDIO_C22P register are reserved.70		 */71		tmp = readl(priv->ioaddr + XGMAC_MDIO_C22P);72		tmp &= ~MII_XGMAC_C22P_MASK;73	}74	/* Set port as Clause 22 */75	tmp |= BIT(phyaddr);76	writel(tmp, priv->ioaddr + XGMAC_MDIO_C22P);77 78	*hw_addr = (phyaddr << MII_XGMAC_PA_SHIFT) | (phyreg & 0x1f);79}80 81static int stmmac_xgmac2_mdio_read(struct stmmac_priv *priv, u32 addr,82				   u32 value)83{84	unsigned int mii_address = priv->hw->mii.addr;85	unsigned int mii_data = priv->hw->mii.data;86	u32 tmp;87	int ret;88 89	ret = pm_runtime_resume_and_get(priv->device);90	if (ret < 0)91		return ret;92 93	/* Wait until any existing MII operation is complete */94	if (readl_poll_timeout(priv->ioaddr + mii_data, tmp,95			       !(tmp & MII_XGMAC_BUSY), 100, 10000)) {96		ret = -EBUSY;97		goto err_disable_clks;98	}99 100	value |= (priv->clk_csr << priv->hw->mii.clk_csr_shift)101		& priv->hw->mii.clk_csr_mask;102	value |= MII_XGMAC_READ;103 104	/* Wait until any existing MII operation is complete */105	if (readl_poll_timeout(priv->ioaddr + mii_data, tmp,106			       !(tmp & MII_XGMAC_BUSY), 100, 10000)) {107		ret = -EBUSY;108		goto err_disable_clks;109	}110 111	/* Set the MII address register to read */112	writel(addr, priv->ioaddr + mii_address);113	writel(value, priv->ioaddr + mii_data);114 115	/* Wait until any existing MII operation is complete */116	if (readl_poll_timeout(priv->ioaddr + mii_data, tmp,117			       !(tmp & MII_XGMAC_BUSY), 100, 10000)) {118		ret = -EBUSY;119		goto err_disable_clks;120	}121 122	/* Read the data from the MII data register */123	ret = (int)readl(priv->ioaddr + mii_data) & GENMASK(15, 0);124 125err_disable_clks:126	pm_runtime_put(priv->device);127 128	return ret;129}130 131static int stmmac_xgmac2_mdio_read_c22(struct mii_bus *bus, int phyaddr,132				       int phyreg)133{134	struct net_device *ndev = bus->priv;135	struct stmmac_priv *priv;136	u32 addr;137 138	priv = netdev_priv(ndev);139 140	/* Until ver 2.20 XGMAC does not support C22 addr >= 4 */141	if (priv->synopsys_id < DWXGMAC_CORE_2_20 &&142	    phyaddr > MII_XGMAC_MAX_C22ADDR)143		return -ENODEV;144 145	stmmac_xgmac2_c22_format(priv, phyaddr, phyreg, &addr);146 147	return stmmac_xgmac2_mdio_read(priv, addr, MII_XGMAC_BUSY);148}149 150static int stmmac_xgmac2_mdio_read_c45(struct mii_bus *bus, int phyaddr,151				       int devad, int phyreg)152{153	struct net_device *ndev = bus->priv;154	struct stmmac_priv *priv;155	u32 addr;156 157	priv = netdev_priv(ndev);158 159	stmmac_xgmac2_c45_format(priv, phyaddr, devad, phyreg, &addr);160 161	return stmmac_xgmac2_mdio_read(priv, addr, MII_XGMAC_BUSY);162}163 164static int stmmac_xgmac2_mdio_write(struct stmmac_priv *priv, u32 addr,165				    u32 value, u16 phydata)166{167	unsigned int mii_address = priv->hw->mii.addr;168	unsigned int mii_data = priv->hw->mii.data;169	u32 tmp;170	int ret;171 172	ret = pm_runtime_resume_and_get(priv->device);173	if (ret < 0)174		return ret;175 176	/* Wait until any existing MII operation is complete */177	if (readl_poll_timeout(priv->ioaddr + mii_data, tmp,178			       !(tmp & MII_XGMAC_BUSY), 100, 10000)) {179		ret = -EBUSY;180		goto err_disable_clks;181	}182 183	value |= (priv->clk_csr << priv->hw->mii.clk_csr_shift)184		& priv->hw->mii.clk_csr_mask;185	value |= phydata;186	value |= MII_XGMAC_WRITE;187 188	/* Wait until any existing MII operation is complete */189	if (readl_poll_timeout(priv->ioaddr + mii_data, tmp,190			       !(tmp & MII_XGMAC_BUSY), 100, 10000)) {191		ret = -EBUSY;192		goto err_disable_clks;193	}194 195	/* Set the MII address register to write */196	writel(addr, priv->ioaddr + mii_address);197	writel(value, priv->ioaddr + mii_data);198 199	/* Wait until any existing MII operation is complete */200	ret = readl_poll_timeout(priv->ioaddr + mii_data, tmp,201				 !(tmp & MII_XGMAC_BUSY), 100, 10000);202 203err_disable_clks:204	pm_runtime_put(priv->device);205 206	return ret;207}208 209static int stmmac_xgmac2_mdio_write_c22(struct mii_bus *bus, int phyaddr,210					int phyreg, u16 phydata)211{212	struct net_device *ndev = bus->priv;213	struct stmmac_priv *priv;214	u32 addr;215 216	priv = netdev_priv(ndev);217 218	/* Until ver 2.20 XGMAC does not support C22 addr >= 4 */219	if (priv->synopsys_id < DWXGMAC_CORE_2_20 &&220	    phyaddr > MII_XGMAC_MAX_C22ADDR)221		return -ENODEV;222 223	stmmac_xgmac2_c22_format(priv, phyaddr, phyreg, &addr);224 225	return stmmac_xgmac2_mdio_write(priv, addr,226					MII_XGMAC_BUSY | MII_XGMAC_SADDR, phydata);227}228 229static int stmmac_xgmac2_mdio_write_c45(struct mii_bus *bus, int phyaddr,230					int devad, int phyreg, u16 phydata)231{232	struct net_device *ndev = bus->priv;233	struct stmmac_priv *priv;234	u32 addr;235 236	priv = netdev_priv(ndev);237 238	stmmac_xgmac2_c45_format(priv, phyaddr, devad, phyreg, &addr);239 240	return stmmac_xgmac2_mdio_write(priv, addr, MII_XGMAC_BUSY,241					phydata);242}243 244static int stmmac_mdio_read(struct stmmac_priv *priv, int data, u32 value)245{246	unsigned int mii_address = priv->hw->mii.addr;247	unsigned int mii_data = priv->hw->mii.data;248	u32 v;249 250	if (readl_poll_timeout(priv->ioaddr + mii_address, v, !(v & MII_BUSY),251			       100, 10000))252		return -EBUSY;253 254	writel(data, priv->ioaddr + mii_data);255	writel(value, priv->ioaddr + mii_address);256 257	if (readl_poll_timeout(priv->ioaddr + mii_address, v, !(v & MII_BUSY),258			       100, 10000))259		return -EBUSY;260 261	/* Read the data from the MII data register */262	return readl(priv->ioaddr + mii_data) & MII_DATA_MASK;263}264 265/**266 * stmmac_mdio_read_c22267 * @bus: points to the mii_bus structure268 * @phyaddr: MII addr269 * @phyreg: MII reg270 * Description: it reads data from the MII register from within the phy device.271 * For the 7111 GMAC, we must set the bit 0 in the MII address register while272 * accessing the PHY registers.273 * Fortunately, it seems this has no drawback for the 7109 MAC.274 */275static int stmmac_mdio_read_c22(struct mii_bus *bus, int phyaddr, int phyreg)276{277	struct net_device *ndev = bus->priv;278	struct stmmac_priv *priv = netdev_priv(ndev);279	u32 value = MII_BUSY;280	int data = 0;281 282	data = pm_runtime_resume_and_get(priv->device);283	if (data < 0)284		return data;285 286	value |= (phyaddr << priv->hw->mii.addr_shift)287		& priv->hw->mii.addr_mask;288	value |= (phyreg << priv->hw->mii.reg_shift) & priv->hw->mii.reg_mask;289	value |= (priv->clk_csr << priv->hw->mii.clk_csr_shift)290		& priv->hw->mii.clk_csr_mask;291	if (priv->plat->has_gmac4)292		value |= MII_GMAC4_READ;293 294	data = stmmac_mdio_read(priv, data, value);295 296	pm_runtime_put(priv->device);297 298	return data;299}300 301/**302 * stmmac_mdio_read_c45303 * @bus: points to the mii_bus structure304 * @phyaddr: MII addr305 * @devad: device address to read306 * @phyreg: MII reg307 * Description: it reads data from the MII register from within the phy device.308 * For the 7111 GMAC, we must set the bit 0 in the MII address register while309 * accessing the PHY registers.310 * Fortunately, it seems this has no drawback for the 7109 MAC.311 */312static int stmmac_mdio_read_c45(struct mii_bus *bus, int phyaddr, int devad,313				int phyreg)314{315	struct net_device *ndev = bus->priv;316	struct stmmac_priv *priv = netdev_priv(ndev);317	u32 value = MII_BUSY;318	int data = 0;319 320	data = pm_runtime_get_sync(priv->device);321	if (data < 0) {322		pm_runtime_put_noidle(priv->device);323		return data;324	}325 326	value |= (phyaddr << priv->hw->mii.addr_shift)327		& priv->hw->mii.addr_mask;328	value |= (phyreg << priv->hw->mii.reg_shift) & priv->hw->mii.reg_mask;329	value |= (priv->clk_csr << priv->hw->mii.clk_csr_shift)330		& priv->hw->mii.clk_csr_mask;331	value |= MII_GMAC4_READ;332	value |= MII_GMAC4_C45E;333	value &= ~priv->hw->mii.reg_mask;334	value |= (devad << priv->hw->mii.reg_shift) & priv->hw->mii.reg_mask;335 336	data |= phyreg << MII_GMAC4_REG_ADDR_SHIFT;337 338	data = stmmac_mdio_read(priv, data, value);339 340	pm_runtime_put(priv->device);341 342	return data;343}344 345static int stmmac_mdio_write(struct stmmac_priv *priv, int data, u32 value)346{347	unsigned int mii_address = priv->hw->mii.addr;348	unsigned int mii_data = priv->hw->mii.data;349	u32 v;350 351	/* Wait until any existing MII operation is complete */352	if (readl_poll_timeout(priv->ioaddr + mii_address, v, !(v & MII_BUSY),353			       100, 10000))354		return -EBUSY;355 356	/* Set the MII address register to write */357	writel(data, priv->ioaddr + mii_data);358	writel(value, priv->ioaddr + mii_address);359 360	/* Wait until any existing MII operation is complete */361	return readl_poll_timeout(priv->ioaddr + mii_address, v,362				  !(v & MII_BUSY), 100, 10000);363}364 365/**366 * stmmac_mdio_write_c22367 * @bus: points to the mii_bus structure368 * @phyaddr: MII addr369 * @phyreg: MII reg370 * @phydata: phy data371 * Description: it writes the data into the MII register from within the device.372 */373static int stmmac_mdio_write_c22(struct mii_bus *bus, int phyaddr, int phyreg,374				 u16 phydata)375{376	struct net_device *ndev = bus->priv;377	struct stmmac_priv *priv = netdev_priv(ndev);378	int ret, data = phydata;379	u32 value = MII_BUSY;380 381	ret = pm_runtime_resume_and_get(priv->device);382	if (ret < 0)383		return ret;384 385	value |= (phyaddr << priv->hw->mii.addr_shift)386		& priv->hw->mii.addr_mask;387	value |= (phyreg << priv->hw->mii.reg_shift) & priv->hw->mii.reg_mask;388 389	value |= (priv->clk_csr << priv->hw->mii.clk_csr_shift)390		& priv->hw->mii.clk_csr_mask;391	if (priv->plat->has_gmac4)392		value |= MII_GMAC4_WRITE;393	else394		value |= MII_WRITE;395 396	ret = stmmac_mdio_write(priv, data, value);397 398	pm_runtime_put(priv->device);399 400	return ret;401}402 403/**404 * stmmac_mdio_write_c45405 * @bus: points to the mii_bus structure406 * @phyaddr: MII addr407 * @phyreg: MII reg408 * @devad: device address to read409 * @phydata: phy data410 * Description: it writes the data into the MII register from within the device.411 */412static int stmmac_mdio_write_c45(struct mii_bus *bus, int phyaddr,413				 int devad, int phyreg, u16 phydata)414{415	struct net_device *ndev = bus->priv;416	struct stmmac_priv *priv = netdev_priv(ndev);417	int ret, data = phydata;418	u32 value = MII_BUSY;419 420	ret = pm_runtime_get_sync(priv->device);421	if (ret < 0) {422		pm_runtime_put_noidle(priv->device);423		return ret;424	}425 426	value |= (phyaddr << priv->hw->mii.addr_shift)427		& priv->hw->mii.addr_mask;428	value |= (phyreg << priv->hw->mii.reg_shift) & priv->hw->mii.reg_mask;429 430	value |= (priv->clk_csr << priv->hw->mii.clk_csr_shift)431		& priv->hw->mii.clk_csr_mask;432 433	value |= MII_GMAC4_WRITE;434	value |= MII_GMAC4_C45E;435	value &= ~priv->hw->mii.reg_mask;436	value |= (devad << priv->hw->mii.reg_shift) & priv->hw->mii.reg_mask;437 438	data |= phyreg << MII_GMAC4_REG_ADDR_SHIFT;439 440	ret = stmmac_mdio_write(priv, data, value);441 442	pm_runtime_put(priv->device);443 444	return ret;445}446 447/**448 * stmmac_mdio_reset449 * @bus: points to the mii_bus structure450 * Description: reset the MII bus451 */452int stmmac_mdio_reset(struct mii_bus *bus)453{454#if IS_ENABLED(CONFIG_STMMAC_PLATFORM)455	struct net_device *ndev = bus->priv;456	struct stmmac_priv *priv = netdev_priv(ndev);457	unsigned int mii_address = priv->hw->mii.addr;458 459#ifdef CONFIG_OF460	if (priv->device->of_node) {461		struct gpio_desc *reset_gpio;462		u32 delays[3] = { 0, 0, 0 };463 464		reset_gpio = devm_gpiod_get_optional(priv->device,465						     "snps,reset",466						     GPIOD_OUT_LOW);467		if (IS_ERR(reset_gpio))468			return PTR_ERR(reset_gpio);469 470		device_property_read_u32_array(priv->device,471					       "snps,reset-delays-us",472					       delays, ARRAY_SIZE(delays));473 474		if (delays[0])475			msleep(DIV_ROUND_UP(delays[0], 1000));476 477		gpiod_set_value_cansleep(reset_gpio, 1);478		if (delays[1])479			msleep(DIV_ROUND_UP(delays[1], 1000));480 481		gpiod_set_value_cansleep(reset_gpio, 0);482		if (delays[2])483			msleep(DIV_ROUND_UP(delays[2], 1000));484	}485#endif486 487	/* This is a workaround for problems with the STE101P PHY.488	 * It doesn't complete its reset until at least one clock cycle489	 * on MDC, so perform a dummy mdio read. To be updated for GMAC4490	 * if needed.491	 */492	if (!priv->plat->has_gmac4)493		writel(0, priv->ioaddr + mii_address);494#endif495	return 0;496}497 498int stmmac_pcs_setup(struct net_device *ndev)499{500	struct fwnode_handle *devnode, *pcsnode;501	struct dw_xpcs *xpcs = NULL;502	struct stmmac_priv *priv;503	int addr, mode, ret;504 505	priv = netdev_priv(ndev);506	mode = priv->plat->phy_interface;507	devnode = priv->plat->port_node;508 509	if (priv->plat->pcs_init) {510		ret = priv->plat->pcs_init(priv);511	} else if (fwnode_property_present(devnode, "pcs-handle")) {512		pcsnode = fwnode_find_reference(devnode, "pcs-handle", 0);513		xpcs = xpcs_create_fwnode(pcsnode, mode);514		fwnode_handle_put(pcsnode);515		ret = PTR_ERR_OR_ZERO(xpcs);516	} else if (priv->plat->mdio_bus_data &&517		   priv->plat->mdio_bus_data->pcs_mask) {518		addr = ffs(priv->plat->mdio_bus_data->pcs_mask) - 1;519		xpcs = xpcs_create_mdiodev(priv->mii, addr, mode);520		ret = PTR_ERR_OR_ZERO(xpcs);521	} else {522		return 0;523	}524 525	if (ret)526		return dev_err_probe(priv->device, ret, "No xPCS found\n");527 528	priv->hw->xpcs = xpcs;529 530	return 0;531}532 533void stmmac_pcs_clean(struct net_device *ndev)534{535	struct stmmac_priv *priv = netdev_priv(ndev);536 537	if (priv->plat->pcs_exit)538		priv->plat->pcs_exit(priv);539 540	if (!priv->hw->xpcs)541		return;542 543	xpcs_destroy(priv->hw->xpcs);544	priv->hw->xpcs = NULL;545}546 547/**548 * stmmac_mdio_register549 * @ndev: net device structure550 * Description: it registers the MII bus551 */552int stmmac_mdio_register(struct net_device *ndev)553{554	int err = 0;555	struct mii_bus *new_bus;556	struct stmmac_priv *priv = netdev_priv(ndev);557	struct stmmac_mdio_bus_data *mdio_bus_data = priv->plat->mdio_bus_data;558	struct device_node *mdio_node = priv->plat->mdio_node;559	struct device *dev = ndev->dev.parent;560	struct fwnode_handle *fixed_node;561	struct fwnode_handle *fwnode;562	int addr, found, max_addr;563 564	if (!mdio_bus_data)565		return 0;566 567	new_bus = mdiobus_alloc();568	if (!new_bus)569		return -ENOMEM;570 571	if (mdio_bus_data->irqs)572		memcpy(new_bus->irq, mdio_bus_data->irqs, sizeof(new_bus->irq));573 574	new_bus->name = "stmmac";575 576	if (priv->plat->has_xgmac) {577		new_bus->read = &stmmac_xgmac2_mdio_read_c22;578		new_bus->write = &stmmac_xgmac2_mdio_write_c22;579		new_bus->read_c45 = &stmmac_xgmac2_mdio_read_c45;580		new_bus->write_c45 = &stmmac_xgmac2_mdio_write_c45;581 582		if (priv->synopsys_id < DWXGMAC_CORE_2_20) {583			/* Right now only C22 phys are supported */584			max_addr = MII_XGMAC_MAX_C22ADDR + 1;585 586			/* Check if DT specified an unsupported phy addr */587			if (priv->plat->phy_addr > MII_XGMAC_MAX_C22ADDR)588				dev_err(dev, "Unsupported phy_addr (max=%d)\n",589					MII_XGMAC_MAX_C22ADDR);590		} else {591			/* XGMAC version 2.20 onwards support 32 phy addr */592			max_addr = PHY_MAX_ADDR;593		}594	} else {595		new_bus->read = &stmmac_mdio_read_c22;596		new_bus->write = &stmmac_mdio_write_c22;597		if (priv->plat->has_gmac4) {598			new_bus->read_c45 = &stmmac_mdio_read_c45;599			new_bus->write_c45 = &stmmac_mdio_write_c45;600		}601 602		max_addr = PHY_MAX_ADDR;603	}604 605	if (mdio_bus_data->needs_reset)606		new_bus->reset = &stmmac_mdio_reset;607 608	snprintf(new_bus->id, MII_BUS_ID_SIZE, "%s-%x",609		 new_bus->name, priv->plat->bus_id);610	new_bus->priv = ndev;611	new_bus->phy_mask = mdio_bus_data->phy_mask | mdio_bus_data->pcs_mask;612	new_bus->parent = priv->device;613 614	err = of_mdiobus_register(new_bus, mdio_node);615	if (err == -ENODEV) {616		err = 0;617		dev_info(dev, "MDIO bus is disabled\n");618		goto bus_register_fail;619	} else if (err) {620		dev_err_probe(dev, err, "Cannot register the MDIO bus\n");621		goto bus_register_fail;622	}623 624	/* Looks like we need a dummy read for XGMAC only and C45 PHYs */625	if (priv->plat->has_xgmac)626		stmmac_xgmac2_mdio_read_c45(new_bus, 0, 0, 0);627 628	/* If fixed-link is set, skip PHY scanning */629	fwnode = priv->plat->port_node;630	if (!fwnode)631		fwnode = dev_fwnode(priv->device);632 633	if (fwnode) {634		fixed_node = fwnode_get_named_child_node(fwnode, "fixed-link");635		if (fixed_node) {636			fwnode_handle_put(fixed_node);637			goto bus_register_done;638		}639	}640 641	if (priv->plat->phy_node || mdio_node)642		goto bus_register_done;643 644	found = 0;645	for (addr = 0; addr < max_addr; addr++) {646		struct phy_device *phydev = mdiobus_get_phy(new_bus, addr);647 648		if (!phydev)649			continue;650 651		/*652		 * If an IRQ was provided to be assigned after653		 * the bus probe, do it here.654		 */655		if (!mdio_bus_data->irqs &&656		    (mdio_bus_data->probed_phy_irq > 0)) {657			new_bus->irq[addr] = mdio_bus_data->probed_phy_irq;658			phydev->irq = mdio_bus_data->probed_phy_irq;659		}660 661		/*662		 * If we're going to bind the MAC to this PHY bus,663		 * and no PHY number was provided to the MAC,664		 * use the one probed here.665		 */666		if (priv->plat->phy_addr == -1)667			priv->plat->phy_addr = addr;668 669		phy_attached_info(phydev);670		found = 1;671	}672 673	if (!found && !mdio_node) {674		dev_warn(dev, "No PHY found\n");675		err = -ENODEV;676		goto no_phy_found;677	}678 679bus_register_done:680	priv->mii = new_bus;681 682	return 0;683 684no_phy_found:685	mdiobus_unregister(new_bus);686bus_register_fail:687	mdiobus_free(new_bus);688	return err;689}690 691/**692 * stmmac_mdio_unregister693 * @ndev: net device structure694 * Description: it unregisters the MII bus695 */696int stmmac_mdio_unregister(struct net_device *ndev)697{698	struct stmmac_priv *priv = netdev_priv(ndev);699 700	if (!priv->mii)701		return 0;702 703	mdiobus_unregister(priv->mii);704	priv->mii->priv = NULL;705	mdiobus_free(priv->mii);706	priv->mii = NULL;707 708	return 0;709}710