Index: sys/dev/cadence/if_cgem.c =================================================================== --- sys/dev/cadence/if_cgem.c +++ sys/dev/cadence/if_cgem.c @@ -76,6 +76,7 @@ #include #include +#include #include @@ -100,18 +101,21 @@ #define CGEM_CKSUM_ASSIST (CSUM_IP | CSUM_TCP | CSUM_UDP | \ CSUM_TCP_IPV6 | CSUM_UDP_IPV6) -#define HWTYPE_GENERIC_GEM 1 -#define HWTYPE_ZYNQ 2 -#define HWTYPE_ZYNQMP 3 -#define HWTYPE_SIFIVE 4 +#define HWQUIRK_NONE 0 +#define HWQUIRK_NEEDNULLQS 1 +#define HWQUIRK_RXHANGWAR 2 +#define HWQUIRK_TXCLK 4 +#define HWQUIRK_PCLK 8 static struct ofw_compat_data compat_data[] = { - { "cdns,zynq-gem", HWTYPE_ZYNQ }, - { "cdns,zynqmp-gem", HWTYPE_ZYNQMP }, - { "sifive,fu540-c000-gem", HWTYPE_SIFIVE }, - { "sifive,fu740-c000-gem", HWTYPE_SIFIVE }, - { "cdns,gem", HWTYPE_GENERIC_GEM }, - { "cadence,gem", HWTYPE_GENERIC_GEM }, + { "cdns,zynq-gem", HWQUIRK_RXHANGWAR | HWQUIRK_TXCLK }, + { "cdns,zynqmp-gem", HWQUIRK_NEEDNULLQS | HWQUIRK_TXCLK }, + { "microchip,mpfs-mss-gem", HWQUIRK_NEEDNULLQS | HWQUIRK_TXCLK }, + { "sifive,fu540-c000-gem", HWQUIRK_PCLK }, + { "sifive,fu740-c000-gem", HWQUIRK_PCLK }, + { "cdns,gem", HWQUIRK_NONE }, + { "cdns,macb", HWQUIRK_NONE }, + { "cadence,gem", HWQUIRK_NONE }, { NULL, 0 } }; @@ -130,6 +134,7 @@ uint32_t net_cfg_shadow; clk_t ref_clk; int neednullqs; + int phy_contype; bus_dma_tag_t desc_dma_tag; bus_dma_tag_t mbuf_dma_tag; @@ -1083,6 +1088,12 @@ CGEM_NET_CFG_GIGE_EN | CGEM_NET_CFG_1536RXEN | CGEM_NET_CFG_FULL_DUPLEX | CGEM_NET_CFG_SPEED100); + /* Check connection type, enable SGMII bits if necessary. */ + if (sc->phy_contype == MII_CONTYPE_SGMII) { + sc->net_cfg_shadow |= CGEM_NET_CFG_SGMII_EN; + sc->net_cfg_shadow |= CGEM_NET_CFG_PCS_SEL; + } + /* Enable receive checksum offloading? */ if ((if_getcapenable(ifp) & IFCAP_RXCSUM) != 0) sc->net_cfg_shadow |= CGEM_NET_CFG_RX_CHKSUM_OFFLD_EN; @@ -1712,7 +1723,7 @@ if (!ofw_bus_status_okay(dev)) return (ENXIO); - if (ofw_bus_search_compatible(dev, compat_data)->ocd_data == 0) + if (ofw_bus_search_compatible(dev, compat_data)->ocd_str == NULL) return (ENXIO); device_set_desc(dev, "Cadence CGEM Gigabit Ethernet Interface"); @@ -1726,25 +1737,26 @@ if_t ifp = NULL; int rid, err; u_char eaddr[ETHER_ADDR_LEN]; - int hwtype; + int hwquirks; + phandle_t node; sc->dev = dev; CGEM_LOCK_INIT(sc); /* Key off of compatible string and set hardware-specific options. */ - hwtype = ofw_bus_search_compatible(dev, compat_data)->ocd_data; - if (hwtype == HWTYPE_ZYNQMP) + hwquirks = ofw_bus_search_compatible(dev, compat_data)->ocd_data; + if ((hwquirks & HWQUIRK_NEEDNULLQS) != 0) sc->neednullqs = 1; - if (hwtype == HWTYPE_ZYNQ) + if ((hwquirks & HWQUIRK_RXHANGWAR) != 0) sc->rxhangwar = 1; - - if (hwtype == HWTYPE_ZYNQ || hwtype == HWTYPE_ZYNQMP) { + if ((hwquirks & HWQUIRK_TXCLK) != 0) { if (clk_get_by_ofw_name(dev, 0, "tx_clk", &sc->ref_clk) != 0) device_printf(dev, "could not retrieve reference clock.\n"); else if (clk_enable(sc->ref_clk) != 0) device_printf(dev, "could not enable clock.\n"); - } else if (hwtype == HWTYPE_SIFIVE) { + } + if ((hwquirks & HWQUIRK_PCLK) != 0) { if (clk_get_by_ofw_name(dev, 0, "pclk", &sc->ref_clk) != 0) device_printf(dev, "could not retrieve reference clock.\n"); @@ -1752,6 +1764,9 @@ device_printf(dev, "could not enable clock.\n"); } + node = ofw_bus_get_node(dev); + sc->phy_contype = mii_fdt_get_contype(node); + /* Get memory resource. */ rid = 0; sc->mem_res = bus_alloc_resource_any(dev, SYS_RES_MEMORY, &rid, Index: sys/dev/cadence/if_cgem_hw.h =================================================================== --- sys/dev/cadence/if_cgem_hw.h +++ sys/dev/cadence/if_cgem_hw.h @@ -63,7 +63,7 @@ #define CGEM_NET_CTRL_RX_EN (1 << 2) #define CGEM_NET_CTRL_LOOP_LOCAL (1 << 1) -#define CGEM_NET_CFG 0x004 /* Netowrk Configuration */ +#define CGEM_NET_CFG 0x004 /* Network Configuration */ #define CGEM_NET_CFG_UNIDIR_EN (1U << 31) #define CGEM_NET_CFG_IGNORE_IPG_RX_ER (1 << 30) #define CGEM_NET_CFG_RX_BAD_PREAMBLE (1 << 29)