Module Name: src Committed By: msaitoh Date: Tue Jul 18 08:22:55 UTC 2017
Modified Files: src/sys/dev/mii: ihphyreg.h src/sys/dev/pci: if_wm.c Log Message: - Add wm_write_smbus_addr() to set SMBus address by software. - Modify wm_gmii_hv_{read,write}reg_locked() to make them access HV_SMB_ADDR correctly. - Enable wm_init_lcd_from_nvm() again. Tested by Thinkpad X220. To generate a diff of this commit: cvs rdiff -u -r1.1 -r1.2 src/sys/dev/mii/ihphyreg.h cvs rdiff -u -r1.527 -r1.528 src/sys/dev/pci/if_wm.c Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.
Modified files: Index: src/sys/dev/mii/ihphyreg.h diff -u src/sys/dev/mii/ihphyreg.h:1.1 src/sys/dev/mii/ihphyreg.h:1.2 --- src/sys/dev/mii/ihphyreg.h:1.1 Sat Nov 27 20:15:27 2010 +++ src/sys/dev/mii/ihphyreg.h Tue Jul 18 08:22:55 2017 @@ -1,4 +1,4 @@ -/* $NetBSD: ihphyreg.h,v 1.1 2010/11/27 20:15:27 christos Exp $ */ +/* $NetBSD: ihphyreg.h,v 1.2 2017/07/18 08:22:55 msaitoh Exp $ */ /*- * Copyright (c) 2010 The NetBSD Foundation, Inc. @@ -108,4 +108,15 @@ /* Diagnostics Status Register */ #define IHPHY_MII_DSR BME1000_REG(0, 31) +/* + * XXX I21[789] documents say that the SMBus Address register is at + * PHY address 01, Page 0 (not 768), Register 26. + */ +#define HV_SMB_ADDR BME1000_REG(768, 26) +#define HV_SMB_ADDR_ADDR 0x007f +#define HV_SMB_ADDR_VALID (1 << 7) +#define HV_SMB_ADDR_FREQ_LOW (1 << 8) +#define HV_SMB_ADDR_PEC_EN (1 << 9) +#define HV_SMB_ADDR_FREQ_HIGH (1 << 12) + #endif /* _DEV_IHPHY_MIIREG_H_ */ Index: src/sys/dev/pci/if_wm.c diff -u src/sys/dev/pci/if_wm.c:1.527 src/sys/dev/pci/if_wm.c:1.528 --- src/sys/dev/pci/if_wm.c:1.527 Tue Jul 18 08:05:03 2017 +++ src/sys/dev/pci/if_wm.c Tue Jul 18 08:22:55 2017 @@ -1,4 +1,4 @@ -/* $NetBSD: if_wm.c,v 1.527 2017/07/18 08:05:03 msaitoh Exp $ */ +/* $NetBSD: if_wm.c,v 1.528 2017/07/18 08:22:55 msaitoh Exp $ */ /* * Copyright (c) 2001, 2002, 2003, 2004 Wasabi Systems, Inc. @@ -83,7 +83,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: if_wm.c,v 1.527 2017/07/18 08:05:03 msaitoh Exp $"); +__KERNEL_RCSID(0, "$NetBSD: if_wm.c,v 1.528 2017/07/18 08:22:55 msaitoh Exp $"); #ifdef _KERNEL_OPT #include "opt_net_mpsafe.h" @@ -134,6 +134,7 @@ __KERNEL_RCSID(0, "$NetBSD: if_wm.c,v 1. #include <dev/mii/igphyreg.h> #include <dev/mii/igphyvar.h> #include <dev/mii/inbmphyreg.h> +#include <dev/mii/ihphyreg.h> #include <dev/pci/pcireg.h> #include <dev/pci/pcivar.h> @@ -679,6 +680,7 @@ static void wm_get_auto_rd_done(struct w static void wm_lan_init_done(struct wm_softc *); static void wm_get_cfg_done(struct wm_softc *); static void wm_phy_post_reset(struct wm_softc *); +static void wm_write_smbus_addr(struct wm_softc *); static void wm_init_lcd_from_nvm(struct wm_softc *); static void wm_initialize_hardware_bits(struct wm_softc *); static uint32_t wm_rxpbs_adjust_82580(uint32_t); @@ -3705,16 +3707,57 @@ wm_phy_post_reset(struct wm_softc *sc) /* Configure the LCD with the OEM bits in NVM */ } +/* Only for PCH and newer */ +static void +wm_write_smbus_addr(struct wm_softc *sc) +{ + uint32_t strap, freq; + uint32_t phy_data; + + DPRINTF(WM_DEBUG_INIT, ("%s: %s called\n", + device_xname(sc->sc_dev), __func__)); + + strap = CSR_READ(sc, WMREG_STRAP); + freq = __SHIFTOUT(strap, STRAP_FREQ); + + phy_data = wm_gmii_hv_readreg_locked(sc->sc_dev, 2, HV_SMB_ADDR); + + phy_data &= ~HV_SMB_ADDR_ADDR; + phy_data |= __SHIFTOUT(strap, STRAP_SMBUSADDR); + phy_data |= HV_SMB_ADDR_PEC_EN | HV_SMB_ADDR_VALID; + + if (sc->sc_phytype == WMPHY_I217) { + /* Restore SMBus frequency */ + if (freq --) { + phy_data &= ~(HV_SMB_ADDR_FREQ_LOW + | HV_SMB_ADDR_FREQ_HIGH); + phy_data |= __SHIFTIN((freq & 0x01) != 0, + HV_SMB_ADDR_FREQ_LOW); + phy_data |= __SHIFTIN((freq & 0x02) != 0, + HV_SMB_ADDR_FREQ_HIGH); + } else { + DPRINTF(WM_DEBUG_INIT, + ("%s: %s Unsupported SMB frequency in PHY\n", + device_xname(sc->sc_dev), __func__)); + } + } + + wm_gmii_hv_writereg_locked(sc->sc_dev, 2, HV_SMB_ADDR, phy_data); +} + void wm_init_lcd_from_nvm(struct wm_softc *sc) { -#if 0 uint32_t extcnfctr, sw_cfg_mask, cnf_size, word_addr, i, reg; uint16_t phy_page = 0; + DPRINTF(WM_DEBUG_INIT, ("%s: %s called\n", + device_xname(sc->sc_dev), __func__)); + switch (sc->sc_type) { case WM_T_ICH8: - if (sc->sc_phytype != WMPHY_IGP_3) + if ((sc->sc_phytype == WMPHY_UNKNOWN) + || (sc->sc_phytype != WMPHY_IGP_3)) return; if ((sc->sc_pcidevid == PCI_PRODUCT_INTEL_82801H_AMT) @@ -3748,6 +3791,8 @@ wm_init_lcd_from_nvm(struct wm_softc *sc && ((extcnfctr & EXTCNFCTR_PCIE_WRITE_ENABLE) != 0)) goto release; + DPRINTF(WM_DEBUG_INIT, ("%s: %s: Configure LCD by software\n", + device_xname(sc->sc_dev), __func__)); /* word_addr is in DWORD */ word_addr = __SHIFTOUT(extcnfctr, EXTCNFCTR_EXT_CNF_POINTER) << 1; @@ -3762,8 +3807,9 @@ wm_init_lcd_from_nvm(struct wm_softc *sc * LCD Write Enable bits are set in the NVM. When both NVM bits * are cleared, SW will configure them instead. */ - device_printf(sc->sc_dev, "%s: need write_smbus()\n", - __func__); + DPRINTF(WM_DEBUG_INIT, ("%s: %s: Configure SMBus and LED\n", + device_xname(sc->sc_dev), __func__)); + wm_write_smbus_addr(sc); reg = CSR_READ(sc, WMREG_LEDCTL); wm_gmii_hv_writereg_locked(sc->sc_dev, 1, HV_LED_CONFIG, reg); @@ -3793,7 +3839,6 @@ wm_init_lcd_from_nvm(struct wm_softc *sc release: sc->phy.release(sc); return; -#endif } @@ -10135,6 +10180,13 @@ wm_gmii_hv_readreg_locked(device_t dev, return 0; } + /* + * XXX I21[789] documents say that the SMBus Address register is at + * PHY address 01, Page 0 (not 768), Register 26. + */ + if (page == HV_INTC_FC_PAGE_START) + page = 0; + if (regnum > BME1000_MAX_MULTI_PAGE_REG) { wm_gmii_mdic_writereg(dev, 1, MII_IGPHY_PAGE_SELECT, page << BME1000_PAGE_SHIFT); @@ -10197,6 +10249,13 @@ wm_gmii_hv_writereg_locked(device_t dev, { /* + * XXX I21[789] documents say that the SMBus Address register + * is at PHY address 01, Page 0 (not 768), Register 26. + */ + if (page == HV_INTC_FC_PAGE_START) + page = 0; + + /* * XXX Workaround MDIO accesses being disabled after entering * IEEE Power Down (whenever bit 11 of the PHY control * register is set)