Currently n-handler-threads is ignored when using per-cpu mode. There
are some small situations where manually setting the number of handlers
is necessary. For this reason allow manually setting the number of
handlers via n-handler-threads

Reported-at: https://bugzilla.redhat.com/show_bug.cgi?id=2106570
Signed-off-by: Michael Santana <[email protected]>
---
 lib/dpif-netlink.c            | 20 +++++++++++---------
 lib/dpif-provider.h           |  2 +-
 lib/dpif.c                    |  4 ++--
 lib/dpif.h                    |  2 +-
 ofproto/ofproto-dpif-upcall.c |  3 +++
 ofproto/ofproto-dpif.c        |  5 +++--
 6 files changed, 21 insertions(+), 15 deletions(-)

diff --git a/lib/dpif-netlink.c b/lib/dpif-netlink.c
index a620a6ec5..641c9ff99 100644
--- a/lib/dpif-netlink.c
+++ b/lib/dpif-netlink.c
@@ -264,7 +264,8 @@ static void dpif_netlink_handler_uninit(struct dpif_handler 
*handler);
 static int dpif_netlink_refresh_handlers_vport_dispatch(struct dpif_netlink *,
                                                         uint32_t n_handlers);
 static void destroy_all_channels(struct dpif_netlink *);
-static int dpif_netlink_refresh_handlers_cpu_dispatch(struct dpif_netlink *);
+static int dpif_netlink_refresh_handlers_cpu_dispatch(struct dpif_netlink *,
+                                                      uint32_t n_handlers);
 static void destroy_all_handlers(struct dpif_netlink *);
 
 static void dpif_netlink_vport_to_ofpbuf(const struct dpif_netlink_vport *,
@@ -2586,15 +2587,14 @@ dpif_netlink_calculate_n_handlers(void)
 }
 
 static int
