LCOV - code coverage report
Current view: top level - drivers/common/sfc_efx/base - efx_mac.c (source / functions) Hit Total Coverage
Test: Code coverage Lines: 0 249 0.0 %
Date: 2024-01-22 16:13:49 Functions: 0 22 0.0 %
Legend: Lines: hit not hit | Branches: + taken - not taken # not executed Branches: 0 191 0.0 %

           Branch data     Line data    Source code
       1                 :            : /* SPDX-License-Identifier: BSD-3-Clause
       2                 :            :  *
       3                 :            :  * Copyright(c) 2019-2021 Xilinx, Inc.
       4                 :            :  * Copyright(c) 2007-2019 Solarflare Communications Inc.
       5                 :            :  */
       6                 :            : 
       7                 :            : #include "efx.h"
       8                 :            : #include "efx_impl.h"
       9                 :            : 
      10                 :            : #if EFSYS_OPT_SIENA
      11                 :            : 
      12                 :            : static  __checkReturn   efx_rc_t
      13                 :            : siena_mac_multicast_list_set(
      14                 :            :         __in            efx_nic_t *enp);
      15                 :            : 
      16                 :            : #endif /* EFSYS_OPT_SIENA */
      17                 :            : 
      18                 :            : #if EFSYS_OPT_SIENA
      19                 :            : static const efx_mac_ops_t      __efx_mac_siena_ops = {
      20                 :            :         siena_mac_poll,                         /* emo_poll */
      21                 :            :         siena_mac_up,                           /* emo_up */
      22                 :            :         siena_mac_reconfigure,                  /* emo_addr_set */
      23                 :            :         siena_mac_reconfigure,                  /* emo_pdu_set */
      24                 :            :         siena_mac_pdu_get,                      /* emo_pdu_get */
      25                 :            :         siena_mac_reconfigure,                  /* emo_reconfigure */
      26                 :            :         siena_mac_multicast_list_set,           /* emo_multicast_list_set */
      27                 :            :         NULL,                                   /* emo_filter_set_default_rxq */
      28                 :            :         NULL,                           /* emo_filter_default_rxq_clear */
      29                 :            : #if EFSYS_OPT_LOOPBACK
      30                 :            :         siena_mac_loopback_set,                 /* emo_loopback_set */
      31                 :            : #endif  /* EFSYS_OPT_LOOPBACK */
      32                 :            : #if EFSYS_OPT_MAC_STATS
      33                 :            :         siena_mac_stats_get_mask,               /* emo_stats_get_mask */
      34                 :            :         efx_mcdi_mac_stats_clear,               /* emo_stats_clear */
      35                 :            :         efx_mcdi_mac_stats_upload,              /* emo_stats_upload */
      36                 :            :         efx_mcdi_mac_stats_periodic,            /* emo_stats_periodic */
      37                 :            :         siena_mac_stats_update                  /* emo_stats_update */
      38                 :            : #endif  /* EFSYS_OPT_MAC_STATS */
      39                 :            : };
      40                 :            : #endif  /* EFSYS_OPT_SIENA */
      41                 :            : 
      42                 :            : #if EFX_OPTS_EF10()
      43                 :            : static const efx_mac_ops_t      __efx_mac_ef10_ops = {
      44                 :            :         ef10_mac_poll,                          /* emo_poll */
      45                 :            :         ef10_mac_up,                            /* emo_up */
      46                 :            :         ef10_mac_addr_set,                      /* emo_addr_set */
      47                 :            :         ef10_mac_pdu_set,                       /* emo_pdu_set */
      48                 :            :         ef10_mac_pdu_get,                       /* emo_pdu_get */
      49                 :            :         ef10_mac_reconfigure,                   /* emo_reconfigure */
      50                 :            :         ef10_mac_multicast_list_set,            /* emo_multicast_list_set */
      51                 :            :         ef10_mac_filter_default_rxq_set,        /* emo_filter_default_rxq_set */
      52                 :            :         ef10_mac_filter_default_rxq_clear,
      53                 :            :                                         /* emo_filter_default_rxq_clear */
      54                 :            : #if EFSYS_OPT_LOOPBACK
      55                 :            :         ef10_mac_loopback_set,                  /* emo_loopback_set */
      56                 :            : #endif  /* EFSYS_OPT_LOOPBACK */
      57                 :            : #if EFSYS_OPT_MAC_STATS
      58                 :            :         ef10_mac_stats_get_mask,                /* emo_stats_get_mask */
      59                 :            :         efx_mcdi_mac_stats_clear,               /* emo_stats_clear */
      60                 :            :         efx_mcdi_mac_stats_upload,              /* emo_stats_upload */
      61                 :            :         efx_mcdi_mac_stats_periodic,            /* emo_stats_periodic */
      62                 :            :         ef10_mac_stats_update                   /* emo_stats_update */
      63                 :            : #endif  /* EFSYS_OPT_MAC_STATS */
      64                 :            : };
      65                 :            : #endif  /* EFX_OPTS_EF10() */
      66                 :            : 
      67                 :            : #if EFSYS_OPT_RIVERHEAD
      68                 :            : static const efx_mac_ops_t      __efx_mac_rhead_ops = {
      69                 :            :         ef10_mac_poll,                          /* emo_poll */
      70                 :            :         ef10_mac_up,                            /* emo_up */
      71                 :            :         ef10_mac_addr_set,                      /* emo_addr_set */
      72                 :            :         ef10_mac_pdu_set,                       /* emo_pdu_set */
      73                 :            :         ef10_mac_pdu_get,                       /* emo_pdu_get */
      74                 :            :         ef10_mac_reconfigure,                   /* emo_reconfigure */
      75                 :            :         ef10_mac_multicast_list_set,            /* emo_multicast_list_set */
      76                 :            :         ef10_mac_filter_default_rxq_set,        /* emo_filter_default_rxq_set */
      77                 :            :         ef10_mac_filter_default_rxq_clear,
      78                 :            :                                         /* emo_filter_default_rxq_clear */
      79                 :            : #if EFSYS_OPT_LOOPBACK
      80                 :            :         ef10_mac_loopback_set,                  /* emo_loopback_set */
      81                 :            : #endif  /* EFSYS_OPT_LOOPBACK */
      82                 :            : #if EFSYS_OPT_MAC_STATS
      83                 :            :         ef10_mac_stats_get_mask,                /* emo_stats_get_mask */
      84                 :            :         efx_mcdi_mac_stats_clear,               /* emo_stats_clear */
      85                 :            :         efx_mcdi_mac_stats_upload,              /* emo_stats_upload */
      86                 :            :         efx_mcdi_mac_stats_periodic,            /* emo_stats_periodic */
      87                 :            :         ef10_mac_stats_update                   /* emo_stats_update */
      88                 :            : #endif  /* EFSYS_OPT_MAC_STATS */
      89                 :            : };
      90                 :            : #endif  /* EFSYS_OPT_RIVERHEAD */
      91                 :            : 
      92                 :            :         __checkReturn                   efx_rc_t
      93                 :          0 : efx_mac_pdu_set(
      94                 :            :         __in                            efx_nic_t *enp,
      95                 :            :         __in                            size_t pdu)
      96                 :            : {
      97                 :            :         efx_port_t *epp = &(enp->en_port);
      98                 :          0 :         const efx_mac_ops_t *emop = epp->ep_emop;
      99                 :            :         uint32_t old_pdu;
     100                 :            :         efx_rc_t rc;
     101                 :            : 
     102         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     103         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PORT);
     104         [ #  # ]:          0 :         EFSYS_ASSERT(emop != NULL);
     105                 :            : 
     106         [ #  # ]:          0 :         if (pdu < EFX_MAC_PDU_MIN) {
     107                 :            :                 rc = EINVAL;
     108                 :          0 :                 goto fail1;
     109                 :            :         }
     110                 :            : 
     111         [ #  # ]:          0 :         if (pdu > EFX_MAC_PDU_MAX) {
     112                 :            :                 rc = EINVAL;
     113                 :          0 :                 goto fail2;
     114                 :            :         }
     115                 :            : 
     116                 :          0 :         old_pdu = epp->ep_mac_pdu;
     117                 :          0 :         epp->ep_mac_pdu = (uint32_t)pdu;
     118         [ #  # ]:          0 :         if ((rc = emop->emo_pdu_set(enp)) != 0)
     119                 :          0 :                 goto fail3;
     120                 :            : 
     121                 :            :         return (0);
     122                 :            : 
     123                 :            : fail3:
     124                 :            :         EFSYS_PROBE(fail3);
     125                 :            : 
     126                 :          0 :         epp->ep_mac_pdu = old_pdu;
     127                 :            : 
     128                 :            : fail2:
     129                 :            :         EFSYS_PROBE(fail2);
     130                 :            : fail1:
     131                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
     132                 :            : 
     133                 :            :         return (rc);
     134                 :            : }
     135                 :            : 
     136                 :            :         __checkReturn   efx_rc_t
     137                 :          0 : efx_mac_pdu_get(
     138                 :            :         __in            efx_nic_t *enp,
     139                 :            :         __out           size_t *pdu)
     140                 :            : {
     141                 :            :         efx_port_t *epp = &(enp->en_port);
     142                 :          0 :         const efx_mac_ops_t *emop = epp->ep_emop;
     143                 :            :         efx_rc_t rc;
     144                 :            : 
     145         [ #  # ]:          0 :         if ((rc = emop->emo_pdu_get(enp, pdu)) != 0)
     146                 :          0 :                 goto fail1;
     147                 :            : 
     148                 :            :         return (0);
     149                 :            : 
     150                 :            : fail1:
     151                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
     152                 :            : 
     153                 :          0 :         return (rc);
     154                 :            : }
     155                 :            : 
     156                 :            :         __checkReturn                   efx_rc_t
     157                 :          0 : efx_mac_addr_set(
     158                 :            :         __in                            efx_nic_t *enp,
     159                 :            :         __in                            uint8_t *addr)
     160                 :            : {
     161                 :            :         efx_port_t *epp = &(enp->en_port);
     162                 :          0 :         const efx_mac_ops_t *emop = epp->ep_emop;
     163                 :            :         uint8_t old_addr[6];
     164                 :            :         uint32_t oui;
     165                 :            :         efx_rc_t rc;
     166                 :            : 
     167         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     168         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PORT);
     169                 :            : 
     170         [ #  # ]:          0 :         if (EFX_MAC_ADDR_IS_MULTICAST(addr)) {
     171                 :            :                 rc = EINVAL;
     172                 :          0 :                 goto fail1;
     173                 :            :         }
     174                 :            : 
     175                 :          0 :         oui = addr[0] << 16 | addr[1] << 8 | addr[2];
     176         [ #  # ]:          0 :         if (oui == 0x000000) {
     177                 :            :                 rc = EINVAL;
     178                 :          0 :                 goto fail2;
     179                 :            :         }
     180                 :            : 
     181                 :          0 :         EFX_MAC_ADDR_COPY(old_addr, epp->ep_mac_addr);
     182                 :          0 :         EFX_MAC_ADDR_COPY(epp->ep_mac_addr, addr);
     183         [ #  # ]:          0 :         if ((rc = emop->emo_addr_set(enp)) != 0)
     184                 :          0 :                 goto fail3;
     185                 :            : 
     186                 :            :         return (0);
     187                 :            : 
     188                 :            : fail3:
     189                 :            :         EFSYS_PROBE(fail3);
     190                 :            : 
     191                 :          0 :         EFX_MAC_ADDR_COPY(epp->ep_mac_addr, old_addr);
     192                 :            : 
     193                 :            : fail2:
     194                 :            :         EFSYS_PROBE(fail2);
     195                 :            : fail1:
     196                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
     197                 :            : 
     198                 :            :         return (rc);
     199                 :            : }
     200                 :            : 
     201                 :            :         __checkReturn                   efx_rc_t
     202                 :          0 : efx_mac_filter_set(
     203                 :            :         __in                            efx_nic_t *enp,
     204                 :            :         __in                            boolean_t all_unicst,
     205                 :            :         __in                            boolean_t mulcst,
     206                 :            :         __in                            boolean_t all_mulcst,
     207                 :            :         __in                            boolean_t brdcst)
     208                 :            : {
     209                 :            :         efx_port_t *epp = &(enp->en_port);
     210                 :          0 :         const efx_mac_ops_t *emop = epp->ep_emop;
     211                 :            :         boolean_t old_all_unicst;
     212                 :            :         boolean_t old_mulcst;
     213                 :            :         boolean_t old_all_mulcst;
     214                 :            :         boolean_t old_brdcst;
     215                 :            :         efx_rc_t rc;
     216                 :            : 
     217         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     218         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PORT);
     219                 :            : 
     220                 :          0 :         old_all_unicst = epp->ep_all_unicst;
     221                 :          0 :         old_mulcst = epp->ep_mulcst;
     222                 :          0 :         old_all_mulcst = epp->ep_all_mulcst;
     223                 :          0 :         old_brdcst = epp->ep_brdcst;
     224                 :            : 
     225                 :          0 :         epp->ep_all_unicst = all_unicst;
     226                 :          0 :         epp->ep_mulcst = mulcst;
     227                 :          0 :         epp->ep_all_mulcst = all_mulcst;
     228                 :          0 :         epp->ep_brdcst = brdcst;
     229                 :            : 
     230         [ #  # ]:          0 :         if ((rc = emop->emo_reconfigure(enp)) != 0)
     231                 :          0 :                 goto fail1;
     232                 :            : 
     233                 :            :         return (0);
     234                 :            : 
     235                 :            : fail1:
     236                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
     237                 :            : 
     238                 :          0 :         epp->ep_all_unicst = old_all_unicst;
     239                 :          0 :         epp->ep_mulcst = old_mulcst;
     240                 :          0 :         epp->ep_all_mulcst = old_all_mulcst;
     241                 :          0 :         epp->ep_brdcst = old_brdcst;
     242                 :            : 
     243                 :          0 :         return (rc);
     244                 :            : }
     245                 :            : 
     246                 :            :                                         void
     247                 :          0 : efx_mac_filter_get_all_ucast_mcast(
     248                 :            :         __in                            efx_nic_t *enp,
     249                 :            :         __out                           boolean_t *all_unicst,
     250                 :            :         __out                           boolean_t *all_mulcst)
     251                 :            : {
     252                 :            :         efx_port_t *epp = &(enp->en_port);
     253                 :            : 
     254         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     255         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PORT);
     256                 :            : 
     257                 :          0 :         *all_unicst = epp->ep_all_unicst_inserted;
     258                 :          0 :         *all_mulcst = epp->ep_all_mulcst_inserted;
     259                 :          0 : }
     260                 :            : 
     261                 :            :         __checkReturn                   efx_rc_t
     262                 :          0 : efx_mac_drain(
     263                 :            :         __in                            efx_nic_t *enp,
     264                 :            :         __in                            boolean_t enabled)
     265                 :            : {
     266                 :            :         efx_port_t *epp = &(enp->en_port);
     267                 :          0 :         const efx_mac_ops_t *emop = epp->ep_emop;
     268                 :            :         efx_rc_t rc;
     269                 :            : 
     270         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     271         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PORT);
     272         [ #  # ]:          0 :         EFSYS_ASSERT(emop != NULL);
     273                 :            : 
     274         [ #  # ]:          0 :         if (epp->ep_mac_drain == enabled)
     275                 :            :                 return (0);
     276                 :            : 
     277                 :          0 :         epp->ep_mac_drain = enabled;
     278                 :            : 
     279         [ #  # ]:          0 :         if ((rc = emop->emo_reconfigure(enp)) != 0)
     280                 :          0 :                 goto fail1;
     281                 :            : 
     282                 :            :         return (0);
     283                 :            : 
     284                 :            : fail1:
     285                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
     286                 :            : 
     287                 :          0 :         return (rc);
     288                 :            : }
     289                 :            : 
     290                 :            :         __checkReturn   efx_rc_t
     291                 :          0 : efx_mac_up(
     292                 :            :         __in            efx_nic_t *enp,
     293                 :            :         __out           boolean_t *mac_upp)
     294                 :            : {
     295                 :            :         efx_port_t *epp = &(enp->en_port);
     296                 :          0 :         const efx_mac_ops_t *emop = epp->ep_emop;
     297                 :            :         efx_rc_t rc;
     298                 :            : 
     299         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     300         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PORT);
     301                 :            : 
     302         [ #  # ]:          0 :         if ((rc = emop->emo_up(enp, mac_upp)) != 0)
     303                 :          0 :                 goto fail1;
     304                 :            : 
     305                 :            :         return (0);
     306                 :            : 
     307                 :            : fail1:
     308                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
     309                 :            : 
     310                 :          0 :         return (rc);
     311                 :            : }
     312                 :            : 
     313                 :            :         __checkReturn                   efx_rc_t
     314                 :          0 : efx_mac_fcntl_set(
     315                 :            :         __in                            efx_nic_t *enp,
     316                 :            :         __in                            unsigned int fcntl,
     317                 :            :         __in                            boolean_t autoneg)
     318                 :            : {
     319                 :            :         efx_port_t *epp = &(enp->en_port);
     320                 :          0 :         const efx_mac_ops_t *emop = epp->ep_emop;
     321                 :          0 :         const efx_phy_ops_t *epop = epp->ep_epop;
     322                 :            :         unsigned int old_fcntl;
     323                 :            :         boolean_t old_autoneg;
     324                 :            :         unsigned int old_adv_cap;
     325                 :            :         efx_rc_t rc;
     326                 :            : 
     327         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     328         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PORT);
     329                 :            : 
     330         [ #  # ]:          0 :         if ((fcntl & ~(EFX_FCNTL_RESPOND | EFX_FCNTL_GENERATE)) != 0) {
     331                 :            :                 rc = EINVAL;
     332                 :          0 :                 goto fail1;
     333                 :            :         }
     334                 :            : 
     335                 :            :         /*
     336                 :            :          * Ignore a request to set flow control auto-negotiation
     337                 :            :          * if the PHY doesn't support it.
     338                 :            :          */
     339         [ #  # ]:          0 :         if (~epp->ep_phy_cap_mask & (1 << EFX_PHY_CAP_AN))
     340                 :            :                 autoneg = B_FALSE;
     341                 :            : 
     342                 :          0 :         old_fcntl = epp->ep_fcntl;
     343                 :          0 :         old_autoneg = epp->ep_fcntl_autoneg;
     344                 :          0 :         old_adv_cap = epp->ep_adv_cap_mask;
     345                 :            : 
     346                 :          0 :         epp->ep_fcntl = fcntl;
     347                 :          0 :         epp->ep_fcntl_autoneg = autoneg;
     348                 :            : 
     349                 :            :         /*
     350                 :            :          * Always encode the flow control settings in the advertised
     351                 :            :          * capabilities even if we are not trying to auto-negotiate
     352                 :            :          * them and reconfigure both the PHY and the MAC.
     353                 :            :          */
     354         [ #  # ]:          0 :         if (fcntl & EFX_FCNTL_RESPOND)
     355                 :          0 :                 epp->ep_adv_cap_mask |=    (1 << EFX_PHY_CAP_PAUSE |
     356                 :            :                                             1 << EFX_PHY_CAP_ASYM);
     357                 :            :         else
     358                 :          0 :                 epp->ep_adv_cap_mask &=   ~(1 << EFX_PHY_CAP_PAUSE |
     359                 :            :                                             1 << EFX_PHY_CAP_ASYM);
     360                 :            : 
     361         [ #  # ]:          0 :         if (fcntl & EFX_FCNTL_GENERATE)
     362                 :          0 :                 epp->ep_adv_cap_mask ^= (1 << EFX_PHY_CAP_ASYM);
     363                 :            : 
     364         [ #  # ]:          0 :         if ((rc = epop->epo_reconfigure(enp)) != 0)
     365                 :          0 :                 goto fail2;
     366                 :            : 
     367         [ #  # ]:          0 :         if ((rc = emop->emo_reconfigure(enp)) != 0)
     368                 :          0 :                 goto fail3;
     369                 :            : 
     370                 :            :         return (0);
     371                 :            : 
     372                 :            : fail3:
     373                 :            :         EFSYS_PROBE(fail3);
     374                 :            : 
     375                 :          0 : fail2:
     376                 :            :         EFSYS_PROBE(fail2);
     377                 :            : 
     378                 :          0 :         epp->ep_fcntl = old_fcntl;
     379                 :          0 :         epp->ep_fcntl_autoneg = old_autoneg;
     380                 :          0 :         epp->ep_adv_cap_mask = old_adv_cap;
     381                 :            : 
     382                 :            : fail1:
     383                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
     384                 :            : 
     385                 :            :         return (rc);
     386                 :            : }
     387                 :            : 
     388                 :            :                         void
     389                 :          0 : efx_mac_fcntl_get(
     390                 :            :         __in            efx_nic_t *enp,
     391                 :            :         __out           unsigned int *fcntl_wantedp,
     392                 :            :         __out           unsigned int *fcntl_linkp)
     393                 :            : {
     394                 :            :         efx_port_t *epp = &(enp->en_port);
     395                 :            :         unsigned int wanted = 0;
     396                 :            : 
     397         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     398         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PORT);
     399                 :            : 
     400                 :            :         /*
     401                 :            :          * Decode the requested flow control settings from the PHY
     402                 :            :          * advertised capabilities.
     403                 :            :          */
     404         [ #  # ]:          0 :         if (epp->ep_adv_cap_mask & (1 << EFX_PHY_CAP_PAUSE))
     405                 :            :                 wanted = EFX_FCNTL_RESPOND | EFX_FCNTL_GENERATE;
     406         [ #  # ]:          0 :         if (epp->ep_adv_cap_mask & (1 << EFX_PHY_CAP_ASYM))
     407                 :          0 :                 wanted ^= EFX_FCNTL_GENERATE;
     408                 :            : 
     409                 :          0 :         *fcntl_linkp = epp->ep_fcntl;
     410                 :          0 :         *fcntl_wantedp = wanted;
     411                 :          0 : }
     412                 :            : 
     413                 :            :         __checkReturn   efx_rc_t
     414                 :          0 : efx_mac_multicast_list_set(
     415                 :            :         __in                            efx_nic_t *enp,
     416                 :            :         __in_ecount(6*count)            uint8_t const *addrs,
     417                 :            :         __in                            int count)
     418                 :            : {
     419                 :            :         efx_port_t *epp = &(enp->en_port);
     420                 :          0 :         const efx_mac_ops_t *emop = epp->ep_emop;
     421                 :            :         uint8_t *old_mulcst_addr_list = NULL;
     422                 :            :         uint32_t old_mulcst_addr_count;
     423                 :            :         efx_rc_t rc;
     424                 :            : 
     425         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     426         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PORT);
     427                 :            : 
     428         [ #  # ]:          0 :         if (count > EFX_MAC_MULTICAST_LIST_MAX) {
     429                 :            :                 rc = EINVAL;
     430                 :          0 :                 goto fail1;
     431                 :            :         }
     432                 :            : 
     433                 :          0 :         old_mulcst_addr_count = epp->ep_mulcst_addr_count;
     434         [ #  # ]:          0 :         if (old_mulcst_addr_count > 0) {
     435                 :            :                 /* Allocate memory to store old list (instead of using stack) */
     436                 :          0 :                 EFSYS_KMEM_ALLOC(enp->en_esip,
     437                 :            :                                 old_mulcst_addr_count * EFX_MAC_ADDR_LEN,
     438                 :            :                                 old_mulcst_addr_list);
     439         [ #  # ]:          0 :                 if (old_mulcst_addr_list == NULL) {
     440                 :            :                         rc = ENOMEM;
     441                 :          0 :                         goto fail2;
     442                 :            :                 }
     443                 :            : 
     444                 :            :                 /* Save the old list in case we need to rollback */
     445                 :          0 :                 memcpy(old_mulcst_addr_list, epp->ep_mulcst_addr_list,
     446                 :            :                         old_mulcst_addr_count * EFX_MAC_ADDR_LEN);
     447                 :            :         }
     448                 :            : 
     449                 :            :         /* Store the new list */
     450                 :          0 :         memcpy(epp->ep_mulcst_addr_list, addrs,
     451                 :          0 :                 count * EFX_MAC_ADDR_LEN);
     452                 :          0 :         epp->ep_mulcst_addr_count = count;
     453                 :            : 
     454         [ #  # ]:          0 :         if ((rc = emop->emo_multicast_list_set(enp)) != 0)
     455                 :          0 :                 goto fail3;
     456                 :            : 
     457         [ #  # ]:          0 :         if (old_mulcst_addr_count > 0) {
     458                 :          0 :                 EFSYS_KMEM_FREE(enp->en_esip,
     459                 :            :                                 old_mulcst_addr_count * EFX_MAC_ADDR_LEN,
     460                 :            :                                 old_mulcst_addr_list);
     461                 :            :         }
     462                 :            : 
     463                 :            :         return (0);
     464                 :            : 
     465                 :            : fail3:
     466                 :            :         EFSYS_PROBE(fail3);
     467                 :            : 
     468                 :            :         /* Restore original list on failure */
     469                 :          0 :         epp->ep_mulcst_addr_count = old_mulcst_addr_count;
     470         [ #  # ]:          0 :         if (old_mulcst_addr_count > 0) {
     471                 :          0 :                 memcpy(epp->ep_mulcst_addr_list, old_mulcst_addr_list,
     472                 :          0 :                         old_mulcst_addr_count * EFX_MAC_ADDR_LEN);
     473                 :            : 
     474                 :          0 :                 EFSYS_KMEM_FREE(enp->en_esip,
     475                 :            :                                 old_mulcst_addr_count * EFX_MAC_ADDR_LEN,
     476                 :            :                                 old_mulcst_addr_list);
     477                 :            :         }
     478                 :            : 
     479                 :          0 : fail2:
     480                 :            :         EFSYS_PROBE(fail2);
     481                 :            : 
     482                 :            : fail1:
     483                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
     484                 :            : 
     485                 :            :         return (rc);
     486                 :            : 
     487                 :            : }
     488                 :            : 
     489                 :            :         __checkReturn   efx_rc_t
     490                 :          0 : efx_mac_filter_default_rxq_set(
     491                 :            :         __in            efx_nic_t *enp,
     492                 :            :         __in            efx_rxq_t *erp,
     493                 :            :         __in            boolean_t using_rss)
     494                 :            : {
     495                 :            :         efx_port_t *epp = &(enp->en_port);
     496                 :          0 :         const efx_mac_ops_t *emop = epp->ep_emop;
     497                 :            :         efx_rc_t rc;
     498                 :            : 
     499         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     500         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PORT);
     501                 :            : 
     502         [ #  # ]:          0 :         if (emop->emo_filter_default_rxq_set != NULL) {
     503                 :          0 :                 rc = emop->emo_filter_default_rxq_set(enp, erp, using_rss);
     504         [ #  # ]:          0 :                 if (rc != 0)
     505                 :          0 :                         goto fail1;
     506                 :            :         }
     507                 :            : 
     508                 :            :         return (0);
     509                 :            : 
     510                 :            : fail1:
     511                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
     512                 :            : 
     513                 :          0 :         return (rc);
     514                 :            : }
     515                 :            : 
     516                 :            :                         void
     517                 :          0 : efx_mac_filter_default_rxq_clear(
     518                 :            :         __in            efx_nic_t *enp)
     519                 :            : {
     520                 :            :         efx_port_t *epp = &(enp->en_port);
     521                 :          0 :         const efx_mac_ops_t *emop = epp->ep_emop;
     522                 :            : 
     523         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     524         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PORT);
     525                 :            : 
     526         [ #  # ]:          0 :         if (emop->emo_filter_default_rxq_clear != NULL)
     527                 :          0 :                 emop->emo_filter_default_rxq_clear(enp);
     528                 :          0 : }
     529                 :            : 
     530                 :            :         __checkReturn   efx_rc_t
     531                 :          0 : efx_mac_include_fcs_set(
     532                 :            :         __in            efx_nic_t *enp,
     533                 :            :         __in            boolean_t enabled)
     534                 :            : {
     535                 :            :         efx_port_t *epp = &(enp->en_port);
     536                 :            :         efx_nic_cfg_t *encp = &(enp->en_nic_cfg);
     537                 :          0 :         const efx_mac_ops_t *emop = epp->ep_emop;
     538                 :            :         efx_rc_t rc;
     539                 :            : 
     540         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     541         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PORT);
     542         [ #  # ]:          0 :         EFSYS_ASSERT(emop != NULL);
     543                 :            : 
     544   [ #  #  #  # ]:          0 :         if (enabled && !encp->enc_rx_include_fcs_supported) {
     545                 :            :                 rc = ENOTSUP;
     546                 :          0 :                 goto fail1;
     547                 :            :         }
     548                 :            : 
     549                 :            :         /*
     550                 :            :          * Enabling 'include FCS' changes link control state and affects
     551                 :            :          * behaviour for all PCI functions on the port, so to avoid this it
     552                 :            :          * can be enabled only if the PCI function is exclusive port user
     553                 :            :          */
     554   [ #  #  #  # ]:          0 :         if (enabled && encp->enc_port_usage != EFX_PORT_USAGE_EXCLUSIVE) {
     555                 :            :                 rc = EACCES;
     556                 :          0 :                 goto fail2;
     557                 :            :         }
     558                 :            : 
     559         [ #  # ]:          0 :         if (epp->ep_include_fcs != enabled) {
     560                 :          0 :                 epp->ep_include_fcs = enabled;
     561                 :            : 
     562                 :          0 :                 rc = emop->emo_reconfigure(enp);
     563         [ #  # ]:          0 :                 if (rc != 0)
     564                 :          0 :                         goto fail3;
     565                 :            :         }
     566                 :            : 
     567                 :            :         return 0;
     568                 :            : 
     569                 :            : fail3:
     570                 :            :         EFSYS_PROBE(fail3);
     571                 :            : fail2:
     572                 :            :         EFSYS_PROBE(fail2);
     573                 :            : fail1:
     574                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
     575                 :            : 
     576                 :            :         return rc;
     577                 :            : }
     578                 :            : 
     579                 :            : #if EFSYS_OPT_MAC_STATS
     580                 :            : 
     581                 :            : #if EFSYS_OPT_NAMES
     582                 :            : 
     583                 :            : /* START MKCONFIG GENERATED EfxMacStatNamesBlock 1a45a82fcfb30c1b */
     584                 :            : static const char * const __efx_mac_stat_name[] = {
     585                 :            :         "rx_octets",
     586                 :            :         "rx_pkts",
     587                 :            :         "rx_unicst_pkts",
     588                 :            :         "rx_multicst_pkts",
     589                 :            :         "rx_brdcst_pkts",
     590                 :            :         "rx_pause_pkts",
     591                 :            :         "rx_le_64_pkts",
     592                 :            :         "rx_65_to_127_pkts",
     593                 :            :         "rx_128_to_255_pkts",
     594                 :            :         "rx_256_to_511_pkts",
     595                 :            :         "rx_512_to_1023_pkts",
     596                 :            :         "rx_1024_to_15xx_pkts",
     597                 :            :         "rx_ge_15xx_pkts",
     598                 :            :         "rx_errors",
     599                 :            :         "rx_fcs_errors",
     600                 :            :         "rx_drop_events",
     601                 :            :         "rx_false_carrier_errors",
     602                 :            :         "rx_symbol_errors",
     603                 :            :         "rx_align_errors",
     604                 :            :         "rx_internal_errors",
     605                 :            :         "rx_jabber_pkts",
     606                 :            :         "rx_lane0_char_err",
     607                 :            :         "rx_lane1_char_err",
     608                 :            :         "rx_lane2_char_err",
     609                 :            :         "rx_lane3_char_err",
     610                 :            :         "rx_lane0_disp_err",
     611                 :            :         "rx_lane1_disp_err",
     612                 :            :         "rx_lane2_disp_err",
     613                 :            :         "rx_lane3_disp_err",
     614                 :            :         "rx_match_fault",
     615                 :            :         "rx_nodesc_drop_cnt",
     616                 :            :         "tx_octets",
     617                 :            :         "tx_pkts",
     618                 :            :         "tx_unicst_pkts",
     619                 :            :         "tx_multicst_pkts",
     620                 :            :         "tx_brdcst_pkts",
     621                 :            :         "tx_pause_pkts",
     622                 :            :         "tx_le_64_pkts",
     623                 :            :         "tx_65_to_127_pkts",
     624                 :            :         "tx_128_to_255_pkts",
     625                 :            :         "tx_256_to_511_pkts",
     626                 :            :         "tx_512_to_1023_pkts",
     627                 :            :         "tx_1024_to_15xx_pkts",
     628                 :            :         "tx_ge_15xx_pkts",
     629                 :            :         "tx_errors",
     630                 :            :         "tx_sgl_col_pkts",
     631                 :            :         "tx_mult_col_pkts",
     632                 :            :         "tx_ex_col_pkts",
     633                 :            :         "tx_late_col_pkts",
     634                 :            :         "tx_def_pkts",
     635                 :            :         "tx_ex_def_pkts",
     636                 :            :         "pm_trunc_bb_overflow",
     637                 :            :         "pm_discard_bb_overflow",
     638                 :            :         "pm_trunc_vfifo_full",
     639                 :            :         "pm_discard_vfifo_full",
     640                 :            :         "pm_trunc_qbb",
     641                 :            :         "pm_discard_qbb",
     642                 :            :         "pm_discard_mapping",
     643                 :            :         "rxdp_q_disabled_pkts",
     644                 :            :         "rxdp_di_dropped_pkts",
     645                 :            :         "rxdp_streaming_pkts",
     646                 :            :         "rxdp_hlb_fetch",
     647                 :            :         "rxdp_hlb_wait",
     648                 :            :         "vadapter_rx_unicast_packets",
     649                 :            :         "vadapter_rx_unicast_bytes",
     650                 :            :         "vadapter_rx_multicast_packets",
     651                 :            :         "vadapter_rx_multicast_bytes",
     652                 :            :         "vadapter_rx_broadcast_packets",
     653                 :            :         "vadapter_rx_broadcast_bytes",
     654                 :            :         "vadapter_rx_bad_packets",
     655                 :            :         "vadapter_rx_bad_bytes",
     656                 :            :         "vadapter_rx_overflow",
     657                 :            :         "vadapter_tx_unicast_packets",
     658                 :            :         "vadapter_tx_unicast_bytes",
     659                 :            :         "vadapter_tx_multicast_packets",
     660                 :            :         "vadapter_tx_multicast_bytes",
     661                 :            :         "vadapter_tx_broadcast_packets",
     662                 :            :         "vadapter_tx_broadcast_bytes",
     663                 :            :         "vadapter_tx_bad_packets",
     664                 :            :         "vadapter_tx_bad_bytes",
     665                 :            :         "vadapter_tx_overflow",
     666                 :            :         "fec_uncorrected_errors",
     667                 :            :         "fec_corrected_errors",
     668                 :            :         "fec_corrected_symbols_lane0",
     669                 :            :         "fec_corrected_symbols_lane1",
     670                 :            :         "fec_corrected_symbols_lane2",
     671                 :            :         "fec_corrected_symbols_lane3",
     672                 :            :         "ctpio_vi_busy_fallback",
     673                 :            :         "ctpio_long_write_success",
     674                 :            :         "ctpio_missing_dbell_fail",
     675                 :            :         "ctpio_overflow_fail",
     676                 :            :         "ctpio_underflow_fail",
     677                 :            :         "ctpio_timeout_fail",
     678                 :            :         "ctpio_noncontig_wr_fail",
     679                 :            :         "ctpio_frm_clobber_fail",
     680                 :            :         "ctpio_invalid_wr_fail",
     681                 :            :         "ctpio_vi_clobber_fallback",
     682                 :            :         "ctpio_unqualified_fallback",
     683                 :            :         "ctpio_runt_fallback",
     684                 :            :         "ctpio_success",
     685                 :            :         "ctpio_fallback",
     686                 :            :         "ctpio_poison",
     687                 :            :         "ctpio_erase",
     688                 :            :         "rxdp_scatter_disabled_trunc",
     689                 :            :         "rxdp_hlb_idle",
     690                 :            :         "rxdp_hlb_timeout",
     691                 :            : };
     692                 :            : /* END MKCONFIG GENERATED EfxMacStatNamesBlock */
     693                 :            : 
     694                 :            :         __checkReturn                   const char *
     695                 :          0 : efx_mac_stat_name(
     696                 :            :         __in                            efx_nic_t *enp,
     697                 :            :         __in                            unsigned int id)
     698                 :            : {
     699                 :            :         _NOTE(ARGUNUSED(enp))
     700         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     701                 :            : 
     702         [ #  # ]:          0 :         EFSYS_ASSERT3U(id, <, EFX_MAC_NSTATS);
     703                 :          0 :         return (__efx_mac_stat_name[id]);
     704                 :            : }
     705                 :            : 
     706                 :            : #endif  /* EFSYS_OPT_NAMES */
     707                 :            : 
     708                 :            : static                                  efx_rc_t
     709                 :          0 : efx_mac_stats_mask_add_range(
     710                 :            :         __inout_bcount(mask_size)       uint32_t *maskp,
     711                 :            :         __in                            size_t mask_size,
     712                 :            :         __in                            const struct efx_mac_stats_range *rngp)
     713                 :            : {
     714                 :          0 :         unsigned int mask_npages = mask_size / sizeof (*maskp);
     715                 :            :         unsigned int el;
     716                 :            :         unsigned int el_min;
     717                 :            :         unsigned int el_max;
     718                 :            :         unsigned int low;
     719                 :            :         unsigned int high;
     720                 :            :         unsigned int width;
     721                 :            :         efx_rc_t rc;
     722                 :            : 
     723                 :          0 :         if ((mask_npages * EFX_MAC_STATS_MASK_BITS_PER_PAGE) <=
     724         [ #  # ]:          0 :             (unsigned int)rngp->last) {
     725                 :            :                 rc = EINVAL;
     726                 :          0 :                 goto fail1;
     727                 :            :         }
     728                 :            : 
     729         [ #  # ]:          0 :         EFSYS_ASSERT3U(rngp->first, <=, rngp->last);
     730         [ #  # ]:          0 :         EFSYS_ASSERT3U(rngp->last, <, EFX_MAC_NSTATS);
     731                 :            : 
     732         [ #  # ]:          0 :         for (el = 0; el < mask_npages; ++el) {
     733                 :          0 :                 el_min = el * EFX_MAC_STATS_MASK_BITS_PER_PAGE;
     734                 :          0 :                 el_max =
     735                 :            :                     el_min + (EFX_MAC_STATS_MASK_BITS_PER_PAGE - 1);
     736         [ #  # ]:          0 :                 if ((unsigned int)rngp->first > el_max ||
     737         [ #  # ]:          0 :                     (unsigned int)rngp->last < el_min)
     738                 :          0 :                         continue;
     739                 :          0 :                 low = MAX((unsigned int)rngp->first, el_min);
     740                 :          0 :                 high = MIN((unsigned int)rngp->last, el_max);
     741                 :          0 :                 width = high - low + 1;
     742         [ #  # ]:          0 :                 maskp[el] |=
     743                 :            :                     (width == EFX_MAC_STATS_MASK_BITS_PER_PAGE) ?
     744                 :          0 :                     (~0ULL) : (((1ULL << width) - 1) << (low - el_min));
     745                 :            :         }
     746                 :            : 
     747                 :            :         return (0);
     748                 :            : 
     749                 :            : fail1:
     750                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
     751                 :            : 
     752                 :          0 :         return (rc);
     753                 :            : }
     754                 :            : 
     755                 :            :                                         efx_rc_t
     756                 :          0 : efx_mac_stats_mask_add_ranges(
     757                 :            :         __inout_bcount(mask_size)       uint32_t *maskp,
     758                 :            :         __in                            size_t mask_size,
     759                 :            :         __in_ecount(rng_count)          const struct efx_mac_stats_range *rngp,
     760                 :            :         __in                            unsigned int rng_count)
     761                 :            : {
     762                 :            :         unsigned int i;
     763                 :            :         efx_rc_t rc;
     764                 :            : 
     765         [ #  # ]:          0 :         for (i = 0; i < rng_count; ++i) {
     766         [ #  # ]:          0 :                 if ((rc = efx_mac_stats_mask_add_range(maskp, mask_size,
     767                 :          0 :                     &rngp[i])) != 0)
     768                 :          0 :                         goto fail1;
     769                 :            :         }
     770                 :            : 
     771                 :            :         return (0);
     772                 :            : 
     773                 :            : fail1:
     774                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
     775                 :            : 
     776                 :          0 :         return (rc);
     777                 :            : }
     778                 :            : 
     779                 :            :         __checkReturn                   efx_rc_t
     780                 :          0 : efx_mac_stats_get_mask(
     781                 :            :         __in                            efx_nic_t *enp,
     782                 :            :         __out_bcount(mask_size)         uint32_t *maskp,
     783                 :            :         __in                            size_t mask_size)
     784                 :            : {
     785                 :            :         efx_port_t *epp = &(enp->en_port);
     786                 :          0 :         const efx_mac_ops_t *emop = epp->ep_emop;
     787                 :            :         efx_rc_t rc;
     788                 :            : 
     789         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     790         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PROBE);
     791         [ #  # ]:          0 :         EFSYS_ASSERT(maskp != NULL);
     792         [ #  # ]:          0 :         EFSYS_ASSERT(mask_size % sizeof (maskp[0]) == 0);
     793                 :            : 
     794                 :            :         (void) memset(maskp, 0, mask_size);
     795                 :            : 
     796         [ #  # ]:          0 :         if ((rc = emop->emo_stats_get_mask(enp, maskp, mask_size)) != 0)
     797                 :          0 :                 goto fail1;
     798                 :            : 
     799                 :            :         return (0);
     800                 :            : 
     801                 :            : fail1:
     802                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
     803                 :            : 
     804                 :          0 :         return (rc);
     805                 :            : }
     806                 :            : 
     807                 :            :         __checkReturn                   efx_rc_t
     808                 :          0 : efx_mac_stats_clear(
     809                 :            :         __in                            efx_nic_t *enp)
     810                 :            : {
     811                 :            :         efx_port_t *epp = &(enp->en_port);
     812                 :          0 :         const efx_mac_ops_t *emop = epp->ep_emop;
     813                 :            :         efx_rc_t rc;
     814                 :            : 
     815         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     816         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PORT);
     817         [ #  # ]:          0 :         EFSYS_ASSERT(emop != NULL);
     818                 :            : 
     819         [ #  # ]:          0 :         if ((rc = emop->emo_stats_clear(enp)) != 0)
     820                 :          0 :                 goto fail1;
     821                 :            : 
     822                 :            :         return (0);
     823                 :            : 
     824                 :            : fail1:
     825                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
     826                 :            : 
     827                 :          0 :         return (rc);
     828                 :            : }
     829                 :            : 
     830                 :            :         __checkReturn                   efx_rc_t
     831                 :          0 : efx_mac_stats_upload(
     832                 :            :         __in                            efx_nic_t *enp,
     833                 :            :         __in                            efsys_mem_t *esmp)
     834                 :            : {
     835                 :            :         efx_port_t *epp = &(enp->en_port);
     836                 :          0 :         const efx_mac_ops_t *emop = epp->ep_emop;
     837                 :            :         efx_rc_t rc;
     838                 :            : 
     839         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     840         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PORT);
     841         [ #  # ]:          0 :         EFSYS_ASSERT(emop != NULL);
     842                 :            : 
     843         [ #  # ]:          0 :         if ((rc = emop->emo_stats_upload(enp, esmp)) != 0)
     844                 :          0 :                 goto fail1;
     845                 :            : 
     846                 :            :         return (0);
     847                 :            : 
     848                 :            : fail1:
     849                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
     850                 :            : 
     851                 :          0 :         return (rc);
     852                 :            : }
     853                 :            : 
     854                 :            :         __checkReturn                   efx_rc_t
     855                 :          0 : efx_mac_stats_periodic(
     856                 :            :         __in                            efx_nic_t *enp,
     857                 :            :         __in                            efsys_mem_t *esmp,
     858                 :            :         __in                            uint16_t period_ms,
     859                 :            :         __in                            boolean_t events)
     860                 :            : {
     861                 :            :         efx_port_t *epp = &(enp->en_port);
     862                 :          0 :         const efx_mac_ops_t *emop = epp->ep_emop;
     863                 :            :         efx_rc_t rc;
     864                 :            : 
     865         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     866         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PORT);
     867                 :            : 
     868         [ #  # ]:          0 :         EFSYS_ASSERT(emop != NULL);
     869                 :            : 
     870         [ #  # ]:          0 :         if (emop->emo_stats_periodic == NULL) {
     871                 :            :                 rc = EINVAL;
     872                 :          0 :                 goto fail1;
     873                 :            :         }
     874                 :            : 
     875         [ #  # ]:          0 :         if ((rc = emop->emo_stats_periodic(enp, esmp, period_ms, events)) != 0)
     876                 :          0 :                 goto fail2;
     877                 :            : 
     878                 :            :         return (0);
     879                 :            : 
     880                 :            : fail2:
     881                 :            :         EFSYS_PROBE(fail2);
     882                 :            : fail1:
     883                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
     884                 :            : 
     885                 :            :         return (rc);
     886                 :            : }
     887                 :            : 
     888                 :            : 
     889                 :            :         __checkReturn                   efx_rc_t
     890                 :          0 : efx_mac_stats_update(
     891                 :            :         __in                            efx_nic_t *enp,
     892                 :            :         __in                            efsys_mem_t *esmp,
     893                 :            :         __inout_ecount(EFX_MAC_NSTATS)  efsys_stat_t *essp,
     894                 :            :         __inout_opt                     uint32_t *generationp)
     895                 :            : {
     896                 :            :         efx_port_t *epp = &(enp->en_port);
     897                 :          0 :         const efx_mac_ops_t *emop = epp->ep_emop;
     898                 :            :         efx_rc_t rc;
     899                 :            : 
     900         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
     901         [ #  # ]:          0 :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PORT);
     902         [ #  # ]:          0 :         EFSYS_ASSERT(emop != NULL);
     903                 :            : 
     904                 :          0 :         rc = emop->emo_stats_update(enp, esmp, essp, generationp);
     905                 :            : 
     906                 :          0 :         return (rc);
     907                 :            : }
     908                 :            : 
     909                 :            : #endif  /* EFSYS_OPT_MAC_STATS */
     910                 :            : 
     911                 :            :         __checkReturn                   efx_rc_t
     912                 :          0 : efx_mac_select(
     913                 :            :         __in                            efx_nic_t *enp)
     914                 :            : {
     915                 :            :         efx_port_t *epp = &(enp->en_port);
     916                 :            :         efx_mac_type_t type = EFX_MAC_INVALID;
     917                 :            :         const efx_mac_ops_t *emop;
     918                 :            :         int rc = EINVAL;
     919                 :            : 
     920   [ #  #  #  #  :          0 :         switch (enp->en_family) {
                      # ]
     921                 :            : #if EFSYS_OPT_SIENA
     922                 :            :         case EFX_FAMILY_SIENA:
     923                 :            :                 emop = &__efx_mac_siena_ops;
     924                 :            :                 type = EFX_MAC_SIENA;
     925                 :            :                 break;
     926                 :            : #endif /* EFSYS_OPT_SIENA */
     927                 :            : 
     928                 :            : #if EFSYS_OPT_HUNTINGTON
     929                 :            :         case EFX_FAMILY_HUNTINGTON:
     930                 :            :                 emop = &__efx_mac_ef10_ops;
     931                 :            :                 type = EFX_MAC_HUNTINGTON;
     932                 :            :                 break;
     933                 :            : #endif /* EFSYS_OPT_HUNTINGTON */
     934                 :            : 
     935                 :            : #if EFSYS_OPT_MEDFORD
     936                 :          0 :         case EFX_FAMILY_MEDFORD:
     937                 :            :                 emop = &__efx_mac_ef10_ops;
     938                 :            :                 type = EFX_MAC_MEDFORD;
     939                 :          0 :                 break;
     940                 :            : #endif /* EFSYS_OPT_MEDFORD */
     941                 :            : 
     942                 :            : #if EFSYS_OPT_MEDFORD2
     943                 :          0 :         case EFX_FAMILY_MEDFORD2:
     944                 :            :                 emop = &__efx_mac_ef10_ops;
     945                 :            :                 type = EFX_MAC_MEDFORD2;
     946                 :          0 :                 break;
     947                 :            : #endif /* EFSYS_OPT_MEDFORD2 */
     948                 :            : 
     949                 :            : #if EFSYS_OPT_RIVERHEAD
     950                 :          0 :         case EFX_FAMILY_RIVERHEAD:
     951                 :            :                 emop = &__efx_mac_rhead_ops;
     952                 :            :                 type = EFX_MAC_RIVERHEAD;
     953                 :          0 :                 break;
     954                 :            : #endif /* EFSYS_OPT_RIVERHEAD */
     955                 :            : 
     956                 :          0 :         default:
     957                 :            :                 rc = EINVAL;
     958                 :          0 :                 goto fail1;
     959                 :            :         }
     960                 :            : 
     961                 :            :         EFSYS_ASSERT(type != EFX_MAC_INVALID);
     962                 :            :         EFSYS_ASSERT3U(type, <, EFX_MAC_NTYPES);
     963                 :            :         EFSYS_ASSERT(emop != NULL);
     964                 :            : 
     965                 :          0 :         epp->ep_emop = emop;
     966                 :          0 :         epp->ep_mac_type = type;
     967                 :            : 
     968                 :          0 :         return (0);
     969                 :            : 
     970                 :            : fail1:
     971                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
     972                 :            : 
     973                 :          0 :         return (rc);
     974                 :            : }
     975                 :            : 
     976                 :            : 
     977                 :            : #if EFSYS_OPT_SIENA
     978                 :            : 
     979                 :            : #define EFX_MAC_HASH_BITS       (1 << 8)
     980                 :            : 
     981                 :            : /* Compute the multicast hash as used on Falcon and Siena. */
     982                 :            : static  void
     983                 :            : siena_mac_multicast_hash_compute(
     984                 :            :         __in_ecount(6*count)            uint8_t const *addrs,
     985                 :            :         __in                            int count,
     986                 :            :         __out                           efx_oword_t *hash_low,
     987                 :            :         __out                           efx_oword_t *hash_high)
     988                 :            : {
     989                 :            :         uint32_t crc, index;
     990                 :            :         int i;
     991                 :            : 
     992                 :            :         EFSYS_ASSERT(hash_low != NULL);
     993                 :            :         EFSYS_ASSERT(hash_high != NULL);
     994                 :            : 
     995                 :            :         EFX_ZERO_OWORD(*hash_low);
     996                 :            :         EFX_ZERO_OWORD(*hash_high);
     997                 :            : 
     998                 :            :         for (i = 0; i < count; i++) {
     999                 :            :                 /* Calculate hash bucket (IEEE 802.3 CRC32 of the MAC addr) */
    1000                 :            :                 crc = efx_crc32_calculate(0xffffffff, addrs, EFX_MAC_ADDR_LEN);
    1001                 :            :                 index = crc % EFX_MAC_HASH_BITS;
    1002                 :            :                 if (index < 128) {
    1003                 :            :                         EFX_SET_OWORD_BIT(*hash_low, index);
    1004                 :            :                 } else {
    1005                 :            :                         EFX_SET_OWORD_BIT(*hash_high, index - 128);
    1006                 :            :                 }
    1007                 :            : 
    1008                 :            :                 addrs += EFX_MAC_ADDR_LEN;
    1009                 :            :         }
    1010                 :            : }
    1011                 :            : 
    1012                 :            : static  __checkReturn   efx_rc_t
    1013                 :            : siena_mac_multicast_list_set(
    1014                 :            :         __in            efx_nic_t *enp)
    1015                 :            : {
    1016                 :            :         efx_port_t *epp = &(enp->en_port);
    1017                 :            :         const efx_mac_ops_t *emop = epp->ep_emop;
    1018                 :            :         efx_oword_t old_hash[2];
    1019                 :            :         efx_rc_t rc;
    1020                 :            : 
    1021                 :            :         EFSYS_ASSERT3U(enp->en_magic, ==, EFX_NIC_MAGIC);
    1022                 :            :         EFSYS_ASSERT3U(enp->en_mod_flags, &, EFX_MOD_PORT);
    1023                 :            : 
    1024                 :            :         memcpy(old_hash, epp->ep_multicst_hash, sizeof (old_hash));
    1025                 :            : 
    1026                 :            :         siena_mac_multicast_hash_compute(
    1027                 :            :             epp->ep_mulcst_addr_list,
    1028                 :            :             epp->ep_mulcst_addr_count,
    1029                 :            :             &epp->ep_multicst_hash[0],
    1030                 :            :             &epp->ep_multicst_hash[1]);
    1031                 :            : 
    1032                 :            :         if ((rc = emop->emo_reconfigure(enp)) != 0)
    1033                 :            :                 goto fail1;
    1034                 :            : 
    1035                 :            :         return (0);
    1036                 :            : 
    1037                 :            : fail1:
    1038                 :            :         EFSYS_PROBE1(fail1, efx_rc_t, rc);
    1039                 :            : 
    1040                 :            :         memcpy(epp->ep_multicst_hash, old_hash, sizeof (old_hash));
    1041                 :            : 
    1042                 :            :         return (rc);
    1043                 :            : }
    1044                 :            : 
    1045                 :            : #endif /* EFSYS_OPT_SIENA */

Generated by: LCOV version 1.14