1 #ifndef VFIO_USER_PROXY_H 2 #define VFIO_USER_PROXY_H 3 4 /* 5 * vfio protocol over a UNIX socket. 6 * 7 * Copyright © 2018, 2021 Oracle and/or its affiliates. 8 * 9 * SPDX-License-Identifier: GPL-2.0-or-later 10 */ 11 12 #include "io/channel.h" 13 #include "io/channel-socket.h" 14 15 #include "qemu/queue.h" 16 #include "qemu/sockets.h" 17 #include "qemu/thread.h" 18 #include "hw/vfio/vfio-device.h" 19 #include "hw/vfio-user/protocol.h" 20 21 typedef struct { 22 int send_fds; 23 int recv_fds; 24 int *fds; 25 } VFIOUserFDs; 26 27 enum msg_type { 28 VFIO_MSG_NONE, 29 VFIO_MSG_ASYNC, 30 VFIO_MSG_WAIT, 31 VFIO_MSG_NOWAIT, 32 VFIO_MSG_REQ, 33 }; 34 35 typedef struct VFIOUserMsg { 36 QTAILQ_ENTRY(VFIOUserMsg) next; 37 VFIOUserHdr *hdr; 38 VFIOUserFDs *fds; 39 uint32_t rsize; 40 uint32_t id; 41 QemuCond cv; 42 bool complete; 43 bool pending; 44 enum msg_type type; 45 } VFIOUserMsg; 46 47 48 enum proxy_state { 49 VFIO_PROXY_CONNECTED = 1, 50 VFIO_PROXY_ERROR = 2, 51 VFIO_PROXY_CLOSING = 3, 52 VFIO_PROXY_CLOSED = 4, 53 }; 54 55 typedef QTAILQ_HEAD(VFIOUserMsgQ, VFIOUserMsg) VFIOUserMsgQ; 56 57 typedef struct VFIOUserProxy { 58 QLIST_ENTRY(VFIOUserProxy) next; 59 char *sockname; 60 struct QIOChannel *ioc; 61 void (*request)(void *opaque, VFIOUserMsg *msg); 62 void *req_arg; 63 uint64_t max_xfer_size; 64 uint64_t max_send_fds; 65 uint64_t max_dma; 66 uint64_t dma_pgsizes; 67 uint64_t max_bitmap; 68 uint64_t migr_pgsize; 69 int flags; 70 uint32_t wait_time; 71 QemuCond close_cv; 72 AioContext *ctx; 73 QEMUBH *req_bh; 74 bool async_ops; 75 76 /* 77 * above only changed when BQL is held 78 * below are protected by per-proxy lock 79 */ 80 QemuMutex lock; 81 VFIOUserMsgQ free; 82 VFIOUserMsgQ pending; 83 VFIOUserMsgQ incoming; 84 VFIOUserMsgQ outgoing; 85 VFIOUserMsg *last_nowait; 86 VFIOUserMsg *part_recv; 87 size_t recv_left; 88 enum proxy_state state; 89 } VFIOUserProxy; 90 91 /* VFIOProxy flags */ 92 #define VFIO_PROXY_CLIENT 0x1 93 #define VFIO_PROXY_FORCE_QUEUED 0x4 94 95 typedef struct VFIODevice VFIODevice; 96 97 VFIOUserProxy *vfio_user_connect_dev(SocketAddress *addr, Error **errp); 98 void vfio_user_disconnect(VFIOUserProxy *proxy); 99 void vfio_user_set_handler(VFIODevice *vbasedev, 100 void (*handler)(void *opaque, VFIOUserMsg *msg), 101 void *reqarg); 102 bool vfio_user_validate_version(VFIOUserProxy *proxy, Error **errp); 103 104 VFIOUserFDs *vfio_user_getfds(int numfds); 105 void vfio_user_putfds(VFIOUserMsg *msg); 106 107 void vfio_user_request_msg(VFIOUserHdr *hdr, uint16_t cmd, 108 uint32_t size, uint32_t flags); 109 void vfio_user_wait_reqs(VFIOUserProxy *proxy); 110 bool vfio_user_send_wait(VFIOUserProxy *proxy, VFIOUserHdr *hdr, 111 VFIOUserFDs *fds, int rsize, Error **errp); 112 bool vfio_user_send_nowait(VFIOUserProxy *proxy, VFIOUserHdr *hdr, 113 VFIOUserFDs *fds, int rsize, Error **errp); 114 void vfio_user_send_reply(VFIOUserProxy *proxy, VFIOUserHdr *hdr, int size); 115 void vfio_user_send_error(VFIOUserProxy *proxy, VFIOUserHdr *hdr, int error); 116 117 #endif /* VFIO_USER_PROXY_H */ 118