diff options
author | Mark Kettenis <kettenis@cvs.openbsd.org> | 2006-12-28 09:24:28 +0000 |
---|---|---|
committer | Mark Kettenis <kettenis@cvs.openbsd.org> | 2006-12-28 09:24:28 +0000 |
commit | aaff2c75f5c51ba1af4dd9848404ae90457b83ef (patch) | |
tree | 7ebd13692d29f548f009e26a237c60d68010c01c /sys/dev/mii | |
parent | 58236cdba179c22d89bc3310c113a5fb6206d482 (diff) |
Add function to detect flow control status. From NetBSD.
ok brad@
Diffstat (limited to 'sys/dev/mii')
-rw-r--r-- | sys/dev/mii/mii_physubr.c | 48 | ||||
-rw-r--r-- | sys/dev/mii/miivar.h | 4 |
2 files changed, 50 insertions, 2 deletions
diff --git a/sys/dev/mii/mii_physubr.c b/sys/dev/mii/mii_physubr.c index 1ef0455bc73..0fe41652334 100644 --- a/sys/dev/mii/mii_physubr.c +++ b/sys/dev/mii/mii_physubr.c @@ -1,4 +1,4 @@ -/* $OpenBSD: mii_physubr.c,v 1.29 2006/12/15 21:47:27 reyk Exp $ */ +/* $OpenBSD: mii_physubr.c,v 1.30 2006/12/28 09:24:27 kettenis Exp $ */ /* $NetBSD: mii_physubr.c,v 1.20 2001/04/13 23:30:09 thorpej Exp $ */ /*- @@ -519,6 +519,52 @@ mii_phy_match(const struct mii_attach_args *ma, const struct mii_phydesc *mpd) } /* + * Return the flow control status flag from MII_ANAR & MII_ANLPAR. + */ +int +mii_phy_flowstatus(struct mii_softc *sc) +{ + int anar, anlpar; + + if ((sc->mii_flags & MIIF_DOPAUSE) == 0) + return (0); + + anar = PHY_READ(sc, MII_ANAR); + anlpar = PHY_READ(sc, MII_ANLPAR); + + if ((anar & ANAR_X_PAUSE_SYM) & (anlpar & ANLPAR_X_PAUSE_SYM)) + return (IFM_FLOW|IFM_ETH_TXPAUSE|IFM_ETH_RXPAUSE); + + if ((anar & ANAR_X_PAUSE_SYM) == 0) { + if ((anar & ANAR_X_PAUSE_ASYM) && + ((anlpar & + ANLPAR_X_PAUSE_TOWARDS) == ANLPAR_X_PAUSE_TOWARDS)) + return (IFM_FLOW|IFM_ETH_TXPAUSE); + else + return (0); + } + + if ((anar & ANAR_X_PAUSE_ASYM) == 0) { + if (anlpar & ANLPAR_X_PAUSE_SYM) + return (IFM_FLOW|IFM_ETH_TXPAUSE|IFM_ETH_RXPAUSE); + else + return (0); + } + + switch ((anlpar & ANLPAR_X_PAUSE_TOWARDS)) { + case ANLPAR_X_PAUSE_NONE: + return (0); + + case ANLPAR_X_PAUSE_ASYM: + return (IFM_FLOW|IFM_ETH_RXPAUSE); + + default: + return (IFM_FLOW|IFM_ETH_RXPAUSE|IFM_ETH_TXPAUSE); + } + /* NOTREACHED */ +} + +/* * Given an ifmedia word, return the corresponding ANAR value. */ int diff --git a/sys/dev/mii/miivar.h b/sys/dev/mii/miivar.h index 8f986f05692..2e750a03f0f 100644 --- a/sys/dev/mii/miivar.h +++ b/sys/dev/mii/miivar.h @@ -1,4 +1,4 @@ -/* $OpenBSD: miivar.h,v 1.26 2005/11/06 09:27:19 brad Exp $ */ +/* $OpenBSD: miivar.h,v 1.27 2006/12/28 09:24:27 kettenis Exp $ */ /* $NetBSD: miivar.h,v 1.17 2000/03/06 20:56:57 thorpej Exp $ */ /*- @@ -269,6 +269,8 @@ void mii_phy_status(struct mii_softc *); void mii_phy_update(struct mii_softc *, int); int mii_phy_statusmsg(struct mii_softc *); +int mii_phy_flowstatus(struct mii_softc *); + void ukphy_status(struct mii_softc *); #endif /* _KERNEL */ |