Hi Adrian, > -----Original Message----- > From: Adrian Moreno <amore...@redhat.com> > Sent: Monday, June 22, 2020 6:18 PM > To: Xia, Chenbo <chenbo....@intel.com>; Maxime Coquelin > <maxime.coque...@redhat.com>; Ye, Xiaolong <xiaolong...@intel.com>; > shah...@mellanox.com; ma...@mellanox.com; Wang, Xiao W > <xiao.w.w...@intel.com>; viachesl...@mellanox.com; dev@dpdk.org > Cc: jasow...@redhat.com; l...@redhat.com > Subject: Re: [dpdk-dev] [PATCH 6/9] vhost: add support for virtio status > > Hi Chenbo > > On 6/16/20 6:29 AM, Xia, Chenbo wrote: > > Hi Maxime, > > > >> -----Original Message----- > >> From: dev <dev-boun...@dpdk.org> On Behalf Of Maxime Coquelin > >> Sent: Thursday, May 14, 2020 4:02 PM > >> To: Ye, Xiaolong <xiaolong...@intel.com>; shah...@mellanox.com; > >> ma...@mellanox.com; amore...@redhat.com; Wang, Xiao W > >> <xiao.w.w...@intel.com>; viachesl...@mellanox.com; dev@dpdk.org > >> Cc: jasow...@redhat.com; l...@redhat.com; Maxime Coquelin > >> <maxime.coque...@redhat.com> > >> Subject: [dpdk-dev] [PATCH 6/9] vhost: add support for virtio status > >> > >> This patch adds support to the new Virtio device status Vhost-user > >> protocol feature. > >> > >> Getting such information in the backend helps to know when the driver > >> is done with the device configuration and so makes the initialization phase > more robust. > >> > >> Signed-off-by: Maxime Coquelin <maxime.coque...@redhat.com> > >> --- > >> lib/librte_vhost/rte_vhost.h | 4 ++++ > >> lib/librte_vhost/vhost.h | 9 ++++++++ > >> lib/librte_vhost/vhost_user.c | 40 > >> +++++++++++++++++++++++++++++++++++ > >> lib/librte_vhost/vhost_user.h | 6 ++++-- > >> 4 files changed, 57 insertions(+), 2 deletions(-) > >> > >> diff --git a/lib/librte_vhost/rte_vhost.h > >> b/lib/librte_vhost/rte_vhost.h index > >> 5c72fba797..b4b7aa1928 100644 > >> --- a/lib/librte_vhost/rte_vhost.h > >> +++ b/lib/librte_vhost/rte_vhost.h > >> @@ -85,6 +85,10 @@ extern "C" { > >> #define VHOST_USER_PROTOCOL_F_INFLIGHT_SHMFD 12 #endif > >> > >> +#ifndef VHOST_USER_PROTOCOL_F_STATUS #define > >> +VHOST_USER_PROTOCOL_F_STATUS 15 #endif > >> + > >> /** Indicate whether protocol features negotiation is supported. */ > >> #ifndef VHOST_USER_F_PROTOCOL_FEATURES > >> #define VHOST_USER_F_PROTOCOL_FEATURES 30 > >> diff --git a/lib/librte_vhost/vhost.h b/lib/librte_vhost/vhost.h > >> index > >> df98d15de6..9a9c0a98f5 100644 > >> --- a/lib/librte_vhost/vhost.h > >> +++ b/lib/librte_vhost/vhost.h > >> @@ -202,6 +202,14 @@ struct vhost_virtqueue { > >> TAILQ_HEAD(, vhost_iotlb_entry) iotlb_pending_list; } > >> __rte_cache_aligned; > >> > >> +/* Virtio device status as per Virtio specification */ > >> +#define VIRTIO_DEVICE_STATUS_ACK 0x01 > >> +#define VIRTIO_DEVICE_STATUS_DRIVER 0x02 > >> +#define VIRTIO_DEVICE_STATUS_DRIVER_OK 0x04 > >> +#define VIRTIO_DEVICE_STATUS_FEATURES_OK 0x08 > >> +#define VIRTIO_DEVICE_STATUS_DEV_NEED_RESET 0x40 > >> +#define VIRTIO_DEVICE_STATUS_FAILED 0x80 > >> + > >> /* Old kernels have no such macros defined */ #ifndef > >> VIRTIO_NET_F_GUEST_ANNOUNCE > >> #define VIRTIO_NET_F_GUEST_ANNOUNCE 21 @@ -364,6 +372,7 @@ > struct > >> virtio_net { > >> uint64_t log_addr; > >> struct rte_ether_addr mac; > >> uint16_t mtu; > >> + uint8_t status; > >> > >> struct vhost_device_ops const *notify_ops; > >> > >> diff --git a/lib/librte_vhost/vhost_user.c > >> b/lib/librte_vhost/vhost_user.c index 4a847f368c..e5a44be58d 100644 > >> --- a/lib/librte_vhost/vhost_user.c > >> +++ b/lib/librte_vhost/vhost_user.c > >> @@ -87,6 +87,7 @@ static const char > >> *vhost_message_str[VHOST_USER_MAX] > >> = { > >> [VHOST_USER_POSTCOPY_END] = "VHOST_USER_POSTCOPY_END", > >> [VHOST_USER_GET_INFLIGHT_FD] = "VHOST_USER_GET_INFLIGHT_FD", > >> [VHOST_USER_SET_INFLIGHT_FD] = "VHOST_USER_SET_INFLIGHT_FD", > >> + [VHOST_USER_SET_STATUS] = "VHOST_USER_SET_STATUS", > >> }; > >> > >> static int send_vhost_reply(int sockfd, struct VhostUserMsg *msg); > >> @@ -1328,6 > >> +1329,11 @@ virtio_is_ready(struct virtio_net *dev) > >> return 0; > >> } > >> > >> + /* If supported, ensure the frontend is really done with config */ > >> + if (dev->protocol_features & (1ULL << > >> VHOST_USER_PROTOCOL_F_STATUS)) > >> + if (!(dev->status & VIRTIO_DEVICE_STATUS_DRIVER_OK)) > >> + return 0; > >> + > >> dev->flags |= VIRTIO_DEV_READY; > >> > >> VHOST_LOG_CONFIG(INFO, > >> @@ -2425,6 +2431,39 @@ vhost_user_postcopy_end(struct virtio_net > >> **pdev, struct VhostUserMsg *msg, > >> return RTE_VHOST_MSG_RESULT_REPLY; > >> } > >> > >> +static int > >> +vhost_user_set_status(struct virtio_net **pdev, struct VhostUserMsg *msg, > >> + int main_fd __rte_unused) > >> +{ > >> + struct virtio_net *dev = *pdev; > >> + > >> + /* As per Virtio specification, the device status is 8bits long */ > >> + if (msg->payload.u64 > UINT8_MAX) { > >> + VHOST_LOG_CONFIG(ERR, "Invalid VHOST_USER_SET_STATUS > >> payload 0x%" PRIx64 "\n", > >> + msg->payload.u64); > >> + return RTE_VHOST_MSG_RESULT_ERR; > >> + } > >> + > >> + dev->status = msg->payload.u64; > >> + > >> + VHOST_LOG_CONFIG(INFO, "New device status(0x%08x):\n" > >> + "\t-ACKNOWLEDGE: %u\n" > >> + "\t-DRIVER: %u\n" > >> + "\t-FEATURES_OK: %u\n" > >> + "\t-DRIVER_OK: %u\n" > >> + "\t-DEVICE_NEED_RESET: %u\n" > >> + "\t-FAILED: %u\n", > >> + dev->status, > >> + !!(dev->status & VIRTIO_DEVICE_STATUS_ACK), > >> + !!(dev->status & VIRTIO_DEVICE_STATUS_DRIVER), > >> + !!(dev->status & > >> VIRTIO_DEVICE_STATUS_FEATURES_OK), > >> + !!(dev->status & VIRTIO_DEVICE_STATUS_DRIVER_OK), > >> + !!(dev->status & > >> VIRTIO_DEVICE_STATUS_DEV_NEED_RESET), > >> + !!(dev->status & VIRTIO_DEVICE_STATUS_FAILED)); > >> + > >> + return RTE_VHOST_MSG_RESULT_OK; > > > > I see in your patch for virtio-user SET_STATUS support > > (http://patchwork.dpdk.org/patch/70677/), the VHOST_USER_SET_STATUS > > msg may request a reply, but this func does not handle this case. If > > we don't handle here, vhost_user_msg_handler will return > RTE_VHOST_MSG_RESULT_ERR later. So should we handle the case here? > > > Why should the reply be handled in this function? > After this function is called, vhost_user_msg_handler() should handle the > replies > in: > > if (msg.flags & VHOST_USER_NEED_REPLY) { > msg.payload.u64 = ret == RTE_VHOST_MSG_RESULT_ERR; > msg.size = sizeof(msg.payload.u64); > msg.fd_num = 0; > send_vhost_reply(fd, &msg); > } else if (ret == RTE_VHOST_MSG_RESULT_ERR) { > VHOST_LOG_CONFIG(ERR, > "vhost message handling failed.\n"); > return -1; > } > > Am I missing something?
You're correct, I missed this one :) Thanks! Chenbo > > > > Thanks, > > Chenbo > > > >> +} > >> + > >> typedef int (*vhost_message_handler_t)(struct virtio_net **pdev, > >> struct VhostUserMsg *msg, > >> int main_fd); > >> @@ -2457,6 +2496,7 @@ static vhost_message_handler_t > >> vhost_message_handlers[VHOST_USER_MAX] = { > >> [VHOST_USER_POSTCOPY_END] = vhost_user_postcopy_end, > >> [VHOST_USER_GET_INFLIGHT_FD] = vhost_user_get_inflight_fd, > >> [VHOST_USER_SET_INFLIGHT_FD] = vhost_user_set_inflight_fd, > >> + [VHOST_USER_SET_STATUS] = vhost_user_set_status, > >> }; > >> > >> /* return bytes# of read on success or negative val on failure. */ > >> diff --git a/lib/librte_vhost/vhost_user.h > >> b/lib/librte_vhost/vhost_user.h index 1f65efa4a9..74fd361e3a 100644 > >> --- a/lib/librte_vhost/vhost_user.h > >> +++ b/lib/librte_vhost/vhost_user.h > >> @@ -23,7 +23,8 @@ > >> (1ULL << > >> VHOST_USER_PROTOCOL_F_CRYPTO_SESSION) | \ > >> (1ULL << > >> VHOST_USER_PROTOCOL_F_SLAVE_SEND_FD) | \ > >> (1ULL << > >> VHOST_USER_PROTOCOL_F_HOST_NOTIFIER) | \ > >> - (1ULL << > >> VHOST_USER_PROTOCOL_F_PAGEFAULT)) > >> + (1ULL << > >> VHOST_USER_PROTOCOL_F_PAGEFAULT) | \ > >> + (1ULL << > >> VHOST_USER_PROTOCOL_F_STATUS)) > >> > >> typedef enum VhostUserRequest { > >> VHOST_USER_NONE = 0, > >> @@ -56,7 +57,8 @@ typedef enum VhostUserRequest { > >> VHOST_USER_POSTCOPY_END = 30, > >> VHOST_USER_GET_INFLIGHT_FD = 31, > >> VHOST_USER_SET_INFLIGHT_FD = 32, > >> - VHOST_USER_MAX = 33 > >> + VHOST_USER_SET_STATUS = 36, > >> + VHOST_USER_MAX = 37 > >> } VhostUserRequest; > >> > >> typedef enum VhostUserSlaveRequest { > >> -- > >> 2.25.4 > > > > -- > Adrián Moreno