linux/drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0-only
   2/*******************************************************************************
   3  This is the driver for the GMAC on-chip Ethernet controller for ST SoCs.
   4  DWC Ether MAC 10/100/1000 Universal version 3.41a  has been used for
   5  developing this code.
   6
   7  This only implements the mac core functions for this chip.
   8
   9  Copyright (C) 2007-2009  STMicroelectronics Ltd
  10
  11
  12  Author: Giuseppe Cavallaro <peppe.cavallaro@st.com>
  13*******************************************************************************/
  14
  15#include <linux/crc32.h>
  16#include <linux/slab.h>
  17#include <linux/ethtool.h>
  18#include <net/dsa.h>
  19#include <asm/io.h>
  20#include "stmmac.h"
  21#include "stmmac_pcs.h"
  22#include "dwmac1000.h"
  23
  24static void dwmac1000_core_init(struct mac_device_info *hw,
  25                                struct net_device *dev)
  26{
  27        void __iomem *ioaddr = hw->pcsr;
  28        u32 value = readl(ioaddr + GMAC_CONTROL);
  29        int mtu = dev->mtu;
  30
  31        /* Configure GMAC core */
  32        value |= GMAC_CORE_INIT;
  33
  34        /* Clear ACS bit because Ethernet switch tagging formats such as
  35         * Broadcom tags can look like invalid LLC/SNAP packets and cause the
  36         * hardware to truncate packets on reception.
  37         */
  38        if (netdev_uses_dsa(dev))
  39                value &= ~GMAC_CONTROL_ACS;
  40
  41        if (mtu > 1500)
  42                value |= GMAC_CONTROL_2K;
  43        if (mtu > 2000)
  44                value |= GMAC_CONTROL_JE;
  45
  46        if (hw->ps) {
  47                value |= GMAC_CONTROL_TE;
  48
  49                value &= ~hw->link.speed_mask;
  50                switch (hw->ps) {
  51                case SPEED_1000:
  52                        value |= hw->link.speed1000;
  53                        break;
  54                case SPEED_100:
  55                        value |= hw->link.speed100;
  56                        break;
  57                case SPEED_10:
  58                        value |= hw->link.speed10;
  59                        break;
  60                }
  61        }
  62
  63        writel(value, ioaddr + GMAC_CONTROL);
  64
  65        /* Mask GMAC interrupts */
  66        value = GMAC_INT_DEFAULT_MASK;
  67
  68        if (hw->pcs)
  69                value &= ~GMAC_INT_DISABLE_PCS;
  70
  71        writel(value, ioaddr + GMAC_INT_MASK);
  72
  73#ifdef STMMAC_VLAN_TAG_USED
  74        /* Tag detection without filtering */
  75        writel(0x0, ioaddr + GMAC_VLAN_TAG);
  76#endif
  77}
  78
  79static int dwmac1000_rx_ipc_enable(struct mac_device_info *hw)
  80{
  81        void __iomem *ioaddr = hw->pcsr;
  82        u32 value = readl(ioaddr + GMAC_CONTROL);
  83
  84        if (hw->rx_csum)
  85                value |= GMAC_CONTROL_IPC;
  86        else
  87                value &= ~GMAC_CONTROL_IPC;
  88
  89        writel(value, ioaddr + GMAC_CONTROL);
  90
  91        value = readl(ioaddr + GMAC_CONTROL);
  92
  93        return !!(value & GMAC_CONTROL_IPC);
  94}
  95
  96static void dwmac1000_dump_regs(struct mac_device_info *hw, u32 *reg_space)
  97{
  98        void __iomem *ioaddr = hw->pcsr;
  99        int i;
 100
 101        for (i = 0; i < 55; i++)
 102                reg_space[i] = readl(ioaddr + i * 4);
 103}
 104
 105static void dwmac1000_set_umac_addr(struct mac_device_info *hw,
 106                                    unsigned char *addr,
 107                                    unsigned int reg_n)
 108{
 109        void __iomem *ioaddr = hw->pcsr;
 110        stmmac_set_mac_addr(ioaddr, addr, GMAC_ADDR_HIGH(reg_n),
 111                            GMAC_ADDR_LOW(reg_n));
 112}
 113
 114static void dwmac1000_get_umac_addr(struct mac_device_info *hw,
 115                                    unsigned char *addr,
 116                                    unsigned int reg_n)
 117{
 118        void __iomem *ioaddr = hw->pcsr;
 119        stmmac_get_mac_addr(ioaddr, addr, GMAC_ADDR_HIGH(reg_n),
 120                            GMAC_ADDR_LOW(reg_n));
 121}
 122
 123static void dwmac1000_set_mchash(void __iomem *ioaddr, u32 *mcfilterbits,
 124                                 int mcbitslog2)
 125{
 126        int numhashregs, regs;
 127
 128        switch (mcbitslog2) {
 129        case 6:
 130                writel(mcfilterbits[0], ioaddr + GMAC_HASH_LOW);
 131                writel(mcfilterbits[1], ioaddr + GMAC_HASH_HIGH);
 132                return;
 133                break;
 134        case 7:
 135                numhashregs = 4;
 136                break;
 137        case 8:
 138                numhashregs = 8;
 139                break;
 140        default:
 141                pr_debug("STMMAC: err in setting multicast filter\n");
 142                return;
 143                break;
 144        }
 145        for (regs = 0; regs < numhashregs; regs++)
 146                writel(mcfilterbits[regs],
 147                       ioaddr + GMAC_EXTHASH_BASE + regs * 4);
 148}
 149
 150static void dwmac1000_set_filter(struct mac_device_info *hw,
 151                                 struct net_device *dev)
 152{
 153        void __iomem *ioaddr = (void __iomem *)dev->base_addr;
 154        unsigned int value = 0;
 155        unsigned int perfect_addr_number = hw->unicast_filter_entries;
 156        u32 mc_filter[8];
 157        int mcbitslog2 = hw->mcast_bits_log2;
 158
 159        pr_debug("%s: # mcasts %d, # unicast %d\n", __func__,
 160                 netdev_mc_count(dev), netdev_uc_count(dev));
 161
 162        memset(mc_filter, 0, sizeof(mc_filter));
 163
 164        if (dev->flags & IFF_PROMISC) {
 165                value = GMAC_FRAME_FILTER_PR;
 166        } else if (dev->flags & IFF_ALLMULTI) {
 167                value = GMAC_FRAME_FILTER_PM;   /* pass all multi */
 168        } else if (!netdev_mc_empty(dev)) {
 169                struct netdev_hw_addr *ha;
 170
 171                /* Hash filter for multicast */
 172                value = GMAC_FRAME_FILTER_HMC;
 173
 174                netdev_for_each_mc_addr(ha, dev) {
 175                        /* The upper n bits of the calculated CRC are used to
 176                         * index the contents of the hash table. The number of
 177                         * bits used depends on the hardware configuration
 178                         * selected at core configuration time.
 179                         */
 180                        int bit_nr = bitrev32(~crc32_le(~0, ha->addr,
 181                                              ETH_ALEN)) >>
 182                                              (32 - mcbitslog2);
 183                        /* The most significant bit determines the register to
 184                         * use (H/L) while the other 5 bits determine the bit
 185                         * within the register.
 186                         */
 187                        mc_filter[bit_nr >> 5] |= 1 << (bit_nr & 31);
 188                }
 189        }
 190
 191        dwmac1000_set_mchash(ioaddr, mc_filter, mcbitslog2);
 192
 193        /* Handle multiple unicast addresses (perfect filtering) */
 194        if (netdev_uc_count(dev) > perfect_addr_number)
 195                /* Switch to promiscuous mode if more than unicast
 196                 * addresses are requested than supported by hardware.
 197                 */
 198                value |= GMAC_FRAME_FILTER_PR;
 199        else {
 200                int reg = 1;
 201                struct netdev_hw_addr *ha;
 202
 203                netdev_for_each_uc_addr(ha, dev) {
 204                        stmmac_set_mac_addr(ioaddr, ha->addr,
 205                                            GMAC_ADDR_HIGH(reg),
 206                                            GMAC_ADDR_LOW(reg));
 207                        reg++;
 208                }
 209        }
 210
 211#ifdef FRAME_FILTER_DEBUG
 212        /* Enable Receive all mode (to debug filtering_fail errors) */
 213        value |= GMAC_FRAME_FILTER_RA;
 214#endif
 215        writel(value, ioaddr + GMAC_FRAME_FILTER);
 216}
 217
 218
 219static void dwmac1000_flow_ctrl(struct mac_device_info *hw, unsigned int duplex,
 220                                unsigned int fc, unsigned int pause_time,
 221                                u32 tx_cnt)
 222{
 223        void __iomem *ioaddr = hw->pcsr;
 224        /* Set flow such that DZPQ in Mac Register 6 is 0,
 225         * and unicast pause detect is enabled.
 226         */
 227        unsigned int flow = GMAC_FLOW_CTRL_UP;
 228
 229        pr_debug("GMAC Flow-Control:\n");
 230        if (fc & FLOW_RX) {
 231                pr_debug("\tReceive Flow-Control ON\n");
 232                flow |= GMAC_FLOW_CTRL_RFE;
 233        }
 234        if (fc & FLOW_TX) {
 235                pr_debug("\tTransmit Flow-Control ON\n");
 236                flow |= GMAC_FLOW_CTRL_TFE;
 237        }
 238
 239        if (duplex) {
 240                pr_debug("\tduplex mode: PAUSE %d\n", pause_time);
 241                flow |= (pause_time << GMAC_FLOW_CTRL_PT_SHIFT);
 242        }
 243
 244        writel(flow, ioaddr + GMAC_FLOW_CTRL);
 245}
 246
 247static void dwmac1000_pmt(struct mac_device_info *hw, unsigned long mode)
 248{
 249        void __iomem *ioaddr = hw->pcsr;
 250        unsigned int pmt = 0;
 251
 252        if (mode & WAKE_MAGIC) {
 253                pr_debug("GMAC: WOL Magic frame\n");
 254                pmt |= power_down | magic_pkt_en;
 255        }
 256        if (mode & WAKE_UCAST) {
 257                pr_debug("GMAC: WOL on global unicast\n");
 258                pmt |= power_down | global_unicast | wake_up_frame_en;
 259        }
 260
 261        writel(pmt, ioaddr + GMAC_PMT);
 262}
 263
 264/* RGMII or SMII interface */
 265static void dwmac1000_rgsmii(void __iomem *ioaddr, struct stmmac_extra_stats *x)
 266{
 267        u32 status;
 268
 269        status = readl(ioaddr + GMAC_RGSMIIIS);
 270        x->irq_rgmii_n++;
 271
 272        /* Check the link status */
 273        if (status & GMAC_RGSMIIIS_LNKSTS) {
 274                int speed_value;
 275
 276                x->pcs_link = 1;
 277
 278                speed_value = ((status & GMAC_RGSMIIIS_SPEED) >>
 279                               GMAC_RGSMIIIS_SPEED_SHIFT);
 280                if (speed_value == GMAC_RGSMIIIS_SPEED_125)
 281                        x->pcs_speed = SPEED_1000;
 282                else if (speed_value == GMAC_RGSMIIIS_SPEED_25)
 283                        x->pcs_speed = SPEED_100;
 284                else
 285                        x->pcs_speed = SPEED_10;
 286
 287                x->pcs_duplex = (status & GMAC_RGSMIIIS_LNKMOD_MASK);
 288
 289                pr_info("Link is Up - %d/%s\n", (int)x->pcs_speed,
 290                        x->pcs_duplex ? "Full" : "Half");
 291        } else {
 292                x->pcs_link = 0;
 293                pr_info("Link is Down\n");
 294        }
 295}
 296
 297static int dwmac1000_irq_status(struct mac_device_info *hw,
 298                                struct stmmac_extra_stats *x)
 299{
 300        void __iomem *ioaddr = hw->pcsr;
 301        u32 intr_status = readl(ioaddr + GMAC_INT_STATUS);
 302        u32 intr_mask = readl(ioaddr + GMAC_INT_MASK);
 303        int ret = 0;
 304
 305        /* Discard masked bits */
 306        intr_status &= ~intr_mask;
 307
 308        /* Not used events (e.g. MMC interrupts) are not handled. */
 309        if ((intr_status & GMAC_INT_STATUS_MMCTIS))
 310                x->mmc_tx_irq_n++;
 311        if (unlikely(intr_status & GMAC_INT_STATUS_MMCRIS))
 312                x->mmc_rx_irq_n++;
 313        if (unlikely(intr_status & GMAC_INT_STATUS_MMCCSUM))
 314                x->mmc_rx_csum_offload_irq_n++;
 315        if (unlikely(intr_status & GMAC_INT_DISABLE_PMT)) {
 316                /* clear the PMT bits 5 and 6 by reading the PMT status reg */
 317                readl(ioaddr + GMAC_PMT);
 318                x->irq_receive_pmt_irq_n++;
 319        }
 320
 321        /* MAC tx/rx EEE LPI entry/exit interrupts */
 322        if (intr_status & GMAC_INT_STATUS_LPIIS) {
 323                /* Clean LPI interrupt by reading the Reg 12 */
 324                ret = readl(ioaddr + LPI_CTRL_STATUS);
 325
 326                if (ret & LPI_CTRL_STATUS_TLPIEN)
 327                        x->irq_tx_path_in_lpi_mode_n++;
 328                if (ret & LPI_CTRL_STATUS_TLPIEX)
 329                        x->irq_tx_path_exit_lpi_mode_n++;
 330                if (ret & LPI_CTRL_STATUS_RLPIEN)
 331                        x->irq_rx_path_in_lpi_mode_n++;
 332                if (ret & LPI_CTRL_STATUS_RLPIEX)
 333                        x->irq_rx_path_exit_lpi_mode_n++;
 334        }
 335
 336        dwmac_pcs_isr(ioaddr, GMAC_PCS_BASE, intr_status, x);
 337
 338        if (intr_status & PCS_RGSMIIIS_IRQ)
 339                dwmac1000_rgsmii(ioaddr, x);
 340
 341        return ret;
 342}
 343
 344static void dwmac1000_set_eee_mode(struct mac_device_info *hw,
 345                                   bool en_tx_lpi_clockgating)
 346{
 347        void __iomem *ioaddr = hw->pcsr;
 348        u32 value;
 349
 350        /*TODO - en_tx_lpi_clockgating treatment */
 351
 352        /* Enable the link status receive on RGMII, SGMII ore SMII
 353         * receive path and instruct the transmit to enter in LPI
 354         * state.
 355         */
 356        value = readl(ioaddr + LPI_CTRL_STATUS);
 357        value |= LPI_CTRL_STATUS_LPIEN | LPI_CTRL_STATUS_LPITXA;
 358        writel(value, ioaddr + LPI_CTRL_STATUS);
 359}
 360
 361static void dwmac1000_reset_eee_mode(struct mac_device_info *hw)
 362{
 363        void __iomem *ioaddr = hw->pcsr;
 364        u32 value;
 365
 366        value = readl(ioaddr + LPI_CTRL_STATUS);
 367        value &= ~(LPI_CTRL_STATUS_LPIEN | LPI_CTRL_STATUS_LPITXA);
 368        writel(value, ioaddr + LPI_CTRL_STATUS);
 369}
 370
 371static void dwmac1000_set_eee_pls(struct mac_device_info *hw, int link)
 372{
 373        void __iomem *ioaddr = hw->pcsr;
 374        u32 value;
 375
 376        value = readl(ioaddr + LPI_CTRL_STATUS);
 377
 378        if (link)
 379                value |= LPI_CTRL_STATUS_PLS;
 380        else
 381                value &= ~LPI_CTRL_STATUS_PLS;
 382
 383        writel(value, ioaddr + LPI_CTRL_STATUS);
 384}
 385
 386static void dwmac1000_set_eee_timer(struct mac_device_info *hw, int ls, int tw)
 387{
 388        void __iomem *ioaddr = hw->pcsr;
 389        int value = ((tw & 0xffff)) | ((ls & 0x7ff) << 16);
 390
 391        /* Program the timers in the LPI timer control register:
 392         * LS: minimum time (ms) for which the link
 393         *  status from PHY should be ok before transmitting
 394         *  the LPI pattern.
 395         * TW: minimum time (us) for which the core waits
 396         *  after it has stopped transmitting the LPI pattern.
 397         */
 398        writel(value, ioaddr + LPI_TIMER_CTRL);
 399}
 400
 401static void dwmac1000_ctrl_ane(void __iomem *ioaddr, bool ane, bool srgmi_ral,
 402                               bool loopback)
 403{
 404        dwmac_ctrl_ane(ioaddr, GMAC_PCS_BASE, ane, srgmi_ral, loopback);
 405}
 406
 407static void dwmac1000_rane(void __iomem *ioaddr, bool restart)
 408{
 409        dwmac_rane(ioaddr, GMAC_PCS_BASE, restart);
 410}
 411
 412static void dwmac1000_get_adv_lp(void __iomem *ioaddr, struct rgmii_adv *adv)
 413{
 414        dwmac_get_adv_lp(ioaddr, GMAC_PCS_BASE, adv);
 415}
 416
 417static void dwmac1000_debug(void __iomem *ioaddr, struct stmmac_extra_stats *x,
 418                            u32 rx_queues, u32 tx_queues)
 419{
 420        u32 value = readl(ioaddr + GMAC_DEBUG);
 421
 422        if (value & GMAC_DEBUG_TXSTSFSTS)
 423                x->mtl_tx_status_fifo_full++;
 424        if (value & GMAC_DEBUG_TXFSTS)
 425                x->mtl_tx_fifo_not_empty++;
 426        if (value & GMAC_DEBUG_TWCSTS)
 427                x->mmtl_fifo_ctrl++;
 428        if (value & GMAC_DEBUG_TRCSTS_MASK) {
 429                u32 trcsts = (value & GMAC_DEBUG_TRCSTS_MASK)
 430                             >> GMAC_DEBUG_TRCSTS_SHIFT;
 431                if (trcsts == GMAC_DEBUG_TRCSTS_WRITE)
 432                        x->mtl_tx_fifo_read_ctrl_write++;
 433                else if (trcsts == GMAC_DEBUG_TRCSTS_TXW)
 434                        x->mtl_tx_fifo_read_ctrl_wait++;
 435                else if (trcsts == GMAC_DEBUG_TRCSTS_READ)
 436                        x->mtl_tx_fifo_read_ctrl_read++;
 437                else
 438                        x->mtl_tx_fifo_read_ctrl_idle++;
 439        }
 440        if (value & GMAC_DEBUG_TXPAUSED)
 441                x->mac_tx_in_pause++;
 442        if (value & GMAC_DEBUG_TFCSTS_MASK) {
 443                u32 tfcsts = (value & GMAC_DEBUG_TFCSTS_MASK)
 444                              >> GMAC_DEBUG_TFCSTS_SHIFT;
 445
 446                if (tfcsts == GMAC_DEBUG_TFCSTS_XFER)
 447                        x->mac_tx_frame_ctrl_xfer++;
 448                else if (tfcsts == GMAC_DEBUG_TFCSTS_GEN_PAUSE)
 449                        x->mac_tx_frame_ctrl_pause++;
 450                else if (tfcsts == GMAC_DEBUG_TFCSTS_WAIT)
 451                        x->mac_tx_frame_ctrl_wait++;
 452                else
 453                        x->mac_tx_frame_ctrl_idle++;
 454        }
 455        if (value & GMAC_DEBUG_TPESTS)
 456                x->mac_gmii_tx_proto_engine++;
 457        if (value & GMAC_DEBUG_RXFSTS_MASK) {
 458                u32 rxfsts = (value & GMAC_DEBUG_RXFSTS_MASK)
 459                             >> GMAC_DEBUG_RRCSTS_SHIFT;
 460
 461                if (rxfsts == GMAC_DEBUG_RXFSTS_FULL)
 462                        x->mtl_rx_fifo_fill_level_full++;
 463                else if (rxfsts == GMAC_DEBUG_RXFSTS_AT)
 464                        x->mtl_rx_fifo_fill_above_thresh++;
 465                else if (rxfsts == GMAC_DEBUG_RXFSTS_BT)
 466                        x->mtl_rx_fifo_fill_below_thresh++;
 467                else
 468                        x->mtl_rx_fifo_fill_level_empty++;
 469        }
 470        if (value & GMAC_DEBUG_RRCSTS_MASK) {
 471                u32 rrcsts = (value & GMAC_DEBUG_RRCSTS_MASK) >>
 472                             GMAC_DEBUG_RRCSTS_SHIFT;
 473
 474                if (rrcsts == GMAC_DEBUG_RRCSTS_FLUSH)
 475                        x->mtl_rx_fifo_read_ctrl_flush++;
 476                else if (rrcsts == GMAC_DEBUG_RRCSTS_RSTAT)
 477                        x->mtl_rx_fifo_read_ctrl_read_data++;
 478                else if (rrcsts == GMAC_DEBUG_RRCSTS_RDATA)
 479                        x->mtl_rx_fifo_read_ctrl_status++;
 480                else
 481                        x->mtl_rx_fifo_read_ctrl_idle++;
 482        }
 483        if (value & GMAC_DEBUG_RWCSTS)
 484                x->mtl_rx_fifo_ctrl_active++;
 485        if (value & GMAC_DEBUG_RFCFCSTS_MASK)
 486                x->mac_rx_frame_ctrl_fifo = (value & GMAC_DEBUG_RFCFCSTS_MASK)
 487                                            >> GMAC_DEBUG_RFCFCSTS_SHIFT;
 488        if (value & GMAC_DEBUG_RPESTS)
 489                x->mac_gmii_rx_proto_engine++;
 490}
 491
 492const struct stmmac_ops dwmac1000_ops = {
 493        .core_init = dwmac1000_core_init,
 494        .set_mac = stmmac_set_mac,
 495        .rx_ipc = dwmac1000_rx_ipc_enable,
 496        .dump_regs = dwmac1000_dump_regs,
 497        .host_irq_status = dwmac1000_irq_status,
 498        .set_filter = dwmac1000_set_filter,
 499        .flow_ctrl = dwmac1000_flow_ctrl,
 500        .pmt = dwmac1000_pmt,
 501        .set_umac_addr = dwmac1000_set_umac_addr,
 502        .get_umac_addr = dwmac1000_get_umac_addr,
 503        .set_eee_mode = dwmac1000_set_eee_mode,
 504        .reset_eee_mode = dwmac1000_reset_eee_mode,
 505        .set_eee_timer = dwmac1000_set_eee_timer,
 506        .set_eee_pls = dwmac1000_set_eee_pls,
 507        .debug = dwmac1000_debug,
 508        .pcs_ctrl_ane = dwmac1000_ctrl_ane,
 509        .pcs_rane = dwmac1000_rane,
 510        .pcs_get_adv_lp = dwmac1000_get_adv_lp,
 511};
 512
 513int dwmac1000_setup(struct stmmac_priv *priv)
 514{
 515        struct mac_device_info *mac = priv->hw;
 516
 517        dev_info(priv->device, "\tDWMAC1000\n");
 518
 519        priv->dev->priv_flags |= IFF_UNICAST_FLT;
 520        mac->pcsr = priv->ioaddr;
 521        mac->multicast_filter_bins = priv->plat->multicast_filter_bins;
 522        mac->unicast_filter_entries = priv->plat->unicast_filter_entries;
 523        mac->mcast_bits_log2 = 0;
 524
 525        if (mac->multicast_filter_bins)
 526                mac->mcast_bits_log2 = ilog2(mac->multicast_filter_bins);
 527
 528        mac->link.duplex = GMAC_CONTROL_DM;
 529        mac->link.speed10 = GMAC_CONTROL_PS;
 530        mac->link.speed100 = GMAC_CONTROL_PS | GMAC_CONTROL_FES;
 531        mac->link.speed1000 = 0;
 532        mac->link.speed_mask = GMAC_CONTROL_PS | GMAC_CONTROL_FES;
 533        mac->mii.addr = GMAC_MII_ADDR;
 534        mac->mii.data = GMAC_MII_DATA;
 535        mac->mii.addr_shift = 11;
 536        mac->mii.addr_mask = 0x0000F800;
 537        mac->mii.reg_shift = 6;
 538        mac->mii.reg_mask = 0x000007C0;
 539        mac->mii.clk_csr_shift = 2;
 540        mac->mii.clk_csr_mask = GENMASK(5, 2);
 541
 542        return 0;
 543}
 544