1 // SPDX-License-Identifier: GPL-2.0-only 2 /* Atlantic Network Driver 3 * 4 * Copyright (C) 2014-2019 aQuantia Corporation 5 * Copyright (C) 2019-2020 Marvell International Ltd. 6 */ 7 8 /* File aq_ethtool.c: Definition of ethertool related functions. */ 9 10 #include "aq_ethtool.h" 11 #include "aq_nic.h" 12 #include "aq_vec.h" 13 #include "aq_ptp.h" 14 #include "aq_filters.h" 15 #include "aq_macsec.h" 16 #include "aq_main.h" 17 18 #include <linux/linkmode.h> 19 #include <linux/ptp_clock_kernel.h> 20 21 static void aq_ethtool_get_regs(struct net_device *ndev, 22 struct ethtool_regs *regs, void *p) 23 { 24 struct aq_nic_s *aq_nic = netdev_priv(ndev); 25 u32 regs_count; 26 27 regs_count = aq_nic_get_regs_count(aq_nic); 28 29 memset(p, 0, regs_count * sizeof(u32)); 30 aq_nic_get_regs(aq_nic, regs, p); 31 } 32 33 static int aq_ethtool_get_regs_len(struct net_device *ndev) 34 { 35 struct aq_nic_s *aq_nic = netdev_priv(ndev); 36 u32 regs_count; 37 38 regs_count = aq_nic_get_regs_count(aq_nic); 39 40 return regs_count * sizeof(u32); 41 } 42 43 static u32 aq_ethtool_get_link(struct net_device *ndev) 44 { 45 return ethtool_op_get_link(ndev); 46 } 47 48 static int aq_ethtool_get_link_ksettings(struct net_device *ndev, 49 struct ethtool_link_ksettings *cmd) 50 { 51 struct aq_nic_s *aq_nic = netdev_priv(ndev); 52 53 aq_nic_get_link_ksettings(aq_nic, cmd); 54 cmd->base.speed = netif_carrier_ok(ndev) ? 55 aq_nic_get_link_speed(aq_nic) : 0U; 56 57 return 0; 58 } 59 60 static int 61 aq_ethtool_set_link_ksettings(struct net_device *ndev, 62 const struct ethtool_link_ksettings *cmd) 63 { 64 struct aq_nic_s *aq_nic = netdev_priv(ndev); 65 66 return aq_nic_set_link_ksettings(aq_nic, cmd); 67 } 68 69 static const char aq_ethtool_stat_names[][ETH_GSTRING_LEN] = { 70 "InPackets", 71 "InUCast", 72 "InMCast", 73 "InBCast", 74 "InErrors", 75 "OutPackets", 76 "OutUCast", 77 "OutMCast", 78 "OutBCast", 79 "InUCastOctets", 80 "OutUCastOctets", 81 "InMCastOctets", 82 "OutMCastOctets", 83 "InBCastOctets", 84 "OutBCastOctets", 85 "InOctets", 86 "OutOctets", 87 "InPacketsDma", 88 "OutPacketsDma", 89 "InOctetsDma", 90 "OutOctetsDma", 91 "InDroppedDma", 92 }; 93 94 static const char * const aq_ethtool_queue_rx_stat_names[] = { 95 "%sQueue[%d] InPackets", 96 "%sQueue[%d] InJumboPackets", 97 "%sQueue[%d] InLroPackets", 98 "%sQueue[%d] InErrors", 99 "%sQueue[%d] AllocFails", 100 "%sQueue[%d] SkbAllocFails", 101 "%sQueue[%d] Polls", 102 "%sQueue[%d] PageFlips", 103 "%sQueue[%d] PageReuses", 104 "%sQueue[%d] PageFrees", 105 "%sQueue[%d] XdpAbort", 106 "%sQueue[%d] XdpDrop", 107 "%sQueue[%d] XdpPass", 108 "%sQueue[%d] XdpTx", 109 "%sQueue[%d] XdpInvalid", 110 "%sQueue[%d] XdpRedirect", 111 }; 112 113 static const char * const aq_ethtool_queue_tx_stat_names[] = { 114 "%sQueue[%d] OutPackets", 115 "%sQueue[%d] Restarts", 116 }; 117 118 #if IS_ENABLED(CONFIG_MACSEC) 119 static const char aq_macsec_stat_names[][ETH_GSTRING_LEN] = { 120 "MACSec InCtlPackets", 121 "MACSec InTaggedMissPackets", 122 "MACSec InUntaggedMissPackets", 123 "MACSec InNotagPackets", 124 "MACSec InUntaggedPackets", 125 "MACSec InBadTagPackets", 126 "MACSec InNoSciPackets", 127 "MACSec InUnknownSciPackets", 128 "MACSec InCtrlPortPassPackets", 129 "MACSec InUnctrlPortPassPackets", 130 "MACSec InCtrlPortFailPackets", 131 "MACSec InUnctrlPortFailPackets", 132 "MACSec InTooLongPackets", 133 "MACSec InIgpocCtlPackets", 134 "MACSec InEccErrorPackets", 135 "MACSec InUnctrlHitDropRedir", 136 "MACSec OutCtlPackets", 137 "MACSec OutUnknownSaPackets", 138 "MACSec OutUntaggedPackets", 139 "MACSec OutTooLong", 140 "MACSec OutEccErrorPackets", 141 "MACSec OutUnctrlHitDropRedir", 142 }; 143 144 static const char * const aq_macsec_txsc_stat_names[] = { 145 "MACSecTXSC%d ProtectedPkts", 146 "MACSecTXSC%d EncryptedPkts", 147 "MACSecTXSC%d ProtectedOctets", 148 "MACSecTXSC%d EncryptedOctets", 149 }; 150 151 static const char * const aq_macsec_txsa_stat_names[] = { 152 "MACSecTXSC%dSA%d HitDropRedirect", 153 "MACSecTXSC%dSA%d Protected2Pkts", 154 "MACSecTXSC%dSA%d ProtectedPkts", 155 "MACSecTXSC%dSA%d EncryptedPkts", 156 }; 157 158 static const char * const aq_macsec_rxsa_stat_names[] = { 159 "MACSecRXSC%dSA%d UntaggedHitPkts", 160 "MACSecRXSC%dSA%d CtrlHitDrpRedir", 161 "MACSecRXSC%dSA%d NotUsingSa", 162 "MACSecRXSC%dSA%d UnusedSa", 163 "MACSecRXSC%dSA%d NotValidPkts", 164 "MACSecRXSC%dSA%d InvalidPkts", 165 "MACSecRXSC%dSA%d OkPkts", 166 "MACSecRXSC%dSA%d LatePkts", 167 "MACSecRXSC%dSA%d DelayedPkts", 168 "MACSecRXSC%dSA%d UncheckedPkts", 169 "MACSecRXSC%dSA%d ValidatedOctets", 170 "MACSecRXSC%dSA%d DecryptedOctets", 171 }; 172 #endif 173 174 static const char aq_ethtool_priv_flag_names[][ETH_GSTRING_LEN] = { 175 "DMASystemLoopback", 176 "PKTSystemLoopback", 177 "DMANetworkLoopback", 178 "PHYInternalLoopback", 179 "PHYExternalLoopback", 180 }; 181 182 static u32 aq_ethtool_n_stats(struct net_device *ndev) 183 { 184 const int rx_stat_cnt = ARRAY_SIZE(aq_ethtool_queue_rx_stat_names); 185 const int tx_stat_cnt = ARRAY_SIZE(aq_ethtool_queue_tx_stat_names); 186 struct aq_nic_s *nic = netdev_priv(ndev); 187 struct aq_nic_cfg_s *cfg = aq_nic_get_cfg(nic); 188 u32 n_stats = ARRAY_SIZE(aq_ethtool_stat_names) + 189 (rx_stat_cnt + tx_stat_cnt) * cfg->vecs * cfg->tcs; 190 191 #if IS_REACHABLE(CONFIG_PTP_1588_CLOCK) 192 n_stats += rx_stat_cnt * aq_ptp_get_ring_cnt(nic, ATL_RING_RX) + 193 tx_stat_cnt * aq_ptp_get_ring_cnt(nic, ATL_RING_TX); 194 #endif 195 196 #if IS_ENABLED(CONFIG_MACSEC) 197 if (nic->macsec_cfg) { 198 n_stats += ARRAY_SIZE(aq_macsec_stat_names) + 199 ARRAY_SIZE(aq_macsec_txsc_stat_names) * 200 aq_macsec_tx_sc_cnt(nic) + 201 ARRAY_SIZE(aq_macsec_txsa_stat_names) * 202 aq_macsec_tx_sa_cnt(nic) + 203 ARRAY_SIZE(aq_macsec_rxsa_stat_names) * 204 aq_macsec_rx_sa_cnt(nic); 205 } 206 #endif 207 208 return n_stats; 209 } 210 211 static void aq_ethtool_stats(struct net_device *ndev, 212 struct ethtool_stats *stats, u64 *data) 213 { 214 struct aq_nic_s *aq_nic = netdev_priv(ndev); 215 216 memset(data, 0, aq_ethtool_n_stats(ndev) * sizeof(u64)); 217 data = aq_nic_get_stats(aq_nic, data); 218 #if IS_REACHABLE(CONFIG_PTP_1588_CLOCK) 219 data = aq_ptp_get_stats(aq_nic, data); 220 #endif 221 #if IS_ENABLED(CONFIG_MACSEC) 222 data = aq_macsec_get_stats(aq_nic, data); 223 #endif 224 } 225 226 static void aq_ethtool_get_drvinfo(struct net_device *ndev, 227 struct ethtool_drvinfo *drvinfo) 228 { 229 struct pci_dev *pdev = to_pci_dev(ndev->dev.parent); 230 struct aq_nic_s *aq_nic = netdev_priv(ndev); 231 u32 firmware_version; 232 u32 regs_count; 233 234 firmware_version = aq_nic_get_fw_version(aq_nic); 235 regs_count = aq_nic_get_regs_count(aq_nic); 236 237 strlcat(drvinfo->driver, AQ_CFG_DRV_NAME, sizeof(drvinfo->driver)); 238 239 snprintf(drvinfo->fw_version, sizeof(drvinfo->fw_version), 240 "%u.%u.%u", firmware_version >> 24, 241 (firmware_version >> 16) & 0xFFU, firmware_version & 0xFFFFU); 242 243 strscpy(drvinfo->bus_info, pdev ? pci_name(pdev) : "", 244 sizeof(drvinfo->bus_info)); 245 drvinfo->n_stats = aq_ethtool_n_stats(ndev); 246 drvinfo->testinfo_len = 0; 247 drvinfo->regdump_len = regs_count; 248 drvinfo->eedump_len = 0; 249 } 250 251 static void aq_ethtool_get_strings(struct net_device *ndev, 252 u32 stringset, u8 *data) 253 { 254 struct aq_nic_s *nic = netdev_priv(ndev); 255 struct aq_nic_cfg_s *cfg; 256 u8 *p = data; 257 int i, si; 258 #if IS_ENABLED(CONFIG_MACSEC) 259 int sa; 260 #endif 261 262 cfg = aq_nic_get_cfg(nic); 263 264 switch (stringset) { 265 case ETH_SS_STATS: { 266 const int rx_stat_cnt = ARRAY_SIZE(aq_ethtool_queue_rx_stat_names); 267 const int tx_stat_cnt = ARRAY_SIZE(aq_ethtool_queue_tx_stat_names); 268 char tc_string[8]; 269 unsigned int tc; 270 271 memset(tc_string, 0, sizeof(tc_string)); 272 memcpy(p, aq_ethtool_stat_names, 273 sizeof(aq_ethtool_stat_names)); 274 p = p + sizeof(aq_ethtool_stat_names); 275 276 for (tc = 0; tc < cfg->tcs; tc++) { 277 if (cfg->is_qos) 278 snprintf(tc_string, 8, "TC%u ", tc); 279 280 for (i = 0; i < cfg->vecs; i++) { 281 for (si = 0; si < rx_stat_cnt; si++) { 282 ethtool_sprintf(&p, 283 aq_ethtool_queue_rx_stat_names[si], 284 tc_string, 285 AQ_NIC_CFG_TCVEC2RING(cfg, tc, i)); 286 } 287 for (si = 0; si < tx_stat_cnt; si++) { 288 ethtool_sprintf(&p, 289 aq_ethtool_queue_tx_stat_names[si], 290 tc_string, 291 AQ_NIC_CFG_TCVEC2RING(cfg, tc, i)); 292 } 293 } 294 } 295 #if IS_REACHABLE(CONFIG_PTP_1588_CLOCK) 296 if (nic->aq_ptp) { 297 const int rx_ring_cnt = aq_ptp_get_ring_cnt(nic, ATL_RING_RX); 298 const int tx_ring_cnt = aq_ptp_get_ring_cnt(nic, ATL_RING_TX); 299 unsigned int ptp_ring_idx = 300 aq_ptp_ring_idx(nic->aq_nic_cfg.tc_mode); 301 302 snprintf(tc_string, 8, "PTP "); 303 304 for (i = 0; i < max(rx_ring_cnt, tx_ring_cnt); i++) { 305 for (si = 0; si < rx_stat_cnt; si++) { 306 ethtool_sprintf(&p, 307 aq_ethtool_queue_rx_stat_names[si], 308 tc_string, 309 i ? PTP_HWST_RING_IDX : ptp_ring_idx); 310 } 311 if (i >= tx_ring_cnt) 312 continue; 313 for (si = 0; si < tx_stat_cnt; si++) { 314 ethtool_sprintf(&p, 315 aq_ethtool_queue_tx_stat_names[si], 316 tc_string, 317 i ? PTP_HWST_RING_IDX : ptp_ring_idx); 318 } 319 } 320 } 321 #endif 322 #if IS_ENABLED(CONFIG_MACSEC) 323 if (!nic->macsec_cfg) 324 break; 325 326 memcpy(p, aq_macsec_stat_names, sizeof(aq_macsec_stat_names)); 327 p = p + sizeof(aq_macsec_stat_names); 328 for (i = 0; i < AQ_MACSEC_MAX_SC; i++) { 329 struct aq_macsec_txsc *aq_txsc; 330 331 if (!(test_bit(i, &nic->macsec_cfg->txsc_idx_busy))) 332 continue; 333 334 for (si = 0; 335 si < ARRAY_SIZE(aq_macsec_txsc_stat_names); 336 si++) { 337 ethtool_sprintf(&p, 338 aq_macsec_txsc_stat_names[si], i); 339 } 340 aq_txsc = &nic->macsec_cfg->aq_txsc[i]; 341 for (sa = 0; sa < MACSEC_NUM_AN; sa++) { 342 if (!(test_bit(sa, &aq_txsc->tx_sa_idx_busy))) 343 continue; 344 for (si = 0; 345 si < ARRAY_SIZE(aq_macsec_txsa_stat_names); 346 si++) { 347 ethtool_sprintf(&p, 348 aq_macsec_txsa_stat_names[si], 349 i, sa); 350 } 351 } 352 } 353 for (i = 0; i < AQ_MACSEC_MAX_SC; i++) { 354 struct aq_macsec_rxsc *aq_rxsc; 355 356 if (!(test_bit(i, &nic->macsec_cfg->rxsc_idx_busy))) 357 continue; 358 359 aq_rxsc = &nic->macsec_cfg->aq_rxsc[i]; 360 for (sa = 0; sa < MACSEC_NUM_AN; sa++) { 361 if (!(test_bit(sa, &aq_rxsc->rx_sa_idx_busy))) 362 continue; 363 for (si = 0; 364 si < ARRAY_SIZE(aq_macsec_rxsa_stat_names); 365 si++) { 366 ethtool_sprintf(&p, 367 aq_macsec_rxsa_stat_names[si], 368 i, sa); 369 } 370 } 371 } 372 #endif 373 break; 374 } 375 case ETH_SS_PRIV_FLAGS: 376 memcpy(p, aq_ethtool_priv_flag_names, 377 sizeof(aq_ethtool_priv_flag_names)); 378 break; 379 } 380 } 381 382 static int aq_ethtool_set_phys_id(struct net_device *ndev, 383 enum ethtool_phys_id_state state) 384 { 385 struct aq_nic_s *aq_nic = netdev_priv(ndev); 386 struct aq_hw_s *hw = aq_nic->aq_hw; 387 int ret = 0; 388 389 if (!aq_nic->aq_fw_ops->led_control) 390 return -EOPNOTSUPP; 391 392 mutex_lock(&aq_nic->fwreq_mutex); 393 394 switch (state) { 395 case ETHTOOL_ID_ACTIVE: 396 ret = aq_nic->aq_fw_ops->led_control(hw, AQ_HW_LED_BLINK | 397 AQ_HW_LED_BLINK << 2 | AQ_HW_LED_BLINK << 4); 398 break; 399 case ETHTOOL_ID_INACTIVE: 400 ret = aq_nic->aq_fw_ops->led_control(hw, AQ_HW_LED_DEFAULT); 401 break; 402 default: 403 break; 404 } 405 406 mutex_unlock(&aq_nic->fwreq_mutex); 407 408 return ret; 409 } 410 411 static int aq_ethtool_get_sset_count(struct net_device *ndev, int stringset) 412 { 413 int ret = 0; 414 415 switch (stringset) { 416 case ETH_SS_STATS: 417 ret = aq_ethtool_n_stats(ndev); 418 break; 419 case ETH_SS_PRIV_FLAGS: 420 ret = ARRAY_SIZE(aq_ethtool_priv_flag_names); 421 break; 422 default: 423 ret = -EOPNOTSUPP; 424 } 425 426 return ret; 427 } 428 429 static u32 aq_ethtool_get_rss_indir_size(struct net_device *ndev) 430 { 431 return AQ_CFG_RSS_INDIRECTION_TABLE_MAX; 432 } 433 434 static u32 aq_ethtool_get_rss_key_size(struct net_device *ndev) 435 { 436 struct aq_nic_s *aq_nic = netdev_priv(ndev); 437 struct aq_nic_cfg_s *cfg; 438 439 cfg = aq_nic_get_cfg(aq_nic); 440 441 return sizeof(cfg->aq_rss.hash_secret_key); 442 } 443 444 static int aq_ethtool_get_rss(struct net_device *ndev, 445 struct ethtool_rxfh_param *rxfh) 446 { 447 struct aq_nic_s *aq_nic = netdev_priv(ndev); 448 struct aq_nic_cfg_s *cfg; 449 unsigned int i = 0U; 450 451 cfg = aq_nic_get_cfg(aq_nic); 452 453 rxfh->hfunc = ETH_RSS_HASH_TOP; /* Toeplitz */ 454 if (rxfh->indir) { 455 for (i = 0; i < AQ_CFG_RSS_INDIRECTION_TABLE_MAX; i++) 456 rxfh->indir[i] = cfg->aq_rss.indirection_table[i]; 457 } 458 if (rxfh->key) 459 memcpy(rxfh->key, cfg->aq_rss.hash_secret_key, 460 sizeof(cfg->aq_rss.hash_secret_key)); 461 462 return 0; 463 } 464 465 static int aq_ethtool_set_rss(struct net_device *netdev, 466 struct ethtool_rxfh_param *rxfh, 467 struct netlink_ext_ack *extack) 468 { 469 struct aq_nic_s *aq_nic = netdev_priv(netdev); 470 struct aq_nic_cfg_s *cfg; 471 unsigned int i = 0U; 472 u32 rss_entries; 473 int err = 0; 474 475 cfg = aq_nic_get_cfg(aq_nic); 476 rss_entries = cfg->aq_rss.indirection_table_size; 477 478 /* We do not allow change in unsupported parameters */ 479 if (rxfh->hfunc != ETH_RSS_HASH_NO_CHANGE && 480 rxfh->hfunc != ETH_RSS_HASH_TOP) 481 return -EOPNOTSUPP; 482 /* Fill out the redirection table */ 483 if (rxfh->indir) 484 for (i = 0; i < rss_entries; i++) 485 cfg->aq_rss.indirection_table[i] = rxfh->indir[i]; 486 487 /* Fill out the rss hash key */ 488 if (rxfh->key) { 489 memcpy(cfg->aq_rss.hash_secret_key, rxfh->key, 490 sizeof(cfg->aq_rss.hash_secret_key)); 491 err = aq_nic->aq_hw_ops->hw_rss_hash_set(aq_nic->aq_hw, 492 &cfg->aq_rss); 493 if (err) 494 return err; 495 } 496 497 err = aq_nic->aq_hw_ops->hw_rss_set(aq_nic->aq_hw, &cfg->aq_rss); 498 499 return err; 500 } 501 502 static int aq_ethtool_get_rxnfc(struct net_device *ndev, 503 struct ethtool_rxnfc *cmd, 504 u32 *rule_locs) 505 { 506 struct aq_nic_s *aq_nic = netdev_priv(ndev); 507 struct aq_nic_cfg_s *cfg; 508 int err = 0; 509 510 cfg = aq_nic_get_cfg(aq_nic); 511 512 switch (cmd->cmd) { 513 case ETHTOOL_GRXRINGS: 514 cmd->data = cfg->vecs; 515 break; 516 case ETHTOOL_GRXCLSRLCNT: 517 cmd->rule_cnt = aq_get_rxnfc_count_all_rules(aq_nic); 518 break; 519 case ETHTOOL_GRXCLSRULE: 520 err = aq_get_rxnfc_rule(aq_nic, cmd); 521 break; 522 case ETHTOOL_GRXCLSRLALL: 523 err = aq_get_rxnfc_all_rules(aq_nic, cmd, rule_locs); 524 break; 525 default: 526 err = -EOPNOTSUPP; 527 break; 528 } 529 530 return err; 531 } 532 533 static int aq_ethtool_set_rxnfc(struct net_device *ndev, 534 struct ethtool_rxnfc *cmd) 535 { 536 struct aq_nic_s *aq_nic = netdev_priv(ndev); 537 int err = 0; 538 539 switch (cmd->cmd) { 540 case ETHTOOL_SRXCLSRLINS: 541 err = aq_add_rxnfc_rule(aq_nic, cmd); 542 break; 543 case ETHTOOL_SRXCLSRLDEL: 544 err = aq_del_rxnfc_rule(aq_nic, cmd); 545 break; 546 default: 547 err = -EOPNOTSUPP; 548 break; 549 } 550 551 return err; 552 } 553 554 static int aq_ethtool_get_coalesce(struct net_device *ndev, 555 struct ethtool_coalesce *coal, 556 struct kernel_ethtool_coalesce *kernel_coal, 557 struct netlink_ext_ack *extack) 558 { 559 struct aq_nic_s *aq_nic = netdev_priv(ndev); 560 struct aq_nic_cfg_s *cfg; 561 562 cfg = aq_nic_get_cfg(aq_nic); 563 564 if (cfg->itr == AQ_CFG_INTERRUPT_MODERATION_ON || 565 cfg->itr == AQ_CFG_INTERRUPT_MODERATION_AUTO) { 566 coal->rx_coalesce_usecs = cfg->rx_itr; 567 coal->tx_coalesce_usecs = cfg->tx_itr; 568 coal->rx_max_coalesced_frames = 0; 569 coal->tx_max_coalesced_frames = 0; 570 } else { 571 coal->rx_coalesce_usecs = 0; 572 coal->tx_coalesce_usecs = 0; 573 coal->rx_max_coalesced_frames = 1; 574 coal->tx_max_coalesced_frames = 1; 575 } 576 577 return 0; 578 } 579 580 static int aq_ethtool_set_coalesce(struct net_device *ndev, 581 struct ethtool_coalesce *coal, 582 struct kernel_ethtool_coalesce *kernel_coal, 583 struct netlink_ext_ack *extack) 584 { 585 struct aq_nic_s *aq_nic = netdev_priv(ndev); 586 struct aq_nic_cfg_s *cfg; 587 588 cfg = aq_nic_get_cfg(aq_nic); 589 590 /* Atlantic only supports timing based coalescing 591 */ 592 if (coal->rx_max_coalesced_frames > 1 || 593 coal->tx_max_coalesced_frames > 1) 594 return -EOPNOTSUPP; 595 596 /* We do not support frame counting. Check this 597 */ 598 if (!(coal->rx_max_coalesced_frames == !coal->rx_coalesce_usecs)) 599 return -EOPNOTSUPP; 600 if (!(coal->tx_max_coalesced_frames == !coal->tx_coalesce_usecs)) 601 return -EOPNOTSUPP; 602 603 if (coal->rx_coalesce_usecs > AQ_CFG_INTERRUPT_MODERATION_USEC_MAX || 604 coal->tx_coalesce_usecs > AQ_CFG_INTERRUPT_MODERATION_USEC_MAX) 605 return -EINVAL; 606 607 cfg->itr = AQ_CFG_INTERRUPT_MODERATION_ON; 608 609 cfg->rx_itr = coal->rx_coalesce_usecs; 610 cfg->tx_itr = coal->tx_coalesce_usecs; 611 612 return aq_nic_update_interrupt_moderation_settings(aq_nic); 613 } 614 615 static void aq_ethtool_get_wol(struct net_device *ndev, 616 struct ethtool_wolinfo *wol) 617 { 618 struct aq_nic_s *aq_nic = netdev_priv(ndev); 619 struct aq_nic_cfg_s *cfg; 620 621 cfg = aq_nic_get_cfg(aq_nic); 622 623 wol->supported = AQ_NIC_WOL_MODES; 624 wol->wolopts = cfg->wol; 625 } 626 627 static int aq_ethtool_set_wol(struct net_device *ndev, 628 struct ethtool_wolinfo *wol) 629 { 630 struct pci_dev *pdev = to_pci_dev(ndev->dev.parent); 631 struct aq_nic_s *aq_nic = netdev_priv(ndev); 632 struct aq_nic_cfg_s *cfg; 633 int err = 0; 634 635 cfg = aq_nic_get_cfg(aq_nic); 636 637 if (wol->wolopts & ~AQ_NIC_WOL_MODES) 638 return -EOPNOTSUPP; 639 640 cfg->wol = wol->wolopts; 641 642 err = device_set_wakeup_enable(&pdev->dev, !!cfg->wol); 643 644 return err; 645 } 646 647 static int aq_ethtool_get_ts_info(struct net_device *ndev, 648 struct kernel_ethtool_ts_info *info) 649 { 650 struct aq_nic_s *aq_nic = netdev_priv(ndev); 651 652 ethtool_op_get_ts_info(ndev, info); 653 654 if (!aq_nic->aq_ptp) 655 return 0; 656 657 info->so_timestamping |= 658 SOF_TIMESTAMPING_TX_HARDWARE | 659 SOF_TIMESTAMPING_RX_HARDWARE | 660 SOF_TIMESTAMPING_RAW_HARDWARE; 661 662 info->tx_types = BIT(HWTSTAMP_TX_OFF) | 663 BIT(HWTSTAMP_TX_ON); 664 665 info->rx_filters = BIT(HWTSTAMP_FILTER_NONE); 666 667 info->rx_filters |= BIT(HWTSTAMP_FILTER_PTP_V2_L4_EVENT) | 668 BIT(HWTSTAMP_FILTER_PTP_V2_L2_EVENT) | 669 BIT(HWTSTAMP_FILTER_PTP_V2_EVENT); 670 671 #if IS_REACHABLE(CONFIG_PTP_1588_CLOCK) 672 info->phc_index = ptp_clock_index(aq_ptp_get_ptp_clock(aq_nic->aq_ptp)); 673 #endif 674 675 return 0; 676 } 677 678 static void eee_mask_to_ethtool_mask(unsigned long *mode, u32 speed) 679 { 680 if (speed & AQ_NIC_RATE_EEE_10G) 681 linkmode_set_bit(ETHTOOL_LINK_MODE_10000baseT_Full_BIT, mode); 682 683 if (speed & AQ_NIC_RATE_EEE_1G) 684 linkmode_set_bit(ETHTOOL_LINK_MODE_1000baseT_Full_BIT, mode); 685 686 if (speed & AQ_NIC_RATE_EEE_100M) 687 linkmode_set_bit(ETHTOOL_LINK_MODE_100baseT_Full_BIT, mode); 688 } 689 690 static int aq_ethtool_get_eee(struct net_device *ndev, struct ethtool_keee *eee) 691 { 692 struct aq_nic_s *aq_nic = netdev_priv(ndev); 693 u32 rate, supported_rates; 694 int err = 0; 695 696 if (!aq_nic->aq_fw_ops->get_eee_rate) 697 return -EOPNOTSUPP; 698 699 mutex_lock(&aq_nic->fwreq_mutex); 700 err = aq_nic->aq_fw_ops->get_eee_rate(aq_nic->aq_hw, &rate, 701 &supported_rates); 702 mutex_unlock(&aq_nic->fwreq_mutex); 703 if (err < 0) 704 return err; 705 706 eee_mask_to_ethtool_mask(eee->supported, supported_rates); 707 708 if (aq_nic->aq_nic_cfg.eee_speeds) 709 linkmode_copy(eee->advertised, eee->supported); 710 711 eee_mask_to_ethtool_mask(eee->lp_advertised, rate); 712 713 eee->eee_enabled = !linkmode_empty(eee->advertised); 714 715 eee->tx_lpi_enabled = eee->eee_enabled; 716 if ((supported_rates & rate) & AQ_NIC_RATE_EEE_MSK) 717 eee->eee_active = true; 718 719 return 0; 720 } 721 722 static int aq_ethtool_set_eee(struct net_device *ndev, struct ethtool_keee *eee) 723 { 724 struct aq_nic_s *aq_nic = netdev_priv(ndev); 725 u32 rate, supported_rates; 726 struct aq_nic_cfg_s *cfg; 727 int err = 0; 728 729 cfg = aq_nic_get_cfg(aq_nic); 730 731 if (unlikely(!aq_nic->aq_fw_ops->get_eee_rate || 732 !aq_nic->aq_fw_ops->set_eee_rate)) 733 return -EOPNOTSUPP; 734 735 mutex_lock(&aq_nic->fwreq_mutex); 736 err = aq_nic->aq_fw_ops->get_eee_rate(aq_nic->aq_hw, &rate, 737 &supported_rates); 738 mutex_unlock(&aq_nic->fwreq_mutex); 739 if (err < 0) 740 return err; 741 742 if (eee->eee_enabled) { 743 rate = supported_rates; 744 cfg->eee_speeds = rate; 745 } else { 746 rate = 0; 747 cfg->eee_speeds = 0; 748 } 749 750 mutex_lock(&aq_nic->fwreq_mutex); 751 err = aq_nic->aq_fw_ops->set_eee_rate(aq_nic->aq_hw, rate); 752 mutex_unlock(&aq_nic->fwreq_mutex); 753 754 return err; 755 } 756 757 static int aq_ethtool_nway_reset(struct net_device *ndev) 758 { 759 struct aq_nic_s *aq_nic = netdev_priv(ndev); 760 int err = 0; 761 762 if (unlikely(!aq_nic->aq_fw_ops->renegotiate)) 763 return -EOPNOTSUPP; 764 765 if (netif_running(ndev)) { 766 mutex_lock(&aq_nic->fwreq_mutex); 767 err = aq_nic->aq_fw_ops->renegotiate(aq_nic->aq_hw); 768 mutex_unlock(&aq_nic->fwreq_mutex); 769 } 770 771 return err; 772 } 773 774 static void aq_ethtool_get_pauseparam(struct net_device *ndev, 775 struct ethtool_pauseparam *pause) 776 { 777 struct aq_nic_s *aq_nic = netdev_priv(ndev); 778 int fc = aq_nic->aq_nic_cfg.fc.req; 779 780 pause->autoneg = 0; 781 782 pause->rx_pause = !!(fc & AQ_NIC_FC_RX); 783 pause->tx_pause = !!(fc & AQ_NIC_FC_TX); 784 } 785 786 static int aq_ethtool_set_pauseparam(struct net_device *ndev, 787 struct ethtool_pauseparam *pause) 788 { 789 struct aq_nic_s *aq_nic = netdev_priv(ndev); 790 int err = 0; 791 792 if (!aq_nic->aq_fw_ops->set_flow_control) 793 return -EOPNOTSUPP; 794 795 if (pause->autoneg == AUTONEG_ENABLE) 796 return -EOPNOTSUPP; 797 798 if (pause->rx_pause) 799 aq_nic->aq_hw->aq_nic_cfg->fc.req |= AQ_NIC_FC_RX; 800 else 801 aq_nic->aq_hw->aq_nic_cfg->fc.req &= ~AQ_NIC_FC_RX; 802 803 if (pause->tx_pause) 804 aq_nic->aq_hw->aq_nic_cfg->fc.req |= AQ_NIC_FC_TX; 805 else 806 aq_nic->aq_hw->aq_nic_cfg->fc.req &= ~AQ_NIC_FC_TX; 807 808 mutex_lock(&aq_nic->fwreq_mutex); 809 err = aq_nic->aq_fw_ops->set_flow_control(aq_nic->aq_hw); 810 mutex_unlock(&aq_nic->fwreq_mutex); 811 812 return err; 813 } 814 815 static void aq_get_ringparam(struct net_device *ndev, 816 struct ethtool_ringparam *ring, 817 struct kernel_ethtool_ringparam *kernel_ring, 818 struct netlink_ext_ack *extack) 819 { 820 struct aq_nic_s *aq_nic = netdev_priv(ndev); 821 struct aq_nic_cfg_s *cfg; 822 823 cfg = aq_nic_get_cfg(aq_nic); 824 825 ring->rx_pending = cfg->rxds; 826 ring->tx_pending = cfg->txds; 827 828 ring->rx_max_pending = cfg->aq_hw_caps->rxds_max; 829 ring->tx_max_pending = cfg->aq_hw_caps->txds_max; 830 } 831 832 static int aq_set_ringparam(struct net_device *ndev, 833 struct ethtool_ringparam *ring, 834 struct kernel_ethtool_ringparam *kernel_ring, 835 struct netlink_ext_ack *extack) 836 { 837 struct aq_nic_s *aq_nic = netdev_priv(ndev); 838 const struct aq_hw_caps_s *hw_caps; 839 bool ndev_running = false; 840 struct aq_nic_cfg_s *cfg; 841 int err = 0; 842 843 cfg = aq_nic_get_cfg(aq_nic); 844 hw_caps = cfg->aq_hw_caps; 845 846 if (ring->rx_mini_pending || ring->rx_jumbo_pending) { 847 err = -EOPNOTSUPP; 848 goto err_exit; 849 } 850 851 if (netif_running(ndev)) { 852 ndev_running = true; 853 aq_ndev_close(ndev); 854 } 855 856 cfg->rxds = max(ring->rx_pending, hw_caps->rxds_min); 857 cfg->rxds = min(cfg->rxds, hw_caps->rxds_max); 858 cfg->rxds = ALIGN(cfg->rxds, AQ_HW_RXD_MULTIPLE); 859 860 cfg->txds = max(ring->tx_pending, hw_caps->txds_min); 861 cfg->txds = min(cfg->txds, hw_caps->txds_max); 862 cfg->txds = ALIGN(cfg->txds, AQ_HW_TXD_MULTIPLE); 863 864 err = aq_nic_realloc_vectors(aq_nic); 865 if (err) 866 goto err_exit; 867 868 if (ndev_running) 869 err = aq_ndev_open(ndev); 870 871 err_exit: 872 return err; 873 } 874 875 static u32 aq_get_msg_level(struct net_device *ndev) 876 { 877 struct aq_nic_s *aq_nic = netdev_priv(ndev); 878 879 return aq_nic->msg_enable; 880 } 881 882 static void aq_set_msg_level(struct net_device *ndev, u32 data) 883 { 884 struct aq_nic_s *aq_nic = netdev_priv(ndev); 885 886 aq_nic->msg_enable = data; 887 } 888 889 static u32 aq_ethtool_get_priv_flags(struct net_device *ndev) 890 { 891 struct aq_nic_s *aq_nic = netdev_priv(ndev); 892 893 return aq_nic->aq_nic_cfg.priv_flags; 894 } 895 896 static int aq_ethtool_set_priv_flags(struct net_device *ndev, u32 flags) 897 { 898 struct aq_nic_s *aq_nic = netdev_priv(ndev); 899 struct aq_nic_cfg_s *cfg; 900 u32 priv_flags; 901 int ret = 0; 902 903 cfg = aq_nic_get_cfg(aq_nic); 904 priv_flags = cfg->priv_flags; 905 906 if (flags & ~AQ_PRIV_FLAGS_MASK) 907 return -EOPNOTSUPP; 908 909 if (hweight32((flags | priv_flags) & AQ_HW_LOOPBACK_MASK) > 1) { 910 netdev_info(ndev, "Can't enable more than one loopback simultaneously\n"); 911 return -EINVAL; 912 } 913 914 cfg->priv_flags = flags; 915 916 if ((priv_flags ^ flags) & BIT(AQ_HW_LOOPBACK_DMA_NET)) { 917 if (netif_running(ndev)) { 918 dev_close(ndev); 919 920 dev_open(ndev, NULL); 921 } 922 } else if ((priv_flags ^ flags) & AQ_HW_LOOPBACK_MASK) { 923 ret = aq_nic_set_loopback(aq_nic); 924 } 925 926 return ret; 927 } 928 929 static int aq_ethtool_get_phy_tunable(struct net_device *ndev, 930 const struct ethtool_tunable *tuna, void *data) 931 { 932 struct aq_nic_s *aq_nic = netdev_priv(ndev); 933 934 switch (tuna->id) { 935 case ETHTOOL_PHY_EDPD: { 936 u16 *val = data; 937 938 *val = aq_nic->aq_nic_cfg.is_media_detect ? AQ_HW_MEDIA_DETECT_CNT : 0; 939 break; 940 } 941 case ETHTOOL_PHY_DOWNSHIFT: { 942 u8 *val = data; 943 944 *val = (u8)aq_nic->aq_nic_cfg.downshift_counter; 945 break; 946 } 947 default: 948 return -EOPNOTSUPP; 949 } 950 951 return 0; 952 } 953 954 static int aq_ethtool_set_phy_tunable(struct net_device *ndev, 955 const struct ethtool_tunable *tuna, const void *data) 956 { 957 int err = -EOPNOTSUPP; 958 struct aq_nic_s *aq_nic = netdev_priv(ndev); 959 960 switch (tuna->id) { 961 case ETHTOOL_PHY_EDPD: { 962 const u16 *val = data; 963 964 err = aq_nic_set_media_detect(aq_nic, *val); 965 break; 966 } 967 case ETHTOOL_PHY_DOWNSHIFT: { 968 const u8 *val = data; 969 970 err = aq_nic_set_downshift(aq_nic, *val); 971 break; 972 } 973 default: 974 break; 975 } 976 977 return err; 978 } 979 980 const struct ethtool_ops aq_ethtool_ops = { 981 .supported_coalesce_params = ETHTOOL_COALESCE_USECS | 982 ETHTOOL_COALESCE_MAX_FRAMES, 983 .get_link = aq_ethtool_get_link, 984 .get_regs_len = aq_ethtool_get_regs_len, 985 .get_regs = aq_ethtool_get_regs, 986 .get_drvinfo = aq_ethtool_get_drvinfo, 987 .get_strings = aq_ethtool_get_strings, 988 .set_phys_id = aq_ethtool_set_phys_id, 989 .get_rxfh_indir_size = aq_ethtool_get_rss_indir_size, 990 .get_wol = aq_ethtool_get_wol, 991 .set_wol = aq_ethtool_set_wol, 992 .nway_reset = aq_ethtool_nway_reset, 993 .get_ringparam = aq_get_ringparam, 994 .set_ringparam = aq_set_ringparam, 995 .get_eee = aq_ethtool_get_eee, 996 .set_eee = aq_ethtool_set_eee, 997 .get_pauseparam = aq_ethtool_get_pauseparam, 998 .set_pauseparam = aq_ethtool_set_pauseparam, 999 .get_rxfh_key_size = aq_ethtool_get_rss_key_size, 1000 .get_rxfh = aq_ethtool_get_rss, 1001 .set_rxfh = aq_ethtool_set_rss, 1002 .get_rxnfc = aq_ethtool_get_rxnfc, 1003 .set_rxnfc = aq_ethtool_set_rxnfc, 1004 .get_msglevel = aq_get_msg_level, 1005 .set_msglevel = aq_set_msg_level, 1006 .get_sset_count = aq_ethtool_get_sset_count, 1007 .get_ethtool_stats = aq_ethtool_stats, 1008 .get_priv_flags = aq_ethtool_get_priv_flags, 1009 .set_priv_flags = aq_ethtool_set_priv_flags, 1010 .get_link_ksettings = aq_ethtool_get_link_ksettings, 1011 .set_link_ksettings = aq_ethtool_set_link_ksettings, 1012 .get_coalesce = aq_ethtool_get_coalesce, 1013 .set_coalesce = aq_ethtool_set_coalesce, 1014 .get_ts_info = aq_ethtool_get_ts_info, 1015 .get_phy_tunable = aq_ethtool_get_phy_tunable, 1016 .set_phy_tunable = aq_ethtool_set_phy_tunable, 1017 }; 1018