On Wed, Jun 23, 2010 at 11:12 PM, Anthony Liguori <anth...@codemonkey.ws> wrote:
> Shouldn't it be possible to just drop the lock before invoking
> virtqueue_kick() and reacquire it afterwards?  There's nothing in that
> virtqueue_kick() path that the lock is protecting AFAICT.

No, that would lead to a race condition because vq->num_added is
modified by both virtqueue_add_buf_gfp() and virtqueue_kick().
Without a lock held during virtqueue_kick() another vcpu could add
bufs while vq->num_added is used and cleared by virtqueue_kick():

void virtqueue_kick(struct virtqueue *_vq, spinlock_t *lock)
{
        struct vring_virtqueue *vq = to_vvq(_vq);
        START_USE(vq);
        /* Descriptors and available array need to be set before we expose the
         * new available array entries. */
        virtio_wmb();

        vq->vring.avail->idx += vq->num_added;
        vq->num_added = 0;

        /* Need to update avail index before checking if we should notify */
        virtio_mb();

        if (!(vq->vring.used->flags & VRING_USED_F_NO_NOTIFY)) {
                /* Release lock while doing the kick because the guest should
                 * not exit with the lock held. */
                if (lock)
                        spin_unlock(lock);

                /* Prod other side to tell it about changes. */
                vq->notify(&vq->vq);

                if (lock)
                        spin_lock(lock);
        }

        END_USE(vq);
}

Stefan
--
To unsubscribe from this list: send the line "unsubscribe kvm" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

Reply via email to