GCC Code Coverage Report
Directory: ./ Exec Total Coverage
File: usr.sbin/vmd/vmd.h Lines: 0 1 0.0 %
Date: 2017-11-13 Branches: 0 0 0.0 %

Line Branch Exec Source
1
/*	$OpenBSD: vmd.h,v 1.66 2017/11/11 02:50:08 mlarkin 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
#include <sys/queue.h>
21
#include <sys/socket.h>
22
23
#include <machine/vmmvar.h>
24
25
#include <net/if.h>
26
#include <netinet/in.h>
27
#include <netinet/if_ether.h>
28
29
#include <limits.h>
30
#include <stdio.h>
31
#include <pthread.h>
32
33
#include "proc.h"
34
35
#ifndef VMD_H
36
#define VMD_H
37
38
#define SET(_v, _m)		((_v) |= (_m))
39
#define CLR(_v, _m)		((_v) &= ~(_m))
40
#define ISSET(_v, _m)		((_v) & (_m))
41
42
#define VMD_USER		"_vmd"
43
#define VMD_CONF		"/etc/vm.conf"
44
#define SOCKET_NAME		"/var/run/vmd.sock"
45
#define VMM_NODE		"/dev/vmm"
46
#define VM_DEFAULT_BIOS		"/etc/firmware/vmm-bios"
47
#define VM_DEFAULT_KERNEL	"/bsd"
48
#define VM_DEFAULT_DEVICE	"hd0a"
49
#define VM_BOOT_CONF		"/etc/boot.conf"
50
#define VM_NAME_MAX		64
51
#define VM_TTYNAME_MAX		16
52
#define MAX_TAP			256
53
#define NR_BACKLOG		5
54
#define VMD_SWITCH_TYPE		"bridge"
55
#define VM_DEFAULT_MEMORY	512
56
57
/* vmd -> vmctl error codes */
58
#define VMD_BIOS_MISSING	1001
59
#define VMD_DISK_MISSING	1002
60
#define VMD_DISK_INVALID	1003
61
#define VMD_VM_STOP_INVALID	1004
62
63
/* 100.64.0.0/10 from rfc6598 (IPv4 Prefix for Shared Address Space) */
64
#define VMD_DHCP_PREFIX		"100.64.0.0/10"
65
66
#ifdef VMD_DEBUG
67
#define dprintf(x...)   do { log_debug(x); } while(0)
68
#else
69
#define dprintf(x...)
70
#endif /* VMD_DEBUG */
71
72
enum imsg_type {
73
	IMSG_VMDOP_START_VM_REQUEST = IMSG_PROC_MAX,
74
	IMSG_VMDOP_START_VM_DISK,
75
	IMSG_VMDOP_START_VM_IF,
76
	IMSG_VMDOP_START_VM_END,
77
	IMSG_VMDOP_START_VM_RESPONSE,
78
	IMSG_VMDOP_PAUSE_VM,
79
	IMSG_VMDOP_PAUSE_VM_RESPONSE,
80
	IMSG_VMDOP_UNPAUSE_VM,
81
	IMSG_VMDOP_UNPAUSE_VM_RESPONSE,
82
	IMSG_VMDOP_SEND_VM_REQUEST,
83
	IMSG_VMDOP_SEND_VM_RESPONSE,
84
	IMSG_VMDOP_RECEIVE_VM_REQUEST,
85
	IMSG_VMDOP_RECEIVE_VM_RESPONSE,
86
	IMSG_VMDOP_RECEIVE_VM_END,
87
	IMSG_VMDOP_TERMINATE_VM_REQUEST,
88
	IMSG_VMDOP_TERMINATE_VM_RESPONSE,
89
	IMSG_VMDOP_TERMINATE_VM_EVENT,
90
	IMSG_VMDOP_GET_INFO_VM_REQUEST,
91
	IMSG_VMDOP_GET_INFO_VM_DATA,
92
	IMSG_VMDOP_GET_INFO_VM_END_DATA,
93
	IMSG_VMDOP_LOAD,
94
	IMSG_VMDOP_RELOAD,
95
	IMSG_VMDOP_PRIV_IFDESCR,
96
	IMSG_VMDOP_PRIV_IFADD,
97
	IMSG_VMDOP_PRIV_IFEXISTS,
98
	IMSG_VMDOP_PRIV_IFUP,
99
	IMSG_VMDOP_PRIV_IFDOWN,
100
	IMSG_VMDOP_PRIV_IFGROUP,
101
	IMSG_VMDOP_PRIV_IFADDR,
102
	IMSG_VMDOP_PRIV_IFRDOMAIN,
103
	IMSG_VMDOP_VM_SHUTDOWN,
104
	IMSG_VMDOP_VM_REBOOT,
105
	IMSG_VMDOP_CONFIG
106
};
107
108
struct vmop_result {
109
	int			 vmr_result;
110
	uint32_t		 vmr_id;
111
	pid_t			 vmr_pid;
112
	char			 vmr_ttyname[VM_TTYNAME_MAX];
113
};
114
115
struct vmop_info_result {
116
	struct vm_info_result	 vir_info;
117
	char			 vir_ttyname[VM_TTYNAME_MAX];
118
	uid_t			 vir_uid;
119
	int64_t			 vir_gid;
120
};
121
122
struct vmop_id {
123
	uint32_t		 vid_id;
124
	char			 vid_name[VMM_MAX_NAME_LEN];
125
	uid_t			 vid_uid;
126
};
127
128
struct vmop_ifreq {
129
	uint32_t		 vfr_id;
130
	char			 vfr_name[IF_NAMESIZE];
131
	char			 vfr_value[VM_NAME_MAX];
132
	struct ifaliasreq	 vfr_ifra;
133
};
134
135
struct vmop_create_params {
136
	struct vm_create_params	 vmc_params;
137
	unsigned int		 vmc_flags;
138
#define VMOP_CREATE_KERNEL	0x01
139
#define VMOP_CREATE_MEMORY	0x02
140
#define VMOP_CREATE_NETWORK	0x04
141
#define VMOP_CREATE_DISK	0x08
142
143
	/* userland-only part of the create params */
144
	unsigned int		 vmc_ifflags[VMM_MAX_NICS_PER_VM];
145
#define VMIFF_UP		0x01
146
#define VMIFF_LOCKED		0x02
147
#define VMIFF_LOCAL		0x04
148
#define VMIFF_RDOMAIN		0x08
149
#define VMIFF_OPTMASK		(VMIFF_LOCKED|VMIFF_LOCAL|VMIFF_RDOMAIN)
150
	char			 vmc_ifnames[VMM_MAX_NICS_PER_VM][IF_NAMESIZE];
151
	char			 vmc_ifswitch[VMM_MAX_NICS_PER_VM][VM_NAME_MAX];
152
	char			 vmc_ifgroup[VMM_MAX_NICS_PER_VM][IF_NAMESIZE];
153
	unsigned int		 vmc_ifrdomain[VMM_MAX_NICS_PER_VM];
154
	uid_t			 vmc_uid;
155
	int64_t			 vmc_gid;
156
};
157
158
struct vm_dump_header_cpuid {
159
	unsigned long code, leaf;
160
	unsigned int a, b, c, d;
161
};
162
163
#define VM_DUMP_HEADER_CPUID_COUNT	5
164
165
struct vm_dump_header {
166
	uint8_t			 vmh_signature[12];
167
#define VM_DUMP_SIGNATURE	 VMM_HV_SIGNATURE
168
	uint8_t			 vmh_pad[3];
169
	uint8_t			 vmh_version;
170
#define VM_DUMP_VERSION		 2
171
	struct			 vm_dump_header_cpuid
172
	    vmh_cpuids[VM_DUMP_HEADER_CPUID_COUNT];
173
} __packed;
174
175
struct vmboot_params {
176
	int			 vbp_fd;
177
	off_t			 vbp_partoff;
178
	char			 vbp_device[PATH_MAX];
179
	char			 vbp_image[PATH_MAX];
180
	uint32_t		 vbp_bootdev;
181
	uint32_t		 vbp_howto;
182
	char			*vbp_arg;
183
};
184
185
struct vmd_if {
186
	char			*vif_name;
187
	char			*vif_switch;
188
	char			*vif_group;
189
	int			 vif_fd;
190
	unsigned int		 vif_rdomain;
191
	unsigned int		 vif_flags;
192
	TAILQ_ENTRY(vmd_if)	 vif_entry;
193
};
194
195
struct vmd_switch {
196
	uint32_t		 sw_id;
197
	char			*sw_name;
198
	char			 sw_ifname[IF_NAMESIZE];
199
	char			*sw_group;
200
	unsigned int		 sw_rdomain;
201
	unsigned int		 sw_flags;
202
	int			 sw_running;
203
	TAILQ_ENTRY(vmd_switch)	 sw_entry;
204
};
205
TAILQ_HEAD(switchlist, vmd_switch);
206
207
struct vmd_vm {
208
	struct vmop_create_params vm_params;
209
	pid_t			 vm_pid;
210
	uint32_t		 vm_vmid;
211
	int			 vm_kernel;
212
	int			 vm_disks[VMM_MAX_DISKS_PER_VM];
213
	struct vmd_if		 vm_ifs[VMM_MAX_NICS_PER_VM];
214
	char			*vm_ttyname;
215
	int			 vm_tty;
216
	uint32_t		 vm_peerid;
217
	/* When set, VM is running now (PROC_PARENT only) */
218
	int			 vm_running;
219
	/* When set, VM is not started by default (PROC_PARENT only) */
220
	int			 vm_disabled;
221
	/* When set, VM was defined in a config file */
222
	int			 vm_from_config;
223
	struct imsgev		 vm_iev;
224
	int			 vm_shutdown;
225
	uid_t			 vm_uid;
226
	int			 vm_received;
227
	int			 vm_paused;
228
	int			 vm_receive_fd;
229
230
	TAILQ_ENTRY(vmd_vm)	 vm_entry;
231
};
232
TAILQ_HEAD(vmlist, vmd_vm);
233
234
struct address {
235
	struct sockaddr_storage	 ss;
236
	int			 prefixlen;
237
	TAILQ_ENTRY(address)	 entry;
238
};
239
TAILQ_HEAD(addresslist, address);
240
241
struct vmd_config {
242
	struct address		 cfg_localprefix;
243
};
244
245
struct vmd {
246
	struct privsep		 vmd_ps;
247
	const char		*vmd_conffile;
248
249
	/* global configuration that is sent to the children */
250
	struct vmd_config	 vmd_cfg;
251
252
	int			 vmd_debug;
253
	int			 vmd_verbose;
254
	int			 vmd_noaction;
255
256
	uint32_t		 vmd_nvm;
257
	struct vmlist		*vmd_vms;
258
	uint32_t		 vmd_nswitches;
259
	struct switchlist	*vmd_switches;
260
261
	int			 vmd_fd;
262
	int			 vmd_ptmfd;
263
};
264
265
static inline struct sockaddr_in *
266
ss2sin(struct sockaddr_storage *ss)
267
{
268
	return ((struct sockaddr_in *)ss);
269
}
270
271
static inline struct sockaddr_in6 *
272
ss2sin6(struct sockaddr_storage *ss)
273
{
274
	return ((struct sockaddr_in6 *)ss);
275
}
276
277
struct packet_ctx {
278
	uint8_t			 pc_htype;
279
	uint8_t			 pc_hlen;
280
	uint8_t			 pc_smac[ETHER_ADDR_LEN];
281
	uint8_t			 pc_dmac[ETHER_ADDR_LEN];
282
283
	struct sockaddr_storage	 pc_src;
284
	struct sockaddr_storage	 pc_dst;
285
};
286
287
/* packet.c */
288
ssize_t	 assemble_hw_header(unsigned char *, size_t, size_t,
289
	    struct packet_ctx *, unsigned int);
