On Wed, Jun 27, 2018 at 04:42:22PM +0800, Kevin Lo wrote:
> 
> Hi,
> 
> The diff below sets SMSC_MII_BUSY bit, which is necessary for PHY to 
> acknowledge a read/write request; from FreeBSD r333096.
> While here, mask off the PHY address and register.
> 
> Tested on rpi3.
> 
> # dmesg |grep smsc
> smsc0 at uhub1 port 1 configuration 1 interface 0 "Standard Microsystems 
> SMSC9512/14" rev 2.00/2.00 addr 3
> smsc0: address b8:27:eb:b0:32:5d
> ukphy0 at smsc0 phy 1: Generic IEEE 802.3u media interface, rev. 3: OUI 
> 0x0001f0, model 0x000c
> 

Anyone?  It also matches Linux commit 80928805babfd97b6f1721dd942a55dd2e7813ea.

> 
> Index: sys/dev/usb/if_smsc.c
> ===================================================================
> RCS file: /cvs/src/sys/dev/usb/if_smsc.c,v
> retrieving revision 1.31
> diff -u -p -u -p -r1.31 if_smsc.c
> --- sys/dev/usb/if_smsc.c     29 Jul 2017 17:24:04 -0000      1.31
> +++ sys/dev/usb/if_smsc.c     27 Jun 2018 08:37:34 -0000
> @@ -283,7 +283,6 @@ int
>  smsc_miibus_readreg(struct device *dev, int phy, int reg)
>  {
>       struct smsc_softc *sc = (struct smsc_softc *)dev;
> -     uint32_t addr;
>       uint32_t val = 0;
>  
>       smsc_lock_mii(sc);
> @@ -292,8 +291,8 @@ smsc_miibus_readreg(struct device *dev, 
>               goto done;
>       }
>  
> -     addr = (phy << 11) | (reg << 6) | SMSC_MII_READ;
> -     smsc_write_reg(sc, SMSC_MII_ADDR, addr);
> +     smsc_write_reg(sc, SMSC_MII_ADDR, SMSC_MII_READ | SMSC_MII_BUSY |
> +         SMSC_MII_PHY_ADDR(phy) | SMSC_MII_REG_ADDR(reg));
>  
>       if (smsc_wait_for_bits(sc, SMSC_MII_ADDR, SMSC_MII_BUSY) != 0)
>               smsc_warn_printf(sc, "MII read timeout\n");
> @@ -309,7 +308,6 @@ void
>  smsc_miibus_writereg(struct device *dev, int phy, int reg, int val)
>  {
>       struct smsc_softc *sc = (struct smsc_softc *)dev;
> -     uint32_t addr;
>  
>       if (sc->sc_phyno != phy)
>               return;
> @@ -323,8 +321,9 @@ smsc_miibus_writereg(struct device *dev,
>  
>       smsc_write_reg(sc, SMSC_MII_DATA, val);
>  
> -     addr = (phy << 11) | (reg << 6) | SMSC_MII_WRITE;
> -     smsc_write_reg(sc, SMSC_MII_ADDR, addr);
> +     smsc_write_reg(sc, SMSC_MII_ADDR, SMSC_MII_WRITE | SMSC_MII_BUSY |
> +         SMSC_MII_PHY_ADDR(phy) | SMSC_MII_REG_ADDR(reg));
> +
>       smsc_unlock_mii(sc);
>  
>       if (smsc_wait_for_bits(sc, SMSC_MII_ADDR, SMSC_MII_BUSY) != 0)
> Index: sys/dev/usb/if_smscreg.h
> ===================================================================
> RCS file: /cvs/src/sys/dev/usb/if_smscreg.h,v
> retrieving revision 1.5
> diff -u -p -u -p -r1.5 if_smscreg.h
> --- sys/dev/usb/if_smscreg.h  18 Jun 2015 09:28:54 -0000      1.5
> +++ sys/dev/usb/if_smscreg.h  27 Jun 2018 08:37:35 -0000
> @@ -215,9 +215,17 @@
>  #define SMSC_INTR_GPIOS             0x000007FFUL
>  
>  /* Phy MII interface register */
> +#define SMSC_MII_PHY_ADDR_MASK      0x0000F800
> +#define SMSC_MII_PHY_ADDR_SHIFT     11
> +#define SMSC_MII_REG_ADDR_MASK      0x000007C0
> +#define SMSC_MII_REG_ADDR_SHIFT     6
>  #define SMSC_MII_WRITE              (0x1UL << 1)
>  #define SMSC_MII_READ               (0x0UL << 1)
>  #define SMSC_MII_BUSY               (0x1UL << 0)
> +#define SMSC_MII_REG_ADDR(x)        \
> +        (((x) << SMSC_MII_REG_ADDR_SHIFT ) & SMSC_MII_REG_ADDR_MASK)
> +#define SMSC_MII_PHY_ADDR(x)         \
> +        (((x) << SMSC_MII_PHY_ADDR_SHIFT) & SMSC_MII_PHY_ADDR_MASK)
>  
>  /* H/W checksum register */
>  #define SMSC_COE_CTRL_TX_EN         (0x1UL << 16)  /* Tx H/W csum enable */
> 
> 

Reply via email to