[PATCH net-next v2 14/15] gve: add ctrl ops to for queue operations
From: Harshitha Ramamurthy
Date: Tue Jun 02 2026 - 20:07:36 EST
Add the next few control ops to
- create queues
- destroy queues
These changes are just moving existing code into ops, no functional
change.
Reviewed-by: Willem de Bruijn <willemb@xxxxxxxxxx>
Reviewed-by: Jordan Rhee <jordanrhee@xxxxxxxxxx>
Signed-off-by: Harshitha Ramamurthy <hramamurthy@xxxxxxxxxx>
---
Changes in v2:
- Fixed typo in commit message (exisiting -> existing)
drivers/net/ethernet/google/gve/gve.h | 4 ++
drivers/net/ethernet/google/gve/gve_adminq.c | 50 ++++++++++++++++++++
drivers/net/ethernet/google/gve/gve_adminq.h | 3 +-
drivers/net/ethernet/google/gve/gve_main.c | 41 ++++------------
4 files changed, 65 insertions(+), 33 deletions(-)
diff --git a/drivers/net/ethernet/google/gve/gve.h b/drivers/net/ethernet/google/gve/gve.h
index b2e578b3d450..4283cb9b49de 100644
--- a/drivers/net/ethernet/google/gve/gve.h
+++ b/drivers/net/ethernet/google/gve/gve.h
@@ -841,6 +841,8 @@ struct gve_device_info {
* @configure_rss: Set up default RSS configuration
* @setup_stats_report: Set up DMA region for stats report (AdminQ only)
* @reset_flow_rules: Flush all flow rules from device
+ * @create_queues: Sends commands to the device to create TX/RX queues.
+ * @destroy_queues: Sends commands to the device to destroy TX/RX queues.
*/
struct gve_ctrl_ops {
int (*map_db_bar)(struct gve_priv *priv);
@@ -859,6 +861,8 @@ struct gve_ctrl_ops {
dma_addr_t stats_report_addr,
u64 interval_ms); /* AQ-specific */
int (*reset_flow_rules)(struct gve_priv *priv);
+ int (*create_queues)(struct gve_priv *priv);
+ int (*destroy_queues)(struct gve_priv *priv);
};
struct gve_priv {
diff --git a/drivers/net/ethernet/google/gve/gve_adminq.c b/drivers/net/ethernet/google/gve/gve_adminq.c
index 5dc5c63cee32..799381d24c71 100644
--- a/drivers/net/ethernet/google/gve/gve_adminq.c
+++ b/drivers/net/ethernet/google/gve/gve_adminq.c
@@ -941,6 +941,30 @@ static void gve_set_default_rss_sizes(struct gve_priv *priv)
}
}
+int gve_adminq_destroy_queues(struct gve_priv *priv)
+{
+ int num_tx_queues = gve_num_tx_queues(priv);
+ int err;
+
+ err = gve_adminq_destroy_tx_queues(priv, 0, num_tx_queues);
+ if (err) {
+ netif_err(priv, drv, priv->dev,
+ "failed to destroy tx queues\n");
+ /* This failure will trigger a reset - no need to clean up */
+ return err;
+ }
+ netif_dbg(priv, drv, priv->dev, "destroyed tx queues\n");
+ err = gve_adminq_destroy_rx_queues(priv, priv->rx_cfg.num_queues);
+ if (err) {
+ netif_err(priv, drv, priv->dev,
+ "failed to destroy rx queues\n");
+ /* This failure will trigger a reset - no need to clean up */
+ return err;
+ }
+ netif_dbg(priv, drv, priv->dev, "destroyed rx queues\n");
+ return err;
+}
+
static void gve_enable_supported_features(struct gve_priv *priv,
u32 supported_features_mask,
const struct gve_device_option_jumbo_frames
@@ -1822,3 +1846,29 @@ void gve_adminq_teardown_mgmt_irq(struct gve_priv *priv)
priv->mgmt_irq_requested = false;
}
}
+
+int gve_adminq_create_queues(struct gve_priv *priv)
+{
+ int num_tx_queues = gve_num_tx_queues(priv);
+ int err;
+
+ err = gve_adminq_create_tx_queues(priv, 0, num_tx_queues);
+ if (err) {
+ netif_err(priv, drv, priv->dev, "failed to create %d tx queues\n",
+ num_tx_queues);
+ return err;
+ }
+ netif_dbg(priv, drv, priv->dev, "created %d tx queues\n",
+ num_tx_queues);
+
+ err = gve_adminq_create_rx_queues(priv, priv->rx_cfg.num_queues);
+ if (err) {
+ netif_err(priv, drv, priv->dev, "failed to create %d rx queues\n",
+ priv->rx_cfg.num_queues);
+ return err;
+ }
+ netif_dbg(priv, drv, priv->dev, "created %d rx queues\n",
+ priv->rx_cfg.num_queues);
+
+ return err;
+}
diff --git a/drivers/net/ethernet/google/gve/gve_adminq.h b/drivers/net/ethernet/google/gve/gve_adminq.h
index ff656fb4f113..03e8318f7327 100644
--- a/drivers/net/ethernet/google/gve/gve_adminq.h
+++ b/drivers/net/ethernet/google/gve/gve_adminq.h
@@ -628,6 +628,8 @@ int gve_adminq_configure_device_resources(struct gve_priv *priv,
dma_addr_t db_array_bus_addr,
u32 num_ntfy_blks);
int gve_adminq_deconfigure_device_resources(struct gve_priv *priv);
+int gve_adminq_create_queues(struct gve_priv *priv);
+int gve_adminq_destroy_queues(struct gve_priv *priv);
int gve_adminq_create_tx_queues(struct gve_priv *priv, u32 start_id, u32 num_queues);
int gve_adminq_destroy_tx_queues(struct gve_priv *priv, u32 start_id, u32 num_queues);
int gve_adminq_create_single_rx_queue(struct gve_priv *priv, u32 queue_index);
@@ -661,5 +663,4 @@ int gve_adminq_request_db_info(struct gve_priv *priv);
void gve_adminq_free_db_resources(struct gve_priv *priv);
int gve_adminq_setup_mgmt_irq(struct gve_priv *priv);
void gve_adminq_teardown_mgmt_irq(struct gve_priv *priv);
-
#endif /* _GVE_ADMINQ_H */
diff --git a/drivers/net/ethernet/google/gve/gve_main.c b/drivers/net/ethernet/google/gve/gve_main.c
index 9d00093826e3..dfc734d8bec9 100644
--- a/drivers/net/ethernet/google/gve/gve_main.c
+++ b/drivers/net/ethernet/google/gve/gve_main.c
@@ -841,33 +841,18 @@ static int gve_unregister_qpls(struct gve_priv *priv)
static int gve_create_rings(struct gve_priv *priv)
{
- int num_tx_queues = gve_num_tx_queues(priv);
int err;
int i;
- err = gve_adminq_create_tx_queues(priv, 0, num_tx_queues);
+ err = priv->ctrl_ops->create_queues(priv);
if (err) {
- netif_err(priv, drv, priv->dev, "failed to create %d tx queues\n",
- num_tx_queues);
- /* This failure will trigger a reset - no need to clean
- * up
- */
- return err;
- }
- netif_dbg(priv, drv, priv->dev, "created %d tx queues\n",
- num_tx_queues);
-
- err = gve_adminq_create_rx_queues(priv, priv->rx_cfg.num_queues);
- if (err) {
- netif_err(priv, drv, priv->dev, "failed to create %d rx queues\n",
- priv->rx_cfg.num_queues);
+ netif_err(priv, drv, priv->dev,
+ "failed to create queues\n");
/* This failure will trigger a reset - no need to clean
* up
*/
return err;
}
- netif_dbg(priv, drv, priv->dev, "created %d rx queues\n",
- priv->rx_cfg.num_queues);
if (gve_is_gqi(priv)) {
/* Rx data ring has been prefilled with packet buffers at queue
@@ -1022,26 +1007,16 @@ static int gve_queues_mem_alloc(struct gve_priv *priv,
static int gve_destroy_rings(struct gve_priv *priv)
{
- int num_tx_queues = gve_num_tx_queues(priv);
int err;
- err = gve_adminq_destroy_tx_queues(priv, 0, num_tx_queues);
+ err = priv->ctrl_ops->destroy_queues(priv);
+
if (err) {
- netif_err(priv, drv, priv->dev,
- "failed to destroy tx queues\n");
/* This failure will trigger a reset - no need to clean up */
- return err;
- }
- netif_dbg(priv, drv, priv->dev, "destroyed tx queues\n");
- err = gve_adminq_destroy_rx_queues(priv, priv->rx_cfg.num_queues);
- if (err) {
netif_err(priv, drv, priv->dev,
- "failed to destroy rx queues\n");
- /* This failure will trigger a reset - no need to clean up */
- return err;
+ "failed to destroy queues\n");
}
- netif_dbg(priv, drv, priv->dev, "destroyed rx queues\n");
- return 0;
+ return err;
}
static void gve_queues_mem_free(struct gve_priv *priv,
@@ -2450,6 +2425,8 @@ static const struct gve_ctrl_ops gve_adminq_ops = {
.free_db_resources = gve_adminq_free_db_resources,
.setup_mgmt_irq = gve_adminq_setup_mgmt_irq,
.teardown_mgmt_irq = gve_adminq_teardown_mgmt_irq,
+ .create_queues = gve_adminq_create_queues,
+ .destroy_queues = gve_adminq_destroy_queues,
};
static int gve_init_priv(struct gve_priv *priv)
--
2.54.0.1013.g208068f2d8-goog