mirror of
https://gitlab.com/libvirt/libvirt.git
synced 2025-02-22 03:12:22 +00:00
Implement support for virtio plan9fs filesystem passthrough in QEMU
Make use of the existing <filesystem> element to support plan9fs filesystem passthrough in the QEMU driver <filesystem type='mount'> <source dir='/export/to/guest'/> <target dir='/import/from/host'/> </filesystem> NB, the target is not actually a directory, it is merely a arbitrary string tag that is exported to the guest as a hint for where to mount it.
This commit is contained in:
parent
458c99b121
commit
a5c646a770
@ -1213,6 +1213,8 @@ static unsigned long long qemudComputeCmdFlags(const char *help,
|
||||
flags |= QEMUD_CMD_FLAG_TDF;
|
||||
if (strstr(help, ",menu=on"))
|
||||
flags |= QEMUD_CMD_FLAG_BOOT_MENU;
|
||||
if (strstr(help, "-fsdev"))
|
||||
flags |= QEMUD_CMD_FLAG_FSDEV;
|
||||
|
||||
/* Keep disabled till we're actually ready to turn on netdev mode
|
||||
* The plan is todo it in 0.13.0 QEMU, but lets wait & see... */
|
||||
@ -2012,6 +2014,10 @@ qemuAssignDeviceAliases(virDomainDefPtr def, unsigned long long qemuCmdFlags)
|
||||
if (!(qemuCmdFlags & QEMUD_CMD_FLAG_DEVICE))
|
||||
return 0;
|
||||
|
||||
for (i = 0; i < def->nfss ; i++) {
|
||||
if (virAsprintf(&def->fss[i]->info.alias, "fs%d", i) < 0)
|
||||
goto no_memory;
|
||||
}
|
||||
for (i = 0; i < def->nsounds ; i++) {
|
||||
if (virAsprintf(&def->sounds[i]->info.alias, "sound%d", i) < 0)
|
||||
goto no_memory;
|
||||
@ -2375,6 +2381,15 @@ qemuAssignDevicePCISlots(virDomainDefPtr def, qemuDomainPCIAddressSetPtr addrs)
|
||||
goto error;
|
||||
}
|
||||
}
|
||||
for (i = 0; i < def->nfss ; i++) {
|
||||
if (def->fss[i]->info.type != VIR_DOMAIN_DEVICE_ADDRESS_TYPE_NONE)
|
||||
continue;
|
||||
|
||||
/* Only support VirtIO-9p-pci so far. If that changes,
|
||||
* we might need to skip devices here */
|
||||
if (qemuDomainPCIAddressSetNextAddr(addrs, &def->fss[i]->info) < 0)
|
||||
goto error;
|
||||
}
|
||||
|
||||
/* Network interfaces */
|
||||
for (i = 0; i < def->nnets ; i++) {
|
||||
@ -2765,6 +2780,64 @@ error:
|
||||
}
|
||||
|
||||
|
||||
char *qemuBuildFSStr(virDomainFSDefPtr fs,
|
||||
unsigned long long qemuCmdFlags ATTRIBUTE_UNUSED)
|
||||
{
|
||||
virBuffer opt = VIR_BUFFER_INITIALIZER;
|
||||
|
||||
if (fs->type != VIR_DOMAIN_FS_TYPE_MOUNT) {
|
||||
qemuReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
|
||||
_("can only passthrough directories"));
|
||||
goto error;
|
||||
}
|
||||
|
||||
virBufferAddLit(&opt, "local,security_model=passthrough");
|
||||
virBufferVSprintf(&opt, ",id=%s%s", QEMU_FSDEV_HOST_PREFIX, fs->info.alias);
|
||||
virBufferVSprintf(&opt, ",path=%s", fs->src);
|
||||
|
||||
if (virBufferError(&opt)) {
|
||||
virReportOOMError();
|
||||
goto error;
|
||||
}
|
||||
|
||||
return virBufferContentAndReset(&opt);
|
||||
|
||||
error:
|
||||
virBufferFreeAndReset(&opt);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
char *
|
||||
qemuBuildFSDevStr(virDomainFSDefPtr fs)
|
||||
{
|
||||
virBuffer opt = VIR_BUFFER_INITIALIZER;
|
||||
|
||||
if (fs->type != VIR_DOMAIN_FS_TYPE_MOUNT) {
|
||||
qemuReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
|
||||
_("can only passthrough directories"));
|
||||
goto error;
|
||||
}
|
||||
|
||||
virBufferAddLit(&opt, "virtio-9p-pci");
|
||||
virBufferVSprintf(&opt, ",id=%s", fs->info.alias);
|
||||
virBufferVSprintf(&opt, ",fsdev=%s%s", QEMU_FSDEV_HOST_PREFIX, fs->info.alias);
|
||||
virBufferVSprintf(&opt, ",mount_tag=%s", fs->dst);
|
||||
qemuBuildDeviceAddressStr(&opt, &fs->info);
|
||||
|
||||
if (virBufferError(&opt)) {
|
||||
virReportOOMError();
|
||||
goto error;
|
||||
}
|
||||
|
||||
return virBufferContentAndReset(&opt);
|
||||
|
||||
error:
|
||||
virBufferFreeAndReset(&opt);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
char *
|
||||
qemuBuildControllerDevStr(virDomainControllerDefPtr def)
|
||||
{
|
||||
@ -4381,6 +4454,29 @@ int qemudBuildCommandLine(virConnectPtr conn,
|
||||
}
|
||||
}
|
||||
|
||||
if (qemuCmdFlags & QEMUD_CMD_FLAG_FSDEV) {
|
||||
for (i = 0 ; i < def->nfss ; i++) {
|
||||
char *optstr;
|
||||
virDomainFSDefPtr fs = def->fss[i];
|
||||
|
||||
ADD_ARG_LIT("-fsdev");
|
||||
if (!(optstr = qemuBuildFSStr(fs, qemuCmdFlags)))
|
||||
goto error;
|
||||
ADD_ARG(optstr);
|
||||
|
||||
ADD_ARG_LIT("-device");
|
||||
if (!(optstr = qemuBuildFSDevStr(fs)))
|
||||
goto error;
|
||||
ADD_ARG(optstr);
|
||||
}
|
||||
} else {
|
||||
if (def->nfss) {
|
||||
qemuReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
|
||||
_("filesystem passthrough not supported by this QEMU"));
|
||||
goto error;
|
||||
}
|
||||
}
|
||||
|
||||
if (!def->nnets) {
|
||||
/* If we have -device, then we set -nodefault already */
|
||||
if (!(qemuCmdFlags & QEMUD_CMD_FLAG_DEVICE)) {
|
||||
|
@ -93,6 +93,7 @@ enum qemud_cmd_flags {
|
||||
QEMUD_CMD_FLAG_NODEFCONFIG = (1LL << 37), /* -nodefconfig */
|
||||
QEMUD_CMD_FLAG_BOOT_MENU = (1LL << 38), /* -boot menu=on support */
|
||||
QEMUD_CMD_FLAG_ENABLE_KQEMU = (1LL << 39), /* -enable-kqemu flag */
|
||||
QEMUD_CMD_FLAG_FSDEV = (1LL << 40), /* -fstype filesystem passthrough */
|
||||
};
|
||||
|
||||
/* Main driver state */
|
||||
@ -188,6 +189,7 @@ struct _qemuDomainCmdlineDef {
|
||||
|
||||
# define QEMU_DRIVE_HOST_PREFIX "drive-"
|
||||
# define QEMU_VIRTIO_SERIAL_PREFIX "virtio-serial"
|
||||
# define QEMU_FSDEV_HOST_PREFIX "fsdev-"
|
||||
|
||||
# define qemuReportError(code, ...) \
|
||||
virReportErrorHelper(NULL, VIR_FROM_QEMU, code, __FILE__, \
|
||||
@ -248,9 +250,12 @@ char *qemuDeviceDriveHostAlias(virDomainDiskDefPtr disk,
|
||||
char *qemuBuildDriveStr(virDomainDiskDefPtr disk,
|
||||
int bootable,
|
||||
unsigned long long qemuCmdFlags);
|
||||
char *qemuBuildFSStr(virDomainFSDefPtr fs,
|
||||
unsigned long long qemuCmdFlags);
|
||||
|
||||
/* Current, best practice */
|
||||
char * qemuBuildDriveDevStr(virDomainDiskDefPtr disk);
|
||||
char * qemuBuildFSDevStr(virDomainFSDefPtr fs);
|
||||
/* Current, best practice */
|
||||
char * qemuBuildControllerDevStr(virDomainControllerDefPtr def);
|
||||
|
||||
|
1
tests/qemuxml2argvdata/qemuxml2argv-fs9p.args
Normal file
1
tests/qemuxml2argvdata/qemuxml2argv-fs9p.args
Normal file
@ -0,0 +1 @@
|
||||
LC_ALL=C PATH=/bin HOME=/home/test USER=test LOGNAME=test /usr/bin/qemu -S -M pc -m 214 -smp 1 -nographic -nodefconfig -nodefaults -monitor unix:/tmp/test-monitor,server,nowait -no-acpi -boot c -hda /dev/HostVG/QEMUGuest1 -fsdev local,security_model=passthrough,id=fsdev-fs0,path=/export/to/guest -device virtio-9p-pci,id=fs0,fsdev=fsdev-fs0,mount_tag=/import/from/host,bus=pci.0,addr=0x2 -usb -device virtio-balloon-pci,id=balloon0,bus=pci.0,addr=0x3
|
28
tests/qemuxml2argvdata/qemuxml2argv-fs9p.xml
Normal file
28
tests/qemuxml2argvdata/qemuxml2argv-fs9p.xml
Normal file
@ -0,0 +1,28 @@
|
||||
<domain type='qemu'>
|
||||
<name>QEMUGuest1</name>
|
||||
<uuid>c7a5fdbd-edaf-9455-926a-d65c16db1809</uuid>
|
||||
<memory>219200</memory>
|
||||
<currentMemory>219200</currentMemory>
|
||||
<vcpu>1</vcpu>
|
||||
<os>
|
||||
<type arch='i686' machine='pc'>hvm</type>
|
||||
<boot dev='hd'/>
|
||||
</os>
|
||||
<clock offset='utc'/>
|
||||
<on_poweroff>destroy</on_poweroff>
|
||||
<on_reboot>restart</on_reboot>
|
||||
<on_crash>destroy</on_crash>
|
||||
<devices>
|
||||
<emulator>/usr/bin/qemu</emulator>
|
||||
<disk type='block' device='disk'>
|
||||
<source dev='/dev/HostVG/QEMUGuest1'/>
|
||||
<target dev='hda' bus='ide'/>
|
||||
<address type='drive' controller='0' bus='0' unit='0'/>
|
||||
</disk>
|
||||
<controller type='ide' index='0'/>
|
||||
<filesystem type='mount'>
|
||||
<source dir='/export/to/guest'/>
|
||||
<target dir='/import/from/host'/>
|
||||
</filesystem>
|
||||
</devices>
|
||||
</domain>
|
@ -368,6 +368,8 @@ mymain(int argc, char **argv)
|
||||
DO_TEST("sound", 0);
|
||||
DO_TEST("sound-device", QEMUD_CMD_FLAG_DEVICE |
|
||||
QEMUD_CMD_FLAG_NODEFCONFIG);
|
||||
DO_TEST("fs9p", QEMUD_CMD_FLAG_DEVICE |
|
||||
QEMUD_CMD_FLAG_NODEFCONFIG | QEMUD_CMD_FLAG_FSDEV);
|
||||
|
||||
DO_TEST("hostdev-usb-address", 0);
|
||||
DO_TEST("hostdev-usb-address-device", QEMUD_CMD_FLAG_DEVICE |
|
||||
|
Loading…
x
Reference in New Issue
Block a user