1 /* 2 * This is the driver for the GMAC on-chip Ethernet controller for ST SoCs. 3 * DWC Ether MAC version 4.00 has been used for developing this code. 4 * 5 * This only implements the mac core functions for this chip. 6 * 7 * Copyright (C) 2015 STMicroelectronics Ltd 8 * 9 * This program is free software; you can redistribute it and/or modify it 10 * under the terms and conditions of the GNU General Public License, 11 * version 2, as published by the Free Software Foundation. 12 * 13 * Author: Alexandre Torgue <alexandre.torgue@st.com> 14 */ 15 16 #include <linux/crc32.h> 17 #include <linux/slab.h> 18 #include <linux/ethtool.h> 19 #include <linux/io.h> 20 #include "dwmac4.h" 21 22 static void dwmac4_core_init(struct mac_device_info *hw, int mtu) 23 { 24 void __iomem *ioaddr = hw->pcsr; 25 u32 value = readl(ioaddr + GMAC_CONFIG); 26 27 value |= GMAC_CORE_INIT; 28 29 if (mtu > 1500) 30 value |= GMAC_CONFIG_2K; 31 if (mtu > 2000) 32 value |= GMAC_CONFIG_JE; 33 34 writel(value, ioaddr + GMAC_CONFIG); 35 36 /* Mask GMAC interrupts */ 37 writel(GMAC_INT_PMT_EN, ioaddr + GMAC_INT_EN); 38 } 39 40 static void dwmac4_dump_regs(struct mac_device_info *hw) 41 { 42 void __iomem *ioaddr = hw->pcsr; 43 int i; 44 45 pr_debug("\tDWMAC4 regs (base addr = 0x%p)\n", ioaddr); 46 47 for (i = 0; i < GMAC_REG_NUM; i++) { 48 int offset = i * 4; 49 50 pr_debug("\tReg No. %d (offset 0x%x): 0x%08x\n", i, 51 offset, readl(ioaddr + offset)); 52 } 53 } 54 55 static int dwmac4_rx_ipc_enable(struct mac_device_info *hw) 56 { 57 void __iomem *ioaddr = hw->pcsr; 58 u32 value = readl(ioaddr + GMAC_CONFIG); 59 60 if (hw->rx_csum) 61 value |= GMAC_CONFIG_IPC; 62 else 63 value &= ~GMAC_CONFIG_IPC; 64 65 writel(value, ioaddr + GMAC_CONFIG); 66 67 value = readl(ioaddr + GMAC_CONFIG); 68 69 return !!(value & GMAC_CONFIG_IPC); 70 } 71 72 static void dwmac4_pmt(struct mac_device_info *hw, unsigned long mode) 73 { 74 void __iomem *ioaddr = hw->pcsr; 75 unsigned int pmt = 0; 76 77 if (mode & WAKE_MAGIC) { 78 pr_debug("GMAC: WOL Magic frame\n"); 79 pmt |= power_down | magic_pkt_en; 80 } 81 if (mode & WAKE_UCAST) { 82 pr_debug("GMAC: WOL on global unicast\n"); 83 pmt |= global_unicast; 84 } 85 86 writel(pmt, ioaddr + GMAC_PMT); 87 } 88 89 static void dwmac4_set_umac_addr(struct mac_device_info *hw, 90 unsigned char *addr, unsigned int reg_n) 91 { 92 void __iomem *ioaddr = hw->pcsr; 93 94 stmmac_dwmac4_set_mac_addr(ioaddr, addr, GMAC_ADDR_HIGH(reg_n), 95 GMAC_ADDR_LOW(reg_n)); 96 } 97 98 static void dwmac4_get_umac_addr(struct mac_device_info *hw, 99 unsigned char *addr, unsigned int reg_n) 100 { 101 void __iomem *ioaddr = hw->pcsr; 102 103 stmmac_dwmac4_get_mac_addr(ioaddr, addr, GMAC_ADDR_HIGH(reg_n), 104 GMAC_ADDR_LOW(reg_n)); 105 } 106 107 static void dwmac4_set_filter(struct mac_device_info *hw, 108 struct net_device *dev) 109 { 110 void __iomem *ioaddr = (void __iomem *)dev->base_addr; 111 unsigned int value = 0; 112 113 if (dev->flags & IFF_PROMISC) { 114 value = GMAC_PACKET_FILTER_PR; 115 } else if ((dev->flags & IFF_ALLMULTI) || 116 (netdev_mc_count(dev) > HASH_TABLE_SIZE)) { 117 /* Pass all multi */ 118 value = GMAC_PACKET_FILTER_PM; 119 /* Set the 64 bits of the HASH tab. To be updated if taller 120 * hash table is used 121 */ 122 writel(0xffffffff, ioaddr + GMAC_HASH_TAB_0_31); 123 writel(0xffffffff, ioaddr + GMAC_HASH_TAB_32_63); 124 } else if (!netdev_mc_empty(dev)) { 125 u32 mc_filter[2]; 126 struct netdev_hw_addr *ha; 127 128 /* Hash filter for multicast */ 129 value = GMAC_PACKET_FILTER_HMC; 130 131 memset(mc_filter, 0, sizeof(mc_filter)); 132 netdev_for_each_mc_addr(ha, dev) { 133 /* The upper 6 bits of the calculated CRC are used to 134 * index the content of the Hash Table Reg 0 and 1. 135 */ 136 int bit_nr = 137 (bitrev32(~crc32_le(~0, ha->addr, 6)) >> 26); 138 /* The most significant bit determines the register 139 * to use while the other 5 bits determines the bit 140 * within the selected register 141 */ 142 mc_filter[bit_nr >> 5] |= (1 << (bit_nr & 0x1F)); 143 } 144 writel(mc_filter[0], ioaddr + GMAC_HASH_TAB_0_31); 145 writel(mc_filter[1], ioaddr + GMAC_HASH_TAB_32_63); 146 } 147 148 /* Handle multiple unicast addresses */ 149 if (netdev_uc_count(dev) > GMAC_MAX_PERFECT_ADDRESSES) { 150 /* Switch to promiscuous mode if more than 128 addrs 151 * are required 152 */ 153 value |= GMAC_PACKET_FILTER_PR; 154 } else if (!netdev_uc_empty(dev)) { 155 int reg = 1; 156 struct netdev_hw_addr *ha; 157 158 netdev_for_each_uc_addr(ha, dev) { 159 dwmac4_set_umac_addr(ioaddr, ha->addr, reg); 160 reg++; 161 } 162 } 163 164 writel(value, ioaddr + GMAC_PACKET_FILTER); 165 } 166 167 static void dwmac4_flow_ctrl(struct mac_device_info *hw, unsigned int duplex, 168 unsigned int fc, unsigned int pause_time) 169 { 170 void __iomem *ioaddr = hw->pcsr; 171 u32 channel = STMMAC_CHAN0; /* FIXME */ 172 unsigned int flow = 0; 173 174 pr_debug("GMAC Flow-Control:\n"); 175 if (fc & FLOW_RX) { 176 pr_debug("\tReceive Flow-Control ON\n"); 177 flow |= GMAC_RX_FLOW_CTRL_RFE; 178 writel(flow, ioaddr + GMAC_RX_FLOW_CTRL); 179 } 180 if (fc & FLOW_TX) { 181 pr_debug("\tTransmit Flow-Control ON\n"); 182 flow |= GMAC_TX_FLOW_CTRL_TFE; 183 writel(flow, ioaddr + GMAC_QX_TX_FLOW_CTRL(channel)); 184 185 if (duplex) { 186 pr_debug("\tduplex mode: PAUSE %d\n", pause_time); 187 flow |= (pause_time << GMAC_TX_FLOW_CTRL_PT_SHIFT); 188 writel(flow, ioaddr + GMAC_QX_TX_FLOW_CTRL(channel)); 189 } 190 } 191 } 192 193 static void dwmac4_ctrl_ane(struct mac_device_info *hw, bool restart) 194 { 195 void __iomem *ioaddr = hw->pcsr; 196 197 /* auto negotiation enable and External Loopback enable */ 198 u32 value = GMAC_AN_CTRL_ANE | GMAC_AN_CTRL_ELE; 199 200 if (restart) 201 value |= GMAC_AN_CTRL_RAN; 202 203 writel(value, ioaddr + GMAC_AN_CTRL); 204 } 205 206 static void dwmac4_get_adv(struct mac_device_info *hw, struct rgmii_adv *adv) 207 { 208 void __iomem *ioaddr = hw->pcsr; 209 u32 value = readl(ioaddr + GMAC_AN_ADV); 210 211 if (value & GMAC_AN_FD) 212 adv->duplex = DUPLEX_FULL; 213 if (value & GMAC_AN_HD) 214 adv->duplex |= DUPLEX_HALF; 215 216 adv->pause = (value & GMAC_AN_PSE_MASK) >> GMAC_AN_PSE_SHIFT; 217 218 value = readl(ioaddr + GMAC_AN_LPA); 219 220 if (value & GMAC_AN_FD) 221 adv->lp_duplex = DUPLEX_FULL; 222 if (value & GMAC_AN_HD) 223 adv->lp_duplex = DUPLEX_HALF; 224 225 adv->lp_pause = (value & GMAC_AN_PSE_MASK) >> GMAC_AN_PSE_SHIFT; 226 } 227 228 static int dwmac4_irq_status(struct mac_device_info *hw, 229 struct stmmac_extra_stats *x) 230 { 231 void __iomem *ioaddr = hw->pcsr; 232 u32 mtl_int_qx_status; 233 u32 intr_status; 234 int ret = 0; 235 236 intr_status = readl(ioaddr + GMAC_INT_STATUS); 237 238 /* Not used events (e.g. MMC interrupts) are not handled. */ 239 if ((intr_status & mmc_tx_irq)) 240 x->mmc_tx_irq_n++; 241 if (unlikely(intr_status & mmc_rx_irq)) 242 x->mmc_rx_irq_n++; 243 if (unlikely(intr_status & mmc_rx_csum_offload_irq)) 244 x->mmc_rx_csum_offload_irq_n++; 245 /* Clear the PMT bits 5 and 6 by reading the PMT status reg */ 246 if (unlikely(intr_status & pmt_irq)) { 247 readl(ioaddr + GMAC_PMT); 248 x->irq_receive_pmt_irq_n++; 249 } 250 251 if ((intr_status & pcs_ane_irq) || (intr_status & pcs_link_irq)) { 252 readl(ioaddr + GMAC_AN_STATUS); 253 x->irq_pcs_ane_n++; 254 } 255 256 mtl_int_qx_status = readl(ioaddr + MTL_INT_STATUS); 257 /* Check MTL Interrupt: Currently only one queue is used: Q0. */ 258 if (mtl_int_qx_status & MTL_INT_Q0) { 259 /* read Queue 0 Interrupt status */ 260 u32 status = readl(ioaddr + MTL_CHAN_INT_CTRL(STMMAC_CHAN0)); 261 262 if (status & MTL_RX_OVERFLOW_INT) { 263 /* clear Interrupt */ 264 writel(status | MTL_RX_OVERFLOW_INT, 265 ioaddr + MTL_CHAN_INT_CTRL(STMMAC_CHAN0)); 266 ret = CORE_IRQ_MTL_RX_OVERFLOW; 267 } 268 } 269 270 return ret; 271 } 272 273 static void dwmac4_debug(void __iomem *ioaddr, struct stmmac_extra_stats *x) 274 { 275 u32 value; 276 277 /* Currently only channel 0 is supported */ 278 value = readl(ioaddr + MTL_CHAN_TX_DEBUG(STMMAC_CHAN0)); 279 280 if (value & MTL_DEBUG_TXSTSFSTS) 281 x->mtl_tx_status_fifo_full++; 282 if (value & MTL_DEBUG_TXFSTS) 283 x->mtl_tx_fifo_not_empty++; 284 if (value & MTL_DEBUG_TWCSTS) 285 x->mmtl_fifo_ctrl++; 286 if (value & MTL_DEBUG_TRCSTS_MASK) { 287 u32 trcsts = (value & MTL_DEBUG_TRCSTS_MASK) 288 >> MTL_DEBUG_TRCSTS_SHIFT; 289 if (trcsts == MTL_DEBUG_TRCSTS_WRITE) 290 x->mtl_tx_fifo_read_ctrl_write++; 291 else if (trcsts == MTL_DEBUG_TRCSTS_TXW) 292 x->mtl_tx_fifo_read_ctrl_wait++; 293 else if (trcsts == MTL_DEBUG_TRCSTS_READ) 294 x->mtl_tx_fifo_read_ctrl_read++; 295 else 296 x->mtl_tx_fifo_read_ctrl_idle++; 297 } 298 if (value & MTL_DEBUG_TXPAUSED) 299 x->mac_tx_in_pause++; 300 301 value = readl(ioaddr + MTL_CHAN_RX_DEBUG(STMMAC_CHAN0)); 302 303 if (value & MTL_DEBUG_RXFSTS_MASK) { 304 u32 rxfsts = (value & MTL_DEBUG_RXFSTS_MASK) 305 >> MTL_DEBUG_RRCSTS_SHIFT; 306 307 if (rxfsts == MTL_DEBUG_RXFSTS_FULL) 308 x->mtl_rx_fifo_fill_level_full++; 309 else if (rxfsts == MTL_DEBUG_RXFSTS_AT) 310 x->mtl_rx_fifo_fill_above_thresh++; 311 else if (rxfsts == MTL_DEBUG_RXFSTS_BT) 312 x->mtl_rx_fifo_fill_below_thresh++; 313 else 314 x->mtl_rx_fifo_fill_level_empty++; 315 } 316 if (value & MTL_DEBUG_RRCSTS_MASK) { 317 u32 rrcsts = (value & MTL_DEBUG_RRCSTS_MASK) >> 318 MTL_DEBUG_RRCSTS_SHIFT; 319 320 if (rrcsts == MTL_DEBUG_RRCSTS_FLUSH) 321 x->mtl_rx_fifo_read_ctrl_flush++; 322 else if (rrcsts == MTL_DEBUG_RRCSTS_RSTAT) 323 x->mtl_rx_fifo_read_ctrl_read_data++; 324 else if (rrcsts == MTL_DEBUG_RRCSTS_RDATA) 325 x->mtl_rx_fifo_read_ctrl_status++; 326 else 327 x->mtl_rx_fifo_read_ctrl_idle++; 328 } 329 if (value & MTL_DEBUG_RWCSTS) 330 x->mtl_rx_fifo_ctrl_active++; 331 332 /* GMAC debug */ 333 value = readl(ioaddr + GMAC_DEBUG); 334 335 if (value & GMAC_DEBUG_TFCSTS_MASK) { 336 u32 tfcsts = (value & GMAC_DEBUG_TFCSTS_MASK) 337 >> GMAC_DEBUG_TFCSTS_SHIFT; 338 339 if (tfcsts == GMAC_DEBUG_TFCSTS_XFER) 340 x->mac_tx_frame_ctrl_xfer++; 341 else if (tfcsts == GMAC_DEBUG_TFCSTS_GEN_PAUSE) 342 x->mac_tx_frame_ctrl_pause++; 343 else if (tfcsts == GMAC_DEBUG_TFCSTS_WAIT) 344 x->mac_tx_frame_ctrl_wait++; 345 else 346 x->mac_tx_frame_ctrl_idle++; 347 } 348 if (value & GMAC_DEBUG_TPESTS) 349 x->mac_gmii_tx_proto_engine++; 350 if (value & GMAC_DEBUG_RFCFCSTS_MASK) 351 x->mac_rx_frame_ctrl_fifo = (value & GMAC_DEBUG_RFCFCSTS_MASK) 352 >> GMAC_DEBUG_RFCFCSTS_SHIFT; 353 if (value & GMAC_DEBUG_RPESTS) 354 x->mac_gmii_rx_proto_engine++; 355 } 356 357 static const struct stmmac_ops dwmac4_ops = { 358 .core_init = dwmac4_core_init, 359 .rx_ipc = dwmac4_rx_ipc_enable, 360 .dump_regs = dwmac4_dump_regs, 361 .host_irq_status = dwmac4_irq_status, 362 .flow_ctrl = dwmac4_flow_ctrl, 363 .pmt = dwmac4_pmt, 364 .set_umac_addr = dwmac4_set_umac_addr, 365 .get_umac_addr = dwmac4_get_umac_addr, 366 .ctrl_ane = dwmac4_ctrl_ane, 367 .get_adv = dwmac4_get_adv, 368 .debug = dwmac4_debug, 369 .set_filter = dwmac4_set_filter, 370 }; 371 372 struct mac_device_info *dwmac4_setup(void __iomem *ioaddr, int mcbins, 373 int perfect_uc_entries, int *synopsys_id) 374 { 375 struct mac_device_info *mac; 376 u32 hwid = readl(ioaddr + GMAC_VERSION); 377 378 mac = kzalloc(sizeof(const struct mac_device_info), GFP_KERNEL); 379 if (!mac) 380 return NULL; 381 382 mac->pcsr = ioaddr; 383 mac->multicast_filter_bins = mcbins; 384 mac->unicast_filter_entries = perfect_uc_entries; 385 mac->mcast_bits_log2 = 0; 386 387 if (mac->multicast_filter_bins) 388 mac->mcast_bits_log2 = ilog2(mac->multicast_filter_bins); 389 390 mac->mac = &dwmac4_ops; 391 392 mac->link.port = GMAC_CONFIG_PS; 393 mac->link.duplex = GMAC_CONFIG_DM; 394 mac->link.speed = GMAC_CONFIG_FES; 395 mac->mii.addr = GMAC_MDIO_ADDR; 396 mac->mii.data = GMAC_MDIO_DATA; 397 398 /* Get and dump the chip ID */ 399 *synopsys_id = stmmac_get_synopsys_id(hwid); 400 401 if (*synopsys_id > DWMAC_CORE_4_00) 402 mac->dma = &dwmac410_dma_ops; 403 else 404 mac->dma = &dwmac4_dma_ops; 405 406 return mac; 407 } 408