X-Git-Url: http://git.droids-corp.org/?a=blobdiff_plain;f=drivers%2Fnet%2Fsfc%2Fsfc_port.c;h=32a0894a55d96ea5738695683a32a2292dc69e20;hb=9311beeea4963d8b97330c20ff1736b006486c5d;hp=5eb4b3acafbc99c9597b08969bd7b1c6f01ef747;hpb=ab77a0013a811aacdde49e903786eff7abb308ec;p=dpdk.git diff --git a/drivers/net/sfc/sfc_port.c b/drivers/net/sfc/sfc_port.c index 5eb4b3acaf..32a0894a55 100644 --- a/drivers/net/sfc/sfc_port.c +++ b/drivers/net/sfc/sfc_port.c @@ -1,7 +1,7 @@ /* SPDX-License-Identifier: BSD-3-Clause * - * Copyright (c) 2016-2018 Solarflare Communications Inc. - * All rights reserved. + * Copyright(c) 2019-2020 Xilinx, Inc. + * Copyright(c) 2016-2019 Solarflare Communications Inc. * * This software was jointly developed between OKTET Labs (under contract * for Solarflare) and Solarflare Communications, Inc. @@ -226,8 +226,8 @@ sfc_port_start(struct sfc_adapter *sa) if (rc != 0) goto fail_mac_pdu_set; - if (!port->isolated) { - struct ether_addr *addr = &port->default_mac_addr; + if (!sfc_sa2shared(sa)->isolated) { + struct rte_ether_addr *addr = &port->default_mac_addr; sfc_log_init(sa, "set MAC address"); rc = efx_mac_addr_set(sa->nic, addr->addr_bytes); @@ -239,7 +239,7 @@ sfc_port_start(struct sfc_adapter *sa) B_TRUE : B_FALSE; port->allmulti = (sa->eth_dev->data->all_multicast != 0) ? B_TRUE : B_FALSE; - rc = sfc_set_rx_mode(sa); + rc = sfc_set_rx_mode_unchecked(sa); if (rc != 0) goto fail_mac_filter_set; @@ -386,7 +386,7 @@ sfc_port_attach(struct sfc_adapter *sa) { struct sfc_port *port = &sa->port; const efx_nic_cfg_t *encp = efx_nic_cfg_get(sa->nic); - const struct ether_addr *from; + const struct rte_ether_addr *from; uint32_t mac_nstats; size_t mac_stats_size; long kvarg_stats_update_period_ms; @@ -401,8 +401,8 @@ sfc_port_attach(struct sfc_adapter *sa) port->flow_ctrl_autoneg = B_TRUE; RTE_BUILD_BUG_ON(sizeof(encp->enc_mac_addr) != sizeof(*from)); - from = (const struct ether_addr *)(encp->enc_mac_addr); - ether_addr_copy(from, &port->default_mac_addr); + from = (const struct rte_ether_addr *)(encp->enc_mac_addr); + rte_ether_addr_copy(from, &port->default_mac_addr); port->max_mcast_addrs = EFX_MAC_MULTICAST_LIST_MAX; port->nb_mcast_addrs = 0; @@ -485,16 +485,70 @@ sfc_port_detach(struct sfc_adapter *sa) sfc_log_init(sa, "done"); } +static boolean_t +sfc_get_requested_all_ucast(struct sfc_port *port) +{ + return port->promisc; +} + +static boolean_t +sfc_get_requested_all_mcast(struct sfc_port *port) +{ + return port->promisc || port->allmulti; +} + +int +sfc_set_rx_mode_unchecked(struct sfc_adapter *sa) +{ + struct sfc_port *port = &sa->port; + boolean_t requested_all_ucast = sfc_get_requested_all_ucast(port); + boolean_t requested_all_mcast = sfc_get_requested_all_mcast(port); + int rc; + + rc = efx_mac_filter_set(sa->nic, requested_all_ucast, B_TRUE, + requested_all_mcast, B_TRUE); + if (rc != 0) + return rc; + + return 0; +} + int sfc_set_rx_mode(struct sfc_adapter *sa) { struct sfc_port *port = &sa->port; + boolean_t old_all_ucast; + boolean_t old_all_mcast; + boolean_t requested_all_ucast = sfc_get_requested_all_ucast(port); + boolean_t requested_all_mcast = sfc_get_requested_all_mcast(port); + boolean_t actual_all_ucast; + boolean_t actual_all_mcast; int rc; - rc = efx_mac_filter_set(sa->nic, port->promisc, B_TRUE, - port->promisc || port->allmulti, B_TRUE); + efx_mac_filter_get_all_ucast_mcast(sa->nic, &old_all_ucast, + &old_all_mcast); - return rc; + rc = sfc_set_rx_mode_unchecked(sa); + if (rc != 0) + return rc; + + efx_mac_filter_get_all_ucast_mcast(sa->nic, &actual_all_ucast, + &actual_all_mcast); + + if (actual_all_ucast != requested_all_ucast || + actual_all_mcast != requested_all_mcast) { + /* + * MAC filter set succeeded but not all requested modes + * were applied. The rollback is necessary to bring back the + * consistent old state. + */ + (void)efx_mac_filter_set(sa->nic, old_all_ucast, B_TRUE, + old_all_mcast, B_TRUE); + + return EPERM; + } + + return 0; } void