18691632fSRavi Kumar /* SPDX-License-Identifier: BSD-3-Clause 28691632fSRavi Kumar * Copyright(c) 2018 Advanced Micro Devices, Inc. All rights reserved. 38691632fSRavi Kumar * Copyright(c) 2018 Synopsys, Inc. All rights reserved. 48691632fSRavi Kumar */ 58691632fSRavi Kumar 69e890103SRavi Kumar #include "axgbe_rxtx.h" 78691632fSRavi Kumar #include "axgbe_ethdev.h" 8572890efSRavi Kumar #include "axgbe_common.h" 9572890efSRavi Kumar #include "axgbe_phy.h" 10df4867cdSChandu Babu N #include "axgbe_regs.h" 118691632fSRavi Kumar 128691632fSRavi Kumar static int eth_axgbe_dev_init(struct rte_eth_dev *eth_dev); 138691632fSRavi Kumar static int eth_axgbe_dev_uninit(struct rte_eth_dev *eth_dev); 147c4158a5SRavi Kumar static int axgbe_dev_configure(struct rte_eth_dev *dev); 157c4158a5SRavi Kumar static int axgbe_dev_start(struct rte_eth_dev *dev); 167c4158a5SRavi Kumar static void axgbe_dev_stop(struct rte_eth_dev *dev); 17456ff159SRavi Kumar static void axgbe_dev_interrupt_handler(void *param); 189e890103SRavi Kumar static void axgbe_dev_close(struct rte_eth_dev *dev); 199039c812SAndrew Rybchenko static int axgbe_dev_promiscuous_enable(struct rte_eth_dev *dev); 209039c812SAndrew Rybchenko static int axgbe_dev_promiscuous_disable(struct rte_eth_dev *dev); 21ca041cd4SIvan Ilchenko static int axgbe_dev_allmulticast_enable(struct rte_eth_dev *dev); 22ca041cd4SIvan Ilchenko static int axgbe_dev_allmulticast_disable(struct rte_eth_dev *dev); 2349a5e622SChandu Babu N static int axgbe_dev_mac_addr_set(struct rte_eth_dev *dev, 2449a5e622SChandu Babu N struct rte_ether_addr *mac_addr); 2549a5e622SChandu Babu N static int axgbe_dev_mac_addr_add(struct rte_eth_dev *dev, 2649a5e622SChandu Babu N struct rte_ether_addr *mac_addr, 2749a5e622SChandu Babu N uint32_t index, 2849a5e622SChandu Babu N uint32_t vmdq); 2949a5e622SChandu Babu N static void axgbe_dev_mac_addr_remove(struct rte_eth_dev *dev, uint32_t index); 3049a5e622SChandu Babu N static int axgbe_dev_set_mc_addr_list(struct rte_eth_dev *dev, 3149a5e622SChandu Babu N struct rte_ether_addr *mc_addr_set, 3249a5e622SChandu Babu N uint32_t nb_mc_addr); 33e01d9b2eSChandu Babu N static int axgbe_dev_uc_hash_table_set(struct rte_eth_dev *dev, 34e01d9b2eSChandu Babu N struct rte_ether_addr *mac_addr, 35e01d9b2eSChandu Babu N uint8_t add); 36e01d9b2eSChandu Babu N static int axgbe_dev_uc_all_hash_table_set(struct rte_eth_dev *dev, 37e01d9b2eSChandu Babu N uint8_t add); 3844d45ffeSRavi Kumar static int axgbe_dev_link_update(struct rte_eth_dev *dev, 3944d45ffeSRavi Kumar int wait_to_complete); 40df4867cdSChandu Babu N static int axgbe_dev_get_regs(struct rte_eth_dev *dev, 41df4867cdSChandu Babu N struct rte_dev_reg_info *regs); 423e730511SRavi Kumar static int axgbe_dev_stats_get(struct rte_eth_dev *dev, 433e730511SRavi Kumar struct rte_eth_stats *stats); 449970a9adSIgor Romanov static int axgbe_dev_stats_reset(struct rte_eth_dev *dev); 459d1ef6b2SChandu Babu N static int axgbe_dev_xstats_get(struct rte_eth_dev *dev, 469d1ef6b2SChandu Babu N struct rte_eth_xstat *stats, 479d1ef6b2SChandu Babu N unsigned int n); 489d1ef6b2SChandu Babu N static int 499d1ef6b2SChandu Babu N axgbe_dev_xstats_get_names(struct rte_eth_dev *dev, 509d1ef6b2SChandu Babu N struct rte_eth_xstat_name *xstats_names, 519d1ef6b2SChandu Babu N unsigned int size); 529d1ef6b2SChandu Babu N static int 539d1ef6b2SChandu Babu N axgbe_dev_xstats_get_by_id(struct rte_eth_dev *dev, 549d1ef6b2SChandu Babu N const uint64_t *ids, 559d1ef6b2SChandu Babu N uint64_t *values, 569d1ef6b2SChandu Babu N unsigned int n); 579d1ef6b2SChandu Babu N static int 589d1ef6b2SChandu Babu N axgbe_dev_xstats_get_names_by_id(struct rte_eth_dev *dev, 599d1ef6b2SChandu Babu N struct rte_eth_xstat_name *xstats_names, 609d1ef6b2SChandu Babu N const uint64_t *ids, 619d1ef6b2SChandu Babu N unsigned int size); 629d1ef6b2SChandu Babu N static int axgbe_dev_xstats_reset(struct rte_eth_dev *dev); 63bdad90d1SIvan Ilchenko static int axgbe_dev_info_get(struct rte_eth_dev *dev, 649e890103SRavi Kumar struct rte_eth_dev_info *dev_info); 65cf97f33eSAmaranath Somalapuram static int axgbe_flow_ctrl_get(struct rte_eth_dev *dev, 66cf97f33eSAmaranath Somalapuram struct rte_eth_fc_conf *fc_conf); 67cf97f33eSAmaranath Somalapuram static int axgbe_flow_ctrl_set(struct rte_eth_dev *dev, 68cf97f33eSAmaranath Somalapuram struct rte_eth_fc_conf *fc_conf); 69e0543d4eSAmaranath Somalapuram static int axgbe_priority_flow_ctrl_set(struct rte_eth_dev *dev, 70e0543d4eSAmaranath Somalapuram struct rte_eth_pfc_conf *pfc_conf); 717aed95c9SAmaranath Somalapuram static void axgbe_rxq_info_get(struct rte_eth_dev *dev, uint16_t queue_id, 727aed95c9SAmaranath Somalapuram struct rte_eth_rxq_info *qinfo); 737aed95c9SAmaranath Somalapuram static void axgbe_txq_info_get(struct rte_eth_dev *dev, uint16_t queue_id, 747aed95c9SAmaranath Somalapuram struct rte_eth_txq_info *qinfo); 75*410cf087SAmaranath Somalapuram const uint32_t *axgbe_dev_supported_ptypes_get(struct rte_eth_dev *dev); 768691632fSRavi Kumar 779d1ef6b2SChandu Babu N struct axgbe_xstats { 789d1ef6b2SChandu Babu N char name[RTE_ETH_XSTATS_NAME_SIZE]; 799d1ef6b2SChandu Babu N int offset; 809d1ef6b2SChandu Babu N }; 819d1ef6b2SChandu Babu N 829d1ef6b2SChandu Babu N #define AXGMAC_MMC_STAT(_string, _var) \ 839d1ef6b2SChandu Babu N { _string, \ 849d1ef6b2SChandu Babu N offsetof(struct axgbe_mmc_stats, _var), \ 859d1ef6b2SChandu Babu N } 869d1ef6b2SChandu Babu N 879d1ef6b2SChandu Babu N static const struct axgbe_xstats axgbe_xstats_strings[] = { 889d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("tx_bytes", txoctetcount_gb), 899d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("tx_packets", txframecount_gb), 909d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("tx_unicast_packets", txunicastframes_gb), 919d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("tx_broadcast_packets", txbroadcastframes_gb), 929d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("tx_multicast_packets", txmulticastframes_gb), 939d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("tx_vlan_packets", txvlanframes_g), 949d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("tx_64_byte_packets", tx64octets_gb), 959d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("tx_65_to_127_byte_packets", tx65to127octets_gb), 969d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("tx_128_to_255_byte_packets", tx128to255octets_gb), 979d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("tx_256_to_511_byte_packets", tx256to511octets_gb), 989d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("tx_512_to_1023_byte_packets", tx512to1023octets_gb), 999d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("tx_1024_to_max_byte_packets", tx1024tomaxoctets_gb), 1009d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("tx_underflow_errors", txunderflowerror), 1019d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("tx_pause_frames", txpauseframes), 1029d1ef6b2SChandu Babu N 1039d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_bytes", rxoctetcount_gb), 1049d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_packets", rxframecount_gb), 1059d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_unicast_packets", rxunicastframes_g), 1069d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_broadcast_packets", rxbroadcastframes_g), 1079d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_multicast_packets", rxmulticastframes_g), 1089d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_vlan_packets", rxvlanframes_gb), 1099d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_64_byte_packets", rx64octets_gb), 1109d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_65_to_127_byte_packets", rx65to127octets_gb), 1119d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_128_to_255_byte_packets", rx128to255octets_gb), 1129d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_256_to_511_byte_packets", rx256to511octets_gb), 1139d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_512_to_1023_byte_packets", rx512to1023octets_gb), 1149d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_1024_to_max_byte_packets", rx1024tomaxoctets_gb), 1159d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_undersize_packets", rxundersize_g), 1169d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_oversize_packets", rxoversize_g), 1179d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_crc_errors", rxcrcerror), 1189d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_crc_errors_small_packets", rxrunterror), 1199d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_crc_errors_giant_packets", rxjabbererror), 1209d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_length_errors", rxlengtherror), 1219d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_out_of_range_errors", rxoutofrangetype), 1229d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_fifo_overflow_errors", rxfifooverflow), 1239d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_watchdog_errors", rxwatchdogerror), 1249d1ef6b2SChandu Babu N AXGMAC_MMC_STAT("rx_pause_frames", rxpauseframes), 1259d1ef6b2SChandu Babu N }; 1269d1ef6b2SChandu Babu N 1279d1ef6b2SChandu Babu N #define AXGBE_XSTATS_COUNT ARRAY_SIZE(axgbe_xstats_strings) 1289d1ef6b2SChandu Babu N 1298691632fSRavi Kumar /* The set of PCI devices this driver supports */ 1308691632fSRavi Kumar #define AMD_PCI_VENDOR_ID 0x1022 131991e0b1dSSelwin Sebastian #define AMD_PCI_RV_ROOT_COMPLEX_ID 0x15d0 1328691632fSRavi Kumar #define AMD_PCI_AXGBE_DEVICE_V2A 0x1458 1338691632fSRavi Kumar #define AMD_PCI_AXGBE_DEVICE_V2B 0x1459 1348691632fSRavi Kumar 1358691632fSRavi Kumar int axgbe_logtype_init; 1368691632fSRavi Kumar int axgbe_logtype_driver; 1378691632fSRavi Kumar 1388691632fSRavi Kumar static const struct rte_pci_id pci_id_axgbe_map[] = { 1398691632fSRavi Kumar {RTE_PCI_DEVICE(AMD_PCI_VENDOR_ID, AMD_PCI_AXGBE_DEVICE_V2A)}, 1408691632fSRavi Kumar {RTE_PCI_DEVICE(AMD_PCI_VENDOR_ID, AMD_PCI_AXGBE_DEVICE_V2B)}, 1418691632fSRavi Kumar { .vendor_id = 0, }, 1428691632fSRavi Kumar }; 1438691632fSRavi Kumar 144572890efSRavi Kumar static struct axgbe_version_data axgbe_v2a = { 1454ac7516bSRavi Kumar .init_function_ptrs_phy_impl = axgbe_init_function_ptrs_phy_v2, 146572890efSRavi Kumar .xpcs_access = AXGBE_XPCS_ACCESS_V2, 147572890efSRavi Kumar .mmc_64bit = 1, 148572890efSRavi Kumar .tx_max_fifo_size = 229376, 149572890efSRavi Kumar .rx_max_fifo_size = 229376, 150572890efSRavi Kumar .tx_tstamp_workaround = 1, 151572890efSRavi Kumar .ecc_support = 1, 152572890efSRavi Kumar .i2c_support = 1, 15300072056SRavi Kumar .an_cdr_workaround = 1, 154572890efSRavi Kumar }; 155572890efSRavi Kumar 156572890efSRavi Kumar static struct axgbe_version_data axgbe_v2b = { 1574ac7516bSRavi Kumar .init_function_ptrs_phy_impl = axgbe_init_function_ptrs_phy_v2, 158572890efSRavi Kumar .xpcs_access = AXGBE_XPCS_ACCESS_V2, 159572890efSRavi Kumar .mmc_64bit = 1, 160572890efSRavi Kumar .tx_max_fifo_size = 65536, 161572890efSRavi Kumar .rx_max_fifo_size = 65536, 162572890efSRavi Kumar .tx_tstamp_workaround = 1, 163572890efSRavi Kumar .ecc_support = 1, 164572890efSRavi Kumar .i2c_support = 1, 16500072056SRavi Kumar .an_cdr_workaround = 1, 166572890efSRavi Kumar }; 167572890efSRavi Kumar 1689e890103SRavi Kumar static const struct rte_eth_desc_lim rx_desc_lim = { 1699e890103SRavi Kumar .nb_max = AXGBE_MAX_RING_DESC, 1709e890103SRavi Kumar .nb_min = AXGBE_MIN_RING_DESC, 1719e890103SRavi Kumar .nb_align = 8, 1729e890103SRavi Kumar }; 1739e890103SRavi Kumar 1749e890103SRavi Kumar static const struct rte_eth_desc_lim tx_desc_lim = { 1759e890103SRavi Kumar .nb_max = AXGBE_MAX_RING_DESC, 1769e890103SRavi Kumar .nb_min = AXGBE_MIN_RING_DESC, 1779e890103SRavi Kumar .nb_align = 8, 1789e890103SRavi Kumar }; 1799e890103SRavi Kumar 1809e890103SRavi Kumar static const struct eth_dev_ops axgbe_eth_dev_ops = { 1817c4158a5SRavi Kumar .dev_configure = axgbe_dev_configure, 1827c4158a5SRavi Kumar .dev_start = axgbe_dev_start, 1837c4158a5SRavi Kumar .dev_stop = axgbe_dev_stop, 1849e890103SRavi Kumar .dev_close = axgbe_dev_close, 185fa3e0440SRavi Kumar .promiscuous_enable = axgbe_dev_promiscuous_enable, 186fa3e0440SRavi Kumar .promiscuous_disable = axgbe_dev_promiscuous_disable, 187fa3e0440SRavi Kumar .allmulticast_enable = axgbe_dev_allmulticast_enable, 188fa3e0440SRavi Kumar .allmulticast_disable = axgbe_dev_allmulticast_disable, 18949a5e622SChandu Babu N .mac_addr_set = axgbe_dev_mac_addr_set, 19049a5e622SChandu Babu N .mac_addr_add = axgbe_dev_mac_addr_add, 19149a5e622SChandu Babu N .mac_addr_remove = axgbe_dev_mac_addr_remove, 19249a5e622SChandu Babu N .set_mc_addr_list = axgbe_dev_set_mc_addr_list, 193e01d9b2eSChandu Babu N .uc_hash_table_set = axgbe_dev_uc_hash_table_set, 194e01d9b2eSChandu Babu N .uc_all_hash_table_set = axgbe_dev_uc_all_hash_table_set, 19544d45ffeSRavi Kumar .link_update = axgbe_dev_link_update, 196df4867cdSChandu Babu N .get_reg = axgbe_dev_get_regs, 1973e730511SRavi Kumar .stats_get = axgbe_dev_stats_get, 1983e730511SRavi Kumar .stats_reset = axgbe_dev_stats_reset, 1999d1ef6b2SChandu Babu N .xstats_get = axgbe_dev_xstats_get, 2009d1ef6b2SChandu Babu N .xstats_reset = axgbe_dev_xstats_reset, 2019d1ef6b2SChandu Babu N .xstats_get_names = axgbe_dev_xstats_get_names, 2029d1ef6b2SChandu Babu N .xstats_get_names_by_id = axgbe_dev_xstats_get_names_by_id, 2039d1ef6b2SChandu Babu N .xstats_get_by_id = axgbe_dev_xstats_get_by_id, 2049e890103SRavi Kumar .dev_infos_get = axgbe_dev_info_get, 2059e890103SRavi Kumar .rx_queue_setup = axgbe_dev_rx_queue_setup, 2069e890103SRavi Kumar .rx_queue_release = axgbe_dev_rx_queue_release, 2079e890103SRavi Kumar .tx_queue_setup = axgbe_dev_tx_queue_setup, 2089e890103SRavi Kumar .tx_queue_release = axgbe_dev_tx_queue_release, 209cf97f33eSAmaranath Somalapuram .flow_ctrl_get = axgbe_flow_ctrl_get, 210cf97f33eSAmaranath Somalapuram .flow_ctrl_set = axgbe_flow_ctrl_set, 211e0543d4eSAmaranath Somalapuram .priority_flow_ctrl_set = axgbe_priority_flow_ctrl_set, 2127aed95c9SAmaranath Somalapuram .rxq_info_get = axgbe_rxq_info_get, 2137aed95c9SAmaranath Somalapuram .txq_info_get = axgbe_txq_info_get, 214*410cf087SAmaranath Somalapuram .dev_supported_ptypes_get = axgbe_dev_supported_ptypes_get, 2159e890103SRavi Kumar }; 2169e890103SRavi Kumar 2177c4158a5SRavi Kumar static int axgbe_phy_reset(struct axgbe_port *pdata) 2187c4158a5SRavi Kumar { 2197c4158a5SRavi Kumar pdata->phy_link = -1; 2207c4158a5SRavi Kumar pdata->phy_speed = SPEED_UNKNOWN; 2217c4158a5SRavi Kumar return pdata->phy_if.phy_reset(pdata); 2227c4158a5SRavi Kumar } 2237c4158a5SRavi Kumar 224456ff159SRavi Kumar /* 225456ff159SRavi Kumar * Interrupt handler triggered by NIC for handling 226456ff159SRavi Kumar * specific interrupt. 227456ff159SRavi Kumar * 228456ff159SRavi Kumar * @param handle 229456ff159SRavi Kumar * Pointer to interrupt handle. 230456ff159SRavi Kumar * @param param 231456ff159SRavi Kumar * The address of parameter (struct rte_eth_dev *) regsitered before. 232456ff159SRavi Kumar * 233456ff159SRavi Kumar * @return 234456ff159SRavi Kumar * void 235456ff159SRavi Kumar */ 236456ff159SRavi Kumar static void 237456ff159SRavi Kumar axgbe_dev_interrupt_handler(void *param) 238456ff159SRavi Kumar { 239456ff159SRavi Kumar struct rte_eth_dev *dev = (struct rte_eth_dev *)param; 240456ff159SRavi Kumar struct axgbe_port *pdata = dev->data->dev_private; 2418590b93dSRavi Kumar unsigned int dma_isr, dma_ch_isr; 242456ff159SRavi Kumar 243456ff159SRavi Kumar pdata->phy_if.an_isr(pdata); 2448590b93dSRavi Kumar /*DMA related interrupts*/ 2458590b93dSRavi Kumar dma_isr = AXGMAC_IOREAD(pdata, DMA_ISR); 2464216cdc0SChandu Babu N PMD_DRV_LOG(DEBUG, "DMA_ISR=%#010x\n", dma_isr); 2478590b93dSRavi Kumar if (dma_isr) { 2488590b93dSRavi Kumar if (dma_isr & 1) { 2498590b93dSRavi Kumar dma_ch_isr = 2508590b93dSRavi Kumar AXGMAC_DMA_IOREAD((struct axgbe_rx_queue *) 2518590b93dSRavi Kumar pdata->rx_queues[0], 2528590b93dSRavi Kumar DMA_CH_SR); 2534216cdc0SChandu Babu N PMD_DRV_LOG(DEBUG, "DMA_CH0_ISR=%#010x\n", dma_ch_isr); 2548590b93dSRavi Kumar AXGMAC_DMA_IOWRITE((struct axgbe_rx_queue *) 2558590b93dSRavi Kumar pdata->rx_queues[0], 2568590b93dSRavi Kumar DMA_CH_SR, dma_ch_isr); 2578590b93dSRavi Kumar } 2588590b93dSRavi Kumar } 2596bee9d5fSNithin Dabilpuram /* Unmask interrupts since disabled after generation */ 2606bee9d5fSNithin Dabilpuram rte_intr_ack(&pdata->pci_dev->intr_handle); 261456ff159SRavi Kumar } 262456ff159SRavi Kumar 2637c4158a5SRavi Kumar /* 2647c4158a5SRavi Kumar * Configure device link speed and setup link. 2657c4158a5SRavi Kumar * It returns 0 on success. 2667c4158a5SRavi Kumar */ 2677c4158a5SRavi Kumar static int 2687c4158a5SRavi Kumar axgbe_dev_configure(struct rte_eth_dev *dev) 2697c4158a5SRavi Kumar { 2707c4158a5SRavi Kumar struct axgbe_port *pdata = dev->data->dev_private; 2717c4158a5SRavi Kumar /* Checksum offload to hardware */ 2727c4158a5SRavi Kumar pdata->rx_csum_enable = dev->data->dev_conf.rxmode.offloads & 2737c4158a5SRavi Kumar DEV_RX_OFFLOAD_CHECKSUM; 2747c4158a5SRavi Kumar return 0; 2757c4158a5SRavi Kumar } 2767c4158a5SRavi Kumar 2777c4158a5SRavi Kumar static int 2787c4158a5SRavi Kumar axgbe_dev_rx_mq_config(struct rte_eth_dev *dev) 2797c4158a5SRavi Kumar { 2800bc212a8SStephen Hemminger struct axgbe_port *pdata = dev->data->dev_private; 2817c4158a5SRavi Kumar 2827c4158a5SRavi Kumar if (dev->data->dev_conf.rxmode.mq_mode == ETH_MQ_RX_RSS) 2837c4158a5SRavi Kumar pdata->rss_enable = 1; 2847c4158a5SRavi Kumar else if (dev->data->dev_conf.rxmode.mq_mode == ETH_MQ_RX_NONE) 2857c4158a5SRavi Kumar pdata->rss_enable = 0; 2867c4158a5SRavi Kumar else 2877c4158a5SRavi Kumar return -1; 2887c4158a5SRavi Kumar return 0; 2897c4158a5SRavi Kumar } 2907c4158a5SRavi Kumar 2917c4158a5SRavi Kumar static int 2927c4158a5SRavi Kumar axgbe_dev_start(struct rte_eth_dev *dev) 2937c4158a5SRavi Kumar { 2940bc212a8SStephen Hemminger struct axgbe_port *pdata = dev->data->dev_private; 2957c4158a5SRavi Kumar int ret; 296965b3127SSelwin Sebastian struct rte_eth_dev_data *dev_data = dev->data; 297965b3127SSelwin Sebastian uint16_t max_pkt_len = dev_data->dev_conf.rxmode.max_rx_pkt_len; 298965b3127SSelwin Sebastian 299965b3127SSelwin Sebastian dev->dev_ops = &axgbe_eth_dev_ops; 3007c4158a5SRavi Kumar 3010bc212a8SStephen Hemminger PMD_INIT_FUNC_TRACE(); 3020bc212a8SStephen Hemminger 3037c4158a5SRavi Kumar /* Multiqueue RSS */ 3047c4158a5SRavi Kumar ret = axgbe_dev_rx_mq_config(dev); 3057c4158a5SRavi Kumar if (ret) { 3067c4158a5SRavi Kumar PMD_DRV_LOG(ERR, "Unable to config RX MQ\n"); 3077c4158a5SRavi Kumar return ret; 3087c4158a5SRavi Kumar } 3097c4158a5SRavi Kumar ret = axgbe_phy_reset(pdata); 3107c4158a5SRavi Kumar if (ret) { 3117c4158a5SRavi Kumar PMD_DRV_LOG(ERR, "phy reset failed\n"); 3127c4158a5SRavi Kumar return ret; 3137c4158a5SRavi Kumar } 3147c4158a5SRavi Kumar ret = pdata->hw_if.init(pdata); 3157c4158a5SRavi Kumar if (ret) { 3167c4158a5SRavi Kumar PMD_DRV_LOG(ERR, "dev_init failed\n"); 3177c4158a5SRavi Kumar return ret; 3187c4158a5SRavi Kumar } 3197c4158a5SRavi Kumar 3207c4158a5SRavi Kumar /* enable uio/vfio intr/eventfd mapping */ 3217c4158a5SRavi Kumar rte_intr_enable(&pdata->pci_dev->intr_handle); 3227c4158a5SRavi Kumar 3237c4158a5SRavi Kumar /* phy start*/ 3247c4158a5SRavi Kumar pdata->phy_if.phy_start(pdata); 3258590b93dSRavi Kumar axgbe_dev_enable_tx(dev); 3268590b93dSRavi Kumar axgbe_dev_enable_rx(dev); 3277c4158a5SRavi Kumar 3287c4158a5SRavi Kumar axgbe_clear_bit(AXGBE_STOPPED, &pdata->dev_state); 3297c4158a5SRavi Kumar axgbe_clear_bit(AXGBE_DOWN, &pdata->dev_state); 330965b3127SSelwin Sebastian if ((dev_data->dev_conf.rxmode.offloads & DEV_RX_OFFLOAD_SCATTER) || 331965b3127SSelwin Sebastian max_pkt_len > pdata->rx_buf_size) 332965b3127SSelwin Sebastian dev_data->scattered_rx = 1; 333965b3127SSelwin Sebastian 334965b3127SSelwin Sebastian /* Scatter Rx handling */ 335965b3127SSelwin Sebastian if (dev_data->scattered_rx) 336965b3127SSelwin Sebastian dev->rx_pkt_burst = ð_axgbe_recv_scattered_pkts; 337965b3127SSelwin Sebastian else 338965b3127SSelwin Sebastian dev->rx_pkt_burst = &axgbe_recv_pkts; 339965b3127SSelwin Sebastian 3407c4158a5SRavi Kumar return 0; 3417c4158a5SRavi Kumar } 3427c4158a5SRavi Kumar 3437c4158a5SRavi Kumar /* Stop device: disable rx and tx functions to allow for reconfiguring. */ 3447c4158a5SRavi Kumar static void 3457c4158a5SRavi Kumar axgbe_dev_stop(struct rte_eth_dev *dev) 3467c4158a5SRavi Kumar { 3477c4158a5SRavi Kumar struct axgbe_port *pdata = dev->data->dev_private; 3487c4158a5SRavi Kumar 3490bc212a8SStephen Hemminger PMD_INIT_FUNC_TRACE(); 3500bc212a8SStephen Hemminger 3517c4158a5SRavi Kumar rte_intr_disable(&pdata->pci_dev->intr_handle); 3527c4158a5SRavi Kumar 3537c4158a5SRavi Kumar if (axgbe_test_bit(AXGBE_STOPPED, &pdata->dev_state)) 3547c4158a5SRavi Kumar return; 3557c4158a5SRavi Kumar 3567c4158a5SRavi Kumar axgbe_set_bit(AXGBE_STOPPED, &pdata->dev_state); 3578590b93dSRavi Kumar axgbe_dev_disable_tx(dev); 3588590b93dSRavi Kumar axgbe_dev_disable_rx(dev); 3597c4158a5SRavi Kumar 3607c4158a5SRavi Kumar pdata->phy_if.phy_stop(pdata); 3617c4158a5SRavi Kumar pdata->hw_if.exit(pdata); 3627c4158a5SRavi Kumar memset(&dev->data->dev_link, 0, sizeof(struct rte_eth_link)); 3637c4158a5SRavi Kumar axgbe_set_bit(AXGBE_DOWN, &pdata->dev_state); 3647c4158a5SRavi Kumar } 3657c4158a5SRavi Kumar 3669e890103SRavi Kumar /* Clear all resources like TX/RX queues. */ 3679e890103SRavi Kumar static void 3689e890103SRavi Kumar axgbe_dev_close(struct rte_eth_dev *dev) 3699e890103SRavi Kumar { 3709e890103SRavi Kumar axgbe_dev_clear_queues(dev); 3719e890103SRavi Kumar } 3729e890103SRavi Kumar 3739039c812SAndrew Rybchenko static int 374fa3e0440SRavi Kumar axgbe_dev_promiscuous_enable(struct rte_eth_dev *dev) 375fa3e0440SRavi Kumar { 376fa3e0440SRavi Kumar struct axgbe_port *pdata = dev->data->dev_private; 377fa3e0440SRavi Kumar 3780bc212a8SStephen Hemminger PMD_INIT_FUNC_TRACE(); 3790bc212a8SStephen Hemminger 380fa3e0440SRavi Kumar AXGMAC_IOWRITE_BITS(pdata, MAC_PFR, PR, 1); 3819039c812SAndrew Rybchenko 3829039c812SAndrew Rybchenko return 0; 383fa3e0440SRavi Kumar } 384fa3e0440SRavi Kumar 3859039c812SAndrew Rybchenko static int 386fa3e0440SRavi Kumar axgbe_dev_promiscuous_disable(struct rte_eth_dev *dev) 387fa3e0440SRavi Kumar { 388fa3e0440SRavi Kumar struct axgbe_port *pdata = dev->data->dev_private; 389fa3e0440SRavi Kumar 3900bc212a8SStephen Hemminger PMD_INIT_FUNC_TRACE(); 3910bc212a8SStephen Hemminger 392fa3e0440SRavi Kumar AXGMAC_IOWRITE_BITS(pdata, MAC_PFR, PR, 0); 3939039c812SAndrew Rybchenko 3949039c812SAndrew Rybchenko return 0; 395fa3e0440SRavi Kumar } 396fa3e0440SRavi Kumar 397ca041cd4SIvan Ilchenko static int 398fa3e0440SRavi Kumar axgbe_dev_allmulticast_enable(struct rte_eth_dev *dev) 399fa3e0440SRavi Kumar { 400fa3e0440SRavi Kumar struct axgbe_port *pdata = dev->data->dev_private; 401fa3e0440SRavi Kumar 4020bc212a8SStephen Hemminger PMD_INIT_FUNC_TRACE(); 4030bc212a8SStephen Hemminger 404fa3e0440SRavi Kumar if (AXGMAC_IOREAD_BITS(pdata, MAC_PFR, PM)) 405ca041cd4SIvan Ilchenko return 0; 406fa3e0440SRavi Kumar AXGMAC_IOWRITE_BITS(pdata, MAC_PFR, PM, 1); 407ca041cd4SIvan Ilchenko 408ca041cd4SIvan Ilchenko return 0; 409fa3e0440SRavi Kumar } 410fa3e0440SRavi Kumar 411ca041cd4SIvan Ilchenko static int 412fa3e0440SRavi Kumar axgbe_dev_allmulticast_disable(struct rte_eth_dev *dev) 413fa3e0440SRavi Kumar { 414fa3e0440SRavi Kumar struct axgbe_port *pdata = dev->data->dev_private; 415fa3e0440SRavi Kumar 4160bc212a8SStephen Hemminger PMD_INIT_FUNC_TRACE(); 4170bc212a8SStephen Hemminger 418fa3e0440SRavi Kumar if (!AXGMAC_IOREAD_BITS(pdata, MAC_PFR, PM)) 419ca041cd4SIvan Ilchenko return 0; 420fa3e0440SRavi Kumar AXGMAC_IOWRITE_BITS(pdata, MAC_PFR, PM, 0); 421ca041cd4SIvan Ilchenko 422ca041cd4SIvan Ilchenko return 0; 423fa3e0440SRavi Kumar } 424fa3e0440SRavi Kumar 42549a5e622SChandu Babu N static int 42649a5e622SChandu Babu N axgbe_dev_mac_addr_set(struct rte_eth_dev *dev, struct rte_ether_addr *mac_addr) 42749a5e622SChandu Babu N { 42849a5e622SChandu Babu N struct axgbe_port *pdata = dev->data->dev_private; 42949a5e622SChandu Babu N 43049a5e622SChandu Babu N /* Set Default MAC Addr */ 43149a5e622SChandu Babu N axgbe_set_mac_addn_addr(pdata, (u8 *)mac_addr, 0); 43249a5e622SChandu Babu N 43349a5e622SChandu Babu N return 0; 43449a5e622SChandu Babu N } 43549a5e622SChandu Babu N 43649a5e622SChandu Babu N static int 43749a5e622SChandu Babu N axgbe_dev_mac_addr_add(struct rte_eth_dev *dev, struct rte_ether_addr *mac_addr, 43849a5e622SChandu Babu N uint32_t index, uint32_t pool __rte_unused) 43949a5e622SChandu Babu N { 44049a5e622SChandu Babu N struct axgbe_port *pdata = dev->data->dev_private; 44149a5e622SChandu Babu N struct axgbe_hw_features *hw_feat = &pdata->hw_feat; 44249a5e622SChandu Babu N 44349a5e622SChandu Babu N if (index > hw_feat->addn_mac) { 44449a5e622SChandu Babu N PMD_DRV_LOG(ERR, "Invalid Index %d\n", index); 44549a5e622SChandu Babu N return -EINVAL; 44649a5e622SChandu Babu N } 44749a5e622SChandu Babu N axgbe_set_mac_addn_addr(pdata, (u8 *)mac_addr, index); 44849a5e622SChandu Babu N return 0; 44949a5e622SChandu Babu N } 45049a5e622SChandu Babu N 45149a5e622SChandu Babu N static void 45249a5e622SChandu Babu N axgbe_dev_mac_addr_remove(struct rte_eth_dev *dev, uint32_t index) 45349a5e622SChandu Babu N { 45449a5e622SChandu Babu N struct axgbe_port *pdata = dev->data->dev_private; 45549a5e622SChandu Babu N struct axgbe_hw_features *hw_feat = &pdata->hw_feat; 45649a5e622SChandu Babu N 45749a5e622SChandu Babu N if (index > hw_feat->addn_mac) { 45849a5e622SChandu Babu N PMD_DRV_LOG(ERR, "Invalid Index %d\n", index); 45949a5e622SChandu Babu N return; 46049a5e622SChandu Babu N } 46149a5e622SChandu Babu N axgbe_set_mac_addn_addr(pdata, NULL, index); 46249a5e622SChandu Babu N } 46349a5e622SChandu Babu N 46449a5e622SChandu Babu N static int 46549a5e622SChandu Babu N axgbe_dev_set_mc_addr_list(struct rte_eth_dev *dev, 46649a5e622SChandu Babu N struct rte_ether_addr *mc_addr_set, 46749a5e622SChandu Babu N uint32_t nb_mc_addr) 46849a5e622SChandu Babu N { 46949a5e622SChandu Babu N struct axgbe_port *pdata = dev->data->dev_private; 47049a5e622SChandu Babu N struct axgbe_hw_features *hw_feat = &pdata->hw_feat; 47149a5e622SChandu Babu N uint32_t index = 1; /* 0 is always default mac */ 47249a5e622SChandu Babu N uint32_t i; 47349a5e622SChandu Babu N 47449a5e622SChandu Babu N if (nb_mc_addr > hw_feat->addn_mac) { 47549a5e622SChandu Babu N PMD_DRV_LOG(ERR, "Invalid Index %d\n", nb_mc_addr); 47649a5e622SChandu Babu N return -EINVAL; 47749a5e622SChandu Babu N } 47849a5e622SChandu Babu N 47949a5e622SChandu Babu N /* clear unicast addresses */ 48049a5e622SChandu Babu N for (i = 1; i < hw_feat->addn_mac; i++) { 48149a5e622SChandu Babu N if (rte_is_zero_ether_addr(&dev->data->mac_addrs[i])) 48249a5e622SChandu Babu N continue; 48349a5e622SChandu Babu N memset(&dev->data->mac_addrs[i], 0, 48449a5e622SChandu Babu N sizeof(struct rte_ether_addr)); 48549a5e622SChandu Babu N } 48649a5e622SChandu Babu N 48749a5e622SChandu Babu N while (nb_mc_addr--) 48849a5e622SChandu Babu N axgbe_set_mac_addn_addr(pdata, (u8 *)mc_addr_set++, index++); 48949a5e622SChandu Babu N 49049a5e622SChandu Babu N return 0; 49149a5e622SChandu Babu N } 49249a5e622SChandu Babu N 493e01d9b2eSChandu Babu N static int 494e01d9b2eSChandu Babu N axgbe_dev_uc_hash_table_set(struct rte_eth_dev *dev, 495e01d9b2eSChandu Babu N struct rte_ether_addr *mac_addr, uint8_t add) 496e01d9b2eSChandu Babu N { 497e01d9b2eSChandu Babu N struct axgbe_port *pdata = dev->data->dev_private; 498e01d9b2eSChandu Babu N struct axgbe_hw_features *hw_feat = &pdata->hw_feat; 499e01d9b2eSChandu Babu N 500e01d9b2eSChandu Babu N if (!hw_feat->hash_table_size) { 501e01d9b2eSChandu Babu N PMD_DRV_LOG(ERR, "MAC Hash Table not supported\n"); 502e01d9b2eSChandu Babu N return -ENOTSUP; 503e01d9b2eSChandu Babu N } 504e01d9b2eSChandu Babu N 505e01d9b2eSChandu Babu N axgbe_set_mac_hash_table(pdata, (u8 *)mac_addr, add); 506e01d9b2eSChandu Babu N 507e01d9b2eSChandu Babu N if (pdata->uc_hash_mac_addr > 0) { 508e01d9b2eSChandu Babu N AXGMAC_IOWRITE_BITS(pdata, MAC_PFR, HPF, 1); 509e01d9b2eSChandu Babu N AXGMAC_IOWRITE_BITS(pdata, MAC_PFR, HUC, 1); 510e01d9b2eSChandu Babu N } else { 511e01d9b2eSChandu Babu N AXGMAC_IOWRITE_BITS(pdata, MAC_PFR, HPF, 0); 512e01d9b2eSChandu Babu N AXGMAC_IOWRITE_BITS(pdata, MAC_PFR, HUC, 0); 513e01d9b2eSChandu Babu N } 514e01d9b2eSChandu Babu N return 0; 515e01d9b2eSChandu Babu N } 516e01d9b2eSChandu Babu N 517e01d9b2eSChandu Babu N static int 518e01d9b2eSChandu Babu N axgbe_dev_uc_all_hash_table_set(struct rte_eth_dev *dev, uint8_t add) 519e01d9b2eSChandu Babu N { 520e01d9b2eSChandu Babu N struct axgbe_port *pdata = dev->data->dev_private; 521e01d9b2eSChandu Babu N struct axgbe_hw_features *hw_feat = &pdata->hw_feat; 522e01d9b2eSChandu Babu N uint32_t index; 523e01d9b2eSChandu Babu N 524e01d9b2eSChandu Babu N if (!hw_feat->hash_table_size) { 525e01d9b2eSChandu Babu N PMD_DRV_LOG(ERR, "MAC Hash Table not supported\n"); 526e01d9b2eSChandu Babu N return -ENOTSUP; 527e01d9b2eSChandu Babu N } 528e01d9b2eSChandu Babu N 529e01d9b2eSChandu Babu N for (index = 0; index < pdata->hash_table_count; index++) { 530e01d9b2eSChandu Babu N if (add) 531e01d9b2eSChandu Babu N pdata->uc_hash_table[index] = ~0; 532e01d9b2eSChandu Babu N else 533e01d9b2eSChandu Babu N pdata->uc_hash_table[index] = 0; 534e01d9b2eSChandu Babu N 535e01d9b2eSChandu Babu N PMD_DRV_LOG(DEBUG, "%s MAC hash table at Index %#x\n", 536e01d9b2eSChandu Babu N add ? "set" : "clear", index); 537e01d9b2eSChandu Babu N 538e01d9b2eSChandu Babu N AXGMAC_IOWRITE(pdata, MAC_HTR(index), 539e01d9b2eSChandu Babu N pdata->uc_hash_table[index]); 540e01d9b2eSChandu Babu N } 541e01d9b2eSChandu Babu N 542e01d9b2eSChandu Babu N if (add) { 543e01d9b2eSChandu Babu N AXGMAC_IOWRITE_BITS(pdata, MAC_PFR, HPF, 1); 544e01d9b2eSChandu Babu N AXGMAC_IOWRITE_BITS(pdata, MAC_PFR, HUC, 1); 545e01d9b2eSChandu Babu N } else { 546e01d9b2eSChandu Babu N AXGMAC_IOWRITE_BITS(pdata, MAC_PFR, HPF, 0); 547e01d9b2eSChandu Babu N AXGMAC_IOWRITE_BITS(pdata, MAC_PFR, HUC, 0); 548e01d9b2eSChandu Babu N } 549e01d9b2eSChandu Babu N return 0; 550e01d9b2eSChandu Babu N } 551e01d9b2eSChandu Babu N 55244d45ffeSRavi Kumar /* return 0 means link status changed, -1 means not changed */ 55344d45ffeSRavi Kumar static int 55444d45ffeSRavi Kumar axgbe_dev_link_update(struct rte_eth_dev *dev, 55544d45ffeSRavi Kumar int wait_to_complete __rte_unused) 55644d45ffeSRavi Kumar { 55744d45ffeSRavi Kumar struct axgbe_port *pdata = dev->data->dev_private; 55844d45ffeSRavi Kumar struct rte_eth_link link; 55944d45ffeSRavi Kumar int ret = 0; 56044d45ffeSRavi Kumar 56144d45ffeSRavi Kumar PMD_INIT_FUNC_TRACE(); 56244d45ffeSRavi Kumar rte_delay_ms(800); 56344d45ffeSRavi Kumar 56444d45ffeSRavi Kumar pdata->phy_if.phy_status(pdata); 56544d45ffeSRavi Kumar 56644d45ffeSRavi Kumar memset(&link, 0, sizeof(struct rte_eth_link)); 56744d45ffeSRavi Kumar link.link_duplex = pdata->phy.duplex; 56844d45ffeSRavi Kumar link.link_status = pdata->phy_link; 56944d45ffeSRavi Kumar link.link_speed = pdata->phy_speed; 57044d45ffeSRavi Kumar link.link_autoneg = !(dev->data->dev_conf.link_speeds & 57144d45ffeSRavi Kumar ETH_LINK_SPEED_FIXED); 57244d45ffeSRavi Kumar ret = rte_eth_linkstatus_set(dev, &link); 57344d45ffeSRavi Kumar if (ret == -1) 57444d45ffeSRavi Kumar PMD_DRV_LOG(ERR, "No change in link status\n"); 57544d45ffeSRavi Kumar 57644d45ffeSRavi Kumar return ret; 57744d45ffeSRavi Kumar } 57844d45ffeSRavi Kumar 579df4867cdSChandu Babu N static int 580df4867cdSChandu Babu N axgbe_dev_get_regs(struct rte_eth_dev *dev, struct rte_dev_reg_info *regs) 581df4867cdSChandu Babu N { 582df4867cdSChandu Babu N struct axgbe_port *pdata = dev->data->dev_private; 583df4867cdSChandu Babu N 584df4867cdSChandu Babu N if (regs->data == NULL) { 585df4867cdSChandu Babu N regs->length = axgbe_regs_get_count(pdata); 586df4867cdSChandu Babu N regs->width = sizeof(uint32_t); 587df4867cdSChandu Babu N return 0; 588df4867cdSChandu Babu N } 589df4867cdSChandu Babu N 590df4867cdSChandu Babu N /* Only full register dump is supported */ 591df4867cdSChandu Babu N if (regs->length && 592df4867cdSChandu Babu N regs->length != (uint32_t)axgbe_regs_get_count(pdata)) 593df4867cdSChandu Babu N return -ENOTSUP; 594df4867cdSChandu Babu N 595df4867cdSChandu Babu N regs->version = pdata->pci_dev->id.vendor_id << 16 | 596df4867cdSChandu Babu N pdata->pci_dev->id.device_id; 597df4867cdSChandu Babu N axgbe_regs_dump(pdata, regs->data); 598df4867cdSChandu Babu N return 0; 599df4867cdSChandu Babu N } 6009d1ef6b2SChandu Babu N static void axgbe_read_mmc_stats(struct axgbe_port *pdata) 6019d1ef6b2SChandu Babu N { 6029d1ef6b2SChandu Babu N struct axgbe_mmc_stats *stats = &pdata->mmc_stats; 6039d1ef6b2SChandu Babu N 6049d1ef6b2SChandu Babu N /* Freeze counters */ 6059d1ef6b2SChandu Babu N AXGMAC_IOWRITE_BITS(pdata, MMC_CR, MCF, 1); 6069d1ef6b2SChandu Babu N 6079d1ef6b2SChandu Babu N /* Tx counters */ 6089d1ef6b2SChandu Babu N stats->txoctetcount_gb += 6099d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TXOCTETCOUNT_GB_LO); 6109d1ef6b2SChandu Babu N stats->txoctetcount_gb += 6119d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TXOCTETCOUNT_GB_HI) << 32); 6129d1ef6b2SChandu Babu N 6139d1ef6b2SChandu Babu N stats->txframecount_gb += 6149d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TXFRAMECOUNT_GB_LO); 6159d1ef6b2SChandu Babu N stats->txframecount_gb += 6169d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TXFRAMECOUNT_GB_HI) << 32); 6179d1ef6b2SChandu Babu N 6189d1ef6b2SChandu Babu N stats->txbroadcastframes_g += 6199d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TXBROADCASTFRAMES_G_LO); 6209d1ef6b2SChandu Babu N stats->txbroadcastframes_g += 6219d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TXBROADCASTFRAMES_G_HI) << 32); 6229d1ef6b2SChandu Babu N 6239d1ef6b2SChandu Babu N stats->txmulticastframes_g += 6249d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TXMULTICASTFRAMES_G_LO); 6259d1ef6b2SChandu Babu N stats->txmulticastframes_g += 6269d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TXMULTICASTFRAMES_G_HI) << 32); 6279d1ef6b2SChandu Babu N 6289d1ef6b2SChandu Babu N stats->tx64octets_gb += 6299d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TX64OCTETS_GB_LO); 6309d1ef6b2SChandu Babu N stats->tx64octets_gb += 6319d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TX64OCTETS_GB_HI) << 32); 6329d1ef6b2SChandu Babu N 6339d1ef6b2SChandu Babu N stats->tx65to127octets_gb += 6349d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TX65TO127OCTETS_GB_LO); 6359d1ef6b2SChandu Babu N stats->tx65to127octets_gb += 6369d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TX65TO127OCTETS_GB_HI) << 32); 6379d1ef6b2SChandu Babu N 6389d1ef6b2SChandu Babu N stats->tx128to255octets_gb += 6399d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TX128TO255OCTETS_GB_LO); 6409d1ef6b2SChandu Babu N stats->tx128to255octets_gb += 6419d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TX128TO255OCTETS_GB_HI) << 32); 6429d1ef6b2SChandu Babu N 6439d1ef6b2SChandu Babu N stats->tx256to511octets_gb += 6449d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TX256TO511OCTETS_GB_LO); 6459d1ef6b2SChandu Babu N stats->tx256to511octets_gb += 6469d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TX256TO511OCTETS_GB_HI) << 32); 6479d1ef6b2SChandu Babu N 6489d1ef6b2SChandu Babu N stats->tx512to1023octets_gb += 6499d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TX512TO1023OCTETS_GB_LO); 6509d1ef6b2SChandu Babu N stats->tx512to1023octets_gb += 6519d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TX512TO1023OCTETS_GB_HI) << 32); 6529d1ef6b2SChandu Babu N 6539d1ef6b2SChandu Babu N stats->tx1024tomaxoctets_gb += 6549d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TX1024TOMAXOCTETS_GB_LO); 6559d1ef6b2SChandu Babu N stats->tx1024tomaxoctets_gb += 6569d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TX1024TOMAXOCTETS_GB_HI) << 32); 6579d1ef6b2SChandu Babu N 6589d1ef6b2SChandu Babu N stats->txunicastframes_gb += 6599d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TXUNICASTFRAMES_GB_LO); 6609d1ef6b2SChandu Babu N stats->txunicastframes_gb += 6619d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TXUNICASTFRAMES_GB_HI) << 32); 6629d1ef6b2SChandu Babu N 6639d1ef6b2SChandu Babu N stats->txmulticastframes_gb += 6649d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TXMULTICASTFRAMES_GB_LO); 6659d1ef6b2SChandu Babu N stats->txmulticastframes_gb += 6669d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TXMULTICASTFRAMES_GB_HI) << 32); 6679d1ef6b2SChandu Babu N 6689d1ef6b2SChandu Babu N stats->txbroadcastframes_g += 6699d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TXBROADCASTFRAMES_GB_LO); 6709d1ef6b2SChandu Babu N stats->txbroadcastframes_g += 6719d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TXBROADCASTFRAMES_GB_HI) << 32); 6729d1ef6b2SChandu Babu N 6739d1ef6b2SChandu Babu N stats->txunderflowerror += 6749d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TXUNDERFLOWERROR_LO); 6759d1ef6b2SChandu Babu N stats->txunderflowerror += 6769d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TXUNDERFLOWERROR_HI) << 32); 6779d1ef6b2SChandu Babu N 6789d1ef6b2SChandu Babu N stats->txoctetcount_g += 6799d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TXOCTETCOUNT_G_LO); 6809d1ef6b2SChandu Babu N stats->txoctetcount_g += 6819d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TXOCTETCOUNT_G_HI) << 32); 6829d1ef6b2SChandu Babu N 6839d1ef6b2SChandu Babu N stats->txframecount_g += 6849d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TXFRAMECOUNT_G_LO); 6859d1ef6b2SChandu Babu N stats->txframecount_g += 6869d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TXFRAMECOUNT_G_HI) << 32); 6879d1ef6b2SChandu Babu N 6889d1ef6b2SChandu Babu N stats->txpauseframes += 6899d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TXPAUSEFRAMES_LO); 6909d1ef6b2SChandu Babu N stats->txpauseframes += 6919d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TXPAUSEFRAMES_HI) << 32); 6929d1ef6b2SChandu Babu N 6939d1ef6b2SChandu Babu N stats->txvlanframes_g += 6949d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_TXVLANFRAMES_G_LO); 6959d1ef6b2SChandu Babu N stats->txvlanframes_g += 6969d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_TXVLANFRAMES_G_HI) << 32); 6979d1ef6b2SChandu Babu N 6989d1ef6b2SChandu Babu N /* Rx counters */ 6999d1ef6b2SChandu Babu N stats->rxframecount_gb += 7009d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RXFRAMECOUNT_GB_LO); 7019d1ef6b2SChandu Babu N stats->rxframecount_gb += 7029d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RXFRAMECOUNT_GB_HI) << 32); 7039d1ef6b2SChandu Babu N 7049d1ef6b2SChandu Babu N stats->rxoctetcount_gb += 7059d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RXOCTETCOUNT_GB_LO); 7069d1ef6b2SChandu Babu N stats->rxoctetcount_gb += 7079d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RXOCTETCOUNT_GB_HI) << 32); 7089d1ef6b2SChandu Babu N 7099d1ef6b2SChandu Babu N stats->rxoctetcount_g += 7109d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RXOCTETCOUNT_G_LO); 7119d1ef6b2SChandu Babu N stats->rxoctetcount_g += 7129d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RXOCTETCOUNT_G_HI) << 32); 7139d1ef6b2SChandu Babu N 7149d1ef6b2SChandu Babu N stats->rxbroadcastframes_g += 7159d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RXBROADCASTFRAMES_G_LO); 7169d1ef6b2SChandu Babu N stats->rxbroadcastframes_g += 7179d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RXBROADCASTFRAMES_G_HI) << 32); 7189d1ef6b2SChandu Babu N 7199d1ef6b2SChandu Babu N stats->rxmulticastframes_g += 7209d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RXMULTICASTFRAMES_G_LO); 7219d1ef6b2SChandu Babu N stats->rxmulticastframes_g += 7229d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RXMULTICASTFRAMES_G_HI) << 32); 7239d1ef6b2SChandu Babu N 7249d1ef6b2SChandu Babu N stats->rxcrcerror += 7259d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RXCRCERROR_LO); 7269d1ef6b2SChandu Babu N stats->rxcrcerror += 7279d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RXCRCERROR_HI) << 32); 7289d1ef6b2SChandu Babu N 7299d1ef6b2SChandu Babu N stats->rxrunterror += 7309d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RXRUNTERROR); 7319d1ef6b2SChandu Babu N 7329d1ef6b2SChandu Babu N stats->rxjabbererror += 7339d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RXJABBERERROR); 7349d1ef6b2SChandu Babu N 7359d1ef6b2SChandu Babu N stats->rxundersize_g += 7369d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RXUNDERSIZE_G); 7379d1ef6b2SChandu Babu N 7389d1ef6b2SChandu Babu N stats->rxoversize_g += 7399d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RXOVERSIZE_G); 7409d1ef6b2SChandu Babu N 7419d1ef6b2SChandu Babu N stats->rx64octets_gb += 7429d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RX64OCTETS_GB_LO); 7439d1ef6b2SChandu Babu N stats->rx64octets_gb += 7449d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RX64OCTETS_GB_HI) << 32); 7459d1ef6b2SChandu Babu N 7469d1ef6b2SChandu Babu N stats->rx65to127octets_gb += 7479d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RX65TO127OCTETS_GB_LO); 7489d1ef6b2SChandu Babu N stats->rx65to127octets_gb += 7499d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RX65TO127OCTETS_GB_HI) << 32); 7509d1ef6b2SChandu Babu N 7519d1ef6b2SChandu Babu N stats->rx128to255octets_gb += 7529d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RX128TO255OCTETS_GB_LO); 7539d1ef6b2SChandu Babu N stats->rx128to255octets_gb += 7549d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RX128TO255OCTETS_GB_HI) << 32); 7559d1ef6b2SChandu Babu N 7569d1ef6b2SChandu Babu N stats->rx256to511octets_gb += 7579d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RX256TO511OCTETS_GB_LO); 7589d1ef6b2SChandu Babu N stats->rx256to511octets_gb += 7599d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RX256TO511OCTETS_GB_HI) << 32); 7609d1ef6b2SChandu Babu N 7619d1ef6b2SChandu Babu N stats->rx512to1023octets_gb += 7629d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RX512TO1023OCTETS_GB_LO); 7639d1ef6b2SChandu Babu N stats->rx512to1023octets_gb += 7649d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RX512TO1023OCTETS_GB_HI) << 32); 7659d1ef6b2SChandu Babu N 7669d1ef6b2SChandu Babu N stats->rx1024tomaxoctets_gb += 7679d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RX1024TOMAXOCTETS_GB_LO); 7689d1ef6b2SChandu Babu N stats->rx1024tomaxoctets_gb += 7699d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RX1024TOMAXOCTETS_GB_HI) << 32); 7709d1ef6b2SChandu Babu N 7719d1ef6b2SChandu Babu N stats->rxunicastframes_g += 7729d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RXUNICASTFRAMES_G_LO); 7739d1ef6b2SChandu Babu N stats->rxunicastframes_g += 7749d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RXUNICASTFRAMES_G_HI) << 32); 7759d1ef6b2SChandu Babu N 7769d1ef6b2SChandu Babu N stats->rxlengtherror += 7779d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RXLENGTHERROR_LO); 7789d1ef6b2SChandu Babu N stats->rxlengtherror += 7799d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RXLENGTHERROR_HI) << 32); 7809d1ef6b2SChandu Babu N 7819d1ef6b2SChandu Babu N stats->rxoutofrangetype += 7829d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RXOUTOFRANGETYPE_LO); 7839d1ef6b2SChandu Babu N stats->rxoutofrangetype += 7849d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RXOUTOFRANGETYPE_HI) << 32); 7859d1ef6b2SChandu Babu N 7869d1ef6b2SChandu Babu N stats->rxpauseframes += 7879d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RXPAUSEFRAMES_LO); 7889d1ef6b2SChandu Babu N stats->rxpauseframes += 7899d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RXPAUSEFRAMES_HI) << 32); 7909d1ef6b2SChandu Babu N 7919d1ef6b2SChandu Babu N stats->rxfifooverflow += 7929d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RXFIFOOVERFLOW_LO); 7939d1ef6b2SChandu Babu N stats->rxfifooverflow += 7949d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RXFIFOOVERFLOW_HI) << 32); 7959d1ef6b2SChandu Babu N 7969d1ef6b2SChandu Babu N stats->rxvlanframes_gb += 7979d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RXVLANFRAMES_GB_LO); 7989d1ef6b2SChandu Babu N stats->rxvlanframes_gb += 7999d1ef6b2SChandu Babu N ((uint64_t)AXGMAC_IOREAD(pdata, MMC_RXVLANFRAMES_GB_HI) << 32); 8009d1ef6b2SChandu Babu N 8019d1ef6b2SChandu Babu N stats->rxwatchdogerror += 8029d1ef6b2SChandu Babu N AXGMAC_IOREAD(pdata, MMC_RXWATCHDOGERROR); 8039d1ef6b2SChandu Babu N 8049d1ef6b2SChandu Babu N /* Un-freeze counters */ 8059d1ef6b2SChandu Babu N AXGMAC_IOWRITE_BITS(pdata, MMC_CR, MCF, 0); 8069d1ef6b2SChandu Babu N } 8079d1ef6b2SChandu Babu N 8089d1ef6b2SChandu Babu N static int 8099d1ef6b2SChandu Babu N axgbe_dev_xstats_get(struct rte_eth_dev *dev, struct rte_eth_xstat *stats, 8109d1ef6b2SChandu Babu N unsigned int n) 8119d1ef6b2SChandu Babu N { 8129d1ef6b2SChandu Babu N struct axgbe_port *pdata = dev->data->dev_private; 8139d1ef6b2SChandu Babu N unsigned int i; 8149d1ef6b2SChandu Babu N 8159d1ef6b2SChandu Babu N if (!stats) 8169d1ef6b2SChandu Babu N return 0; 8179d1ef6b2SChandu Babu N 8189d1ef6b2SChandu Babu N axgbe_read_mmc_stats(pdata); 8199d1ef6b2SChandu Babu N 8209d1ef6b2SChandu Babu N for (i = 0; i < n && i < AXGBE_XSTATS_COUNT; i++) { 8219d1ef6b2SChandu Babu N stats[i].id = i; 8229d1ef6b2SChandu Babu N stats[i].value = *(u64 *)((uint8_t *)&pdata->mmc_stats + 8239d1ef6b2SChandu Babu N axgbe_xstats_strings[i].offset); 8249d1ef6b2SChandu Babu N } 8259d1ef6b2SChandu Babu N 8269d1ef6b2SChandu Babu N return i; 8279d1ef6b2SChandu Babu N } 8289d1ef6b2SChandu Babu N 8299d1ef6b2SChandu Babu N static int 8309d1ef6b2SChandu Babu N axgbe_dev_xstats_get_names(__rte_unused struct rte_eth_dev *dev, 8319d1ef6b2SChandu Babu N struct rte_eth_xstat_name *xstats_names, 8329d1ef6b2SChandu Babu N unsigned int n) 8339d1ef6b2SChandu Babu N { 8349d1ef6b2SChandu Babu N unsigned int i; 8359d1ef6b2SChandu Babu N 8369d1ef6b2SChandu Babu N if (n >= AXGBE_XSTATS_COUNT && xstats_names) { 8379d1ef6b2SChandu Babu N for (i = 0; i < AXGBE_XSTATS_COUNT; ++i) { 8389d1ef6b2SChandu Babu N snprintf(xstats_names[i].name, 8399d1ef6b2SChandu Babu N RTE_ETH_XSTATS_NAME_SIZE, "%s", 8409d1ef6b2SChandu Babu N axgbe_xstats_strings[i].name); 8419d1ef6b2SChandu Babu N } 8429d1ef6b2SChandu Babu N } 8439d1ef6b2SChandu Babu N 8449d1ef6b2SChandu Babu N return AXGBE_XSTATS_COUNT; 8459d1ef6b2SChandu Babu N } 8469d1ef6b2SChandu Babu N 8479d1ef6b2SChandu Babu N static int 8489d1ef6b2SChandu Babu N axgbe_dev_xstats_get_by_id(struct rte_eth_dev *dev, const uint64_t *ids, 8499d1ef6b2SChandu Babu N uint64_t *values, unsigned int n) 8509d1ef6b2SChandu Babu N { 8519d1ef6b2SChandu Babu N unsigned int i; 8529d1ef6b2SChandu Babu N uint64_t values_copy[AXGBE_XSTATS_COUNT]; 8539d1ef6b2SChandu Babu N 8549d1ef6b2SChandu Babu N if (!ids) { 8559d1ef6b2SChandu Babu N struct axgbe_port *pdata = dev->data->dev_private; 8569d1ef6b2SChandu Babu N 8579d1ef6b2SChandu Babu N if (n < AXGBE_XSTATS_COUNT) 8589d1ef6b2SChandu Babu N return AXGBE_XSTATS_COUNT; 8599d1ef6b2SChandu Babu N 8609d1ef6b2SChandu Babu N axgbe_read_mmc_stats(pdata); 8619d1ef6b2SChandu Babu N 8629d1ef6b2SChandu Babu N for (i = 0; i < AXGBE_XSTATS_COUNT; i++) { 8639d1ef6b2SChandu Babu N values[i] = *(u64 *)((uint8_t *)&pdata->mmc_stats + 8649d1ef6b2SChandu Babu N axgbe_xstats_strings[i].offset); 8659d1ef6b2SChandu Babu N } 8669d1ef6b2SChandu Babu N 8679d1ef6b2SChandu Babu N return i; 8689d1ef6b2SChandu Babu N } 8699d1ef6b2SChandu Babu N 8709d1ef6b2SChandu Babu N axgbe_dev_xstats_get_by_id(dev, NULL, values_copy, AXGBE_XSTATS_COUNT); 8719d1ef6b2SChandu Babu N 8729d1ef6b2SChandu Babu N for (i = 0; i < n; i++) { 8739d1ef6b2SChandu Babu N if (ids[i] >= AXGBE_XSTATS_COUNT) { 8749d1ef6b2SChandu Babu N PMD_DRV_LOG(ERR, "id value isn't valid\n"); 8759d1ef6b2SChandu Babu N return -1; 8769d1ef6b2SChandu Babu N } 8779d1ef6b2SChandu Babu N values[i] = values_copy[ids[i]]; 8789d1ef6b2SChandu Babu N } 8799d1ef6b2SChandu Babu N return n; 8809d1ef6b2SChandu Babu N } 8819d1ef6b2SChandu Babu N 8829d1ef6b2SChandu Babu N static int 8839d1ef6b2SChandu Babu N axgbe_dev_xstats_get_names_by_id(struct rte_eth_dev *dev, 8849d1ef6b2SChandu Babu N struct rte_eth_xstat_name *xstats_names, 8859d1ef6b2SChandu Babu N const uint64_t *ids, 8869d1ef6b2SChandu Babu N unsigned int size) 8879d1ef6b2SChandu Babu N { 8889d1ef6b2SChandu Babu N struct rte_eth_xstat_name xstats_names_copy[AXGBE_XSTATS_COUNT]; 8899d1ef6b2SChandu Babu N unsigned int i; 8909d1ef6b2SChandu Babu N 8919d1ef6b2SChandu Babu N if (!ids) 8929d1ef6b2SChandu Babu N return axgbe_dev_xstats_get_names(dev, xstats_names, size); 8939d1ef6b2SChandu Babu N 8949d1ef6b2SChandu Babu N axgbe_dev_xstats_get_names(dev, xstats_names_copy, size); 8959d1ef6b2SChandu Babu N 8969d1ef6b2SChandu Babu N for (i = 0; i < size; i++) { 8979d1ef6b2SChandu Babu N if (ids[i] >= AXGBE_XSTATS_COUNT) { 8989d1ef6b2SChandu Babu N PMD_DRV_LOG(ERR, "id value isn't valid\n"); 8999d1ef6b2SChandu Babu N return -1; 9009d1ef6b2SChandu Babu N } 9019d1ef6b2SChandu Babu N strcpy(xstats_names[i].name, xstats_names_copy[ids[i]].name); 9029d1ef6b2SChandu Babu N } 9039d1ef6b2SChandu Babu N return size; 9049d1ef6b2SChandu Babu N } 9059d1ef6b2SChandu Babu N 9069d1ef6b2SChandu Babu N static int 9079d1ef6b2SChandu Babu N axgbe_dev_xstats_reset(struct rte_eth_dev *dev) 9089d1ef6b2SChandu Babu N { 9099d1ef6b2SChandu Babu N struct axgbe_port *pdata = dev->data->dev_private; 9109d1ef6b2SChandu Babu N struct axgbe_mmc_stats *stats = &pdata->mmc_stats; 9119d1ef6b2SChandu Babu N 9129d1ef6b2SChandu Babu N /* MMC registers are configured for reset on read */ 9139d1ef6b2SChandu Babu N axgbe_read_mmc_stats(pdata); 9149d1ef6b2SChandu Babu N 9159d1ef6b2SChandu Babu N /* Reset stats */ 9169d1ef6b2SChandu Babu N memset(stats, 0, sizeof(*stats)); 9179d1ef6b2SChandu Babu N 9189d1ef6b2SChandu Babu N return 0; 9199d1ef6b2SChandu Babu N } 9209d1ef6b2SChandu Babu N 9213e730511SRavi Kumar static int 9223e730511SRavi Kumar axgbe_dev_stats_get(struct rte_eth_dev *dev, 9233e730511SRavi Kumar struct rte_eth_stats *stats) 9243e730511SRavi Kumar { 9253e730511SRavi Kumar struct axgbe_rx_queue *rxq; 9263e730511SRavi Kumar struct axgbe_tx_queue *txq; 9279d1ef6b2SChandu Babu N struct axgbe_port *pdata = dev->data->dev_private; 9289d1ef6b2SChandu Babu N struct axgbe_mmc_stats *mmc_stats = &pdata->mmc_stats; 9293e730511SRavi Kumar unsigned int i; 9303e730511SRavi Kumar 9319d1ef6b2SChandu Babu N axgbe_read_mmc_stats(pdata); 9329d1ef6b2SChandu Babu N 9339d1ef6b2SChandu Babu N stats->imissed = mmc_stats->rxfifooverflow; 9349d1ef6b2SChandu Babu N 9353e730511SRavi Kumar for (i = 0; i < dev->data->nb_rx_queues; i++) { 9363e730511SRavi Kumar rxq = dev->data->rx_queues[i]; 9373e730511SRavi Kumar stats->q_ipackets[i] = rxq->pkts; 9383e730511SRavi Kumar stats->ipackets += rxq->pkts; 9393e730511SRavi Kumar stats->q_ibytes[i] = rxq->bytes; 9403e730511SRavi Kumar stats->ibytes += rxq->bytes; 9419d1ef6b2SChandu Babu N stats->rx_nombuf += rxq->rx_mbuf_alloc_failed; 9429d1ef6b2SChandu Babu N stats->q_errors[i] = rxq->errors + rxq->rx_mbuf_alloc_failed; 9439d1ef6b2SChandu Babu N stats->ierrors += rxq->errors; 9443e730511SRavi Kumar } 9459d1ef6b2SChandu Babu N 9463e730511SRavi Kumar for (i = 0; i < dev->data->nb_tx_queues; i++) { 9473e730511SRavi Kumar txq = dev->data->tx_queues[i]; 9483e730511SRavi Kumar stats->q_opackets[i] = txq->pkts; 9493e730511SRavi Kumar stats->opackets += txq->pkts; 9503e730511SRavi Kumar stats->q_obytes[i] = txq->bytes; 9513e730511SRavi Kumar stats->obytes += txq->bytes; 9529d1ef6b2SChandu Babu N stats->oerrors += txq->errors; 9533e730511SRavi Kumar } 9543e730511SRavi Kumar 9553e730511SRavi Kumar return 0; 9563e730511SRavi Kumar } 9573e730511SRavi Kumar 9589970a9adSIgor Romanov static int 9593e730511SRavi Kumar axgbe_dev_stats_reset(struct rte_eth_dev *dev) 9603e730511SRavi Kumar { 9613e730511SRavi Kumar struct axgbe_rx_queue *rxq; 9623e730511SRavi Kumar struct axgbe_tx_queue *txq; 9633e730511SRavi Kumar unsigned int i; 9643e730511SRavi Kumar 9653e730511SRavi Kumar for (i = 0; i < dev->data->nb_rx_queues; i++) { 9663e730511SRavi Kumar rxq = dev->data->rx_queues[i]; 9673e730511SRavi Kumar rxq->pkts = 0; 9683e730511SRavi Kumar rxq->bytes = 0; 9693e730511SRavi Kumar rxq->errors = 0; 9709d1ef6b2SChandu Babu N rxq->rx_mbuf_alloc_failed = 0; 9713e730511SRavi Kumar } 9723e730511SRavi Kumar for (i = 0; i < dev->data->nb_tx_queues; i++) { 9733e730511SRavi Kumar txq = dev->data->tx_queues[i]; 9743e730511SRavi Kumar txq->pkts = 0; 9753e730511SRavi Kumar txq->bytes = 0; 9763e730511SRavi Kumar txq->errors = 0; 9773e730511SRavi Kumar } 9789970a9adSIgor Romanov 9799970a9adSIgor Romanov return 0; 9803e730511SRavi Kumar } 9813e730511SRavi Kumar 982bdad90d1SIvan Ilchenko static int 983cd8c7c7cSFerruh Yigit axgbe_dev_info_get(struct rte_eth_dev *dev, struct rte_eth_dev_info *dev_info) 9849e890103SRavi Kumar { 9859e890103SRavi Kumar struct axgbe_port *pdata = dev->data->dev_private; 9869e890103SRavi Kumar 9879e890103SRavi Kumar dev_info->max_rx_queues = pdata->rx_ring_count; 9889e890103SRavi Kumar dev_info->max_tx_queues = pdata->tx_ring_count; 9899e890103SRavi Kumar dev_info->min_rx_bufsize = AXGBE_RX_MIN_BUF_SIZE; 9909e890103SRavi Kumar dev_info->max_rx_pktlen = AXGBE_RX_MAX_BUF_SIZE; 99149a5e622SChandu Babu N dev_info->max_mac_addrs = pdata->hw_feat.addn_mac + 1; 992e01d9b2eSChandu Babu N dev_info->max_hash_mac_addrs = pdata->hw_feat.hash_table_size; 9939e890103SRavi Kumar dev_info->speed_capa = ETH_LINK_SPEED_10G; 9949e890103SRavi Kumar 9959e890103SRavi Kumar dev_info->rx_offload_capa = 9969e890103SRavi Kumar DEV_RX_OFFLOAD_IPV4_CKSUM | 9979e890103SRavi Kumar DEV_RX_OFFLOAD_UDP_CKSUM | 99870815c9eSFerruh Yigit DEV_RX_OFFLOAD_TCP_CKSUM | 999965b3127SSelwin Sebastian DEV_RX_OFFLOAD_JUMBO_FRAME | 1000965b3127SSelwin Sebastian DEV_RX_OFFLOAD_SCATTER | 100170815c9eSFerruh Yigit DEV_RX_OFFLOAD_KEEP_CRC; 10029e890103SRavi Kumar 10039e890103SRavi Kumar dev_info->tx_offload_capa = 10049e890103SRavi Kumar DEV_TX_OFFLOAD_IPV4_CKSUM | 10059e890103SRavi Kumar DEV_TX_OFFLOAD_UDP_CKSUM | 10069e890103SRavi Kumar DEV_TX_OFFLOAD_TCP_CKSUM; 10079e890103SRavi Kumar 10089e890103SRavi Kumar if (pdata->hw_feat.rss) { 10099e890103SRavi Kumar dev_info->flow_type_rss_offloads = AXGBE_RSS_OFFLOAD; 10109e890103SRavi Kumar dev_info->reta_size = pdata->hw_feat.hash_table_size; 10119e890103SRavi Kumar dev_info->hash_key_size = AXGBE_RSS_HASH_KEY_SIZE; 10129e890103SRavi Kumar } 10139e890103SRavi Kumar 10149e890103SRavi Kumar dev_info->rx_desc_lim = rx_desc_lim; 10159e890103SRavi Kumar dev_info->tx_desc_lim = tx_desc_lim; 10169e890103SRavi Kumar 10179e890103SRavi Kumar dev_info->default_rxconf = (struct rte_eth_rxconf) { 10189e890103SRavi Kumar .rx_free_thresh = AXGBE_RX_FREE_THRESH, 10199e890103SRavi Kumar }; 10209e890103SRavi Kumar 10219e890103SRavi Kumar dev_info->default_txconf = (struct rte_eth_txconf) { 10229e890103SRavi Kumar .tx_free_thresh = AXGBE_TX_FREE_THRESH, 10239e890103SRavi Kumar }; 1024bdad90d1SIvan Ilchenko 1025bdad90d1SIvan Ilchenko return 0; 10269e890103SRavi Kumar } 10279e890103SRavi Kumar 1028cf97f33eSAmaranath Somalapuram static int 1029cf97f33eSAmaranath Somalapuram axgbe_flow_ctrl_get(struct rte_eth_dev *dev, struct rte_eth_fc_conf *fc_conf) 1030cf97f33eSAmaranath Somalapuram { 1031cf97f33eSAmaranath Somalapuram struct axgbe_port *pdata = dev->data->dev_private; 1032cf97f33eSAmaranath Somalapuram struct xgbe_fc_info fc = pdata->fc; 1033cf97f33eSAmaranath Somalapuram unsigned int reg, reg_val = 0; 1034cf97f33eSAmaranath Somalapuram 1035cf97f33eSAmaranath Somalapuram reg = MAC_Q0TFCR; 1036cf97f33eSAmaranath Somalapuram reg_val = AXGMAC_IOREAD(pdata, reg); 1037cf97f33eSAmaranath Somalapuram fc.low_water[0] = AXGMAC_MTL_IOREAD_BITS(pdata, 0, MTL_Q_RQFCR, RFA); 1038cf97f33eSAmaranath Somalapuram fc.high_water[0] = AXGMAC_MTL_IOREAD_BITS(pdata, 0, MTL_Q_RQFCR, RFD); 1039cf97f33eSAmaranath Somalapuram fc.pause_time[0] = AXGMAC_GET_BITS(reg_val, MAC_Q0TFCR, PT); 1040cf97f33eSAmaranath Somalapuram fc.autoneg = pdata->pause_autoneg; 1041cf97f33eSAmaranath Somalapuram 1042cf97f33eSAmaranath Somalapuram if (pdata->rx_pause && pdata->tx_pause) 1043cf97f33eSAmaranath Somalapuram fc.mode = RTE_FC_FULL; 1044cf97f33eSAmaranath Somalapuram else if (pdata->rx_pause) 1045cf97f33eSAmaranath Somalapuram fc.mode = RTE_FC_RX_PAUSE; 1046cf97f33eSAmaranath Somalapuram else if (pdata->tx_pause) 1047cf97f33eSAmaranath Somalapuram fc.mode = RTE_FC_TX_PAUSE; 1048cf97f33eSAmaranath Somalapuram else 1049cf97f33eSAmaranath Somalapuram fc.mode = RTE_FC_NONE; 1050cf97f33eSAmaranath Somalapuram 1051cf97f33eSAmaranath Somalapuram fc_conf->high_water = (1024 + (fc.low_water[0] << 9)) / 1024; 1052cf97f33eSAmaranath Somalapuram fc_conf->low_water = (1024 + (fc.high_water[0] << 9)) / 1024; 1053cf97f33eSAmaranath Somalapuram fc_conf->pause_time = fc.pause_time[0]; 1054cf97f33eSAmaranath Somalapuram fc_conf->send_xon = fc.send_xon; 1055cf97f33eSAmaranath Somalapuram fc_conf->mode = fc.mode; 1056cf97f33eSAmaranath Somalapuram 1057cf97f33eSAmaranath Somalapuram return 0; 1058cf97f33eSAmaranath Somalapuram } 1059cf97f33eSAmaranath Somalapuram 1060cf97f33eSAmaranath Somalapuram static int 1061cf97f33eSAmaranath Somalapuram axgbe_flow_ctrl_set(struct rte_eth_dev *dev, struct rte_eth_fc_conf *fc_conf) 1062cf97f33eSAmaranath Somalapuram { 1063cf97f33eSAmaranath Somalapuram struct axgbe_port *pdata = dev->data->dev_private; 1064cf97f33eSAmaranath Somalapuram struct xgbe_fc_info fc = pdata->fc; 1065cf97f33eSAmaranath Somalapuram unsigned int reg, reg_val = 0; 1066cf97f33eSAmaranath Somalapuram reg = MAC_Q0TFCR; 1067cf97f33eSAmaranath Somalapuram 1068cf97f33eSAmaranath Somalapuram pdata->pause_autoneg = fc_conf->autoneg; 1069cf97f33eSAmaranath Somalapuram pdata->phy.pause_autoneg = pdata->pause_autoneg; 1070cf97f33eSAmaranath Somalapuram fc.send_xon = fc_conf->send_xon; 1071cf97f33eSAmaranath Somalapuram AXGMAC_MTL_IOWRITE_BITS(pdata, 0, MTL_Q_RQFCR, RFA, 1072cf97f33eSAmaranath Somalapuram AXGMAC_FLOW_CONTROL_VALUE(1024 * fc_conf->high_water)); 1073cf97f33eSAmaranath Somalapuram AXGMAC_MTL_IOWRITE_BITS(pdata, 0, MTL_Q_RQFCR, RFD, 1074cf97f33eSAmaranath Somalapuram AXGMAC_FLOW_CONTROL_VALUE(1024 * fc_conf->low_water)); 1075cf97f33eSAmaranath Somalapuram AXGMAC_SET_BITS(reg_val, MAC_Q0TFCR, PT, fc_conf->pause_time); 1076cf97f33eSAmaranath Somalapuram AXGMAC_IOWRITE(pdata, reg, reg_val); 1077cf97f33eSAmaranath Somalapuram fc.mode = fc_conf->mode; 1078cf97f33eSAmaranath Somalapuram 1079cf97f33eSAmaranath Somalapuram if (fc.mode == RTE_FC_FULL) { 1080cf97f33eSAmaranath Somalapuram pdata->tx_pause = 1; 1081cf97f33eSAmaranath Somalapuram pdata->rx_pause = 1; 1082cf97f33eSAmaranath Somalapuram } else if (fc.mode == RTE_FC_RX_PAUSE) { 1083cf97f33eSAmaranath Somalapuram pdata->tx_pause = 0; 1084cf97f33eSAmaranath Somalapuram pdata->rx_pause = 1; 1085cf97f33eSAmaranath Somalapuram } else if (fc.mode == RTE_FC_TX_PAUSE) { 1086cf97f33eSAmaranath Somalapuram pdata->tx_pause = 1; 1087cf97f33eSAmaranath Somalapuram pdata->rx_pause = 0; 1088cf97f33eSAmaranath Somalapuram } else { 1089cf97f33eSAmaranath Somalapuram pdata->tx_pause = 0; 1090cf97f33eSAmaranath Somalapuram pdata->rx_pause = 0; 1091cf97f33eSAmaranath Somalapuram } 1092cf97f33eSAmaranath Somalapuram 1093cf97f33eSAmaranath Somalapuram if (pdata->tx_pause != (unsigned int)pdata->phy.tx_pause) 1094cf97f33eSAmaranath Somalapuram pdata->hw_if.config_tx_flow_control(pdata); 1095cf97f33eSAmaranath Somalapuram 1096cf97f33eSAmaranath Somalapuram if (pdata->rx_pause != (unsigned int)pdata->phy.rx_pause) 1097cf97f33eSAmaranath Somalapuram pdata->hw_if.config_rx_flow_control(pdata); 1098cf97f33eSAmaranath Somalapuram 1099cf97f33eSAmaranath Somalapuram pdata->hw_if.config_flow_control(pdata); 1100cf97f33eSAmaranath Somalapuram pdata->phy.tx_pause = pdata->tx_pause; 1101cf97f33eSAmaranath Somalapuram pdata->phy.rx_pause = pdata->rx_pause; 1102cf97f33eSAmaranath Somalapuram 1103cf97f33eSAmaranath Somalapuram return 0; 1104cf97f33eSAmaranath Somalapuram } 1105cf97f33eSAmaranath Somalapuram 1106e0543d4eSAmaranath Somalapuram static int 1107e0543d4eSAmaranath Somalapuram axgbe_priority_flow_ctrl_set(struct rte_eth_dev *dev, 1108e0543d4eSAmaranath Somalapuram struct rte_eth_pfc_conf *pfc_conf) 1109e0543d4eSAmaranath Somalapuram { 1110e0543d4eSAmaranath Somalapuram struct axgbe_port *pdata = dev->data->dev_private; 1111e0543d4eSAmaranath Somalapuram struct xgbe_fc_info fc = pdata->fc; 1112e0543d4eSAmaranath Somalapuram uint8_t tc_num; 1113e0543d4eSAmaranath Somalapuram 1114e0543d4eSAmaranath Somalapuram tc_num = pdata->pfc_map[pfc_conf->priority]; 1115e0543d4eSAmaranath Somalapuram 1116e0543d4eSAmaranath Somalapuram if (pfc_conf->priority >= pdata->hw_feat.tc_cnt) { 1117e0543d4eSAmaranath Somalapuram PMD_INIT_LOG(ERR, "Max supported traffic class: %d\n", 1118e0543d4eSAmaranath Somalapuram pdata->hw_feat.tc_cnt); 1119e0543d4eSAmaranath Somalapuram return -EINVAL; 1120e0543d4eSAmaranath Somalapuram } 1121e0543d4eSAmaranath Somalapuram 1122e0543d4eSAmaranath Somalapuram pdata->pause_autoneg = pfc_conf->fc.autoneg; 1123e0543d4eSAmaranath Somalapuram pdata->phy.pause_autoneg = pdata->pause_autoneg; 1124e0543d4eSAmaranath Somalapuram fc.send_xon = pfc_conf->fc.send_xon; 1125e0543d4eSAmaranath Somalapuram AXGMAC_MTL_IOWRITE_BITS(pdata, tc_num, MTL_Q_RQFCR, RFA, 1126e0543d4eSAmaranath Somalapuram AXGMAC_FLOW_CONTROL_VALUE(1024 * pfc_conf->fc.high_water)); 1127e0543d4eSAmaranath Somalapuram AXGMAC_MTL_IOWRITE_BITS(pdata, tc_num, MTL_Q_RQFCR, RFD, 1128e0543d4eSAmaranath Somalapuram AXGMAC_FLOW_CONTROL_VALUE(1024 * pfc_conf->fc.low_water)); 1129e0543d4eSAmaranath Somalapuram 1130e0543d4eSAmaranath Somalapuram switch (tc_num) { 1131e0543d4eSAmaranath Somalapuram case 0: 1132e0543d4eSAmaranath Somalapuram AXGMAC_IOWRITE_BITS(pdata, MTL_TCPM0R, 1133e0543d4eSAmaranath Somalapuram PSTC0, pfc_conf->fc.pause_time); 1134e0543d4eSAmaranath Somalapuram break; 1135e0543d4eSAmaranath Somalapuram case 1: 1136e0543d4eSAmaranath Somalapuram AXGMAC_IOWRITE_BITS(pdata, MTL_TCPM0R, 1137e0543d4eSAmaranath Somalapuram PSTC1, pfc_conf->fc.pause_time); 1138e0543d4eSAmaranath Somalapuram break; 1139e0543d4eSAmaranath Somalapuram case 2: 1140e0543d4eSAmaranath Somalapuram AXGMAC_IOWRITE_BITS(pdata, MTL_TCPM0R, 1141e0543d4eSAmaranath Somalapuram PSTC2, pfc_conf->fc.pause_time); 1142e0543d4eSAmaranath Somalapuram break; 1143e0543d4eSAmaranath Somalapuram case 3: 1144e0543d4eSAmaranath Somalapuram AXGMAC_IOWRITE_BITS(pdata, MTL_TCPM0R, 1145e0543d4eSAmaranath Somalapuram PSTC3, pfc_conf->fc.pause_time); 1146e0543d4eSAmaranath Somalapuram break; 1147e0543d4eSAmaranath Somalapuram case 4: 1148e0543d4eSAmaranath Somalapuram AXGMAC_IOWRITE_BITS(pdata, MTL_TCPM1R, 1149e0543d4eSAmaranath Somalapuram PSTC4, pfc_conf->fc.pause_time); 1150e0543d4eSAmaranath Somalapuram break; 1151e0543d4eSAmaranath Somalapuram case 5: 1152e0543d4eSAmaranath Somalapuram AXGMAC_IOWRITE_BITS(pdata, MTL_TCPM1R, 1153e0543d4eSAmaranath Somalapuram PSTC5, pfc_conf->fc.pause_time); 1154e0543d4eSAmaranath Somalapuram break; 1155e0543d4eSAmaranath Somalapuram case 7: 1156e0543d4eSAmaranath Somalapuram AXGMAC_IOWRITE_BITS(pdata, MTL_TCPM1R, 1157e0543d4eSAmaranath Somalapuram PSTC6, pfc_conf->fc.pause_time); 1158e0543d4eSAmaranath Somalapuram break; 1159e0543d4eSAmaranath Somalapuram case 6: 1160e0543d4eSAmaranath Somalapuram AXGMAC_IOWRITE_BITS(pdata, MTL_TCPM1R, 1161e0543d4eSAmaranath Somalapuram PSTC7, pfc_conf->fc.pause_time); 1162e0543d4eSAmaranath Somalapuram break; 1163e0543d4eSAmaranath Somalapuram } 1164e0543d4eSAmaranath Somalapuram 1165e0543d4eSAmaranath Somalapuram fc.mode = pfc_conf->fc.mode; 1166e0543d4eSAmaranath Somalapuram 1167e0543d4eSAmaranath Somalapuram if (fc.mode == RTE_FC_FULL) { 1168e0543d4eSAmaranath Somalapuram pdata->tx_pause = 1; 1169e0543d4eSAmaranath Somalapuram pdata->rx_pause = 1; 1170e0543d4eSAmaranath Somalapuram AXGMAC_IOWRITE_BITS(pdata, MAC_RFCR, PFCE, 1); 1171e0543d4eSAmaranath Somalapuram } else if (fc.mode == RTE_FC_RX_PAUSE) { 1172e0543d4eSAmaranath Somalapuram pdata->tx_pause = 0; 1173e0543d4eSAmaranath Somalapuram pdata->rx_pause = 1; 1174e0543d4eSAmaranath Somalapuram AXGMAC_IOWRITE_BITS(pdata, MAC_RFCR, PFCE, 1); 1175e0543d4eSAmaranath Somalapuram } else if (fc.mode == RTE_FC_TX_PAUSE) { 1176e0543d4eSAmaranath Somalapuram pdata->tx_pause = 1; 1177e0543d4eSAmaranath Somalapuram pdata->rx_pause = 0; 1178e0543d4eSAmaranath Somalapuram AXGMAC_IOWRITE_BITS(pdata, MAC_RFCR, PFCE, 0); 1179e0543d4eSAmaranath Somalapuram } else { 1180e0543d4eSAmaranath Somalapuram pdata->tx_pause = 0; 1181e0543d4eSAmaranath Somalapuram pdata->rx_pause = 0; 1182e0543d4eSAmaranath Somalapuram AXGMAC_IOWRITE_BITS(pdata, MAC_RFCR, PFCE, 0); 1183e0543d4eSAmaranath Somalapuram } 1184e0543d4eSAmaranath Somalapuram 1185e0543d4eSAmaranath Somalapuram if (pdata->tx_pause != (unsigned int)pdata->phy.tx_pause) 1186e0543d4eSAmaranath Somalapuram pdata->hw_if.config_tx_flow_control(pdata); 1187e0543d4eSAmaranath Somalapuram 1188e0543d4eSAmaranath Somalapuram if (pdata->rx_pause != (unsigned int)pdata->phy.rx_pause) 1189e0543d4eSAmaranath Somalapuram pdata->hw_if.config_rx_flow_control(pdata); 1190e0543d4eSAmaranath Somalapuram pdata->hw_if.config_flow_control(pdata); 1191e0543d4eSAmaranath Somalapuram pdata->phy.tx_pause = pdata->tx_pause; 1192e0543d4eSAmaranath Somalapuram pdata->phy.rx_pause = pdata->rx_pause; 1193e0543d4eSAmaranath Somalapuram 1194e0543d4eSAmaranath Somalapuram return 0; 1195e0543d4eSAmaranath Somalapuram } 1196e0543d4eSAmaranath Somalapuram 11977aed95c9SAmaranath Somalapuram void 11987aed95c9SAmaranath Somalapuram axgbe_rxq_info_get(struct rte_eth_dev *dev, uint16_t queue_id, 11997aed95c9SAmaranath Somalapuram struct rte_eth_rxq_info *qinfo) 12007aed95c9SAmaranath Somalapuram { 12017aed95c9SAmaranath Somalapuram struct axgbe_rx_queue *rxq; 12027aed95c9SAmaranath Somalapuram 12037aed95c9SAmaranath Somalapuram rxq = dev->data->rx_queues[queue_id]; 12047aed95c9SAmaranath Somalapuram qinfo->mp = rxq->mb_pool; 12057aed95c9SAmaranath Somalapuram qinfo->scattered_rx = dev->data->scattered_rx; 12067aed95c9SAmaranath Somalapuram qinfo->nb_desc = rxq->nb_desc; 12077aed95c9SAmaranath Somalapuram qinfo->conf.rx_free_thresh = rxq->free_thresh; 12087aed95c9SAmaranath Somalapuram } 12097aed95c9SAmaranath Somalapuram 12107aed95c9SAmaranath Somalapuram void 12117aed95c9SAmaranath Somalapuram axgbe_txq_info_get(struct rte_eth_dev *dev, uint16_t queue_id, 12127aed95c9SAmaranath Somalapuram struct rte_eth_txq_info *qinfo) 12137aed95c9SAmaranath Somalapuram { 12147aed95c9SAmaranath Somalapuram struct axgbe_tx_queue *txq; 12157aed95c9SAmaranath Somalapuram 12167aed95c9SAmaranath Somalapuram txq = dev->data->tx_queues[queue_id]; 12177aed95c9SAmaranath Somalapuram qinfo->nb_desc = txq->nb_desc; 12187aed95c9SAmaranath Somalapuram qinfo->conf.tx_free_thresh = txq->free_thresh; 12197aed95c9SAmaranath Somalapuram } 1220*410cf087SAmaranath Somalapuram const uint32_t * 1221*410cf087SAmaranath Somalapuram axgbe_dev_supported_ptypes_get(struct rte_eth_dev *dev) 1222*410cf087SAmaranath Somalapuram { 1223*410cf087SAmaranath Somalapuram static const uint32_t ptypes[] = { 1224*410cf087SAmaranath Somalapuram RTE_PTYPE_L2_ETHER, 1225*410cf087SAmaranath Somalapuram RTE_PTYPE_L2_ETHER_TIMESYNC, 1226*410cf087SAmaranath Somalapuram RTE_PTYPE_L2_ETHER_LLDP, 1227*410cf087SAmaranath Somalapuram RTE_PTYPE_L2_ETHER_ARP, 1228*410cf087SAmaranath Somalapuram RTE_PTYPE_L3_IPV4_EXT_UNKNOWN, 1229*410cf087SAmaranath Somalapuram RTE_PTYPE_L3_IPV6_EXT_UNKNOWN, 1230*410cf087SAmaranath Somalapuram RTE_PTYPE_L4_FRAG, 1231*410cf087SAmaranath Somalapuram RTE_PTYPE_L4_ICMP, 1232*410cf087SAmaranath Somalapuram RTE_PTYPE_L4_NONFRAG, 1233*410cf087SAmaranath Somalapuram RTE_PTYPE_L4_SCTP, 1234*410cf087SAmaranath Somalapuram RTE_PTYPE_L4_TCP, 1235*410cf087SAmaranath Somalapuram RTE_PTYPE_L4_UDP, 1236*410cf087SAmaranath Somalapuram RTE_PTYPE_TUNNEL_GRENAT, 1237*410cf087SAmaranath Somalapuram RTE_PTYPE_TUNNEL_IP, 1238*410cf087SAmaranath Somalapuram RTE_PTYPE_INNER_L2_ETHER, 1239*410cf087SAmaranath Somalapuram RTE_PTYPE_INNER_L2_ETHER_VLAN, 1240*410cf087SAmaranath Somalapuram RTE_PTYPE_INNER_L3_IPV4_EXT_UNKNOWN, 1241*410cf087SAmaranath Somalapuram RTE_PTYPE_INNER_L3_IPV6_EXT_UNKNOWN, 1242*410cf087SAmaranath Somalapuram RTE_PTYPE_INNER_L4_FRAG, 1243*410cf087SAmaranath Somalapuram RTE_PTYPE_INNER_L4_ICMP, 1244*410cf087SAmaranath Somalapuram RTE_PTYPE_INNER_L4_NONFRAG, 1245*410cf087SAmaranath Somalapuram RTE_PTYPE_INNER_L4_SCTP, 1246*410cf087SAmaranath Somalapuram RTE_PTYPE_INNER_L4_TCP, 1247*410cf087SAmaranath Somalapuram RTE_PTYPE_INNER_L4_UDP, 1248*410cf087SAmaranath Somalapuram RTE_PTYPE_UNKNOWN 1249*410cf087SAmaranath Somalapuram }; 1250*410cf087SAmaranath Somalapuram 1251*410cf087SAmaranath Somalapuram if (dev->rx_pkt_burst == axgbe_recv_pkts) 1252*410cf087SAmaranath Somalapuram return ptypes; 1253*410cf087SAmaranath Somalapuram return NULL; 1254*410cf087SAmaranath Somalapuram } 12557aed95c9SAmaranath Somalapuram 1256572890efSRavi Kumar static void axgbe_get_all_hw_features(struct axgbe_port *pdata) 1257572890efSRavi Kumar { 1258572890efSRavi Kumar unsigned int mac_hfr0, mac_hfr1, mac_hfr2; 1259572890efSRavi Kumar struct axgbe_hw_features *hw_feat = &pdata->hw_feat; 1260572890efSRavi Kumar 1261572890efSRavi Kumar mac_hfr0 = AXGMAC_IOREAD(pdata, MAC_HWF0R); 1262572890efSRavi Kumar mac_hfr1 = AXGMAC_IOREAD(pdata, MAC_HWF1R); 1263572890efSRavi Kumar mac_hfr2 = AXGMAC_IOREAD(pdata, MAC_HWF2R); 1264572890efSRavi Kumar 1265572890efSRavi Kumar memset(hw_feat, 0, sizeof(*hw_feat)); 1266572890efSRavi Kumar 1267572890efSRavi Kumar hw_feat->version = AXGMAC_IOREAD(pdata, MAC_VR); 1268572890efSRavi Kumar 1269572890efSRavi Kumar /* Hardware feature register 0 */ 1270572890efSRavi Kumar hw_feat->gmii = AXGMAC_GET_BITS(mac_hfr0, MAC_HWF0R, GMIISEL); 1271572890efSRavi Kumar hw_feat->vlhash = AXGMAC_GET_BITS(mac_hfr0, MAC_HWF0R, VLHASH); 1272572890efSRavi Kumar hw_feat->sma = AXGMAC_GET_BITS(mac_hfr0, MAC_HWF0R, SMASEL); 1273572890efSRavi Kumar hw_feat->rwk = AXGMAC_GET_BITS(mac_hfr0, MAC_HWF0R, RWKSEL); 1274572890efSRavi Kumar hw_feat->mgk = AXGMAC_GET_BITS(mac_hfr0, MAC_HWF0R, MGKSEL); 1275572890efSRavi Kumar hw_feat->mmc = AXGMAC_GET_BITS(mac_hfr0, MAC_HWF0R, MMCSEL); 1276572890efSRavi Kumar hw_feat->aoe = AXGMAC_GET_BITS(mac_hfr0, MAC_HWF0R, ARPOFFSEL); 1277572890efSRavi Kumar hw_feat->ts = AXGMAC_GET_BITS(mac_hfr0, MAC_HWF0R, TSSEL); 1278572890efSRavi Kumar hw_feat->eee = AXGMAC_GET_BITS(mac_hfr0, MAC_HWF0R, EEESEL); 1279572890efSRavi Kumar hw_feat->tx_coe = AXGMAC_GET_BITS(mac_hfr0, MAC_HWF0R, TXCOESEL); 1280572890efSRavi Kumar hw_feat->rx_coe = AXGMAC_GET_BITS(mac_hfr0, MAC_HWF0R, RXCOESEL); 1281572890efSRavi Kumar hw_feat->addn_mac = AXGMAC_GET_BITS(mac_hfr0, MAC_HWF0R, 1282572890efSRavi Kumar ADDMACADRSEL); 1283572890efSRavi Kumar hw_feat->ts_src = AXGMAC_GET_BITS(mac_hfr0, MAC_HWF0R, TSSTSSEL); 1284572890efSRavi Kumar hw_feat->sa_vlan_ins = AXGMAC_GET_BITS(mac_hfr0, MAC_HWF0R, SAVLANINS); 1285572890efSRavi Kumar 1286572890efSRavi Kumar /* Hardware feature register 1 */ 1287572890efSRavi Kumar hw_feat->rx_fifo_size = AXGMAC_GET_BITS(mac_hfr1, MAC_HWF1R, 1288572890efSRavi Kumar RXFIFOSIZE); 1289572890efSRavi Kumar hw_feat->tx_fifo_size = AXGMAC_GET_BITS(mac_hfr1, MAC_HWF1R, 1290572890efSRavi Kumar TXFIFOSIZE); 1291572890efSRavi Kumar hw_feat->adv_ts_hi = AXGMAC_GET_BITS(mac_hfr1, 1292572890efSRavi Kumar MAC_HWF1R, ADVTHWORD); 1293572890efSRavi Kumar hw_feat->dma_width = AXGMAC_GET_BITS(mac_hfr1, MAC_HWF1R, ADDR64); 1294572890efSRavi Kumar hw_feat->dcb = AXGMAC_GET_BITS(mac_hfr1, MAC_HWF1R, DCBEN); 1295572890efSRavi Kumar hw_feat->sph = AXGMAC_GET_BITS(mac_hfr1, MAC_HWF1R, SPHEN); 1296572890efSRavi Kumar hw_feat->tso = AXGMAC_GET_BITS(mac_hfr1, MAC_HWF1R, TSOEN); 1297572890efSRavi Kumar hw_feat->dma_debug = AXGMAC_GET_BITS(mac_hfr1, MAC_HWF1R, DBGMEMA); 1298572890efSRavi Kumar hw_feat->rss = AXGMAC_GET_BITS(mac_hfr1, MAC_HWF1R, RSSEN); 1299572890efSRavi Kumar hw_feat->tc_cnt = AXGMAC_GET_BITS(mac_hfr1, MAC_HWF1R, NUMTC); 1300572890efSRavi Kumar hw_feat->hash_table_size = AXGMAC_GET_BITS(mac_hfr1, MAC_HWF1R, 1301572890efSRavi Kumar HASHTBLSZ); 1302572890efSRavi Kumar hw_feat->l3l4_filter_num = AXGMAC_GET_BITS(mac_hfr1, MAC_HWF1R, 1303572890efSRavi Kumar L3L4FNUM); 1304572890efSRavi Kumar 1305572890efSRavi Kumar /* Hardware feature register 2 */ 1306572890efSRavi Kumar hw_feat->rx_q_cnt = AXGMAC_GET_BITS(mac_hfr2, MAC_HWF2R, RXQCNT); 1307572890efSRavi Kumar hw_feat->tx_q_cnt = AXGMAC_GET_BITS(mac_hfr2, MAC_HWF2R, TXQCNT); 1308572890efSRavi Kumar hw_feat->rx_ch_cnt = AXGMAC_GET_BITS(mac_hfr2, MAC_HWF2R, RXCHCNT); 1309572890efSRavi Kumar hw_feat->tx_ch_cnt = AXGMAC_GET_BITS(mac_hfr2, MAC_HWF2R, TXCHCNT); 1310572890efSRavi Kumar hw_feat->pps_out_num = AXGMAC_GET_BITS(mac_hfr2, MAC_HWF2R, PPSOUTNUM); 1311572890efSRavi Kumar hw_feat->aux_snap_num = AXGMAC_GET_BITS(mac_hfr2, MAC_HWF2R, 1312572890efSRavi Kumar AUXSNAPNUM); 1313572890efSRavi Kumar 1314572890efSRavi Kumar /* Translate the Hash Table size into actual number */ 1315572890efSRavi Kumar switch (hw_feat->hash_table_size) { 1316572890efSRavi Kumar case 0: 1317572890efSRavi Kumar break; 1318572890efSRavi Kumar case 1: 1319572890efSRavi Kumar hw_feat->hash_table_size = 64; 1320572890efSRavi Kumar break; 1321572890efSRavi Kumar case 2: 1322572890efSRavi Kumar hw_feat->hash_table_size = 128; 1323572890efSRavi Kumar break; 1324572890efSRavi Kumar case 3: 1325572890efSRavi Kumar hw_feat->hash_table_size = 256; 1326572890efSRavi Kumar break; 1327572890efSRavi Kumar } 1328572890efSRavi Kumar 1329572890efSRavi Kumar /* Translate the address width setting into actual number */ 1330572890efSRavi Kumar switch (hw_feat->dma_width) { 1331572890efSRavi Kumar case 0: 1332572890efSRavi Kumar hw_feat->dma_width = 32; 1333572890efSRavi Kumar break; 1334572890efSRavi Kumar case 1: 1335572890efSRavi Kumar hw_feat->dma_width = 40; 1336572890efSRavi Kumar break; 1337572890efSRavi Kumar case 2: 1338572890efSRavi Kumar hw_feat->dma_width = 48; 1339572890efSRavi Kumar break; 1340572890efSRavi Kumar default: 1341572890efSRavi Kumar hw_feat->dma_width = 32; 1342572890efSRavi Kumar } 1343572890efSRavi Kumar 1344572890efSRavi Kumar /* The Queue, Channel and TC counts are zero based so increment them 1345572890efSRavi Kumar * to get the actual number 1346572890efSRavi Kumar */ 1347572890efSRavi Kumar hw_feat->rx_q_cnt++; 1348572890efSRavi Kumar hw_feat->tx_q_cnt++; 1349572890efSRavi Kumar hw_feat->rx_ch_cnt++; 1350572890efSRavi Kumar hw_feat->tx_ch_cnt++; 1351572890efSRavi Kumar hw_feat->tc_cnt++; 1352572890efSRavi Kumar 1353572890efSRavi Kumar /* Translate the fifo sizes into actual numbers */ 1354572890efSRavi Kumar hw_feat->rx_fifo_size = 1 << (hw_feat->rx_fifo_size + 7); 1355572890efSRavi Kumar hw_feat->tx_fifo_size = 1 << (hw_feat->tx_fifo_size + 7); 1356572890efSRavi Kumar } 1357572890efSRavi Kumar 1358572890efSRavi Kumar static void axgbe_init_all_fptrs(struct axgbe_port *pdata) 1359572890efSRavi Kumar { 1360572890efSRavi Kumar axgbe_init_function_ptrs_dev(&pdata->hw_if); 13614ac7516bSRavi Kumar axgbe_init_function_ptrs_phy(&pdata->phy_if); 13624ac7516bSRavi Kumar axgbe_init_function_ptrs_i2c(&pdata->i2c_if); 13634ac7516bSRavi Kumar pdata->vdata->init_function_ptrs_phy_impl(&pdata->phy_if); 1364572890efSRavi Kumar } 1365572890efSRavi Kumar 1366572890efSRavi Kumar static void axgbe_set_counts(struct axgbe_port *pdata) 1367572890efSRavi Kumar { 1368572890efSRavi Kumar /* Set all the function pointers */ 1369572890efSRavi Kumar axgbe_init_all_fptrs(pdata); 1370572890efSRavi Kumar 1371572890efSRavi Kumar /* Populate the hardware features */ 1372572890efSRavi Kumar axgbe_get_all_hw_features(pdata); 1373572890efSRavi Kumar 1374572890efSRavi Kumar /* Set default max values if not provided */ 1375572890efSRavi Kumar if (!pdata->tx_max_channel_count) 1376572890efSRavi Kumar pdata->tx_max_channel_count = pdata->hw_feat.tx_ch_cnt; 1377572890efSRavi Kumar if (!pdata->rx_max_channel_count) 1378572890efSRavi Kumar pdata->rx_max_channel_count = pdata->hw_feat.rx_ch_cnt; 1379572890efSRavi Kumar 1380572890efSRavi Kumar if (!pdata->tx_max_q_count) 1381572890efSRavi Kumar pdata->tx_max_q_count = pdata->hw_feat.tx_q_cnt; 1382572890efSRavi Kumar if (!pdata->rx_max_q_count) 1383572890efSRavi Kumar pdata->rx_max_q_count = pdata->hw_feat.rx_q_cnt; 1384572890efSRavi Kumar 1385572890efSRavi Kumar /* Calculate the number of Tx and Rx rings to be created 1386572890efSRavi Kumar * -Tx (DMA) Channels map 1-to-1 to Tx Queues so set 1387572890efSRavi Kumar * the number of Tx queues to the number of Tx channels 1388572890efSRavi Kumar * enabled 1389572890efSRavi Kumar * -Rx (DMA) Channels do not map 1-to-1 so use the actual 1390572890efSRavi Kumar * number of Rx queues or maximum allowed 1391572890efSRavi Kumar */ 1392572890efSRavi Kumar pdata->tx_ring_count = RTE_MIN(pdata->hw_feat.tx_ch_cnt, 1393572890efSRavi Kumar pdata->tx_max_channel_count); 1394572890efSRavi Kumar pdata->tx_ring_count = RTE_MIN(pdata->tx_ring_count, 1395572890efSRavi Kumar pdata->tx_max_q_count); 1396572890efSRavi Kumar 1397572890efSRavi Kumar pdata->tx_q_count = pdata->tx_ring_count; 1398572890efSRavi Kumar 1399572890efSRavi Kumar pdata->rx_ring_count = RTE_MIN(pdata->hw_feat.rx_ch_cnt, 1400572890efSRavi Kumar pdata->rx_max_channel_count); 1401572890efSRavi Kumar 1402572890efSRavi Kumar pdata->rx_q_count = RTE_MIN(pdata->hw_feat.rx_q_cnt, 1403572890efSRavi Kumar pdata->rx_max_q_count); 1404572890efSRavi Kumar } 1405572890efSRavi Kumar 1406572890efSRavi Kumar static void axgbe_default_config(struct axgbe_port *pdata) 1407572890efSRavi Kumar { 1408572890efSRavi Kumar pdata->pblx8 = DMA_PBL_X8_ENABLE; 1409572890efSRavi Kumar pdata->tx_sf_mode = MTL_TSF_ENABLE; 1410572890efSRavi Kumar pdata->tx_threshold = MTL_TX_THRESHOLD_64; 1411572890efSRavi Kumar pdata->tx_pbl = DMA_PBL_32; 1412572890efSRavi Kumar pdata->tx_osp_mode = DMA_OSP_ENABLE; 1413572890efSRavi Kumar pdata->rx_sf_mode = MTL_RSF_ENABLE; 1414572890efSRavi Kumar pdata->rx_threshold = MTL_RX_THRESHOLD_64; 1415572890efSRavi Kumar pdata->rx_pbl = DMA_PBL_32; 1416572890efSRavi Kumar pdata->pause_autoneg = 1; 1417572890efSRavi Kumar pdata->tx_pause = 0; 1418572890efSRavi Kumar pdata->rx_pause = 0; 1419572890efSRavi Kumar pdata->phy_speed = SPEED_UNKNOWN; 1420572890efSRavi Kumar pdata->power_down = 0; 1421572890efSRavi Kumar } 1422572890efSRavi Kumar 1423991e0b1dSSelwin Sebastian static int 1424991e0b1dSSelwin Sebastian pci_device_cmp(const struct rte_device *dev, const void *_pci_id) 1425991e0b1dSSelwin Sebastian { 1426991e0b1dSSelwin Sebastian const struct rte_pci_device *pdev = RTE_DEV_TO_PCI_CONST(dev); 1427991e0b1dSSelwin Sebastian const struct rte_pci_id *pcid = _pci_id; 1428991e0b1dSSelwin Sebastian 1429991e0b1dSSelwin Sebastian if (pdev->id.vendor_id == AMD_PCI_VENDOR_ID && 1430991e0b1dSSelwin Sebastian pdev->id.device_id == pcid->device_id) 1431991e0b1dSSelwin Sebastian return 0; 1432991e0b1dSSelwin Sebastian return 1; 1433991e0b1dSSelwin Sebastian } 1434991e0b1dSSelwin Sebastian 1435991e0b1dSSelwin Sebastian static bool 1436991e0b1dSSelwin Sebastian pci_search_device(int device_id) 1437991e0b1dSSelwin Sebastian { 1438991e0b1dSSelwin Sebastian struct rte_bus *pci_bus; 1439991e0b1dSSelwin Sebastian struct rte_pci_id dev_id; 1440991e0b1dSSelwin Sebastian 1441991e0b1dSSelwin Sebastian dev_id.device_id = device_id; 1442991e0b1dSSelwin Sebastian pci_bus = rte_bus_find_by_name("pci"); 1443991e0b1dSSelwin Sebastian return (pci_bus != NULL) && 1444991e0b1dSSelwin Sebastian (pci_bus->find_device(NULL, pci_device_cmp, &dev_id) != NULL); 1445991e0b1dSSelwin Sebastian } 1446991e0b1dSSelwin Sebastian 14478691632fSRavi Kumar /* 14488691632fSRavi Kumar * It returns 0 on success. 14498691632fSRavi Kumar */ 14508691632fSRavi Kumar static int 14518691632fSRavi Kumar eth_axgbe_dev_init(struct rte_eth_dev *eth_dev) 14528691632fSRavi Kumar { 14538691632fSRavi Kumar PMD_INIT_FUNC_TRACE(); 14548691632fSRavi Kumar struct axgbe_port *pdata; 14558691632fSRavi Kumar struct rte_pci_device *pci_dev; 1456572890efSRavi Kumar uint32_t reg, mac_lo, mac_hi; 145749a5e622SChandu Babu N uint32_t len; 1458572890efSRavi Kumar int ret; 14598691632fSRavi Kumar 14609e890103SRavi Kumar eth_dev->dev_ops = &axgbe_eth_dev_ops; 14619e890103SRavi Kumar 14628691632fSRavi Kumar /* 14638691632fSRavi Kumar * For secondary processes, we don't initialise any further as primary 14648691632fSRavi Kumar * has already done this work. 14658691632fSRavi Kumar */ 14668691632fSRavi Kumar if (rte_eal_process_type() != RTE_PROC_PRIMARY) 14678691632fSRavi Kumar return 0; 14688691632fSRavi Kumar 14690bc212a8SStephen Hemminger pdata = eth_dev->data->dev_private; 1470572890efSRavi Kumar /* initial state */ 1471572890efSRavi Kumar axgbe_set_bit(AXGBE_DOWN, &pdata->dev_state); 1472572890efSRavi Kumar axgbe_set_bit(AXGBE_STOPPED, &pdata->dev_state); 14738691632fSRavi Kumar pdata->eth_dev = eth_dev; 14748691632fSRavi Kumar 14758691632fSRavi Kumar pci_dev = RTE_DEV_TO_PCI(eth_dev->device); 14768691632fSRavi Kumar pdata->pci_dev = pci_dev; 14778691632fSRavi Kumar 1478991e0b1dSSelwin Sebastian /* 1479991e0b1dSSelwin Sebastian * Use root complex device ID to differentiate RV AXGBE vs SNOWY AXGBE 1480991e0b1dSSelwin Sebastian */ 1481991e0b1dSSelwin Sebastian if (pci_search_device(AMD_PCI_RV_ROOT_COMPLEX_ID)) { 1482991e0b1dSSelwin Sebastian pdata->xpcs_window_def_reg = PCS_V2_RV_WINDOW_DEF; 1483991e0b1dSSelwin Sebastian pdata->xpcs_window_sel_reg = PCS_V2_RV_WINDOW_SELECT; 1484991e0b1dSSelwin Sebastian } else { 1485991e0b1dSSelwin Sebastian pdata->xpcs_window_def_reg = PCS_V2_WINDOW_DEF; 1486991e0b1dSSelwin Sebastian pdata->xpcs_window_sel_reg = PCS_V2_WINDOW_SELECT; 1487991e0b1dSSelwin Sebastian } 1488991e0b1dSSelwin Sebastian 1489572890efSRavi Kumar pdata->xgmac_regs = 14907784d0d3SRavi Kumar (void *)pci_dev->mem_resource[AXGBE_AXGMAC_BAR].addr; 14917784d0d3SRavi Kumar pdata->xprop_regs = (void *)((uint8_t *)pdata->xgmac_regs 14927784d0d3SRavi Kumar + AXGBE_MAC_PROP_OFFSET); 14937784d0d3SRavi Kumar pdata->xi2c_regs = (void *)((uint8_t *)pdata->xgmac_regs 14947784d0d3SRavi Kumar + AXGBE_I2C_CTRL_OFFSET); 14957784d0d3SRavi Kumar pdata->xpcs_regs = (void *)pci_dev->mem_resource[AXGBE_XPCS_BAR].addr; 1496572890efSRavi Kumar 1497572890efSRavi Kumar /* version specific driver data*/ 1498572890efSRavi Kumar if (pci_dev->id.device_id == AMD_PCI_AXGBE_DEVICE_V2A) 1499572890efSRavi Kumar pdata->vdata = &axgbe_v2a; 1500572890efSRavi Kumar else 1501572890efSRavi Kumar pdata->vdata = &axgbe_v2b; 1502572890efSRavi Kumar 1503572890efSRavi Kumar /* Configure the PCS indirect addressing support */ 1504991e0b1dSSelwin Sebastian reg = XPCS32_IOREAD(pdata, pdata->xpcs_window_def_reg); 1505572890efSRavi Kumar pdata->xpcs_window = XPCS_GET_BITS(reg, PCS_V2_WINDOW_DEF, OFFSET); 1506572890efSRavi Kumar pdata->xpcs_window <<= 6; 1507572890efSRavi Kumar pdata->xpcs_window_size = XPCS_GET_BITS(reg, PCS_V2_WINDOW_DEF, SIZE); 1508572890efSRavi Kumar pdata->xpcs_window_size = 1 << (pdata->xpcs_window_size + 7); 1509572890efSRavi Kumar pdata->xpcs_window_mask = pdata->xpcs_window_size - 1; 1510991e0b1dSSelwin Sebastian 1511572890efSRavi Kumar PMD_INIT_LOG(DEBUG, 1512572890efSRavi Kumar "xpcs window :%x, size :%x, mask :%x ", pdata->xpcs_window, 1513572890efSRavi Kumar pdata->xpcs_window_size, pdata->xpcs_window_mask); 1514572890efSRavi Kumar XP_IOWRITE(pdata, XP_INT_EN, 0x1fffff); 1515572890efSRavi Kumar 1516572890efSRavi Kumar /* Retrieve the MAC address */ 1517572890efSRavi Kumar mac_lo = XP_IOREAD(pdata, XP_MAC_ADDR_LO); 1518572890efSRavi Kumar mac_hi = XP_IOREAD(pdata, XP_MAC_ADDR_HI); 1519572890efSRavi Kumar pdata->mac_addr.addr_bytes[0] = mac_lo & 0xff; 1520572890efSRavi Kumar pdata->mac_addr.addr_bytes[1] = (mac_lo >> 8) & 0xff; 1521572890efSRavi Kumar pdata->mac_addr.addr_bytes[2] = (mac_lo >> 16) & 0xff; 1522572890efSRavi Kumar pdata->mac_addr.addr_bytes[3] = (mac_lo >> 24) & 0xff; 1523572890efSRavi Kumar pdata->mac_addr.addr_bytes[4] = mac_hi & 0xff; 1524572890efSRavi Kumar pdata->mac_addr.addr_bytes[5] = (mac_hi >> 8) & 0xff; 1525572890efSRavi Kumar 152649a5e622SChandu Babu N len = RTE_ETHER_ADDR_LEN * AXGBE_MAX_MAC_ADDRS; 152749a5e622SChandu Babu N eth_dev->data->mac_addrs = rte_zmalloc("axgbe_mac_addr", len, 0); 152849a5e622SChandu Babu N 1529572890efSRavi Kumar if (!eth_dev->data->mac_addrs) { 1530572890efSRavi Kumar PMD_INIT_LOG(ERR, 153149a5e622SChandu Babu N "Failed to alloc %u bytes needed to " 153249a5e622SChandu Babu N "store MAC addresses", len); 1533572890efSRavi Kumar return -ENOMEM; 1534572890efSRavi Kumar } 1535572890efSRavi Kumar 1536e01d9b2eSChandu Babu N /* Allocate memory for storing hash filter MAC addresses */ 1537e01d9b2eSChandu Babu N len = RTE_ETHER_ADDR_LEN * AXGBE_MAX_HASH_MAC_ADDRS; 1538e01d9b2eSChandu Babu N eth_dev->data->hash_mac_addrs = rte_zmalloc("axgbe_hash_mac_addr", 1539e01d9b2eSChandu Babu N len, 0); 1540e01d9b2eSChandu Babu N 1541e01d9b2eSChandu Babu N if (eth_dev->data->hash_mac_addrs == NULL) { 1542e01d9b2eSChandu Babu N PMD_INIT_LOG(ERR, 1543e01d9b2eSChandu Babu N "Failed to allocate %d bytes needed to " 1544e01d9b2eSChandu Babu N "store MAC addresses", len); 1545e01d9b2eSChandu Babu N return -ENOMEM; 1546e01d9b2eSChandu Babu N } 1547e01d9b2eSChandu Babu N 1548538da7a1SOlivier Matz if (!rte_is_valid_assigned_ether_addr(&pdata->mac_addr)) 1549538da7a1SOlivier Matz rte_eth_random_addr(pdata->mac_addr.addr_bytes); 1550572890efSRavi Kumar 1551572890efSRavi Kumar /* Copy the permanent MAC address */ 1552538da7a1SOlivier Matz rte_ether_addr_copy(&pdata->mac_addr, ð_dev->data->mac_addrs[0]); 1553572890efSRavi Kumar 1554572890efSRavi Kumar /* Clock settings */ 1555572890efSRavi Kumar pdata->sysclk_rate = AXGBE_V2_DMA_CLOCK_FREQ; 1556572890efSRavi Kumar pdata->ptpclk_rate = AXGBE_V2_PTP_CLOCK_FREQ; 1557572890efSRavi Kumar 1558572890efSRavi Kumar /* Set the DMA coherency values */ 1559572890efSRavi Kumar pdata->coherent = 1; 1560572890efSRavi Kumar pdata->axdomain = AXGBE_DMA_OS_AXDOMAIN; 1561572890efSRavi Kumar pdata->arcache = AXGBE_DMA_OS_ARCACHE; 1562572890efSRavi Kumar pdata->awcache = AXGBE_DMA_OS_AWCACHE; 1563572890efSRavi Kumar 1564572890efSRavi Kumar /* Set the maximum channels and queues */ 1565572890efSRavi Kumar reg = XP_IOREAD(pdata, XP_PROP_1); 1566572890efSRavi Kumar pdata->tx_max_channel_count = XP_GET_BITS(reg, XP_PROP_1, MAX_TX_DMA); 1567572890efSRavi Kumar pdata->rx_max_channel_count = XP_GET_BITS(reg, XP_PROP_1, MAX_RX_DMA); 1568572890efSRavi Kumar pdata->tx_max_q_count = XP_GET_BITS(reg, XP_PROP_1, MAX_TX_QUEUES); 1569572890efSRavi Kumar pdata->rx_max_q_count = XP_GET_BITS(reg, XP_PROP_1, MAX_RX_QUEUES); 1570572890efSRavi Kumar 1571572890efSRavi Kumar /* Set the hardware channel and queue counts */ 1572572890efSRavi Kumar axgbe_set_counts(pdata); 1573572890efSRavi Kumar 1574572890efSRavi Kumar /* Set the maximum fifo amounts */ 1575572890efSRavi Kumar reg = XP_IOREAD(pdata, XP_PROP_2); 1576572890efSRavi Kumar pdata->tx_max_fifo_size = XP_GET_BITS(reg, XP_PROP_2, TX_FIFO_SIZE); 1577572890efSRavi Kumar pdata->tx_max_fifo_size *= 16384; 1578572890efSRavi Kumar pdata->tx_max_fifo_size = RTE_MIN(pdata->tx_max_fifo_size, 1579572890efSRavi Kumar pdata->vdata->tx_max_fifo_size); 1580572890efSRavi Kumar pdata->rx_max_fifo_size = XP_GET_BITS(reg, XP_PROP_2, RX_FIFO_SIZE); 1581572890efSRavi Kumar pdata->rx_max_fifo_size *= 16384; 1582572890efSRavi Kumar pdata->rx_max_fifo_size = RTE_MIN(pdata->rx_max_fifo_size, 1583572890efSRavi Kumar pdata->vdata->rx_max_fifo_size); 1584572890efSRavi Kumar /* Issue software reset to DMA */ 1585572890efSRavi Kumar ret = pdata->hw_if.exit(pdata); 1586572890efSRavi Kumar if (ret) 1587572890efSRavi Kumar PMD_DRV_LOG(ERR, "hw_if->exit EBUSY error\n"); 1588572890efSRavi Kumar 1589572890efSRavi Kumar /* Set default configuration data */ 1590572890efSRavi Kumar axgbe_default_config(pdata); 1591572890efSRavi Kumar 1592572890efSRavi Kumar /* Set default max values if not provided */ 1593572890efSRavi Kumar if (!pdata->tx_max_fifo_size) 1594572890efSRavi Kumar pdata->tx_max_fifo_size = pdata->hw_feat.tx_fifo_size; 1595572890efSRavi Kumar if (!pdata->rx_max_fifo_size) 1596572890efSRavi Kumar pdata->rx_max_fifo_size = pdata->hw_feat.rx_fifo_size; 1597572890efSRavi Kumar 15989e890103SRavi Kumar pdata->tx_desc_count = AXGBE_MAX_RING_DESC; 15999e890103SRavi Kumar pdata->rx_desc_count = AXGBE_MAX_RING_DESC; 1600572890efSRavi Kumar pthread_mutex_init(&pdata->xpcs_mutex, NULL); 1601572890efSRavi Kumar pthread_mutex_init(&pdata->i2c_mutex, NULL); 1602572890efSRavi Kumar pthread_mutex_init(&pdata->an_mutex, NULL); 1603572890efSRavi Kumar pthread_mutex_init(&pdata->phy_mutex, NULL); 1604572890efSRavi Kumar 16054ac7516bSRavi Kumar ret = pdata->phy_if.phy_init(pdata); 16064ac7516bSRavi Kumar if (ret) { 16074ac7516bSRavi Kumar rte_free(eth_dev->data->mac_addrs); 1608e7f2fa88SDavid Marchand eth_dev->data->mac_addrs = NULL; 16094ac7516bSRavi Kumar return ret; 16104ac7516bSRavi Kumar } 16114ac7516bSRavi Kumar 1612456ff159SRavi Kumar rte_intr_callback_register(&pci_dev->intr_handle, 1613456ff159SRavi Kumar axgbe_dev_interrupt_handler, 1614456ff159SRavi Kumar (void *)eth_dev); 16158691632fSRavi Kumar PMD_INIT_LOG(DEBUG, "port %d vendorID=0x%x deviceID=0x%x", 16168691632fSRavi Kumar eth_dev->data->port_id, pci_dev->id.vendor_id, 16178691632fSRavi Kumar pci_dev->id.device_id); 16188691632fSRavi Kumar 16198691632fSRavi Kumar return 0; 16208691632fSRavi Kumar } 16218691632fSRavi Kumar 16228691632fSRavi Kumar static int 1623572890efSRavi Kumar eth_axgbe_dev_uninit(struct rte_eth_dev *eth_dev) 16248691632fSRavi Kumar { 1625456ff159SRavi Kumar struct rte_pci_device *pci_dev; 1626456ff159SRavi Kumar 16278691632fSRavi Kumar PMD_INIT_FUNC_TRACE(); 16288691632fSRavi Kumar 1629572890efSRavi Kumar if (rte_eal_process_type() != RTE_PROC_PRIMARY) 1630572890efSRavi Kumar return 0; 1631572890efSRavi Kumar 1632456ff159SRavi Kumar pci_dev = RTE_DEV_TO_PCI(eth_dev->device); 16339e890103SRavi Kumar eth_dev->dev_ops = NULL; 16348590b93dSRavi Kumar eth_dev->rx_pkt_burst = NULL; 16358590b93dSRavi Kumar eth_dev->tx_pkt_burst = NULL; 16369e890103SRavi Kumar axgbe_dev_clear_queues(eth_dev); 1637572890efSRavi Kumar 1638456ff159SRavi Kumar /* disable uio intr before callback unregister */ 1639456ff159SRavi Kumar rte_intr_disable(&pci_dev->intr_handle); 1640456ff159SRavi Kumar rte_intr_callback_unregister(&pci_dev->intr_handle, 1641456ff159SRavi Kumar axgbe_dev_interrupt_handler, 1642456ff159SRavi Kumar (void *)eth_dev); 1643456ff159SRavi Kumar 16448691632fSRavi Kumar return 0; 16458691632fSRavi Kumar } 16468691632fSRavi Kumar 16478691632fSRavi Kumar static int eth_axgbe_pci_probe(struct rte_pci_driver *pci_drv __rte_unused, 16488691632fSRavi Kumar struct rte_pci_device *pci_dev) 16498691632fSRavi Kumar { 16508691632fSRavi Kumar return rte_eth_dev_pci_generic_probe(pci_dev, 16518691632fSRavi Kumar sizeof(struct axgbe_port), eth_axgbe_dev_init); 16528691632fSRavi Kumar } 16538691632fSRavi Kumar 16548691632fSRavi Kumar static int eth_axgbe_pci_remove(struct rte_pci_device *pci_dev) 16558691632fSRavi Kumar { 16568691632fSRavi Kumar return rte_eth_dev_pci_generic_remove(pci_dev, eth_axgbe_dev_uninit); 16578691632fSRavi Kumar } 16588691632fSRavi Kumar 16598691632fSRavi Kumar static struct rte_pci_driver rte_axgbe_pmd = { 16608691632fSRavi Kumar .id_table = pci_id_axgbe_map, 16618691632fSRavi Kumar .drv_flags = RTE_PCI_DRV_NEED_MAPPING, 16628691632fSRavi Kumar .probe = eth_axgbe_pci_probe, 16638691632fSRavi Kumar .remove = eth_axgbe_pci_remove, 16648691632fSRavi Kumar }; 16658691632fSRavi Kumar 16668691632fSRavi Kumar RTE_PMD_REGISTER_PCI(net_axgbe, rte_axgbe_pmd); 16678691632fSRavi Kumar RTE_PMD_REGISTER_PCI_TABLE(net_axgbe, pci_id_axgbe_map); 16688691632fSRavi Kumar RTE_PMD_REGISTER_KMOD_DEP(net_axgbe, "* igb_uio | uio_pci_generic | vfio-pci"); 16698691632fSRavi Kumar 1670f8e99896SThomas Monjalon RTE_INIT(axgbe_init_log) 16718691632fSRavi Kumar { 16728691632fSRavi Kumar axgbe_logtype_init = rte_log_register("pmd.net.axgbe.init"); 16738691632fSRavi Kumar if (axgbe_logtype_init >= 0) 16748691632fSRavi Kumar rte_log_set_level(axgbe_logtype_init, RTE_LOG_NOTICE); 16758691632fSRavi Kumar axgbe_logtype_driver = rte_log_register("pmd.net.axgbe.driver"); 16768691632fSRavi Kumar if (axgbe_logtype_driver >= 0) 16778691632fSRavi Kumar rte_log_set_level(axgbe_logtype_driver, RTE_LOG_NOTICE); 16788691632fSRavi Kumar } 1679