diff options
Diffstat (limited to 'drivers/net/stmmac/stmmac_main.c')
-rw-r--r-- | drivers/net/stmmac/stmmac_main.c | 268 |
1 files changed, 37 insertions, 231 deletions
diff --git a/drivers/net/stmmac/stmmac_main.c b/drivers/net/stmmac/stmmac_main.c index 86e910300969..e6c5a3cf4af2 100644 --- a/drivers/net/stmmac/stmmac_main.c +++ b/drivers/net/stmmac/stmmac_main.c | |||
@@ -572,50 +572,6 @@ static void free_dma_desc_resources(struct stmmac_priv *priv) | |||
572 | } | 572 | } |
573 | 573 | ||
574 | /** | 574 | /** |
575 | * stmmac_dma_start_tx | ||
576 | * @ioaddr: device I/O address | ||
577 | * Description: this function starts the DMA tx process. | ||
578 | */ | ||
579 | static void stmmac_dma_start_tx(unsigned long ioaddr) | ||
580 | { | ||
581 | u32 value = readl(ioaddr + DMA_CONTROL); | ||
582 | value |= DMA_CONTROL_ST; | ||
583 | writel(value, ioaddr + DMA_CONTROL); | ||
584 | return; | ||
585 | } | ||
586 | |||
587 | static void stmmac_dma_stop_tx(unsigned long ioaddr) | ||
588 | { | ||
589 | u32 value = readl(ioaddr + DMA_CONTROL); | ||
590 | value &= ~DMA_CONTROL_ST; | ||
591 | writel(value, ioaddr + DMA_CONTROL); | ||
592 | return; | ||
593 | } | ||
594 | |||
595 | /** | ||
596 | * stmmac_dma_start_rx | ||
597 | * @ioaddr: device I/O address | ||
598 | * Description: this function starts the DMA rx process. | ||
599 | */ | ||
600 | static void stmmac_dma_start_rx(unsigned long ioaddr) | ||
601 | { | ||
602 | u32 value = readl(ioaddr + DMA_CONTROL); | ||
603 | value |= DMA_CONTROL_SR; | ||
604 | writel(value, ioaddr + DMA_CONTROL); | ||
605 | |||
606 | return; | ||
607 | } | ||
608 | |||
609 | static void stmmac_dma_stop_rx(unsigned long ioaddr) | ||
610 | { | ||
611 | u32 value = readl(ioaddr + DMA_CONTROL); | ||
612 | value &= ~DMA_CONTROL_SR; | ||
613 | writel(value, ioaddr + DMA_CONTROL); | ||
614 | |||
615 | return; | ||
616 | } | ||
617 | |||
618 | /** | ||
619 | * stmmac_dma_operation_mode - HW DMA operation mode | 575 | * stmmac_dma_operation_mode - HW DMA operation mode |
620 | * @priv : pointer to the private device structure. | 576 | * @priv : pointer to the private device structure. |
621 | * Description: it sets the DMA operation mode: tx/rx DMA thresholds | 577 | * Description: it sets the DMA operation mode: tx/rx DMA thresholds |
@@ -646,88 +602,6 @@ static void stmmac_dma_operation_mode(struct stmmac_priv *priv) | |||
646 | return; | 602 | return; |
647 | } | 603 | } |
648 | 604 | ||
649 | #ifdef STMMAC_DEBUG | ||
650 | /** | ||
651 | * show_tx_process_state | ||
652 | * @status: tx descriptor status field | ||
653 | * Description: it shows the Transmit Process State for CSR5[22:20] | ||
654 | */ | ||
655 | static void show_tx_process_state(unsigned int status) | ||
656 | { | ||
657 | unsigned int state; | ||
658 | state = (status & DMA_STATUS_TS_MASK) >> DMA_STATUS_TS_SHIFT; | ||
659 | |||
660 | switch (state) { | ||
661 | case 0: | ||
662 | pr_info("- TX (Stopped): Reset or Stop command\n"); | ||
663 | break; | ||
664 | case 1: | ||
665 | pr_info("- TX (Running):Fetching the Tx desc\n"); | ||
666 | break; | ||
667 | case 2: | ||
668 | pr_info("- TX (Running): Waiting for end of tx\n"); | ||
669 | break; | ||
670 | case 3: | ||
671 | pr_info("- TX (Running): Reading the data " | ||
672 | "and queuing the data into the Tx buf\n"); | ||
673 | break; | ||
674 | case 6: | ||
675 | pr_info("- TX (Suspended): Tx Buff Underflow " | ||
676 | "or an unavailable Transmit descriptor\n"); | ||
677 | break; | ||
678 | case 7: | ||
679 | pr_info("- TX (Running): Closing Tx descriptor\n"); | ||
680 | break; | ||
681 | default: | ||
682 | break; | ||
683 | } | ||
684 | return; | ||
685 | } | ||
686 | |||
687 | /** | ||
688 | * show_rx_process_state | ||
689 | * @status: rx descriptor status field | ||
690 | * Description: it shows the Receive Process State for CSR5[19:17] | ||
691 | */ | ||
692 | static void show_rx_process_state(unsigned int status) | ||
693 | { | ||
694 | unsigned int state; | ||
695 | state = (status & DMA_STATUS_RS_MASK) >> DMA_STATUS_RS_SHIFT; | ||
696 | |||
697 | switch (state) { | ||
698 | case 0: | ||
699 | pr_info("- RX (Stopped): Reset or Stop command\n"); | ||
700 | break; | ||
701 | case 1: | ||
702 | pr_info("- RX (Running): Fetching the Rx desc\n"); | ||
703 | break; | ||
704 | case 2: | ||
705 | pr_info("- RX (Running):Checking for end of pkt\n"); | ||
706 | break; | ||
707 | case 3: | ||
708 | pr_info("- RX (Running): Waiting for Rx pkt\n"); | ||
709 | break; | ||
710 | case 4: | ||
711 | pr_info("- RX (Suspended): Unavailable Rx buf\n"); | ||
712 | break; | ||
713 | case 5: | ||
714 | pr_info("- RX (Running): Closing Rx descriptor\n"); | ||
715 | break; | ||
716 | case 6: | ||
717 | pr_info("- RX(Running): Flushing the current frame" | ||
718 | " from the Rx buf\n"); | ||
719 | break; | ||
720 | case 7: | ||
721 | pr_info("- RX (Running): Queuing the Rx frame" | ||
722 | " from the Rx buf into memory\n"); | ||
723 | break; | ||
724 | default: | ||
725 | break; | ||
726 | } | ||
727 | return; | ||
728 | } | ||
729 | #endif | ||
730 | |||
731 | /** | 605 | /** |
732 | * stmmac_tx: | 606 | * stmmac_tx: |
733 | * @priv: private driver structure | 607 | * @priv: private driver structure |
@@ -811,7 +685,7 @@ static inline void stmmac_enable_irq(struct stmmac_priv *priv) | |||
811 | priv->tm->timer_start(tmrate); | 685 | priv->tm->timer_start(tmrate); |
812 | else | 686 | else |
813 | #endif | 687 | #endif |
814 | writel(DMA_INTR_DEFAULT_MASK, priv->dev->base_addr + DMA_INTR_ENA); | 688 | priv->hw->dma->enable_dma_irq(priv->dev->base_addr); |
815 | } | 689 | } |
816 | 690 | ||
817 | static inline void stmmac_disable_irq(struct stmmac_priv *priv) | 691 | static inline void stmmac_disable_irq(struct stmmac_priv *priv) |
@@ -821,7 +695,7 @@ static inline void stmmac_disable_irq(struct stmmac_priv *priv) | |||
821 | priv->tm->timer_stop(); | 695 | priv->tm->timer_stop(); |
822 | else | 696 | else |
823 | #endif | 697 | #endif |
824 | writel(0, priv->dev->base_addr + DMA_INTR_ENA); | 698 | priv->hw->dma->disable_dma_irq(priv->dev->base_addr); |
825 | } | 699 | } |
826 | 700 | ||
827 | static int stmmac_has_work(struct stmmac_priv *priv) | 701 | static int stmmac_has_work(struct stmmac_priv *priv) |
@@ -880,12 +754,12 @@ static void stmmac_tx_err(struct stmmac_priv *priv) | |||
880 | { | 754 | { |
881 | netif_stop_queue(priv->dev); | 755 | netif_stop_queue(priv->dev); |
882 | 756 | ||
883 | stmmac_dma_stop_tx(priv->dev->base_addr); | 757 | priv->hw->dma->stop_tx(priv->dev->base_addr); |
884 | dma_free_tx_skbufs(priv); | 758 | dma_free_tx_skbufs(priv); |
885 | priv->hw->desc->init_tx_desc(priv->dma_tx, priv->dma_tx_size); | 759 | priv->hw->desc->init_tx_desc(priv->dma_tx, priv->dma_tx_size); |
886 | priv->dirty_tx = 0; | 760 | priv->dirty_tx = 0; |
887 | priv->cur_tx = 0; | 761 | priv->cur_tx = 0; |
888 | stmmac_dma_start_tx(priv->dev->base_addr); | 762 | priv->hw->dma->start_tx(priv->dev->base_addr); |
889 | 763 | ||
890 | priv->dev->stats.tx_errors++; | 764 | priv->dev->stats.tx_errors++; |
891 | netif_wake_queue(priv->dev); | 765 | netif_wake_queue(priv->dev); |
@@ -893,95 +767,27 @@ static void stmmac_tx_err(struct stmmac_priv *priv) | |||
893 | return; | 767 | return; |
894 | } | 768 | } |
895 | 769 | ||
896 | /** | ||
897 | * stmmac_dma_interrupt - Interrupt handler for the driver | ||
898 | * @dev: net device structure | ||
899 | * Description: Interrupt handler for the driver (DMA). | ||
900 | */ | ||
901 | static void stmmac_dma_interrupt(struct net_device *dev) | ||
902 | { | ||
903 | unsigned long ioaddr = dev->base_addr; | ||
904 | struct stmmac_priv *priv = netdev_priv(dev); | ||
905 | /* read the status register (CSR5) */ | ||
906 | u32 intr_status = readl(ioaddr + DMA_STATUS); | ||
907 | |||
908 | DBG(intr, INFO, "%s: [CSR5: 0x%08x]\n", __func__, intr_status); | ||
909 | 770 | ||
910 | #ifdef STMMAC_DEBUG | 771 | static void stmmac_dma_interrupt(struct stmmac_priv *priv) |
911 | /* It displays the DMA transmit process state (CSR5 register) */ | 772 | { |
912 | if (netif_msg_tx_done(priv)) | 773 | unsigned long ioaddr = priv->dev->base_addr; |
913 | show_tx_process_state(intr_status); | 774 | int status; |
914 | if (netif_msg_rx_status(priv)) | 775 | |
915 | show_rx_process_state(intr_status); | 776 | status = priv->hw->dma->dma_interrupt(priv->dev->base_addr, |
916 | #endif | 777 | &priv->xstats); |
917 | /* ABNORMAL interrupts */ | 778 | if (likely(status == handle_tx_rx)) |
918 | if (unlikely(intr_status & DMA_STATUS_AIS)) { | 779 | _stmmac_schedule(priv); |
919 | DBG(intr, INFO, "CSR5[15] DMA ABNORMAL IRQ: "); | 780 | |
920 | if (unlikely(intr_status & DMA_STATUS_UNF)) { | 781 | else if (unlikely(status == tx_hard_error_bump_tc)) { |
921 | DBG(intr, INFO, "transmit underflow\n"); | 782 | /* Try to bump up the dma threshold on this failure */ |
922 | if (unlikely(tc != SF_DMA_MODE) && (tc <= 256)) { | 783 | if (unlikely(tc != SF_DMA_MODE) && (tc <= 256)) { |
923 | /* Try to bump up the threshold */ | 784 | tc += 64; |
924 | tc += 64; | 785 | priv->hw->dma->dma_mode(ioaddr, tc, SF_DMA_MODE); |
925 | priv->hw->dma->dma_mode(ioaddr, tc, | 786 | priv->xstats.threshold = tc; |
926 | SF_DMA_MODE); | ||
927 | priv->xstats.threshold = tc; | ||
928 | } | ||
929 | stmmac_tx_err(priv); | ||
930 | priv->xstats.tx_undeflow_irq++; | ||
931 | } | ||
932 | if (unlikely(intr_status & DMA_STATUS_TJT)) { | ||
933 | DBG(intr, INFO, "transmit jabber\n"); | ||
934 | priv->xstats.tx_jabber_irq++; | ||
935 | } | ||
936 | if (unlikely(intr_status & DMA_STATUS_OVF)) { | ||
937 | DBG(intr, INFO, "recv overflow\n"); | ||
938 | priv->xstats.rx_overflow_irq++; | ||
939 | } | ||
940 | if (unlikely(intr_status & DMA_STATUS_RU)) { | ||
941 | DBG(intr, INFO, "receive buffer unavailable\n"); | ||
942 | priv->xstats.rx_buf_unav_irq++; | ||
943 | } | ||
944 | if (unlikely(intr_status & DMA_STATUS_RPS)) { | ||
945 | DBG(intr, INFO, "receive process stopped\n"); | ||
946 | priv->xstats.rx_process_stopped_irq++; | ||
947 | } | ||
948 | if (unlikely(intr_status & DMA_STATUS_RWT)) { | ||
949 | DBG(intr, INFO, "receive watchdog\n"); | ||
950 | priv->xstats.rx_watchdog_irq++; | ||
951 | } | ||
952 | if (unlikely(intr_status & DMA_STATUS_ETI)) { | ||
953 | DBG(intr, INFO, "transmit early interrupt\n"); | ||
954 | priv->xstats.tx_early_irq++; | ||
955 | } | ||
956 | if (unlikely(intr_status & DMA_STATUS_TPS)) { | ||
957 | DBG(intr, INFO, "transmit process stopped\n"); | ||
958 | priv->xstats.tx_process_stopped_irq++; | ||
959 | stmmac_tx_err(priv); | ||
960 | } | ||
961 | if (unlikely(intr_status & DMA_STATUS_FBI)) { | ||
962 | DBG(intr, INFO, "fatal bus error\n"); | ||
963 | priv->xstats.fatal_bus_error_irq++; | ||
964 | stmmac_tx_err(priv); | ||
965 | } | 787 | } |
966 | } | 788 | stmmac_tx_err(priv); |
967 | 789 | } else if (unlikely(status == tx_hard_error)) | |
968 | /* TX/RX NORMAL interrupts */ | 790 | stmmac_tx_err(priv); |
969 | if (intr_status & DMA_STATUS_NIS) { | ||
970 | priv->xstats.normal_irq_n++; | ||
971 | if (likely((intr_status & DMA_STATUS_RI) || | ||
972 | (intr_status & (DMA_STATUS_TI)))) | ||
973 | _stmmac_schedule(priv); | ||
974 | } | ||
975 | |||
976 | /* Optional hardware blocks, interrupts should be disabled */ | ||
977 | if (unlikely(intr_status & | ||
978 | (DMA_STATUS_GPI | DMA_STATUS_GMI | DMA_STATUS_GLI))) | ||
979 | pr_info("%s: unexpected status %08x\n", __func__, intr_status); | ||
980 | |||
981 | /* Clear the interrupt by writing a logic 1 to the CSR5[15-0] */ | ||
982 | writel((intr_status & 0x1ffff), ioaddr + DMA_STATUS); | ||
983 | |||
984 | DBG(intr, INFO, "\n\n"); | ||
985 | 791 | ||
986 | return; | 792 | return; |
987 | } | 793 | } |
@@ -1089,8 +895,8 @@ static int stmmac_open(struct net_device *dev) | |||
1089 | 895 | ||
1090 | /* Start the ball rolling... */ | 896 | /* Start the ball rolling... */ |
1091 | DBG(probe, DEBUG, "%s: DMA RX/TX processes started...\n", dev->name); | 897 | DBG(probe, DEBUG, "%s: DMA RX/TX processes started...\n", dev->name); |
1092 | stmmac_dma_start_tx(ioaddr); | 898 | priv->hw->dma->start_tx(ioaddr); |
1093 | stmmac_dma_start_rx(ioaddr); | 899 | priv->hw->dma->start_rx(ioaddr); |
1094 | 900 | ||
1095 | #ifdef CONFIG_STMMAC_TIMER | 901 | #ifdef CONFIG_STMMAC_TIMER |
1096 | priv->tm->timer_start(tmrate); | 902 | priv->tm->timer_start(tmrate); |
@@ -1142,8 +948,8 @@ static int stmmac_release(struct net_device *dev) | |||
1142 | free_irq(dev->irq, dev); | 948 | free_irq(dev->irq, dev); |
1143 | 949 | ||
1144 | /* Stop TX/RX DMA and clear the descriptors */ | 950 | /* Stop TX/RX DMA and clear the descriptors */ |
1145 | stmmac_dma_stop_tx(dev->base_addr); | 951 | priv->hw->dma->stop_tx(dev->base_addr); |
1146 | stmmac_dma_stop_rx(dev->base_addr); | 952 | priv->hw->dma->stop_rx(dev->base_addr); |
1147 | 953 | ||
1148 | /* Release and free the Rx/Tx resources */ | 954 | /* Release and free the Rx/Tx resources */ |
1149 | free_dma_desc_resources(priv); | 955 | free_dma_desc_resources(priv); |
@@ -1227,7 +1033,6 @@ static unsigned int stmmac_handle_jumbo_frames(struct sk_buff *skb, | |||
1227 | priv->hw->desc->prepare_tx_desc(desc, 0, buf2_size, | 1033 | priv->hw->desc->prepare_tx_desc(desc, 0, buf2_size, |
1228 | csum_insertion); | 1034 | csum_insertion); |
1229 | priv->hw->desc->set_tx_owner(desc); | 1035 | priv->hw->desc->set_tx_owner(desc); |
1230 | |||
1231 | priv->tx_skbuff[entry] = NULL; | 1036 | priv->tx_skbuff[entry] = NULL; |
1232 | } else { | 1037 | } else { |
1233 | desc->des2 = dma_map_single(priv->device, skb->data, | 1038 | desc->des2 = dma_map_single(priv->device, skb->data, |
@@ -1353,8 +1158,7 @@ static netdev_tx_t stmmac_xmit(struct sk_buff *skb, struct net_device *dev) | |||
1353 | 1158 | ||
1354 | dev->stats.tx_bytes += skb->len; | 1159 | dev->stats.tx_bytes += skb->len; |
1355 | 1160 | ||
1356 | /* CSR1 enables the transmit DMA to check for new descriptor */ | 1161 | priv->hw->dma->enable_dma_transmission(dev->base_addr); |
1357 | writel(1, dev->base_addr + DMA_XMT_POLL_DEMAND); | ||
1358 | 1162 | ||
1359 | return NETDEV_TX_OK; | 1163 | return NETDEV_TX_OK; |
1360 | } | 1164 | } |
@@ -1624,7 +1428,8 @@ static irqreturn_t stmmac_interrupt(int irq, void *dev_id) | |||
1624 | /* To handle GMAC own interrupts */ | 1428 | /* To handle GMAC own interrupts */ |
1625 | priv->hw->mac->host_irq_status(ioaddr); | 1429 | priv->hw->mac->host_irq_status(ioaddr); |
1626 | } | 1430 | } |
1627 | stmmac_dma_interrupt(dev); | 1431 | |
1432 | stmmac_dma_interrupt(priv); | ||
1628 | 1433 | ||
1629 | return IRQ_HANDLED; | 1434 | return IRQ_HANDLED; |
1630 | } | 1435 | } |
@@ -1988,12 +1793,13 @@ out: | |||
1988 | static int stmmac_dvr_remove(struct platform_device *pdev) | 1793 | static int stmmac_dvr_remove(struct platform_device *pdev) |
1989 | { | 1794 | { |
1990 | struct net_device *ndev = platform_get_drvdata(pdev); | 1795 | struct net_device *ndev = platform_get_drvdata(pdev); |
1796 | struct stmmac_priv *priv = netdev_priv(ndev); | ||
1991 | struct resource *res; | 1797 | struct resource *res; |
1992 | 1798 | ||
1993 | pr_info("%s:\n\tremoving driver", __func__); | 1799 | pr_info("%s:\n\tremoving driver", __func__); |
1994 | 1800 | ||
1995 | stmmac_dma_stop_rx(ndev->base_addr); | 1801 | priv->hw->dma->stop_rx(ndev->base_addr); |
1996 | stmmac_dma_stop_tx(ndev->base_addr); | 1802 | priv->hw->dma->stop_tx(ndev->base_addr); |
1997 | 1803 | ||
1998 | stmmac_mac_disable_rx(ndev->base_addr); | 1804 | stmmac_mac_disable_rx(ndev->base_addr); |
1999 | stmmac_mac_disable_tx(ndev->base_addr); | 1805 | stmmac_mac_disable_tx(ndev->base_addr); |
@@ -2040,8 +1846,8 @@ static int stmmac_suspend(struct platform_device *pdev, pm_message_t state) | |||
2040 | napi_disable(&priv->napi); | 1846 | napi_disable(&priv->napi); |
2041 | 1847 | ||
2042 | /* Stop TX/RX DMA */ | 1848 | /* Stop TX/RX DMA */ |
2043 | stmmac_dma_stop_tx(dev->base_addr); | 1849 | priv->hw->dma->stop_tx(dev->base_addr); |
2044 | stmmac_dma_stop_rx(dev->base_addr); | 1850 | priv->hw->dma->stop_rx(dev->base_addr); |
2045 | /* Clear the Rx/Tx descriptors */ | 1851 | /* Clear the Rx/Tx descriptors */ |
2046 | priv->hw->desc->init_rx_desc(priv->dma_rx, priv->dma_rx_size, | 1852 | priv->hw->desc->init_rx_desc(priv->dma_rx, priv->dma_rx_size, |
2047 | dis_ic); | 1853 | dis_ic); |
@@ -2101,8 +1907,8 @@ static int stmmac_resume(struct platform_device *pdev) | |||
2101 | /* Enable the MAC and DMA */ | 1907 | /* Enable the MAC and DMA */ |
2102 | stmmac_mac_enable_rx(ioaddr); | 1908 | stmmac_mac_enable_rx(ioaddr); |
2103 | stmmac_mac_enable_tx(ioaddr); | 1909 | stmmac_mac_enable_tx(ioaddr); |
2104 | stmmac_dma_start_tx(ioaddr); | 1910 | priv->hw->dma->start_tx(ioaddr); |
2105 | stmmac_dma_start_rx(ioaddr); | 1911 | priv->hw->dma->start_rx(ioaddr); |
2106 | 1912 | ||
2107 | #ifdef CONFIG_STMMAC_TIMER | 1913 | #ifdef CONFIG_STMMAC_TIMER |
2108 | priv->tm->timer_start(tmrate); | 1914 | priv->tm->timer_start(tmrate); |