290
ssize_t	 assemble_udp_ip_header(unsigned char *, size_t, size_t,
291
	    struct packet_ctx *pc, unsigned char *, size_t);
292
ssize_t	 decode_hw_header(unsigned char *, size_t, size_t, struct packet_ctx *,
293
	    unsigned int);
294
ssize_t	 decode_udp_ip_header(unsigned char *, size_t, size_t,
295
	    struct packet_ctx *);
296
297
/* vmd.c */
298
int	 vmd_reload(unsigned int, const char *);
299
struct vmd_vm *vm_getbyid(uint32_t);
300
struct vmd_vm *vm_getbyvmid(uint32_t);
301
uint32_t vm_id2vmid(uint32_t, struct vmd_vm *);
302
uint32_t vm_vmid2id(uint32_t, struct vmd_vm *);
303
struct vmd_vm *vm_getbyname(const char *);
304
struct vmd_vm *vm_getbypid(pid_t);
305
void	 vm_stop(struct vmd_vm *, int);
306
void	 vm_remove(struct vmd_vm *);
307
int	 vm_register(struct privsep *, struct vmop_create_params *,
308
	    struct vmd_vm **, uint32_t, uid_t);
309
int	 vm_checkperm(struct vmd_vm *, uid_t);
310
int	 vm_opentty(struct vmd_vm *);
311
void	 vm_closetty(struct vmd_vm *);
312
void	 switch_remove(struct vmd_switch *);
313
struct vmd_switch *switch_getbyname(const char *);
314
char	*get_string(uint8_t *, size_t);
315
uint32_t prefixlen2mask(uint8_t);
316
317
/* priv.c */
318
void	 priv(struct privsep *, struct privsep_proc *);
319
int	 priv_getiftype(char *, char *, unsigned int *);
320
int	 priv_findname(const char *, const char **);
321
int	 priv_validgroup(const char *);
322
int	 vm_priv_ifconfig(struct privsep *, struct vmd_vm *);
323
int	 vm_priv_brconfig(struct privsep *, struct vmd_switch *);
324
uint32_t vm_priv_addr(struct address *, uint32_t, int, int);
325
326
/* vmm.c */
327
struct iovec;
328
329
void	 vmm(struct privsep *, struct privsep_proc *);
330
void	 vmm_shutdown(void);
331
void	*vaddr_mem(paddr_t, size_t);
332
int	 write_mem(paddr_t, const void *buf, size_t);
333
int	 read_mem(paddr_t, void *buf, size_t);
334
int	 iovec_mem(paddr_t, size_t, struct iovec *, int);
335
int	 opentap(char *);
336
int	 fd_hasdata(int);
337
void	 mutex_lock(pthread_mutex_t *);
338
void	 mutex_unlock(pthread_mutex_t *);
339
int	 vmm_pipe(struct vmd_vm *, int, void (*)(int, short, void *));
340
341
/* vm.c */
342
int	 start_vm(struct vmd_vm *, int);
343
int receive_vm(struct vmd_vm *, int, int);
344
__dead void vm_shutdown(unsigned int);
345
346
/* control.c */
347
int	 config_init(struct vmd *);
348
void	 config_purge(struct vmd *, unsigned int);
349
int	 config_setconfig(struct vmd *);
350
int	 config_getconfig(struct vmd *, struct imsg *);
351
int	 config_setreset(struct vmd *, unsigned int);
352
int	 config_getreset(struct vmd *, struct imsg *);
353
int	 config_setvm(struct privsep *, struct vmd_vm *, uint32_t, uid_t);
354
int	 config_getvm(struct privsep *, struct imsg *);
355
int	 config_getdisk(struct privsep *, struct imsg *);
356
int	 config_getif(struct privsep *, struct imsg *);
357
358
/* vmboot.c */
359
FILE	*vmboot_open(int, int, struct vmboot_params *);
360
void	 vmboot_close(FILE *, struct vmboot_params *);
361
362
/* parse.y */
363
int	 parse_config(const char *);
364
int	 cmdline_symset(char *);
365
int	 host(const char *, struct address *);
366
367
#endif /* VMD_H */