patch 'net/iavf: add thread for event callbacks' has been queued to stable release 20.11.7
luca.boccassi at gmail.com
luca.boccassi at gmail.com
Sat Nov 5 18:11:31 CET 2022
Hi,
FYI, your patch has been queued to stable release 20.11.7
Note it hasn't been pushed to http://dpdk.org/browse/dpdk-stable yet.
It will be pushed if I get no objections before 11/07/22. So please
shout if anyone has objections.
Also note that after the patch there's a diff of the upstream commit vs the
patch applied to the branch. This will indicate if there was any rebasing
needed to apply to the stable branch. If there were code changes for rebasing
(ie: not only metadata diffs), please double check that the rebase was
correctly done.
Queued patches are on a temporary branch at:
https://github.com/kevintraynor/dpdk-stable
This queued commit can be viewed at:
https://github.com/kevintraynor/dpdk-stable/commit/6932f663ad5c5d163678aaf98c92cac4af077111
Thanks.
Luca Boccassi
---
>From 6932f663ad5c5d163678aaf98c92cac4af077111 Mon Sep 17 00:00:00 2001
From: Yiding Zhou <yidingx.zhou at intel.com>
Date: Thu, 20 Oct 2022 13:00:22 +0800
Subject: [PATCH] net/iavf: add thread for event callbacks
[ upstream commit cb5c1b91f76f436724cd09f26c7432b2775b519c ]
All callbacks registered for ethdev events are called in
eal-intr-thread, and some of them execute virtchnl commands.
Because interrupts are disabled in the intr thread, no response
will be received for these commands. So all callbacks should
be called in a new context.
When the device is bonded, the bond pmd registers a callback for
the LSC event to execute virtchnl commands to reinitialize the
device, and it would also raise the above issue.
This commit adds a new thread to call all event callbacks.
Fixes: 48de41ca11f0 ("net/avf: enable link status update")
Fixes: 84108425054a ("net/iavf: support asynchronous virtual channel message")
Signed-off-by: Yiding Zhou <yidingx.zhou at intel.com>
Acked-by: Qi Zhang <qi.z.zhang at intel.com>
---
drivers/net/iavf/iavf.h | 2 +
drivers/net/iavf/iavf_ethdev.c | 5 ++
drivers/net/iavf/iavf_vchnl.c | 147 ++++++++++++++++++++++++++++++++-
3 files changed, 151 insertions(+), 3 deletions(-)
diff --git a/drivers/net/iavf/iavf.h b/drivers/net/iavf/iavf.h
index bc49f1fa17..41d9856358 100644
--- a/drivers/net/iavf/iavf.h
+++ b/drivers/net/iavf/iavf.h
@@ -287,6 +287,8 @@ _atomic_set_cmd(struct iavf_info *vf, enum virtchnl_ops ops)
int iavf_check_api_version(struct iavf_adapter *adapter);
int iavf_get_vf_resource(struct iavf_adapter *adapter);
+void iavf_dev_event_handler_fini(void);
+int iavf_dev_event_handler_init(void);
void iavf_handle_virtchnl_msg(struct rte_eth_dev *dev);
int iavf_enable_vlan_strip(struct iavf_adapter *adapter);
int iavf_disable_vlan_strip(struct iavf_adapter *adapter);
diff --git a/drivers/net/iavf/iavf_ethdev.c b/drivers/net/iavf/iavf_ethdev.c
index 060b3e3707..9387f17c81 100644
--- a/drivers/net/iavf/iavf_ethdev.c
+++ b/drivers/net/iavf/iavf_ethdev.c
@@ -2034,6 +2034,9 @@ iavf_dev_init(struct rte_eth_dev *eth_dev)
rte_ether_addr_copy((struct rte_ether_addr *)hw->mac.addr,
ð_dev->data->mac_addrs[0]);
+ if (iavf_dev_event_handler_init())
+ return 0;
+
/* register callback func to eal lib */
rte_intr_callback_register(&pci_dev->intr_handle,
iavf_dev_interrupt_handler,
@@ -2121,6 +2124,8 @@ iavf_dev_uninit(struct rte_eth_dev *dev)
iavf_dev_close(dev);
+ iavf_dev_event_handler_fini();
+
return 0;
}
diff --git a/drivers/net/iavf/iavf_vchnl.c b/drivers/net/iavf/iavf_vchnl.c
index f6da2cf4bd..77f10a90c7 100644
--- a/drivers/net/iavf/iavf_vchnl.c
+++ b/drivers/net/iavf/iavf_vchnl.c
@@ -2,6 +2,7 @@
* Copyright(c) 2017 Intel Corporation
*/
+#include <fcntl.h>
#include <stdio.h>
#include <errno.h>
#include <stdint.h>
@@ -26,6 +27,146 @@
#define MAX_TRY_TIMES 200
#define ASQ_DELAY_MS 10
+#define MAX_EVENT_PENDING 16
+
+struct iavf_event_element {
+ TAILQ_ENTRY(iavf_event_element) next;
+ struct rte_eth_dev *dev;
+ enum rte_eth_event_type event;
+ void *param;
+ size_t param_alloc_size;
+ uint8_t param_alloc_data[0];
+};
+
+struct iavf_event_handler {
+ uint32_t ndev;
+ pthread_t tid;
+ int fd[2];
+ pthread_mutex_t lock;
+ TAILQ_HEAD(event_list, iavf_event_element) pending;
+};
+
+static struct iavf_event_handler event_handler = {
+ .fd = {-1, -1},
+};
+
+#ifndef TAILQ_FOREACH_SAFE
+#define TAILQ_FOREACH_SAFE(var, head, field, tvar) \
+ for ((var) = TAILQ_FIRST((head)); \
+ (var) && ((tvar) = TAILQ_NEXT((var), field), 1); \
+ (var) = (tvar))
+#endif
+
+static void *
+iavf_dev_event_handle(void *param __rte_unused)
+{
+ struct iavf_event_handler *handler = &event_handler;
+ TAILQ_HEAD(event_list, iavf_event_element) pending;
+
+ while (true) {
+ char unused[MAX_EVENT_PENDING];
+ ssize_t nr = read(handler->fd[0], &unused, sizeof(unused));
+ if (nr <= 0)
+ break;
+
+ TAILQ_INIT(&pending);
+ pthread_mutex_lock(&handler->lock);
+ TAILQ_CONCAT(&pending, &handler->pending, next);
+ pthread_mutex_unlock(&handler->lock);
+
+ struct iavf_event_element *pos, *save_next;
+ TAILQ_FOREACH_SAFE(pos, &pending, next, save_next) {
+ TAILQ_REMOVE(&pending, pos, next);
+ rte_eth_dev_callback_process(pos->dev, pos->event, pos->param);
+ rte_free(pos);
+ }
+ }
+
+ return NULL;
+}
+
+static void
+iavf_dev_event_post(struct rte_eth_dev *dev,
+ enum rte_eth_event_type event,
+ void *param, size_t param_alloc_size)
+{
+ struct iavf_event_handler *handler = &event_handler;
+ char notify_byte;
+ struct iavf_event_element *elem = rte_malloc(NULL, sizeof(*elem) + param_alloc_size, 0);
+ if (!elem)
+ return;
+
+ elem->dev = dev;
+ elem->event = event;
+ elem->param = param;
+ elem->param_alloc_size = param_alloc_size;
+ if (param && param_alloc_size) {
+ rte_memcpy(elem->param_alloc_data, param, param_alloc_size);
+ elem->param = elem->param_alloc_data;
+ }
+
+ pthread_mutex_lock(&handler->lock);
+ TAILQ_INSERT_TAIL(&handler->pending, elem, next);
+ pthread_mutex_unlock(&handler->lock);
+
+ ssize_t nw = write(handler->fd[1], ¬ify_byte, 1);
+ RTE_SET_USED(nw);
+}
+
+int
+iavf_dev_event_handler_init(void)
+{
+ struct iavf_event_handler *handler = &event_handler;
+
+ if (__atomic_add_fetch(&handler->ndev, 1, __ATOMIC_RELAXED) != 1)
+ return 0;
+#if defined(RTE_EXEC_ENV_IS_WINDOWS) && RTE_EXEC_ENV_IS_WINDOWS != 0
+ int err = _pipe(handler->fd, MAX_EVENT_PENDING, O_BINARY);
+#else
+ int err = pipe(handler->fd);
+#endif
+ if (err != 0) {
+ __atomic_sub_fetch(&handler->ndev, 1, __ATOMIC_RELAXED);
+ return -1;
+ }
+
+ TAILQ_INIT(&handler->pending);
+ pthread_mutex_init(&handler->lock, NULL);
+
+ if (rte_ctrl_thread_create(&handler->tid, "iavf-event-thread",
+ NULL, iavf_dev_event_handle, NULL)) {
+ __atomic_sub_fetch(&handler->ndev, 1, __ATOMIC_RELAXED);
+ return -1;
+ }
+
+ return 0;
+}
+
+void
+iavf_dev_event_handler_fini(void)
+{
+ struct iavf_event_handler *handler = &event_handler;
+
+ if (__atomic_sub_fetch(&handler->ndev, 1, __ATOMIC_RELAXED) != 0)
+ return;
+
+ int unused = pthread_cancel(handler->tid);
+ RTE_SET_USED(unused);
+ close(handler->fd[0]);
+ close(handler->fd[1]);
+ handler->fd[0] = -1;
+ handler->fd[1] = -1;
+
+ pthread_join(handler->tid, NULL);
+ pthread_mutex_destroy(&handler->lock);
+
+ struct iavf_event_element *pos, *save_next;
+ TAILQ_FOREACH_SAFE(pos, &handler->pending, next, save_next) {
+ TAILQ_REMOVE(&handler->pending, pos, next);
+ rte_free(pos);
+ }
+}
+
static uint32_t
iavf_convert_link_speed(enum virtchnl_link_speed virt_link_speed)
{
@@ -262,8 +403,8 @@ iavf_handle_pf_event_msg(struct rte_eth_dev *dev, uint8_t *msg,
case VIRTCHNL_EVENT_RESET_IMPENDING:
PMD_DRV_LOG(DEBUG, "VIRTCHNL_EVENT_RESET_IMPENDING event");
vf->vf_reset = true;
- rte_eth_dev_callback_process(dev, RTE_ETH_EVENT_INTR_RESET,
- NULL);
+ iavf_dev_event_post(dev, RTE_ETH_EVENT_INTR_RESET,
+ NULL, 0);
break;
case VIRTCHNL_EVENT_LINK_CHANGE:
PMD_DRV_LOG(DEBUG, "VIRTCHNL_EVENT_LINK_CHANGE event");
@@ -277,7 +418,7 @@ iavf_handle_pf_event_msg(struct rte_eth_dev *dev, uint8_t *msg,
vf->link_speed = iavf_convert_link_speed(speed);
}
iavf_dev_link_update(dev, 0);
- rte_eth_dev_callback_process(dev, RTE_ETH_EVENT_INTR_LSC, NULL);
+ iavf_dev_event_post(dev, RTE_ETH_EVENT_INTR_LSC, NULL, 0);
break;
case VIRTCHNL_EVENT_PF_DRIVER_CLOSE:
PMD_DRV_LOG(DEBUG, "VIRTCHNL_EVENT_PF_DRIVER_CLOSE event");
--
2.34.1
---
Diff of the applied patch vs upstream commit (please double-check if non-empty:
---
--- - 2022-11-05 17:11:11.499928021 +0000
+++ 0032-net-iavf-add-thread-for-event-callbacks.patch 2022-11-05 17:11:08.750944273 +0000
@@ -1 +1 @@
-From cb5c1b91f76f436724cd09f26c7432b2775b519c Mon Sep 17 00:00:00 2001
+From 6932f663ad5c5d163678aaf98c92cac4af077111 Mon Sep 17 00:00:00 2001
@@ -5,0 +6,2 @@
+[ upstream commit cb5c1b91f76f436724cd09f26c7432b2775b519c ]
+
@@ -20 +21,0 @@
-Cc: stable at dpdk.org
@@ -27,2 +28,2 @@
- drivers/net/iavf/iavf_vchnl.c | 153 +++++++++++++++++++++++++++++++--
- 3 files changed, 154 insertions(+), 6 deletions(-)
+ drivers/net/iavf/iavf_vchnl.c | 147 ++++++++++++++++++++++++++++++++-
+ 3 files changed, 151 insertions(+), 3 deletions(-)
@@ -31 +32 @@
-index 26b858f6f0..1edebab8dc 100644
+index bc49f1fa17..41d9856358 100644
@@ -34,2 +35,2 @@
-@@ -424,6 +424,8 @@ _atomic_set_async_response_cmd(struct iavf_info *vf, enum virtchnl_ops ops)
- }
+@@ -287,6 +287,8 @@ _atomic_set_cmd(struct iavf_info *vf, enum virtchnl_ops ops)
+
@@ -44 +45 @@
-index b1958e0474..8d9f3a6d3d 100644
+index 060b3e3707..9387f17c81 100644
@@ -47 +48 @@
-@@ -2633,6 +2633,9 @@ iavf_dev_init(struct rte_eth_dev *eth_dev)
+@@ -2034,6 +2034,9 @@ iavf_dev_init(struct rte_eth_dev *eth_dev)
@@ -52 +53 @@
-+ goto init_vf_err;
++ return 0;
@@ -54,4 +55,4 @@
- if (vf->vf_res->vf_cap_flags & VIRTCHNL_VF_OFFLOAD_WB_ON_ITR) {
- /* register callback func to eal lib */
- rte_intr_callback_register(pci_dev->intr_handle,
-@@ -2787,6 +2790,8 @@ iavf_dev_uninit(struct rte_eth_dev *dev)
+ /* register callback func to eal lib */
+ rte_intr_callback_register(&pci_dev->intr_handle,
+ iavf_dev_interrupt_handler,
+@@ -2121,6 +2124,8 @@ iavf_dev_uninit(struct rte_eth_dev *dev)
@@ -67 +68 @@
-index 729400cb91..654bc7edb6 100644
+index f6da2cf4bd..77f10a90c7 100644
@@ -78,11 +79,3 @@
-@@ -11,6 +12,7 @@
- #include <inttypes.h>
- #include <rte_byteorder.h>
- #include <rte_common.h>
-+#include <rte_os_shim.h>
-
- #include <rte_debug.h>
- #include <rte_alarm.h>
-@@ -27,6 +29,146 @@
- #define MAX_TRY_TIMES 2000
- #define ASQ_DELAY_MS 1
+@@ -26,6 +27,146 @@
+ #define MAX_TRY_TIMES 200
+ #define ASQ_DELAY_MS 10
@@ -233 +226 @@
-@@ -278,8 +420,8 @@ iavf_handle_pf_event_msg(struct rte_eth_dev *dev, uint8_t *msg,
+@@ -262,8 +403,8 @@ iavf_handle_pf_event_msg(struct rte_eth_dev *dev, uint8_t *msg,
@@ -244 +237 @@
-@@ -293,7 +435,7 @@ iavf_handle_pf_event_msg(struct rte_eth_dev *dev, uint8_t *msg,
+@@ -277,7 +418,7 @@ iavf_handle_pf_event_msg(struct rte_eth_dev *dev, uint8_t *msg,
@@ -253,12 +245,0 @@
-@@ -359,9 +501,8 @@ iavf_handle_virtchnl_msg(struct rte_eth_dev *dev)
- desc.subtype =
- RTE_ETH_EVENT_IPSEC_UNKNOWN;
- desc.metadata = ev->ipsec_event_data;
-- rte_eth_dev_callback_process(dev,
-- RTE_ETH_EVENT_IPSEC,
-- &desc);
-+ iavf_dev_event_post(dev, RTE_ETH_EVENT_IPSEC,
-+ &desc, sizeof(desc));
- return;
- }
-
More information about the stable
mailing list