1 /* $OpenBSD: virtio.h,v 1.41 2021/07/16 16:21:22 dv Exp $ */ 2 3 /* 4 * Copyright (c) 2015 Mike Larkin <mlarkin@openbsd.org> 5 * 6 * Permission to use, copy, modify, and distribute this software for any 7 * purpose with or without fee is hereby granted, provided that the above 8 * copyright notice and this permission notice appear in all copies. 9 * 10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 11 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 12 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 13 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 14 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 15 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 16 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 17 */ 18 19 #include <sys/types.h> 20 21 #include <dev/pv/virtioreg.h> 22 #include <net/if_tun.h> 23 24 #include <event.h> 25 26 #include "vmd.h" 27 28 #ifndef _VIRTIO_H_ 29 #define _VIRTIO_H_ 30 31 #define VIRTQUEUE_ALIGN(n) (((n)+(VIRTIO_PAGE_SIZE-1))& \ 32 ~(VIRTIO_PAGE_SIZE-1)) 33 #define ALIGNSZ(sz, align) ((sz + align - 1) & ~(align - 1)) 34 #define MIN(a,b) (((a)<(b))?(a):(b)) 35 36 /* Queue sizes must be power of two */ 37 #define VIORND_QUEUE_SIZE 64 38 #define VIORND_QUEUE_MASK (VIORND_QUEUE_SIZE - 1) 39 40 #define VIOBLK_QUEUE_SIZE 128 41 #define VIOBLK_QUEUE_MASK (VIOBLK_QUEUE_SIZE - 1) 42 43 #define VIOSCSI_QUEUE_SIZE 128 44 #define VIOSCSI_QUEUE_MASK (VIOSCSI_QUEUE_SIZE - 1) 45 46 #define VIONET_QUEUE_SIZE 256 47 #define VIONET_QUEUE_MASK (VIONET_QUEUE_SIZE - 1) 48 49 /* Virtio network device is backed by tap(4), so inherit limits */ 50 #define VIONET_HARD_MTU TUNMRU 51 #define VIONET_MIN_TXLEN ETHER_HDR_LEN 52 #define VIONET_MAX_TXLEN VIONET_HARD_MTU + ETHER_HDR_LEN 53 54 /* VMM Control Interface shutdown timeout (in seconds) */ 55 #define VMMCI_TIMEOUT 3 56 #define VMMCI_SHUTDOWN_TIMEOUT 120 57 58 /* All the devices we support have either 1, 2 or 3 queues */ 59 /* viornd - 1 queue 60 * vioblk - 1 queue 61 * vionet - 2 queues 62 * vioscsi - 3 queues 63 */ 64 #define VIRTIO_MAX_QUEUES 3 65 66 /* 67 * This struct stores notifications from a virtio driver. There is 68 * one such struct per virtio device. 69 */ 70 struct virtio_io_cfg { 71 uint32_t device_feature; 72 uint32_t guest_feature; 73 uint32_t queue_address; 74 uint16_t queue_size; 75 uint16_t queue_select; 76 uint16_t queue_notify; 77 uint8_t device_status; 78 uint8_t isr_status; 79 }; 80 81 struct virtio_backing { 82 void *p; 83 ssize_t (*pread)(void *p, char *buf, size_t len, off_t off); 84 ssize_t (*pwrite)(void *p, char *buf, size_t len, off_t off); 85 void (*close)(void *p, int); 86 }; 87 88 /* 89 * A virtio device can have several virtqs. For example, vionet has one virtq 90 * each for transmitting and receiving packets. This struct describes the state 91 * of one virtq, such as their address in memory, size, offsets of rings, etc. 92 * There is one virtio_vq_info per virtq. 93 */ 94 struct virtio_vq_info { 95 /* Guest physical address of virtq */ 96 uint32_t qa; 97 98 /* Queue size: number of queue entries in virtq */ 99 uint32_t qs; 100 101 /* 102 * The offset of the 'available' ring within the virtq located at 103 * guest physical address qa above 104 */ 105 uint32_t vq_availoffset; 106 107 /* 108 * The offset of the 'used' ring within the virtq located at guest 109 * physical address qa above 110 */ 111 uint32_t vq_usedoffset; 112 113 /* 114 * The index into a slot of the 'available' ring that a virtio device 115 * can consume next 116 */ 117 uint16_t last_avail; 118 119 /* 120 * The most recent index into the 'available' ring that a virtio 121 * driver notified to the host. 122 */ 123 uint16_t notified_avail; 124 }; 125 126 /* 127 * Each virtio driver has a notifyq method where one or more messages 128 * are ready to be processed on a given virtq. As such, various 129 * pieces of information are needed to provide ring accounting while 130 * processing a given message such as virtq indexes, vring pointers, and 131 * vring descriptors. 132 */ 133 struct virtio_vq_acct { 134 135 /* index of previous avail vring message */ 136 uint16_t idx; 137 138 /* index of current message containing the request */ 139 uint16_t req_idx; 140 141 /* index of current message containing the response */ 142 uint16_t resp_idx; 143 144 /* vring descriptor pointer */ 145 struct vring_desc *desc; 146 147 /* vring descriptor pointer for request header and data */ 148 struct vring_desc *req_desc; 149 150 /* vring descriptor pointer for response header and data */ 151 struct vring_desc *resp_desc; 152 153 /* pointer to the available vring */ 154 struct vring_avail *avail; 155 156 /* pointer to the used vring */ 157 struct vring_used *used; 158 }; 159 160 struct viornd_dev { 161 struct virtio_io_cfg cfg; 162 163 struct virtio_vq_info vq[VIRTIO_MAX_QUEUES]; 164 165 uint8_t pci_id; 166 int irq; 167 uint32_t vm_id; 168 }; 169 170 struct vioblk_dev { 171 struct virtio_io_cfg cfg; 172 173 struct virtio_vq_info vq[VIRTIO_MAX_QUEUES]; 174 struct virtio_backing file; 175 176 uint64_t sz; 177 uint32_t max_xfer; 178 179 uint8_t pci_id; 180 int irq; 181 uint32_t vm_id; 182 }; 183 184 /* vioscsi will use at least 3 queues - 5.6.2 Virtqueues 185 * Current implementation will use 3 186 * 0 - control 187 * 1 - event 188 * 2 - requests 189 */ 190 struct vioscsi_dev { 191 struct virtio_io_cfg cfg; 192 193 struct virtio_vq_info vq[VIRTIO_MAX_QUEUES]; 194 195 struct virtio_backing file; 196 197 /* is the device locked */ 198 int locked; 199 /* size of iso file in bytes */ 200 uint64_t sz; 201 /* last block address read */ 202 uint64_t lba; 203 /* number of blocks represented in iso */ 204 uint64_t n_blocks; 205 uint32_t max_xfer; 206 207 uint8_t pci_id; 208 uint32_t vm_id; 209 int irq; 210 }; 211 212 struct vionet_dev { 213 pthread_mutex_t mutex; 214 struct event event; 215 216 struct virtio_io_cfg cfg; 217 218 struct virtio_vq_info vq[VIRTIO_MAX_QUEUES]; 219 220 int fd; 221 uint32_t vm_id; 222 uint32_t vm_vmid; 223 int irq; 224 uint8_t mac[6]; 225 uint8_t hostmac[6]; 226 227 int idx; 228 int lockedmac; 229 int local; 230 int pxeboot; 231 232 uint8_t pci_id; 233 }; 234 235 struct virtio_net_hdr { 236 uint8_t flags; 237 uint8_t gso_type; 238 uint16_t hdr_len; 239 uint16_t gso_size; 240 uint16_t csum_start; 241 uint16_t csum_offset; 242 243 /* 244 * num_buffers is only used if VIRTIO_NET_F_MRG_RXBUF is negotiated. 245 * vmd(8) doesn't negotiate that, but the field is listed here 246 * for completeness sake. 247 */ 248 /* uint16_t num_buffers; */ 249 }; 250 251 enum vmmci_cmd { 252 VMMCI_NONE = 0, 253 VMMCI_SHUTDOWN, 254 VMMCI_REBOOT, 255 VMMCI_SYNCRTC, 256 }; 257 258 struct vmmci_dev { 259 struct virtio_io_cfg cfg; 260 struct event timeout; 261 struct timeval time; 262 enum vmmci_cmd cmd; 263 uint32_t vm_id; 264 int irq; 265 266 uint8_t pci_id; 267 }; 268 269 struct ioinfo { 270 struct virtio_backing *file; 271 uint8_t *buf; 272 ssize_t len; 273 off_t offset; 274 int error; 275 }; 276 277 /* virtio.c */ 278 void virtio_init(struct vmd_vm *, int, int[][VM_MAX_BASE_PER_DISK], int *); 279 void virtio_shutdown(struct vmd_vm *); 280 int virtio_dump(int); 281 int virtio_restore(int, struct vmd_vm *, int, 282 int[][VM_MAX_BASE_PER_DISK], int *); 283 uint32_t vring_size(uint32_t); 284 285 int virtio_rnd_io(int, uint16_t, uint32_t *, uint8_t *, void *, uint8_t); 286 int viornd_dump(int); 287 int viornd_restore(int, struct vm_create_params *); 288 void viornd_update_qs(void); 289 void viornd_update_qa(void); 290 int viornd_notifyq(void); 291 292 ssize_t virtio_qcow2_get_base(int, char *, size_t, const char *); 293 int virtio_qcow2_create(const char *, const char *, long); 294 int virtio_qcow2_init(struct virtio_backing *, off_t *, int*, size_t); 295 int virtio_raw_create(const char *, long); 296 int virtio_raw_init(struct virtio_backing *, off_t *, int*, size_t); 297 298 int virtio_blk_io(int, uint16_t, uint32_t *, uint8_t *, void *, uint8_t); 299 int vioblk_dump(int); 300 int vioblk_restore(int, struct vmop_create_params *, 301 int[][VM_MAX_BASE_PER_DISK]); 302 void vioblk_update_qs(struct vioblk_dev *); 303 void vioblk_update_qa(struct vioblk_dev *); 304 int vioblk_notifyq(struct vioblk_dev *); 305 306 int virtio_net_io(int, uint16_t, uint32_t *, uint8_t *, void *, uint8_t); 307 int vionet_dump(int); 308 int vionet_restore(int, struct vmd_vm *, int *); 309 void vionet_update_qs(struct vionet_dev *); 310 void vionet_update_qa(struct vionet_dev *); 311 int vionet_notifyq(struct vionet_dev *); 312 void vionet_notify_rx(struct vionet_dev *); 313 int vionet_notify_tx(struct vionet_dev *); 314 void vionet_process_rx(uint32_t); 315 int vionet_enq_rx(struct vionet_dev *, char *, size_t, int *); 316 void vionet_set_hostmac(struct vmd_vm *, unsigned int, uint8_t *); 317 318 int vmmci_io(int, uint16_t, uint32_t *, uint8_t *, void *, uint8_t); 319 int vmmci_dump(int); 320 int vmmci_restore(int, uint32_t); 321 int vmmci_ctl(unsigned int); 322 void vmmci_ack(unsigned int); 323 void vmmci_timeout(int, short, void *); 324 325 const char *vioblk_cmd_name(uint32_t); 326 int vioscsi_dump(int); 327 int vioscsi_restore(int, struct vm_create_params *, int); 328 329 /* dhcp.c */ 330 ssize_t dhcp_request(struct vionet_dev *, char *, size_t, char **); 331 332 /* vioscsi.c */ 333 int vioscsi_io(int, uint16_t, uint32_t *, uint8_t *, void *, uint8_t); 334 void vioscsi_update_qs(struct vioscsi_dev *); 335 void vioscsi_update_qa(struct vioscsi_dev *); 336 int vioscsi_notifyq(struct vioscsi_dev *); 337 void virtio_stop(struct vm_create_params *vcp); 338 void virtio_start(struct vm_create_params *vcp); 339 340 #endif /* _VIRTIO_H_ */ 341