X-Git-Url: http://git.droids-corp.org/?a=blobdiff_plain;f=drivers%2Fnet%2Fhns3%2Fhns3_ethdev.c;h=d4751d4780439b0769a92cc99552201b3f0857d5;hb=6dca716c9e1daa8ea770a4a198bd068e72a2e03c;hp=4ce9515a9285ff9a53f56315ec842e33105f7a21;hpb=89c04d81175aaf6b0277f1f1d2345d6daf97df43;p=dpdk.git diff --git a/drivers/net/hns3/hns3_ethdev.c b/drivers/net/hns3/hns3_ethdev.c index 4ce9515a92..d4751d4780 100644 --- a/drivers/net/hns3/hns3_ethdev.c +++ b/drivers/net/hns3/hns3_ethdev.c @@ -1473,8 +1473,6 @@ hns3_remove_mac_addr(struct rte_eth_dev *dev, uint32_t idx) return; } - if (idx == 0) - hw->mac.default_addr_setted = false; rte_spinlock_unlock(&hw->lock); } @@ -2061,10 +2059,11 @@ hns3_bind_ring_with_vector(struct rte_eth_dev *dev, uint8_t vector_id, static int hns3_dev_configure(struct rte_eth_dev *dev) { - struct hns3_hw *hw = HNS3_DEV_PRIVATE_TO_HW(dev->data->dev_private); - struct hns3_rss_conf *rss_cfg = &hw->rss_info; + struct hns3_adapter *hns = dev->data->dev_private; struct rte_eth_conf *conf = &dev->data->dev_conf; enum rte_eth_rx_mq_mode mq_mode = conf->rxmode.mq_mode; + struct hns3_hw *hw = &hns->hw; + struct hns3_rss_conf *rss_cfg = &hw->rss_info; uint16_t nb_rx_q = dev->data->nb_rx_queues; uint16_t nb_tx_q = dev->data->nb_tx_queues; struct rte_eth_rss_conf rss_conf; @@ -2072,23 +2071,28 @@ hns3_dev_configure(struct rte_eth_dev *dev) int ret; /* - * Hardware does not support where the number of rx and tx queues is - * not equal in hip08. + * Hardware does not support individually enable/disable/reset the Tx or + * Rx queue in hns3 network engine. Driver must enable/disable/reset Tx + * and Rx queues at the same time. When the numbers of Tx queues + * allocated by upper applications are not equal to the numbers of Rx + * queues, driver needs to setup fake Tx or Rx queues to adjust numbers + * of Tx/Rx queues. otherwise, network engine can not work as usual. But + * these fake queues are imperceptible, and can not be used by upper + * applications. */ - if (nb_rx_q != nb_tx_q) { - hns3_err(hw, - "nb_rx_queues(%u) not equal with nb_tx_queues(%u)! " - "Hardware does not support this configuration!", - nb_rx_q, nb_tx_q); - return -EINVAL; + ret = hns3_set_fake_rx_or_tx_queues(dev, nb_rx_q, nb_tx_q); + if (ret) { + hns3_err(hw, "Failed to set rx/tx fake queues: %d", ret); + return ret; } + hw->adapter_state = HNS3_NIC_CONFIGURING; if (conf->link_speeds & ETH_LINK_SPEED_FIXED) { hns3_err(hw, "setting link speed/duplex not supported"); - return -EINVAL; + ret = -EINVAL; + goto cfg_err; } - hw->adapter_state = HNS3_NIC_CONFIGURING; if ((uint32_t)mq_mode & ETH_MQ_RX_DCB_FLAG) { ret = hns3_check_dcb_cfg(dev); if (ret) @@ -2134,7 +2138,9 @@ hns3_dev_configure(struct rte_eth_dev *dev) return 0; cfg_err: + (void)hns3_set_fake_rx_or_tx_queues(dev, 0, 0); hw->adapter_state = HNS3_NIC_INITIALIZED; + return ret; } @@ -2250,6 +2256,10 @@ hns3_dev_infos_get(struct rte_eth_dev *eth_dev, struct rte_eth_dev_info *info) DEV_TX_OFFLOAD_VLAN_INSERT | DEV_TX_OFFLOAD_QINQ_INSERT | DEV_TX_OFFLOAD_MULTI_SEGS | + DEV_TX_OFFLOAD_TCP_TSO | + DEV_TX_OFFLOAD_VXLAN_TNL_TSO | + DEV_TX_OFFLOAD_GRE_TNL_TSO | + DEV_TX_OFFLOAD_GENEVE_TNL_TSO | info->tx_queue_offload_capa); info->rx_desc_lim = (struct rte_eth_desc_lim) { @@ -2400,6 +2410,7 @@ hns3_query_pf_resource(struct hns3_hw *hw) hw->total_tqps_num = rte_le_to_cpu_16(req->tqp_num); pf->pkt_buf_size = rte_le_to_cpu_16(req->buf_size) << HNS3_BUF_UNIT_S; hw->tqps_num = RTE_MIN(hw->total_tqps_num, HNS3_MAX_TQP_NUM_PER_FUNC); + pf->func_num = rte_le_to_cpu_16(req->pf_own_fun_number); if (req->tx_buf_size) pf->tx_buf_size = @@ -2676,6 +2687,7 @@ hns3_map_tqp(struct hns3_hw *hw) uint16_t tqps_num = hw->total_tqps_num; uint16_t func_id; uint16_t tqp_id; + bool is_pf; int num; int ret; int i; @@ -2687,10 +2699,11 @@ hns3_map_tqp(struct hns3_hw *hw) tqp_id = 0; num = DIV_ROUND_UP(hw->total_tqps_num, HNS3_MAX_TQP_NUM_PER_FUNC); for (func_id = 0; func_id < num; func_id++) { + is_pf = func_id == 0 ? true : false; for (i = 0; i < HNS3_MAX_TQP_NUM_PER_FUNC && tqp_id < tqps_num; i++) { ret = hns3_map_tqps_to_func(hw, func_id, tqp_id++, i, - true); + is_pf); if (ret) return ret; } @@ -3591,13 +3604,33 @@ hns3_set_promisc_mode(struct hns3_hw *hw, bool en_uc_pmc, bool en_mc_pmc) return 0; } +static int +hns3_clear_all_vfs_promisc_mode(struct hns3_hw *hw) +{ + struct hns3_adapter *hns = HNS3_DEV_HW_TO_ADAPTER(hw); + struct hns3_pf *pf = &hns->pf; + struct hns3_promisc_param param; + uint16_t func_id; + int ret; + + /* func_id 0 is denoted PF, the VFs start from 1 */ + for (func_id = 1; func_id < pf->func_num; func_id++) { + hns3_promisc_param_init(¶m, false, false, false, func_id); + ret = hns3_cmd_set_promisc_mode(hw, ¶m); + if (ret) + return ret; + } + + return 0; +} + static int hns3_dev_promiscuous_enable(struct rte_eth_dev *dev) { struct hns3_adapter *hns = dev->data->dev_private; struct hns3_hw *hw = &hns->hw; bool en_mc_pmc = (dev->data->all_multicast == 1) ? true : false; - int ret = 0; + int ret; rte_spinlock_lock(&hw->lock); ret = hns3_set_promisc_mode(hw, true, en_mc_pmc); @@ -3614,7 +3647,7 @@ hns3_dev_promiscuous_disable(struct rte_eth_dev *dev) struct hns3_adapter *hns = dev->data->dev_private; struct hns3_hw *hw = &hns->hw; bool en_mc_pmc = (dev->data->all_multicast == 1) ? true : false; - int ret = 0; + int ret; /* If now in all_multicast mode, must remain in all_multicast mode. */ rte_spinlock_lock(&hw->lock); @@ -3632,7 +3665,7 @@ hns3_dev_allmulticast_enable(struct rte_eth_dev *dev) struct hns3_adapter *hns = dev->data->dev_private; struct hns3_hw *hw = &hns->hw; bool en_uc_pmc = (dev->data->promiscuous == 1) ? true : false; - int ret = 0; + int ret; rte_spinlock_lock(&hw->lock); ret = hns3_set_promisc_mode(hw, en_uc_pmc, true); @@ -3649,7 +3682,7 @@ hns3_dev_allmulticast_disable(struct rte_eth_dev *dev) struct hns3_adapter *hns = dev->data->dev_private; struct hns3_hw *hw = &hns->hw; bool en_uc_pmc = (dev->data->promiscuous == 1) ? true : false; - int ret = 0; + int ret; /* If now in promiscuous mode, must remain in all_multicast mode. */ if (dev->data->promiscuous == 1) @@ -3805,7 +3838,7 @@ hns3_get_mac_link_status(struct hns3_hw *hw) ret = hns3_cmd_send(hw, &desc, 1); if (ret) { hns3_err(hw, "get link status cmd failed %d", ret); - return ret; + return ETH_LINK_DOWN; } req = (struct hns3_link_status_cmd *)desc.data; @@ -3878,6 +3911,13 @@ hns3_init_hardware(struct hns3_adapter *hns) goto err_mac_init; } + ret = hns3_clear_all_vfs_promisc_mode(hw); + if (ret) { + PMD_INIT_LOG(ERR, "Failed to clear all vfs promisc mode: %d", + ret); + goto err_mac_init; + } + ret = hns3_init_vlan_config(hns); if (ret) { PMD_INIT_LOG(ERR, "Failed to init vlan: %d", ret); @@ -4084,7 +4124,7 @@ hns3_map_rx_interrupt(struct rte_eth_dev *dev) /* check and configure queue intr-vector mapping */ if (rte_intr_cap_multiple(intr_handle) || !RTE_ETH_DEV_SRIOV(dev).active) { - intr_vector = dev->data->nb_rx_queues; + intr_vector = hw->used_rx_queues; /* creates event fd for each intr vector when MSIX is used */ if (rte_intr_efd_enable(intr_handle, intr_vector)) return -EINVAL; @@ -4092,10 +4132,10 @@ hns3_map_rx_interrupt(struct rte_eth_dev *dev) if (rte_intr_dp_is_en(intr_handle) && !intr_handle->intr_vec) { intr_handle->intr_vec = rte_zmalloc("intr_vec", - dev->data->nb_rx_queues * sizeof(int), 0); + hw->used_rx_queues * sizeof(int), 0); if (intr_handle->intr_vec == NULL) { hns3_err(hw, "Failed to allocate %d rx_queues" - " intr_vec", dev->data->nb_rx_queues); + " intr_vec", hw->used_rx_queues); ret = -ENOMEM; goto alloc_intr_vec_error; } @@ -4106,7 +4146,7 @@ hns3_map_rx_interrupt(struct rte_eth_dev *dev) base = RTE_INTR_VEC_RXTX_OFFSET; } if (rte_intr_dp_is_en(intr_handle)) { - for (q_id = 0; q_id < dev->data->nb_rx_queues; q_id++) { + for (q_id = 0; q_id < hw->used_rx_queues; q_id++) { ret = hns3_bind_ring_with_vector(dev, vec, true, q_id); if (ret) goto bind_vector_error; @@ -4135,7 +4175,7 @@ hns3_dev_start(struct rte_eth_dev *dev) { struct hns3_adapter *hns = dev->data->dev_private; struct hns3_hw *hw = &hns->hw; - int ret = 0; + int ret; PMD_INIT_FUNC_TRACE(); if (rte_atomic16_read(&hw->reset.resetting)) @@ -4159,6 +4199,7 @@ hns3_dev_start(struct rte_eth_dev *dev) return ret; hns3_set_rxtx_function(dev); hns3_mp_req_start_rxtx(dev); + rte_eal_alarm_set(HNS3_SERVICE_INTERVAL, hns3_service_handler, dev); hns3_info(hw, "hns3 dev start successful!"); return 0; @@ -4190,6 +4231,8 @@ hns3_unmap_rx_interrupt(struct rte_eth_dev *dev) { struct rte_pci_device *pci_dev = RTE_ETH_DEV_TO_PCI(dev); struct rte_intr_handle *intr_handle = &pci_dev->intr_handle; + struct hns3_adapter *hns = dev->data->dev_private; + struct hns3_hw *hw = &hns->hw; uint8_t base = 0; uint8_t vec = 0; uint16_t q_id; @@ -4203,7 +4246,7 @@ hns3_unmap_rx_interrupt(struct rte_eth_dev *dev) base = RTE_INTR_VEC_RXTX_OFFSET; } if (rte_intr_dp_is_en(intr_handle)) { - for (q_id = 0; q_id < dev->data->nb_rx_queues; q_id++) { + for (q_id = 0; q_id < hw->used_rx_queues; q_id++) { (void)hns3_bind_ring_with_vector(dev, vec, false, q_id); if (vec < base + intr_handle->nb_efd - 1) vec++; @@ -4239,6 +4282,7 @@ hns3_dev_stop(struct rte_eth_dev *dev) hns3_dev_release_mbufs(hns); hw->adapter_state = HNS3_NIC_CONFIGURED; } + rte_eal_alarm_cancel(hns3_service_handler, dev); rte_spinlock_unlock(&hw->lock); hns3_unmap_rx_interrupt(dev); } @@ -4261,7 +4305,6 @@ hns3_dev_close(struct rte_eth_dev *eth_dev) hw->adapter_state = HNS3_NIC_CLOSING; hns3_reset_abort(hns); hw->adapter_state = HNS3_NIC_CLOSED; - rte_eal_alarm_cancel(hns3_service_handler, eth_dev); hns3_configure_all_mc_mac_addr(hns, true); hns3_remove_all_vlan_table(hns); @@ -4446,15 +4489,13 @@ hns3_get_dcb_info(struct rte_eth_dev *dev, struct rte_eth_dcb_info *dcb_info) for (i = 0; i < dcb_info->nb_tcs; i++) dcb_info->tc_bws[i] = hw->dcb_info.pg_info[0].tc_dwrr[i]; - for (i = 0; i < HNS3_MAX_TC_NUM; i++) { - dcb_info->tc_queue.tc_rxq[0][i].base = - hw->tc_queue[i].tqp_offset; + for (i = 0; i < hw->num_tc; i++) { + dcb_info->tc_queue.tc_rxq[0][i].base = hw->alloc_rss_size * i; dcb_info->tc_queue.tc_txq[0][i].base = - hw->tc_queue[i].tqp_offset; - dcb_info->tc_queue.tc_rxq[0][i].nb_queue = - hw->tc_queue[i].tqp_count; + hw->tc_queue[i].tqp_offset; + dcb_info->tc_queue.tc_rxq[0][i].nb_queue = hw->alloc_rss_size; dcb_info->tc_queue.tc_txq[0][i].nb_queue = - hw->tc_queue[i].tqp_count; + hw->tc_queue[i].tqp_count; } rte_spinlock_unlock(&hw->lock); @@ -4722,7 +4763,8 @@ hns3_stop_service(struct hns3_adapter *hns) struct rte_eth_dev *eth_dev; eth_dev = &rte_eth_devices[hw->data->port_id]; - rte_eal_alarm_cancel(hns3_service_handler, eth_dev); + if (hw->adapter_state == HNS3_NIC_STARTED) + rte_eal_alarm_cancel(hns3_service_handler, eth_dev); hw->mac.link_status = ETH_LINK_DOWN; hns3_set_rxtx_function(eth_dev); @@ -4763,7 +4805,9 @@ hns3_start_service(struct hns3_adapter *hns) eth_dev = &rte_eth_devices[hw->data->port_id]; hns3_set_rxtx_function(eth_dev); hns3_mp_req_start_rxtx(eth_dev); - hns3_service_handler(eth_dev); + if (hw->adapter_state == HNS3_NIC_STARTED) + hns3_service_handler(eth_dev); + return 0; } @@ -5021,7 +5065,6 @@ hns3_dev_init(struct rte_eth_dev *eth_dev) hns3_notify_reset_ready(hw, false); } - rte_eal_alarm_set(HNS3_SERVICE_INTERVAL, hns3_service_handler, eth_dev); hns3_info(hw, "hns3 dev initialization successful!"); return 0;