VMchannel Requirements: Difference between revisions
(Update TODO: hot-unplug done) |
(Update for latest rev of patches: devices are now at /dev/vport0p1..) |
||
Line 84: | Line 84: | ||
<pre> | <pre> | ||
/dev/ | /dev/vport0p1 | ||
/dev/ | /dev/vport0p2 | ||
/dev/ | /dev/vport0p3 | ||
</pre> | </pre> | ||
Line 92: | Line 92: | ||
* cache_buffers: default 1. This property specifies whether ports retain data received when the char device is closed on the guest or when the qemu chardev connection is closed on the host. | * cache_buffers: default 1. This property specifies whether ports retain data received when the char device is closed on the guest or when the qemu chardev connection is closed on the host. | ||
* byte_limit | * byte_limit: This property specifies the max. number of bytes that can be cached before no more data is pushed out. This is to prevent OOM conditions from happening inside the host. The guest doesn't need this mechanism as the number of outstanding buffers are controlled by the host when it initializes the virtqueues. | ||
* name: This property puts the string in the guest's sysfs entries for it to be found by udev rules to create symlinks to the actual device. This is useful for guest applications discovering the ports of their interest. For example, | * name: This property puts the string in the guest's sysfs entries for it to be found by udev rules to create symlinks to the actual device. This is useful for guest applications discovering the ports of their interest. For example, | ||
<pre> | <pre> | ||
$ cat /sys/class/virtio- | $ cat /sys/class/virtio-ports/vport0p1/name | ||
org.linux-kvm.port.0 | org.linux-kvm.port.0 | ||
$ | $ | ||
</pre> | </pre> | ||
A simple udev rule can create a symlink to the actual device from this name: eg, create a new file in <code>/etc/udev/rules.d</code>, eg, <code>90-virtio- | A simple udev rule can create a symlink to the actual device from this name: eg, create a new file in <code>/etc/udev/rules.d</code>, eg, <code>90-virtio-ports</code>. Put the following code in it: | ||
<pre> | <pre> | ||
KERNEL==" | KERNEL=="vport*", SYMLINK+="virtio-ports/$ATTR{name}" | ||
</pre> | </pre> | ||
In the above example, a symlink, <code>/dev/virtio- | In the above example, a symlink, <code>/dev/virtio-ports/org.linux-kvm.port.0</code> will be created that points to <code>/dev/vport0p1</code> | ||
Line 138: | Line 138: | ||
A few items from my TODO list. Please drop me a note at <amit.shah@redhat.com> if you're planning to pick something from here so that there's no duplication of work. Thanks! | A few items from my TODO list. Please drop me a note at <amit.shah@redhat.com> if you're planning to pick something from here so that there's no duplication of work. Thanks! | ||
* Guest kernel driver | * Guest kernel driver | ||
** | ** Allow module removal | ||
* Host device | * Host device | ||
** Convert to VMState | ** Convert to VMState | ||
** Generic chardev infrastructure: During migration, make sure if the other endpoint didn't receive data, resend it | ** Generic chardev infrastructure: During migration, make sure if the other endpoint didn't receive data, resend it |
Revision as of 01:12, 23 December 2009
Requirements
- We want an interface between the guest and the host
- The channel is to be used for simple communication, like sharing of the clipboard between the user desktop and the guest desktop
- For relatively low rate of data transfer -- a few MB/s
- Events to be delivered to the guest, like 'shutdown', 'reboot', 'logoff'
- Queries to the guest, like 'which users are logged in'
- Survive live migration
- Support for multiple agents (consumers of the data) on the guest
- Multiple channels could be opened at the same time
- In multi-channels case, one blocked channel shouldn't block communication between others (or one channel shouldn't hog all the bandwidth)
- Stable ABI (for future upgrades)
- Channel addressing
- An agent in the guest should be able to find the channel it's interested in
- Dynamic channel creation
- Security
- No threats to the host
- Unprivileged user should be able to use the channel
- Should work out of the box, without any configuration necessary on the part of the guest
- Notifications of channels being added / removed (hotplugging)
- Notifications on connection / disconnection on guest as well as host side
- An API inside qemu to communicate with agents in the guest
History
A few reasons why the obvious solutions do not work:
- via the fully emulated serial device.
- performance (exit per byte)
- scalability - only 4 serial ports per guest
- accessed by root only in the guest
- via TCP/IP network sockets
- The guest may not have networking enabled
- The guest firewall may block access to the host IPs
- Windows can't bind sockets to specific ethernet interfaces
- via slirp
This implementation does exist upstream as "-net channel" http://www.nabble.com/-PATCH--specify-vmchannel-as-a-net-option-td21911523.html- Again, based on networking so same drawbacks mentioned above apply
- Currently used by libguestfs
Use Cases
- Guest - Host clipboard copy/paste operations
- By a VMM or via an internal API within qemu
- libguestfs (offline usage)
- For poking inside a guest to fetch the list of installed apps, etc.
- Online usage
- Locking desktop session when vnc session is closed
- Cluster I/O Fencing aka STONITH
- Current models require networking between guest/host
- fence_virsh, xen0 -> ssh to defined host and to perform fencing; no migration tracking; requires ssh key distribution to work.
- fence_xvm -> tracks migrations, but requires multicast between guest/host; distributed key recommended but not required
- Using VMChannel-Serial, the requirement of guest-host can be avoided
- Key distribution of any sort can be avoided, making this easier to configure than existing solutions
- Current models require networking between guest/host
Invocation
The virtio-console code is extended to spawn multiple serial ports inside the guest. Creating the serial ports on the host looks like this:
-device virtio-serial-pci \ -device virtserialport,chardev=...,name=org.linux-kvm.port.0 \ -device virtserialport,chardev=...,name=org.linux-kvm.port.1,cache_buffers=0 \ -device virtserialport,chardev=...,name=org.linux-kvm.port.2,byte_limit=1048576
This creates three ports. The guest sees them as:
/dev/vport0p1 /dev/vport0p2 /dev/vport0p3
The ports are assigned some properties:
- cache_buffers: default 1. This property specifies whether ports retain data received when the char device is closed on the guest or when the qemu chardev connection is closed on the host.
- byte_limit: This property specifies the max. number of bytes that can be cached before no more data is pushed out. This is to prevent OOM conditions from happening inside the host. The guest doesn't need this mechanism as the number of outstanding buffers are controlled by the host when it initializes the virtqueues.
- name: This property puts the string in the guest's sysfs entries for it to be found by udev rules to create symlinks to the actual device. This is useful for guest applications discovering the ports of their interest. For example,
$ cat /sys/class/virtio-ports/vport0p1/name org.linux-kvm.port.0 $
A simple udev rule can create a symlink to the actual device from this name: eg, create a new file in /etc/udev/rules.d
, eg, 90-virtio-ports
. Put the following code in it:
KERNEL=="vport*", SYMLINK+="virtio-ports/$ATTR{name}"
In the above example, a symlink, /dev/virtio-ports/org.linux-kvm.port.0
will be created that points to /dev/vport0p1
To create console ports, use:
-device virtio-serial-pci \ -device virtconsole,chardev=...,name=console.0
You can then spawn a tty on this console port from the guest:
# agetty /dev/hvc0 9600 vt100
Multiple console ports can be specified on the command line and they will be available as /dev/hvc0, /dev/hvc1...
Testing
A repository containing test code is put up at
http://fedorapeople.org/gitweb?p=amitshah/public_git/test-virtserial.git
This repo contains manual as well as automated testsuites that can be run to verify the functionality. The test-virtserial.c file also documents the various options and the ways in which they can be tested.
TODO
A few items from my TODO list. Please drop me a note at <amit.shah@redhat.com> if you're planning to pick something from here so that there's no duplication of work. Thanks!
- Guest kernel driver
- Allow module removal
- Host device
- Convert to VMState
- Generic chardev infrastructure: During migration, make sure if the other endpoint didn't receive data, resend it