Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 77501a79 authored by Philipp Zabel's avatar Philipp Zabel Committed by David S. Miller
Browse files

net: phy: micrel: Add KSZ8041FTL fiber mode support



We can't detect the FXEN (fiber mode) bootstrap pin, so configure
it via a boolean device tree property "micrel,fiber-mode".
If it is enabled, auto-negotiation is not supported.
The only available modes are 100base-fx (full duplex and half duplex).

Signed-off-by: default avatarPhilipp Zabel <p.zabel@pengutronix.de>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 2f43b9be
Loading
Loading
Loading
Loading
+10 −0
Original line number Diff line number Diff line
@@ -35,3 +35,13 @@ Optional properties:
	supported clocks:
	- KSZ8021, KSZ8031, KSZ8081, KSZ8091: "rmii-ref": The RMII reference
	  input clock. Used to determine the XI input clock.

 - micrel,fiber-mode: If present the PHY is configured to operate in fiber mode

	Some PHYs, such as the KSZ8041FTL variant, support fiber mode, enabled
	by the FXEN boot strapping pin. It can't be determined from the PHY
	registers whether the PHY is in fiber mode, so this boolean device tree
	property can be used to describe it.

	In fiber mode, auto-negotiation is disabled and the PHY can only work in
	100base-fx (full and half duplex) modes.
+32 −2
Original line number Diff line number Diff line
@@ -311,6 +311,36 @@ static int kszphy_config_init(struct phy_device *phydev)
	return 0;
}

static int ksz8041_config_init(struct phy_device *phydev)
{
	struct device_node *of_node = phydev->mdio.dev.of_node;

	/* Limit supported and advertised modes in fiber mode */
	if (of_property_read_bool(of_node, "micrel,fiber-mode")) {
		phydev->dev_flags |= MICREL_PHY_FXEN;
		phydev->supported &= SUPPORTED_FIBRE |
				     SUPPORTED_100baseT_Full |
				     SUPPORTED_100baseT_Half;
		phydev->advertising &= ADVERTISED_FIBRE |
				       ADVERTISED_100baseT_Full |
				       ADVERTISED_100baseT_Half;
		phydev->autoneg = AUTONEG_DISABLE;
	}

	return kszphy_config_init(phydev);
}

static int ksz8041_config_aneg(struct phy_device *phydev)
{
	/* Skip auto-negotiation in fiber mode */
	if (phydev->dev_flags & MICREL_PHY_FXEN) {
		phydev->speed = SPEED_100;
		return 0;
	}

	return genphy_config_aneg(phydev);
}

static int ksz9021_load_values_from_of(struct phy_device *phydev,
				       const struct device_node *of_node,
				       u16 reg,
@@ -788,8 +818,8 @@ static struct phy_driver ksphy_driver[] = {
	.flags		= PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT,
	.driver_data	= &ksz8041_type,
	.probe		= kszphy_probe,
	.config_init	= kszphy_config_init,
	.config_aneg	= genphy_config_aneg,
	.config_init	= ksz8041_config_init,
	.config_aneg	= ksz8041_config_aneg,
	.read_status	= genphy_read_status,
	.ack_interrupt	= kszphy_ack_interrupt,
	.config_intr	= kszphy_config_intr,
+1 −0
Original line number Diff line number Diff line
@@ -37,6 +37,7 @@

/* struct phy_device dev_flags definitions */
#define MICREL_PHY_50MHZ_CLK	0x00000001
#define MICREL_PHY_FXEN		0x00000002

#define MICREL_KSZ9021_EXTREG_CTRL	0xB
#define MICREL_KSZ9021_EXTREG_DATA_WRITE	0xC