Skip to content

Commit 01f5f35

Browse files
committed
Merge branch 'net-ethtool-fixes-for-hds-threshold'
Jakub Kicinski says: ==================== net: ethtool: fixes for HDS threshold Quick follow up on the HDS threshold work, since the merge window is upon us. Fix the bnxt implementation to apply the settings right away, because we update the parameters _after_ configuring HW user needed to reconfig the device twice to get the settings to stick. For this I took the liberty of moving the config to a separate struct. This follows my original thinking for the queue API. It should also fit more neatly into how many drivers which support safe config update operate. Drivers can allocate new objects using the "pending" struct. netdevsim: KTAP version 1 1..7 ok 1 hds.get_hds ok 2 hds.get_hds_thresh ok 3 hds.set_hds_disable ok 4 hds.set_hds_enable ok 5 hds.set_hds_thresh_zero ok 6 hds.set_hds_thresh_max ok 7 hds.set_hds_thresh_gt # Totals: pass:7 fail:0 xfail:0 xpass:0 skip:0 error:0 bnxt: KTAP version 1 1..7 ok 1 hds.get_hds ok 2 hds.get_hds_thresh ok 3 hds.set_hds_disable # SKIP disabling of HDS not supported by the device ok 4 hds.set_hds_enable ok 5 hds.set_hds_thresh_zero ok 6 hds.set_hds_thresh_max ok 7 hds.set_hds_thresh_gt # Totals: pass:6 fail:0 xfail:0 xpass:0 skip:1 error:0 v1: https://lore.kernel.org/20250117194815.1514410-1-kuba@kernel.org ==================== Link: https://patch.msgid.link/20250119020518.1962249-1-kuba@kernel.org Signed-off-by: Jakub Kicinski <kuba@kernel.org>
2 parents e81fdf7 + 99d028c commit 01f5f35

File tree

11 files changed

+84
-37
lines changed

11 files changed

+84
-37
lines changed

drivers/net/ethernet/broadcom/bnxt/bnxt.c

Lines changed: 11 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -4609,8 +4609,13 @@ void bnxt_set_tpa_flags(struct bnxt *bp)
46094609

46104610
static void bnxt_init_ring_params(struct bnxt *bp)
46114611
{
4612+
unsigned int rx_size;
4613+
46124614
bp->rx_copybreak = BNXT_DEFAULT_RX_COPYBREAK;
4613-
bp->dev->ethtool->hds_thresh = BNXT_DEFAULT_RX_COPYBREAK;
4615+
/* Try to fit 4 chunks into a 4k page */
4616+
rx_size = SZ_1K -
4617+
NET_SKB_PAD - SKB_DATA_ALIGN(sizeof(struct skb_shared_info));
4618+
bp->dev->cfg->hds_thresh = max(BNXT_DEFAULT_RX_COPYBREAK, rx_size);
46144619
}
46154620

