Skip to content

Commit

Permalink
vhost: introduce vring call API
Browse files Browse the repository at this point in the history
Users of librte_vhost currently implement the vring call operation
themselves.  Each caller performs the operation slightly differently.

This patch introduces a new librte_vhost API called
rte_vhost_vring_call() that performs the operation so that vhost-user
applications don't have to duplicate it.

Signed-off-by: Stefan Hajnoczi <stefanha@redhat.com>
Reviewed-by: Maxime Coquelin <maxime.coquelin@redhat.com>
Acked-by: Yuanhan Liu <yliu@fridaylinux.org>
  • Loading branch information
stefanhaRH authored and Ferruh Yigit committed Jan 16, 2018
1 parent 413a8fe commit 6c299bb
Show file tree
Hide file tree
Showing 5 changed files with 48 additions and 12 deletions.
11 changes: 2 additions & 9 deletions examples/vhost/virtio_net.c
Original file line number Diff line number Diff line change
Expand Up @@ -178,13 +178,8 @@ vs_enqueue_pkts(struct vhost_dev *dev, uint16_t queue_id,
*(volatile uint16_t *)&vr->used->idx += count;
queue->last_used_idx += count;

/* flush used->idx update before we read avail->flags. */
rte_mb();
rte_vhost_vring_call(dev->vid, queue_id);

/* Kick the guest if necessary. */
if (!(vr->avail->flags & VRING_AVAIL_F_NO_INTERRUPT)
&& (vr->callfd >= 0))
eventfd_write(vr->callfd, (eventfd_t)1);
return count;
}

Expand Down Expand Up @@ -367,9 +362,7 @@ vs_dequeue_pkts(struct vhost_dev *dev, uint16_t queue_id,

vr->used->idx += i;

if (!(vr->avail->flags & VRING_AVAIL_F_NO_INTERRUPT)
&& (vr->callfd >= 0))
eventfd_write(vr->callfd, (eventfd_t)1);
rte_vhost_vring_call(dev->vid, queue_id);

return i;
}
6 changes: 3 additions & 3 deletions examples/vhost_scsi/vhost_scsi.c
Original file line number Diff line number Diff line change
Expand Up @@ -81,7 +81,7 @@ descriptor_is_wr(struct vring_desc *cur_desc)
}

static void
submit_completion(struct vhost_scsi_task *task)
submit_completion(struct vhost_scsi_task *task, uint32_t q_idx)
{
struct rte_vhost_vring *vq;
struct vring_used *used;
Expand All @@ -102,7 +102,7 @@ submit_completion(struct vhost_scsi_task *task)
/* Send an interrupt back to the guest VM so that it knows
* a completion is ready to be processed.
*/
eventfd_write(vq->callfd, (eventfd_t)1);
rte_vhost_vring_call(task->bdev->vid, q_idx);
}

static void
Expand Down Expand Up @@ -234,7 +234,7 @@ process_requestq(struct vhost_scsi_ctrlr *ctrlr, uint32_t q_idx)
task->resp->status = 0;
task->resp->resid = 0;
}
submit_completion(task);
submit_completion(task, q_idx);
rte_free(task);
}
}
Expand Down
15 changes: 15 additions & 0 deletions lib/librte_vhost/rte_vhost.h
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,9 @@ struct rte_vhost_vring {
struct vring_used *used;
uint64_t log_guest_addr;

/** Deprecated, use rte_vhost_vring_call() instead. */
int callfd;

int kickfd;
uint16_t size;
};
Expand Down Expand Up @@ -407,6 +409,19 @@ int rte_vhost_get_mem_table(int vid, struct rte_vhost_memory **mem);
int rte_vhost_get_vhost_vring(int vid, uint16_t vring_idx,
struct rte_vhost_vring *vring);

/**
* Notify the guest that used descriptors have been added to the vring. This
* function acts as a memory barrier.
*
* @param vid
* vhost device ID
* @param vring_idx
* vring index
* @return
* 0 on success, -1 on failure
*/
int rte_vhost_vring_call(int vid, uint16_t vring_idx);

/**
* Get vhost RX queue avail count.
*
Expand Down
7 changes: 7 additions & 0 deletions lib/librte_vhost/rte_vhost_version.map
Original file line number Diff line number Diff line change
Expand Up @@ -52,3 +52,10 @@ DPDK_17.08 {
rte_vhost_rx_queue_count;

} DPDK_17.05;

DPDK_18.02 {
global:

rte_vhost_vring_call;

} DPDK_17.08;
21 changes: 21 additions & 0 deletions lib/librte_vhost/vhost.c
Original file line number Diff line number Diff line change
Expand Up @@ -490,6 +490,27 @@ rte_vhost_get_vhost_vring(int vid, uint16_t vring_idx,
return 0;
}

int
rte_vhost_vring_call(int vid, uint16_t vring_idx)
{
struct virtio_net *dev;
struct vhost_virtqueue *vq;

dev = get_device(vid);
if (!dev)
return -1;

if (vring_idx >= VHOST_MAX_VRING)
return -1;

vq = dev->virtqueue[vring_idx];
if (!vq)
return -1;

vhost_vring_call(vq);
return 0;
}

uint16_t
rte_vhost_avail_entries(int vid, uint16_t queue_id)
{
Expand Down

0 comments on commit 6c299bb

Please sign in to comment.