Thread (4 messages) flat view 4 messages, 3 authors, 21h ago

Re: [PATCH net-next] net: libwx: Add ethtool -L support for VF drivers

From: Harshitha Ramamurthy <hramamurthy@google.com>
Date: 2026-09-15 19:19:30

On Tue, Sep 15, 2026 at 3:18 AM Mengyuan Lou [off-list ref] wrote:
quoted hunk ↗ jump to hunk
Implement get_channels and set_channels ethtool operations for Wangxun
VF net_device instances in libwx.

This allows users to query and dynamically reconfigure the number of RX/TX
channels on VF interfaces via `ethtool -l/ -L`.

Specifically:
- Add wx_get_channels_vf() and wx_set_channels_vf() to report and update
  channel limits and combined queue counts.
- Re-evaluate RSS limits in txgbevf_set_num_queues() based on user settings
  stored in wx->ring_feature[RING_F_RSS].limit.
- Adjust VF MRQC RSS hash mask logic in wx_setup_vfmrqc_vf() to correctly
  match queue configuration thresholds.

Signed-off-by: Mengyuan Lou <mengyuanlou@net-swift.com>
---
 .../net/ethernet/wangxun/libwx/wx_ethtool.c   | 64 +++++++++++++++++++
 .../net/ethernet/wangxun/libwx/wx_vf_lib.c    |  2 +-
 .../ethernet/wangxun/txgbevf/txgbevf_main.c   |  3 +
 3 files changed, 68 insertions(+), 1 deletion(-)
diff --git a/drivers/net/ethernet/wangxun/libwx/wx_ethtool.c b/drivers/net/ethernet/wangxun/libwx/wx_ethtool.c
index 940d2e59876c..d24370790941 100644
--- a/drivers/net/ethernet/wangxun/libwx/wx_ethtool.c
+++ b/drivers/net/ethernet/wangxun/libwx/wx_ethtool.c
@@ -564,6 +564,68 @@ int wx_set_channels(struct net_device *dev,
 }
 EXPORT_SYMBOL(wx_set_channels);

+static void wx_get_channels_vf(struct net_device *dev,
+                              struct ethtool_channels *ch)
+{
+       struct wx *wx = netdev_priv(dev);
+
+       /* report maximum channels */
+       ch->max_combined = wx->mac.max_rx_queues;
+
+       ch->max_other = 1;
+       ch->other_count = 1;
+
+       /* record current channels */
+       ch->combined_count = wx->num_rx_queues;
+}
+
+static int wx_set_channels_vf(struct net_device *dev,
+                             struct ethtool_channels *ch)
+{
+       struct wx *wx = netdev_priv(dev);
+       u16 rss_limit;
+       int ret;
+
+       rss_limit = wx->ring_feature[RING_F_RSS].limit;
+
+       /* verify other_count has not changed */
+       if (ch->other_count != 1)
+               return -EINVAL;
+
+       /* verify the number of channels does not exceed hardware limits */
+       if (ch->combined_count > wx->mac.max_rx_queues)
+               return -EINVAL;
+
+       /* if device is resetting, do nothing */
+       if (test_bit(WX_STATE_RESETTING, wx->state))
+               return -EBUSY;
+
+       wx->ring_feature[RING_F_RSS].limit = ch->combined_count;
+
+       if (netif_running(dev))
+               wxvf_close(dev);
The precedent has been for some time now that drivers are required to
pre-allocate resources for the new queue counts before tearing down
the existing ones. So that the driver doesn't knock itself out if
something fails when attempting to apply the new configuration.

Look at the nfp_net_ring_config() or gve_adjust_config() for examples:
both try to allocate memory for the new config first.
quoted hunk ↗ jump to hunk
+
+       wx_clear_interrupt_scheme(wx);
+
+       ret = wx_init_interrupt_scheme(wx);
+       if (ret)
+               goto err_out;
+
+       if (netif_running(dev)) {
+               ret = wxvf_open(dev);
+               if (ret)
+                       goto err_close;
+       }
+
+       return 0;
+
+err_close:
+       wx_clear_interrupt_scheme(wx);
+err_out:
+       wx->ring_feature[RING_F_RSS].limit = rss_limit;
+       return ret;
+}
+
 u32 wx_rss_indir_size(struct net_device *netdev)
 {
        struct wx *wx = netdev_priv(netdev);
@@ -852,6 +914,8 @@ static const struct ethtool_ops wx_ethtool_ops_vf = {
        .set_coalesce           = wx_set_coalesce,
        .get_ts_info            = ethtool_op_get_ts_info,
        .get_link_ksettings     = wx_get_link_ksettings_vf,
+       .get_channels           = wx_get_channels_vf,
+       .set_channels           = wx_set_channels_vf,
 };

 void wx_set_ethtool_ops_vf(struct net_device *netdev)
diff --git a/drivers/net/ethernet/wangxun/libwx/wx_vf_lib.c b/drivers/net/ethernet/wangxun/libwx/wx_vf_lib.c
index 7325b475ee10..6fec3ab5e4e4 100644
--- a/drivers/net/ethernet/wangxun/libwx/wx_vf_lib.c
+++ b/drivers/net/ethernet/wangxun/libwx/wx_vf_lib.c
@@ -237,7 +237,7 @@ void wx_setup_vfmrqc_vf(struct wx *wx)

        vfmrqc |= WX_VXMRQC_RSS_EN;

-       if (wx->num_rx_queues > 3)
+       if (wx->num_rx_queues >= 3)
                vfmrqc |= WX_VXMRQC_RSS_HASH(2);
        else if (wx->num_rx_queues > 1)
                vfmrqc |= WX_VXMRQC_RSS_HASH(1);
diff --git a/drivers/net/ethernet/wangxun/txgbevf/txgbevf_main.c b/drivers/net/ethernet/wangxun/txgbevf/txgbevf_main.c
index 8b16b900820a..6e8659082051 100644
--- a/drivers/net/ethernet/wangxun/txgbevf/txgbevf_main.c
+++ b/drivers/net/ethernet/wangxun/txgbevf/txgbevf_main.c
@@ -72,6 +72,9 @@ static void txgbevf_set_num_queues(struct wx *wx)
                queue = min_t(u16, wx->mac.max_rx_queues, wx->mac.max_tx_queues);
                rss = min_t(u16, queue, rss);

+               if (wx->ring_feature[RING_F_RSS].limit)
+                       rss = min_t(u16, rss, wx->ring_feature[RING_F_RSS].limit);
+
                if (wx->vfinfo->vf_api >= wx_mbox_api_13) {
                        wx->num_rx_queues = rss;
                        wx->num_tx_queues = rss;
--
2.30.1

Keyboard shortcuts
hback out one level
jnext message in thread
kprevious message in thread
ldrill in
Escclose help / fold thread tree
?toggle this help