46164621
/* bp->rx_ring_size, bp->tx_ring_size, dev->mtu, BNXT_FLAG_{G|L}RO flags must
@@ -4671,9 +4676,10 @@ void bnxt_set_ring_params(struct bnxt *bp)
46714676
ALIGN(max(NET_SKB_PAD, XDP_PACKET_HEADROOM), 8) -
46724677
SKB_DATA_ALIGN(sizeof(struct skb_shared_info));
46734678
} else {
4674-
rx_size = SKB_DATA_ALIGN(max(BNXT_DEFAULT_RX_COPYBREAK,
4675-
bp->rx_copybreak) +
4676-
NET_IP_ALIGN);
4679+
rx_size = max3(BNXT_DEFAULT_RX_COPYBREAK,
4680+
bp->rx_copybreak,
4681+
bp->dev->cfg_pending->hds_thresh);
4682+
rx_size = SKB_DATA_ALIGN(rx_size + NET_IP_ALIGN);
46774683
rx_space = rx_size + NET_SKB_PAD +
46784684
SKB_DATA_ALIGN(sizeof(struct skb_shared_info));
46794685
}
@@ -6585,7 +6591,7 @@ static void bnxt_hwrm_update_rss_hash_cfg(struct bnxt *bp)
65856591

65866592
static int bnxt_hwrm_vnic_set_hds(struct bnxt *bp, struct bnxt_vnic_info *vnic)
65876593
{
6588-
u16 hds_thresh = (u16)bp->dev->ethtool->hds_thresh;
6594+
u16 hds_thresh = (u16)bp->dev->cfg_pending->hds_thresh;
65896595
struct hwrm_vnic_plcmodes_cfg_input *req;
65906596
int rc;
65916597

drivers/net/ethernet/broadcom/bnxt/bnxt_ethtool.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@
2424
#include <linux/ptp_clock_kernel.h>
2525
#include <linux/net_tstamp.h>
2626
#include <linux/timecounter.h>
27+
#include <net/netdev_queues.h>
2728
#include <net/netlink.h>
2829
#include "bnxt_hsi.h"
2930
#include "bnxt.h"
@@ -834,7 +835,6 @@ static void bnxt_get_ringparam(struct net_device *dev,
834835
ering->rx_jumbo_pending = bp->rx_agg_ring_size;
835836
ering->tx_pending = bp->tx_ring_size;
836837

837-
kernel_ering->hds_thresh = dev->ethtool->hds_thresh;
838838
kernel_ering->hds_thresh_max = BNXT_HDS_THRESHOLD_MAX;
839839
}
840840

@@ -852,7 +852,7 @@ static int bnxt_set_ringparam(struct net_device *dev,
852852
(ering->tx_pending < BNXT_MIN_TX_DESC_CNT))
853853
return -EINVAL;
854854

855-
hds_config_mod = tcp_data_split != dev->ethtool->hds_config;
855+
hds_config_mod = tcp_data_split != dev->cfg->hds_config;
856856
if (tcp_data_split == ETHTOOL_TCP_DATA_SPLIT_DISABLED && hds_config_mod)
857857
return -EINVAL;
858858

drivers/net/netdevsim/ethtool.c

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33

44
#include <linux/debugfs.h>
55
#include <linux/random.h>
6+
#include <net/netdev_queues.h>
67

78
#include "netdevsim.h"
89

@@ -71,8 +72,6 @@ static void nsim_get_ringparam(struct net_device *dev,
7172
struct netdevsim *ns = netdev_priv(dev);
7273

7374
memcpy(ring, &ns->ethtool.ring, sizeof(ns->ethtool.ring));
74-
kernel_ring->tcp_data_split = dev->ethtool->hds_config;
75-
kernel_ring->hds_thresh = dev->ethtool->hds_thresh;
7675
kernel_ring->hds_thresh_max = NSIM_HDS_THRESHOLD_MAX;
7776

7877
if (kernel_ring->tcp_data_split == ETHTOOL_TCP_DATA_SPLIT_UNKNOWN)
@@ -189,9 +188,6 @@ static void nsim_ethtool_ring_init(struct netdevsim *ns)
189188
ns->ethtool.ring.rx_jumbo_max_pending = 4096;
190189
ns->ethtool.ring.rx_mini_max_pending = 4096;
191190
ns->ethtool.ring.tx_max_pending = 4096;
192-
193-
ns->netdev->ethtool->hds_config = ETHTOOL_TCP_DATA_SPLIT_UNKNOWN;
194-
ns->netdev->ethtool->hds_thresh = 0;
195191
}
196192

197193
void nsim_ethtool_init(struct netdevsim *ns)

drivers/net/netdevsim/netdev.c

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -55,10 +55,10 @@ static int nsim_forward_skb(struct net_device *dev, struct sk_buff *skb,
5555
static netdev_tx_t nsim_start_xmit(struct sk_buff *skb, struct net_device *dev)
5656
{
5757
struct netdevsim *ns = netdev_priv(dev);
58-
struct ethtool_netdev_state *ethtool;
5958
struct net_device *peer_dev;
6059
unsigned int len = skb->len;
6160
struct netdevsim *peer_ns;
61+
struct netdev_config *cfg;
6262
struct nsim_rq *rq;
6363
int rxq;
6464

@@ -76,11 +76,11 @@ static netdev_tx_t nsim_start_xmit(struct sk_buff *skb, struct net_device *dev)
7676
rxq = rxq % peer_dev->num_rx_queues;
7777
rq = peer_ns->rq[rxq];
7878

79-
ethtool = peer_dev->ethtool;
79+
cfg = peer_dev->cfg;
8080
if (skb_is_nonlinear(skb) &&
81-
(ethtool->hds_config != ETHTOOL_TCP_DATA_SPLIT_ENABLED ||
82-
(ethtool->hds_config == ETHTOOL_TCP_DATA_SPLIT_ENABLED &&
83-
ethtool->hds_thresh > len)))
81+
(cfg->hds_config != ETHTOOL_TCP_DATA_SPLIT_ENABLED ||
82+
(cfg->hds_config == ETHTOOL_TCP_DATA_SPLIT_ENABLED &&
83+
cfg->hds_thresh > len)))
8484
skb_linearize(skb);
8585

8686
skb_tx_timestamp(skb);

include/linux/ethtool.h

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1171,16 +1171,12 @@ int ethtool_virtdev_set_link_ksettings(struct net_device *dev,
11711171
* @rss_ctx: XArray of custom RSS contexts
11721172
* @rss_lock: Protects entries in @rss_ctx. May be taken from
11731173
* within RTNL.
1174-
* @hds_thresh: HDS Threshold value.
1175-
* @hds_config: HDS value from userspace.
11761174
* @wol_enabled: Wake-on-LAN is enabled
11771175
* @module_fw_flash_in_progress: Module firmware flashing is in progress.
11781176
*/
11791177
struct ethtool_netdev_state {
11801178
struct xarray rss_ctx;
11811179
struct mutex rss_lock;
1182-
u32 hds_thresh;
1183-
u8 hds_config;
11841180
unsigned wol_enabled:1;
11851181
unsigned module_fw_flash_in_progress:1;
11861182
};

