diff options
-rw-r--r-- | usr.sbin/vmctl/vmctl.c | 43 | ||||
-rw-r--r-- | usr.sbin/vmd/parse.y | 8 | ||||
-rw-r--r-- | usr.sbin/vmd/vmd.c | 21 | ||||
-rw-r--r-- | usr.sbin/vmd/vmd.h | 7 |
4 files changed, 59 insertions, 20 deletions
diff --git a/usr.sbin/vmctl/vmctl.c b/usr.sbin/vmctl/vmctl.c index 3e845563979..352383c299f 100644 --- a/usr.sbin/vmctl/vmctl.c +++ b/usr.sbin/vmctl/vmctl.c @@ -1,4 +1,4 @@ -/* $OpenBSD: vmctl.c,v 1.20 2016/11/26 19:49:11 reyk Exp $ */ +/* $OpenBSD: vmctl.c,v 1.21 2016/12/14 21:17:25 reyk Exp $ */ /* * Copyright (c) 2014 Mike Larkin <mlarkin@openbsd.org> @@ -67,27 +67,40 @@ start_vm(const char *name, int memsize, int nnics, char **nics, { struct vmop_create_params *vmc; struct vm_create_params *vcp; + unsigned int flags = 0; int i; - if (memsize < 1) - memsize = VM_DEFAULT_MEMORY; - if (ndisks > VMM_MAX_DISKS_PER_VM) - errx(1, "too many disks"); - else if (ndisks == 0) - warnx("starting without disks"); - if (kernel == NULL && ndisks == 0) - errx(1, "no kernel or disk specified"); - if (nnics == -1) - nnics = 0; - if (nnics > VMM_MAX_NICS_PER_VM) - errx(1, "too many network interfaces"); - if (nnics == 0) - warnx("starting without network interfaces"); + if (memsize) + flags |= VMOP_CREATE_MEMORY; + if (nnics) + flags |= VMOP_CREATE_NETWORK; + if (ndisks) + flags |= VMOP_CREATE_DISK; + if (kernel) + flags |= VMOP_CREATE_KERNEL; + if (flags != 0) { + if (memsize < 1) + memsize = VM_DEFAULT_MEMORY; + if (ndisks > VMM_MAX_DISKS_PER_VM) + errx(1, "too many disks"); + else if (ndisks == 0) + warnx("starting without disks"); + if (kernel == NULL && ndisks == 0) + errx(1, "no kernel or disk specified"); + if (nnics == -1) + nnics = 0; + if (nnics > VMM_MAX_NICS_PER_VM) + errx(1, "too many network interfaces"); + if (nnics == 0) + warnx("starting without network interfaces"); + } vmc = calloc(1, sizeof(struct vmop_create_params)); if (vmc == NULL) return (ENOMEM); + vmc->vmc_flags = flags; + /* vcp includes configuration that is shared with the kernel */ vcp = &vmc->vmc_params; diff --git a/usr.sbin/vmd/parse.y b/usr.sbin/vmd/parse.y index 691f7c8e2b6..6cf06b02f44 100644 --- a/usr.sbin/vmd/parse.y +++ b/usr.sbin/vmd/parse.y @@ -1,4 +1,4 @@ -/* $OpenBSD: parse.y,v 1.16 2016/11/22 11:31:38 edd Exp $ */ +/* $OpenBSD: parse.y,v 1.17 2016/12/14 21:17:25 reyk Exp $ */ /* * Copyright (c) 2007-2016 Reyk Floeter <reyk@openbsd.org> @@ -306,6 +306,7 @@ vm_opts : disable { YYERROR; } free($2); + vmc.vmc_flags |= VMOP_CREATE_DISK; } | INTERFACE optstring iface_opts_o { unsigned int i; @@ -337,6 +338,7 @@ vm_opts : disable { } } free($2); + vmc.vmc_flags |= VMOP_CREATE_NETWORK; } | KERNEL string { if (vcp->vcp_kernel[0] != '\0') { @@ -353,6 +355,7 @@ vm_opts : disable { YYERROR; } free($2); + vmc.vmc_flags |= VMOP_CREATE_KERNEL; } | NIFS NUMBER { if (vcp->vcp_nnics != 0) { @@ -364,6 +367,7 @@ vm_opts : disable { YYERROR; } vcp->vcp_nnics = (size_t)$2; + vmc.vmc_flags |= VMOP_CREATE_NETWORK; } | MEMORY NUMBER { ssize_t res; @@ -376,6 +380,7 @@ vm_opts : disable { YYERROR; } vcp->vcp_memranges[0].vmr_size = (size_t)res; + vmc.vmc_flags |= VMOP_CREATE_MEMORY; } | MEMORY STRING { ssize_t res; @@ -390,6 +395,7 @@ vm_opts : disable { YYERROR; } vcp->vcp_memranges[0].vmr_size = (size_t)res; + vmc.vmc_flags |= VMOP_CREATE_MEMORY; } ; diff --git a/usr.sbin/vmd/vmd.c b/usr.sbin/vmd/vmd.c index d572784bb05..26de91144d4 100644 --- a/usr.sbin/vmd/vmd.c +++ b/usr.sbin/vmd/vmd.c @@ -1,4 +1,4 @@ -/* $OpenBSD: vmd.c,v 1.46 2016/12/14 06:59:12 reyk Exp $ */ +/* $OpenBSD: vmd.c,v 1.47 2016/12/14 21:17:25 reyk Exp $ */ /* * Copyright (c) 2015 Reyk Floeter <reyk@openbsd.org> @@ -65,7 +65,7 @@ int vmd_dispatch_control(int fd, struct privsep_proc *p, struct imsg *imsg) { struct privsep *ps = p->p_ps; - int res = 0, cmd = 0; + int res = 0, ret = 0, cmd = 0; unsigned int v = 0; struct vmop_create_params vmc; struct vmop_id vid; @@ -79,7 +79,18 @@ vmd_dispatch_control(int fd, struct privsep_proc *p, struct imsg *imsg) case IMSG_VMDOP_START_VM_REQUEST: IMSG_SIZE_CHECK(imsg, &vmc); memcpy(&vmc, imsg->data, sizeof(vmc)); - if (vm_register(ps, &vmc, &vm, 0) == -1 || + ret = vm_register(ps, &vmc, &vm, 0); + if (vmc.vmc_flags == 0) { + /* start an existing VM with pre-configured options */ + if (!(ret == -1 && errno == EALREADY)) { + res = errno; + cmd = IMSG_VMDOP_START_VM_RESPONSE; + } + } else if (ret != 0) { + res = errno; + cmd = IMSG_VMDOP_START_VM_RESPONSE; + } + if (res == 0 && config_setvm(ps, vm, imsg->hdr.peerid) == -1) { res = errno; cmd = IMSG_VMDOP_START_VM_RESPONSE; @@ -698,6 +709,10 @@ vm_register(struct privsep *ps, struct vmop_create_params *vmc, goto fail; } + if (vmc->vmc_flags == 0) { + errno = ENOENT; + goto fail; + } if (vcp->vcp_ncpus == 0) vcp->vcp_ncpus = 1; if (vcp->vcp_memranges[0].vmr_size == 0) diff --git a/usr.sbin/vmd/vmd.h b/usr.sbin/vmd/vmd.h index 5053db79b5b..499f64388c8 100644 --- a/usr.sbin/vmd/vmd.h +++ b/usr.sbin/vmd/vmd.h @@ -1,4 +1,4 @@ -/* $OpenBSD: vmd.h,v 1.39 2016/12/14 06:59:12 reyk Exp $ */ +/* $OpenBSD: vmd.h,v 1.40 2016/12/14 21:17:25 reyk Exp $ */ /* * Copyright (c) 2015 Mike Larkin <mlarkin@openbsd.org> @@ -100,6 +100,11 @@ struct vmop_ifreq { struct vmop_create_params { struct vm_create_params vmc_params; + unsigned int vmc_flags; +#define VMOP_CREATE_KERNEL 0x01 +#define VMOP_CREATE_MEMORY 0x02 +#define VMOP_CREATE_NETWORK 0x04 +#define VMOP_CREATE_DISK 0x08 /* userland-only part of the create params */ unsigned int vmc_ifflags[VMM_MAX_NICS_PER_VM]; |