[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[PATCH 3/5] virtio-net: add RSS support for Vhost backends
From: |
Maxime Coquelin |
Subject: |
[PATCH 3/5] virtio-net: add RSS support for Vhost backends |
Date: |
Fri, 8 Apr 2022 14:28:11 +0200 |
This patch introduces new Vhost backend callbacks to
support RSS, and makes them called in Virtio-net
device.
It will be used by Vhost-user backend implementation to
support RSS feature.
Signed-off-by: Maxime Coquelin <maxime.coquelin@redhat.com>
---
hw/net/vhost_net-stub.c | 10 ++++++
hw/net/vhost_net.c | 22 +++++++++++++
hw/net/virtio-net.c | 53 +++++++++++++++++++++----------
include/hw/virtio/vhost-backend.h | 7 ++++
include/net/vhost_net.h | 4 +++
5 files changed, 79 insertions(+), 17 deletions(-)
diff --git a/hw/net/vhost_net-stub.c b/hw/net/vhost_net-stub.c
index 89d71cfb8e..cc05e07c1f 100644
--- a/hw/net/vhost_net-stub.c
+++ b/hw/net/vhost_net-stub.c
@@ -101,3 +101,13 @@ int vhost_net_set_mtu(struct vhost_net *net, uint16_t mtu)
{
return 0;
}
+
+int vhost_net_get_rss(struct vhost_net *net, VirtioNetRssCapa *rss_capa)
+{
+ return 0;
+}
+
+int vhost_net_set_rss(struct vhost_net *net, VirtioNetRssData *rss_data)
+{
+ return 0;
+}
diff --git a/hw/net/vhost_net.c b/hw/net/vhost_net.c
index 30379d2ca4..aa2a1e8e5f 100644
--- a/hw/net/vhost_net.c
+++ b/hw/net/vhost_net.c
@@ -512,3 +512,25 @@ int vhost_net_set_mtu(struct vhost_net *net, uint16_t mtu)
return vhost_ops->vhost_net_set_mtu(&net->dev, mtu);
}
+
+int vhost_net_get_rss(struct vhost_net *net, VirtioNetRssCapa *rss_capa)
+{
+ const VhostOps *vhost_ops = net->dev.vhost_ops;
+
+ if (!vhost_ops->vhost_net_get_rss) {
+ return 0;
+ }
+
+ return vhost_ops->vhost_net_get_rss(&net->dev, rss_capa);
+}
+
+int vhost_net_set_rss(struct vhost_net *net, VirtioNetRssData *rss_data)
+{
+ const VhostOps *vhost_ops = net->dev.vhost_ops;
+
+ if (!vhost_ops->vhost_net_set_rss) {
+ return 0;
+ }
+
+ return vhost_ops->vhost_net_set_rss(&net->dev, rss_data);
+}
diff --git a/hw/net/virtio-net.c b/hw/net/virtio-net.c
index 38436e472b..237bbdb1b3 100644
--- a/hw/net/virtio-net.c
+++ b/hw/net/virtio-net.c
@@ -741,8 +741,10 @@ static uint64_t virtio_net_get_features(VirtIODevice
*vdev, uint64_t features,
return features;
}
- if (!ebpf_rss_is_loaded(&n->ebpf_rss)) {
- virtio_clear_feature(&features, VIRTIO_NET_F_RSS);
+ if (nc->peer->info->type == NET_CLIENT_DRIVER_TAP) {
+ if (!ebpf_rss_is_loaded(&n->ebpf_rss)) {
+ virtio_clear_feature(&features, VIRTIO_NET_F_RSS);
+ }
}
features = vhost_net_get_features(get_vhost_net(nc->peer), features);
vdev->backend_features = features;
@@ -1161,11 +1163,17 @@ static void virtio_net_detach_epbf_rss(VirtIONet *n);
static void virtio_net_disable_rss(VirtIONet *n)
{
+ NetClientState *nc = qemu_get_queue(n->nic);
+
if (n->rss_data.enabled) {
trace_virtio_net_rss_disable();
}
n->rss_data.enabled = false;
+ if (nc->peer && nc->peer->info->type == NET_CLIENT_DRIVER_VHOST_USER) {
+ vhost_net_set_rss(get_vhost_net(nc->peer), &n->rss_data);
+ }
+
virtio_net_detach_epbf_rss(n);
}
@@ -1239,6 +1247,7 @@ static uint16_t virtio_net_handle_rss(VirtIONet *n,
bool do_rss)
{
VirtIODevice *vdev = VIRTIO_DEVICE(n);
+ NetClientState *nc = qemu_get_queue(n->nic);
struct virtio_net_rss_config cfg;
size_t s, offset = 0, size_get;
uint16_t queue_pairs, i;
@@ -1354,22 +1363,29 @@ static uint16_t virtio_net_handle_rss(VirtIONet *n,
}
n->rss_data.enabled = true;
- if (!n->rss_data.populate_hash) {
- if (!virtio_net_attach_epbf_rss(n)) {
- /* EBPF must be loaded for vhost */
- if (get_vhost_net(qemu_get_queue(n->nic)->peer)) {
- warn_report("Can't load eBPF RSS for vhost");
- goto error;
+ if (nc->peer && nc->peer->info->type == NET_CLIENT_DRIVER_VHOST_USER) {
+ if (vhost_net_set_rss(get_vhost_net(nc->peer), &n->rss_data)) {
+ warn_report("Failed to configure RSS for vhost-user");
+ goto error;
+ }
+ } else {
+ if (!n->rss_data.populate_hash) {
+ if (!virtio_net_attach_epbf_rss(n)) {
+ /* EBPF must be loaded for vhost */
+ if (get_vhost_net(nc->peer)) {
+ warn_report("Can't load eBPF RSS for vhost");
+ goto error;
+ }
+ /* fallback to software RSS */
+ warn_report("Can't load eBPF RSS - fallback to software RSS");
+ n->rss_data.enabled_software_rss = true;
}
- /* fallback to software RSS */
- warn_report("Can't load eBPF RSS - fallback to software RSS");
+ } else {
+ /* use software RSS for hash populating */
+ /* and detach eBPF if was loaded before */
+ virtio_net_detach_epbf_rss(n);
n->rss_data.enabled_software_rss = true;
}
- } else {
- /* use software RSS for hash populating */
- /* and detach eBPF if was loaded before */
- virtio_net_detach_epbf_rss(n);
- n->rss_data.enabled_software_rss = true;
}
trace_virtio_net_rss_enable(n->rss_data.hash_types,
@@ -3534,8 +3550,11 @@ static void virtio_net_device_realize(DeviceState *dev,
Error **errp)
n->rss_capa.max_key_size = VIRTIO_NET_RSS_DEFAULT_KEY_SIZE;
n->rss_capa.max_indirection_len = VIRTIO_NET_RSS_DEFAULT_TABLE_LEN;
n->rss_capa.supported_hashes = VIRTIO_NET_RSS_SUPPORTED_HASHES;
-
- virtio_net_load_ebpf(n);
+ if (nc->peer && nc->peer->info->type == NET_CLIENT_DRIVER_VHOST_USER) {
+ vhost_net_get_rss(get_vhost_net(nc->peer), &n->rss_capa);
+ } else {
+ virtio_net_load_ebpf(n);
+ }
} else {
n->rss_capa.max_indirection_len = 1;
}
diff --git a/include/hw/virtio/vhost-backend.h
b/include/hw/virtio/vhost-backend.h
index 81bf3109f8..0b9e2ea26e 100644
--- a/include/hw/virtio/vhost-backend.h
+++ b/include/hw/virtio/vhost-backend.h
@@ -12,6 +12,7 @@
#define VHOST_BACKEND_H
#include "exec/memory.h"
+#include "hw/virtio/virtio-net.h"
typedef enum VhostBackendType {
VHOST_BACKEND_TYPE_NONE = 0,
@@ -45,6 +46,10 @@ typedef int (*vhost_backend_memslots_limit)(struct vhost_dev
*dev);
typedef int (*vhost_net_set_backend_op)(struct vhost_dev *dev,
struct vhost_vring_file *file);
typedef int (*vhost_net_set_mtu_op)(struct vhost_dev *dev, uint16_t mtu);
+typedef int (*vhost_net_get_rss_op)(struct vhost_dev *dev,
+ VirtioNetRssCapa *rss_capa);
+typedef int (*vhost_net_set_rss_op)(struct vhost_dev *dev,
+ VirtioNetRssData *rss_data);
typedef int (*vhost_scsi_set_endpoint_op)(struct vhost_dev *dev,
struct vhost_scsi_target *target);
typedef int (*vhost_scsi_clear_endpoint_op)(struct vhost_dev *dev,
@@ -133,6 +138,8 @@ typedef struct VhostOps {
vhost_backend_memslots_limit vhost_backend_memslots_limit;
vhost_net_set_backend_op vhost_net_set_backend;
vhost_net_set_mtu_op vhost_net_set_mtu;
+ vhost_net_get_rss_op vhost_net_get_rss;
+ vhost_net_set_rss_op vhost_net_set_rss;
vhost_scsi_set_endpoint_op vhost_scsi_set_endpoint;
vhost_scsi_clear_endpoint_op vhost_scsi_clear_endpoint;
vhost_scsi_get_abi_version_op vhost_scsi_get_abi_version;
diff --git a/include/net/vhost_net.h b/include/net/vhost_net.h
index 387e913e4e..9cf702e7e3 100644
--- a/include/net/vhost_net.h
+++ b/include/net/vhost_net.h
@@ -48,4 +48,8 @@ uint64_t vhost_net_get_acked_features(VHostNetState *net);
int vhost_net_set_mtu(struct vhost_net *net, uint16_t mtu);
+int vhost_net_get_rss(struct vhost_net *net, VirtioNetRssCapa *rss_capa);
+
+int vhost_net_set_rss(struct vhost_net *net, VirtioNetRssData *rss_data);
+
#endif
--
2.35.1
- [PATCH 0/5] Vhost-user: add Virtio RSS support, Maxime Coquelin, 2022/04/08
- [PATCH 5/5] vhost-user: add RSS support, Maxime Coquelin, 2022/04/08
- [PATCH 4/5] docs: introduce RSS support in Vhost-user specification, Maxime Coquelin, 2022/04/08
- [PATCH 3/5] virtio-net: add RSS support for Vhost backends,
Maxime Coquelin <=
- [PATCH 1/5] ebpf: pass and check RSS key length to the loader, Maxime Coquelin, 2022/04/08
- [PATCH 2/5] virtio-net: prepare for variable RSS key and indir table lengths, Maxime Coquelin, 2022/04/08
- Re: [PATCH 0/5] Vhost-user: add Virtio RSS support, Jason Wang, 2022/04/15