17ac6653aSJeff Kirsher /*******************************************************************************
27ac6653aSJeff Kirsher   This is the driver for the ST MAC 10/100/1000 on-chip Ethernet controllers.
37ac6653aSJeff Kirsher   ST Ethernet IPs are built around a Synopsys IP Core.
47ac6653aSJeff Kirsher 
5286a8372SGiuseppe CAVALLARO 	Copyright(C) 2007-2011 STMicroelectronics Ltd
67ac6653aSJeff Kirsher 
77ac6653aSJeff Kirsher   This program is free software; you can redistribute it and/or modify it
87ac6653aSJeff Kirsher   under the terms and conditions of the GNU General Public License,
97ac6653aSJeff Kirsher   version 2, as published by the Free Software Foundation.
107ac6653aSJeff Kirsher 
117ac6653aSJeff Kirsher   This program is distributed in the hope it will be useful, but WITHOUT
127ac6653aSJeff Kirsher   ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
137ac6653aSJeff Kirsher   FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
147ac6653aSJeff Kirsher   more details.
157ac6653aSJeff Kirsher 
167ac6653aSJeff Kirsher   You should have received a copy of the GNU General Public License along with
177ac6653aSJeff Kirsher   this program; if not, write to the Free Software Foundation, Inc.,
187ac6653aSJeff Kirsher   51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
197ac6653aSJeff Kirsher 
207ac6653aSJeff Kirsher   The full GNU General Public License is included in this distribution in
217ac6653aSJeff Kirsher   the file called "COPYING".
227ac6653aSJeff Kirsher 
237ac6653aSJeff Kirsher   Author: Giuseppe Cavallaro <peppe.cavallaro@st.com>
247ac6653aSJeff Kirsher 
257ac6653aSJeff Kirsher   Documentation available at:
267ac6653aSJeff Kirsher 	http://www.stlinux.com
277ac6653aSJeff Kirsher   Support available at:
287ac6653aSJeff Kirsher 	https://bugzilla.stlinux.com/
297ac6653aSJeff Kirsher *******************************************************************************/
307ac6653aSJeff Kirsher 
317ac6653aSJeff Kirsher #include <linux/kernel.h>
327ac6653aSJeff Kirsher #include <linux/interrupt.h>
337ac6653aSJeff Kirsher #include <linux/ip.h>
347ac6653aSJeff Kirsher #include <linux/tcp.h>
357ac6653aSJeff Kirsher #include <linux/skbuff.h>
367ac6653aSJeff Kirsher #include <linux/ethtool.h>
377ac6653aSJeff Kirsher #include <linux/if_ether.h>
387ac6653aSJeff Kirsher #include <linux/crc32.h>
397ac6653aSJeff Kirsher #include <linux/mii.h>
4001789349SJiri Pirko #include <linux/if.h>
417ac6653aSJeff Kirsher #include <linux/if_vlan.h>
427ac6653aSJeff Kirsher #include <linux/dma-mapping.h>
437ac6653aSJeff Kirsher #include <linux/slab.h>
447ac6653aSJeff Kirsher #include <linux/prefetch.h>
457ac29055SGiuseppe CAVALLARO #ifdef CONFIG_STMMAC_DEBUG_FS
467ac29055SGiuseppe CAVALLARO #include <linux/debugfs.h>
477ac29055SGiuseppe CAVALLARO #include <linux/seq_file.h>
487ac29055SGiuseppe CAVALLARO #endif
49286a8372SGiuseppe CAVALLARO #include "stmmac.h"
507ac6653aSJeff Kirsher 
517ac6653aSJeff Kirsher #undef STMMAC_DEBUG
527ac6653aSJeff Kirsher /*#define STMMAC_DEBUG*/
537ac6653aSJeff Kirsher #ifdef STMMAC_DEBUG
547ac6653aSJeff Kirsher #define DBG(nlevel, klevel, fmt, args...) \
557ac6653aSJeff Kirsher 		((void)(netif_msg_##nlevel(priv) && \
567ac6653aSJeff Kirsher 		printk(KERN_##klevel fmt, ## args)))
577ac6653aSJeff Kirsher #else
587ac6653aSJeff Kirsher #define DBG(nlevel, klevel, fmt, args...) do { } while (0)
597ac6653aSJeff Kirsher #endif
607ac6653aSJeff Kirsher 
617ac6653aSJeff Kirsher #undef STMMAC_RX_DEBUG
627ac6653aSJeff Kirsher /*#define STMMAC_RX_DEBUG*/
637ac6653aSJeff Kirsher #ifdef STMMAC_RX_DEBUG
647ac6653aSJeff Kirsher #define RX_DBG(fmt, args...)  printk(fmt, ## args)
657ac6653aSJeff Kirsher #else
667ac6653aSJeff Kirsher #define RX_DBG(fmt, args...)  do { } while (0)
677ac6653aSJeff Kirsher #endif
687ac6653aSJeff Kirsher 
697ac6653aSJeff Kirsher #undef STMMAC_XMIT_DEBUG
707ac6653aSJeff Kirsher /*#define STMMAC_XMIT_DEBUG*/
717ac6653aSJeff Kirsher #ifdef STMMAC_TX_DEBUG
727ac6653aSJeff Kirsher #define TX_DBG(fmt, args...)  printk(fmt, ## args)
737ac6653aSJeff Kirsher #else
747ac6653aSJeff Kirsher #define TX_DBG(fmt, args...)  do { } while (0)
757ac6653aSJeff Kirsher #endif
767ac6653aSJeff Kirsher 
777ac6653aSJeff Kirsher #define STMMAC_ALIGN(x)	L1_CACHE_ALIGN(x)
787ac6653aSJeff Kirsher #define JUMBO_LEN	9000
797ac6653aSJeff Kirsher 
807ac6653aSJeff Kirsher /* Module parameters */
817ac6653aSJeff Kirsher #define TX_TIMEO 5000 /* default 5 seconds */
827ac6653aSJeff Kirsher static int watchdog = TX_TIMEO;
837ac6653aSJeff Kirsher module_param(watchdog, int, S_IRUGO | S_IWUSR);
847ac6653aSJeff Kirsher MODULE_PARM_DESC(watchdog, "Transmit timeout in milliseconds");
857ac6653aSJeff Kirsher 
867ac6653aSJeff Kirsher static int debug = -1;		/* -1: default, 0: no output, 16:  all */
877ac6653aSJeff Kirsher module_param(debug, int, S_IRUGO | S_IWUSR);
887ac6653aSJeff Kirsher MODULE_PARM_DESC(debug, "Message Level (0: no output, 16: all)");
897ac6653aSJeff Kirsher 
90bfab27a1SGiuseppe CAVALLARO int phyaddr = -1;
917ac6653aSJeff Kirsher module_param(phyaddr, int, S_IRUGO);
927ac6653aSJeff Kirsher MODULE_PARM_DESC(phyaddr, "Physical device address");
937ac6653aSJeff Kirsher 
947ac6653aSJeff Kirsher #define DMA_TX_SIZE 256
957ac6653aSJeff Kirsher static int dma_txsize = DMA_TX_SIZE;
967ac6653aSJeff Kirsher module_param(dma_txsize, int, S_IRUGO | S_IWUSR);
977ac6653aSJeff Kirsher MODULE_PARM_DESC(dma_txsize, "Number of descriptors in the TX list");
987ac6653aSJeff Kirsher 
997ac6653aSJeff Kirsher #define DMA_RX_SIZE 256
1007ac6653aSJeff Kirsher static int dma_rxsize = DMA_RX_SIZE;
1017ac6653aSJeff Kirsher module_param(dma_rxsize, int, S_IRUGO | S_IWUSR);
1027ac6653aSJeff Kirsher MODULE_PARM_DESC(dma_rxsize, "Number of descriptors in the RX list");
1037ac6653aSJeff Kirsher 
1047ac6653aSJeff Kirsher static int flow_ctrl = FLOW_OFF;
1057ac6653aSJeff Kirsher module_param(flow_ctrl, int, S_IRUGO | S_IWUSR);
1067ac6653aSJeff Kirsher MODULE_PARM_DESC(flow_ctrl, "Flow control ability [on/off]");
1077ac6653aSJeff Kirsher 
1087ac6653aSJeff Kirsher static int pause = PAUSE_TIME;
1097ac6653aSJeff Kirsher module_param(pause, int, S_IRUGO | S_IWUSR);
1107ac6653aSJeff Kirsher MODULE_PARM_DESC(pause, "Flow Control Pause Time");
1117ac6653aSJeff Kirsher 
1127ac6653aSJeff Kirsher #define TC_DEFAULT 64
1137ac6653aSJeff Kirsher static int tc = TC_DEFAULT;
1147ac6653aSJeff Kirsher module_param(tc, int, S_IRUGO | S_IWUSR);
1157ac6653aSJeff Kirsher MODULE_PARM_DESC(tc, "DMA threshold control value");
1167ac6653aSJeff Kirsher 
1177ac6653aSJeff Kirsher /* Pay attention to tune this parameter; take care of both
1187ac6653aSJeff Kirsher  * hardware capability and network stabitily/performance impact.
1197ac6653aSJeff Kirsher  * Many tests showed that ~4ms latency seems to be good enough. */
1207ac6653aSJeff Kirsher #ifdef CONFIG_STMMAC_TIMER
1217ac6653aSJeff Kirsher #define DEFAULT_PERIODIC_RATE	256
1227ac6653aSJeff Kirsher static int tmrate = DEFAULT_PERIODIC_RATE;
1237ac6653aSJeff Kirsher module_param(tmrate, int, S_IRUGO | S_IWUSR);
1247ac6653aSJeff Kirsher MODULE_PARM_DESC(tmrate, "External timer freq. (default: 256Hz)");
1257ac6653aSJeff Kirsher #endif
1267ac6653aSJeff Kirsher 
1277ac6653aSJeff Kirsher #define DMA_BUFFER_SIZE	BUF_SIZE_2KiB
1287ac6653aSJeff Kirsher static int buf_sz = DMA_BUFFER_SIZE;
1297ac6653aSJeff Kirsher module_param(buf_sz, int, S_IRUGO | S_IWUSR);
1307ac6653aSJeff Kirsher MODULE_PARM_DESC(buf_sz, "DMA buffer size");
1317ac6653aSJeff Kirsher 
1327ac6653aSJeff Kirsher static const u32 default_msg_level = (NETIF_MSG_DRV | NETIF_MSG_PROBE |
1337ac6653aSJeff Kirsher 				      NETIF_MSG_LINK | NETIF_MSG_IFUP |
1347ac6653aSJeff Kirsher 				      NETIF_MSG_IFDOWN | NETIF_MSG_TIMER);
1357ac6653aSJeff Kirsher 
1367ac6653aSJeff Kirsher static irqreturn_t stmmac_interrupt(int irq, void *dev_id);
1377ac6653aSJeff Kirsher 
138bfab27a1SGiuseppe CAVALLARO #ifdef CONFIG_STMMAC_DEBUG_FS
139bfab27a1SGiuseppe CAVALLARO static int stmmac_init_fs(struct net_device *dev);
140bfab27a1SGiuseppe CAVALLARO static void stmmac_exit_fs(void);
141bfab27a1SGiuseppe CAVALLARO #endif
142bfab27a1SGiuseppe CAVALLARO 
1437ac6653aSJeff Kirsher /**
1447ac6653aSJeff Kirsher  * stmmac_verify_args - verify the driver parameters.
1457ac6653aSJeff Kirsher  * Description: it verifies if some wrong parameter is passed to the driver.
1467ac6653aSJeff Kirsher  * Note that wrong parameters are replaced with the default values.
1477ac6653aSJeff Kirsher  */
1487ac6653aSJeff Kirsher static void stmmac_verify_args(void)
1497ac6653aSJeff Kirsher {
1507ac6653aSJeff Kirsher 	if (unlikely(watchdog < 0))
1517ac6653aSJeff Kirsher 		watchdog = TX_TIMEO;
1527ac6653aSJeff Kirsher 	if (unlikely(dma_rxsize < 0))
1537ac6653aSJeff Kirsher 		dma_rxsize = DMA_RX_SIZE;
1547ac6653aSJeff Kirsher 	if (unlikely(dma_txsize < 0))
1557ac6653aSJeff Kirsher 		dma_txsize = DMA_TX_SIZE;
1567ac6653aSJeff Kirsher 	if (unlikely((buf_sz < DMA_BUFFER_SIZE) || (buf_sz > BUF_SIZE_16KiB)))
1577ac6653aSJeff Kirsher 		buf_sz = DMA_BUFFER_SIZE;
1587ac6653aSJeff Kirsher 	if (unlikely(flow_ctrl > 1))
1597ac6653aSJeff Kirsher 		flow_ctrl = FLOW_AUTO;
1607ac6653aSJeff Kirsher 	else if (likely(flow_ctrl < 0))
1617ac6653aSJeff Kirsher 		flow_ctrl = FLOW_OFF;
1627ac6653aSJeff Kirsher 	if (unlikely((pause < 0) || (pause > 0xffff)))
1637ac6653aSJeff Kirsher 		pause = PAUSE_TIME;
1647ac6653aSJeff Kirsher }
1657ac6653aSJeff Kirsher 
1667ac6653aSJeff Kirsher #if defined(STMMAC_XMIT_DEBUG) || defined(STMMAC_RX_DEBUG)
1677ac6653aSJeff Kirsher static void print_pkt(unsigned char *buf, int len)
1687ac6653aSJeff Kirsher {
1697ac6653aSJeff Kirsher 	int j;
1707ac6653aSJeff Kirsher 	pr_info("len = %d byte, buf addr: 0x%p", len, buf);
1717ac6653aSJeff Kirsher 	for (j = 0; j < len; j++) {
1727ac6653aSJeff Kirsher 		if ((j % 16) == 0)
1737ac6653aSJeff Kirsher 			pr_info("\n %03x:", j);
1747ac6653aSJeff Kirsher 		pr_info(" %02x", buf[j]);
1757ac6653aSJeff Kirsher 	}
1767ac6653aSJeff Kirsher 	pr_info("\n");
1777ac6653aSJeff Kirsher }
1787ac6653aSJeff Kirsher #endif
1797ac6653aSJeff Kirsher 
1807ac6653aSJeff Kirsher /* minimum number of free TX descriptors required to wake up TX process */
1817ac6653aSJeff Kirsher #define STMMAC_TX_THRESH(x)	(x->dma_tx_size/4)
1827ac6653aSJeff Kirsher 
1837ac6653aSJeff Kirsher static inline u32 stmmac_tx_avail(struct stmmac_priv *priv)
1847ac6653aSJeff Kirsher {
1857ac6653aSJeff Kirsher 	return priv->dirty_tx + priv->dma_tx_size - priv->cur_tx - 1;
1867ac6653aSJeff Kirsher }
1877ac6653aSJeff Kirsher 
1887ac6653aSJeff Kirsher /* On some ST platforms, some HW system configuraton registers have to be
1897ac6653aSJeff Kirsher  * set according to the link speed negotiated.
1907ac6653aSJeff Kirsher  */
1917ac6653aSJeff Kirsher static inline void stmmac_hw_fix_mac_speed(struct stmmac_priv *priv)
1927ac6653aSJeff Kirsher {
1937ac6653aSJeff Kirsher 	struct phy_device *phydev = priv->phydev;
1947ac6653aSJeff Kirsher 
1957ac6653aSJeff Kirsher 	if (likely(priv->plat->fix_mac_speed))
1967ac6653aSJeff Kirsher 		priv->plat->fix_mac_speed(priv->plat->bsp_priv,
1977ac6653aSJeff Kirsher 					  phydev->speed);
1987ac6653aSJeff Kirsher }
1997ac6653aSJeff Kirsher 
2007ac6653aSJeff Kirsher /**
2017ac6653aSJeff Kirsher  * stmmac_adjust_link
2027ac6653aSJeff Kirsher  * @dev: net device structure
2037ac6653aSJeff Kirsher  * Description: it adjusts the link parameters.
2047ac6653aSJeff Kirsher  */
2057ac6653aSJeff Kirsher static void stmmac_adjust_link(struct net_device *dev)
2067ac6653aSJeff Kirsher {
2077ac6653aSJeff Kirsher 	struct stmmac_priv *priv = netdev_priv(dev);
2087ac6653aSJeff Kirsher 	struct phy_device *phydev = priv->phydev;
2097ac6653aSJeff Kirsher 	unsigned long flags;
2107ac6653aSJeff Kirsher 	int new_state = 0;
2117ac6653aSJeff Kirsher 	unsigned int fc = priv->flow_ctrl, pause_time = priv->pause;
2127ac6653aSJeff Kirsher 
2137ac6653aSJeff Kirsher 	if (phydev == NULL)
2147ac6653aSJeff Kirsher 		return;
2157ac6653aSJeff Kirsher 
2167ac6653aSJeff Kirsher 	DBG(probe, DEBUG, "stmmac_adjust_link: called.  address %d link %d\n",
2177ac6653aSJeff Kirsher 	    phydev->addr, phydev->link);
2187ac6653aSJeff Kirsher 
2197ac6653aSJeff Kirsher 	spin_lock_irqsave(&priv->lock, flags);
2207ac6653aSJeff Kirsher 	if (phydev->link) {
2217ac6653aSJeff Kirsher 		u32 ctrl = readl(priv->ioaddr + MAC_CTRL_REG);
2227ac6653aSJeff Kirsher 
2237ac6653aSJeff Kirsher 		/* Now we make sure that we can be in full duplex mode.
2247ac6653aSJeff Kirsher 		 * If not, we operate in half-duplex mode. */
2257ac6653aSJeff Kirsher 		if (phydev->duplex != priv->oldduplex) {
2267ac6653aSJeff Kirsher 			new_state = 1;
2277ac6653aSJeff Kirsher 			if (!(phydev->duplex))
2287ac6653aSJeff Kirsher 				ctrl &= ~priv->hw->link.duplex;
2297ac6653aSJeff Kirsher 			else
2307ac6653aSJeff Kirsher 				ctrl |= priv->hw->link.duplex;
2317ac6653aSJeff Kirsher 			priv->oldduplex = phydev->duplex;
2327ac6653aSJeff Kirsher 		}
2337ac6653aSJeff Kirsher 		/* Flow Control operation */
2347ac6653aSJeff Kirsher 		if (phydev->pause)
2357ac6653aSJeff Kirsher 			priv->hw->mac->flow_ctrl(priv->ioaddr, phydev->duplex,
2367ac6653aSJeff Kirsher 						 fc, pause_time);
2377ac6653aSJeff Kirsher 
2387ac6653aSJeff Kirsher 		if (phydev->speed != priv->speed) {
2397ac6653aSJeff Kirsher 			new_state = 1;
2407ac6653aSJeff Kirsher 			switch (phydev->speed) {
2417ac6653aSJeff Kirsher 			case 1000:
2427ac6653aSJeff Kirsher 				if (likely(priv->plat->has_gmac))
2437ac6653aSJeff Kirsher 					ctrl &= ~priv->hw->link.port;
2447ac6653aSJeff Kirsher 					stmmac_hw_fix_mac_speed(priv);
2457ac6653aSJeff Kirsher 				break;
2467ac6653aSJeff Kirsher 			case 100:
2477ac6653aSJeff Kirsher 			case 10:
2487ac6653aSJeff Kirsher 				if (priv->plat->has_gmac) {
2497ac6653aSJeff Kirsher 					ctrl |= priv->hw->link.port;
2507ac6653aSJeff Kirsher 					if (phydev->speed == SPEED_100) {
2517ac6653aSJeff Kirsher 						ctrl |= priv->hw->link.speed;
2527ac6653aSJeff Kirsher 					} else {
2537ac6653aSJeff Kirsher 						ctrl &= ~(priv->hw->link.speed);
2547ac6653aSJeff Kirsher 					}
2557ac6653aSJeff Kirsher 				} else {
2567ac6653aSJeff Kirsher 					ctrl &= ~priv->hw->link.port;
2577ac6653aSJeff Kirsher 				}
2587ac6653aSJeff Kirsher 				stmmac_hw_fix_mac_speed(priv);
2597ac6653aSJeff Kirsher 				break;
2607ac6653aSJeff Kirsher 			default:
2617ac6653aSJeff Kirsher 				if (netif_msg_link(priv))
2627ac6653aSJeff Kirsher 					pr_warning("%s: Speed (%d) is not 10"
2637ac6653aSJeff Kirsher 				       " or 100!\n", dev->name, phydev->speed);
2647ac6653aSJeff Kirsher 				break;
2657ac6653aSJeff Kirsher 			}
2667ac6653aSJeff Kirsher 
2677ac6653aSJeff Kirsher 			priv->speed = phydev->speed;
2687ac6653aSJeff Kirsher 		}
2697ac6653aSJeff Kirsher 
2707ac6653aSJeff Kirsher 		writel(ctrl, priv->ioaddr + MAC_CTRL_REG);
2717ac6653aSJeff Kirsher 
2727ac6653aSJeff Kirsher 		if (!priv->oldlink) {
2737ac6653aSJeff Kirsher 			new_state = 1;
2747ac6653aSJeff Kirsher 			priv->oldlink = 1;
2757ac6653aSJeff Kirsher 		}
2767ac6653aSJeff Kirsher 	} else if (priv->oldlink) {
2777ac6653aSJeff Kirsher 		new_state = 1;
2787ac6653aSJeff Kirsher 		priv->oldlink = 0;
2797ac6653aSJeff Kirsher 		priv->speed = 0;
2807ac6653aSJeff Kirsher 		priv->oldduplex = -1;
2817ac6653aSJeff Kirsher 	}
2827ac6653aSJeff Kirsher 
2837ac6653aSJeff Kirsher 	if (new_state && netif_msg_link(priv))
2847ac6653aSJeff Kirsher 		phy_print_status(phydev);
2857ac6653aSJeff Kirsher 
2867ac6653aSJeff Kirsher 	spin_unlock_irqrestore(&priv->lock, flags);
2877ac6653aSJeff Kirsher 
2887ac6653aSJeff Kirsher 	DBG(probe, DEBUG, "stmmac_adjust_link: exiting\n");
2897ac6653aSJeff Kirsher }
2907ac6653aSJeff Kirsher 
2917ac6653aSJeff Kirsher /**
2927ac6653aSJeff Kirsher  * stmmac_init_phy - PHY initialization
2937ac6653aSJeff Kirsher  * @dev: net device structure
2947ac6653aSJeff Kirsher  * Description: it initializes the driver's PHY state, and attaches the PHY
2957ac6653aSJeff Kirsher  * to the mac driver.
2967ac6653aSJeff Kirsher  *  Return value:
2977ac6653aSJeff Kirsher  *  0 on success
2987ac6653aSJeff Kirsher  */
2997ac6653aSJeff Kirsher static int stmmac_init_phy(struct net_device *dev)
3007ac6653aSJeff Kirsher {
3017ac6653aSJeff Kirsher 	struct stmmac_priv *priv = netdev_priv(dev);
3027ac6653aSJeff Kirsher 	struct phy_device *phydev;
3037ac6653aSJeff Kirsher 	char phy_id[MII_BUS_ID_SIZE + 3];
3047ac6653aSJeff Kirsher 	char bus_id[MII_BUS_ID_SIZE];
30579ee1dc3SSrinivas Kandagatla 	int interface = priv->plat->interface;
3067ac6653aSJeff Kirsher 	priv->oldlink = 0;
3077ac6653aSJeff Kirsher 	priv->speed = 0;
3087ac6653aSJeff Kirsher 	priv->oldduplex = -1;
3097ac6653aSJeff Kirsher 
310db8857bfSFlorian Fainelli 	snprintf(bus_id, MII_BUS_ID_SIZE, "stmmac-%x", priv->plat->bus_id);
3117ac6653aSJeff Kirsher 	snprintf(phy_id, MII_BUS_ID_SIZE + 3, PHY_ID_FMT, bus_id,
3127ac6653aSJeff Kirsher 		 priv->plat->phy_addr);
3137ac6653aSJeff Kirsher 	pr_debug("stmmac_init_phy:  trying to attach to %s\n", phy_id);
3147ac6653aSJeff Kirsher 
31579ee1dc3SSrinivas Kandagatla 	phydev = phy_connect(dev, phy_id, &stmmac_adjust_link, 0, interface);
3167ac6653aSJeff Kirsher 
3177ac6653aSJeff Kirsher 	if (IS_ERR(phydev)) {
3187ac6653aSJeff Kirsher 		pr_err("%s: Could not attach to PHY\n", dev->name);
3197ac6653aSJeff Kirsher 		return PTR_ERR(phydev);
3207ac6653aSJeff Kirsher 	}
3217ac6653aSJeff Kirsher 
32279ee1dc3SSrinivas Kandagatla 	/* Stop Advertising 1000BASE Capability if interface is not GMII */
323c5b9b4e4SSrinivas Kandagatla 	if ((interface == PHY_INTERFACE_MODE_MII) ||
324c5b9b4e4SSrinivas Kandagatla 	    (interface == PHY_INTERFACE_MODE_RMII))
325c5b9b4e4SSrinivas Kandagatla 		phydev->advertising &= ~(SUPPORTED_1000baseT_Half |
326c5b9b4e4SSrinivas Kandagatla 					 SUPPORTED_1000baseT_Full);
32779ee1dc3SSrinivas Kandagatla 
3287ac6653aSJeff Kirsher 	/*
3297ac6653aSJeff Kirsher 	 * Broken HW is sometimes missing the pull-up resistor on the
3307ac6653aSJeff Kirsher 	 * MDIO line, which results in reads to non-existent devices returning
3317ac6653aSJeff Kirsher 	 * 0 rather than 0xffff. Catch this here and treat 0 as a non-existent
3327ac6653aSJeff Kirsher 	 * device as well.
3337ac6653aSJeff Kirsher 	 * Note: phydev->phy_id is the result of reading the UID PHY registers.
3347ac6653aSJeff Kirsher 	 */
3357ac6653aSJeff Kirsher 	if (phydev->phy_id == 0) {
3367ac6653aSJeff Kirsher 		phy_disconnect(phydev);
3377ac6653aSJeff Kirsher 		return -ENODEV;
3387ac6653aSJeff Kirsher 	}
3397ac6653aSJeff Kirsher 	pr_debug("stmmac_init_phy:  %s: attached to PHY (UID 0x%x)"
3407ac6653aSJeff Kirsher 		 " Link = %d\n", dev->name, phydev->phy_id, phydev->link);
3417ac6653aSJeff Kirsher 
3427ac6653aSJeff Kirsher 	priv->phydev = phydev;
3437ac6653aSJeff Kirsher 
3447ac6653aSJeff Kirsher 	return 0;
3457ac6653aSJeff Kirsher }
3467ac6653aSJeff Kirsher 
3477ac6653aSJeff Kirsher /**
3487ac6653aSJeff Kirsher  * display_ring
3497ac6653aSJeff Kirsher  * @p: pointer to the ring.
3507ac6653aSJeff Kirsher  * @size: size of the ring.
3517ac6653aSJeff Kirsher  * Description: display all the descriptors within the ring.
3527ac6653aSJeff Kirsher  */
3537ac6653aSJeff Kirsher static void display_ring(struct dma_desc *p, int size)
3547ac6653aSJeff Kirsher {
3557ac6653aSJeff Kirsher 	struct tmp_s {
3567ac6653aSJeff Kirsher 		u64 a;
3577ac6653aSJeff Kirsher 		unsigned int b;
3587ac6653aSJeff Kirsher 		unsigned int c;
3597ac6653aSJeff Kirsher 	};
3607ac6653aSJeff Kirsher 	int i;
3617ac6653aSJeff Kirsher 	for (i = 0; i < size; i++) {
3627ac6653aSJeff Kirsher 		struct tmp_s *x = (struct tmp_s *)(p + i);
3637ac6653aSJeff Kirsher 		pr_info("\t%d [0x%x]: DES0=0x%x DES1=0x%x BUF1=0x%x BUF2=0x%x",
3647ac6653aSJeff Kirsher 		       i, (unsigned int)virt_to_phys(&p[i]),
3657ac6653aSJeff Kirsher 		       (unsigned int)(x->a), (unsigned int)((x->a) >> 32),
3667ac6653aSJeff Kirsher 		       x->b, x->c);
3677ac6653aSJeff Kirsher 		pr_info("\n");
3687ac6653aSJeff Kirsher 	}
3697ac6653aSJeff Kirsher }
3707ac6653aSJeff Kirsher 
371286a8372SGiuseppe CAVALLARO static int stmmac_set_bfsize(int mtu, int bufsize)
372286a8372SGiuseppe CAVALLARO {
373286a8372SGiuseppe CAVALLARO 	int ret = bufsize;
374286a8372SGiuseppe CAVALLARO 
375286a8372SGiuseppe CAVALLARO 	if (mtu >= BUF_SIZE_4KiB)
376286a8372SGiuseppe CAVALLARO 		ret = BUF_SIZE_8KiB;
377286a8372SGiuseppe CAVALLARO 	else if (mtu >= BUF_SIZE_2KiB)
378286a8372SGiuseppe CAVALLARO 		ret = BUF_SIZE_4KiB;
379286a8372SGiuseppe CAVALLARO 	else if (mtu >= DMA_BUFFER_SIZE)
380286a8372SGiuseppe CAVALLARO 		ret = BUF_SIZE_2KiB;
381286a8372SGiuseppe CAVALLARO 	else
382286a8372SGiuseppe CAVALLARO 		ret = DMA_BUFFER_SIZE;
383286a8372SGiuseppe CAVALLARO 
384286a8372SGiuseppe CAVALLARO 	return ret;
385286a8372SGiuseppe CAVALLARO }
386286a8372SGiuseppe CAVALLARO 
3877ac6653aSJeff Kirsher /**
3887ac6653aSJeff Kirsher  * init_dma_desc_rings - init the RX/TX descriptor rings
3897ac6653aSJeff Kirsher  * @dev: net device structure
3907ac6653aSJeff Kirsher  * Description:  this function initializes the DMA RX/TX descriptors
391286a8372SGiuseppe CAVALLARO  * and allocates the socket buffers. It suppors the chained and ring
392286a8372SGiuseppe CAVALLARO  * modes.
3937ac6653aSJeff Kirsher  */
3947ac6653aSJeff Kirsher static void init_dma_desc_rings(struct net_device *dev)
3957ac6653aSJeff Kirsher {
3967ac6653aSJeff Kirsher 	int i;
3977ac6653aSJeff Kirsher 	struct stmmac_priv *priv = netdev_priv(dev);
3987ac6653aSJeff Kirsher 	struct sk_buff *skb;
3997ac6653aSJeff Kirsher 	unsigned int txsize = priv->dma_tx_size;
4007ac6653aSJeff Kirsher 	unsigned int rxsize = priv->dma_rx_size;
401286a8372SGiuseppe CAVALLARO 	unsigned int bfsize;
402286a8372SGiuseppe CAVALLARO 	int dis_ic = 0;
403286a8372SGiuseppe CAVALLARO 	int des3_as_data_buf = 0;
4047ac6653aSJeff Kirsher 
405286a8372SGiuseppe CAVALLARO 	/* Set the max buffer size according to the DESC mode
406286a8372SGiuseppe CAVALLARO 	 * and the MTU. Note that RING mode allows 16KiB bsize. */
407286a8372SGiuseppe CAVALLARO 	bfsize = priv->hw->ring->set_16kib_bfsize(dev->mtu);
408286a8372SGiuseppe CAVALLARO 
409286a8372SGiuseppe CAVALLARO 	if (bfsize == BUF_SIZE_16KiB)
410286a8372SGiuseppe CAVALLARO 		des3_as_data_buf = 1;
4117ac6653aSJeff Kirsher 	else
412286a8372SGiuseppe CAVALLARO 		bfsize = stmmac_set_bfsize(dev->mtu, priv->dma_buf_sz);
4137ac6653aSJeff Kirsher 
4147ac6653aSJeff Kirsher #ifdef CONFIG_STMMAC_TIMER
4157ac6653aSJeff Kirsher 	/* Disable interrupts on completion for the reception if timer is on */
4167ac6653aSJeff Kirsher 	if (likely(priv->tm->enable))
4177ac6653aSJeff Kirsher 		dis_ic = 1;
4187ac6653aSJeff Kirsher #endif
4197ac6653aSJeff Kirsher 
4207ac6653aSJeff Kirsher 	DBG(probe, INFO, "stmmac: txsize %d, rxsize %d, bfsize %d\n",
4217ac6653aSJeff Kirsher 	    txsize, rxsize, bfsize);
4227ac6653aSJeff Kirsher 
4237ac6653aSJeff Kirsher 	priv->rx_skbuff_dma = kmalloc(rxsize * sizeof(dma_addr_t), GFP_KERNEL);
4247ac6653aSJeff Kirsher 	priv->rx_skbuff =
4257ac6653aSJeff Kirsher 	    kmalloc(sizeof(struct sk_buff *) * rxsize, GFP_KERNEL);
4267ac6653aSJeff Kirsher 	priv->dma_rx =
4277ac6653aSJeff Kirsher 	    (struct dma_desc *)dma_alloc_coherent(priv->device,
4287ac6653aSJeff Kirsher 						  rxsize *
4297ac6653aSJeff Kirsher 						  sizeof(struct dma_desc),
4307ac6653aSJeff Kirsher 						  &priv->dma_rx_phy,
4317ac6653aSJeff Kirsher 						  GFP_KERNEL);
4327ac6653aSJeff Kirsher 	priv->tx_skbuff = kmalloc(sizeof(struct sk_buff *) * txsize,
4337ac6653aSJeff Kirsher 				       GFP_KERNEL);
4347ac6653aSJeff Kirsher 	priv->dma_tx =
4357ac6653aSJeff Kirsher 	    (struct dma_desc *)dma_alloc_coherent(priv->device,
4367ac6653aSJeff Kirsher 						  txsize *
4377ac6653aSJeff Kirsher 						  sizeof(struct dma_desc),
4387ac6653aSJeff Kirsher 						  &priv->dma_tx_phy,
4397ac6653aSJeff Kirsher 						  GFP_KERNEL);
4407ac6653aSJeff Kirsher 
4417ac6653aSJeff Kirsher 	if ((priv->dma_rx == NULL) || (priv->dma_tx == NULL)) {
4427ac6653aSJeff Kirsher 		pr_err("%s:ERROR allocating the DMA Tx/Rx desc\n", __func__);
4437ac6653aSJeff Kirsher 		return;
4447ac6653aSJeff Kirsher 	}
4457ac6653aSJeff Kirsher 
446286a8372SGiuseppe CAVALLARO 	DBG(probe, INFO, "stmmac (%s) DMA desc: virt addr (Rx %p, "
4477ac6653aSJeff Kirsher 	    "Tx %p)\n\tDMA phy addr (Rx 0x%08x, Tx 0x%08x)\n",
4487ac6653aSJeff Kirsher 	    dev->name, priv->dma_rx, priv->dma_tx,
4497ac6653aSJeff Kirsher 	    (unsigned int)priv->dma_rx_phy, (unsigned int)priv->dma_tx_phy);
4507ac6653aSJeff Kirsher 
4517ac6653aSJeff Kirsher 	/* RX INITIALIZATION */
4527ac6653aSJeff Kirsher 	DBG(probe, INFO, "stmmac: SKB addresses:\n"
4537ac6653aSJeff Kirsher 			 "skb\t\tskb data\tdma data\n");
4547ac6653aSJeff Kirsher 
4557ac6653aSJeff Kirsher 	for (i = 0; i < rxsize; i++) {
4567ac6653aSJeff Kirsher 		struct dma_desc *p = priv->dma_rx + i;
4577ac6653aSJeff Kirsher 
45845db81e1SGiuseppe CAVALLARO 		skb = __netdev_alloc_skb(dev, bfsize + NET_IP_ALIGN,
45945db81e1SGiuseppe CAVALLARO 					 GFP_KERNEL);
4607ac6653aSJeff Kirsher 		if (unlikely(skb == NULL)) {
4617ac6653aSJeff Kirsher 			pr_err("%s: Rx init fails; skb is NULL\n", __func__);
4627ac6653aSJeff Kirsher 			break;
4637ac6653aSJeff Kirsher 		}
46445db81e1SGiuseppe CAVALLARO 		skb_reserve(skb, NET_IP_ALIGN);
4657ac6653aSJeff Kirsher 		priv->rx_skbuff[i] = skb;
4667ac6653aSJeff Kirsher 		priv->rx_skbuff_dma[i] = dma_map_single(priv->device, skb->data,
4677ac6653aSJeff Kirsher 						bfsize, DMA_FROM_DEVICE);
4687ac6653aSJeff Kirsher 
4697ac6653aSJeff Kirsher 		p->des2 = priv->rx_skbuff_dma[i];
470286a8372SGiuseppe CAVALLARO 
471286a8372SGiuseppe CAVALLARO 		priv->hw->ring->init_desc3(des3_as_data_buf, p);
472286a8372SGiuseppe CAVALLARO 
4737ac6653aSJeff Kirsher 		DBG(probe, INFO, "[%p]\t[%p]\t[%x]\n", priv->rx_skbuff[i],
4747ac6653aSJeff Kirsher 			priv->rx_skbuff[i]->data, priv->rx_skbuff_dma[i]);
4757ac6653aSJeff Kirsher 	}
4767ac6653aSJeff Kirsher 	priv->cur_rx = 0;
4777ac6653aSJeff Kirsher 	priv->dirty_rx = (unsigned int)(i - rxsize);
4787ac6653aSJeff Kirsher 	priv->dma_buf_sz = bfsize;
4797ac6653aSJeff Kirsher 	buf_sz = bfsize;
4807ac6653aSJeff Kirsher 
4817ac6653aSJeff Kirsher 	/* TX INITIALIZATION */
4827ac6653aSJeff Kirsher 	for (i = 0; i < txsize; i++) {
4837ac6653aSJeff Kirsher 		priv->tx_skbuff[i] = NULL;
4847ac6653aSJeff Kirsher 		priv->dma_tx[i].des2 = 0;
4857ac6653aSJeff Kirsher 	}
486286a8372SGiuseppe CAVALLARO 
487286a8372SGiuseppe CAVALLARO 	/* In case of Chained mode this sets the des3 to the next
488286a8372SGiuseppe CAVALLARO 	 * element in the chain */
489286a8372SGiuseppe CAVALLARO 	priv->hw->ring->init_dma_chain(priv->dma_rx, priv->dma_rx_phy, rxsize);
490286a8372SGiuseppe CAVALLARO 	priv->hw->ring->init_dma_chain(priv->dma_tx, priv->dma_tx_phy, txsize);
491286a8372SGiuseppe CAVALLARO 
4927ac6653aSJeff Kirsher 	priv->dirty_tx = 0;
4937ac6653aSJeff Kirsher 	priv->cur_tx = 0;
4947ac6653aSJeff Kirsher 
4957ac6653aSJeff Kirsher 	/* Clear the Rx/Tx descriptors */
4967ac6653aSJeff Kirsher 	priv->hw->desc->init_rx_desc(priv->dma_rx, rxsize, dis_ic);
4977ac6653aSJeff Kirsher 	priv->hw->desc->init_tx_desc(priv->dma_tx, txsize);
4987ac6653aSJeff Kirsher 
4997ac6653aSJeff Kirsher 	if (netif_msg_hw(priv)) {
5007ac6653aSJeff Kirsher 		pr_info("RX descriptor ring:\n");
5017ac6653aSJeff Kirsher 		display_ring(priv->dma_rx, rxsize);
5027ac6653aSJeff Kirsher 		pr_info("TX descriptor ring:\n");
5037ac6653aSJeff Kirsher 		display_ring(priv->dma_tx, txsize);
5047ac6653aSJeff Kirsher 	}
5057ac6653aSJeff Kirsher }
5067ac6653aSJeff Kirsher 
5077ac6653aSJeff Kirsher static void dma_free_rx_skbufs(struct stmmac_priv *priv)
5087ac6653aSJeff Kirsher {
5097ac6653aSJeff Kirsher 	int i;
5107ac6653aSJeff Kirsher 
5117ac6653aSJeff Kirsher 	for (i = 0; i < priv->dma_rx_size; i++) {
5127ac6653aSJeff Kirsher 		if (priv->rx_skbuff[i]) {
5137ac6653aSJeff Kirsher 			dma_unmap_single(priv->device, priv->rx_skbuff_dma[i],
5147ac6653aSJeff Kirsher 					 priv->dma_buf_sz, DMA_FROM_DEVICE);
5157ac6653aSJeff Kirsher 			dev_kfree_skb_any(priv->rx_skbuff[i]);
5167ac6653aSJeff Kirsher 		}
5177ac6653aSJeff Kirsher 		priv->rx_skbuff[i] = NULL;
5187ac6653aSJeff Kirsher 	}
5197ac6653aSJeff Kirsher }
5207ac6653aSJeff Kirsher 
5217ac6653aSJeff Kirsher static void dma_free_tx_skbufs(struct stmmac_priv *priv)
5227ac6653aSJeff Kirsher {
5237ac6653aSJeff Kirsher 	int i;
5247ac6653aSJeff Kirsher 
5257ac6653aSJeff Kirsher 	for (i = 0; i < priv->dma_tx_size; i++) {
5267ac6653aSJeff Kirsher 		if (priv->tx_skbuff[i] != NULL) {
5277ac6653aSJeff Kirsher 			struct dma_desc *p = priv->dma_tx + i;
5287ac6653aSJeff Kirsher 			if (p->des2)
5297ac6653aSJeff Kirsher 				dma_unmap_single(priv->device, p->des2,
5307ac6653aSJeff Kirsher 						 priv->hw->desc->get_tx_len(p),
5317ac6653aSJeff Kirsher 						 DMA_TO_DEVICE);
5327ac6653aSJeff Kirsher 			dev_kfree_skb_any(priv->tx_skbuff[i]);
5337ac6653aSJeff Kirsher 			priv->tx_skbuff[i] = NULL;
5347ac6653aSJeff Kirsher 		}
5357ac6653aSJeff Kirsher 	}
5367ac6653aSJeff Kirsher }
5377ac6653aSJeff Kirsher 
5387ac6653aSJeff Kirsher static void free_dma_desc_resources(struct stmmac_priv *priv)
5397ac6653aSJeff Kirsher {
5407ac6653aSJeff Kirsher 	/* Release the DMA TX/RX socket buffers */
5417ac6653aSJeff Kirsher 	dma_free_rx_skbufs(priv);
5427ac6653aSJeff Kirsher 	dma_free_tx_skbufs(priv);
5437ac6653aSJeff Kirsher 
5447ac6653aSJeff Kirsher 	/* Free the region of consistent memory previously allocated for
5457ac6653aSJeff Kirsher 	 * the DMA */
5467ac6653aSJeff Kirsher 	dma_free_coherent(priv->device,
5477ac6653aSJeff Kirsher 			  priv->dma_tx_size * sizeof(struct dma_desc),
5487ac6653aSJeff Kirsher 			  priv->dma_tx, priv->dma_tx_phy);
5497ac6653aSJeff Kirsher 	dma_free_coherent(priv->device,
5507ac6653aSJeff Kirsher 			  priv->dma_rx_size * sizeof(struct dma_desc),
5517ac6653aSJeff Kirsher 			  priv->dma_rx, priv->dma_rx_phy);
5527ac6653aSJeff Kirsher 	kfree(priv->rx_skbuff_dma);
5537ac6653aSJeff Kirsher 	kfree(priv->rx_skbuff);
5547ac6653aSJeff Kirsher 	kfree(priv->tx_skbuff);
5557ac6653aSJeff Kirsher }
5567ac6653aSJeff Kirsher 
5577ac6653aSJeff Kirsher /**
5587ac6653aSJeff Kirsher  *  stmmac_dma_operation_mode - HW DMA operation mode
5597ac6653aSJeff Kirsher  *  @priv : pointer to the private device structure.
5607ac6653aSJeff Kirsher  *  Description: it sets the DMA operation mode: tx/rx DMA thresholds
5617ac6653aSJeff Kirsher  *  or Store-And-Forward capability.
5627ac6653aSJeff Kirsher  */
5637ac6653aSJeff Kirsher static void stmmac_dma_operation_mode(struct stmmac_priv *priv)
5647ac6653aSJeff Kirsher {
5657ac6653aSJeff Kirsher 	if (likely(priv->plat->force_sf_dma_mode ||
5667ac6653aSJeff Kirsher 		((priv->plat->tx_coe) && (!priv->no_csum_insertion)))) {
5677ac6653aSJeff Kirsher 		/*
5687ac6653aSJeff Kirsher 		 * In case of GMAC, SF mode can be enabled
5697ac6653aSJeff Kirsher 		 * to perform the TX COE in HW. This depends on:
5707ac6653aSJeff Kirsher 		 * 1) TX COE if actually supported
5717ac6653aSJeff Kirsher 		 * 2) There is no bugged Jumbo frame support
5727ac6653aSJeff Kirsher 		 *    that needs to not insert csum in the TDES.
5737ac6653aSJeff Kirsher 		 */
5747ac6653aSJeff Kirsher 		priv->hw->dma->dma_mode(priv->ioaddr,
5757ac6653aSJeff Kirsher 					SF_DMA_MODE, SF_DMA_MODE);
5767ac6653aSJeff Kirsher 		tc = SF_DMA_MODE;
5777ac6653aSJeff Kirsher 	} else
5787ac6653aSJeff Kirsher 		priv->hw->dma->dma_mode(priv->ioaddr, tc, SF_DMA_MODE);
5797ac6653aSJeff Kirsher }
5807ac6653aSJeff Kirsher 
5817ac6653aSJeff Kirsher /**
5827ac6653aSJeff Kirsher  * stmmac_tx:
5837ac6653aSJeff Kirsher  * @priv: private driver structure
5847ac6653aSJeff Kirsher  * Description: it reclaims resources after transmission completes.
5857ac6653aSJeff Kirsher  */
5867ac6653aSJeff Kirsher static void stmmac_tx(struct stmmac_priv *priv)
5877ac6653aSJeff Kirsher {
5887ac6653aSJeff Kirsher 	unsigned int txsize = priv->dma_tx_size;
5897ac6653aSJeff Kirsher 
590a9097a96SGiuseppe CAVALLARO 	spin_lock(&priv->tx_lock);
591a9097a96SGiuseppe CAVALLARO 
5927ac6653aSJeff Kirsher 	while (priv->dirty_tx != priv->cur_tx) {
5937ac6653aSJeff Kirsher 		int last;
5947ac6653aSJeff Kirsher 		unsigned int entry = priv->dirty_tx % txsize;
5957ac6653aSJeff Kirsher 		struct sk_buff *skb = priv->tx_skbuff[entry];
5967ac6653aSJeff Kirsher 		struct dma_desc *p = priv->dma_tx + entry;
5977ac6653aSJeff Kirsher 
5987ac6653aSJeff Kirsher 		/* Check if the descriptor is owned by the DMA. */
5997ac6653aSJeff Kirsher 		if (priv->hw->desc->get_tx_owner(p))
6007ac6653aSJeff Kirsher 			break;
6017ac6653aSJeff Kirsher 
6027ac6653aSJeff Kirsher 		/* Verify tx error by looking at the last segment */
6037ac6653aSJeff Kirsher 		last = priv->hw->desc->get_tx_ls(p);
6047ac6653aSJeff Kirsher 		if (likely(last)) {
6057ac6653aSJeff Kirsher 			int tx_error =
6067ac6653aSJeff Kirsher 				priv->hw->desc->tx_status(&priv->dev->stats,
6077ac6653aSJeff Kirsher 							  &priv->xstats, p,
6087ac6653aSJeff Kirsher 							  priv->ioaddr);
6097ac6653aSJeff Kirsher 			if (likely(tx_error == 0)) {
6107ac6653aSJeff Kirsher 				priv->dev->stats.tx_packets++;
6117ac6653aSJeff Kirsher 				priv->xstats.tx_pkt_n++;
6127ac6653aSJeff Kirsher 			} else
6137ac6653aSJeff Kirsher 				priv->dev->stats.tx_errors++;
6147ac6653aSJeff Kirsher 		}
6157ac6653aSJeff Kirsher 		TX_DBG("%s: curr %d, dirty %d\n", __func__,
6167ac6653aSJeff Kirsher 			priv->cur_tx, priv->dirty_tx);
6177ac6653aSJeff Kirsher 
6187ac6653aSJeff Kirsher 		if (likely(p->des2))
6197ac6653aSJeff Kirsher 			dma_unmap_single(priv->device, p->des2,
6207ac6653aSJeff Kirsher 					 priv->hw->desc->get_tx_len(p),
6217ac6653aSJeff Kirsher 					 DMA_TO_DEVICE);
622286a8372SGiuseppe CAVALLARO 		priv->hw->ring->clean_desc3(p);
6237ac6653aSJeff Kirsher 
6247ac6653aSJeff Kirsher 		if (likely(skb != NULL)) {
6257ac6653aSJeff Kirsher 			/*
6267ac6653aSJeff Kirsher 			 * If there's room in the queue (limit it to size)
6277ac6653aSJeff Kirsher 			 * we add this skb back into the pool,
6287ac6653aSJeff Kirsher 			 * if it's the right size.
6297ac6653aSJeff Kirsher 			 */
6307ac6653aSJeff Kirsher 			if ((skb_queue_len(&priv->rx_recycle) <
6317ac6653aSJeff Kirsher 				priv->dma_rx_size) &&
6327ac6653aSJeff Kirsher 				skb_recycle_check(skb, priv->dma_buf_sz))
6337ac6653aSJeff Kirsher 				__skb_queue_head(&priv->rx_recycle, skb);
6347ac6653aSJeff Kirsher 			else
6357ac6653aSJeff Kirsher 				dev_kfree_skb(skb);
6367ac6653aSJeff Kirsher 
6377ac6653aSJeff Kirsher 			priv->tx_skbuff[entry] = NULL;
6387ac6653aSJeff Kirsher 		}
6397ac6653aSJeff Kirsher 
6407ac6653aSJeff Kirsher 		priv->hw->desc->release_tx_desc(p);
6417ac6653aSJeff Kirsher 
6427ac6653aSJeff Kirsher 		entry = (++priv->dirty_tx) % txsize;
6437ac6653aSJeff Kirsher 	}
6447ac6653aSJeff Kirsher 	if (unlikely(netif_queue_stopped(priv->dev) &&
6457ac6653aSJeff Kirsher 		     stmmac_tx_avail(priv) > STMMAC_TX_THRESH(priv))) {
6467ac6653aSJeff Kirsher 		netif_tx_lock(priv->dev);
6477ac6653aSJeff Kirsher 		if (netif_queue_stopped(priv->dev) &&
6487ac6653aSJeff Kirsher 		     stmmac_tx_avail(priv) > STMMAC_TX_THRESH(priv)) {
6497ac6653aSJeff Kirsher 			TX_DBG("%s: restart transmit\n", __func__);
6507ac6653aSJeff Kirsher 			netif_wake_queue(priv->dev);
6517ac6653aSJeff Kirsher 		}
6527ac6653aSJeff Kirsher 		netif_tx_unlock(priv->dev);
6537ac6653aSJeff Kirsher 	}
654a9097a96SGiuseppe CAVALLARO 	spin_unlock(&priv->tx_lock);
6557ac6653aSJeff Kirsher }
6567ac6653aSJeff Kirsher 
6577ac6653aSJeff Kirsher static inline void stmmac_enable_irq(struct stmmac_priv *priv)
6587ac6653aSJeff Kirsher {
6597ac6653aSJeff Kirsher #ifdef CONFIG_STMMAC_TIMER
6607ac6653aSJeff Kirsher 	if (likely(priv->tm->enable))
6617ac6653aSJeff Kirsher 		priv->tm->timer_start(tmrate);
6627ac6653aSJeff Kirsher 	else
6637ac6653aSJeff Kirsher #endif
6647ac6653aSJeff Kirsher 		priv->hw->dma->enable_dma_irq(priv->ioaddr);
6657ac6653aSJeff Kirsher }
6667ac6653aSJeff Kirsher 
6677ac6653aSJeff Kirsher static inline void stmmac_disable_irq(struct stmmac_priv *priv)
6687ac6653aSJeff Kirsher {
6697ac6653aSJeff Kirsher #ifdef CONFIG_STMMAC_TIMER
6707ac6653aSJeff Kirsher 	if (likely(priv->tm->enable))
6717ac6653aSJeff Kirsher 		priv->tm->timer_stop();
6727ac6653aSJeff Kirsher 	else
6737ac6653aSJeff Kirsher #endif
6747ac6653aSJeff Kirsher 		priv->hw->dma->disable_dma_irq(priv->ioaddr);
6757ac6653aSJeff Kirsher }
6767ac6653aSJeff Kirsher 
6777ac6653aSJeff Kirsher static int stmmac_has_work(struct stmmac_priv *priv)
6787ac6653aSJeff Kirsher {
6797ac6653aSJeff Kirsher 	unsigned int has_work = 0;
6807ac6653aSJeff Kirsher 	int rxret, tx_work = 0;
6817ac6653aSJeff Kirsher 
6827ac6653aSJeff Kirsher 	rxret = priv->hw->desc->get_rx_owner(priv->dma_rx +
6837ac6653aSJeff Kirsher 		(priv->cur_rx % priv->dma_rx_size));
6847ac6653aSJeff Kirsher 
6857ac6653aSJeff Kirsher 	if (priv->dirty_tx != priv->cur_tx)
6867ac6653aSJeff Kirsher 		tx_work = 1;
6877ac6653aSJeff Kirsher 
6887ac6653aSJeff Kirsher 	if (likely(!rxret || tx_work))
6897ac6653aSJeff Kirsher 		has_work = 1;
6907ac6653aSJeff Kirsher 
6917ac6653aSJeff Kirsher 	return has_work;
6927ac6653aSJeff Kirsher }
6937ac6653aSJeff Kirsher 
6947ac6653aSJeff Kirsher static inline void _stmmac_schedule(struct stmmac_priv *priv)
6957ac6653aSJeff Kirsher {
6967ac6653aSJeff Kirsher 	if (likely(stmmac_has_work(priv))) {
6977ac6653aSJeff Kirsher 		stmmac_disable_irq(priv);
6987ac6653aSJeff Kirsher 		napi_schedule(&priv->napi);
6997ac6653aSJeff Kirsher 	}
7007ac6653aSJeff Kirsher }
7017ac6653aSJeff Kirsher 
7027ac6653aSJeff Kirsher #ifdef CONFIG_STMMAC_TIMER
7037ac6653aSJeff Kirsher void stmmac_schedule(struct net_device *dev)
7047ac6653aSJeff Kirsher {
7057ac6653aSJeff Kirsher 	struct stmmac_priv *priv = netdev_priv(dev);
7067ac6653aSJeff Kirsher 
7077ac6653aSJeff Kirsher 	priv->xstats.sched_timer_n++;
7087ac6653aSJeff Kirsher 
7097ac6653aSJeff Kirsher 	_stmmac_schedule(priv);
7107ac6653aSJeff Kirsher }
7117ac6653aSJeff Kirsher 
7127ac6653aSJeff Kirsher static void stmmac_no_timer_started(unsigned int x)
7137ac6653aSJeff Kirsher {;
7147ac6653aSJeff Kirsher };
7157ac6653aSJeff Kirsher 
7167ac6653aSJeff Kirsher static void stmmac_no_timer_stopped(void)
7177ac6653aSJeff Kirsher {;
7187ac6653aSJeff Kirsher };
7197ac6653aSJeff Kirsher #endif
7207ac6653aSJeff Kirsher 
7217ac6653aSJeff Kirsher /**
7227ac6653aSJeff Kirsher  * stmmac_tx_err:
7237ac6653aSJeff Kirsher  * @priv: pointer to the private device structure
7247ac6653aSJeff Kirsher  * Description: it cleans the descriptors and restarts the transmission
7257ac6653aSJeff Kirsher  * in case of errors.
7267ac6653aSJeff Kirsher  */
7277ac6653aSJeff Kirsher static void stmmac_tx_err(struct stmmac_priv *priv)
7287ac6653aSJeff Kirsher {
7297ac6653aSJeff Kirsher 	netif_stop_queue(priv->dev);
7307ac6653aSJeff Kirsher 
7317ac6653aSJeff Kirsher 	priv->hw->dma->stop_tx(priv->ioaddr);
7327ac6653aSJeff Kirsher 	dma_free_tx_skbufs(priv);
7337ac6653aSJeff Kirsher 	priv->hw->desc->init_tx_desc(priv->dma_tx, priv->dma_tx_size);
7347ac6653aSJeff Kirsher 	priv->dirty_tx = 0;
7357ac6653aSJeff Kirsher 	priv->cur_tx = 0;
7367ac6653aSJeff Kirsher 	priv->hw->dma->start_tx(priv->ioaddr);
7377ac6653aSJeff Kirsher 
7387ac6653aSJeff Kirsher 	priv->dev->stats.tx_errors++;
7397ac6653aSJeff Kirsher 	netif_wake_queue(priv->dev);
7407ac6653aSJeff Kirsher }
7417ac6653aSJeff Kirsher 
7427ac6653aSJeff Kirsher 
7437ac6653aSJeff Kirsher static void stmmac_dma_interrupt(struct stmmac_priv *priv)
7447ac6653aSJeff Kirsher {
7457ac6653aSJeff Kirsher 	int status;
7467ac6653aSJeff Kirsher 
7477ac6653aSJeff Kirsher 	status = priv->hw->dma->dma_interrupt(priv->ioaddr, &priv->xstats);
7487ac6653aSJeff Kirsher 	if (likely(status == handle_tx_rx))
7497ac6653aSJeff Kirsher 		_stmmac_schedule(priv);
7507ac6653aSJeff Kirsher 
7517ac6653aSJeff Kirsher 	else if (unlikely(status == tx_hard_error_bump_tc)) {
7527ac6653aSJeff Kirsher 		/* Try to bump up the dma threshold on this failure */
7537ac6653aSJeff Kirsher 		if (unlikely(tc != SF_DMA_MODE) && (tc <= 256)) {
7547ac6653aSJeff Kirsher 			tc += 64;
7557ac6653aSJeff Kirsher 			priv->hw->dma->dma_mode(priv->ioaddr, tc, SF_DMA_MODE);
7567ac6653aSJeff Kirsher 			priv->xstats.threshold = tc;
7577ac6653aSJeff Kirsher 		}
7587ac6653aSJeff Kirsher 	} else if (unlikely(status == tx_hard_error))
7597ac6653aSJeff Kirsher 		stmmac_tx_err(priv);
7607ac6653aSJeff Kirsher }
7617ac6653aSJeff Kirsher 
7621c901a46SGiuseppe CAVALLARO static void stmmac_mmc_setup(struct stmmac_priv *priv)
7631c901a46SGiuseppe CAVALLARO {
7641c901a46SGiuseppe CAVALLARO 	unsigned int mode = MMC_CNTRL_RESET_ON_READ | MMC_CNTRL_COUNTER_RESET |
7651c901a46SGiuseppe CAVALLARO 			    MMC_CNTRL_PRESET | MMC_CNTRL_FULL_HALF_PRESET;
7661c901a46SGiuseppe CAVALLARO 
7674f795b25SGiuseppe CAVALLARO 	/* Mask MMC irq, counters are managed in SW and registers
7684f795b25SGiuseppe CAVALLARO 	 * are cleared on each READ eventually. */
7691c901a46SGiuseppe CAVALLARO 	dwmac_mmc_intr_all_mask(priv->ioaddr);
7704f795b25SGiuseppe CAVALLARO 
7714f795b25SGiuseppe CAVALLARO 	if (priv->dma_cap.rmon) {
7721c901a46SGiuseppe CAVALLARO 		dwmac_mmc_ctrl(priv->ioaddr, mode);
7731c901a46SGiuseppe CAVALLARO 		memset(&priv->mmc, 0, sizeof(struct stmmac_counters));
7744f795b25SGiuseppe CAVALLARO 	} else
775aae54cffSStefan Roese 		pr_info(" No MAC Management Counters available\n");
7761c901a46SGiuseppe CAVALLARO }
7771c901a46SGiuseppe CAVALLARO 
778f0b9d786SGiuseppe CAVALLARO static u32 stmmac_get_synopsys_id(struct stmmac_priv *priv)
779f0b9d786SGiuseppe CAVALLARO {
780f0b9d786SGiuseppe CAVALLARO 	u32 hwid = priv->hw->synopsys_uid;
781f0b9d786SGiuseppe CAVALLARO 
782f0b9d786SGiuseppe CAVALLARO 	/* Only check valid Synopsys Id because old MAC chips
783f0b9d786SGiuseppe CAVALLARO 	 * have no HW registers where get the ID */
784f0b9d786SGiuseppe CAVALLARO 	if (likely(hwid)) {
785f0b9d786SGiuseppe CAVALLARO 		u32 uid = ((hwid & 0x0000ff00) >> 8);
786f0b9d786SGiuseppe CAVALLARO 		u32 synid = (hwid & 0x000000ff);
787f0b9d786SGiuseppe CAVALLARO 
788cf3f047bSGiuseppe CAVALLARO 		pr_info("stmmac - user ID: 0x%x, Synopsys ID: 0x%x\n",
789f0b9d786SGiuseppe CAVALLARO 			uid, synid);
790f0b9d786SGiuseppe CAVALLARO 
791f0b9d786SGiuseppe CAVALLARO 		return synid;
792f0b9d786SGiuseppe CAVALLARO 	}
793f0b9d786SGiuseppe CAVALLARO 	return 0;
794f0b9d786SGiuseppe CAVALLARO }
795e7434821SGiuseppe CAVALLARO 
79619e30c14SGiuseppe CAVALLARO /**
79719e30c14SGiuseppe CAVALLARO  * stmmac_selec_desc_mode
79819e30c14SGiuseppe CAVALLARO  * @dev : device pointer
79919e30c14SGiuseppe CAVALLARO  * Description: select the Enhanced/Alternate or Normal descriptors */
80019e30c14SGiuseppe CAVALLARO static void stmmac_selec_desc_mode(struct stmmac_priv *priv)
80119e30c14SGiuseppe CAVALLARO {
80219e30c14SGiuseppe CAVALLARO 	if (priv->plat->enh_desc) {
80319e30c14SGiuseppe CAVALLARO 		pr_info(" Enhanced/Alternate descriptors\n");
80419e30c14SGiuseppe CAVALLARO 		priv->hw->desc = &enh_desc_ops;
80519e30c14SGiuseppe CAVALLARO 	} else {
80619e30c14SGiuseppe CAVALLARO 		pr_info(" Normal descriptors\n");
80719e30c14SGiuseppe CAVALLARO 		priv->hw->desc = &ndesc_ops;
80819e30c14SGiuseppe CAVALLARO 	}
80919e30c14SGiuseppe CAVALLARO }
81019e30c14SGiuseppe CAVALLARO 
81119e30c14SGiuseppe CAVALLARO /**
81219e30c14SGiuseppe CAVALLARO  * stmmac_get_hw_features
81319e30c14SGiuseppe CAVALLARO  * @priv : private device pointer
81419e30c14SGiuseppe CAVALLARO  * Description:
81519e30c14SGiuseppe CAVALLARO  *  new GMAC chip generations have a new register to indicate the
816e7434821SGiuseppe CAVALLARO  *  presence of the optional feature/functions.
81719e30c14SGiuseppe CAVALLARO  *  This can be also used to override the value passed through the
81819e30c14SGiuseppe CAVALLARO  *  platform and necessary for old MAC10/100 and GMAC chips.
819e7434821SGiuseppe CAVALLARO  */
820e7434821SGiuseppe CAVALLARO static int stmmac_get_hw_features(struct stmmac_priv *priv)
821e7434821SGiuseppe CAVALLARO {
8225e6efe88SGiuseppe CAVALLARO 	u32 hw_cap = 0;
8233c20f72fSGiuseppe CAVALLARO 
8245e6efe88SGiuseppe CAVALLARO 	if (priv->hw->dma->get_hw_feature) {
8255e6efe88SGiuseppe CAVALLARO 		hw_cap = priv->hw->dma->get_hw_feature(priv->ioaddr);
826e7434821SGiuseppe CAVALLARO 
8271db123fbSRayagond Kokatanur 		priv->dma_cap.mbps_10_100 = (hw_cap & DMA_HW_FEAT_MIISEL);
8281db123fbSRayagond Kokatanur 		priv->dma_cap.mbps_1000 = (hw_cap & DMA_HW_FEAT_GMIISEL) >> 1;
8291db123fbSRayagond Kokatanur 		priv->dma_cap.half_duplex = (hw_cap & DMA_HW_FEAT_HDSEL) >> 2;
8301db123fbSRayagond Kokatanur 		priv->dma_cap.hash_filter = (hw_cap & DMA_HW_FEAT_HASHSEL) >> 4;
8311db123fbSRayagond Kokatanur 		priv->dma_cap.multi_addr =
8321db123fbSRayagond Kokatanur 			(hw_cap & DMA_HW_FEAT_ADDMACADRSEL) >> 5;
8331db123fbSRayagond Kokatanur 		priv->dma_cap.pcs = (hw_cap & DMA_HW_FEAT_PCSSEL) >> 6;
8341db123fbSRayagond Kokatanur 		priv->dma_cap.sma_mdio = (hw_cap & DMA_HW_FEAT_SMASEL) >> 8;
8351db123fbSRayagond Kokatanur 		priv->dma_cap.pmt_remote_wake_up =
8361db123fbSRayagond Kokatanur 			(hw_cap & DMA_HW_FEAT_RWKSEL) >> 9;
8371db123fbSRayagond Kokatanur 		priv->dma_cap.pmt_magic_frame =
8381db123fbSRayagond Kokatanur 			(hw_cap & DMA_HW_FEAT_MGKSEL) >> 10;
8391db123fbSRayagond Kokatanur 		/* MMC */
8401db123fbSRayagond Kokatanur 		priv->dma_cap.rmon = (hw_cap & DMA_HW_FEAT_MMCSEL) >> 11;
841e7434821SGiuseppe CAVALLARO 		/* IEEE 1588-2002*/
8421db123fbSRayagond Kokatanur 		priv->dma_cap.time_stamp =
8431db123fbSRayagond Kokatanur 			(hw_cap & DMA_HW_FEAT_TSVER1SEL) >> 12;
844e7434821SGiuseppe CAVALLARO 		/* IEEE 1588-2008*/
8451db123fbSRayagond Kokatanur 		priv->dma_cap.atime_stamp =
8461db123fbSRayagond Kokatanur 			(hw_cap & DMA_HW_FEAT_TSVER2SEL) >> 13;
847e7434821SGiuseppe CAVALLARO 		/* 802.3az - Energy-Efficient Ethernet (EEE) */
8481db123fbSRayagond Kokatanur 		priv->dma_cap.eee = (hw_cap & DMA_HW_FEAT_EEESEL) >> 14;
8491db123fbSRayagond Kokatanur 		priv->dma_cap.av = (hw_cap & DMA_HW_FEAT_AVSEL) >> 15;
850e7434821SGiuseppe CAVALLARO 		/* TX and RX csum */
8511db123fbSRayagond Kokatanur 		priv->dma_cap.tx_coe = (hw_cap & DMA_HW_FEAT_TXCOESEL) >> 16;
8521db123fbSRayagond Kokatanur 		priv->dma_cap.rx_coe_type1 =
8531db123fbSRayagond Kokatanur 			(hw_cap & DMA_HW_FEAT_RXTYP1COE) >> 17;
8541db123fbSRayagond Kokatanur 		priv->dma_cap.rx_coe_type2 =
8551db123fbSRayagond Kokatanur 			(hw_cap & DMA_HW_FEAT_RXTYP2COE) >> 18;
8561db123fbSRayagond Kokatanur 		priv->dma_cap.rxfifo_over_2048 =
8571db123fbSRayagond Kokatanur 			(hw_cap & DMA_HW_FEAT_RXFIFOSIZE) >> 19;
858e7434821SGiuseppe CAVALLARO 		/* TX and RX number of channels */
8591db123fbSRayagond Kokatanur 		priv->dma_cap.number_rx_channel =
8601db123fbSRayagond Kokatanur 			(hw_cap & DMA_HW_FEAT_RXCHCNT) >> 20;
8611db123fbSRayagond Kokatanur 		priv->dma_cap.number_tx_channel =
8621db123fbSRayagond Kokatanur 			(hw_cap & DMA_HW_FEAT_TXCHCNT) >> 22;
863e7434821SGiuseppe CAVALLARO 		/* Alternate (enhanced) DESC mode*/
8641db123fbSRayagond Kokatanur 		priv->dma_cap.enh_desc =
8651db123fbSRayagond Kokatanur 			(hw_cap & DMA_HW_FEAT_ENHDESSEL) >> 24;
866e7434821SGiuseppe CAVALLARO 
86719e30c14SGiuseppe CAVALLARO 	}
868e7434821SGiuseppe CAVALLARO 
869e7434821SGiuseppe CAVALLARO 	return hw_cap;
870e7434821SGiuseppe CAVALLARO }
871e7434821SGiuseppe CAVALLARO 
872bfab27a1SGiuseppe CAVALLARO static void stmmac_check_ether_addr(struct stmmac_priv *priv)
873bfab27a1SGiuseppe CAVALLARO {
874bfab27a1SGiuseppe CAVALLARO 	/* verify if the MAC address is valid, in case of failures it
875bfab27a1SGiuseppe CAVALLARO 	 * generates a random MAC address */
876bfab27a1SGiuseppe CAVALLARO 	if (!is_valid_ether_addr(priv->dev->dev_addr)) {
877bfab27a1SGiuseppe CAVALLARO 		priv->hw->mac->get_umac_addr((void __iomem *)
878bfab27a1SGiuseppe CAVALLARO 					     priv->dev->base_addr,
879bfab27a1SGiuseppe CAVALLARO 					     priv->dev->dev_addr, 0);
880bfab27a1SGiuseppe CAVALLARO 		if  (!is_valid_ether_addr(priv->dev->dev_addr))
881bfab27a1SGiuseppe CAVALLARO 			random_ether_addr(priv->dev->dev_addr);
882bfab27a1SGiuseppe CAVALLARO 	}
883bfab27a1SGiuseppe CAVALLARO 	pr_warning("%s: device MAC address %pM\n", priv->dev->name,
884bfab27a1SGiuseppe CAVALLARO 						   priv->dev->dev_addr);
885bfab27a1SGiuseppe CAVALLARO }
886bfab27a1SGiuseppe CAVALLARO 
887bfab27a1SGiuseppe CAVALLARO /**
8887ac6653aSJeff Kirsher  *  stmmac_open - open entry point of the driver
8897ac6653aSJeff Kirsher  *  @dev : pointer to the device structure.
8907ac6653aSJeff Kirsher  *  Description:
8917ac6653aSJeff Kirsher  *  This function is the open entry point of the driver.
8927ac6653aSJeff Kirsher  *  Return value:
8937ac6653aSJeff Kirsher  *  0 on success and an appropriate (-)ve integer as defined in errno.h
8947ac6653aSJeff Kirsher  *  file on failure.
8957ac6653aSJeff Kirsher  */
8967ac6653aSJeff Kirsher static int stmmac_open(struct net_device *dev)
8977ac6653aSJeff Kirsher {
8987ac6653aSJeff Kirsher 	struct stmmac_priv *priv = netdev_priv(dev);
8997ac6653aSJeff Kirsher 	int ret;
9007ac6653aSJeff Kirsher 
901bfab27a1SGiuseppe CAVALLARO 	stmmac_check_ether_addr(priv);
9027ac6653aSJeff Kirsher 
903bfab27a1SGiuseppe CAVALLARO 	/* MDIO bus Registration */
904bfab27a1SGiuseppe CAVALLARO 	ret = stmmac_mdio_register(dev);
905bfab27a1SGiuseppe CAVALLARO 	if (ret < 0) {
906bfab27a1SGiuseppe CAVALLARO 		pr_debug("%s: MDIO bus (id: %d) registration failed",
907bfab27a1SGiuseppe CAVALLARO 			 __func__, priv->plat->bus_id);
908bfab27a1SGiuseppe CAVALLARO 		return ret;
909bfab27a1SGiuseppe CAVALLARO 	}
910bfab27a1SGiuseppe CAVALLARO 
9117ac6653aSJeff Kirsher #ifdef CONFIG_STMMAC_TIMER
9127ac6653aSJeff Kirsher 	priv->tm = kzalloc(sizeof(struct stmmac_timer *), GFP_KERNEL);
9137ac6653aSJeff Kirsher 	if (unlikely(priv->tm == NULL)) {
9147ac6653aSJeff Kirsher 		pr_err("%s: ERROR: timer memory alloc failed\n", __func__);
9157ac6653aSJeff Kirsher 		return -ENOMEM;
9167ac6653aSJeff Kirsher 	}
9177ac6653aSJeff Kirsher 	priv->tm->freq = tmrate;
9187ac6653aSJeff Kirsher 
9197ac6653aSJeff Kirsher 	/* Test if the external timer can be actually used.
9207ac6653aSJeff Kirsher 	 * In case of failure continue without timer. */
9217ac6653aSJeff Kirsher 	if (unlikely((stmmac_open_ext_timer(dev, priv->tm)) < 0)) {
9227ac6653aSJeff Kirsher 		pr_warning("stmmaceth: cannot attach the external timer.\n");
9237ac6653aSJeff Kirsher 		priv->tm->freq = 0;
9247ac6653aSJeff Kirsher 		priv->tm->timer_start = stmmac_no_timer_started;
9257ac6653aSJeff Kirsher 		priv->tm->timer_stop = stmmac_no_timer_stopped;
9267ac6653aSJeff Kirsher 	} else
9277ac6653aSJeff Kirsher 		priv->tm->enable = 1;
9287ac6653aSJeff Kirsher #endif
9297ac6653aSJeff Kirsher 	ret = stmmac_init_phy(dev);
9307ac6653aSJeff Kirsher 	if (unlikely(ret)) {
9317ac6653aSJeff Kirsher 		pr_err("%s: Cannot attach to PHY (error: %d)\n", __func__, ret);
9327ac6653aSJeff Kirsher 		goto open_error;
9337ac6653aSJeff Kirsher 	}
9347ac6653aSJeff Kirsher 
9357ac6653aSJeff Kirsher 	/* Create and initialize the TX/RX descriptors chains. */
9367ac6653aSJeff Kirsher 	priv->dma_tx_size = STMMAC_ALIGN(dma_txsize);
9377ac6653aSJeff Kirsher 	priv->dma_rx_size = STMMAC_ALIGN(dma_rxsize);
9387ac6653aSJeff Kirsher 	priv->dma_buf_sz = STMMAC_ALIGN(buf_sz);
9397ac6653aSJeff Kirsher 	init_dma_desc_rings(dev);
9407ac6653aSJeff Kirsher 
9417ac6653aSJeff Kirsher 	/* DMA initialization and SW reset */
9427ac6653aSJeff Kirsher 	ret = priv->hw->dma->init(priv->ioaddr, priv->plat->pbl,
9437ac6653aSJeff Kirsher 				  priv->dma_tx_phy, priv->dma_rx_phy);
9447ac6653aSJeff Kirsher 	if (ret < 0) {
9457ac6653aSJeff Kirsher 		pr_err("%s: DMA initialization failed\n", __func__);
9467ac6653aSJeff Kirsher 		goto open_error;
9477ac6653aSJeff Kirsher 	}
9487ac6653aSJeff Kirsher 
9497ac6653aSJeff Kirsher 	/* Copy the MAC addr into the HW  */
9507ac6653aSJeff Kirsher 	priv->hw->mac->set_umac_addr(priv->ioaddr, dev->dev_addr, 0);
951cf3f047bSGiuseppe CAVALLARO 
9527ac6653aSJeff Kirsher 	/* If required, perform hw setup of the bus. */
9537ac6653aSJeff Kirsher 	if (priv->plat->bus_setup)
9547ac6653aSJeff Kirsher 		priv->plat->bus_setup(priv->ioaddr);
955cf3f047bSGiuseppe CAVALLARO 
9567ac6653aSJeff Kirsher 	/* Initialize the MAC Core */
9577ac6653aSJeff Kirsher 	priv->hw->mac->core_init(priv->ioaddr);
9587ac6653aSJeff Kirsher 
9597ac6653aSJeff Kirsher 	/* Request the IRQ lines */
9607ac6653aSJeff Kirsher 	ret = request_irq(dev->irq, stmmac_interrupt,
9617ac6653aSJeff Kirsher 			 IRQF_SHARED, dev->name, dev);
9627ac6653aSJeff Kirsher 	if (unlikely(ret < 0)) {
9637ac6653aSJeff Kirsher 		pr_err("%s: ERROR: allocating the IRQ %d (error: %d)\n",
9647ac6653aSJeff Kirsher 		       __func__, dev->irq, ret);
9657ac6653aSJeff Kirsher 		goto open_error;
9667ac6653aSJeff Kirsher 	}
9677ac6653aSJeff Kirsher 
9687a13f8f5SFrancesco Virlinzi 	/* Request the Wake IRQ in case of another line is used for WoL */
9697a13f8f5SFrancesco Virlinzi 	if (priv->wol_irq != dev->irq) {
9707a13f8f5SFrancesco Virlinzi 		ret = request_irq(priv->wol_irq, stmmac_interrupt,
9717a13f8f5SFrancesco Virlinzi 				  IRQF_SHARED, dev->name, dev);
9727a13f8f5SFrancesco Virlinzi 		if (unlikely(ret < 0)) {
9737a13f8f5SFrancesco Virlinzi 			pr_err("%s: ERROR: allocating the ext WoL IRQ %d "
9747a13f8f5SFrancesco Virlinzi 			       "(error: %d)\n",	__func__, priv->wol_irq, ret);
9757a13f8f5SFrancesco Virlinzi 			goto open_error_wolirq;
9767a13f8f5SFrancesco Virlinzi 		}
9777a13f8f5SFrancesco Virlinzi 	}
9787a13f8f5SFrancesco Virlinzi 
9797ac6653aSJeff Kirsher 	/* Enable the MAC Rx/Tx */
980bfab27a1SGiuseppe CAVALLARO 	stmmac_set_mac(priv->ioaddr, true);
9817ac6653aSJeff Kirsher 
9827ac6653aSJeff Kirsher 	/* Set the HW DMA mode and the COE */
9837ac6653aSJeff Kirsher 	stmmac_dma_operation_mode(priv);
9847ac6653aSJeff Kirsher 
9857ac6653aSJeff Kirsher 	/* Extra statistics */
9867ac6653aSJeff Kirsher 	memset(&priv->xstats, 0, sizeof(struct stmmac_extra_stats));
9877ac6653aSJeff Kirsher 	priv->xstats.threshold = tc;
9887ac6653aSJeff Kirsher 
9891c901a46SGiuseppe CAVALLARO 	stmmac_mmc_setup(priv);
9901c901a46SGiuseppe CAVALLARO 
991bfab27a1SGiuseppe CAVALLARO #ifdef CONFIG_STMMAC_DEBUG_FS
992bfab27a1SGiuseppe CAVALLARO 	ret = stmmac_init_fs(dev);
993bfab27a1SGiuseppe CAVALLARO 	if (ret < 0)
994cf3f047bSGiuseppe CAVALLARO 		pr_warning("%s: failed debugFS registration\n", __func__);
995bfab27a1SGiuseppe CAVALLARO #endif
9967ac6653aSJeff Kirsher 	/* Start the ball rolling... */
9977ac6653aSJeff Kirsher 	DBG(probe, DEBUG, "%s: DMA RX/TX processes started...\n", dev->name);
9987ac6653aSJeff Kirsher 	priv->hw->dma->start_tx(priv->ioaddr);
9997ac6653aSJeff Kirsher 	priv->hw->dma->start_rx(priv->ioaddr);
10007ac6653aSJeff Kirsher 
10017ac6653aSJeff Kirsher #ifdef CONFIG_STMMAC_TIMER
10027ac6653aSJeff Kirsher 	priv->tm->timer_start(tmrate);
10037ac6653aSJeff Kirsher #endif
1004cf3f047bSGiuseppe CAVALLARO 
10057ac6653aSJeff Kirsher 	/* Dump DMA/MAC registers */
10067ac6653aSJeff Kirsher 	if (netif_msg_hw(priv)) {
10077ac6653aSJeff Kirsher 		priv->hw->mac->dump_regs(priv->ioaddr);
10087ac6653aSJeff Kirsher 		priv->hw->dma->dump_regs(priv->ioaddr);
10097ac6653aSJeff Kirsher 	}
10107ac6653aSJeff Kirsher 
10117ac6653aSJeff Kirsher 	if (priv->phydev)
10127ac6653aSJeff Kirsher 		phy_start(priv->phydev);
10137ac6653aSJeff Kirsher 
10147ac6653aSJeff Kirsher 	napi_enable(&priv->napi);
10157ac6653aSJeff Kirsher 	skb_queue_head_init(&priv->rx_recycle);
10167ac6653aSJeff Kirsher 	netif_start_queue(dev);
10177ac6653aSJeff Kirsher 
10187ac6653aSJeff Kirsher 	return 0;
10197ac6653aSJeff Kirsher 
10207a13f8f5SFrancesco Virlinzi open_error_wolirq:
10217a13f8f5SFrancesco Virlinzi 	free_irq(dev->irq, dev);
10227a13f8f5SFrancesco Virlinzi 
10237ac6653aSJeff Kirsher open_error:
10247ac6653aSJeff Kirsher #ifdef CONFIG_STMMAC_TIMER
10257ac6653aSJeff Kirsher 	kfree(priv->tm);
10267ac6653aSJeff Kirsher #endif
10277ac6653aSJeff Kirsher 	if (priv->phydev)
10287ac6653aSJeff Kirsher 		phy_disconnect(priv->phydev);
10297ac6653aSJeff Kirsher 
10307ac6653aSJeff Kirsher 	return ret;
10317ac6653aSJeff Kirsher }
10327ac6653aSJeff Kirsher 
10337ac6653aSJeff Kirsher /**
10347ac6653aSJeff Kirsher  *  stmmac_release - close entry point of the driver
10357ac6653aSJeff Kirsher  *  @dev : device pointer.
10367ac6653aSJeff Kirsher  *  Description:
10377ac6653aSJeff Kirsher  *  This is the stop entry point of the driver.
10387ac6653aSJeff Kirsher  */
10397ac6653aSJeff Kirsher static int stmmac_release(struct net_device *dev)
10407ac6653aSJeff Kirsher {
10417ac6653aSJeff Kirsher 	struct stmmac_priv *priv = netdev_priv(dev);
10427ac6653aSJeff Kirsher 
10437ac6653aSJeff Kirsher 	/* Stop and disconnect the PHY */
10447ac6653aSJeff Kirsher 	if (priv->phydev) {
10457ac6653aSJeff Kirsher 		phy_stop(priv->phydev);
10467ac6653aSJeff Kirsher 		phy_disconnect(priv->phydev);
10477ac6653aSJeff Kirsher 		priv->phydev = NULL;
10487ac6653aSJeff Kirsher 	}
10497ac6653aSJeff Kirsher 
10507ac6653aSJeff Kirsher 	netif_stop_queue(dev);
10517ac6653aSJeff Kirsher 
10527ac6653aSJeff Kirsher #ifdef CONFIG_STMMAC_TIMER
10537ac6653aSJeff Kirsher 	/* Stop and release the timer */
10547ac6653aSJeff Kirsher 	stmmac_close_ext_timer();
10557ac6653aSJeff Kirsher 	if (priv->tm != NULL)
10567ac6653aSJeff Kirsher 		kfree(priv->tm);
10577ac6653aSJeff Kirsher #endif
10587ac6653aSJeff Kirsher 	napi_disable(&priv->napi);
10597ac6653aSJeff Kirsher 	skb_queue_purge(&priv->rx_recycle);
10607ac6653aSJeff Kirsher 
10617ac6653aSJeff Kirsher 	/* Free the IRQ lines */
10627ac6653aSJeff Kirsher 	free_irq(dev->irq, dev);
10637a13f8f5SFrancesco Virlinzi 	if (priv->wol_irq != dev->irq)
10647a13f8f5SFrancesco Virlinzi 		free_irq(priv->wol_irq, dev);
10657ac6653aSJeff Kirsher 
10667ac6653aSJeff Kirsher 	/* Stop TX/RX DMA and clear the descriptors */
10677ac6653aSJeff Kirsher 	priv->hw->dma->stop_tx(priv->ioaddr);
10687ac6653aSJeff Kirsher 	priv->hw->dma->stop_rx(priv->ioaddr);
10697ac6653aSJeff Kirsher 
10707ac6653aSJeff Kirsher 	/* Release and free the Rx/Tx resources */
10717ac6653aSJeff Kirsher 	free_dma_desc_resources(priv);
10727ac6653aSJeff Kirsher 
10737ac6653aSJeff Kirsher 	/* Disable the MAC Rx/Tx */
1074bfab27a1SGiuseppe CAVALLARO 	stmmac_set_mac(priv->ioaddr, false);
10757ac6653aSJeff Kirsher 
10767ac6653aSJeff Kirsher 	netif_carrier_off(dev);
10777ac6653aSJeff Kirsher 
1078bfab27a1SGiuseppe CAVALLARO #ifdef CONFIG_STMMAC_DEBUG_FS
1079bfab27a1SGiuseppe CAVALLARO 	stmmac_exit_fs();
1080bfab27a1SGiuseppe CAVALLARO #endif
1081bfab27a1SGiuseppe CAVALLARO 	stmmac_mdio_unregister(dev);
1082bfab27a1SGiuseppe CAVALLARO 
10837ac6653aSJeff Kirsher 	return 0;
10847ac6653aSJeff Kirsher }
10857ac6653aSJeff Kirsher 
10867ac6653aSJeff Kirsher /**
10877ac6653aSJeff Kirsher  *  stmmac_xmit:
10887ac6653aSJeff Kirsher  *  @skb : the socket buffer
10897ac6653aSJeff Kirsher  *  @dev : device pointer
10907ac6653aSJeff Kirsher  *  Description : Tx entry point of the driver.
10917ac6653aSJeff Kirsher  */
10927ac6653aSJeff Kirsher static netdev_tx_t stmmac_xmit(struct sk_buff *skb, struct net_device *dev)
10937ac6653aSJeff Kirsher {
10947ac6653aSJeff Kirsher 	struct stmmac_priv *priv = netdev_priv(dev);
10957ac6653aSJeff Kirsher 	unsigned int txsize = priv->dma_tx_size;
10967ac6653aSJeff Kirsher 	unsigned int entry;
10977ac6653aSJeff Kirsher 	int i, csum_insertion = 0;
10987ac6653aSJeff Kirsher 	int nfrags = skb_shinfo(skb)->nr_frags;
10997ac6653aSJeff Kirsher 	struct dma_desc *desc, *first;
1100286a8372SGiuseppe CAVALLARO 	unsigned int nopaged_len = skb_headlen(skb);
11017ac6653aSJeff Kirsher 
11027ac6653aSJeff Kirsher 	if (unlikely(stmmac_tx_avail(priv) < nfrags + 1)) {
11037ac6653aSJeff Kirsher 		if (!netif_queue_stopped(dev)) {
11047ac6653aSJeff Kirsher 			netif_stop_queue(dev);
11057ac6653aSJeff Kirsher 			/* This is a hard error, log it. */
11067ac6653aSJeff Kirsher 			pr_err("%s: BUG! Tx Ring full when queue awake\n",
11077ac6653aSJeff Kirsher 				__func__);
11087ac6653aSJeff Kirsher 		}
11097ac6653aSJeff Kirsher 		return NETDEV_TX_BUSY;
11107ac6653aSJeff Kirsher 	}
11117ac6653aSJeff Kirsher 
1112a9097a96SGiuseppe CAVALLARO 	spin_lock(&priv->tx_lock);
1113a9097a96SGiuseppe CAVALLARO 
11147ac6653aSJeff Kirsher 	entry = priv->cur_tx % txsize;
11157ac6653aSJeff Kirsher 
11167ac6653aSJeff Kirsher #ifdef STMMAC_XMIT_DEBUG
11177ac6653aSJeff Kirsher 	if ((skb->len > ETH_FRAME_LEN) || nfrags)
11187ac6653aSJeff Kirsher 		pr_info("stmmac xmit:\n"
11197ac6653aSJeff Kirsher 		       "\tskb addr %p - len: %d - nopaged_len: %d\n"
11207ac6653aSJeff Kirsher 		       "\tn_frags: %d - ip_summed: %d - %s gso\n",
1121286a8372SGiuseppe CAVALLARO 		       skb, skb->len, nopaged_len, nfrags, skb->ip_summed,
11227ac6653aSJeff Kirsher 		       !skb_is_gso(skb) ? "isn't" : "is");
11237ac6653aSJeff Kirsher #endif
11247ac6653aSJeff Kirsher 
11257ac6653aSJeff Kirsher 	csum_insertion = (skb->ip_summed == CHECKSUM_PARTIAL);
11267ac6653aSJeff Kirsher 
11277ac6653aSJeff Kirsher 	desc = priv->dma_tx + entry;
11287ac6653aSJeff Kirsher 	first = desc;
11297ac6653aSJeff Kirsher 
11307ac6653aSJeff Kirsher #ifdef STMMAC_XMIT_DEBUG
11317ac6653aSJeff Kirsher 	if ((nfrags > 0) || (skb->len > ETH_FRAME_LEN))
11327ac6653aSJeff Kirsher 		pr_debug("stmmac xmit: skb len: %d, nopaged_len: %d,\n"
11337ac6653aSJeff Kirsher 		       "\t\tn_frags: %d, ip_summed: %d\n",
1134286a8372SGiuseppe CAVALLARO 		       skb->len, nopaged_len, nfrags, skb->ip_summed);
11357ac6653aSJeff Kirsher #endif
11367ac6653aSJeff Kirsher 	priv->tx_skbuff[entry] = skb;
1137286a8372SGiuseppe CAVALLARO 
1138286a8372SGiuseppe CAVALLARO 	if (priv->hw->ring->is_jumbo_frm(skb->len, priv->plat->enh_desc)) {
1139286a8372SGiuseppe CAVALLARO 		entry = priv->hw->ring->jumbo_frm(priv, skb, csum_insertion);
11407ac6653aSJeff Kirsher 		desc = priv->dma_tx + entry;
11417ac6653aSJeff Kirsher 	} else {
11427ac6653aSJeff Kirsher 		desc->des2 = dma_map_single(priv->device, skb->data,
11437ac6653aSJeff Kirsher 					nopaged_len, DMA_TO_DEVICE);
11447ac6653aSJeff Kirsher 		priv->hw->desc->prepare_tx_desc(desc, 1, nopaged_len,
11457ac6653aSJeff Kirsher 						csum_insertion);
11467ac6653aSJeff Kirsher 	}
11477ac6653aSJeff Kirsher 
11487ac6653aSJeff Kirsher 	for (i = 0; i < nfrags; i++) {
11499e903e08SEric Dumazet 		const skb_frag_t *frag = &skb_shinfo(skb)->frags[i];
11509e903e08SEric Dumazet 		int len = skb_frag_size(frag);
11517ac6653aSJeff Kirsher 
11527ac6653aSJeff Kirsher 		entry = (++priv->cur_tx) % txsize;
11537ac6653aSJeff Kirsher 		desc = priv->dma_tx + entry;
11547ac6653aSJeff Kirsher 
11557ac6653aSJeff Kirsher 		TX_DBG("\t[entry %d] segment len: %d\n", entry, len);
1156f722380dSIan Campbell 		desc->des2 = skb_frag_dma_map(priv->device, frag, 0, len,
1157f722380dSIan Campbell 					      DMA_TO_DEVICE);
11587ac6653aSJeff Kirsher 		priv->tx_skbuff[entry] = NULL;
11597ac6653aSJeff Kirsher 		priv->hw->desc->prepare_tx_desc(desc, 0, len, csum_insertion);
11607ac6653aSJeff Kirsher 		wmb();
11617ac6653aSJeff Kirsher 		priv->hw->desc->set_tx_owner(desc);
11627ac6653aSJeff Kirsher 	}
11637ac6653aSJeff Kirsher 
11647ac6653aSJeff Kirsher 	/* Interrupt on completition only for the latest segment */
11657ac6653aSJeff Kirsher 	priv->hw->desc->close_tx_desc(desc);
11667ac6653aSJeff Kirsher 
11677ac6653aSJeff Kirsher #ifdef CONFIG_STMMAC_TIMER
11687ac6653aSJeff Kirsher 	/* Clean IC while using timer */
11697ac6653aSJeff Kirsher 	if (likely(priv->tm->enable))
11707ac6653aSJeff Kirsher 		priv->hw->desc->clear_tx_ic(desc);
11717ac6653aSJeff Kirsher #endif
11727ac6653aSJeff Kirsher 
11737ac6653aSJeff Kirsher 	wmb();
11747ac6653aSJeff Kirsher 
11757ac6653aSJeff Kirsher 	/* To avoid raise condition */
11767ac6653aSJeff Kirsher 	priv->hw->desc->set_tx_owner(first);
11777ac6653aSJeff Kirsher 
11787ac6653aSJeff Kirsher 	priv->cur_tx++;
11797ac6653aSJeff Kirsher 
11807ac6653aSJeff Kirsher #ifdef STMMAC_XMIT_DEBUG
11817ac6653aSJeff Kirsher 	if (netif_msg_pktdata(priv)) {
11827ac6653aSJeff Kirsher 		pr_info("stmmac xmit: current=%d, dirty=%d, entry=%d, "
11837ac6653aSJeff Kirsher 		       "first=%p, nfrags=%d\n",
11847ac6653aSJeff Kirsher 		       (priv->cur_tx % txsize), (priv->dirty_tx % txsize),
11857ac6653aSJeff Kirsher 		       entry, first, nfrags);
11867ac6653aSJeff Kirsher 		display_ring(priv->dma_tx, txsize);
11877ac6653aSJeff Kirsher 		pr_info(">>> frame to be transmitted: ");
11887ac6653aSJeff Kirsher 		print_pkt(skb->data, skb->len);
11897ac6653aSJeff Kirsher 	}
11907ac6653aSJeff Kirsher #endif
11917ac6653aSJeff Kirsher 	if (unlikely(stmmac_tx_avail(priv) <= (MAX_SKB_FRAGS + 1))) {
11927ac6653aSJeff Kirsher 		TX_DBG("%s: stop transmitted packets\n", __func__);
11937ac6653aSJeff Kirsher 		netif_stop_queue(dev);
11947ac6653aSJeff Kirsher 	}
11957ac6653aSJeff Kirsher 
11967ac6653aSJeff Kirsher 	dev->stats.tx_bytes += skb->len;
11977ac6653aSJeff Kirsher 
11987ac6653aSJeff Kirsher 	skb_tx_timestamp(skb);
11997ac6653aSJeff Kirsher 
12007ac6653aSJeff Kirsher 	priv->hw->dma->enable_dma_transmission(priv->ioaddr);
12017ac6653aSJeff Kirsher 
1202a9097a96SGiuseppe CAVALLARO 	spin_unlock(&priv->tx_lock);
1203a9097a96SGiuseppe CAVALLARO 
12047ac6653aSJeff Kirsher 	return NETDEV_TX_OK;
12057ac6653aSJeff Kirsher }
12067ac6653aSJeff Kirsher 
12077ac6653aSJeff Kirsher static inline void stmmac_rx_refill(struct stmmac_priv *priv)
12087ac6653aSJeff Kirsher {
12097ac6653aSJeff Kirsher 	unsigned int rxsize = priv->dma_rx_size;
12107ac6653aSJeff Kirsher 	int bfsize = priv->dma_buf_sz;
12117ac6653aSJeff Kirsher 	struct dma_desc *p = priv->dma_rx;
12127ac6653aSJeff Kirsher 
12137ac6653aSJeff Kirsher 	for (; priv->cur_rx - priv->dirty_rx > 0; priv->dirty_rx++) {
12147ac6653aSJeff Kirsher 		unsigned int entry = priv->dirty_rx % rxsize;
12157ac6653aSJeff Kirsher 		if (likely(priv->rx_skbuff[entry] == NULL)) {
12167ac6653aSJeff Kirsher 			struct sk_buff *skb;
12177ac6653aSJeff Kirsher 
12187ac6653aSJeff Kirsher 			skb = __skb_dequeue(&priv->rx_recycle);
12197ac6653aSJeff Kirsher 			if (skb == NULL)
12207ac6653aSJeff Kirsher 				skb = netdev_alloc_skb_ip_align(priv->dev,
12217ac6653aSJeff Kirsher 								bfsize);
12227ac6653aSJeff Kirsher 
12237ac6653aSJeff Kirsher 			if (unlikely(skb == NULL))
12247ac6653aSJeff Kirsher 				break;
12257ac6653aSJeff Kirsher 
12267ac6653aSJeff Kirsher 			priv->rx_skbuff[entry] = skb;
12277ac6653aSJeff Kirsher 			priv->rx_skbuff_dma[entry] =
12287ac6653aSJeff Kirsher 			    dma_map_single(priv->device, skb->data, bfsize,
12297ac6653aSJeff Kirsher 					   DMA_FROM_DEVICE);
12307ac6653aSJeff Kirsher 
12317ac6653aSJeff Kirsher 			(p + entry)->des2 = priv->rx_skbuff_dma[entry];
1232286a8372SGiuseppe CAVALLARO 
1233286a8372SGiuseppe CAVALLARO 			if (unlikely(priv->plat->has_gmac))
1234286a8372SGiuseppe CAVALLARO 				priv->hw->ring->refill_desc3(bfsize, p + entry);
1235286a8372SGiuseppe CAVALLARO 
12367ac6653aSJeff Kirsher 			RX_DBG(KERN_INFO "\trefill entry #%d\n", entry);
12377ac6653aSJeff Kirsher 		}
12387ac6653aSJeff Kirsher 		wmb();
12397ac6653aSJeff Kirsher 		priv->hw->desc->set_rx_owner(p + entry);
12407ac6653aSJeff Kirsher 	}
12417ac6653aSJeff Kirsher }
12427ac6653aSJeff Kirsher 
12437ac6653aSJeff Kirsher static int stmmac_rx(struct stmmac_priv *priv, int limit)
12447ac6653aSJeff Kirsher {
12457ac6653aSJeff Kirsher 	unsigned int rxsize = priv->dma_rx_size;
12467ac6653aSJeff Kirsher 	unsigned int entry = priv->cur_rx % rxsize;
12477ac6653aSJeff Kirsher 	unsigned int next_entry;
12487ac6653aSJeff Kirsher 	unsigned int count = 0;
12497ac6653aSJeff Kirsher 	struct dma_desc *p = priv->dma_rx + entry;
12507ac6653aSJeff Kirsher 	struct dma_desc *p_next;
12517ac6653aSJeff Kirsher 
12527ac6653aSJeff Kirsher #ifdef STMMAC_RX_DEBUG
12537ac6653aSJeff Kirsher 	if (netif_msg_hw(priv)) {
12547ac6653aSJeff Kirsher 		pr_debug(">>> stmmac_rx: descriptor ring:\n");
12557ac6653aSJeff Kirsher 		display_ring(priv->dma_rx, rxsize);
12567ac6653aSJeff Kirsher 	}
12577ac6653aSJeff Kirsher #endif
12587ac6653aSJeff Kirsher 	count = 0;
12597ac6653aSJeff Kirsher 	while (!priv->hw->desc->get_rx_owner(p)) {
12607ac6653aSJeff Kirsher 		int status;
12617ac6653aSJeff Kirsher 
12627ac6653aSJeff Kirsher 		if (count >= limit)
12637ac6653aSJeff Kirsher 			break;
12647ac6653aSJeff Kirsher 
12657ac6653aSJeff Kirsher 		count++;
12667ac6653aSJeff Kirsher 
12677ac6653aSJeff Kirsher 		next_entry = (++priv->cur_rx) % rxsize;
12687ac6653aSJeff Kirsher 		p_next = priv->dma_rx + next_entry;
12697ac6653aSJeff Kirsher 		prefetch(p_next);
12707ac6653aSJeff Kirsher 
12717ac6653aSJeff Kirsher 		/* read the status of the incoming frame */
12727ac6653aSJeff Kirsher 		status = (priv->hw->desc->rx_status(&priv->dev->stats,
12737ac6653aSJeff Kirsher 						    &priv->xstats, p));
12747ac6653aSJeff Kirsher 		if (unlikely(status == discard_frame))
12757ac6653aSJeff Kirsher 			priv->dev->stats.rx_errors++;
12767ac6653aSJeff Kirsher 		else {
12777ac6653aSJeff Kirsher 			struct sk_buff *skb;
12787ac6653aSJeff Kirsher 			int frame_len;
12797ac6653aSJeff Kirsher 
12807ac6653aSJeff Kirsher 			frame_len = priv->hw->desc->get_rx_frame_len(p);
12817ac6653aSJeff Kirsher 			/* ACS is set; GMAC core strips PAD/FCS for IEEE 802.3
12827ac6653aSJeff Kirsher 			 * Type frames (LLC/LLC-SNAP) */
12837ac6653aSJeff Kirsher 			if (unlikely(status != llc_snap))
12847ac6653aSJeff Kirsher 				frame_len -= ETH_FCS_LEN;
12857ac6653aSJeff Kirsher #ifdef STMMAC_RX_DEBUG
12867ac6653aSJeff Kirsher 			if (frame_len > ETH_FRAME_LEN)
12877ac6653aSJeff Kirsher 				pr_debug("\tRX frame size %d, COE status: %d\n",
12887ac6653aSJeff Kirsher 					frame_len, status);
12897ac6653aSJeff Kirsher 
12907ac6653aSJeff Kirsher 			if (netif_msg_hw(priv))
12917ac6653aSJeff Kirsher 				pr_debug("\tdesc: %p [entry %d] buff=0x%x\n",
12927ac6653aSJeff Kirsher 					p, entry, p->des2);
12937ac6653aSJeff Kirsher #endif
12947ac6653aSJeff Kirsher 			skb = priv->rx_skbuff[entry];
12957ac6653aSJeff Kirsher 			if (unlikely(!skb)) {
12967ac6653aSJeff Kirsher 				pr_err("%s: Inconsistent Rx descriptor chain\n",
12977ac6653aSJeff Kirsher 					priv->dev->name);
12987ac6653aSJeff Kirsher 				priv->dev->stats.rx_dropped++;
12997ac6653aSJeff Kirsher 				break;
13007ac6653aSJeff Kirsher 			}
13017ac6653aSJeff Kirsher 			prefetch(skb->data - NET_IP_ALIGN);
13027ac6653aSJeff Kirsher 			priv->rx_skbuff[entry] = NULL;
13037ac6653aSJeff Kirsher 
13047ac6653aSJeff Kirsher 			skb_put(skb, frame_len);
13057ac6653aSJeff Kirsher 			dma_unmap_single(priv->device,
13067ac6653aSJeff Kirsher 					 priv->rx_skbuff_dma[entry],
13077ac6653aSJeff Kirsher 					 priv->dma_buf_sz, DMA_FROM_DEVICE);
13087ac6653aSJeff Kirsher #ifdef STMMAC_RX_DEBUG
13097ac6653aSJeff Kirsher 			if (netif_msg_pktdata(priv)) {
13107ac6653aSJeff Kirsher 				pr_info(" frame received (%dbytes)", frame_len);
13117ac6653aSJeff Kirsher 				print_pkt(skb->data, frame_len);
13127ac6653aSJeff Kirsher 			}
13137ac6653aSJeff Kirsher #endif
13147ac6653aSJeff Kirsher 			skb->protocol = eth_type_trans(skb, priv->dev);
13157ac6653aSJeff Kirsher 
13163c20f72fSGiuseppe CAVALLARO 			if (unlikely(!priv->rx_coe)) {
13173c20f72fSGiuseppe CAVALLARO 				/* No RX COE for old mac10/100 devices */
13187ac6653aSJeff Kirsher 				skb_checksum_none_assert(skb);
13197ac6653aSJeff Kirsher 				netif_receive_skb(skb);
13207ac6653aSJeff Kirsher 			} else {
13217ac6653aSJeff Kirsher 				skb->ip_summed = CHECKSUM_UNNECESSARY;
13227ac6653aSJeff Kirsher 				napi_gro_receive(&priv->napi, skb);
13237ac6653aSJeff Kirsher 			}
13247ac6653aSJeff Kirsher 
13257ac6653aSJeff Kirsher 			priv->dev->stats.rx_packets++;
13267ac6653aSJeff Kirsher 			priv->dev->stats.rx_bytes += frame_len;
13277ac6653aSJeff Kirsher 		}
13287ac6653aSJeff Kirsher 		entry = next_entry;
13297ac6653aSJeff Kirsher 		p = p_next;	/* use prefetched values */
13307ac6653aSJeff Kirsher 	}
13317ac6653aSJeff Kirsher 
13327ac6653aSJeff Kirsher 	stmmac_rx_refill(priv);
13337ac6653aSJeff Kirsher 
13347ac6653aSJeff Kirsher 	priv->xstats.rx_pkt_n += count;
13357ac6653aSJeff Kirsher 
13367ac6653aSJeff Kirsher 	return count;
13377ac6653aSJeff Kirsher }
13387ac6653aSJeff Kirsher 
13397ac6653aSJeff Kirsher /**
13407ac6653aSJeff Kirsher  *  stmmac_poll - stmmac poll method (NAPI)
13417ac6653aSJeff Kirsher  *  @napi : pointer to the napi structure.
13427ac6653aSJeff Kirsher  *  @budget : maximum number of packets that the current CPU can receive from
13437ac6653aSJeff Kirsher  *	      all interfaces.
13447ac6653aSJeff Kirsher  *  Description :
13457ac6653aSJeff Kirsher  *   This function implements the the reception process.
13467ac6653aSJeff Kirsher  *   Also it runs the TX completion thread
13477ac6653aSJeff Kirsher  */
13487ac6653aSJeff Kirsher static int stmmac_poll(struct napi_struct *napi, int budget)
13497ac6653aSJeff Kirsher {
13507ac6653aSJeff Kirsher 	struct stmmac_priv *priv = container_of(napi, struct stmmac_priv, napi);
13517ac6653aSJeff Kirsher 	int work_done = 0;
13527ac6653aSJeff Kirsher 
13537ac6653aSJeff Kirsher 	priv->xstats.poll_n++;
13547ac6653aSJeff Kirsher 	stmmac_tx(priv);
13557ac6653aSJeff Kirsher 	work_done = stmmac_rx(priv, budget);
13567ac6653aSJeff Kirsher 
13577ac6653aSJeff Kirsher 	if (work_done < budget) {
13587ac6653aSJeff Kirsher 		napi_complete(napi);
13597ac6653aSJeff Kirsher 		stmmac_enable_irq(priv);
13607ac6653aSJeff Kirsher 	}
13617ac6653aSJeff Kirsher 	return work_done;
13627ac6653aSJeff Kirsher }
13637ac6653aSJeff Kirsher 
13647ac6653aSJeff Kirsher /**
13657ac6653aSJeff Kirsher  *  stmmac_tx_timeout
13667ac6653aSJeff Kirsher  *  @dev : Pointer to net device structure
13677ac6653aSJeff Kirsher  *  Description: this function is called when a packet transmission fails to
13687ac6653aSJeff Kirsher  *   complete within a reasonable tmrate. The driver will mark the error in the
13697ac6653aSJeff Kirsher  *   netdev structure and arrange for the device to be reset to a sane state
13707ac6653aSJeff Kirsher  *   in order to transmit a new packet.
13717ac6653aSJeff Kirsher  */
13727ac6653aSJeff Kirsher static void stmmac_tx_timeout(struct net_device *dev)
13737ac6653aSJeff Kirsher {
13747ac6653aSJeff Kirsher 	struct stmmac_priv *priv = netdev_priv(dev);
13757ac6653aSJeff Kirsher 
13767ac6653aSJeff Kirsher 	/* Clear Tx resources and restart transmitting again */
13777ac6653aSJeff Kirsher 	stmmac_tx_err(priv);
13787ac6653aSJeff Kirsher }
13797ac6653aSJeff Kirsher 
13807ac6653aSJeff Kirsher /* Configuration changes (passed on by ifconfig) */
13817ac6653aSJeff Kirsher static int stmmac_config(struct net_device *dev, struct ifmap *map)
13827ac6653aSJeff Kirsher {
13837ac6653aSJeff Kirsher 	if (dev->flags & IFF_UP)	/* can't act on a running interface */
13847ac6653aSJeff Kirsher 		return -EBUSY;
13857ac6653aSJeff Kirsher 
13867ac6653aSJeff Kirsher 	/* Don't allow changing the I/O address */
13877ac6653aSJeff Kirsher 	if (map->base_addr != dev->base_addr) {
13887ac6653aSJeff Kirsher 		pr_warning("%s: can't change I/O address\n", dev->name);
13897ac6653aSJeff Kirsher 		return -EOPNOTSUPP;
13907ac6653aSJeff Kirsher 	}
13917ac6653aSJeff Kirsher 
13927ac6653aSJeff Kirsher 	/* Don't allow changing the IRQ */
13937ac6653aSJeff Kirsher 	if (map->irq != dev->irq) {
13947ac6653aSJeff Kirsher 		pr_warning("%s: can't change IRQ number %d\n",
13957ac6653aSJeff Kirsher 		       dev->name, dev->irq);
13967ac6653aSJeff Kirsher 		return -EOPNOTSUPP;
13977ac6653aSJeff Kirsher 	}
13987ac6653aSJeff Kirsher 
13997ac6653aSJeff Kirsher 	/* ignore other fields */
14007ac6653aSJeff Kirsher 	return 0;
14017ac6653aSJeff Kirsher }
14027ac6653aSJeff Kirsher 
14037ac6653aSJeff Kirsher /**
140401789349SJiri Pirko  *  stmmac_set_rx_mode - entry point for multicast addressing
14057ac6653aSJeff Kirsher  *  @dev : pointer to the device structure
14067ac6653aSJeff Kirsher  *  Description:
14077ac6653aSJeff Kirsher  *  This function is a driver entry point which gets called by the kernel
14087ac6653aSJeff Kirsher  *  whenever multicast addresses must be enabled/disabled.
14097ac6653aSJeff Kirsher  *  Return value:
14107ac6653aSJeff Kirsher  *  void.
14117ac6653aSJeff Kirsher  */
141201789349SJiri Pirko static void stmmac_set_rx_mode(struct net_device *dev)
14137ac6653aSJeff Kirsher {
14147ac6653aSJeff Kirsher 	struct stmmac_priv *priv = netdev_priv(dev);
14157ac6653aSJeff Kirsher 
14167ac6653aSJeff Kirsher 	spin_lock(&priv->lock);
14177ac6653aSJeff Kirsher 	priv->hw->mac->set_filter(dev);
14187ac6653aSJeff Kirsher 	spin_unlock(&priv->lock);
14197ac6653aSJeff Kirsher }
14207ac6653aSJeff Kirsher 
14217ac6653aSJeff Kirsher /**
14227ac6653aSJeff Kirsher  *  stmmac_change_mtu - entry point to change MTU size for the device.
14237ac6653aSJeff Kirsher  *  @dev : device pointer.
14247ac6653aSJeff Kirsher  *  @new_mtu : the new MTU size for the device.
14257ac6653aSJeff Kirsher  *  Description: the Maximum Transfer Unit (MTU) is used by the network layer
14267ac6653aSJeff Kirsher  *  to drive packet transmission. Ethernet has an MTU of 1500 octets
14277ac6653aSJeff Kirsher  *  (ETH_DATA_LEN). This value can be changed with ifconfig.
14287ac6653aSJeff Kirsher  *  Return value:
14297ac6653aSJeff Kirsher  *  0 on success and an appropriate (-)ve integer as defined in errno.h
14307ac6653aSJeff Kirsher  *  file on failure.
14317ac6653aSJeff Kirsher  */
14327ac6653aSJeff Kirsher static int stmmac_change_mtu(struct net_device *dev, int new_mtu)
14337ac6653aSJeff Kirsher {
14347ac6653aSJeff Kirsher 	struct stmmac_priv *priv = netdev_priv(dev);
14357ac6653aSJeff Kirsher 	int max_mtu;
14367ac6653aSJeff Kirsher 
14377ac6653aSJeff Kirsher 	if (netif_running(dev)) {
14387ac6653aSJeff Kirsher 		pr_err("%s: must be stopped to change its MTU\n", dev->name);
14397ac6653aSJeff Kirsher 		return -EBUSY;
14407ac6653aSJeff Kirsher 	}
14417ac6653aSJeff Kirsher 
144248febf7eSGiuseppe CAVALLARO 	if (priv->plat->enh_desc)
14437ac6653aSJeff Kirsher 		max_mtu = JUMBO_LEN;
14447ac6653aSJeff Kirsher 	else
144545db81e1SGiuseppe CAVALLARO 		max_mtu = SKB_MAX_HEAD(NET_SKB_PAD + NET_IP_ALIGN);
14467ac6653aSJeff Kirsher 
14477ac6653aSJeff Kirsher 	if ((new_mtu < 46) || (new_mtu > max_mtu)) {
14487ac6653aSJeff Kirsher 		pr_err("%s: invalid MTU, max MTU is: %d\n", dev->name, max_mtu);
14497ac6653aSJeff Kirsher 		return -EINVAL;
14507ac6653aSJeff Kirsher 	}
14517ac6653aSJeff Kirsher 
14527ac6653aSJeff Kirsher 	dev->mtu = new_mtu;
14537ac6653aSJeff Kirsher 	netdev_update_features(dev);
14547ac6653aSJeff Kirsher 
14557ac6653aSJeff Kirsher 	return 0;
14567ac6653aSJeff Kirsher }
14577ac6653aSJeff Kirsher 
1458c8f44affSMichał Mirosław static netdev_features_t stmmac_fix_features(struct net_device *dev,
1459c8f44affSMichał Mirosław 	netdev_features_t features)
14607ac6653aSJeff Kirsher {
14617ac6653aSJeff Kirsher 	struct stmmac_priv *priv = netdev_priv(dev);
14627ac6653aSJeff Kirsher 
14637ac6653aSJeff Kirsher 	if (!priv->rx_coe)
14647ac6653aSJeff Kirsher 		features &= ~NETIF_F_RXCSUM;
14657ac6653aSJeff Kirsher 	if (!priv->plat->tx_coe)
14667ac6653aSJeff Kirsher 		features &= ~NETIF_F_ALL_CSUM;
14677ac6653aSJeff Kirsher 
14687ac6653aSJeff Kirsher 	/* Some GMAC devices have a bugged Jumbo frame support that
14697ac6653aSJeff Kirsher 	 * needs to have the Tx COE disabled for oversized frames
14707ac6653aSJeff Kirsher 	 * (due to limited buffer sizes). In this case we disable
14717ac6653aSJeff Kirsher 	 * the TX csum insertionin the TDES and not use SF. */
14727ac6653aSJeff Kirsher 	if (priv->plat->bugged_jumbo && (dev->mtu > ETH_DATA_LEN))
14737ac6653aSJeff Kirsher 		features &= ~NETIF_F_ALL_CSUM;
14747ac6653aSJeff Kirsher 
14757ac6653aSJeff Kirsher 	return features;
14767ac6653aSJeff Kirsher }
14777ac6653aSJeff Kirsher 
14787ac6653aSJeff Kirsher static irqreturn_t stmmac_interrupt(int irq, void *dev_id)
14797ac6653aSJeff Kirsher {
14807ac6653aSJeff Kirsher 	struct net_device *dev = (struct net_device *)dev_id;
14817ac6653aSJeff Kirsher 	struct stmmac_priv *priv = netdev_priv(dev);
14827ac6653aSJeff Kirsher 
14837ac6653aSJeff Kirsher 	if (unlikely(!dev)) {
14847ac6653aSJeff Kirsher 		pr_err("%s: invalid dev pointer\n", __func__);
14857ac6653aSJeff Kirsher 		return IRQ_NONE;
14867ac6653aSJeff Kirsher 	}
14877ac6653aSJeff Kirsher 
14887ac6653aSJeff Kirsher 	if (priv->plat->has_gmac)
14897ac6653aSJeff Kirsher 		/* To handle GMAC own interrupts */
14907ac6653aSJeff Kirsher 		priv->hw->mac->host_irq_status((void __iomem *) dev->base_addr);
14917ac6653aSJeff Kirsher 
14927ac6653aSJeff Kirsher 	stmmac_dma_interrupt(priv);
14937ac6653aSJeff Kirsher 
14947ac6653aSJeff Kirsher 	return IRQ_HANDLED;
14957ac6653aSJeff Kirsher }
14967ac6653aSJeff Kirsher 
14977ac6653aSJeff Kirsher #ifdef CONFIG_NET_POLL_CONTROLLER
14987ac6653aSJeff Kirsher /* Polling receive - used by NETCONSOLE and other diagnostic tools
14997ac6653aSJeff Kirsher  * to allow network I/O with interrupts disabled. */
15007ac6653aSJeff Kirsher static void stmmac_poll_controller(struct net_device *dev)
15017ac6653aSJeff Kirsher {
15027ac6653aSJeff Kirsher 	disable_irq(dev->irq);
15037ac6653aSJeff Kirsher 	stmmac_interrupt(dev->irq, dev);
15047ac6653aSJeff Kirsher 	enable_irq(dev->irq);
15057ac6653aSJeff Kirsher }
15067ac6653aSJeff Kirsher #endif
15077ac6653aSJeff Kirsher 
15087ac6653aSJeff Kirsher /**
15097ac6653aSJeff Kirsher  *  stmmac_ioctl - Entry point for the Ioctl
15107ac6653aSJeff Kirsher  *  @dev: Device pointer.
15117ac6653aSJeff Kirsher  *  @rq: An IOCTL specefic structure, that can contain a pointer to
15127ac6653aSJeff Kirsher  *  a proprietary structure used to pass information to the driver.
15137ac6653aSJeff Kirsher  *  @cmd: IOCTL command
15147ac6653aSJeff Kirsher  *  Description:
15157ac6653aSJeff Kirsher  *  Currently there are no special functionality supported in IOCTL, just the
15167ac6653aSJeff Kirsher  *  phy_mii_ioctl(...) can be invoked.
15177ac6653aSJeff Kirsher  */
15187ac6653aSJeff Kirsher static int stmmac_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
15197ac6653aSJeff Kirsher {
15207ac6653aSJeff Kirsher 	struct stmmac_priv *priv = netdev_priv(dev);
15217ac6653aSJeff Kirsher 	int ret;
15227ac6653aSJeff Kirsher 
15237ac6653aSJeff Kirsher 	if (!netif_running(dev))
15247ac6653aSJeff Kirsher 		return -EINVAL;
15257ac6653aSJeff Kirsher 
15267ac6653aSJeff Kirsher 	if (!priv->phydev)
15277ac6653aSJeff Kirsher 		return -EINVAL;
15287ac6653aSJeff Kirsher 
15297ac6653aSJeff Kirsher 	ret = phy_mii_ioctl(priv->phydev, rq, cmd);
15307ac6653aSJeff Kirsher 
15317ac6653aSJeff Kirsher 	return ret;
15327ac6653aSJeff Kirsher }
15337ac6653aSJeff Kirsher 
15347ac29055SGiuseppe CAVALLARO #ifdef CONFIG_STMMAC_DEBUG_FS
15357ac29055SGiuseppe CAVALLARO static struct dentry *stmmac_fs_dir;
15367ac29055SGiuseppe CAVALLARO static struct dentry *stmmac_rings_status;
1537e7434821SGiuseppe CAVALLARO static struct dentry *stmmac_dma_cap;
15387ac29055SGiuseppe CAVALLARO 
15397ac29055SGiuseppe CAVALLARO static int stmmac_sysfs_ring_read(struct seq_file *seq, void *v)
15407ac29055SGiuseppe CAVALLARO {
15417ac29055SGiuseppe CAVALLARO 	struct tmp_s {
15427ac29055SGiuseppe CAVALLARO 		u64 a;
15437ac29055SGiuseppe CAVALLARO 		unsigned int b;
15447ac29055SGiuseppe CAVALLARO 		unsigned int c;
15457ac29055SGiuseppe CAVALLARO 	};
15467ac29055SGiuseppe CAVALLARO 	int i;
15477ac29055SGiuseppe CAVALLARO 	struct net_device *dev = seq->private;
15487ac29055SGiuseppe CAVALLARO 	struct stmmac_priv *priv = netdev_priv(dev);
15497ac29055SGiuseppe CAVALLARO 
15507ac29055SGiuseppe CAVALLARO 	seq_printf(seq, "=======================\n");
15517ac29055SGiuseppe CAVALLARO 	seq_printf(seq, " RX descriptor ring\n");
15527ac29055SGiuseppe CAVALLARO 	seq_printf(seq, "=======================\n");
15537ac29055SGiuseppe CAVALLARO 
15547ac29055SGiuseppe CAVALLARO 	for (i = 0; i < priv->dma_rx_size; i++) {
15557ac29055SGiuseppe CAVALLARO 		struct tmp_s *x = (struct tmp_s *)(priv->dma_rx + i);
15567ac29055SGiuseppe CAVALLARO 		seq_printf(seq, "[%d] DES0=0x%x DES1=0x%x BUF1=0x%x BUF2=0x%x",
15577ac29055SGiuseppe CAVALLARO 			   i, (unsigned int)(x->a),
15587ac29055SGiuseppe CAVALLARO 			   (unsigned int)((x->a) >> 32), x->b, x->c);
15597ac29055SGiuseppe CAVALLARO 		seq_printf(seq, "\n");
15607ac29055SGiuseppe CAVALLARO 	}
15617ac29055SGiuseppe CAVALLARO 
15627ac29055SGiuseppe CAVALLARO 	seq_printf(seq, "\n");
15637ac29055SGiuseppe CAVALLARO 	seq_printf(seq, "=======================\n");
15647ac29055SGiuseppe CAVALLARO 	seq_printf(seq, "  TX descriptor ring\n");
15657ac29055SGiuseppe CAVALLARO 	seq_printf(seq, "=======================\n");
15667ac29055SGiuseppe CAVALLARO 
15677ac29055SGiuseppe CAVALLARO 	for (i = 0; i < priv->dma_tx_size; i++) {
15687ac29055SGiuseppe CAVALLARO 		struct tmp_s *x = (struct tmp_s *)(priv->dma_tx + i);
15697ac29055SGiuseppe CAVALLARO 		seq_printf(seq, "[%d] DES0=0x%x DES1=0x%x BUF1=0x%x BUF2=0x%x",
15707ac29055SGiuseppe CAVALLARO 			   i, (unsigned int)(x->a),
15717ac29055SGiuseppe CAVALLARO 			   (unsigned int)((x->a) >> 32), x->b, x->c);
15727ac29055SGiuseppe CAVALLARO 		seq_printf(seq, "\n");
15737ac29055SGiuseppe CAVALLARO 	}
15747ac29055SGiuseppe CAVALLARO 
15757ac29055SGiuseppe CAVALLARO 	return 0;
15767ac29055SGiuseppe CAVALLARO }
15777ac29055SGiuseppe CAVALLARO 
15787ac29055SGiuseppe CAVALLARO static int stmmac_sysfs_ring_open(struct inode *inode, struct file *file)
15797ac29055SGiuseppe CAVALLARO {
15807ac29055SGiuseppe CAVALLARO 	return single_open(file, stmmac_sysfs_ring_read, inode->i_private);
15817ac29055SGiuseppe CAVALLARO }
15827ac29055SGiuseppe CAVALLARO 
15837ac29055SGiuseppe CAVALLARO static const struct file_operations stmmac_rings_status_fops = {
15847ac29055SGiuseppe CAVALLARO 	.owner = THIS_MODULE,
15857ac29055SGiuseppe CAVALLARO 	.open = stmmac_sysfs_ring_open,
15867ac29055SGiuseppe CAVALLARO 	.read = seq_read,
15877ac29055SGiuseppe CAVALLARO 	.llseek = seq_lseek,
15887ac29055SGiuseppe CAVALLARO 	.release = seq_release,
15897ac29055SGiuseppe CAVALLARO };
15907ac29055SGiuseppe CAVALLARO 
1591e7434821SGiuseppe CAVALLARO static int stmmac_sysfs_dma_cap_read(struct seq_file *seq, void *v)
1592e7434821SGiuseppe CAVALLARO {
1593e7434821SGiuseppe CAVALLARO 	struct net_device *dev = seq->private;
1594e7434821SGiuseppe CAVALLARO 	struct stmmac_priv *priv = netdev_priv(dev);
1595e7434821SGiuseppe CAVALLARO 
159619e30c14SGiuseppe CAVALLARO 	if (!priv->hw_cap_support) {
1597e7434821SGiuseppe CAVALLARO 		seq_printf(seq, "DMA HW features not supported\n");
1598e7434821SGiuseppe CAVALLARO 		return 0;
1599e7434821SGiuseppe CAVALLARO 	}
1600e7434821SGiuseppe CAVALLARO 
1601e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "==============================\n");
1602e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tDMA HW features\n");
1603e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "==============================\n");
1604e7434821SGiuseppe CAVALLARO 
1605e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\t10/100 Mbps %s\n",
1606e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.mbps_10_100) ? "Y" : "N");
1607e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\t1000 Mbps %s\n",
1608e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.mbps_1000) ? "Y" : "N");
1609e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tHalf duple %s\n",
1610e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.half_duplex) ? "Y" : "N");
1611e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tHash Filter: %s\n",
1612e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.hash_filter) ? "Y" : "N");
1613e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tMultiple MAC address registers: %s\n",
1614e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.multi_addr) ? "Y" : "N");
1615e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tPCS (TBI/SGMII/RTBI PHY interfatces): %s\n",
1616e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.pcs) ? "Y" : "N");
1617e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tSMA (MDIO) Interface: %s\n",
1618e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.sma_mdio) ? "Y" : "N");
1619e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tPMT Remote wake up: %s\n",
1620e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.pmt_remote_wake_up) ? "Y" : "N");
1621e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tPMT Magic Frame: %s\n",
1622e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.pmt_magic_frame) ? "Y" : "N");
1623e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tRMON module: %s\n",
1624e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.rmon) ? "Y" : "N");
1625e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tIEEE 1588-2002 Time Stamp: %s\n",
1626e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.time_stamp) ? "Y" : "N");
1627e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tIEEE 1588-2008 Advanced Time Stamp:%s\n",
1628e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.atime_stamp) ? "Y" : "N");
1629e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\t802.3az - Energy-Efficient Ethernet (EEE) %s\n",
1630e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.eee) ? "Y" : "N");
1631e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tAV features: %s\n", (priv->dma_cap.av) ? "Y" : "N");
1632e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tChecksum Offload in TX: %s\n",
1633e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.tx_coe) ? "Y" : "N");
1634e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tIP Checksum Offload (type1) in RX: %s\n",
1635e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.rx_coe_type1) ? "Y" : "N");
1636e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tIP Checksum Offload (type2) in RX: %s\n",
1637e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.rx_coe_type2) ? "Y" : "N");
1638e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tRXFIFO > 2048bytes: %s\n",
1639e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.rxfifo_over_2048) ? "Y" : "N");
1640e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tNumber of Additional RX channel: %d\n",
1641e7434821SGiuseppe CAVALLARO 		   priv->dma_cap.number_rx_channel);
1642e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tNumber of Additional TX channel: %d\n",
1643e7434821SGiuseppe CAVALLARO 		   priv->dma_cap.number_tx_channel);
1644e7434821SGiuseppe CAVALLARO 	seq_printf(seq, "\tEnhanced descriptors: %s\n",
1645e7434821SGiuseppe CAVALLARO 		   (priv->dma_cap.enh_desc) ? "Y" : "N");
1646e7434821SGiuseppe CAVALLARO 
1647e7434821SGiuseppe CAVALLARO 	return 0;
1648e7434821SGiuseppe CAVALLARO }
1649e7434821SGiuseppe CAVALLARO 
1650e7434821SGiuseppe CAVALLARO static int stmmac_sysfs_dma_cap_open(struct inode *inode, struct file *file)
1651e7434821SGiuseppe CAVALLARO {
1652e7434821SGiuseppe CAVALLARO 	return single_open(file, stmmac_sysfs_dma_cap_read, inode->i_private);
1653e7434821SGiuseppe CAVALLARO }
1654e7434821SGiuseppe CAVALLARO 
1655e7434821SGiuseppe CAVALLARO static const struct file_operations stmmac_dma_cap_fops = {
1656e7434821SGiuseppe CAVALLARO 	.owner = THIS_MODULE,
1657e7434821SGiuseppe CAVALLARO 	.open = stmmac_sysfs_dma_cap_open,
1658e7434821SGiuseppe CAVALLARO 	.read = seq_read,
1659e7434821SGiuseppe CAVALLARO 	.llseek = seq_lseek,
1660e7434821SGiuseppe CAVALLARO 	.release = seq_release,
1661e7434821SGiuseppe CAVALLARO };
1662e7434821SGiuseppe CAVALLARO 
16637ac29055SGiuseppe CAVALLARO static int stmmac_init_fs(struct net_device *dev)
16647ac29055SGiuseppe CAVALLARO {
16657ac29055SGiuseppe CAVALLARO 	/* Create debugfs entries */
16667ac29055SGiuseppe CAVALLARO 	stmmac_fs_dir = debugfs_create_dir(STMMAC_RESOURCE_NAME, NULL);
16677ac29055SGiuseppe CAVALLARO 
16687ac29055SGiuseppe CAVALLARO 	if (!stmmac_fs_dir || IS_ERR(stmmac_fs_dir)) {
16697ac29055SGiuseppe CAVALLARO 		pr_err("ERROR %s, debugfs create directory failed\n",
16707ac29055SGiuseppe CAVALLARO 		       STMMAC_RESOURCE_NAME);
16717ac29055SGiuseppe CAVALLARO 
16727ac29055SGiuseppe CAVALLARO 		return -ENOMEM;
16737ac29055SGiuseppe CAVALLARO 	}
16747ac29055SGiuseppe CAVALLARO 
16757ac29055SGiuseppe CAVALLARO 	/* Entry to report DMA RX/TX rings */
16767ac29055SGiuseppe CAVALLARO 	stmmac_rings_status = debugfs_create_file("descriptors_status",
16777ac29055SGiuseppe CAVALLARO 					   S_IRUGO, stmmac_fs_dir, dev,
16787ac29055SGiuseppe CAVALLARO 					   &stmmac_rings_status_fops);
16797ac29055SGiuseppe CAVALLARO 
16807ac29055SGiuseppe CAVALLARO 	if (!stmmac_rings_status || IS_ERR(stmmac_rings_status)) {
16817ac29055SGiuseppe CAVALLARO 		pr_info("ERROR creating stmmac ring debugfs file\n");
16827ac29055SGiuseppe CAVALLARO 		debugfs_remove(stmmac_fs_dir);
16837ac29055SGiuseppe CAVALLARO 
16847ac29055SGiuseppe CAVALLARO 		return -ENOMEM;
16857ac29055SGiuseppe CAVALLARO 	}
16867ac29055SGiuseppe CAVALLARO 
1687e7434821SGiuseppe CAVALLARO 	/* Entry to report the DMA HW features */
1688e7434821SGiuseppe CAVALLARO 	stmmac_dma_cap = debugfs_create_file("dma_cap", S_IRUGO, stmmac_fs_dir,
1689e7434821SGiuseppe CAVALLARO 					     dev, &stmmac_dma_cap_fops);
1690e7434821SGiuseppe CAVALLARO 
1691e7434821SGiuseppe CAVALLARO 	if (!stmmac_dma_cap || IS_ERR(stmmac_dma_cap)) {
1692e7434821SGiuseppe CAVALLARO 		pr_info("ERROR creating stmmac MMC debugfs file\n");
1693e7434821SGiuseppe CAVALLARO 		debugfs_remove(stmmac_rings_status);
1694e7434821SGiuseppe CAVALLARO 		debugfs_remove(stmmac_fs_dir);
1695e7434821SGiuseppe CAVALLARO 
1696e7434821SGiuseppe CAVALLARO 		return -ENOMEM;
1697e7434821SGiuseppe CAVALLARO 	}
1698e7434821SGiuseppe CAVALLARO 
16997ac29055SGiuseppe CAVALLARO 	return 0;
17007ac29055SGiuseppe CAVALLARO }
17017ac29055SGiuseppe CAVALLARO 
17027ac29055SGiuseppe CAVALLARO static void stmmac_exit_fs(void)
17037ac29055SGiuseppe CAVALLARO {
17047ac29055SGiuseppe CAVALLARO 	debugfs_remove(stmmac_rings_status);
1705e7434821SGiuseppe CAVALLARO 	debugfs_remove(stmmac_dma_cap);
17067ac29055SGiuseppe CAVALLARO 	debugfs_remove(stmmac_fs_dir);
17077ac29055SGiuseppe CAVALLARO }
17087ac29055SGiuseppe CAVALLARO #endif /* CONFIG_STMMAC_DEBUG_FS */
17097ac29055SGiuseppe CAVALLARO 
17107ac6653aSJeff Kirsher static const struct net_device_ops stmmac_netdev_ops = {
17117ac6653aSJeff Kirsher 	.ndo_open = stmmac_open,
17127ac6653aSJeff Kirsher 	.ndo_start_xmit = stmmac_xmit,
17137ac6653aSJeff Kirsher 	.ndo_stop = stmmac_release,
17147ac6653aSJeff Kirsher 	.ndo_change_mtu = stmmac_change_mtu,
17157ac6653aSJeff Kirsher 	.ndo_fix_features = stmmac_fix_features,
171601789349SJiri Pirko 	.ndo_set_rx_mode = stmmac_set_rx_mode,
17177ac6653aSJeff Kirsher 	.ndo_tx_timeout = stmmac_tx_timeout,
17187ac6653aSJeff Kirsher 	.ndo_do_ioctl = stmmac_ioctl,
17197ac6653aSJeff Kirsher 	.ndo_set_config = stmmac_config,
17207ac6653aSJeff Kirsher #ifdef CONFIG_NET_POLL_CONTROLLER
17217ac6653aSJeff Kirsher 	.ndo_poll_controller = stmmac_poll_controller,
17227ac6653aSJeff Kirsher #endif
17237ac6653aSJeff Kirsher 	.ndo_set_mac_address = eth_mac_addr,
17247ac6653aSJeff Kirsher };
17257ac6653aSJeff Kirsher 
17267ac6653aSJeff Kirsher /**
1727cf3f047bSGiuseppe CAVALLARO  *  stmmac_hw_init - Init the MAC device
1728cf3f047bSGiuseppe CAVALLARO  *  @priv : pointer to the private device structure.
1729cf3f047bSGiuseppe CAVALLARO  *  Description: this function detects which MAC device
1730cf3f047bSGiuseppe CAVALLARO  *  (GMAC/MAC10-100) has to attached, checks the HW capability
1731cf3f047bSGiuseppe CAVALLARO  *  (if supported) and sets the driver's features (for example
1732cf3f047bSGiuseppe CAVALLARO  *  to use the ring or chaine mode or support the normal/enh
1733cf3f047bSGiuseppe CAVALLARO  *  descriptor structure).
1734cf3f047bSGiuseppe CAVALLARO  */
1735cf3f047bSGiuseppe CAVALLARO static int stmmac_hw_init(struct stmmac_priv *priv)
1736cf3f047bSGiuseppe CAVALLARO {
1737cf3f047bSGiuseppe CAVALLARO 	int ret = 0;
1738cf3f047bSGiuseppe CAVALLARO 	struct mac_device_info *mac;
1739cf3f047bSGiuseppe CAVALLARO 
1740cf3f047bSGiuseppe CAVALLARO 	/* Identify the MAC HW device */
1741cf3f047bSGiuseppe CAVALLARO 	if (priv->plat->has_gmac)
1742cf3f047bSGiuseppe CAVALLARO 		mac = dwmac1000_setup(priv->ioaddr);
1743cf3f047bSGiuseppe CAVALLARO 	else
1744cf3f047bSGiuseppe CAVALLARO 		mac = dwmac100_setup(priv->ioaddr);
1745cf3f047bSGiuseppe CAVALLARO 	if (!mac)
1746cf3f047bSGiuseppe CAVALLARO 		return -ENOMEM;
1747cf3f047bSGiuseppe CAVALLARO 
1748cf3f047bSGiuseppe CAVALLARO 	priv->hw = mac;
1749cf3f047bSGiuseppe CAVALLARO 
1750cf3f047bSGiuseppe CAVALLARO 	/* To use the chained or ring mode */
1751cf3f047bSGiuseppe CAVALLARO 	priv->hw->ring = &ring_mode_ops;
1752cf3f047bSGiuseppe CAVALLARO 
1753cf3f047bSGiuseppe CAVALLARO 	/* Get and dump the chip ID */
1754cf3f047bSGiuseppe CAVALLARO 	stmmac_get_synopsys_id(priv);
1755cf3f047bSGiuseppe CAVALLARO 
1756cf3f047bSGiuseppe CAVALLARO 	/* Get the HW capability (new GMAC newer than 3.50a) */
1757cf3f047bSGiuseppe CAVALLARO 	priv->hw_cap_support = stmmac_get_hw_features(priv);
1758cf3f047bSGiuseppe CAVALLARO 	if (priv->hw_cap_support) {
1759cf3f047bSGiuseppe CAVALLARO 		pr_info(" DMA HW capability register supported");
1760cf3f047bSGiuseppe CAVALLARO 
1761cf3f047bSGiuseppe CAVALLARO 		/* We can override some gmac/dma configuration fields: e.g.
1762cf3f047bSGiuseppe CAVALLARO 		 * enh_desc, tx_coe (e.g. that are passed through the
1763cf3f047bSGiuseppe CAVALLARO 		 * platform) with the values from the HW capability
1764cf3f047bSGiuseppe CAVALLARO 		 * register (if supported).
1765cf3f047bSGiuseppe CAVALLARO 		 */
1766cf3f047bSGiuseppe CAVALLARO 		priv->plat->enh_desc = priv->dma_cap.enh_desc;
1767cf3f047bSGiuseppe CAVALLARO 		priv->plat->tx_coe = priv->dma_cap.tx_coe;
1768cf3f047bSGiuseppe CAVALLARO 		priv->plat->pmt = priv->dma_cap.pmt_remote_wake_up;
1769cf3f047bSGiuseppe CAVALLARO 	} else
1770cf3f047bSGiuseppe CAVALLARO 		pr_info(" No HW DMA feature register supported");
1771cf3f047bSGiuseppe CAVALLARO 
1772cf3f047bSGiuseppe CAVALLARO 	/* Select the enhnaced/normal descriptor structures */
1773cf3f047bSGiuseppe CAVALLARO 	stmmac_selec_desc_mode(priv);
1774cf3f047bSGiuseppe CAVALLARO 
1775cf3f047bSGiuseppe CAVALLARO 	priv->rx_coe = priv->hw->mac->rx_coe(priv->ioaddr);
1776cf3f047bSGiuseppe CAVALLARO 	if (priv->rx_coe)
1777cf3f047bSGiuseppe CAVALLARO 		pr_info(" RX Checksum Offload Engine supported\n");
1778cf3f047bSGiuseppe CAVALLARO 	if (priv->plat->tx_coe)
1779cf3f047bSGiuseppe CAVALLARO 		pr_info(" TX Checksum insertion supported\n");
1780cf3f047bSGiuseppe CAVALLARO 
1781cf3f047bSGiuseppe CAVALLARO 	if (priv->plat->pmt) {
1782cf3f047bSGiuseppe CAVALLARO 		pr_info(" Wake-Up On Lan supported\n");
1783cf3f047bSGiuseppe CAVALLARO 		device_set_wakeup_capable(priv->device, 1);
1784cf3f047bSGiuseppe CAVALLARO 	}
1785cf3f047bSGiuseppe CAVALLARO 
1786cf3f047bSGiuseppe CAVALLARO 	return ret;
1787cf3f047bSGiuseppe CAVALLARO }
1788cf3f047bSGiuseppe CAVALLARO 
1789cf3f047bSGiuseppe CAVALLARO /**
1790bfab27a1SGiuseppe CAVALLARO  * stmmac_dvr_probe
1791bfab27a1SGiuseppe CAVALLARO  * @device: device pointer
1792bfab27a1SGiuseppe CAVALLARO  * Description: this is the main probe function used to
1793bfab27a1SGiuseppe CAVALLARO  * call the alloc_etherdev, allocate the priv structure.
17947ac6653aSJeff Kirsher  */
1795bfab27a1SGiuseppe CAVALLARO struct stmmac_priv *stmmac_dvr_probe(struct device *device,
1796cf3f047bSGiuseppe CAVALLARO 				     struct plat_stmmacenet_data *plat_dat,
1797cf3f047bSGiuseppe CAVALLARO 				     void __iomem *addr)
17987ac6653aSJeff Kirsher {
17997ac6653aSJeff Kirsher 	int ret = 0;
1800bfab27a1SGiuseppe CAVALLARO 	struct net_device *ndev = NULL;
1801bfab27a1SGiuseppe CAVALLARO 	struct stmmac_priv *priv;
18027ac6653aSJeff Kirsher 
1803bfab27a1SGiuseppe CAVALLARO 	ndev = alloc_etherdev(sizeof(struct stmmac_priv));
1804bfab27a1SGiuseppe CAVALLARO 	if (!ndev) {
1805bfab27a1SGiuseppe CAVALLARO 		pr_err("%s: ERROR: allocating the device\n", __func__);
1806bfab27a1SGiuseppe CAVALLARO 		return NULL;
1807bfab27a1SGiuseppe CAVALLARO 	}
18087ac6653aSJeff Kirsher 
1809bfab27a1SGiuseppe CAVALLARO 	SET_NETDEV_DEV(ndev, device);
18107ac6653aSJeff Kirsher 
1811bfab27a1SGiuseppe CAVALLARO 	priv = netdev_priv(ndev);
1812bfab27a1SGiuseppe CAVALLARO 	priv->device = device;
1813bfab27a1SGiuseppe CAVALLARO 	priv->dev = ndev;
1814bfab27a1SGiuseppe CAVALLARO 
1815bfab27a1SGiuseppe CAVALLARO 	ether_setup(ndev);
1816bfab27a1SGiuseppe CAVALLARO 
1817bfab27a1SGiuseppe CAVALLARO 	stmmac_set_ethtool_ops(ndev);
1818cf3f047bSGiuseppe CAVALLARO 	priv->pause = pause;
1819cf3f047bSGiuseppe CAVALLARO 	priv->plat = plat_dat;
1820cf3f047bSGiuseppe CAVALLARO 	priv->ioaddr = addr;
1821cf3f047bSGiuseppe CAVALLARO 	priv->dev->base_addr = (unsigned long)addr;
1822bfab27a1SGiuseppe CAVALLARO 
1823cf3f047bSGiuseppe CAVALLARO 	/* Verify driver arguments */
1824cf3f047bSGiuseppe CAVALLARO 	stmmac_verify_args();
1825cf3f047bSGiuseppe CAVALLARO 
1826cf3f047bSGiuseppe CAVALLARO 	/* Override with kernel parameters if supplied XXX CRS XXX
1827cf3f047bSGiuseppe CAVALLARO 	 * this needs to have multiple instances */
1828cf3f047bSGiuseppe CAVALLARO 	if ((phyaddr >= 0) && (phyaddr <= 31))
1829cf3f047bSGiuseppe CAVALLARO 		priv->plat->phy_addr = phyaddr;
1830cf3f047bSGiuseppe CAVALLARO 
1831cf3f047bSGiuseppe CAVALLARO 	/* Init MAC and get the capabilities */
1832cf3f047bSGiuseppe CAVALLARO 	stmmac_hw_init(priv);
1833cf3f047bSGiuseppe CAVALLARO 
1834cf3f047bSGiuseppe CAVALLARO 	ndev->netdev_ops = &stmmac_netdev_ops;
1835cf3f047bSGiuseppe CAVALLARO 
1836cf3f047bSGiuseppe CAVALLARO 	ndev->hw_features = NETIF_F_SG | NETIF_F_IP_CSUM | NETIF_F_IPV6_CSUM |
1837cf3f047bSGiuseppe CAVALLARO 			    NETIF_F_RXCSUM;
1838bfab27a1SGiuseppe CAVALLARO 	ndev->features |= ndev->hw_features | NETIF_F_HIGHDMA;
1839bfab27a1SGiuseppe CAVALLARO 	ndev->watchdog_timeo = msecs_to_jiffies(watchdog);
18407ac6653aSJeff Kirsher #ifdef STMMAC_VLAN_TAG_USED
18417ac6653aSJeff Kirsher 	/* Both mac100 and gmac support receive VLAN tag detection */
1842bfab27a1SGiuseppe CAVALLARO 	ndev->features |= NETIF_F_HW_VLAN_RX;
18437ac6653aSJeff Kirsher #endif
18447ac6653aSJeff Kirsher 	priv->msg_enable = netif_msg_init(debug, default_msg_level);
18457ac6653aSJeff Kirsher 
18467ac6653aSJeff Kirsher 	if (flow_ctrl)
18477ac6653aSJeff Kirsher 		priv->flow_ctrl = FLOW_AUTO;	/* RX/TX pause on */
18487ac6653aSJeff Kirsher 
1849bfab27a1SGiuseppe CAVALLARO 	netif_napi_add(ndev, &priv->napi, stmmac_poll, 64);
18507ac6653aSJeff Kirsher 
18517ac6653aSJeff Kirsher 	spin_lock_init(&priv->lock);
1852a9097a96SGiuseppe CAVALLARO 	spin_lock_init(&priv->tx_lock);
18537ac6653aSJeff Kirsher 
1854bfab27a1SGiuseppe CAVALLARO 	ret = register_netdev(ndev);
18557ac6653aSJeff Kirsher 	if (ret) {
1856cf3f047bSGiuseppe CAVALLARO 		pr_err("%s: ERROR %i registering the device\n", __func__, ret);
1857bfab27a1SGiuseppe CAVALLARO 		goto error;
18587ac6653aSJeff Kirsher 	}
18597ac6653aSJeff Kirsher 
1860bfab27a1SGiuseppe CAVALLARO 	return priv;
18617ac6653aSJeff Kirsher 
1862bfab27a1SGiuseppe CAVALLARO error:
1863bfab27a1SGiuseppe CAVALLARO 	netif_napi_del(&priv->napi);
18647ac6653aSJeff Kirsher 
18657ac6653aSJeff Kirsher 	unregister_netdev(ndev);
18667ac6653aSJeff Kirsher 	free_netdev(ndev);
18677ac6653aSJeff Kirsher 
1868bfab27a1SGiuseppe CAVALLARO 	return NULL;
18697ac6653aSJeff Kirsher }
18707ac6653aSJeff Kirsher 
18717ac6653aSJeff Kirsher /**
18727ac6653aSJeff Kirsher  * stmmac_dvr_remove
1873bfab27a1SGiuseppe CAVALLARO  * @ndev: net device pointer
18747ac6653aSJeff Kirsher  * Description: this function resets the TX/RX processes, disables the MAC RX/TX
1875bfab27a1SGiuseppe CAVALLARO  * changes the link status, releases the DMA descriptor rings.
18767ac6653aSJeff Kirsher  */
1877bfab27a1SGiuseppe CAVALLARO int stmmac_dvr_remove(struct net_device *ndev)
18787ac6653aSJeff Kirsher {
18797ac6653aSJeff Kirsher 	struct stmmac_priv *priv = netdev_priv(ndev);
18807ac6653aSJeff Kirsher 
18817ac6653aSJeff Kirsher 	pr_info("%s:\n\tremoving driver", __func__);
18827ac6653aSJeff Kirsher 
18837ac6653aSJeff Kirsher 	priv->hw->dma->stop_rx(priv->ioaddr);
18847ac6653aSJeff Kirsher 	priv->hw->dma->stop_tx(priv->ioaddr);
18857ac6653aSJeff Kirsher 
1886bfab27a1SGiuseppe CAVALLARO 	stmmac_set_mac(priv->ioaddr, false);
18877ac6653aSJeff Kirsher 	netif_carrier_off(ndev);
18887ac6653aSJeff Kirsher 	unregister_netdev(ndev);
18897ac6653aSJeff Kirsher 	free_netdev(ndev);
18907ac6653aSJeff Kirsher 
18917ac6653aSJeff Kirsher 	return 0;
18927ac6653aSJeff Kirsher }
18937ac6653aSJeff Kirsher 
18947ac6653aSJeff Kirsher #ifdef CONFIG_PM
1895bfab27a1SGiuseppe CAVALLARO int stmmac_suspend(struct net_device *ndev)
18967ac6653aSJeff Kirsher {
18977ac6653aSJeff Kirsher 	struct stmmac_priv *priv = netdev_priv(ndev);
18987ac6653aSJeff Kirsher 	int dis_ic = 0;
18997ac6653aSJeff Kirsher 
19007ac6653aSJeff Kirsher 	if (!ndev || !netif_running(ndev))
19017ac6653aSJeff Kirsher 		return 0;
19027ac6653aSJeff Kirsher 
1903102463b1SFrancesco Virlinzi 	if (priv->phydev)
1904102463b1SFrancesco Virlinzi 		phy_stop(priv->phydev);
1905102463b1SFrancesco Virlinzi 
19067ac6653aSJeff Kirsher 	spin_lock(&priv->lock);
19077ac6653aSJeff Kirsher 
19087ac6653aSJeff Kirsher 	netif_device_detach(ndev);
19097ac6653aSJeff Kirsher 	netif_stop_queue(ndev);
19107ac6653aSJeff Kirsher 
19117ac6653aSJeff Kirsher #ifdef CONFIG_STMMAC_TIMER
19127ac6653aSJeff Kirsher 	priv->tm->timer_stop();
19137ac6653aSJeff Kirsher 	if (likely(priv->tm->enable))
19147ac6653aSJeff Kirsher 		dis_ic = 1;
19157ac6653aSJeff Kirsher #endif
19167ac6653aSJeff Kirsher 	napi_disable(&priv->napi);
19177ac6653aSJeff Kirsher 
19187ac6653aSJeff Kirsher 	/* Stop TX/RX DMA */
19197ac6653aSJeff Kirsher 	priv->hw->dma->stop_tx(priv->ioaddr);
19207ac6653aSJeff Kirsher 	priv->hw->dma->stop_rx(priv->ioaddr);
19217ac6653aSJeff Kirsher 	/* Clear the Rx/Tx descriptors */
19227ac6653aSJeff Kirsher 	priv->hw->desc->init_rx_desc(priv->dma_rx, priv->dma_rx_size,
19237ac6653aSJeff Kirsher 				     dis_ic);
19247ac6653aSJeff Kirsher 	priv->hw->desc->init_tx_desc(priv->dma_tx, priv->dma_tx_size);
19257ac6653aSJeff Kirsher 
19267ac6653aSJeff Kirsher 	/* Enable Power down mode by programming the PMT regs */
19277ac6653aSJeff Kirsher 	if (device_may_wakeup(priv->device))
19287ac6653aSJeff Kirsher 		priv->hw->mac->pmt(priv->ioaddr, priv->wolopts);
19297ac6653aSJeff Kirsher 	else
1930bfab27a1SGiuseppe CAVALLARO 		stmmac_set_mac(priv->ioaddr, false);
19317ac6653aSJeff Kirsher 
19327ac6653aSJeff Kirsher 	spin_unlock(&priv->lock);
19337ac6653aSJeff Kirsher 	return 0;
19347ac6653aSJeff Kirsher }
19357ac6653aSJeff Kirsher 
1936bfab27a1SGiuseppe CAVALLARO int stmmac_resume(struct net_device *ndev)
19377ac6653aSJeff Kirsher {
19387ac6653aSJeff Kirsher 	struct stmmac_priv *priv = netdev_priv(ndev);
19397ac6653aSJeff Kirsher 
19407ac6653aSJeff Kirsher 	if (!netif_running(ndev))
19417ac6653aSJeff Kirsher 		return 0;
19427ac6653aSJeff Kirsher 
19437ac6653aSJeff Kirsher 	spin_lock(&priv->lock);
19447ac6653aSJeff Kirsher 
19457ac6653aSJeff Kirsher 	/* Power Down bit, into the PM register, is cleared
19467ac6653aSJeff Kirsher 	 * automatically as soon as a magic packet or a Wake-up frame
19477ac6653aSJeff Kirsher 	 * is received. Anyway, it's better to manually clear
19487ac6653aSJeff Kirsher 	 * this bit because it can generate problems while resuming
19497ac6653aSJeff Kirsher 	 * from another devices (e.g. serial console). */
19507ac6653aSJeff Kirsher 	if (device_may_wakeup(priv->device))
19517ac6653aSJeff Kirsher 		priv->hw->mac->pmt(priv->ioaddr, 0);
19527ac6653aSJeff Kirsher 
19537ac6653aSJeff Kirsher 	netif_device_attach(ndev);
19547ac6653aSJeff Kirsher 
19557ac6653aSJeff Kirsher 	/* Enable the MAC and DMA */
1956bfab27a1SGiuseppe CAVALLARO 	stmmac_set_mac(priv->ioaddr, true);
19577ac6653aSJeff Kirsher 	priv->hw->dma->start_tx(priv->ioaddr);
19587ac6653aSJeff Kirsher 	priv->hw->dma->start_rx(priv->ioaddr);
19597ac6653aSJeff Kirsher 
19607ac6653aSJeff Kirsher #ifdef CONFIG_STMMAC_TIMER
19617ac6653aSJeff Kirsher 	if (likely(priv->tm->enable))
19627ac6653aSJeff Kirsher 		priv->tm->timer_start(tmrate);
19637ac6653aSJeff Kirsher #endif
19647ac6653aSJeff Kirsher 	napi_enable(&priv->napi);
19657ac6653aSJeff Kirsher 
19667ac6653aSJeff Kirsher 	netif_start_queue(ndev);
19677ac6653aSJeff Kirsher 
19687ac6653aSJeff Kirsher 	spin_unlock(&priv->lock);
1969102463b1SFrancesco Virlinzi 
1970102463b1SFrancesco Virlinzi 	if (priv->phydev)
1971102463b1SFrancesco Virlinzi 		phy_start(priv->phydev);
1972102463b1SFrancesco Virlinzi 
19737ac6653aSJeff Kirsher 	return 0;
19747ac6653aSJeff Kirsher }
19757ac6653aSJeff Kirsher 
1976bfab27a1SGiuseppe CAVALLARO int stmmac_freeze(struct net_device *ndev)
19777ac6653aSJeff Kirsher {
19787ac6653aSJeff Kirsher 	if (!ndev || !netif_running(ndev))
19797ac6653aSJeff Kirsher 		return 0;
19807ac6653aSJeff Kirsher 
19817ac6653aSJeff Kirsher 	return stmmac_release(ndev);
19827ac6653aSJeff Kirsher }
19837ac6653aSJeff Kirsher 
1984bfab27a1SGiuseppe CAVALLARO int stmmac_restore(struct net_device *ndev)
19857ac6653aSJeff Kirsher {
19867ac6653aSJeff Kirsher 	if (!ndev || !netif_running(ndev))
19877ac6653aSJeff Kirsher 		return 0;
19887ac6653aSJeff Kirsher 
19897ac6653aSJeff Kirsher 	return stmmac_open(ndev);
19907ac6653aSJeff Kirsher }
19917ac6653aSJeff Kirsher #endif /* CONFIG_PM */
19927ac6653aSJeff Kirsher 
19937ac6653aSJeff Kirsher #ifndef MODULE
19947ac6653aSJeff Kirsher static int __init stmmac_cmdline_opt(char *str)
19957ac6653aSJeff Kirsher {
19967ac6653aSJeff Kirsher 	char *opt;
19977ac6653aSJeff Kirsher 
19987ac6653aSJeff Kirsher 	if (!str || !*str)
19997ac6653aSJeff Kirsher 		return -EINVAL;
20007ac6653aSJeff Kirsher 	while ((opt = strsep(&str, ",")) != NULL) {
20017ac6653aSJeff Kirsher 		if (!strncmp(opt, "debug:", 6)) {
20027ac6653aSJeff Kirsher 			if (strict_strtoul(opt + 6, 0, (unsigned long *)&debug))
20037ac6653aSJeff Kirsher 				goto err;
20047ac6653aSJeff Kirsher 		} else if (!strncmp(opt, "phyaddr:", 8)) {
20057ac6653aSJeff Kirsher 			if (strict_strtoul(opt + 8, 0,
20067ac6653aSJeff Kirsher 					   (unsigned long *)&phyaddr))
20077ac6653aSJeff Kirsher 				goto err;
20087ac6653aSJeff Kirsher 		} else if (!strncmp(opt, "dma_txsize:", 11)) {
20097ac6653aSJeff Kirsher 			if (strict_strtoul(opt + 11, 0,
20107ac6653aSJeff Kirsher 					   (unsigned long *)&dma_txsize))
20117ac6653aSJeff Kirsher 				goto err;
20127ac6653aSJeff Kirsher 		} else if (!strncmp(opt, "dma_rxsize:", 11)) {
20137ac6653aSJeff Kirsher 			if (strict_strtoul(opt + 11, 0,
20147ac6653aSJeff Kirsher 					   (unsigned long *)&dma_rxsize))
20157ac6653aSJeff Kirsher 				goto err;
20167ac6653aSJeff Kirsher 		} else if (!strncmp(opt, "buf_sz:", 7)) {
20177ac6653aSJeff Kirsher 			if (strict_strtoul(opt + 7, 0,
20187ac6653aSJeff Kirsher 					   (unsigned long *)&buf_sz))
20197ac6653aSJeff Kirsher 				goto err;
20207ac6653aSJeff Kirsher 		} else if (!strncmp(opt, "tc:", 3)) {
20217ac6653aSJeff Kirsher 			if (strict_strtoul(opt + 3, 0, (unsigned long *)&tc))
20227ac6653aSJeff Kirsher 				goto err;
20237ac6653aSJeff Kirsher 		} else if (!strncmp(opt, "watchdog:", 9)) {
20247ac6653aSJeff Kirsher 			if (strict_strtoul(opt + 9, 0,
20257ac6653aSJeff Kirsher 					   (unsigned long *)&watchdog))
20267ac6653aSJeff Kirsher 				goto err;
20277ac6653aSJeff Kirsher 		} else if (!strncmp(opt, "flow_ctrl:", 10)) {
20287ac6653aSJeff Kirsher 			if (strict_strtoul(opt + 10, 0,
20297ac6653aSJeff Kirsher 					   (unsigned long *)&flow_ctrl))
20307ac6653aSJeff Kirsher 				goto err;
20317ac6653aSJeff Kirsher 		} else if (!strncmp(opt, "pause:", 6)) {
20327ac6653aSJeff Kirsher 			if (strict_strtoul(opt + 6, 0, (unsigned long *)&pause))
20337ac6653aSJeff Kirsher 				goto err;
20347ac6653aSJeff Kirsher #ifdef CONFIG_STMMAC_TIMER
20357ac6653aSJeff Kirsher 		} else if (!strncmp(opt, "tmrate:", 7)) {
20367ac6653aSJeff Kirsher 			if (strict_strtoul(opt + 7, 0,
20377ac6653aSJeff Kirsher 					   (unsigned long *)&tmrate))
20387ac6653aSJeff Kirsher 				goto err;
20397ac6653aSJeff Kirsher #endif
20407ac6653aSJeff Kirsher 		}
20417ac6653aSJeff Kirsher 	}
20427ac6653aSJeff Kirsher 	return 0;
20437ac6653aSJeff Kirsher 
20447ac6653aSJeff Kirsher err:
20457ac6653aSJeff Kirsher 	pr_err("%s: ERROR broken module parameter conversion", __func__);
20467ac6653aSJeff Kirsher 	return -EINVAL;
20477ac6653aSJeff Kirsher }
20487ac6653aSJeff Kirsher 
20497ac6653aSJeff Kirsher __setup("stmmaceth=", stmmac_cmdline_opt);
20507ac6653aSJeff Kirsher #endif
20516fc0d0f2SGiuseppe Cavallaro 
20526fc0d0f2SGiuseppe Cavallaro MODULE_DESCRIPTION("STMMAC 10/100/1000 Ethernet device driver");
20536fc0d0f2SGiuseppe Cavallaro MODULE_AUTHOR("Giuseppe Cavallaro <peppe.cavallaro@st.com>");
20546fc0d0f2SGiuseppe Cavallaro MODULE_LICENSE("GPL");
2055