Lines Matching +full:- +full:- +full:disable +full:- +full:vhost +full:- +full:user
2 * Base vhost-user-base implementation. This can be used to derive a
3 * more fully specified vhost-user backend either generically (see
4 * vhost-user-device) or via a specific stub for a device which
10 * SPDX-License-Identifier: GPL-2.0-or-later
15 #include "hw/qdev-properties.h"
16 #include "hw/virtio/virtio-bus.h"
17 #include "hw/virtio/vhost-user-base.h"
18 #include "qemu/error-report.h"
27 if (!k->set_guest_notifiers) { in vub_start()
32 ret = vhost_dev_enable_notifiers(&vub->vhost_dev, vdev); in vub_start()
34 error_report("Error enabling host notifiers: %d", -ret); in vub_start()
38 ret = k->set_guest_notifiers(qbus->parent, vub->vhost_dev.nvqs, true); in vub_start()
40 error_report("Error binding guest notifier: %d", -ret); in vub_start()
44 vub->vhost_dev.acked_features = vdev->guest_features; in vub_start()
46 ret = vhost_dev_start(&vub->vhost_dev, vdev, true); in vub_start()
48 error_report("Error starting vhost-user-base: %d", -ret); in vub_start()
54 * everything here. virtio-pci will do the right thing by in vub_start()
57 for (i = 0; i < vub->vhost_dev.nvqs; i++) { in vub_start()
58 vhost_virtqueue_mask(&vub->vhost_dev, vdev, i, false); in vub_start()
64 k->set_guest_notifiers(qbus->parent, vub->vhost_dev.nvqs, false); in vub_start()
66 vhost_dev_disable_notifiers(&vub->vhost_dev, vdev); in vub_start()
76 if (!k->set_guest_notifiers) { in vub_stop()
80 ret = vhost_dev_stop(&vub->vhost_dev, vdev, true); in vub_stop()
82 if (k->set_guest_notifiers(qbus->parent, vub->vhost_dev.nvqs, false) < 0) { in vub_stop()
83 error_report("vhost guest notifier cleanup failed: %d", ret); in vub_stop()
84 return -1; in vub_stop()
87 vhost_dev_disable_notifiers(&vub->vhost_dev, vdev); in vub_stop()
96 if (vhost_dev_is_started(&vub->vhost_dev) == should_start) { in vub_set_status()
121 /* This should be set when the vhost connection initialises */ in vub_get_features()
122 g_assert(vub->vhost_dev.features); in vub_get_features()
123 return vub->vhost_dev.features & ~(1ULL << VHOST_USER_F_PROTOCOL_FEATURES); in vub_get_features()
128 * space. We don't cache the config but re-fetch it from the guest
140 g_assert(vub->config_size && vub->vhost_user.supports_config == true); in vub_get_config()
142 if (vhost_dev_get_config(&vub->vhost_dev, config, in vub_get_config()
143 vub->config_size, &local_err)) { in vub_get_config()
153 g_assert(vub->config_size && vub->vhost_user.supports_config == true); in vub_set_config()
155 ret = vhost_dev_set_config(&vub->vhost_dev, config_data, in vub_set_config()
156 0, vub->config_size, in vub_set_config()
159 error_report("vhost guest set device config space failed: %d", ret); in vub_set_config()
166 * signal the guest as we re-read the config on demand above.
170 virtio_notify_config(dev->vdev); in vub_config_notifier()
188 vhost_user_cleanup(&vub->vhost_user); in do_vhost_user_cleanup()
190 for (int i = 0; i < vub->num_vqs; i++) { in do_vhost_user_cleanup()
191 VirtQueue *vq = g_ptr_array_index(vub->vqs, i); in do_vhost_user_cleanup()
202 struct vhost_dev *vhost_dev = &vub->vhost_dev; in vub_connect()
204 if (vub->connected) { in vub_connect()
207 vub->connected = true; in vub_connect()
213 if (vub->vhost_user.supports_config) { in vub_connect()
217 /* restore vhost state */ in vub_connect()
218 if (virtio_device_started(vdev, vdev->status)) { in vub_connect()
231 struct vhost_virtqueue *vhost_vqs = vub->vhost_dev.vqs; in vub_disconnect()
233 if (!vub->connected) { in vub_disconnect()
236 vub->connected = false; in vub_disconnect()
239 vhost_dev_cleanup(&vub->vhost_dev); in vub_disconnect()
243 /* Re-instate the event handler for new connections */ in vub_disconnect()
244 qemu_chr_fe_set_handlers(&vub->chardev, in vub_disconnect()
258 qemu_chr_fe_disconnect(&vub->chardev); in vub_event()
264 vhost_user_async_close(dev, &vub->chardev, &vub->vhost_dev, in vub_event()
281 if (!vub->chardev.chr) { in vub_device_realize()
282 error_setg(errp, "vhost-user-base: missing chardev"); in vub_device_realize()
286 if (!vub->virtio_id) { in vub_device_realize()
287 error_setg(errp, "vhost-user-base: need to define device id"); in vub_device_realize()
291 if (!vub->num_vqs) { in vub_device_realize()
292 vub->num_vqs = 1; /* reasonable default? */ in vub_device_realize()
295 if (!vub->vq_size) { in vub_device_realize()
296 vub->vq_size = 64; in vub_device_realize()
301 * config region, specialisations of the vhost-user-base will be in vub_device_realize()
304 if (vub->config_size) { in vub_device_realize()
305 vub->vhost_user.supports_config = true; in vub_device_realize()
308 if (!vhost_user_init(&vub->vhost_user, &vub->chardev, errp)) { in vub_device_realize()
312 virtio_init(vdev, vub->virtio_id, vub->config_size); in vub_device_realize()
315 * Disable guest notifiers, by default all notifications will be via the in vub_device_realize()
316 * asynchronous vhost-user socket. in vub_device_realize()
318 vdev->use_guest_notifier_mask = false; in vub_device_realize()
321 vub->vqs = g_ptr_array_sized_new(vub->num_vqs); in vub_device_realize()
322 for (int i = 0; i < vub->num_vqs; i++) { in vub_device_realize()
323 g_ptr_array_add(vub->vqs, in vub_device_realize()
324 virtio_add_queue(vdev, vub->vq_size, in vub_device_realize()
328 vub->vhost_dev.nvqs = vub->num_vqs; in vub_device_realize()
329 vub->vhost_dev.vqs = g_new0(struct vhost_virtqueue, vub->vhost_dev.nvqs); in vub_device_realize()
332 ret = vhost_dev_init(&vub->vhost_dev, &vub->vhost_user, in vub_device_realize()
339 qemu_chr_fe_set_handlers(&vub->chardev, NULL, NULL, vub_event, NULL, in vub_device_realize()
347 struct vhost_virtqueue *vhost_vqs = vub->vhost_dev.vqs; in vub_device_unrealize()
349 /* This will stop vhost backend if appropriate. */ in vub_device_unrealize()
351 vhost_dev_cleanup(&vub->vhost_dev); in vub_device_unrealize()
360 vdc->realize = vub_device_realize; in vub_class_init()
361 vdc->unrealize = vub_device_unrealize; in vub_class_init()
362 vdc->get_features = vub_get_features; in vub_class_init()
363 vdc->get_config = vub_get_config; in vub_class_init()
364 vdc->set_config = vub_set_config; in vub_class_init()
365 vdc->set_status = vub_set_status; in vub_class_init()