mirror of
git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
synced 2025-05-24 10:39:52 +00:00
net: phy: micrel: Adding interrupt support for Link up/Link down in LAN8814 Quad phy
This patch add support for Link up or Link down interrupt support in LAN8814 Quad phy Signed-off-by: Divya Koppera <Divya.Koppera@microchip.com> Reviewed-by: Andrew Lunn <andrew@lunn.ch> Link: https://lore.kernel.org/r/20211221112217.9502-1-Divya.Koppera@microchip.com Signed-off-by: Jakub Kicinski <kuba@kernel.org>
This commit is contained in:
parent
294e70c952
commit
b3ec7248f1
1 changed files with 67 additions and 0 deletions
|
@ -66,6 +66,19 @@
|
|||
#define KSZ8081_LMD_SHORT_INDICATOR BIT(12)
|
||||
#define KSZ8081_LMD_DELTA_TIME_MASK GENMASK(8, 0)
|
||||
|
||||
/* Lan8814 general Interrupt control/status reg in GPHY specific block. */
|
||||
#define LAN8814_INTC 0x18
|
||||
#define LAN8814_INTS 0x1B
|
||||
|
||||
#define LAN8814_INT_LINK_DOWN BIT(2)
|
||||
#define LAN8814_INT_LINK_UP BIT(0)
|
||||
#define LAN8814_INT_LINK (LAN8814_INT_LINK_UP |\
|
||||
LAN8814_INT_LINK_DOWN)
|
||||
|
||||
#define LAN8814_INTR_CTRL_REG 0x34
|
||||
#define LAN8814_INTR_CTRL_REG_POLARITY BIT(1)
|
||||
#define LAN8814_INTR_CTRL_REG_INTR_ENABLE BIT(0)
|
||||
|
||||
/* PHY Control 1 */
|
||||
#define MII_KSZPHY_CTRL_1 0x1e
|
||||
#define KSZ8081_CTRL1_MDIX_STAT BIT(4)
|
||||
|
@ -1620,6 +1633,58 @@ static int lan8804_config_init(struct phy_device *phydev)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static irqreturn_t lan8814_handle_interrupt(struct phy_device *phydev)
|
||||
{
|
||||
int irq_status;
|
||||
|
||||
irq_status = phy_read(phydev, LAN8814_INTS);
|
||||
if (irq_status < 0)
|
||||
return IRQ_NONE;
|
||||
|
||||
if (!(irq_status & LAN8814_INT_LINK))
|
||||
return IRQ_NONE;
|
||||
|
||||
phy_trigger_machine(phydev);
|
||||
|
||||
return IRQ_HANDLED;
|
||||
}
|
||||
|
||||
static int lan8814_ack_interrupt(struct phy_device *phydev)
|
||||
{
|
||||
/* bit[12..0] int status, which is a read and clear register. */
|
||||
int rc;
|
||||
|
||||
rc = phy_read(phydev, LAN8814_INTS);
|
||||
|
||||
return (rc < 0) ? rc : 0;
|
||||
}
|
||||
|
||||
static int lan8814_config_intr(struct phy_device *phydev)
|
||||
{
|
||||
int err;
|
||||
|
||||
lanphy_write_page_reg(phydev, 4, LAN8814_INTR_CTRL_REG,
|
||||
LAN8814_INTR_CTRL_REG_POLARITY |
|
||||
LAN8814_INTR_CTRL_REG_INTR_ENABLE);
|
||||
|
||||
/* enable / disable interrupts */
|
||||
if (phydev->interrupts == PHY_INTERRUPT_ENABLED) {
|
||||
err = lan8814_ack_interrupt(phydev);
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
err = phy_write(phydev, LAN8814_INTC, LAN8814_INT_LINK);
|
||||
} else {
|
||||
err = phy_write(phydev, LAN8814_INTC, 0);
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
err = lan8814_ack_interrupt(phydev);
|
||||
}
|
||||
|
||||
return err;
|
||||
}
|
||||
|
||||
static struct phy_driver ksphy_driver[] = {
|
||||
{
|
||||
.phy_id = PHY_ID_KS8737,
|
||||
|
@ -1802,6 +1867,8 @@ static struct phy_driver ksphy_driver[] = {
|
|||
.get_stats = kszphy_get_stats,
|
||||
.suspend = genphy_suspend,
|
||||
.resume = kszphy_resume,
|
||||
.config_intr = lan8814_config_intr,
|
||||
.handle_interrupt = lan8814_handle_interrupt,
|
||||
}, {
|
||||
.phy_id = PHY_ID_LAN8804,
|
||||
.phy_id_mask = MICREL_PHY_ID_MASK,
|
||||
|
|
Loading…
Add table
Reference in a new issue