vhost-user: add VHOST_USER_GET_QUEUE_NUM message

This is for querying how many queues the backend supports if it has mq
support(when VHOST_USER_PROTOCOL_F_MQ flag is set from the quried
protocol features).

vhost_net_get_max_queues() is the interface to export that value, and
to tell if the backend supports # of queues user requested, which is
done in the following patch.

Signed-off-by: Yuanhan Liu <yuanhan.liu@linux.intel.com>
Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
Signed-off-by: Yuanhan Liu <yuanhan.liu@linux.intel.com>
Tested-by: Marcel Apfelbaum <marcel@redhat.com>
This commit is contained in:
Yuanhan Liu 2015-09-23 12:19:58 +08:00 committed by Michael S. Tsirkin
parent d1f8b30ec8
commit e2051e9e00
5 changed files with 39 additions and 1 deletions

View File

@ -301,3 +301,14 @@ Message types
Bits (0-7) of the payload contain the vring index. Bit 8 is the Bits (0-7) of the payload contain the vring index. Bit 8 is the
invalid FD flag. This flag is set when there is no file descriptor invalid FD flag. This flag is set when there is no file descriptor
in the ancillary data. in the ancillary data.
* VHOST_USER_GET_QUEUE_NUM
Id: 17
Equivalent ioctl: N/A
Master payload: N/A
Slave payload: u64
Query how many queues the backend supports. This request should be
sent only when VHOST_USER_PROTOCOL_F_MQ is set in quried protocol
features by VHOST_USER_GET_PROTOCOL_FEATURES.

View File

@ -122,6 +122,11 @@ void vhost_net_ack_features(struct vhost_net *net, uint64_t features)
vhost_ack_features(&net->dev, vhost_net_get_feature_bits(net), features); vhost_ack_features(&net->dev, vhost_net_get_feature_bits(net), features);
} }
uint64_t vhost_net_get_max_queues(VHostNetState *net)
{
return net->dev.max_queues;
}
static int vhost_net_get_fd(NetClientState *backend) static int vhost_net_get_fd(NetClientState *backend)
{ {
switch (backend->info->type) { switch (backend->info->type) {
@ -144,6 +149,8 @@ struct vhost_net *vhost_net_init(VhostNetOptions *options)
goto fail; goto fail;
} }
net->dev.max_queues = 1;
if (backend_kernel) { if (backend_kernel) {
r = vhost_net_get_fd(options->net_backend); r = vhost_net_get_fd(options->net_backend);
if (r < 0) { if (r < 0) {
@ -414,6 +421,11 @@ VHostNetState *get_vhost_net(NetClientState *nc)
return vhost_net; return vhost_net;
} }
#else #else
uint64_t vhost_net_get_max_queues(VHostNetState *net)
{
return 1;
}
struct vhost_net *vhost_net_init(VhostNetOptions *options) struct vhost_net *vhost_net_init(VhostNetOptions *options)
{ {
error_report("vhost-net support is not compiled in"); error_report("vhost-net support is not compiled in");

View File

@ -25,7 +25,9 @@
#define VHOST_MEMORY_MAX_NREGIONS 8 #define VHOST_MEMORY_MAX_NREGIONS 8
#define VHOST_USER_F_PROTOCOL_FEATURES 30 #define VHOST_USER_F_PROTOCOL_FEATURES 30
#define VHOST_USER_PROTOCOL_FEATURE_MASK 0x0ULL #define VHOST_USER_PROTOCOL_FEATURE_MASK 0x1ULL
#define VHOST_USER_PROTOCOL_F_MQ 0
typedef enum VhostUserRequest { typedef enum VhostUserRequest {
VHOST_USER_NONE = 0, VHOST_USER_NONE = 0,
@ -45,6 +47,7 @@ typedef enum VhostUserRequest {
VHOST_USER_SET_VRING_ERR = 14, VHOST_USER_SET_VRING_ERR = 14,
VHOST_USER_GET_PROTOCOL_FEATURES = 15, VHOST_USER_GET_PROTOCOL_FEATURES = 15,
VHOST_USER_SET_PROTOCOL_FEATURES = 16, VHOST_USER_SET_PROTOCOL_FEATURES = 16,
VHOST_USER_GET_QUEUE_NUM = 17,
VHOST_USER_MAX VHOST_USER_MAX
} VhostUserRequest; } VhostUserRequest;
@ -211,6 +214,7 @@ static int vhost_user_call(struct vhost_dev *dev, unsigned long int request,
switch (msg_request) { switch (msg_request) {
case VHOST_USER_GET_FEATURES: case VHOST_USER_GET_FEATURES:
case VHOST_USER_GET_PROTOCOL_FEATURES: case VHOST_USER_GET_PROTOCOL_FEATURES:
case VHOST_USER_GET_QUEUE_NUM:
need_reply = 1; need_reply = 1;
break; break;
@ -315,6 +319,7 @@ static int vhost_user_call(struct vhost_dev *dev, unsigned long int request,
switch (msg_request) { switch (msg_request) {
case VHOST_USER_GET_FEATURES: case VHOST_USER_GET_FEATURES:
case VHOST_USER_GET_PROTOCOL_FEATURES: case VHOST_USER_GET_PROTOCOL_FEATURES:
case VHOST_USER_GET_QUEUE_NUM:
if (msg.size != sizeof(m.u64)) { if (msg.size != sizeof(m.u64)) {
error_report("Received bad msg size."); error_report("Received bad msg size.");
return -1; return -1;
@ -366,6 +371,14 @@ static int vhost_user_init(struct vhost_dev *dev, void *opaque)
if (err < 0) { if (err < 0) {
return err; return err;
} }
/* query the max queues we support if backend supports Multiple Queue */
if (dev->protocol_features & (1ULL << VHOST_USER_PROTOCOL_F_MQ)) {
err = vhost_user_call(dev, VHOST_USER_GET_QUEUE_NUM, &dev->max_queues);
if (err < 0) {
return err;
}
}
} }
return 0; return 0;

View File

@ -48,6 +48,7 @@ struct vhost_dev {
unsigned long long acked_features; unsigned long long acked_features;
unsigned long long backend_features; unsigned long long backend_features;
unsigned long long protocol_features; unsigned long long protocol_features;
unsigned long long max_queues;
bool started; bool started;
bool log_enabled; bool log_enabled;
unsigned long long log_size; unsigned long long log_size;

View File

@ -13,6 +13,7 @@ typedef struct VhostNetOptions {
void *opaque; void *opaque;
} VhostNetOptions; } VhostNetOptions;
uint64_t vhost_net_get_max_queues(VHostNetState *net);
struct vhost_net *vhost_net_init(VhostNetOptions *options); struct vhost_net *vhost_net_init(VhostNetOptions *options);
int vhost_net_start(VirtIODevice *dev, NetClientState *ncs, int total_queues); int vhost_net_start(VirtIODevice *dev, NetClientState *ncs, int total_queues);