root/drivers/net/ethernet/aquantia/atlantic/aq_ethtool.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. aq_ethtool_get_regs
  2. aq_ethtool_get_regs_len
  3. aq_ethtool_get_link
  4. aq_ethtool_get_link_ksettings
  5. aq_ethtool_set_link_ksettings
  6. aq_ethtool_stats
  7. aq_ethtool_get_drvinfo
  8. aq_ethtool_get_strings
  9. aq_ethtool_get_sset_count
  10. aq_ethtool_get_rss_indir_size
  11. aq_ethtool_get_rss_key_size
  12. aq_ethtool_get_rss
  13. aq_ethtool_set_rss
  14. aq_ethtool_get_rxnfc
  15. aq_ethtool_set_rxnfc
  16. aq_ethtool_get_coalesce
  17. aq_ethtool_set_coalesce
  18. aq_ethtool_get_wol
  19. aq_ethtool_set_wol
  20. eee_mask_to_ethtool_mask
  21. aq_ethtool_get_eee
  22. aq_ethtool_set_eee
  23. aq_ethtool_nway_reset
  24. aq_ethtool_get_pauseparam
  25. aq_ethtool_set_pauseparam
  26. aq_get_ringparam
  27. aq_set_ringparam

   1 // SPDX-License-Identifier: GPL-2.0-only
   2 /*
   3  * aQuantia Corporation Network Driver
   4  * Copyright (C) 2014-2017 aQuantia Corporation. All rights reserved
   5  */
   6 
   7 /* File aq_ethtool.c: Definition of ethertool related functions. */
   8 
   9 #include "aq_ethtool.h"
  10 #include "aq_nic.h"
  11 #include "aq_vec.h"
  12 #include "aq_filters.h"
  13 
  14 static void aq_ethtool_get_regs(struct net_device *ndev,
  15                                 struct ethtool_regs *regs, void *p)
  16 {
  17         struct aq_nic_s *aq_nic = netdev_priv(ndev);
  18         u32 regs_count = aq_nic_get_regs_count(aq_nic);
  19 
  20         memset(p, 0, regs_count * sizeof(u32));
  21         aq_nic_get_regs(aq_nic, regs, p);
  22 }
  23 
  24 static int aq_ethtool_get_regs_len(struct net_device *ndev)
  25 {
  26         struct aq_nic_s *aq_nic = netdev_priv(ndev);
  27         u32 regs_count = aq_nic_get_regs_count(aq_nic);
  28 
  29         return regs_count * sizeof(u32);
  30 }
  31 
  32 static u32 aq_ethtool_get_link(struct net_device *ndev)
  33 {
  34         return ethtool_op_get_link(ndev);
  35 }
  36 
  37 static int aq_ethtool_get_link_ksettings(struct net_device *ndev,
  38                                          struct ethtool_link_ksettings *cmd)
  39 {
  40         struct aq_nic_s *aq_nic = netdev_priv(ndev);
  41 
  42         aq_nic_get_link_ksettings(aq_nic, cmd);
  43         cmd->base.speed = netif_carrier_ok(ndev) ?
  44                                 aq_nic_get_link_speed(aq_nic) : 0U;
  45 
  46         return 0;
  47 }
  48 
  49 static int
  50 aq_ethtool_set_link_ksettings(struct net_device *ndev,
  51                               const struct ethtool_link_ksettings *cmd)
  52 {
  53         struct aq_nic_s *aq_nic = netdev_priv(ndev);
  54 
  55         return aq_nic_set_link_ksettings(aq_nic, cmd);
  56 }
  57 
  58 static const char aq_ethtool_stat_names[][ETH_GSTRING_LEN] = {
  59         "InPackets",
  60         "InUCast",
  61         "InMCast",
  62         "InBCast",
  63         "InErrors",
  64         "OutPackets",
  65         "OutUCast",
  66         "OutMCast",
  67         "OutBCast",
  68         "InUCastOctets",
  69         "OutUCastOctets",
  70         "InMCastOctets",
  71         "OutMCastOctets",
  72         "InBCastOctets",
  73         "OutBCastOctets",
  74         "InOctets",
  75         "OutOctets",
  76         "InPacketsDma",
  77         "OutPacketsDma",
  78         "InOctetsDma",
  79         "OutOctetsDma",
  80         "InDroppedDma",
  81 };
  82 
  83 static const char aq_ethtool_queue_stat_names[][ETH_GSTRING_LEN] = {
  84         "Queue[%d] InPackets",
  85         "Queue[%d] OutPackets",
  86         "Queue[%d] Restarts",
  87         "Queue[%d] InJumboPackets",
  88         "Queue[%d] InLroPackets",
  89         "Queue[%d] InErrors",
  90 };
  91 
  92 static void aq_ethtool_stats(struct net_device *ndev,
  93                              struct ethtool_stats *stats, u64 *data)
  94 {
  95         struct aq_nic_s *aq_nic = netdev_priv(ndev);
  96         struct aq_nic_cfg_s *cfg = aq_nic_get_cfg(aq_nic);
  97 
  98         memset(data, 0, (ARRAY_SIZE(aq_ethtool_stat_names) +
  99                          ARRAY_SIZE(aq_ethtool_queue_stat_names) *
 100                          cfg->vecs) * sizeof(u64));
 101         aq_nic_get_stats(aq_nic, data);
 102 }
 103 
 104 static void aq_ethtool_get_drvinfo(struct net_device *ndev,
 105                                    struct ethtool_drvinfo *drvinfo)
 106 {
 107         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 108         struct aq_nic_cfg_s *cfg = aq_nic_get_cfg(aq_nic);
 109         struct pci_dev *pdev = to_pci_dev(ndev->dev.parent);
 110         u32 firmware_version = aq_nic_get_fw_version(aq_nic);
 111         u32 regs_count = aq_nic_get_regs_count(aq_nic);
 112 
 113         strlcat(drvinfo->driver, AQ_CFG_DRV_NAME, sizeof(drvinfo->driver));
 114         strlcat(drvinfo->version, AQ_CFG_DRV_VERSION, sizeof(drvinfo->version));
 115 
 116         snprintf(drvinfo->fw_version, sizeof(drvinfo->fw_version),
 117                  "%u.%u.%u", firmware_version >> 24,
 118                  (firmware_version >> 16) & 0xFFU, firmware_version & 0xFFFFU);
 119 
 120         strlcpy(drvinfo->bus_info, pdev ? pci_name(pdev) : "",
 121                 sizeof(drvinfo->bus_info));
 122         drvinfo->n_stats = ARRAY_SIZE(aq_ethtool_stat_names) +
 123                 cfg->vecs * ARRAY_SIZE(aq_ethtool_queue_stat_names);
 124         drvinfo->testinfo_len = 0;
 125         drvinfo->regdump_len = regs_count;
 126         drvinfo->eedump_len = 0;
 127 }
 128 
 129 static void aq_ethtool_get_strings(struct net_device *ndev,
 130                                    u32 stringset, u8 *data)
 131 {
 132         int i, si;
 133         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 134         struct aq_nic_cfg_s *cfg = aq_nic_get_cfg(aq_nic);
 135         u8 *p = data;
 136 
 137         if (stringset == ETH_SS_STATS) {
 138                 memcpy(p, aq_ethtool_stat_names,
 139                        sizeof(aq_ethtool_stat_names));
 140                 p = p + sizeof(aq_ethtool_stat_names);
 141                 for (i = 0; i < cfg->vecs; i++) {
 142                         for (si = 0;
 143                                 si < ARRAY_SIZE(aq_ethtool_queue_stat_names);
 144                                 si++) {
 145                                 snprintf(p, ETH_GSTRING_LEN,
 146                                          aq_ethtool_queue_stat_names[si], i);
 147                                 p += ETH_GSTRING_LEN;
 148                         }
 149                 }
 150         }
 151 }
 152 
 153 static int aq_ethtool_get_sset_count(struct net_device *ndev, int stringset)
 154 {
 155         int ret = 0;
 156         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 157         struct aq_nic_cfg_s *cfg = aq_nic_get_cfg(aq_nic);
 158 
 159         switch (stringset) {
 160         case ETH_SS_STATS:
 161                 ret = ARRAY_SIZE(aq_ethtool_stat_names) +
 162                         cfg->vecs * ARRAY_SIZE(aq_ethtool_queue_stat_names);
 163                 break;
 164         default:
 165                 ret = -EOPNOTSUPP;
 166         }
 167         return ret;
 168 }
 169 
 170 static u32 aq_ethtool_get_rss_indir_size(struct net_device *ndev)
 171 {
 172         return AQ_CFG_RSS_INDIRECTION_TABLE_MAX;
 173 }
 174 
 175 static u32 aq_ethtool_get_rss_key_size(struct net_device *ndev)
 176 {
 177         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 178         struct aq_nic_cfg_s *cfg = aq_nic_get_cfg(aq_nic);
 179 
 180         return sizeof(cfg->aq_rss.hash_secret_key);
 181 }
 182 
 183 static int aq_ethtool_get_rss(struct net_device *ndev, u32 *indir, u8 *key,
 184                               u8 *hfunc)
 185 {
 186         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 187         struct aq_nic_cfg_s *cfg = aq_nic_get_cfg(aq_nic);
 188         unsigned int i = 0U;
 189 
 190         if (hfunc)
 191                 *hfunc = ETH_RSS_HASH_TOP; /* Toeplitz */
 192         if (indir) {
 193                 for (i = 0; i < AQ_CFG_RSS_INDIRECTION_TABLE_MAX; i++)
 194                         indir[i] = cfg->aq_rss.indirection_table[i];
 195         }
 196         if (key)
 197                 memcpy(key, cfg->aq_rss.hash_secret_key,
 198                        sizeof(cfg->aq_rss.hash_secret_key));
 199         return 0;
 200 }
 201 
 202 static int aq_ethtool_set_rss(struct net_device *netdev, const u32 *indir,
 203                               const u8 *key, const u8 hfunc)
 204 {
 205         struct aq_nic_s *aq_nic = netdev_priv(netdev);
 206         struct aq_nic_cfg_s *cfg;
 207         unsigned int i = 0U;
 208         u32 rss_entries;
 209         int err = 0;
 210 
 211         cfg = aq_nic_get_cfg(aq_nic);
 212         rss_entries = cfg->aq_rss.indirection_table_size;
 213 
 214         /* We do not allow change in unsupported parameters */
 215         if (hfunc != ETH_RSS_HASH_NO_CHANGE && hfunc != ETH_RSS_HASH_TOP)
 216                 return -EOPNOTSUPP;
 217         /* Fill out the redirection table */
 218         if (indir)
 219                 for (i = 0; i < rss_entries; i++)
 220                         cfg->aq_rss.indirection_table[i] = indir[i];
 221 
 222         /* Fill out the rss hash key */
 223         if (key) {
 224                 memcpy(cfg->aq_rss.hash_secret_key, key,
 225                        sizeof(cfg->aq_rss.hash_secret_key));
 226                 err = aq_nic->aq_hw_ops->hw_rss_hash_set(aq_nic->aq_hw,
 227                         &cfg->aq_rss);
 228                 if (err)
 229                         return err;
 230         }
 231 
 232         err = aq_nic->aq_hw_ops->hw_rss_set(aq_nic->aq_hw, &cfg->aq_rss);
 233 
 234         return err;
 235 }
 236 
 237 static int aq_ethtool_get_rxnfc(struct net_device *ndev,
 238                                 struct ethtool_rxnfc *cmd,
 239                                 u32 *rule_locs)
 240 {
 241         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 242         struct aq_nic_cfg_s *cfg = aq_nic_get_cfg(aq_nic);
 243         int err = 0;
 244 
 245         switch (cmd->cmd) {
 246         case ETHTOOL_GRXRINGS:
 247                 cmd->data = cfg->vecs;
 248                 break;
 249         case ETHTOOL_GRXCLSRLCNT:
 250                 cmd->rule_cnt = aq_get_rxnfc_count_all_rules(aq_nic);
 251                 break;
 252         case ETHTOOL_GRXCLSRULE:
 253                 err = aq_get_rxnfc_rule(aq_nic, cmd);
 254                 break;
 255         case ETHTOOL_GRXCLSRLALL:
 256                 err = aq_get_rxnfc_all_rules(aq_nic, cmd, rule_locs);
 257                 break;
 258         default:
 259                 err = -EOPNOTSUPP;
 260                 break;
 261         }
 262 
 263         return err;
 264 }
 265 
 266 static int aq_ethtool_set_rxnfc(struct net_device *ndev,
 267                                 struct ethtool_rxnfc *cmd)
 268 {
 269         int err = 0;
 270         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 271 
 272         switch (cmd->cmd) {
 273         case ETHTOOL_SRXCLSRLINS:
 274                 err = aq_add_rxnfc_rule(aq_nic, cmd);
 275                 break;
 276         case ETHTOOL_SRXCLSRLDEL:
 277                 err = aq_del_rxnfc_rule(aq_nic, cmd);
 278                 break;
 279         default:
 280                 err = -EOPNOTSUPP;
 281                 break;
 282         }
 283 
 284         return err;
 285 }
 286 
 287 static int aq_ethtool_get_coalesce(struct net_device *ndev,
 288                                    struct ethtool_coalesce *coal)
 289 {
 290         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 291         struct aq_nic_cfg_s *cfg = aq_nic_get_cfg(aq_nic);
 292 
 293         if (cfg->itr == AQ_CFG_INTERRUPT_MODERATION_ON ||
 294             cfg->itr == AQ_CFG_INTERRUPT_MODERATION_AUTO) {
 295                 coal->rx_coalesce_usecs = cfg->rx_itr;
 296                 coal->tx_coalesce_usecs = cfg->tx_itr;
 297                 coal->rx_max_coalesced_frames = 0;
 298                 coal->tx_max_coalesced_frames = 0;
 299         } else {
 300                 coal->rx_coalesce_usecs = 0;
 301                 coal->tx_coalesce_usecs = 0;
 302                 coal->rx_max_coalesced_frames = 1;
 303                 coal->tx_max_coalesced_frames = 1;
 304         }
 305         return 0;
 306 }
 307 
 308 static int aq_ethtool_set_coalesce(struct net_device *ndev,
 309                                    struct ethtool_coalesce *coal)
 310 {
 311         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 312         struct aq_nic_cfg_s *cfg = aq_nic_get_cfg(aq_nic);
 313 
 314         /* This is not yet supported
 315          */
 316         if (coal->use_adaptive_rx_coalesce || coal->use_adaptive_tx_coalesce)
 317                 return -EOPNOTSUPP;
 318 
 319         /* Atlantic only supports timing based coalescing
 320          */
 321         if (coal->rx_max_coalesced_frames > 1 ||
 322             coal->rx_coalesce_usecs_irq ||
 323             coal->rx_max_coalesced_frames_irq)
 324                 return -EOPNOTSUPP;
 325 
 326         if (coal->tx_max_coalesced_frames > 1 ||
 327             coal->tx_coalesce_usecs_irq ||
 328             coal->tx_max_coalesced_frames_irq)
 329                 return -EOPNOTSUPP;
 330 
 331         /* We do not support frame counting. Check this
 332          */
 333         if (!(coal->rx_max_coalesced_frames == !coal->rx_coalesce_usecs))
 334                 return -EOPNOTSUPP;
 335         if (!(coal->tx_max_coalesced_frames == !coal->tx_coalesce_usecs))
 336                 return -EOPNOTSUPP;
 337 
 338         if (coal->rx_coalesce_usecs > AQ_CFG_INTERRUPT_MODERATION_USEC_MAX ||
 339             coal->tx_coalesce_usecs > AQ_CFG_INTERRUPT_MODERATION_USEC_MAX)
 340                 return -EINVAL;
 341 
 342         cfg->itr = AQ_CFG_INTERRUPT_MODERATION_ON;
 343 
 344         cfg->rx_itr = coal->rx_coalesce_usecs;
 345         cfg->tx_itr = coal->tx_coalesce_usecs;
 346 
 347         return aq_nic_update_interrupt_moderation_settings(aq_nic);
 348 }
 349 
 350 static void aq_ethtool_get_wol(struct net_device *ndev,
 351                                struct ethtool_wolinfo *wol)
 352 {
 353         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 354         struct aq_nic_cfg_s *cfg = aq_nic_get_cfg(aq_nic);
 355 
 356         wol->supported = WAKE_MAGIC;
 357         wol->wolopts = 0;
 358 
 359         if (cfg->wol)
 360                 wol->wolopts |= WAKE_MAGIC;
 361 }
 362 
 363 static int aq_ethtool_set_wol(struct net_device *ndev,
 364                               struct ethtool_wolinfo *wol)
 365 {
 366         struct pci_dev *pdev = to_pci_dev(ndev->dev.parent);
 367         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 368         struct aq_nic_cfg_s *cfg = aq_nic_get_cfg(aq_nic);
 369         int err = 0;
 370 
 371         if (wol->wolopts & WAKE_MAGIC)
 372                 cfg->wol |= AQ_NIC_WOL_ENABLED;
 373         else
 374                 cfg->wol &= ~AQ_NIC_WOL_ENABLED;
 375         err = device_set_wakeup_enable(&pdev->dev, wol->wolopts);
 376 
 377         return err;
 378 }
 379 
 380 static enum hw_atl_fw2x_rate eee_mask_to_ethtool_mask(u32 speed)
 381 {
 382         u32 rate = 0;
 383 
 384         if (speed & AQ_NIC_RATE_EEE_10G)
 385                 rate |= SUPPORTED_10000baseT_Full;
 386 
 387         if (speed & AQ_NIC_RATE_EEE_2GS)
 388                 rate |= SUPPORTED_2500baseX_Full;
 389 
 390         if (speed & AQ_NIC_RATE_EEE_1G)
 391                 rate |= SUPPORTED_1000baseT_Full;
 392 
 393         return rate;
 394 }
 395 
 396 static int aq_ethtool_get_eee(struct net_device *ndev, struct ethtool_eee *eee)
 397 {
 398         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 399         u32 rate, supported_rates;
 400         int err = 0;
 401 
 402         if (!aq_nic->aq_fw_ops->get_eee_rate)
 403                 return -EOPNOTSUPP;
 404 
 405         mutex_lock(&aq_nic->fwreq_mutex);
 406         err = aq_nic->aq_fw_ops->get_eee_rate(aq_nic->aq_hw, &rate,
 407                                               &supported_rates);
 408         mutex_unlock(&aq_nic->fwreq_mutex);
 409         if (err < 0)
 410                 return err;
 411 
 412         eee->supported = eee_mask_to_ethtool_mask(supported_rates);
 413 
 414         if (aq_nic->aq_nic_cfg.eee_speeds)
 415                 eee->advertised = eee->supported;
 416 
 417         eee->lp_advertised = eee_mask_to_ethtool_mask(rate);
 418 
 419         eee->eee_enabled = !!eee->advertised;
 420 
 421         eee->tx_lpi_enabled = eee->eee_enabled;
 422         if (eee->advertised & eee->lp_advertised)
 423                 eee->eee_active = true;
 424 
 425         return 0;
 426 }
 427 
 428 static int aq_ethtool_set_eee(struct net_device *ndev, struct ethtool_eee *eee)
 429 {
 430         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 431         u32 rate, supported_rates;
 432         struct aq_nic_cfg_s *cfg;
 433         int err = 0;
 434 
 435         cfg = aq_nic_get_cfg(aq_nic);
 436 
 437         if (unlikely(!aq_nic->aq_fw_ops->get_eee_rate ||
 438                      !aq_nic->aq_fw_ops->set_eee_rate))
 439                 return -EOPNOTSUPP;
 440 
 441         mutex_lock(&aq_nic->fwreq_mutex);
 442         err = aq_nic->aq_fw_ops->get_eee_rate(aq_nic->aq_hw, &rate,
 443                                               &supported_rates);
 444         mutex_unlock(&aq_nic->fwreq_mutex);
 445         if (err < 0)
 446                 return err;
 447 
 448         if (eee->eee_enabled) {
 449                 rate = supported_rates;
 450                 cfg->eee_speeds = rate;
 451         } else {
 452                 rate = 0;
 453                 cfg->eee_speeds = 0;
 454         }
 455 
 456         mutex_lock(&aq_nic->fwreq_mutex);
 457         err = aq_nic->aq_fw_ops->set_eee_rate(aq_nic->aq_hw, rate);
 458         mutex_unlock(&aq_nic->fwreq_mutex);
 459 
 460         return err;
 461 }
 462 
 463 static int aq_ethtool_nway_reset(struct net_device *ndev)
 464 {
 465         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 466         int err = 0;
 467 
 468         if (unlikely(!aq_nic->aq_fw_ops->renegotiate))
 469                 return -EOPNOTSUPP;
 470 
 471         if (netif_running(ndev)) {
 472                 mutex_lock(&aq_nic->fwreq_mutex);
 473                 err = aq_nic->aq_fw_ops->renegotiate(aq_nic->aq_hw);
 474                 mutex_unlock(&aq_nic->fwreq_mutex);
 475         }
 476 
 477         return err;
 478 }
 479 
 480 static void aq_ethtool_get_pauseparam(struct net_device *ndev,
 481                                       struct ethtool_pauseparam *pause)
 482 {
 483         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 484         u32 fc = aq_nic->aq_nic_cfg.flow_control;
 485 
 486         pause->autoneg = 0;
 487 
 488         pause->rx_pause = !!(fc & AQ_NIC_FC_RX);
 489         pause->tx_pause = !!(fc & AQ_NIC_FC_TX);
 490 
 491 }
 492 
 493 static int aq_ethtool_set_pauseparam(struct net_device *ndev,
 494                                      struct ethtool_pauseparam *pause)
 495 {
 496         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 497         int err = 0;
 498 
 499         if (!aq_nic->aq_fw_ops->set_flow_control)
 500                 return -EOPNOTSUPP;
 501 
 502         if (pause->autoneg == AUTONEG_ENABLE)
 503                 return -EOPNOTSUPP;
 504 
 505         if (pause->rx_pause)
 506                 aq_nic->aq_hw->aq_nic_cfg->flow_control |= AQ_NIC_FC_RX;
 507         else
 508                 aq_nic->aq_hw->aq_nic_cfg->flow_control &= ~AQ_NIC_FC_RX;
 509 
 510         if (pause->tx_pause)
 511                 aq_nic->aq_hw->aq_nic_cfg->flow_control |= AQ_NIC_FC_TX;
 512         else
 513                 aq_nic->aq_hw->aq_nic_cfg->flow_control &= ~AQ_NIC_FC_TX;
 514 
 515         mutex_lock(&aq_nic->fwreq_mutex);
 516         err = aq_nic->aq_fw_ops->set_flow_control(aq_nic->aq_hw);
 517         mutex_unlock(&aq_nic->fwreq_mutex);
 518 
 519         return err;
 520 }
 521 
 522 static void aq_get_ringparam(struct net_device *ndev,
 523                              struct ethtool_ringparam *ring)
 524 {
 525         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 526         struct aq_nic_cfg_s *aq_nic_cfg = aq_nic_get_cfg(aq_nic);
 527 
 528         ring->rx_pending = aq_nic_cfg->rxds;
 529         ring->tx_pending = aq_nic_cfg->txds;
 530 
 531         ring->rx_max_pending = aq_nic_cfg->aq_hw_caps->rxds_max;
 532         ring->tx_max_pending = aq_nic_cfg->aq_hw_caps->txds_max;
 533 }
 534 
 535 static int aq_set_ringparam(struct net_device *ndev,
 536                             struct ethtool_ringparam *ring)
 537 {
 538         int err = 0;
 539         bool ndev_running = false;
 540         struct aq_nic_s *aq_nic = netdev_priv(ndev);
 541         struct aq_nic_cfg_s *aq_nic_cfg = aq_nic_get_cfg(aq_nic);
 542         const struct aq_hw_caps_s *hw_caps = aq_nic_cfg->aq_hw_caps;
 543 
 544         if (ring->rx_mini_pending || ring->rx_jumbo_pending) {
 545                 err = -EOPNOTSUPP;
 546                 goto err_exit;
 547         }
 548 
 549         if (netif_running(ndev)) {
 550                 ndev_running = true;
 551                 dev_close(ndev);
 552         }
 553 
 554         aq_nic_free_vectors(aq_nic);
 555 
 556         aq_nic_cfg->rxds = max(ring->rx_pending, hw_caps->rxds_min);
 557         aq_nic_cfg->rxds = min(aq_nic_cfg->rxds, hw_caps->rxds_max);
 558         aq_nic_cfg->rxds = ALIGN(aq_nic_cfg->rxds, AQ_HW_RXD_MULTIPLE);
 559 
 560         aq_nic_cfg->txds = max(ring->tx_pending, hw_caps->txds_min);
 561         aq_nic_cfg->txds = min(aq_nic_cfg->txds, hw_caps->txds_max);
 562         aq_nic_cfg->txds = ALIGN(aq_nic_cfg->txds, AQ_HW_TXD_MULTIPLE);
 563 
 564         for (aq_nic->aq_vecs = 0; aq_nic->aq_vecs < aq_nic_cfg->vecs;
 565              aq_nic->aq_vecs++) {
 566                 aq_nic->aq_vec[aq_nic->aq_vecs] =
 567                     aq_vec_alloc(aq_nic, aq_nic->aq_vecs, aq_nic_cfg);
 568                 if (unlikely(!aq_nic->aq_vec[aq_nic->aq_vecs])) {
 569                         err = -ENOMEM;
 570                         goto err_exit;
 571                 }
 572         }
 573         if (ndev_running)
 574                 err = dev_open(ndev, NULL);
 575 
 576 err_exit:
 577         return err;
 578 }
 579 
 580 const struct ethtool_ops aq_ethtool_ops = {
 581         .get_link            = aq_ethtool_get_link,
 582         .get_regs_len        = aq_ethtool_get_regs_len,
 583         .get_regs            = aq_ethtool_get_regs,
 584         .get_drvinfo         = aq_ethtool_get_drvinfo,
 585         .get_strings         = aq_ethtool_get_strings,
 586         .get_rxfh_indir_size = aq_ethtool_get_rss_indir_size,
 587         .get_wol             = aq_ethtool_get_wol,
 588         .set_wol             = aq_ethtool_set_wol,
 589         .nway_reset          = aq_ethtool_nway_reset,
 590         .get_ringparam       = aq_get_ringparam,
 591         .set_ringparam       = aq_set_ringparam,
 592         .get_eee             = aq_ethtool_get_eee,
 593         .set_eee             = aq_ethtool_set_eee,
 594         .get_pauseparam      = aq_ethtool_get_pauseparam,
 595         .set_pauseparam      = aq_ethtool_set_pauseparam,
 596         .get_rxfh_key_size   = aq_ethtool_get_rss_key_size,
 597         .get_rxfh            = aq_ethtool_get_rss,
 598         .set_rxfh            = aq_ethtool_set_rss,
 599         .get_rxnfc           = aq_ethtool_get_rxnfc,
 600         .set_rxnfc           = aq_ethtool_set_rxnfc,
 601         .get_sset_count      = aq_ethtool_get_sset_count,
 602         .get_ethtool_stats   = aq_ethtool_stats,
 603         .get_link_ksettings  = aq_ethtool_get_link_ksettings,
 604         .set_link_ksettings  = aq_ethtool_set_link_ksettings,
 605         .get_coalesce        = aq_ethtool_get_coalesce,
 606         .set_coalesce        = aq_ethtool_set_coalesce,
 607 };

/* [<][>][^][v][top][bottom][index][help] */