include/linux/netdevice.h

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -63,6 +63,7 @@ struct dsa_port;
6363
struct ip_tunnel_parm_kern;
6464
struct macsec_context;
6565
struct macsec_ops;
66+
struct netdev_config;
6667
struct netdev_name_node;
6768
struct sd_flow_limit;
6869
struct sfp_bus;
@@ -2410,6 +2411,14 @@ struct net_device {
24102411
const struct udp_tunnel_nic_info *udp_tunnel_nic_info;
24112412
struct udp_tunnel_nic *udp_tunnel_nic;
24122413

2414+
/** @cfg: net_device queue-related configuration */
2415+
struct netdev_config *cfg;
2416+
/**
2417+
* @cfg_pending: same as @cfg but when device is being actively
2418+
* reconfigured includes any changes to the configuration
2419+
* requested by the user, but which may or may not be rejected.
2420+
*/
2421+
struct netdev_config *cfg_pending;
24132422
struct ethtool_netdev_state *ethtool;
24142423

24152424
/* protected by rtnl_lock */

include/net/netdev_queues.h

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,16 @@
44

55
#include <linux/netdevice.h>
66

7+
/**
8+
* struct netdev_config - queue-related configuration for a netdev
9+
* @hds_thresh: HDS Threshold value.
10+
* @hds_config: HDS value from userspace.
11+
*/
12+
struct netdev_config {
13+
u32 hds_thresh;
14+
u8 hds_config;
15+
};
16+
717
/* See the netdev.yaml spec for definition of each statistic */
818
struct netdev_queue_stats_rx {
919
u64 bytes;

net/core/dev.c

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -106,6 +106,7 @@
106106
#include <net/dst.h>
107107
#include <net/dst_metadata.h>
108108
#include <net/gro.h>
109+
#include <net/netdev_queues.h>
109110
#include <net/pkt_sched.h>
110111
#include <net/pkt_cls.h>
111112
#include <net/checksum.h>
@@ -9719,7 +9720,7 @@ int dev_xdp_propagate(struct net_device *dev, struct netdev_bpf *bpf)
97199720
if (!dev->netdev_ops->ndo_bpf)
97209721
return -EOPNOTSUPP;
97219722

9722-
if (dev->ethtool->hds_config == ETHTOOL_TCP_DATA_SPLIT_ENABLED &&
9723+
if (dev->cfg->hds_config == ETHTOOL_TCP_DATA_SPLIT_ENABLED &&
97239724
bpf->command == XDP_SETUP_PROG &&
97249725
bpf->prog && !bpf->prog->aux->xdp_has_frags) {
97259726
NL_SET_ERR_MSG(bpf->extack,
@@ -9764,7 +9765,7 @@ static int dev_xdp_install(struct net_device *dev, enum bpf_xdp_mode mode,
97649765
struct netdev_bpf xdp;
97659766
int err;
97669767

9767-
if (dev->ethtool->hds_config == ETHTOOL_TCP_DATA_SPLIT_ENABLED &&
9768+
if (dev->cfg->hds_config == ETHTOOL_TCP_DATA_SPLIT_ENABLED &&
97689769
prog && !prog->aux->xdp_has_frags) {
97699770
NL_SET_ERR_MSG(extack, "unable to install XDP to device using tcp-data-split");
97709771
return -EBUSY;
@@ -11542,6 +11543,11 @@ struct net_device *alloc_netdev_mqs(int sizeof_priv, const char *name,
1154211543
if (!dev->ethtool)
1154311544
goto free_all;
1154411545

11546+
dev->cfg = kzalloc(sizeof(*dev->cfg), GFP_KERNEL_ACCOUNT);
11547+
if (!dev->cfg)
11548+
goto free_all;
11549+
dev->cfg_pending = dev->cfg;
11550+
1154511551
napi_config_sz = array_size(maxqs, sizeof(*dev->napi_config));
1154611552
dev->napi_config = kvzalloc(napi_config_sz, GFP_KERNEL_ACCOUNT);
1154711553
if (!dev->napi_config)
@@ -11610,6 +11616,8 @@ void free_netdev(struct net_device *dev)
1161011616
return;
1161111617
}
1161211618

11619+
WARN_ON(dev->cfg != dev->cfg_pending);
11620+
kfree(dev->cfg);
1161311621
kfree(dev->ethtool);
1161411622
netif_free_tx_queues(dev);
1161511623
netif_free_rx_queues(dev);

net/core/devmem.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -141,12 +141,12 @@ int net_devmem_bind_dmabuf_to_queue(struct net_device *dev, u32 rxq_idx,
141141
return -ERANGE;
142142
}
143143

144-
if (dev->ethtool->hds_config != ETHTOOL_TCP_DATA_SPLIT_ENABLED) {
144+
if (dev->cfg->hds_config != ETHTOOL_TCP_DATA_SPLIT_ENABLED) {
145145
NL_SET_ERR_MSG(extack, "tcp-data-split is disabled");
146146
return -EINVAL;
147147
}
148148

149-
if (dev->ethtool->hds_thresh) {
149+
if (dev->cfg->hds_thresh) {
150150
NL_SET_ERR_MSG(extack, "hds-thresh is not zero");
151151
return -EINVAL;
152152
}

net/ethtool/netlink.c

Lines changed: 24 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
// SPDX-License-Identifier: GPL-2.0-only
22

3+
#include <net/netdev_queues.h>
34
#include <net/sock.h>
45
#include <linux/ethtool_netlink.h>
56
#include <linux/phy_link_topology.h>
@@ -667,6 +668,7 @@ static int ethnl_default_set_doit(struct sk_buff *skb, struct genl_info *info)
667668
const struct ethnl_request_ops *ops;
668669
struct ethnl_req_info req_info = {};
669670
const u8 cmd = info->genlhdr->cmd;
671+
struct net_device *dev;
670672
int ret;
671673

672674
ops = ethnl_default_requests[cmd];
@@ -688,20 +690,36 @@ static int ethnl_default_set_doit(struct sk_buff *skb, struct genl_info *info)
688690
goto out_dev;
689691
}
690692

693+
dev = req_info.dev;
694+
691695
rtnl_lock();
692-
ret = ethnl_ops_begin(req_info.dev);
696+
dev->cfg_pending = kmemdup(dev->cfg, sizeof(*dev->cfg),
697+
GFP_KERNEL_ACCOUNT);
698+
if (!dev->cfg_pending) {
699+
ret = -ENOMEM;
700+
goto out_tie_cfg;
701+
}
702+
703+
ret = ethnl_ops_begin(dev);
693704
if (ret < 0)
694-
goto out_rtnl;
705+
goto out_free_cfg;
695706

696707
ret = ops->set(&req_info, info);
697-
if (ret <= 0)
708+
if (ret < 0)
709+
goto out_ops;
710+
711+
swap(dev->cfg, dev->cfg_pending);
712+
if (!ret)
698713
goto out_ops;
699-
ethtool_notify(req_info.dev, ops->set_ntf_cmd, NULL);
714+
ethtool_notify(dev, ops->set_ntf_cmd, NULL);
700715

701716
ret = 0;
702717
out_ops:
703-
ethnl_ops_complete(req_info.dev);
704-
out_rtnl:
718+
ethnl_ops_complete(dev);
719+
out_free_cfg:
720+
kfree(dev->cfg_pending);
721+
out_tie_cfg:
722+
dev->cfg_pending = dev->cfg;
705723
rtnl_unlock();
706724
out_dev:
707725
ethnl_parse_header_dev_put(&req_info);

0 commit comments

Comments
 (0)