-dpif_netlink_refresh_handlers_cpu_dispatch(struct dpif_netlink *dpif)
+dpif_netlink_refresh_handlers_cpu_dispatch(struct dpif_netlink *dpif,
+                                           uint32_t n_handlers)
     OVS_REQ_WRLOCK(dpif->upcall_lock)
 {
     int handler_id;
     int error = 0;
-    uint32_t n_handlers;
     uint32_t *upcall_pids;
 
-    n_handlers = dpif_netlink_calculate_n_handlers();
     if (dpif->n_handlers != n_handlers) {
         VLOG_DBG("Dispatch mode(per-cpu): initializing %d handlers",
                    n_handlers);
@@ -2770,7 +2770,8 @@ dpif_netlink_recv_set_vport_dispatch(struct dpif_netlink 
*dpif, bool enable)
 }
 
 static int
-dpif_netlink_recv_set_cpu_dispatch(struct dpif_netlink *dpif, bool enable)
+dpif_netlink_recv_set_cpu_dispatch(struct dpif_netlink *dpif, bool enable,
+                                   uint32_t handler)
     OVS_REQ_WRLOCK(dpif->upcall_lock)
 {
     if ((dpif->handlers != NULL) == enable) {
@@ -2779,19 +2780,19 @@ dpif_netlink_recv_set_cpu_dispatch(struct dpif_netlink 
*dpif, bool enable)
         destroy_all_handlers(dpif);
         return 0;
     } else {
-        return dpif_netlink_refresh_handlers_cpu_dispatch(dpif);
+        return dpif_netlink_refresh_handlers_cpu_dispatch(dpif, handler);
     }
 }
 
 static int
-dpif_netlink_recv_set(struct dpif *dpif_, bool enable)
+dpif_netlink_recv_set(struct dpif *dpif_, bool enable, uint32_t handlers)
 {
     struct dpif_netlink *dpif = dpif_netlink_cast(dpif_);
     int error;
 
     fat_rwlock_wrlock(&dpif->upcall_lock);
     if (dpif_netlink_upcall_per_cpu(dpif)) {
-        error = dpif_netlink_recv_set_cpu_dispatch(dpif, enable);
+        error = dpif_netlink_recv_set_cpu_dispatch(dpif, enable, handlers);
     } else {
         error = dpif_netlink_recv_set_vport_dispatch(dpif, enable);
     }
@@ -2817,7 +2818,8 @@ dpif_netlink_handlers_set(struct dpif *dpif_, uint32_t 
n_handlers)
     fat_rwlock_wrlock(&dpif->upcall_lock);
     if (dpif->handlers) {
         if (dpif_netlink_upcall_per_cpu(dpif)) {
-            error = dpif_netlink_refresh_handlers_cpu_dispatch(dpif);
+            error = dpif_netlink_refresh_handlers_cpu_dispatch(dpif,
+                                                               n_handlers);
         } else {
             error = dpif_netlink_refresh_handlers_vport_dispatch(dpif,
                                                                  n_handlers);
diff --git a/lib/dpif-provider.h b/lib/dpif-provider.h
index 12477a24f..91be767a8 100644
--- a/lib/dpif-provider.h
+++ b/lib/dpif-provider.h
@@ -342,7 +342,7 @@ struct dpif_class {
      * Turning packet receive off and then back on is allowed to change Netlink
      * PID assignments (see ->port_get_pid()).  The client is responsible for
      * updating flows as necessary if it does this. */
-    int (*recv_set)(struct dpif *dpif, bool enable);
+    int (*recv_set)(struct dpif *dpif, bool enable, uint32_t n_handlers);
 
     /* Attempts to refresh the poll loops and Netlink sockets used for handling
      * upcalls when the number of upcall handlers (upcall receiving thread) is
diff --git a/lib/dpif.c b/lib/dpif.c
index 40f5fe446..6fc553ad4 100644
--- a/lib/dpif.c
+++ b/lib/dpif.c
@@ -1459,12 +1459,12 @@ dpif_upcall_type_to_string(enum dpif_upcall_type type)
  * must update all of the flows that have OVS_ACTION_ATTR_USERSPACE actions
  * using the new PID assignment. */
 int
-dpif_recv_set(struct dpif *dpif, bool enable)
+dpif_recv_set(struct dpif *dpif, bool enable, uint32_t n_handlers)
 {
     int error = 0;
 
     if (dpif->dpif_class->recv_set) {
-        error = dpif->dpif_class->recv_set(dpif, enable);
+        error = dpif->dpif_class->recv_set(dpif, enable, n_handlers);
         log_operation(dpif, "recv_set", error);
     }
     return error;
diff --git a/lib/dpif.h b/lib/dpif.h
index 6cb4dae6d..96dc88237 100644
--- a/lib/dpif.h
+++ b/lib/dpif.h
@@ -882,7 +882,7 @@ typedef int upcall_callback(const struct dp_packet *packet,
 
 void dpif_register_upcall_cb(struct dpif *, upcall_callback *, void *aux);
 
-int dpif_recv_set(struct dpif *, bool enable);
+int dpif_recv_set(struct dpif *, bool enable, uint32_t n_handlers);
 int dpif_handlers_set(struct dpif *, uint32_t n_handlers);
 bool dpif_number_handlers_required(struct dpif *, uint32_t *n_handlers);
 int dpif_set_config(struct dpif *, const struct smap *cfg);
diff --git a/ofproto/ofproto-dpif-upcall.c b/ofproto/ofproto-dpif-upcall.c
index 7ad728adf..734eaac5c 100644
--- a/ofproto/ofproto-dpif-upcall.c
+++ b/ofproto/ofproto-dpif-upcall.c
@@ -655,6 +655,9 @@ udpif_set_threads(struct udpif *udpif, uint32_t n_handlers_,
         } else {
             n_revalidators_requested = n_revalidators_;
         }
+        if (n_handlers_) {
+            n_handlers_requested = n_handlers_;
+        }
     } else {
         int threads = MAX(count_cpu_cores(), 2);
 
diff --git a/ofproto/ofproto-dpif.c b/ofproto/ofproto-dpif.c
index f9562dee8..cdbd25000 100644
--- a/ofproto/ofproto-dpif.c
+++ b/ofproto/ofproto-dpif.c
@@ -377,7 +377,8 @@ type_run(const char *type)
 
         backer->recv_set_enable = true;
 
-        error = dpif_recv_set(backer->dpif, backer->recv_set_enable);
+        error = dpif_recv_set(backer->dpif, backer->recv_set_enable,
+                              n_handlers);
         if (error) {
             VLOG_ERR("Failed to enable receiving packets in dpif.");
             return error;
@@ -816,7 +817,7 @@ open_dpif_backer(const char *type, struct dpif_backer 
**backerp)
     check_support(backer);
     atomic_count_init(&backer->tnl_count, 0);
 
-    error = dpif_recv_set(backer->dpif, backer->recv_set_enable);
+    error = dpif_recv_set(backer->dpif, backer->recv_set_enable, n_handlers);
     if (error) {
         VLOG_ERR("failed to listen on datapath of type %s: %s",
                  type, ovs_strerror(error));
-- 
2.33.1

_______________________________________________
dev mailing list
[email protected]
https://mail.openvswitch.org/mailman/listinfo/ovs-dev

Reply via email to