From b4a256ac67e39d1d06b2d0a508df35829254f9b0 Mon Sep 17 00:00:00 2001 From: Pyun YongHyeon Date: Wed, 4 May 2011 17:04:31 +0000 Subject: Add initial BCM57765 family support. The BCM57765 family seems to have similar hardware features of BCM5718 family except the number of receive return ring is 4. The BCM57765 family is known to support IEEE 802.3az EEE(Energy Efficient Ethernet) but this change does not include EEE support code. I hope EEE is implemented in near future. This change will support BCM57761, BCM57765, BCM57781, BCM57785, BCM57791 and BCM57795. All hardware offloading features are supported and suspend/resume also should work. Many thanks to Broadcom for continuing support of FreeBSD. Tested by: Paul Thornton (prt <> prt dot org) HW donated by: Broadcom --- sys/dev/bge/if_bge.c | 53 +++++++++++++++++++++++++++++++++++++++++++------ sys/dev/bge/if_bgereg.h | 12 +++++++++++ 2 files changed, 59 insertions(+), 6 deletions(-) (limited to 'sys') diff --git a/sys/dev/bge/if_bge.c b/sys/dev/bge/if_bge.c index 76496aa1b030..d28844a74c73 100644 --- a/sys/dev/bge/if_bge.c +++ b/sys/dev/bge/if_bge.c @@ -214,9 +214,15 @@ static const struct bge_type { { BCOM_VENDORID, BCOM_DEVICEID_BCM5906 }, { BCOM_VENDORID, BCOM_DEVICEID_BCM5906M }, { BCOM_VENDORID, BCOM_DEVICEID_BCM57760 }, + { BCOM_VENDORID, BCOM_DEVICEID_BCM57761 }, + { BCOM_VENDORID, BCOM_DEVICEID_BCM57765 }, { BCOM_VENDORID, BCOM_DEVICEID_BCM57780 }, + { BCOM_VENDORID, BCOM_DEVICEID_BCM57781 }, + { BCOM_VENDORID, BCOM_DEVICEID_BCM57785 }, { BCOM_VENDORID, BCOM_DEVICEID_BCM57788 }, { BCOM_VENDORID, BCOM_DEVICEID_BCM57790 }, + { BCOM_VENDORID, BCOM_DEVICEID_BCM57791 }, + { BCOM_VENDORID, BCOM_DEVICEID_BCM57795 }, { SK_VENDORID, SK_DEVICEID_ALTIMA }, @@ -307,6 +313,8 @@ static const struct bge_revision { { BGE_CHIPID_BCM5787_A2, "BCM5754/5787 A2" }, { BGE_CHIPID_BCM5906_A1, "BCM5906 A1" }, { BGE_CHIPID_BCM5906_A2, "BCM5906 A2" }, + { BGE_CHIPID_BCM57765_A0, "BCM57765 A0" }, + { BGE_CHIPID_BCM57765_B0, "BCM57765 B0" }, { BGE_CHIPID_BCM57780_A0, "BCM57780 A0" }, { BGE_CHIPID_BCM57780_A1, "BCM57780 A1" }, @@ -335,6 +343,7 @@ static const struct bge_revision const bge_majorrevs[] = { /* 5754 and 5787 share the same ASIC ID */ { BGE_ASICREV_BCM5787, "unknown BCM5754/5787" }, { BGE_ASICREV_BCM5906, "unknown BCM5906" }, + { BGE_ASICREV_BCM57765, "unknown BCM57765" }, { BGE_ASICREV_BCM57780, "unknown BCM57780" }, { BGE_ASICREV_BCM5717, "unknown BCM5717" }, @@ -1467,8 +1476,11 @@ bge_chipinit(struct bge_softc *sc) if (sc->bge_asicrev == BGE_ASICREV_BCM5703 || sc->bge_asicrev == BGE_ASICREV_BCM5704) dma_rw_ctl &= ~BGE_PCIDMARWCTL_MINDMA; - if (BGE_IS_5717_PLUS(sc)) + if (BGE_IS_5717_PLUS(sc)) { dma_rw_ctl &= ~BGE_PCIDMARWCTL_DIS_CACHE_ALIGNMENT; + if (sc->bge_chipid == BGE_CHIPID_BCM57765_A0) + dma_rw_ctl &= ~BGE_PCIDMARWCTL_CRDRDR_RDMA_MRRS_MSK; + } pci_write_config(sc->bge_dev, BGE_PCI_DMA_RW_CTL, dma_rw_ctl, 4); /* @@ -1552,7 +1564,8 @@ bge_blockinit(struct bge_softc *sc) } /* Configure mbuf pool watermarks */ - if (sc->bge_asicrev == BGE_ASICREV_BCM5717) { + if (sc->bge_asicrev == BGE_ASICREV_BCM5717 || + sc->bge_asicrev == BGE_ASICREV_BCM57765) { CSR_WRITE_4(sc, BGE_BMAN_MBUFPOOL_READDMA_LOWAT, 0x0); if (sc->bge_ifp->if_mtu > ETHERMTU) { CSR_WRITE_4(sc, BGE_BMAN_MBUFPOOL_MACRX_LOWAT, 0x7e); @@ -1819,7 +1832,8 @@ bge_blockinit(struct bge_softc *sc) limit = 16; } else if (!BGE_IS_5705_PLUS(sc)) limit = BGE_RX_RINGS_MAX; - else if (sc->bge_asicrev == BGE_ASICREV_BCM5755) + else if (sc->bge_asicrev == BGE_ASICREV_BCM5755 || + sc->bge_asicrev == BGE_ASICREV_BCM57765) limit = 4; else limit = 1; @@ -2180,6 +2194,15 @@ bge_probe(device_t dev) id = pci_read_config(dev, BGE_PCI_GEN2_PRODID_ASICREV, 4); break; + case BCOM_DEVICEID_BCM57761: + case BCOM_DEVICEID_BCM57765: + case BCOM_DEVICEID_BCM57781: + case BCOM_DEVICEID_BCM57785: + case BCOM_DEVICEID_BCM57791: + case BCOM_DEVICEID_BCM57795: + id = pci_read_config(dev, + BGE_PCI_GEN15_PRODID_ASICREV, 4); + break; default: id = pci_read_config(dev, BGE_PCI_PRODID_ASICREV, 4); @@ -2694,6 +2717,15 @@ bge_attach(device_t dev) sc->bge_chipid = pci_read_config(dev, BGE_PCI_GEN2_PRODID_ASICREV, 4); break; + case BCOM_DEVICEID_BCM57761: + case BCOM_DEVICEID_BCM57765: + case BCOM_DEVICEID_BCM57781: + case BCOM_DEVICEID_BCM57785: + case BCOM_DEVICEID_BCM57791: + case BCOM_DEVICEID_BCM57795: + sc->bge_chipid = pci_read_config(dev, + BGE_PCI_GEN15_PRODID_ASICREV, 4); + break; default: sc->bge_chipid = pci_read_config(dev, BGE_PCI_PRODID_ASICREV, 4); @@ -2750,9 +2782,11 @@ bge_attach(device_t dev) /* Save chipset family. */ switch (sc->bge_asicrev) { case BGE_ASICREV_BCM5717: + sc->bge_flags |= BGE_FLAG_SHORT_DMA_BUG; + case BGE_ASICREV_BCM57765: sc->bge_flags |= BGE_FLAG_5717_PLUS | BGE_FLAG_5755_PLUS | BGE_FLAG_575X_PLUS | BGE_FLAG_5705_PLUS | BGE_FLAG_JUMBO | - BGE_FLAG_SHORT_DMA_BUG | BGE_FLAG_JUMBO_FRAME; + BGE_FLAG_JUMBO_FRAME; break; case BGE_ASICREV_BCM5755: case BGE_ASICREV_BCM5761: @@ -2801,6 +2835,7 @@ bge_attach(device_t dev) sc->bge_asicrev != BGE_ASICREV_BCM5906 && sc->bge_asicrev != BGE_ASICREV_BCM5717 && sc->bge_asicrev != BGE_ASICREV_BCM5785 && + sc->bge_asicrev != BGE_ASICREV_BCM57765 && sc->bge_asicrev != BGE_ASICREV_BCM57780) { if (sc->bge_asicrev == BGE_ASICREV_BCM5755 || sc->bge_asicrev == BGE_ASICREV_BCM5761 || @@ -3466,6 +3501,9 @@ bge_reset(struct bge_softc *sc) device_printf(dev, "firmware handshake timed out, found 0x%08x\n", val); + /* BCM57765 A0 needs additional time before accessing. */ + if (sc->bge_chipid == BGE_CHIPID_BCM57765_A0) + DELAY(10 * 1000); /* XXX */ } /* @@ -3506,7 +3544,7 @@ bge_reset(struct bge_softc *sc) /* XXX: Broadcom Linux driver. */ if (sc->bge_flags & BGE_FLAG_PCIE && - sc->bge_asicrev != BGE_ASICREV_BCM5717 && + !BGE_IS_5717_PLUS(sc) && sc->bge_chipid != BGE_CHIPID_BCM5750_A0 && sc->bge_asicrev != BGE_ASICREV_BCM5785) { /* Enable Data FIFO protection. */ @@ -4739,7 +4777,10 @@ bge_init_locked(struct bge_softc *sc) * this number of frames, it will drop subsequent incoming * frames until the MBUF High Watermark is reached. */ - CSR_WRITE_4(sc, BGE_MAX_RX_FRAME_LOWAT, 2); + if (sc->bge_asicrev == BGE_ASICREV_BCM57765) + CSR_WRITE_4(sc, BGE_MAX_RX_FRAME_LOWAT, 1); + else + CSR_WRITE_4(sc, BGE_MAX_RX_FRAME_LOWAT, 2); /* Clear MAC statistics. */ if (BGE_IS_5705_PLUS(sc)) diff --git a/sys/dev/bge/if_bgereg.h b/sys/dev/bge/if_bgereg.h index b63dbfb7ee6f..ab88270d8aea 100644 --- a/sys/dev/bge/if_bgereg.h +++ b/sys/dev/bge/if_bgereg.h @@ -223,6 +223,7 @@ #define BGE_PCI_ISR_MBX_LO 0xB4 #define BGE_PCI_PRODID_ASICREV 0xBC #define BGE_PCI_GEN2_PRODID_ASICREV 0xF4 +#define BGE_PCI_GEN15_PRODID_ASICREV 0xFC /* PCI Misc. Host control register */ #define BGE_PCIMISCCTL_CLEAR_INTA 0x00000001 @@ -318,6 +319,8 @@ #define BGE_CHIPID_BCM57780_A1 0x57780001 #define BGE_CHIPID_BCM5717_A0 0x05717000 #define BGE_CHIPID_BCM5717_B0 0x05717100 +#define BGE_CHIPID_BCM57765_A0 0x57785000 +#define BGE_CHIPID_BCM57765_B0 0x57785100 /* shorthand one */ #define BGE_ASICREV(x) ((x) >> 12) @@ -342,6 +345,7 @@ #define BGE_ASICREV_BCM5761 0x5761 #define BGE_ASICREV_BCM5784 0x5784 #define BGE_ASICREV_BCM5785 0x5785 +#define BGE_ASICREV_BCM57765 0x57785 #define BGE_ASICREV_BCM57780 0x57780 /* chip revisions */ @@ -381,6 +385,8 @@ #define BGE_PCIDMARWCTL_RD_CMD_SHIFT(x) ((x) << 24) #define BGE_PCIDMARWCTL_WR_CMD_SHIFT(x) ((x) << 28) +#define BGE_PCIDMARWCTL_CRDRDR_RDMA_MRRS_MSK 0x00000380 + #define BGE_PCI_READ_BNDRY_DISABLE 0x00000000 #define BGE_PCI_READ_BNDRY_16BYTES 0x00000100 #define BGE_PCI_READ_BNDRY_32BYTES 0x00000200 @@ -2298,9 +2304,15 @@ struct bge_status_block { #define BCOM_DEVICEID_BCM5906 0x1712 #define BCOM_DEVICEID_BCM5906M 0x1713 #define BCOM_DEVICEID_BCM57760 0x1690 +#define BCOM_DEVICEID_BCM57761 0x16B0 +#define BCOM_DEVICEID_BCM57765 0x16B4 #define BCOM_DEVICEID_BCM57780 0x1692 +#define BCOM_DEVICEID_BCM57781 0x16B1 +#define BCOM_DEVICEID_BCM57785 0x16B5 #define BCOM_DEVICEID_BCM57788 0x1691 #define BCOM_DEVICEID_BCM57790 0x1694 +#define BCOM_DEVICEID_BCM57791 0x16B2 +#define BCOM_DEVICEID_BCM57795 0x16B6 /* * Alteon AceNIC PCI vendor/device ID. -- cgit v1.2.3