Re: [Libvir] Authenticate APIs ?
by Richard W.M. Jones
[Apologies that this is not threaded with the original post]
> Following on from the issue of certificate management, is the issue of
> authentication. This hasn't been an issue thus far, because Xen has zero
> authentication. I'm not planning to make this same mistake with the QEMU
> management daemon though - its going to have a secure data transport and
> real authentication from day-1. Thus we need to consider how
authentication
> is exposed at the libvirt client API layer.
>
> First off, there are many possible authentication approaches:
>
> - Username + password
> - Username + one time key
> - Username + password digest
> - Kerberos tickets
> - x509 certificates
> - ...etc
I would definitely avoid over-engineering a solution.
I suspect that "large corp" users will understand certificate
infrastructures -- they probably already use X.509 client certificates
to authenticate desktops -- and will be able to manage those. Everyone
else will want to use ssh, the model for that being the way cvs allows
you to flexibly hand over authentication problems to an external program
through setting the $CVS_RSH environment variable.
It's so easy to set up ssh to get passwordless remote logins. If they
haven't set that up, and they're using libvirt through a command line
tool like virsh then they'll get a prompt from ssh to type a password.
ssh also has the advantage that it is very widely installed.
The only issue is what command to run on the remote system. A simple
command line tool which talks to the daemon over a socket might be one
option. nc (netcat), gnutls_cli or stunnel might work too.
Rich.
--
Red Hat UK Ltd.
64 Baker Street, London, W1U 7DF
Mobile: +44 7866 314 421 (will change soon)
17 years, 10 months
[Libvir] Certificate management APIs ?
by Daniel P. Berrange
I now have the QEMU backend working with full wire encryption using the
TLS protocol, and so ready to start thinking about various authentication
related issues.
- The client needs to have the certificate of the CA in order to
validate the signature on the remote server's certificate
(aka, just like web browsers need a set of CA certificates)
Currently I just have it loading 'cert.pem' out of the current
working directory of the app using libvirt. Obviously this is not
a real solution.
- The client technically should have a certificate revocation list
too. Again I currently load this out of current working dir
- The server end can optionally require the client to present a
certificate too, as its means of authenticating the client.
This obviously requires a way of specifying the client certificate
and secret key in libvirt when opening the connection.
- The first time it connects to a server, the client validates the
server's certificate against the CA certificate, and remote hostname.
Web browsers will also typically display the certificate to the
user and ask them to allow one-time, allow permanently, or reject
it. This would require a way to pass the certificate back to the
client app during the virConnectOpen call.
The above is all related to x509 certificates. So we basically have 5
types of file we need to store / provide to libvirt when opening a
connection:
- Certificate Authority's certificate
- Certificate Authority's certificate revocation list
- Client secret key
- Client certificate
- Trusted server certificates
And some form of callback to let the client app validate the server
certificate.
As a rough stab at an API my thoughts are:
typedef enum {
VIR_CERT_CA_CERT,
VIR_CERT_CA_CRL,
VIR_CERT_CLIENT_KEY,
VIR_CERT_CLIENT_CERT,
} virConnectCertDataType;
/**
* dataType: one of the virConnectCertDataType constants
* data: base64, PEM encoded certificate/key data
*/
int virConnectAddCertData(int dataType, const char *data);
/**
* dataType: one of the virConnectCertDataType constants
* dataFile: file containing base64, PEM encoded certificate/key data
*/
int virConnectAddCertDataFile(int dataType, const char *dataFile);
Virt-manager would use the latter API to load in its client certificate,
CA certs, etc to libvirt prior to opening a connection to a TLS enabled
server. This means libvirt doesn't have to make the policy on where to
store its client cert data. On the otherhand, we probably want the
files to be in a common location for virsh & virt-manager so both can
use the same data. On yet another hand, virt-manager will also likely
end up using TLS to connect to VNC, so needs access to the files
independant on libvirt / virsh for that. So we should probably have
these flexible APIs, but recommend that all apps use a pre-defined
directory unless they have a particular need not to, eg
$HOME/.libvirt/tls/
|
+- ca
| |
| +- cert.pem
| +- ca-crl.pem
|
+- client
| |
| +- cert.pem
| +- key.pem
|
+- server
|
+- trusted.pem
/**
* hostname: canonical name of remote host providing certiifcate
* cert: base64, PEM encoded certificate data
*
* Invoked to let client application decide whether to accept a
* server certificate. The certificate wil already have been
* validated against the CA cert, and its expiration date, etc
* checked. This callback is intended to allow the end user to
* accept/reject the certificate. The trusted flag indicates
* whether the server is present in the list of known servers.
*/
typedef int (*virConnectCertificateValidator)(const char *hostname, const char *cert);
int virConnectSetCertificateValidator(virConnectCertificateValidator cb)
The applications like virt-manager would probably want to present the
certificate details to the user for validation, also optionally maintaining
a list of previously trusted server certs.
Dan.
--
|=- Red Hat, Engineering, Emerging Technologies, Boston. +1 978 392 2496 -=|
|=- Perl modules: http://search.cpan.org/~danberr/ -=|
|=- Projects: http://freshmeat.net/~danielpb/ -=|
|=- GnuPG: 7D3B9505 F3C9 553F A1DA 4AC2 5648 23C1 B3DF F742 7D3B 9505 -=|
17 years, 10 months
[Libvir] Authenticate APIs ?
by Daniel P. Berrange
Following on from the issue of certificate management, is the issue of
authentication. This hasn't been an issue thus far, because Xen has zero
authentication. I'm not planning to make this same mistake with the QEMU
management daemon though - its going to have a secure data transport and
real authentication from day-1. Thus we need to consider how authentication
is exposed at the libvirt client API layer.
First off, there are many possible authentication approaches:
- Username + password
- Username + one time key
- Username + password digest
- Kerberos tickets
- x509 certificates
- ...etc
So of these require prompting the user for data (eg username / password),
others will pick up their credentials from known sources (eg, the keberos
ticket cache file in /tmp/krbXXX), or have to be provided ahead of time
as part of the transport layer securit protocol (eg the x509 certificate
file).
We don't have to consider the latter case, since that's taken care of by
the certificate management API - unless we want to figure out a more
unified API, but I'm not sure it would be particularly sane.
The interesting case from an API point of view is the first, which requires
prompting the user for data. This is pretty much the PAM approach, with the
added complication that you're in the middle of a network protocol and you
may have several wire messages going back & forth, each time requesting
more pieces of info. ie you can't possibly gather the neccessary info ahead
of time.
So we need some form of callback to collect the neccessary auth data. The
network protocol equivalent of PAM is SASL. This actually has a number
of different types of callback function yuou can register, depending on
what sort of data you're prepared to provide as a client
- Challenge / response:
- const char *challenge
- const char *prompt
- const char *defresult,
- const char **result,
- unsigned *len
- Password, username, language
- const char **result
- unsigned *len
- AUthentication realm
- const char **availrealms,
- const char **result
There are a few more auth callback types defined in SASL spec, which I've
omitted here for brevity.
We could map this onto an API something like this:
enum {
VIR_CONN_AUTH_PASSWORD,
VIR_CONN_AUTH_USERNAME,
VIR_CONN_AUTH_LANG,
VIR_CONN_AUTH_CHALLENGE,
VIR_CONN_AUTH_REALM,
} virConnectAuthToken;
typedef int (virConnectAuthCBSimple)(const char **result, unsigned *len);
typedef int (virConnectAuthCBPrompt)(const char *challenge, const char *prompt,
const char *defresult,
const char *result, unsigned *len);
typedef int (virConnetAuthCBRealm)(const char **availrealms, const char *result);
typedef struct {
int token;
union {
virConnectAuthCBSimple simple;
virConnectAuthCBPrompt prompt;
virConnectAuthCBRealm realm;
} cb;
} virConnectAuthCallback;
int virConnectSetAuthCallbacks(virConnectAuthCallback *cbs, int ncbs);
Now, of course not everything is going to be SASL based - Xen may well end
up using TLS/SSL + HTTP Basic auth. There's a couple of other HTTP related
auth protocols too. They are all basically a subset of SASL provides, so the
above API ought to be sufficient to serve their auth needs too.
Finally, one could simply say, this is all rather complicated, why don't
we just use a simple username+password for everything. While this would
be nice from a coding POV, I think we need to be forward looking and
ensure we're setup to cope with things like Kerberos single-sign-on.
This is why I'm looking at SASL for the QEMU authentication process - if
you use libsasl.so you're app doesn't even need to know what auth method
it is using - the admin can simple create an appropriate config file
for sasl, and bingo you're fully kerberized & single sign-on capable.
Regards,
Dan.
--
|=- Red Hat, Engineering, Emerging Technologies, Boston. +1 978 392 2496 -=|
|=- Perl modules: http://search.cpan.org/~danberr/ -=|
|=- Projects: http://freshmeat.net/~danielpb/ -=|
|=- GnuPG: 7D3B9505 F3C9 553F A1DA 4AC2 5648 23C1 B3DF F742 7D3B 9505 -=|
17 years, 10 months
[Libvir] Availability of the Relax-NG schemas for libvirt XML instances
by Daniel Veillard
As hinted previously in the QEmu thread, I developped a Relax-NG schemas to
check the XML instances used to define Domains in libvirt. It's in CVS
in the docs directory and also available online at
http://libvirt.org/libvirt.rng
For those not familiar with Relax-NG there is a nice tutorial and docs at
http://relaxng.org/
Libxml2 on which libvirt depends has support for Relax-NG so we could easilly
add checking at domain creation time within the library, but I decided to not
add this at the moment, at least the schemas need to get more testing itself.
The simplest to validate existing XML instances is to use the command line
tool of libxml2 named xmllint in the following way:
paphio:~/libvirt/tests -> xmllint --noout --relaxng ../docs/libvirt.rng xml2sexprdata/xml2sexpr-disk-drv-blkback.xml
xml2sexprdata/xml2sexpr-disk-drv-blkback.xml validates
paphio:~/libvirt/tests ->
The schemas try to validate content as much as possible, but it's not possible
to validate really in a complete fashion, for example to validate an IP address
I used the following type:
<define name='addrIP'>
<data type='string'>
<param name="pattern">([0-2]?[0-9]?[0-9]\.){3}[0-2]?[0-9]?[0-9]</param>
</data>
</define>
which will catch '192.618.0.254' as erroneous but not '192.168.0.264' . There
is also a number of cases which are structure related but hard to express
cleanly in a schemas for example the fact that we may have an emulator
description in the device list but that it's should only be allowed in an hvm
kind of configuration.
Still despite the limitations I found 2 weirdness:
- we allow both <os> and <bootloader> blocks to be present, but I think they
are redundant, I remember that Xen will ignore the bootloader informations
if the os description is there, shouldn't we ban having both in a domain
description ? e.g. tests/sexpr2xmldata/sexpr2xml-curmem.xml in the tree
I still allowed this in the schemas but this may be wrong.
- I though an interface of type ethernet needed a source description,
but the output tests/sexpr2xmldata/sexpr2xml-net-routed.xml seems to miss
both the source and target of the interface though the device is
present in tests/sexpr2xmldata/sexpr2xml-net-routed.sexpr as (dev 'eth3')
this probably indicates our conversion from sexpr to xml is lossy there.
currently tests/sexpr2xmldata/sexpr2xml-net-routed.xml is the only example
from our regression tests which doesn't pass the schemas testing.
In general the schemas is both stricter than libvirt itself (as libvirt will
only pick the parts of the XML it recognizes and need) and still allows some
invalid constructs, I guess it's nearly impossible to make it a one to one
match but I hope this can still be useful both for client tools, regression
testings, and as another source of documentation.
I still need to update the libvirt documentation, the XML page had some
omissions and document the availability of the schemas and find its place when
doing a 'make install',
Daniel
--
Red Hat Virtualization group http://redhat.com/virtualization/
Daniel Veillard | virtualization library http://libvirt.org/
veillard(a)redhat.com | libxml GNOME XML XSLT toolkit http://xmlsoft.org/
http://veillard.com/ | Rpmfind RPM search engine http://rpmfind.net/
17 years, 10 months
[Libvir] Bug in the virDomainGetInfo() API of libvirt 0.1.9 with Xen 3.0.3
by Philippe Berthault
The maxMem field of the virDomainInfo structure is given in bytes
instead of Kbytes when the domain is 0 (Domain-0). With others domains,
the value of maxMem is correct.
Exemple with virsh:
On a system with 4 GB memory, virsh reports:
# virsh dominfo 0
...
Max memory: 4294967292 kB
With the same libvirt version 0.1.9 but with an older Xen (not 3.0.3),
the maxMem value of Domain-0 is correct.
17 years, 10 months
[Libvir] Question about libvirt integration into RHEL-5
by Philippe Berthault
Hello,
Currently, the libvirt integrated into RHEL-5 beta release is the pretty
old 0.1.8 version.
Could you confirm that in the first release candidate RHEL-5 RC1
(planned february, 28), the libvirt will be the 0.1.8 version or another
one ?
Thanks.
17 years, 10 months
[Libvir] PATCH 0/2: Support QEMU (+KVM) in libvirt
by Daniel P. Berrange
The following series of (2) patches adds a QEMU driver to libvirt. The first patch
provides a daemon for managing QEMU instances, the second provides a driver letting
libvirt manage QEMU via the daemon.
Basic architecture
------------------
The reason for the daemon architecture is two fold:
- At this time, there is no (practical) way to enumerate QEMU instances, or
reliably connect to the monitor console of an existing process. There is
also no way to determine the guest configuration associated with a daemon.
- It is desirable to be able to manage QEMU instances using either an unprivilegd
local client, or a remote client. The daemon can provide connectivity via UNIX
domain sockets, or IPv4 / IPv6 and layer in suitable authentication / encryption
via TLS and/or SASL protocols.
Anthony Ligouri is working on patches for QEMU with the goal of addressing the
first point. For example, an extra command line argument will cause QEMU to save
a PID file and create a UNIX socket for its monitor at a well-defined path. More
functionality in the monitor console will allow the guest configuration to be
reverse engineered from a running guest. Even with those patches, however, it will
still be desirable to have a daemon to provide more flexible connectivity, and to
facilitate implementation libvirt APIs which are host (rather than guest) related.
Thus I expect that over time we can simply enhance the daemon to take advantage of
newer capabilities in the QEMU monitor, but keep the same basic libvirt driver
architecture.
Considering some of the other hypervisor technologies out there, in particular
User Mode Linux, and lhype, it may well become possible to let this QEMU daemon
also provide the management of these guests - allowing re-use of the single driver
backend in the libvirt client library itself.
XML format
----------
As discussed in the previous mail thread, the XML format for describing guests
with the QEMU backend is the same structure as that for Xen guests, with
following enhancements:
- The 'type' attribute on the top level <domain> tag can take one of the
values 'qemu', 'kqemu' or 'kvm' instead of 'xen'. This selects between
the different virtualization approaches QEMU can provide.
- The '<type>' attribute within the <os> block of the XML (for now) is
still expected to the 'hvm' (indicating full virtualization), although
I'm trying to think of a better name, since its not technically hardware
accelerated unless you're using KVM
- The '<type>' attribute within the <os> block of the XML can have two
optional 'arch' and 'machine' attributes. The former selects the CPU
architecture to be emulated; the latter the specific machine to have
QEMU emulate (determine those supported by QEMU using 'qemu -M ?').
- The <kernel>, <initrd>, <cmdline> elements can be used to specify
an explicit kernel to boot off[1], otherwise it'll do a boot of the
cdrom, harddisk / floppy (based on <boot> element). Well,the kernel
bits are parsed at least. I've not got around to using them when
building the QEMU argv yet.
- The disk devices are configured in same way as Xen HVM guests. eg you
have to use hda -> hdd, and/or fda -> fdb. Only hdc can be selected
as a cdrom device.
- The network configuration is work in progress. QEMU has many ways to
setup networking. I use the 'type' attribute to select between the
different approachs 'user', 'tap', 'server', 'client', 'mcast' mapping
them directly onto QEMU command line arguments. You can specify a
MAC address as usual too. I need to implement auto-generation of MAC
addresses if omitted. Most of them have extra bits of metadata though
which I've not figured out appropriate XML for yet. Thus when building
the QEMU argv I currently just hardcode 'user' networking.
- The QEMU binary is determined automatically based on the requested
CPU architecture, defaulting to i686 if non specified. It is possible
to override the default binary using the <emulator> element within the
<devices> section. This is different to previously discussed, because
recent work by Anthony merging VMI + KVM to give paravirt guests means
that the <loader> element is best kept to refer to the VMI ROM (or other
ROM like files :-) - this is also closer to Xen semantics anyway.
Connectivity
------------
The namespace under which all connection URIs come is 'qemud'. Thereafter
there are several options. First, two well-known local hypervisor
connections
- qemud:///session
This is a per-user private hypervisor connection. The libvirt daemon and
qemu guest processes just run as whatever UNIX user your client app is
running. This lets unprivileged users use the qemu driver without needing
any kind admin rights. Obviously you can't use KQEMU or KVM accelerators
unless the /dev/ device node is chmod/chown'd to give you access.
The communication goes over a UNIX domain socket which is mode 0600 created
in the abstract namespace at $HOME/.qemud.d/sock.
- qemud:///system
This is a system-wide privileged hypervisor connection. There is only one
of these on any given machine. The libvirt_qemud daemon would be started
ahead of time (by an init script), possibly running as root, or maybe under
a dedicated system user account (and the KQEMU/KVM devices chown'd to match).
The admin would optionally also make it listen on IPv4/6 addrs to allow
remote communication. (see next URI example)
The local communication goes over one of two possible UNIX domain sockets
Both in the abstract namespace under the directory /var/run. The first socket
called 'qemud' is mode 0600, so only privileged apps (ie root) can access it,
and gives full control capabilities. The other called 'qemud-ro' is mode 0666
and any clients connecting to it will be restricted to only read-only libvirt
operations by the server.
- qemud://hostname:port/
This lets you connect to a daemon over IPv4 or IPv6. If omitted the port is
8123 (will probably change it). This lets you connect to a system daemon
on a remote host - assuming it was configured to listen on IPv4/6 interfaces.
Currently there is zero auth or encryption, but I'm planning to make it
mandortory to use the TLS protocol - using the GNU TLS library. This will give
encryption, and mutual authentication using either x509 certificates or
PGP keys & trustdbs or perhaps both :-) Will probably start off by implementing
PGP since I understand it better.
So if you wanted to remotely manage a server, you'd copy the server's
certificate/public key to the client into a well known location. Similarly
you'd generate a keypair for the client & copy its public key to the
server. Perhaps I'll allow clients without a key to connect in read-only
mode. Need to prototype it first and then write up some ideas.
Server architecture
-------------------
The server is a fairly simple beast. It is single-threaded using non-blocking I/O
and poll() for all operations. It will listen on multiple sockets for incoming
connections. The protocol used for client-server comms is a very simple binary
message format close to the existing libvirt_proxy. Client sends a message, server
receives it, performs appropriate operation & sends a reply to the client. The
client (ie libvirt driver) blocks after sending its message until it gets a reply.
The server does non-blocking reads from the client buffering until it has a single
complete message, then processes it and populates the buffer with a reply and does
non-blocking writes to send it back to the client. It won't try to read a further
message from the client until its sent the entire reply back. ie, it is a totally
synchronous message flow - no batching/pipelining of messages. During the time
the server is processes a message it is not dealing with any other I/O, but thus
far all the operations are very fast to implement, so this isn't a serious issue,
and there ways to deal with it if there are operations which turn out to take a
long time. I certainly want to avoid multi-threading in the server at all costs!
As well as monitoring the client & client sockets, the poll() event loop in the
server also captures stdout & stderr from the QEMU processes. Currently we just
dump this to stdout of the daemon, but I expect we can log it somewhere. When we
start accessing the QEMU monitor there will be another fd in the event loop - ie
the pseduo-TTY (or UNIX socket) on which we talk to the monitor.
Inactive guests
---------------
Guests created using 'virsh create' (or equiv API) are treated as 'transient'
domains - ie their config files are not saved to disk. This is consistent with
the behaviour in the Xen backend. Guests created using 'virsh define', however,
are saved out to disk in $HOME/.qemud.d for the per-user session daemon. The
system-wide daemon should use /etc/qemud.d, but currently its still /root/.qemud.d
The config files are simply saved as the libvirt XML blob ensuring no data
conversion issues. In any case, QEMU doesn't currently have any config file
format we can leverage. The list of inactive guests is loaded at startup of the
daemon. New config files are expected to be created via the API - files manually
created in the directory after initial startup are not seen. Might like to change
this later.
XML Examples
------------
This is a guest using plain qemu, with x86_64 architecture and a ISA-only
(ie no PCI) machine emulation. I was actually running this on a 32-bit
host :-) VNC is configured to run on port 5906. QEMU can't automatically
choose a VNC port, so if one isn't specified we assign one based on the
domain ID. This should be fixed in QEMU....
<domain type='qemu'>
<name>demo1</name>
<uuid>4dea23b3-1d52-d8f3-2516-782e98a23fa0</uuid>
<memory>131072</memory>
<vcpu>1</vcpu>
<os>
<type arch='x86_64' machine='isapc'>hvm</type>
</os>
<devices>
<disk type='file' device='disk'>
<source file='/home/berrange/fedora/diskboot.img'/>
<target dev='hda'/>
</disk>
<interface type='user'>
<mac address='24:42:53:21:52:45'/>
</interface>
<graphics type='vnc' port='5906'/>
</devices>
</domain>
A second example, this time using KVM acceleration. Note how I specify a
non-default path to QEMU to pick up the KVM build of QEMU. Normally KVM
binary will default to /usr/bin/qemu-kvm - this may change depending on
how distro packaging of KVM turns out - it may even be merged into regular
QEMU binaries.
<domain type='kvm'>
<name>demo2</name>
<uuid>4dea24b3-1d52-d8f3-2516-782e98a23fa0</uuid>
<memory>131072</memory>
<vcpu>1</vcpu>
<os>
<type>hvm</type>
</os>
<devices>
<emulator>/home/berrange/usr/kvm-devel/bin/qemu-system-x86_64</emulator>
<disk type='file' device='disk'>
<source file='/home/berrange/fedora/diskboot.img'/>
<target dev='hda'/>
</disk>
<interface type='user'>
<mac address='24:42:53:21:52:45'/>
</interface>
<graphics type='vnc' port='-1'/>
</devices>
</domain>
Outstanding work
----------------
- TLS support. Need to add TLS encryption & authentication to both the client
and server side for IPv4/6 communications. This will obviously add a dependancy
on libgnutls.so in libvirt & the daemon. I don't consider this a major problem
since every non-trivial network app these days uses TLS. The other possible impl
of OpenSSL has GPL-compatability issues, so is not considered.
- Change the wire format to use fixed size data types (ie, int8, int16, int32, etc)
instead of the size-dependant int/long types. At same time define some rules for
the byte ordering. Client must match server ordering ? Server must accept client's
desired ordering ? Everyone must use BE regardless of server/client format ? I'm
inclined to say client must match server, since it distributes the byte-swapping
overhead to all clients and lets the common case of x86->x86 be a no-op.
- Add a protocol version message as first option to let use protocol at will later
while maintaining compat with older libvirt client libraries.
- Improve support for describing the various QEMU network configurations
- Finish boot options - boot device order & explicit kernel
- Open & use connection to QEMU monitor which will let us implement pause/resume,
suspend/restore drivers, and device hotplug / media changes.
- Return sensible data for virNodeInfo - will need to have operating system dependant
code here - parsing /proc for Linux to determine available RAM & CPU speed. Who
knows what for Solaris / BSD ?!? Anyone know of remotely standard ways for doing
this. Accurate host memory reporting is the only really critical data item we need.
- There is a fair bit of duplicate in various helper functions between the daemon,
and various libvirt driver backends. We should probably pull this stuff out into
a separate lib/ directoy, build it into a static library and then link that into
both libvirt, virsh & the qemud daemon as needed.
Dan.
--
|=- Red Hat, Engineering, Emerging Technologies, Boston. +1 978 392 2496 -=|
|=- Perl modules: http://search.cpan.org/~danberr/ -=|
|=- Projects: http://freshmeat.net/~danielpb/ -=|
|=- GnuPG: 7D3B9505 F3C9 553F A1DA 4AC2 5648 23C1 B3DF F742 7D3B 9505 -=|
17 years, 10 months
[Libvir] Get info with libvirt from a remote Xen dom0
by Jordi Prats
Hi,
On the function:
virConnectPtr virConnectOpenReadOnly (const char * name)
name is unused. Is planned any use for it? I'm particullay interested on
obtaining information from a remote machine.
I'm trying to provide HA between dom0, so this way is a dom0 chashes
another dom0 will create every vm from the othe node.
Example:
dom0.1 have vm01 and vm02
dom0.2 have vm03 and vm04
Then if dom0.1 goes down, dom0.2 will have vm01,vm02,vm03 and vm04
I'm pretending to use libvirt as a abstraction layer to operate this Xen
cluster.
Thanks,
--
......................................................................
__
/ / Jordi Prats Català
C E / S / C A Departament de Sistemes
/_/ Centre de Supercomputació de Catalunya
Gran Capità, 2-4 (Edifici Nexus) · 08034 Barcelona
T. 93 205 6464 · F. 93 205 6979 · jprats(a)cesca.es
......................................................................
pgp:0x5D0D1321
......................................................................
17 years, 10 months
[Libvir] XML format for QEMU / KVM driver
by Daniel P. Berrange
Since KVM is the new "shiny thing" in the virtualization world for Linux I
figure its time to resurrect & finish the prototype QEMU backend I started
developing for libvirt. Thanks to the design of KVM, it ought to be possible
to support KVM & QEMU in a single driver with near-zero extra effort to add
the bits for KVM support.
There's a couple of interesting decisions wrt additions in the XML format
describing guests.
1. QEMU can be built with several different CPU accelerators, eg KQEMU,
QVM86 or KVM. These are only available if the guest CPU matches the
host CPU architecture though.
2. QEMU can emulate many different CPU types. x86, x86_64, mips, sparc,
ppc, arm, etc
3. QEMU can emulate many different different 'machine' types, for each
CPU type. eg for x86 cpus:
$ qemu -M ?
Supported machines are:
pc Standard PC (default)
isapc ISA-only PC
Some of these options are activated by specifying a particular command
line flag, eg -M for machine type. Others require you to use a different
qemu binary, eg 'qemu-system-arm', 'qemu-system-ppc' instead of 'qemu'.
QEMU is basically a fully-virt solution, so XML description for the <os>
block would be superficically similar to Xen HVM support, in that it
will typically try to boot the kernel found in the MBR of the first
harddisk (unless you specify an alternate boot device). Unlike Xen HVM
support, it can also have an explicit kernel, initrd & arguments
specified via command line. The other difference is that Xen has a
separater binary for the loader, vs device model - QEMU/KVM does it
all in one binary.
So, my initial thoughts are:
1. Use the <type> element within the <os> block to describe the
CPU accelerator to use, accepting the values 'qemu', 'kvm',
'kqemu' or 'qvm86'.
2. For CPU architecture, there are a couple of choices
a) Add an 'arch' attribute to the <type> element to select between
x86, ppc, sparc, etc.
b) Add an <arch> element within the <os> block to switch between
architectures.
c) Just use the <loader> element to point to the QEMU binary
matching the desired architecture.
d) Use the <emulator> element within the <devices> section to point
to the QEMU binary matching the desired architecture.
e) Option a) and also allow use of <loader> to override the
default QEMU binary to use
f) Option b) and also allow use of <loader> to override the
default QEMU binary to use
g) Option a) and also allow use of <emulator> within the
<devices> block to override the default QEMU binary to use
h) Option b) and also allow use of <emulator> within the
<devices> block to override the default QEMU binary to use
At this time, i'm leaning towards either option e). This would give
examples like
* Using PPC with regular non-accelerated QEMU
<os>
<type arch="ppc">qemu</type>
</os>
* Using non-accelerated QEMU, and guest architecture matching
the host
<os>
<type>qemu</type>
</os>
* Using accelerated KVM
<os>
<type>kvm</type>
</os>
* Using accelerated KVM, but with an alernate binary
<os>
<type>kvm</type>
<loader>/home/berrange/work/kvm-devel/qemu-kvm</loader>
</os>
3. For machine type, again there are a couple of options:
a) Add a 'machine' attribute to the <type> element
b) Add a <machine> element within the <os> block
For this I think we should just follow same scheme that we
use to specify architecture. So I'd lean towards a)
* Using PPC with a Mac-99 machine:
<os>
<type arch="ppc" machine="mac99">qemu</type>
</os>
* Using non-accelerated QEMU, and guest architecture matching
the host, and a non-PCI machine:
<os>
<type machine="isapc">qemu</type>
</os>
All the other bits of XML like disk/network/console configuration are pretty
straightforward, following very similar structure to Xen. So there isn't really
much interesting stuff to discuss there.
Dan.
--
|=- Red Hat, Engineering, Emerging Technologies, Boston. +1 978 392 2496 -=|
|=- Perl modules: http://search.cpan.org/~danberr/ -=|
|=- Projects: http://freshmeat.net/~danielpb/ -=|
|=- GnuPG: 7D3B9505 F3C9 553F A1DA 4AC2 5648 23C1 B3DF F742 7D3B 9505 -=|
17 years, 10 months