From: Liu Ping Fan <pingf...@linux.vnet.ibm.com> Currently, vring_push() modify used ring and publish it, but sometime, we need to gather the changes and publish them all at once. So introduce vring_fill(), vring_flush().
Signed-off-by: Liu Ping Fan <pingf...@linux.vnet.ibm.com> --- hw/dataplane/vring.c | 31 +++++++++++++++++++++++++++++++ hw/dataplane/vring.h | 2 ++ 2 files changed, 33 insertions(+), 0 deletions(-) diff --git a/hw/dataplane/vring.c b/hw/dataplane/vring.c index d5d4ef4..865bd4d 100644 --- a/hw/dataplane/vring.c +++ b/hw/dataplane/vring.c @@ -332,6 +332,37 @@ int vring_pop(VirtIODevice *vdev, Vring *vring, return head; } +/* Same as vring_push, but delay update used->idx, until ready */ +void vring_fill(Vring *vring, unsigned int head, int len) +{ + struct vring_used_elem *used; + + /* Don't touch vring if a fatal error occurred */ + if (vring->broken) { + return; + } + + /* The virtqueue contains a ring of used buffers. Get a pointer to the + * next entry in that used ring. */ + used = &vring->vr.used->ring[vring->last_used_idx % vring->vr.num]; + used->id = head; + used->len = len; + vring->last_used_idx++; +} + +void vring_flush(Vring *vring) +{ + uint16_t new; + + /* Make sure buffer is written before we update index. */ + smp_wmb(); + + new = vring->vr.used->idx = vring->last_used_idx; + if (unlikely((int16_t)(new - vring->signalled_used) < (uint16_t)1)) { + vring->signalled_used_valid = false; + } +} + /* After we've used one of their buffers, we tell them about it. * * Stolen from linux/drivers/vhost/vhost.c. diff --git a/hw/dataplane/vring.h b/hw/dataplane/vring.h index 3274f62..0d00500 100644 --- a/hw/dataplane/vring.h +++ b/hw/dataplane/vring.h @@ -57,6 +57,8 @@ bool vring_should_notify(VirtIODevice *vdev, Vring *vring); int vring_pop(VirtIODevice *vdev, Vring *vring, struct iovec iov[], struct iovec *iov_end, unsigned int *out_num, unsigned int *in_num); +void vring_fill(Vring *vring, unsigned int head, int len); +void vring_flush(Vring *vring); void vring_push(Vring *vring, unsigned int head, int len); #endif /* VRING_H */ -- 1.7.4.4