[SRU][J:linux-bluefield][PATCH v1 0/1] UBUNTU: SAUCE: mlxbf-gige: support fixed phy for Bobcat
Bartlomiej Zolnierkiewicz
bartlomiej.zolnierkiewicz at canonical.com
Mon Feb 26 15:31:29 UTC 2024
Hi Asmaa,
The email title doesn't seem entirely correct ("...v1 0/1..").
On Mon, Feb 26, 2024 at 2:35 AM Asmaa Mnebhi <asmaa at nvidia.com> wrote:
>
> BugLink: https://bugs.launchpad.net/bugs/2054845
>
> There is no external PHY connected to the OOB MAC on the Bobcat
> board and no access to the MDIO bus. The OOB MAC is directly connected
> to the Marvell switch. So support a "fake PHY" and simulate an MDIO bus.
>
> If "fixed-link" property is supported in the ACPI table, register the
> fixed PHY driver.
>
> Signed-off-by: Asmaa Mnebhi <asmaa at nvidia.com>
> Reviewed-by: David Thompson <davthompson at nvidia.com>
> ---
> .../ethernet/mellanox/mlxbf_gige/mlxbf_gige.h | 2 -
> .../mellanox/mlxbf_gige/mlxbf_gige_main.c | 58 ++++++++++++++++---
> 2 files changed, 49 insertions(+), 11 deletions(-)
>
> diff --git a/drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige.h b/drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige.h
> index a453b9cd9033..a85823a64d94 100644
> --- a/drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige.h
> +++ b/drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige.h
> @@ -175,8 +175,6 @@ enum mlxbf_gige_res {
> int mlxbf_gige_mdio_probe(struct platform_device *pdev,
> struct mlxbf_gige *priv);
> void mlxbf_gige_mdio_remove(struct mlxbf_gige *priv);
> -irqreturn_t mlxbf_gige_mdio_handle_phy_interrupt(int irq, void *dev_id);
> -void mlxbf_gige_mdio_enable_phy_int(struct mlxbf_gige *priv);
The above change seems correct but please mention it in the patch description.
> void mlxbf_gige_set_mac_rx_filter(struct mlxbf_gige *priv,
> unsigned int index, u64 dmac);
> diff --git a/drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige_main.c b/drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige_main.c
> index c0da9c05b12a..1f0e24e74e19 100644
> --- a/drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige_main.c
> +++ b/drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige_main.c
> @@ -13,6 +13,7 @@
> #include <linux/iopoll.h>
> #include <linux/module.h>
> #include <linux/phy.h>
> +#include <linux/phy_fixed.h>
> #include <linux/platform_device.h>
> #include <linux/skbuff.h>
>
> @@ -364,6 +365,7 @@ static struct mlxbf_gige_link_cfg mlxbf_gige_link_cfgs[] = {
>
> static int mlxbf_gige_probe(struct platform_device *pdev)
> {
> + struct fixed_phy_status fphy_status = {};
> struct phy_device *phydev;
> struct net_device *netdev;
> struct mlxbf_gige *priv;
> @@ -428,16 +430,49 @@ static int mlxbf_gige_probe(struct platform_device *pdev)
> priv->rx_irq = platform_get_irq(pdev, MLXBF_GIGE_RECEIVE_PKT_INTR_IDX);
> priv->llu_plu_irq = platform_get_irq(pdev, MLXBF_GIGE_LLU_PLU_INTR_IDX);
>
> - phy_irq = acpi_dev_gpio_irq_get_by(ACPI_COMPANION(&pdev->dev), "phy-gpios", 0);
> - if (phy_irq < 0) {
> - dev_err(&pdev->dev, "Error getting PHY irq. Use polling instead");
> + if (device_property_read_bool(&pdev->dev, "fixed-link")) {
> + fphy_status.link = 1;
> + err = device_property_read_u32(&pdev->dev, "full-duplex", &fphy_status.duplex);
> + if (err) {
> + dev_err(&pdev->dev, "Failed to get duplex\n");
> + return -EINVAL;
> + }
> + err = device_property_read_u32(&pdev->dev, "speed", &fphy_status.speed);
> + if (err) {
> + dev_err(&pdev->dev, "Failed to get speed\n");
> + return -EINVAL;
> + }
> + err = device_property_read_u32(&pdev->dev, "pause", &fphy_status.pause);
> + if (err) {
> + dev_err(&pdev->dev, "Failed to get pause\n");
> + return -EINVAL;
> + }
> + err = device_property_read_u32(&pdev->dev, "asym-pause", &fphy_status.asym_pause);
> + if (err) {
> + dev_err(&pdev->dev, "Failed to get asym-pause\n");
> + return -EINVAL;
> + }
> +
> + phydev = fixed_phy_register(PHY_POLL, &fphy_status, NULL);
> + if (IS_ERR(phydev)) {
> + dev_err(&pdev->dev, "Failed to register fixed PHY device\n");
> + err = PTR_ERR(phydev);
> + goto out;
Shouldn't the driver also do the cleanup ("goto out;") on ACPI table
read errors?
--
Best regards,
Bartlomiej
> + }
> +
> phy_irq = PHY_POLL;
> - }
> + } else {
> + phy_irq = acpi_dev_gpio_irq_get_by(ACPI_COMPANION(&pdev->dev), "phy-gpios", 0);
> + if (phy_irq < 0) {
> + dev_err(&pdev->dev, "Error getting PHY irq. Use polling instead");
> + phy_irq = PHY_POLL;
> + }
>
> - phydev = phy_find_first(priv->mdiobus);
> - if (!phydev) {
> - err = -ENODEV;
> - goto out;
> + phydev = phy_find_first(priv->mdiobus);
> + if (!phydev) {
> + err = -ENODEV;
> + goto out;
> + }
> }
>
> addr = phydev->mdio.addr;
> @@ -474,9 +509,14 @@ static int mlxbf_gige_probe(struct platform_device *pdev)
> static int mlxbf_gige_remove(struct platform_device *pdev)
> {
> struct mlxbf_gige *priv = platform_get_drvdata(pdev);
> + struct phy_device *phydev = priv->netdev->phydev;
>
> unregister_netdev(priv->netdev);
> - phy_disconnect(priv->netdev->phydev);
> + phy_disconnect(phydev);
> +
> + if (phy_is_pseudo_fixed_link(phydev))
> + fixed_phy_unregister(phydev);
> +
> mlxbf_gige_mdio_remove(priv);
> platform_set_drvdata(pdev, NULL);
>
More information about the kernel-team
mailing list