Lines Matching +full:tx +full:- +full:burst +full:- +full:length
1 /*-
2 * SPDX-License-Identifier: BSD-2-Clause
78 /* For more information about Tx checksum offload issues see ale_encap(). */
182 { -1, 0, 0 }
187 { -1, 0, 0 }
192 { -1, 0, 0 }
197 { -1, 0, 0 }
211 for (i = ALE_PHY_TIMEOUT; i > 0; i--) { in ale_miibus_readreg()
219 device_printf(sc->ale_dev, "phy read timeout : %d\n", reg); in ale_miibus_readreg()
238 for (i = ALE_PHY_TIMEOUT; i > 0; i--) { in ale_miibus_writereg()
246 device_printf(sc->ale_dev, "phy write timeout : %d\n", reg); in ale_miibus_writereg()
260 mii = device_get_softc(sc->ale_miibus); in ale_miibus_statchg()
261 ifp = sc->ale_ifp; in ale_miibus_statchg()
266 sc->ale_flags &= ~ALE_FLAG_LINK; in ale_miibus_statchg()
267 if ((mii->mii_media_status & (IFM_ACTIVE | IFM_AVALID)) == in ale_miibus_statchg()
269 switch (IFM_SUBTYPE(mii->mii_media_active)) { in ale_miibus_statchg()
272 sc->ale_flags |= ALE_FLAG_LINK; in ale_miibus_statchg()
275 if ((sc->ale_flags & ALE_FLAG_FASTETHER) == 0) in ale_miibus_statchg()
276 sc->ale_flags |= ALE_FLAG_LINK; in ale_miibus_statchg()
283 /* Stop Rx/Tx MACs. */ in ale_miibus_statchg()
286 /* Program MACs with resolved speed/duplex/flow-control. */ in ale_miibus_statchg()
287 if ((sc->ale_flags & ALE_FLAG_LINK) != 0) { in ale_miibus_statchg()
289 /* Reenable Tx/Rx MACs. */ in ale_miibus_statchg()
308 mii = device_get_softc(sc->ale_miibus); in ale_mediastatus()
311 ifmr->ifm_status = mii->mii_media_status; in ale_mediastatus()
312 ifmr->ifm_active = mii->mii_media_active; in ale_mediastatus()
326 mii = device_get_softc(sc->ale_miibus); in ale_mediachange()
327 LIST_FOREACH(miisc, &mii->mii_phys, mii_list) in ale_mediachange()
346 if (vendor == sp->ale_vendorid && in ale_probe()
347 devid == sp->ale_deviceid) { in ale_probe()
348 device_set_desc(dev, sp->ale_name); in ale_probe()
369 if (pci_find_cap(sc->ale_dev, PCIY_VPD, &vpdc) == 0) { in ale_get_macaddr()
376 for (i = 100; i > 0; i--) { in ale_get_macaddr()
383 device_printf(sc->ale_dev, in ale_get_macaddr()
387 device_printf(sc->ale_dev, in ale_get_macaddr()
393 sc->ale_eaddr[0] = (ea[1] >> 8) & 0xFF; in ale_get_macaddr()
394 sc->ale_eaddr[1] = (ea[1] >> 0) & 0xFF; in ale_get_macaddr()
395 sc->ale_eaddr[2] = (ea[0] >> 24) & 0xFF; in ale_get_macaddr()
396 sc->ale_eaddr[3] = (ea[0] >> 16) & 0xFF; in ale_get_macaddr()
397 sc->ale_eaddr[4] = (ea[0] >> 8) & 0xFF; in ale_get_macaddr()
398 sc->ale_eaddr[5] = (ea[0] >> 0) & 0xFF; in ale_get_macaddr()
419 ale_miibus_writereg(sc->ale_dev, sc->ale_phyaddr, in ale_phy_reset()
421 ale_miibus_writereg(sc->ale_dev, sc->ale_phyaddr, in ale_phy_reset()
424 ale_miibus_writereg(sc->ale_dev, sc->ale_phyaddr, in ale_phy_reset()
426 ale_miibus_writereg(sc->ale_dev, sc->ale_phyaddr, in ale_phy_reset()
429 ale_miibus_writereg(sc->ale_dev, sc->ale_phyaddr, in ale_phy_reset()
431 ale_miibus_writereg(sc->ale_dev, sc->ale_phyaddr, in ale_phy_reset()
434 ale_miibus_writereg(sc->ale_dev, sc->ale_phyaddr, in ale_phy_reset()
436 ale_miibus_writereg(sc->ale_dev, sc->ale_phyaddr, in ale_phy_reset()
439 ale_miibus_writereg(sc->ale_dev, sc->ale_phyaddr, in ale_phy_reset()
441 ale_miibus_writereg(sc->ale_dev, sc->ale_phyaddr, in ale_phy_reset()
454 uint16_t burst; in ale_attach() local
460 sc->ale_dev = dev; in ale_attach()
462 mtx_init(&sc->ale_mtx, device_get_nameunit(dev), MTX_NETWORK_LOCK, in ale_attach()
464 callout_init_mtx(&sc->ale_tick_ch, &sc->ale_mtx, 0); in ale_attach()
465 NET_TASK_INIT(&sc->ale_int_task, 0, ale_int_task, sc); in ale_attach()
469 sc->ale_res_spec = ale_res_spec_mem; in ale_attach()
470 sc->ale_irq_spec = ale_irq_spec_legacy; in ale_attach()
471 error = bus_alloc_resources(dev, sc->ale_res_spec, sc->ale_res); in ale_attach()
478 sc->ale_phyaddr = ALE_PHY_ADDR; in ale_attach()
487 sc->ale_rev = pci_get_revid(dev); in ale_attach()
488 if (sc->ale_rev >= 0xF0) { in ale_attach()
490 sc->ale_flags |= ALE_FLAG_FASTETHER; in ale_attach()
494 sc->ale_flags |= ALE_FLAG_JUMBO; in ale_attach()
497 sc->ale_flags |= ALE_FLAG_FASTETHER; in ale_attach()
502 * of Tx buffers to make Tx checksum offload with custom in ale_attach()
505 sc->ale_flags |= ALE_FLAG_TXCSUM_BUG; in ale_attach()
510 sc->ale_flags |= ALE_FLAG_RXCSUM_BUG; in ale_attach()
512 * Don't use Tx CMB. It is known to cause RRS update failure in ale_attach()
517 sc->ale_flags |= ALE_FLAG_TXCMB_BUG; in ale_attach()
518 sc->ale_chip_rev = CSR_READ_4(sc, ALE_MASTER_CFG) >> in ale_attach()
522 sc->ale_rev); in ale_attach()
524 sc->ale_chip_rev); in ale_attach()
530 * as well as 0xFFFFFFFF for Tx/Rx fifo length. in ale_attach()
532 if (sc->ale_chip_rev == 0xFFFF || txf_len == 0xFFFFFFFF || in ale_attach()
534 device_printf(dev,"chip revision : 0x%04x, %u Tx FIFO " in ale_attach()
535 "%u Rx FIFO -- not initialized?\n", sc->ale_chip_rev, in ale_attach()
540 device_printf(dev, "%u Tx FIFO, %u Rx FIFO\n", txf_len, rxf_len); in ale_attach()
557 sc->ale_flags |= ALE_FLAG_MSIX; in ale_attach()
558 sc->ale_irq_spec = ale_irq_spec_msix; in ale_attach()
562 if (msi_disable == 0 && (sc->ale_flags & ALE_FLAG_MSIX) == 0 && in ale_attach()
568 sc->ale_flags |= ALE_FLAG_MSI; in ale_attach()
569 sc->ale_irq_spec = ale_irq_spec_msi; in ale_attach()
575 error = bus_alloc_resources(dev, sc->ale_irq_spec, sc->ale_irq); in ale_attach()
583 sc->ale_flags |= ALE_FLAG_PCIE; in ale_attach()
584 burst = pci_read_config(dev, i + 0x08, 2); in ale_attach()
586 sc->ale_dma_rd_burst = ((burst >> 12) & 0x07) << in ale_attach()
589 sc->ale_dma_wr_burst = ((burst >> 5) & 0x07) << in ale_attach()
593 128 << ((burst >> 12) & 0x07)); in ale_attach()
595 128 << ((burst >> 5) & 0x07)); in ale_attach()
598 sc->ale_dma_rd_burst = DMA_CFG_RD_BURST_128; in ale_attach()
599 sc->ale_dma_wr_burst = DMA_CFG_WR_BURST_128; in ale_attach()
611 ifp = sc->ale_ifp = if_alloc(IFT_ETHER); in ale_attach()
618 if_setsendqlen(ifp, ALE_TX_RING_CNT - 1); in ale_attach()
628 error = mii_attach(dev, &sc->ale_miibus, ifp, ale_mediachange, in ale_attach()
629 ale_mediastatus, BMSR_DEFCAPMASK, sc->ale_phyaddr, MII_OFFSET_ANY, in ale_attach()
636 ether_ifattach(ifp, sc->ale_eaddr); in ale_attach()
655 sc->ale_tq = taskqueue_create_fast("ale_taskq", M_WAITOK, in ale_attach()
656 taskqueue_thread_enqueue, &sc->ale_tq); in ale_attach()
657 taskqueue_start_threads(&sc->ale_tq, 1, PI_NET, "%s taskq", in ale_attach()
658 device_get_nameunit(sc->ale_dev)); in ale_attach()
660 if ((sc->ale_flags & ALE_FLAG_MSIX) != 0) in ale_attach()
662 else if ((sc->ale_flags & ALE_FLAG_MSI) != 0) in ale_attach()
667 error = bus_setup_intr(dev, sc->ale_irq[i], in ale_attach()
669 &sc->ale_intrhand[i]); in ale_attach()
675 taskqueue_free(sc->ale_tq); in ale_attach()
676 sc->ale_tq = NULL; in ale_attach()
697 ifp = sc->ale_ifp; in ale_detach()
703 callout_drain(&sc->ale_tick_ch); in ale_detach()
704 taskqueue_drain(sc->ale_tq, &sc->ale_int_task); in ale_detach()
707 if (sc->ale_tq != NULL) { in ale_detach()
708 taskqueue_drain(sc->ale_tq, &sc->ale_int_task); in ale_detach()
709 taskqueue_free(sc->ale_tq); in ale_detach()
710 sc->ale_tq = NULL; in ale_detach()
718 sc->ale_ifp = NULL; in ale_detach()
721 if ((sc->ale_flags & ALE_FLAG_MSIX) != 0) in ale_detach()
723 else if ((sc->ale_flags & ALE_FLAG_MSI) != 0) in ale_detach()
728 if (sc->ale_intrhand[i] != NULL) { in ale_detach()
729 bus_teardown_intr(dev, sc->ale_irq[i], in ale_detach()
730 sc->ale_intrhand[i]); in ale_detach()
731 sc->ale_intrhand[i] = NULL; in ale_detach()
735 bus_release_resources(dev, sc->ale_irq_spec, sc->ale_irq); in ale_detach()
736 if ((sc->ale_flags & (ALE_FLAG_MSI | ALE_FLAG_MSIX)) != 0) in ale_detach()
738 bus_release_resources(dev, sc->ale_res_spec, sc->ale_res); in ale_detach()
739 mtx_destroy(&sc->ale_mtx); in ale_detach()
759 stats = &sc->ale_stats; in ale_sysctl_node()
760 ctx = device_get_sysctl_ctx(sc->ale_dev); in ale_sysctl_node()
761 child = SYSCTL_CHILDREN(device_get_sysctl_tree(sc->ale_dev)); in ale_sysctl_node()
764 CTLTYPE_INT | CTLFLAG_RW | CTLFLAG_NEEDGIANT, &sc->ale_int_rx_mod, in ale_sysctl_node()
767 CTLTYPE_INT | CTLFLAG_RW | CTLFLAG_NEEDGIANT, &sc->ale_int_tx_mod, in ale_sysctl_node()
768 0, sysctl_hw_ale_int_mod, "I", "ale Tx interrupt moderation"); in ale_sysctl_node()
770 sc->ale_int_rx_mod = ALE_IM_RX_TIMER_DEFAULT; in ale_sysctl_node()
771 error = resource_int_value(device_get_name(sc->ale_dev), in ale_sysctl_node()
772 device_get_unit(sc->ale_dev), "int_rx_mod", &sc->ale_int_rx_mod); in ale_sysctl_node()
774 if (sc->ale_int_rx_mod < ALE_IM_TIMER_MIN || in ale_sysctl_node()
775 sc->ale_int_rx_mod > ALE_IM_TIMER_MAX) { in ale_sysctl_node()
776 device_printf(sc->ale_dev, "int_rx_mod value out of " in ale_sysctl_node()
779 sc->ale_int_rx_mod = ALE_IM_RX_TIMER_DEFAULT; in ale_sysctl_node()
782 sc->ale_int_tx_mod = ALE_IM_TX_TIMER_DEFAULT; in ale_sysctl_node()
783 error = resource_int_value(device_get_name(sc->ale_dev), in ale_sysctl_node()
784 device_get_unit(sc->ale_dev), "int_tx_mod", &sc->ale_int_tx_mod); in ale_sysctl_node()
786 if (sc->ale_int_tx_mod < ALE_IM_TIMER_MIN || in ale_sysctl_node()
787 sc->ale_int_tx_mod > ALE_IM_TIMER_MAX) { in ale_sysctl_node()
788 device_printf(sc->ale_dev, "int_tx_mod value out of " in ale_sysctl_node()
791 sc->ale_int_tx_mod = ALE_IM_TX_TIMER_DEFAULT; in ale_sysctl_node()
796 &sc->ale_process_limit, 0, sysctl_hw_ale_proc_limit, "I", in ale_sysctl_node()
799 sc->ale_process_limit = ALE_PROC_DEFAULT; in ale_sysctl_node()
800 error = resource_int_value(device_get_name(sc->ale_dev), in ale_sysctl_node()
801 device_get_unit(sc->ale_dev), "process_limit", in ale_sysctl_node()
802 &sc->ale_process_limit); in ale_sysctl_node()
804 if (sc->ale_process_limit < ALE_PROC_MIN || in ale_sysctl_node()
805 sc->ale_process_limit > ALE_PROC_MAX) { in ale_sysctl_node()
806 device_printf(sc->ale_dev, in ale_sysctl_node()
809 sc->ale_process_limit = ALE_PROC_DEFAULT; in ale_sysctl_node()
815 &stats->reset_brk_seq, in ale_sysctl_node()
827 &stats->rx_frames, "Good frames"); in ale_sysctl_node()
829 &stats->rx_bcast_frames, "Good broadcast frames"); in ale_sysctl_node()
831 &stats->rx_mcast_frames, "Good multicast frames"); in ale_sysctl_node()
833 &stats->rx_pause_frames, "Pause control frames"); in ale_sysctl_node()
835 &stats->rx_control_frames, "Control frames"); in ale_sysctl_node()
837 &stats->rx_crcerrs, "CRC errors"); in ale_sysctl_node()
839 &stats->rx_lenerrs, "Frames with length mismatched"); in ale_sysctl_node()
841 &stats->rx_bytes, "Good octets"); in ale_sysctl_node()
843 &stats->rx_bcast_bytes, "Good broadcast octets"); in ale_sysctl_node()
845 &stats->rx_mcast_bytes, "Good multicast octets"); in ale_sysctl_node()
847 &stats->rx_runts, "Too short frames"); in ale_sysctl_node()
849 &stats->rx_fragments, "Fragmented frames"); in ale_sysctl_node()
851 &stats->rx_pkts_64, "64 bytes frames"); in ale_sysctl_node()
853 &stats->rx_pkts_65_127, "65 to 127 bytes frames"); in ale_sysctl_node()
855 &stats->rx_pkts_128_255, "128 to 255 bytes frames"); in ale_sysctl_node()
857 &stats->rx_pkts_256_511, "256 to 511 bytes frames"); in ale_sysctl_node()
859 &stats->rx_pkts_512_1023, "512 to 1023 bytes frames"); in ale_sysctl_node()
861 &stats->rx_pkts_1024_1518, "1024 to 1518 bytes frames"); in ale_sysctl_node()
863 &stats->rx_pkts_1519_max, "1519 to max frames"); in ale_sysctl_node()
865 &stats->rx_pkts_truncated, "Truncated frames due to MTU size"); in ale_sysctl_node()
867 &stats->rx_fifo_oflows, "FIFO overflows"); in ale_sysctl_node()
869 &stats->rx_rrs_errs, "Return status write-back errors"); in ale_sysctl_node()
871 &stats->rx_alignerrs, "Alignment errors"); in ale_sysctl_node()
873 &stats->rx_pkts_filtered, in ale_sysctl_node()
876 /* Tx statistics. */ in ale_sysctl_node()
877 tree = SYSCTL_ADD_NODE(ctx, parent, OID_AUTO, "tx", in ale_sysctl_node()
878 CTLFLAG_RD | CTLFLAG_MPSAFE, NULL, "Tx MAC statistics"); in ale_sysctl_node()
881 &stats->tx_frames, "Good frames"); in ale_sysctl_node()
883 &stats->tx_bcast_frames, "Good broadcast frames"); in ale_sysctl_node()
885 &stats->tx_mcast_frames, "Good multicast frames"); in ale_sysctl_node()
887 &stats->tx_pause_frames, "Pause control frames"); in ale_sysctl_node()
889 &stats->tx_control_frames, "Control frames"); in ale_sysctl_node()
891 &stats->tx_excess_defer, "Frames with excessive derferrals"); in ale_sysctl_node()
893 &stats->tx_excess_defer, "Frames with derferrals"); in ale_sysctl_node()
895 &stats->tx_bytes, "Good octets"); in ale_sysctl_node()
897 &stats->tx_bcast_bytes, "Good broadcast octets"); in ale_sysctl_node()
899 &stats->tx_mcast_bytes, "Good multicast octets"); in ale_sysctl_node()
901 &stats->tx_pkts_64, "64 bytes frames"); in ale_sysctl_node()
903 &stats->tx_pkts_65_127, "65 to 127 bytes frames"); in ale_sysctl_node()
905 &stats->tx_pkts_128_255, "128 to 255 bytes frames"); in ale_sysctl_node()
907 &stats->tx_pkts_256_511, "256 to 511 bytes frames"); in ale_sysctl_node()
909 &stats->tx_pkts_512_1023, "512 to 1023 bytes frames"); in ale_sysctl_node()
911 &stats->tx_pkts_1024_1518, "1024 to 1518 bytes frames"); in ale_sysctl_node()
913 &stats->tx_pkts_1519_max, "1519 to max frames"); in ale_sysctl_node()
915 &stats->tx_single_colls, "Single collisions"); in ale_sysctl_node()
917 &stats->tx_multi_colls, "Multiple collisions"); in ale_sysctl_node()
919 &stats->tx_late_colls, "Late collisions"); in ale_sysctl_node()
921 &stats->tx_excess_colls, "Excessive collisions"); in ale_sysctl_node()
923 &stats->tx_underrun, "FIFO underruns"); in ale_sysctl_node()
925 &stats->tx_desc_underrun, "Descriptor write-back errors"); in ale_sysctl_node()
927 &stats->tx_lenerrs, "Frames with length mismatched"); in ale_sysctl_node()
929 &stats->tx_pkts_truncated, "Truncated frames due to MTU size"); in ale_sysctl_node()
950 ctx->ale_busaddr = segs[0].ds_addr; in ale_dmamap_cb()
954 * Tx descriptors/RXF0/CMB DMA blocks share ALE_DESC_ADDR_HI register
965 rx_page_end[0] = sc->ale_cdata.ale_rx_page[0].page_paddr + in ale_check_boundary()
966 sc->ale_pagesize; in ale_check_boundary()
967 rx_page_end[1] = sc->ale_cdata.ale_rx_page[1].page_paddr + in ale_check_boundary()
968 sc->ale_pagesize; in ale_check_boundary()
969 tx_ring_end = sc->ale_cdata.ale_tx_ring_paddr + ALE_TX_RING_SZ; in ale_check_boundary()
970 tx_cmb_end = sc->ale_cdata.ale_tx_cmb_paddr + ALE_TX_CMB_SZ; in ale_check_boundary()
971 rx_cmb_end[0] = sc->ale_cdata.ale_rx_page[0].cmb_paddr + ALE_RX_CMB_SZ; in ale_check_boundary()
972 rx_cmb_end[1] = sc->ale_cdata.ale_rx_page[1].cmb_paddr + ALE_RX_CMB_SZ; in ale_check_boundary()
975 ALE_ADDR_HI(sc->ale_cdata.ale_tx_ring_paddr)) || in ale_check_boundary()
977 ALE_ADDR_HI(sc->ale_cdata.ale_rx_page[0].page_paddr)) || in ale_check_boundary()
979 ALE_ADDR_HI(sc->ale_cdata.ale_rx_page[1].page_paddr)) || in ale_check_boundary()
981 ALE_ADDR_HI(sc->ale_cdata.ale_tx_cmb_paddr)) || in ale_check_boundary()
983 ALE_ADDR_HI(sc->ale_cdata.ale_rx_page[0].cmb_paddr)) || in ale_check_boundary()
985 ALE_ADDR_HI(sc->ale_cdata.ale_rx_page[1].cmb_paddr))) in ale_check_boundary()
1006 if ((sc->ale_flags & ALE_FLAG_JUMBO) != 0) in ale_dma_alloc()
1010 sc->ale_pagesize = roundup(guard_size + ALE_RX_PAGE_SZ, in ale_dma_alloc()
1016 bus_get_dma_tag(sc->ale_dev), /* parent */ in ale_dma_alloc()
1026 &sc->ale_cdata.ale_parent_tag); in ale_dma_alloc()
1028 device_printf(sc->ale_dev, in ale_dma_alloc()
1033 /* Create DMA tag for Tx descriptor ring. */ in ale_dma_alloc()
1035 sc->ale_cdata.ale_parent_tag, /* parent */ in ale_dma_alloc()
1045 &sc->ale_cdata.ale_tx_ring_tag); in ale_dma_alloc()
1047 device_printf(sc->ale_dev, in ale_dma_alloc()
1048 "could not create Tx ring DMA tag.\n"); in ale_dma_alloc()
1055 sc->ale_cdata.ale_parent_tag, /* parent */ in ale_dma_alloc()
1060 sc->ale_pagesize, /* maxsize */ in ale_dma_alloc()
1062 sc->ale_pagesize, /* maxsegsize */ in ale_dma_alloc()
1065 &sc->ale_cdata.ale_rx_page[i].page_tag); in ale_dma_alloc()
1067 device_printf(sc->ale_dev, in ale_dma_alloc()
1073 /* Create DMA tag for Tx coalescing message block. */ in ale_dma_alloc()
1075 sc->ale_cdata.ale_parent_tag, /* parent */ in ale_dma_alloc()
1085 &sc->ale_cdata.ale_tx_cmb_tag); in ale_dma_alloc()
1087 device_printf(sc->ale_dev, in ale_dma_alloc()
1088 "could not create Tx CMB DMA tag.\n"); in ale_dma_alloc()
1095 sc->ale_cdata.ale_parent_tag, /* parent */ in ale_dma_alloc()
1105 &sc->ale_cdata.ale_rx_page[i].cmb_tag); in ale_dma_alloc()
1107 device_printf(sc->ale_dev, in ale_dma_alloc()
1113 /* Allocate DMA'able memory and load the DMA map for Tx ring. */ in ale_dma_alloc()
1114 error = bus_dmamem_alloc(sc->ale_cdata.ale_tx_ring_tag, in ale_dma_alloc()
1115 (void **)&sc->ale_cdata.ale_tx_ring, in ale_dma_alloc()
1117 &sc->ale_cdata.ale_tx_ring_map); in ale_dma_alloc()
1119 device_printf(sc->ale_dev, in ale_dma_alloc()
1120 "could not allocate DMA'able memory for Tx ring.\n"); in ale_dma_alloc()
1124 error = bus_dmamap_load(sc->ale_cdata.ale_tx_ring_tag, in ale_dma_alloc()
1125 sc->ale_cdata.ale_tx_ring_map, sc->ale_cdata.ale_tx_ring, in ale_dma_alloc()
1128 device_printf(sc->ale_dev, in ale_dma_alloc()
1129 "could not load DMA'able memory for Tx ring.\n"); in ale_dma_alloc()
1132 sc->ale_cdata.ale_tx_ring_paddr = ctx.ale_busaddr; in ale_dma_alloc()
1136 error = bus_dmamem_alloc(sc->ale_cdata.ale_rx_page[i].page_tag, in ale_dma_alloc()
1137 (void **)&sc->ale_cdata.ale_rx_page[i].page_addr, in ale_dma_alloc()
1139 &sc->ale_cdata.ale_rx_page[i].page_map); in ale_dma_alloc()
1141 device_printf(sc->ale_dev, in ale_dma_alloc()
1147 error = bus_dmamap_load(sc->ale_cdata.ale_rx_page[i].page_tag, in ale_dma_alloc()
1148 sc->ale_cdata.ale_rx_page[i].page_map, in ale_dma_alloc()
1149 sc->ale_cdata.ale_rx_page[i].page_addr, in ale_dma_alloc()
1150 sc->ale_pagesize, ale_dmamap_cb, &ctx, 0); in ale_dma_alloc()
1152 device_printf(sc->ale_dev, in ale_dma_alloc()
1157 sc->ale_cdata.ale_rx_page[i].page_paddr = ctx.ale_busaddr; in ale_dma_alloc()
1160 /* Tx CMB. */ in ale_dma_alloc()
1161 error = bus_dmamem_alloc(sc->ale_cdata.ale_tx_cmb_tag, in ale_dma_alloc()
1162 (void **)&sc->ale_cdata.ale_tx_cmb, in ale_dma_alloc()
1164 &sc->ale_cdata.ale_tx_cmb_map); in ale_dma_alloc()
1166 device_printf(sc->ale_dev, in ale_dma_alloc()
1167 "could not allocate DMA'able memory for Tx CMB.\n"); in ale_dma_alloc()
1171 error = bus_dmamap_load(sc->ale_cdata.ale_tx_cmb_tag, in ale_dma_alloc()
1172 sc->ale_cdata.ale_tx_cmb_map, sc->ale_cdata.ale_tx_cmb, in ale_dma_alloc()
1175 device_printf(sc->ale_dev, in ale_dma_alloc()
1176 "could not load DMA'able memory for Tx CMB.\n"); in ale_dma_alloc()
1179 sc->ale_cdata.ale_tx_cmb_paddr = ctx.ale_busaddr; in ale_dma_alloc()
1183 error = bus_dmamem_alloc(sc->ale_cdata.ale_rx_page[i].cmb_tag, in ale_dma_alloc()
1184 (void **)&sc->ale_cdata.ale_rx_page[i].cmb_addr, in ale_dma_alloc()
1186 &sc->ale_cdata.ale_rx_page[i].cmb_map); in ale_dma_alloc()
1188 device_printf(sc->ale_dev, "could not allocate " in ale_dma_alloc()
1193 error = bus_dmamap_load(sc->ale_cdata.ale_rx_page[i].cmb_tag, in ale_dma_alloc()
1194 sc->ale_cdata.ale_rx_page[i].cmb_map, in ale_dma_alloc()
1195 sc->ale_cdata.ale_rx_page[i].cmb_addr, in ale_dma_alloc()
1198 device_printf(sc->ale_dev, "could not load DMA'able " in ale_dma_alloc()
1202 sc->ale_cdata.ale_rx_page[i].cmb_paddr = ctx.ale_busaddr; in ale_dma_alloc()
1206 * Tx descriptors/RXF0/CMB DMA blocks share the same in ale_dma_alloc()
1211 device_printf(sc->ale_dev, "4GB boundary crossed, " in ale_dma_alloc()
1223 * Create Tx buffer parent tag. in ale_dma_alloc()
1224 * AR81xx allows 64bit DMA addressing of Tx buffers so it in ale_dma_alloc()
1230 bus_get_dma_tag(sc->ale_dev), /* parent */ in ale_dma_alloc()
1240 &sc->ale_cdata.ale_buffer_tag); in ale_dma_alloc()
1242 device_printf(sc->ale_dev, in ale_dma_alloc()
1247 /* Create DMA tag for Tx buffers. */ in ale_dma_alloc()
1249 sc->ale_cdata.ale_buffer_tag, /* parent */ in ale_dma_alloc()
1259 &sc->ale_cdata.ale_tx_tag); in ale_dma_alloc()
1261 device_printf(sc->ale_dev, "could not create Tx DMA tag.\n"); in ale_dma_alloc()
1265 /* Create DMA maps for Tx buffers. */ in ale_dma_alloc()
1267 txd = &sc->ale_cdata.ale_txdesc[i]; in ale_dma_alloc()
1268 txd->tx_m = NULL; in ale_dma_alloc()
1269 txd->tx_dmamap = NULL; in ale_dma_alloc()
1270 error = bus_dmamap_create(sc->ale_cdata.ale_tx_tag, 0, in ale_dma_alloc()
1271 &txd->tx_dmamap); in ale_dma_alloc()
1273 device_printf(sc->ale_dev, in ale_dma_alloc()
1274 "could not create Tx dmamap.\n"); in ale_dma_alloc()
1289 /* Tx buffers. */ in ale_dma_free()
1290 if (sc->ale_cdata.ale_tx_tag != NULL) { in ale_dma_free()
1292 txd = &sc->ale_cdata.ale_txdesc[i]; in ale_dma_free()
1293 if (txd->tx_dmamap != NULL) { in ale_dma_free()
1294 bus_dmamap_destroy(sc->ale_cdata.ale_tx_tag, in ale_dma_free()
1295 txd->tx_dmamap); in ale_dma_free()
1296 txd->tx_dmamap = NULL; in ale_dma_free()
1299 bus_dma_tag_destroy(sc->ale_cdata.ale_tx_tag); in ale_dma_free()
1300 sc->ale_cdata.ale_tx_tag = NULL; in ale_dma_free()
1302 /* Tx descriptor ring. */ in ale_dma_free()
1303 if (sc->ale_cdata.ale_tx_ring_tag != NULL) { in ale_dma_free()
1304 if (sc->ale_cdata.ale_tx_ring_paddr != 0) in ale_dma_free()
1305 bus_dmamap_unload(sc->ale_cdata.ale_tx_ring_tag, in ale_dma_free()
1306 sc->ale_cdata.ale_tx_ring_map); in ale_dma_free()
1307 if (sc->ale_cdata.ale_tx_ring != NULL) in ale_dma_free()
1308 bus_dmamem_free(sc->ale_cdata.ale_tx_ring_tag, in ale_dma_free()
1309 sc->ale_cdata.ale_tx_ring, in ale_dma_free()
1310 sc->ale_cdata.ale_tx_ring_map); in ale_dma_free()
1311 sc->ale_cdata.ale_tx_ring_paddr = 0; in ale_dma_free()
1312 sc->ale_cdata.ale_tx_ring = NULL; in ale_dma_free()
1313 bus_dma_tag_destroy(sc->ale_cdata.ale_tx_ring_tag); in ale_dma_free()
1314 sc->ale_cdata.ale_tx_ring_tag = NULL; in ale_dma_free()
1318 if (sc->ale_cdata.ale_rx_page[i].page_tag != NULL) { in ale_dma_free()
1319 if (sc->ale_cdata.ale_rx_page[i].page_paddr != 0) in ale_dma_free()
1321 sc->ale_cdata.ale_rx_page[i].page_tag, in ale_dma_free()
1322 sc->ale_cdata.ale_rx_page[i].page_map); in ale_dma_free()
1323 if (sc->ale_cdata.ale_rx_page[i].page_addr != NULL) in ale_dma_free()
1325 sc->ale_cdata.ale_rx_page[i].page_tag, in ale_dma_free()
1326 sc->ale_cdata.ale_rx_page[i].page_addr, in ale_dma_free()
1327 sc->ale_cdata.ale_rx_page[i].page_map); in ale_dma_free()
1328 sc->ale_cdata.ale_rx_page[i].page_paddr = 0; in ale_dma_free()
1329 sc->ale_cdata.ale_rx_page[i].page_addr = NULL; in ale_dma_free()
1331 sc->ale_cdata.ale_rx_page[i].page_tag); in ale_dma_free()
1332 sc->ale_cdata.ale_rx_page[i].page_tag = NULL; in ale_dma_free()
1337 if (sc->ale_cdata.ale_rx_page[i].cmb_tag != NULL) { in ale_dma_free()
1338 if (sc->ale_cdata.ale_rx_page[i].cmb_paddr != 0) in ale_dma_free()
1340 sc->ale_cdata.ale_rx_page[i].cmb_tag, in ale_dma_free()
1341 sc->ale_cdata.ale_rx_page[i].cmb_map); in ale_dma_free()
1342 if (sc->ale_cdata.ale_rx_page[i].cmb_addr != NULL) in ale_dma_free()
1344 sc->ale_cdata.ale_rx_page[i].cmb_tag, in ale_dma_free()
1345 sc->ale_cdata.ale_rx_page[i].cmb_addr, in ale_dma_free()
1346 sc->ale_cdata.ale_rx_page[i].cmb_map); in ale_dma_free()
1347 sc->ale_cdata.ale_rx_page[i].cmb_paddr = 0; in ale_dma_free()
1348 sc->ale_cdata.ale_rx_page[i].cmb_addr = NULL; in ale_dma_free()
1350 sc->ale_cdata.ale_rx_page[i].cmb_tag); in ale_dma_free()
1351 sc->ale_cdata.ale_rx_page[i].cmb_tag = NULL; in ale_dma_free()
1354 /* Tx CMB. */ in ale_dma_free()
1355 if (sc->ale_cdata.ale_tx_cmb_tag != NULL) { in ale_dma_free()
1356 if (sc->ale_cdata.ale_tx_cmb_paddr != 0) in ale_dma_free()
1357 bus_dmamap_unload(sc->ale_cdata.ale_tx_cmb_tag, in ale_dma_free()
1358 sc->ale_cdata.ale_tx_cmb_map); in ale_dma_free()
1359 if (sc->ale_cdata.ale_tx_cmb != NULL) in ale_dma_free()
1360 bus_dmamem_free(sc->ale_cdata.ale_tx_cmb_tag, in ale_dma_free()
1361 sc->ale_cdata.ale_tx_cmb, in ale_dma_free()
1362 sc->ale_cdata.ale_tx_cmb_map); in ale_dma_free()
1363 sc->ale_cdata.ale_tx_cmb_paddr = 0; in ale_dma_free()
1364 sc->ale_cdata.ale_tx_cmb = NULL; in ale_dma_free()
1365 bus_dma_tag_destroy(sc->ale_cdata.ale_tx_cmb_tag); in ale_dma_free()
1366 sc->ale_cdata.ale_tx_cmb_tag = NULL; in ale_dma_free()
1368 if (sc->ale_cdata.ale_buffer_tag != NULL) { in ale_dma_free()
1369 bus_dma_tag_destroy(sc->ale_cdata.ale_buffer_tag); in ale_dma_free()
1370 sc->ale_cdata.ale_buffer_tag = NULL; in ale_dma_free()
1372 if (sc->ale_cdata.ale_parent_tag != NULL) { in ale_dma_free()
1373 bus_dma_tag_destroy(sc->ale_cdata.ale_parent_tag); in ale_dma_free()
1374 sc->ale_cdata.ale_parent_tag = NULL; in ale_dma_free()
1387 * restarting auto-negotiation in suspend/shutdown phase but we
1388 * don't know whether that auto-negotiation would succeed or not
1396 * Save current negotiated media speed/duplex/flow-control to
1407 mii = device_get_softc(sc->ale_miibus); in ale_setlinkspeed()
1410 if ((mii->mii_media_status & (IFM_ACTIVE | IFM_AVALID)) == in ale_setlinkspeed()
1412 switch IFM_SUBTYPE(mii->mii_media_active) { in ale_setlinkspeed()
1423 ale_miibus_writereg(sc->ale_dev, sc->ale_phyaddr, MII_100T2CR, 0); in ale_setlinkspeed()
1424 ale_miibus_writereg(sc->ale_dev, sc->ale_phyaddr, in ale_setlinkspeed()
1426 ale_miibus_writereg(sc->ale_dev, sc->ale_phyaddr, in ale_setlinkspeed()
1435 if ((mii->mii_media_status & (IFM_ACTIVE | IFM_AVALID)) in ale_setlinkspeed()
1438 mii->mii_media_active)) { in ale_setlinkspeed()
1452 device_printf(sc->ale_dev, in ale_setlinkspeed()
1456 * No link, force MAC to have 100Mbps, full-duplex link. in ale_setlinkspeed()
1459 mii->mii_media_status = IFM_AVALID | IFM_ACTIVE; in ale_setlinkspeed()
1460 mii->mii_media_active = IFM_ETHER | IFM_100_TX | IFM_FDX; in ale_setlinkspeed()
1472 if (!pci_has_pm(sc->ale_dev)) { in ale_setwol()
1487 ifp = sc->ale_ifp; in ale_setwol()
1489 if ((sc->ale_flags & ALE_FLAG_FASTETHER) == 0) in ale_setwol()
1519 pci_enable_pme(sc->ale_dev); in ale_setwol()
1548 ifp = sc->ale_ifp; in ale_resume()
1580 if ((m->m_pkthdr.csum_flags & (ALE_CSUM_FEATURES | CSUM_TSO)) != 0) { in ale_encap()
1582 * AR81xx requires offset of TCP/UDP payload in its Tx in ale_encap()
1583 * descriptor to perform hardware Tx checksum offload. in ale_encap()
1605 * Buggy-controller requires 4 byte aligned Tx buffer in ale_encap()
1608 if ((sc->ale_flags & ALE_FLAG_TXCSUM_BUG) != 0 && in ale_encap()
1609 (m->m_pkthdr.csum_flags & ALE_CSUM_FEATURES) != 0 && in ale_encap()
1631 if (eh->ether_type == htons(ETHERTYPE_VLAN)) { in ale_encap()
1645 poff = ip_off + (ip->ip_hl << 2); in ale_encap()
1646 if ((m->m_pkthdr.csum_flags & CSUM_TSO) != 0) { in ale_encap()
1663 m = m_pullup(m, poff + (tcp->th_off << 2)); in ale_encap()
1676 * TCP payload length so ale(4) should recompute in ale_encap()
1682 ip->ip_sum = 0; in ale_encap()
1683 tcp->th_sum = in_pseudo(ip->ip_src.s_addr, in ale_encap()
1684 ip->ip_dst.s_addr, htons(IPPROTO_TCP)); in ale_encap()
1689 si = prod = sc->ale_cdata.ale_tx_prod; in ale_encap()
1690 txd = &sc->ale_cdata.ale_txdesc[prod]; in ale_encap()
1692 map = txd->tx_dmamap; in ale_encap()
1694 error = bus_dmamap_load_mbuf_sg(sc->ale_cdata.ale_tx_tag, map, in ale_encap()
1704 error = bus_dmamap_load_mbuf_sg(sc->ale_cdata.ale_tx_tag, map, in ale_encap()
1720 if (sc->ale_cdata.ale_tx_cnt + nsegs >= ALE_TX_RING_CNT - 3) { in ale_encap()
1721 bus_dmamap_unload(sc->ale_cdata.ale_tx_tag, map); in ale_encap()
1724 bus_dmamap_sync(sc->ale_cdata.ale_tx_tag, map, BUS_DMASYNC_PREWRITE); in ale_encap()
1727 if ((m->m_pkthdr.csum_flags & CSUM_TSO) != 0) { in ale_encap()
1730 cflags |= ((uint32_t)m->m_pkthdr.tso_segsz << ALE_TD_MSS_SHIFT); in ale_encap()
1732 cflags |= ip->ip_hl << ALE_TD_IPHDR_LEN_SHIFT; in ale_encap()
1733 cflags |= tcp->th_off << ALE_TD_TCPHDR_LEN_SHIFT; in ale_encap()
1734 } else if ((m->m_pkthdr.csum_flags & ALE_CSUM_FEATURES) != 0) { in ale_encap()
1736 * AR81xx supports Tx custom checksum offload feature in ale_encap()
1743 * requires 4 bytes aligned Tx buffers due to hardware in ale_encap()
1745 * AR81xx also supports explicit Tx checksum computation in ale_encap()
1748 * because it's fixed length). However with this scheme in ale_encap()
1750 * TSO or explicit Tx checksum offload. I chosen TSO in ale_encap()
1751 * plus custom checksum offload with work-around which in ale_encap()
1753 * ethernet controller. The work-around takes a lot of in ale_encap()
1754 * CPU cycles if Tx buffer is not aligned on 4 bytes in ale_encap()
1761 cflags |= ((poff + m->m_pkthdr.csum_data) << in ale_encap()
1766 if ((m->m_flags & M_VLANTAG) != 0) { in ale_encap()
1767 vtag = ALE_TX_VLAN_TAG(m->m_pkthdr.ether_vtag); in ale_encap()
1773 if ((m->m_pkthdr.csum_flags & CSUM_TSO) != 0) { in ale_encap()
1778 hdrlen = poff + (tcp->th_off << 2); in ale_encap()
1779 desc = &sc->ale_cdata.ale_tx_ring[prod]; in ale_encap()
1780 desc->addr = htole64(txsegs[i].ds_addr); in ale_encap()
1781 desc->len = htole32(ALE_TX_BYTES(hdrlen) | vtag); in ale_encap()
1782 desc->flags = htole32(cflags); in ale_encap()
1783 sc->ale_cdata.ale_tx_cnt++; in ale_encap()
1785 if (m->m_len - hdrlen > 0) { in ale_encap()
1787 desc = &sc->ale_cdata.ale_tx_ring[prod]; in ale_encap()
1788 desc->addr = htole64(txsegs[i].ds_addr + hdrlen); in ale_encap()
1789 desc->len = htole32(ALE_TX_BYTES(m->m_len - hdrlen) | in ale_encap()
1791 desc->flags = htole32(cflags); in ale_encap()
1792 sc->ale_cdata.ale_tx_cnt++; in ale_encap()
1798 desc = &sc->ale_cdata.ale_tx_ring[prod]; in ale_encap()
1799 desc->addr = htole64(txsegs[i].ds_addr); in ale_encap()
1800 desc->len = htole32(ALE_TX_BYTES(txsegs[i].ds_len) | vtag); in ale_encap()
1801 desc->flags = htole32(cflags); in ale_encap()
1802 sc->ale_cdata.ale_tx_cnt++; in ale_encap()
1806 sc->ale_cdata.ale_tx_prod = prod; in ale_encap()
1808 if ((m->m_pkthdr.csum_flags & CSUM_TSO) != 0) { in ale_encap()
1809 desc = &sc->ale_cdata.ale_tx_ring[si]; in ale_encap()
1810 desc->flags |= htole32(ALE_TD_TSO_HDR); in ale_encap()
1814 prod = (prod + ALE_TX_RING_CNT - 1) % ALE_TX_RING_CNT; in ale_encap()
1815 desc = &sc->ale_cdata.ale_tx_ring[prod]; in ale_encap()
1816 desc->flags |= htole32(ALE_TD_EOP); in ale_encap()
1819 txd = &sc->ale_cdata.ale_txdesc[prod]; in ale_encap()
1820 map = txd_last->tx_dmamap; in ale_encap()
1821 txd_last->tx_dmamap = txd->tx_dmamap; in ale_encap()
1822 txd->tx_dmamap = map; in ale_encap()
1823 txd->tx_m = m; in ale_encap()
1826 bus_dmamap_sync(sc->ale_cdata.ale_tx_ring_tag, in ale_encap()
1827 sc->ale_cdata.ale_tx_ring_map, in ale_encap()
1856 if (sc->ale_cdata.ale_tx_cnt >= ALE_TX_DESC_HIWAT) in ale_start_locked()
1860 IFF_DRV_RUNNING || (sc->ale_flags & ALE_FLAG_LINK) == 0) in ale_start_locked()
1891 sc->ale_cdata.ale_tx_prod); in ale_start_locked()
1893 sc->ale_watchdog_timer = ALE_TX_TIMEOUT; in ale_start_locked()
1904 if (sc->ale_watchdog_timer == 0 || --sc->ale_watchdog_timer) in ale_watchdog()
1907 ifp = sc->ale_ifp; in ale_watchdog()
1908 if ((sc->ale_flags & ALE_FLAG_LINK) == 0) { in ale_watchdog()
1909 if_printf(sc->ale_ifp, "watchdog timeout (lost link)\n"); in ale_watchdog()
1915 if_printf(sc->ale_ifp, "watchdog timeout -- resetting\n"); in ale_watchdog()
1936 if (ifr->ifr_mtu < ETHERMIN || ifr->ifr_mtu > ALE_JUMBO_MTU || in ale_ioctl()
1937 ((sc->ale_flags & ALE_FLAG_JUMBO) == 0 && in ale_ioctl()
1938 ifr->ifr_mtu > ETHERMTU)) in ale_ioctl()
1940 else if (if_getmtu(ifp) != ifr->ifr_mtu) { in ale_ioctl()
1942 if_setmtu(ifp, ifr->ifr_mtu); in ale_ioctl()
1954 if (((if_getflags(ifp) ^ sc->ale_if_flags) in ale_ioctl()
1964 sc->ale_if_flags = if_getflags(ifp); in ale_ioctl()
1976 mii = device_get_softc(sc->ale_miibus); in ale_ioctl()
1977 error = ifmedia_ioctl(ifp, ifr, &mii->mii_media, cmd); in ale_ioctl()
1981 mask = ifr->ifr_reqcap ^ if_getcapenable(ifp); in ale_ioctl()
2040 mii = device_get_softc(sc->ale_miibus); in ale_mac_config()
2045 switch (IFM_SUBTYPE(mii->mii_media_active)) { in ale_mac_config()
2054 if ((IFM_OPTIONS(mii->mii_media_active) & IFM_FDX) != 0) { in ale_mac_config()
2056 if ((IFM_OPTIONS(mii->mii_media_active) & IFM_ETH_TXPAUSE) != 0) in ale_mac_config()
2058 if ((IFM_OPTIONS(mii->mii_media_active) & IFM_ETH_RXPAUSE) != 0) in ale_mac_config()
2075 /* Read Tx statistics. */ in ale_stats_clear()
2093 ifp = sc->ale_ifp; in ale_stats_update()
2094 stat = &sc->ale_stats; in ale_stats_update()
2102 /* Read Tx statistics. */ in ale_stats_update()
2109 stat->rx_frames += smb->rx_frames; in ale_stats_update()
2110 stat->rx_bcast_frames += smb->rx_bcast_frames; in ale_stats_update()
2111 stat->rx_mcast_frames += smb->rx_mcast_frames; in ale_stats_update()
2112 stat->rx_pause_frames += smb->rx_pause_frames; in ale_stats_update()
2113 stat->rx_control_frames += smb->rx_control_frames; in ale_stats_update()
2114 stat->rx_crcerrs += smb->rx_crcerrs; in ale_stats_update()
2115 stat->rx_lenerrs += smb->rx_lenerrs; in ale_stats_update()
2116 stat->rx_bytes += smb->rx_bytes; in ale_stats_update()
2117 stat->rx_runts += smb->rx_runts; in ale_stats_update()
2118 stat->rx_fragments += smb->rx_fragments; in ale_stats_update()
2119 stat->rx_pkts_64 += smb->rx_pkts_64; in ale_stats_update()
2120 stat->rx_pkts_65_127 += smb->rx_pkts_65_127; in ale_stats_update()
2121 stat->rx_pkts_128_255 += smb->rx_pkts_128_255; in ale_stats_update()
2122 stat->rx_pkts_256_511 += smb->rx_pkts_256_511; in ale_stats_update()
2123 stat->rx_pkts_512_1023 += smb->rx_pkts_512_1023; in ale_stats_update()
2124 stat->rx_pkts_1024_1518 += smb->rx_pkts_1024_1518; in ale_stats_update()
2125 stat->rx_pkts_1519_max += smb->rx_pkts_1519_max; in ale_stats_update()
2126 stat->rx_pkts_truncated += smb->rx_pkts_truncated; in ale_stats_update()
2127 stat->rx_fifo_oflows += smb->rx_fifo_oflows; in ale_stats_update()
2128 stat->rx_rrs_errs += smb->rx_rrs_errs; in ale_stats_update()
2129 stat->rx_alignerrs += smb->rx_alignerrs; in ale_stats_update()
2130 stat->rx_bcast_bytes += smb->rx_bcast_bytes; in ale_stats_update()
2131 stat->rx_mcast_bytes += smb->rx_mcast_bytes; in ale_stats_update()
2132 stat->rx_pkts_filtered += smb->rx_pkts_filtered; in ale_stats_update()
2134 /* Tx stats. */ in ale_stats_update()
2135 stat->tx_frames += smb->tx_frames; in ale_stats_update()
2136 stat->tx_bcast_frames += smb->tx_bcast_frames; in ale_stats_update()
2137 stat->tx_mcast_frames += smb->tx_mcast_frames; in ale_stats_update()
2138 stat->tx_pause_frames += smb->tx_pause_frames; in ale_stats_update()
2139 stat->tx_excess_defer += smb->tx_excess_defer; in ale_stats_update()
2140 stat->tx_control_frames += smb->tx_control_frames; in ale_stats_update()
2141 stat->tx_deferred += smb->tx_deferred; in ale_stats_update()
2142 stat->tx_bytes += smb->tx_bytes; in ale_stats_update()
2143 stat->tx_pkts_64 += smb->tx_pkts_64; in ale_stats_update()
2144 stat->tx_pkts_65_127 += smb->tx_pkts_65_127; in ale_stats_update()
2145 stat->tx_pkts_128_255 += smb->tx_pkts_128_255; in ale_stats_update()
2146 stat->tx_pkts_256_511 += smb->tx_pkts_256_511; in ale_stats_update()
2147 stat->tx_pkts_512_1023 += smb->tx_pkts_512_1023; in ale_stats_update()
2148 stat->tx_pkts_1024_1518 += smb->tx_pkts_1024_1518; in ale_stats_update()
2149 stat->tx_pkts_1519_max += smb->tx_pkts_1519_max; in ale_stats_update()
2150 stat->tx_single_colls += smb->tx_single_colls; in ale_stats_update()
2151 stat->tx_multi_colls += smb->tx_multi_colls; in ale_stats_update()
2152 stat->tx_late_colls += smb->tx_late_colls; in ale_stats_update()
2153 stat->tx_excess_colls += smb->tx_excess_colls; in ale_stats_update()
2154 stat->tx_underrun += smb->tx_underrun; in ale_stats_update()
2155 stat->tx_desc_underrun += smb->tx_desc_underrun; in ale_stats_update()
2156 stat->tx_lenerrs += smb->tx_lenerrs; in ale_stats_update()
2157 stat->tx_pkts_truncated += smb->tx_pkts_truncated; in ale_stats_update()
2158 stat->tx_bcast_bytes += smb->tx_bcast_bytes; in ale_stats_update()
2159 stat->tx_mcast_bytes += smb->tx_mcast_bytes; in ale_stats_update()
2162 if_inc_counter(ifp, IFCOUNTER_OPACKETS, smb->tx_frames); in ale_stats_update()
2164 if_inc_counter(ifp, IFCOUNTER_COLLISIONS, smb->tx_single_colls + in ale_stats_update()
2165 smb->tx_multi_colls * 2 + smb->tx_late_colls + in ale_stats_update()
2166 smb->tx_excess_colls * HDPX_CFG_RETRY_DEFAULT); in ale_stats_update()
2168 if_inc_counter(ifp, IFCOUNTER_OERRORS, smb->tx_late_colls + in ale_stats_update()
2169 smb->tx_excess_colls + smb->tx_underrun + smb->tx_pkts_truncated); in ale_stats_update()
2171 if_inc_counter(ifp, IFCOUNTER_IPACKETS, smb->rx_frames); in ale_stats_update()
2174 smb->rx_crcerrs + smb->rx_lenerrs + in ale_stats_update()
2175 smb->rx_runts + smb->rx_pkts_truncated + in ale_stats_update()
2176 smb->rx_fifo_oflows + smb->rx_rrs_errs + in ale_stats_update()
2177 smb->rx_alignerrs); in ale_stats_update()
2193 taskqueue_enqueue(sc->ale_tq, &sc->ale_int_task); in ale_intr()
2210 if (sc->ale_morework != 0) in ale_int_task()
2218 ifp = sc->ale_ifp; in ale_int_task()
2221 more = ale_rxeof(sc, sc->ale_process_limit); in ale_int_task()
2223 sc->ale_morework = 1; in ale_int_task()
2225 sc->ale_stats.reset_brk_seq++; in ale_int_task()
2234 device_printf(sc->ale_dev, in ale_int_task()
2235 "DMA read error! -- resetting\n"); in ale_int_task()
2237 device_printf(sc->ale_dev, in ale_int_task()
2238 "DMA write error! -- resetting\n"); in ale_int_task()
2251 taskqueue_enqueue(sc->ale_tq, &sc->ale_int_task); in ale_int_task()
2258 /* Re-enable interrupts. */ in ale_int_task()
2272 ifp = sc->ale_ifp; in ale_txeof()
2274 if (sc->ale_cdata.ale_tx_cnt == 0) in ale_txeof()
2277 bus_dmamap_sync(sc->ale_cdata.ale_tx_ring_tag, in ale_txeof()
2278 sc->ale_cdata.ale_tx_ring_map, in ale_txeof()
2280 if ((sc->ale_flags & ALE_FLAG_TXCMB_BUG) == 0) { in ale_txeof()
2281 bus_dmamap_sync(sc->ale_cdata.ale_tx_cmb_tag, in ale_txeof()
2282 sc->ale_cdata.ale_tx_cmb_map, in ale_txeof()
2284 prod = *sc->ale_cdata.ale_tx_cmb & TPD_CNT_MASK; in ale_txeof()
2287 cons = sc->ale_cdata.ale_tx_cons; in ale_txeof()
2289 * Go through our Tx list and free mbufs for those in ale_txeof()
2294 if (sc->ale_cdata.ale_tx_cnt <= 0) in ale_txeof()
2298 sc->ale_cdata.ale_tx_cnt--; in ale_txeof()
2299 txd = &sc->ale_cdata.ale_txdesc[cons]; in ale_txeof()
2300 if (txd->tx_m != NULL) { in ale_txeof()
2302 bus_dmamap_sync(sc->ale_cdata.ale_tx_tag, in ale_txeof()
2303 txd->tx_dmamap, BUS_DMASYNC_POSTWRITE); in ale_txeof()
2304 bus_dmamap_unload(sc->ale_cdata.ale_tx_tag, in ale_txeof()
2305 txd->tx_dmamap); in ale_txeof()
2306 m_freem(txd->tx_m); in ale_txeof()
2307 txd->tx_m = NULL; in ale_txeof()
2312 sc->ale_cdata.ale_tx_cons = cons; in ale_txeof()
2315 * Tx descriptors in queue. in ale_txeof()
2317 if (sc->ale_cdata.ale_tx_cnt == 0) in ale_txeof()
2318 sc->ale_watchdog_timer = 0; in ale_txeof()
2324 uint32_t length, uint32_t *prod) in ale_rx_update_page() argument
2330 rx_page->cons += roundup(length + sizeof(struct rx_rs), in ale_rx_update_page()
2332 if (rx_page->cons >= ALE_RX_PAGE_SZ) { in ale_rx_update_page()
2337 rx_page->cons = 0; in ale_rx_update_page()
2338 *rx_page->cmb_addr = 0; in ale_rx_update_page()
2339 bus_dmamap_sync(rx_page->cmb_tag, rx_page->cmb_map, in ale_rx_update_page()
2341 CSR_WRITE_1(sc, ALE_RXF0_PAGE0 + sc->ale_cdata.ale_rx_curp, in ale_rx_update_page()
2344 sc->ale_cdata.ale_rx_curp ^= 1; in ale_rx_update_page()
2346 &sc->ale_cdata.ale_rx_page[sc->ale_cdata.ale_rx_curp]; in ale_rx_update_page()
2348 bus_dmamap_sync(rx_page->page_tag, rx_page->page_map, in ale_rx_update_page()
2350 bus_dmamap_sync(rx_page->cmb_tag, rx_page->cmb_map, in ale_rx_update_page()
2353 *prod = *rx_page->cmb_addr; in ale_rx_update_page()
2375 ifp = sc->ale_ifp; in ale_rxcsum()
2376 m->m_pkthdr.csum_flags |= CSUM_IP_CHECKED; in ale_rxcsum()
2378 m->m_pkthdr.csum_flags |= CSUM_IP_VALID; in ale_rxcsum()
2380 if ((sc->ale_flags & ALE_FLAG_RXCSUM_BUG) == 0) { in ale_rxcsum()
2384 m->m_pkthdr.csum_flags |= in ale_rxcsum()
2386 m->m_pkthdr.csum_data = 0xffff; in ale_rxcsum()
2399 if (ip->ip_off != 0 && (status & ALE_RD_IPV4_DF) == 0) in ale_rxcsum()
2401 m->m_pkthdr.csum_flags |= CSUM_DATA_VALID | in ale_rxcsum()
2403 m->m_pkthdr.csum_data = 0xffff; in ale_rxcsum()
2421 uint32_t length, prod, seqno, status, vtags; in ale_rxeof() local
2424 ifp = sc->ale_ifp; in ale_rxeof()
2425 rx_page = &sc->ale_cdata.ale_rx_page[sc->ale_cdata.ale_rx_curp]; in ale_rxeof()
2426 bus_dmamap_sync(rx_page->cmb_tag, rx_page->cmb_map, in ale_rxeof()
2428 bus_dmamap_sync(rx_page->page_tag, rx_page->page_map, in ale_rxeof()
2439 prod = *rx_page->cmb_addr; in ale_rxeof()
2441 if (rx_page->cons >= prod) in ale_rxeof()
2443 rs = (struct rx_rs *)(rx_page->page_addr + rx_page->cons); in ale_rxeof()
2444 seqno = ALE_RX_SEQNO(le32toh(rs->seqno)); in ale_rxeof()
2445 if (sc->ale_cdata.ale_rx_seqno != seqno) { in ale_rxeof()
2453 * with FIFO overflow of hardware or activity of Tx in ale_rxeof()
2459 device_printf(sc->ale_dev, in ale_rxeof()
2460 "garbled seq: %u, expected: %u -- " in ale_rxeof()
2462 sc->ale_cdata.ale_rx_seqno); in ale_rxeof()
2466 sc->ale_cdata.ale_rx_seqno++; in ale_rxeof()
2467 length = ALE_RX_BYTES(le32toh(rs->length)); in ale_rxeof()
2468 status = le32toh(rs->flags); in ale_rxeof()
2476 * o frame length and protocol specific length in ale_rxeof()
2482 ale_rx_update_page(sc, &rx_page, length, &prod); in ale_rxeof()
2487 * m_devget(9) is major bottle-neck of ale(4)(It comes in ale_rxeof()
2493 * on these low-end consumer ethernet controller. in ale_rxeof()
2495 m = m_devget((char *)(rs + 1), length - ETHER_CRC_LEN, in ale_rxeof()
2499 ale_rx_update_page(sc, &rx_page, length, &prod); in ale_rxeof()
2507 vtags = ALE_RX_VLAN(le32toh(rs->vtags)); in ale_rxeof()
2508 m->m_pkthdr.ether_vtag = ALE_RX_VLAN_TAG(vtags); in ale_rxeof()
2509 m->m_flags |= M_VLANTAG; in ale_rxeof()
2517 ale_rx_update_page(sc, &rx_page, length, &prod); in ale_rxeof()
2533 mii = device_get_softc(sc->ale_miibus); in ale_tick()
2537 * Reclaim Tx buffers that have been transferred. It's not in ale_tick()
2543 callout_reset(&sc->ale_tick_ch, hz, ale_tick, sc); in ale_tick()
2556 for (i = ALE_RESET_TIMEOUT; i > 0; i--) { in ale_reset()
2562 device_printf(sc->ale_dev, "master reset timeout!\n"); in ale_reset()
2564 for (i = ALE_RESET_TIMEOUT; i > 0; i--) { in ale_reset()
2571 device_printf(sc->ale_dev, "reset timeout(0x%08x)!\n", reg); in ale_reset()
2596 ifp = sc->ale_ifp; in ale_init_locked()
2597 mii = device_get_softc(sc->ale_miibus); in ale_init_locked()
2609 /* Initialize Tx descriptors, DMA memory blocks. */ in ale_init_locked()
2625 * Set Tx descriptor/RXF0/CMB base addresses. They share in ale_init_locked()
2628 paddr = sc->ale_cdata.ale_tx_ring_paddr; in ale_init_locked()
2634 paddr = sc->ale_cdata.ale_rx_page[0].page_paddr; in ale_init_locked()
2636 paddr = sc->ale_cdata.ale_rx_page[1].page_paddr; in ale_init_locked()
2638 /* Set Tx/Rx CMB addresses. */ in ale_init_locked()
2639 paddr = sc->ale_cdata.ale_tx_cmb_paddr; in ale_init_locked()
2641 paddr = sc->ale_cdata.ale_rx_page[0].cmb_paddr; in ale_init_locked()
2643 paddr = sc->ale_cdata.ale_rx_page[1].cmb_paddr; in ale_init_locked()
2650 * multi-queue yet. in ale_init_locked()
2658 /* Set Rx/Tx interrupt trigger threshold. */ in ale_init_locked()
2671 reg = ALE_USECS(sc->ale_int_rx_mod) << IM_TIMER_RX_SHIFT; in ale_init_locked()
2672 reg |= ALE_USECS(sc->ale_int_tx_mod) << IM_TIMER_TX_SHIFT; in ale_init_locked()
2677 if (ALE_USECS(sc->ale_int_rx_mod) != 0) in ale_init_locked()
2679 if (ALE_USECS(sc->ale_int_tx_mod) != 0) in ale_init_locked()
2686 sc->ale_max_frame_size = ETHERMTU; in ale_init_locked()
2688 sc->ale_max_frame_size = if_getmtu(ifp); in ale_init_locked()
2689 sc->ale_max_frame_size += ETHER_HDR_LEN + ETHER_VLAN_ENCAP_LEN + in ale_init_locked()
2691 CSR_WRITE_4(sc, ALE_FRAME_SIZE, sc->ale_max_frame_size); in ale_init_locked()
2698 /* Set parameters for half-duplex media. */ in ale_init_locked()
2709 /* Configure Tx jumbo frame parameters. */ in ale_init_locked()
2710 if ((sc->ale_flags & ALE_FLAG_JUMBO) != 0) { in ale_init_locked()
2712 reg = sc->ale_max_frame_size; in ale_init_locked()
2714 reg = (sc->ale_max_frame_size * 2) / 3; in ale_init_locked()
2716 reg = sc->ale_max_frame_size / 2; in ale_init_locked()
2722 reg = (128 << (sc->ale_dma_rd_burst >> DMA_CFG_RD_BURST_SHIFT)) in ale_init_locked()
2729 if ((sc->ale_flags & ALE_FLAG_JUMBO) != 0) { in ale_init_locked()
2730 reg = roundup(sc->ale_max_frame_size, RX_JUMBO_THRESH_UNIT); in ale_init_locked()
2756 if ((sc->ale_flags & ALE_FLAG_TXCMB_BUG) == 0) in ale_init_locked()
2760 sc->ale_dma_rd_burst | reg | in ale_init_locked()
2761 sc->ale_dma_wr_burst | DMA_CFG_RXCMB_ENB | in ale_init_locked()
2778 * Configure Tx/Rx MACs. in ale_init_locked()
2779 * - Auto-padding for short frames. in ale_init_locked()
2780 * - Enable CRC generation. in ale_init_locked()
2791 if ((sc->ale_flags & ALE_FLAG_FASTETHER) != 0) in ale_init_locked()
2809 sc->ale_flags &= ~ALE_FLAG_LINK; in ale_init_locked()
2813 callout_reset(&sc->ale_tick_ch, hz, ale_tick, sc); in ale_init_locked()
2828 ifp = sc->ale_ifp; in ale_stop()
2830 sc->ale_flags &= ~ALE_FLAG_LINK; in ale_stop()
2831 callout_stop(&sc->ale_tick_ch); in ale_stop()
2832 sc->ale_watchdog_timer = 0; in ale_stop()
2848 /* Stop Rx/Tx MACs. */ in ale_stop()
2854 * Free TX mbufs still in the queues. in ale_stop()
2857 txd = &sc->ale_cdata.ale_txdesc[i]; in ale_stop()
2858 if (txd->tx_m != NULL) { in ale_stop()
2859 bus_dmamap_sync(sc->ale_cdata.ale_tx_tag, in ale_stop()
2860 txd->tx_dmamap, BUS_DMASYNC_POSTWRITE); in ale_stop()
2861 bus_dmamap_unload(sc->ale_cdata.ale_tx_tag, in ale_stop()
2862 txd->tx_dmamap); in ale_stop()
2863 m_freem(txd->tx_m); in ale_stop()
2864 txd->tx_m = NULL; in ale_stop()
2883 for (i = ALE_TIMEOUT; i > 0; i--) { in ale_stop_mac()
2890 device_printf(sc->ale_dev, in ale_stop_mac()
2891 "could not disable Tx/Rx MAC(0x%08x)!\n", reg); in ale_stop_mac()
2902 sc->ale_cdata.ale_tx_prod = 0; in ale_init_tx_ring()
2903 sc->ale_cdata.ale_tx_cons = 0; in ale_init_tx_ring()
2904 sc->ale_cdata.ale_tx_cnt = 0; in ale_init_tx_ring()
2906 bzero(sc->ale_cdata.ale_tx_ring, ALE_TX_RING_SZ); in ale_init_tx_ring()
2907 bzero(sc->ale_cdata.ale_tx_cmb, ALE_TX_CMB_SZ); in ale_init_tx_ring()
2909 txd = &sc->ale_cdata.ale_txdesc[i]; in ale_init_tx_ring()
2910 txd->tx_m = NULL; in ale_init_tx_ring()
2912 *sc->ale_cdata.ale_tx_cmb = 0; in ale_init_tx_ring()
2913 bus_dmamap_sync(sc->ale_cdata.ale_tx_cmb_tag, in ale_init_tx_ring()
2914 sc->ale_cdata.ale_tx_cmb_map, in ale_init_tx_ring()
2916 bus_dmamap_sync(sc->ale_cdata.ale_tx_ring_tag, in ale_init_tx_ring()
2917 sc->ale_cdata.ale_tx_ring_map, in ale_init_tx_ring()
2929 sc->ale_morework = 0; in ale_init_rx_pages()
2930 sc->ale_cdata.ale_rx_seqno = 0; in ale_init_rx_pages()
2931 sc->ale_cdata.ale_rx_curp = 0; in ale_init_rx_pages()
2934 rx_page = &sc->ale_cdata.ale_rx_page[i]; in ale_init_rx_pages()
2935 bzero(rx_page->page_addr, sc->ale_pagesize); in ale_init_rx_pages()
2936 bzero(rx_page->cmb_addr, ALE_RX_CMB_SZ); in ale_init_rx_pages()
2937 rx_page->cons = 0; in ale_init_rx_pages()
2938 *rx_page->cmb_addr = 0; in ale_init_rx_pages()
2939 bus_dmamap_sync(rx_page->page_tag, rx_page->page_map, in ale_init_rx_pages()
2941 bus_dmamap_sync(rx_page->cmb_tag, rx_page->cmb_map, in ale_init_rx_pages()
2954 ifp = sc->ale_ifp; in ale_rxvlan()
2982 ifp = sc->ale_ifp; in ale_rxfilter()
3017 if (error || req->newptr == NULL) in sysctl_int_range()