[libvirt] [PATCH] qemu: Allow using regular audio backends with VNC

Currently all host audio backends are disabled if a VM is using VNC, in favor of the QEMU VNC audio extension. Unfortunately no released VNC client supports this extension, so users have no way of getting audio to work if using VNC. Add a new config option in qemu.conf which allows changing libvirt's behavior, but keep the default intact. Signed-off-by: Cole Robinson <crobinso@redhat.com> --- src/qemu/qemu.conf | 10 ++++++++++ src/qemu/qemu_conf.c | 17 ++++++++++++----- src/qemu/qemu_conf.h | 2 ++ 3 files changed, 24 insertions(+), 5 deletions(-) diff --git a/src/qemu/qemu.conf b/src/qemu/qemu.conf index 3da332f..fec946d 100644 --- a/src/qemu/qemu.conf +++ b/src/qemu/qemu.conf @@ -168,3 +168,13 @@ # be assigned to guests. # # relaxed_acs_check = 1 + + +# QEMU implements anextension for providing audio over a VNC connection, +# though if your VNC client does not support it, your only chance for getting +# sound output is through regular audio backends. By default, libvirt will +# disable all QEMU sound backends if using VNC, since they can cause +# permissions issues. Enabling this option will make libvirtd honor the +# QEMU_AUDIO_DRV environment variable when using VNC. +# +# vnc_enable_audio_backend = 0 diff --git a/src/qemu/qemu_conf.c b/src/qemu/qemu_conf.c index d7bc798..5c30f48 100644 --- a/src/qemu/qemu_conf.c +++ b/src/qemu/qemu_conf.c @@ -351,6 +351,10 @@ int qemudLoadDriverConfig(struct qemud_driver *driver, CHECK_TYPE ("relaxed_acs_check", VIR_CONF_LONG); if (p) driver->relaxedACS = p->l; + p = virConfGetValue (conf, "vnc_enable_audio_backend"); + CHECK_TYPE ("vnc_enable_audio_backend", VIR_CONF_LONG); + if (p) driver->vncEnableAudioBackend = p->l; + virConfFree (conf); return 0; } @@ -4394,12 +4398,15 @@ int qemudBuildCommandLine(virConnectPtr conn, ADD_ARG_LIT(def->graphics[0]->data.vnc.keymap); } - /* QEMU implements a VNC extension for providing audio, so we - * set the audio backend to none, to prevent it opening the - * host OS audio devices since that causes security issues - * and is non-sensical when using VNC. + /* Unless user requested it, set the audio backend to none, to + * prevent it opening the host OS audio devices since that causes + * security issues and is may not work when using VNC. */ - ADD_ENV_LIT("QEMU_AUDIO_DRV=none"); + if (driver->vncEnableAudioBackend) { + ADD_ENV_COPY("QEMU_AUDIO_DRV"); + } else { + ADD_ENV_LIT("QEMU_AUDIO_DRV=none"); + } } else if ((def->ngraphics == 1) && def->graphics[0]->type == VIR_DOMAIN_GRAPHICS_TYPE_SDL) { char *xauth = NULL; diff --git a/src/qemu/qemu_conf.h b/src/qemu/qemu_conf.h index 11f8dcd..aa6ed61 100644 --- a/src/qemu/qemu_conf.h +++ b/src/qemu/qemu_conf.h @@ -137,6 +137,8 @@ struct qemud_driver { unsigned int relaxedACS : 1; + unsigned int vncEnableAudioBackend : 1; + virCapsPtr caps; /* An array of callbacks */ -- 1.6.6.1

On 05/20/2010 10:04 AM, Cole Robinson wrote:
Currently all host audio backends are disabled if a VM is using VNC, in favor of the QEMU VNC audio extension. Unfortunately no released VNC client supports this extension, so users have no way of getting audio to work if using VNC.
Add a new config option in qemu.conf which allows changing libvirt's behavior, but keep the default intact.
Typos to fix:
+# QEMU implements anextension for providing audio over a VNC connection,
s/anextension/an extension/
@@ -4394,12 +4398,15 @@ int qemudBuildCommandLine(virConnectPtr conn, ADD_ARG_LIT(def->graphics[0]->data.vnc.keymap); }
- /* QEMU implements a VNC extension for providing audio, so we - * set the audio backend to none, to prevent it opening the - * host OS audio devices since that causes security issues - * and is non-sensical when using VNC. + /* Unless user requested it, set the audio backend to none, to + * prevent it opening the host OS audio devices since that causes
s/devices/devices,/
+ * security issues and is may not work when using VNC.
s/is may/might/ ACK with those changes. -- Eric Blake eblake@redhat.com +1-801-349-2682 Libvirt virtualization library http://libvirt.org

On Thu, May 20, 2010 at 12:04:04PM -0400, Cole Robinson wrote:
Currently all host audio backends are disabled if a VM is using VNC, in favor of the QEMU VNC audio extension. Unfortunately no released VNC client supports this extension, so users have no way of getting audio to work if using VNC.
Add a new config option in qemu.conf which allows changing libvirt's behavior, but keep the default intact.
Signed-off-by: Cole Robinson <crobinso@redhat.com> --- src/qemu/qemu.conf | 10 ++++++++++ src/qemu/qemu_conf.c | 17 ++++++++++++----- src/qemu/qemu_conf.h | 2 ++ 3 files changed, 24 insertions(+), 5 deletions(-)
diff --git a/src/qemu/qemu.conf b/src/qemu/qemu.conf index 3da332f..fec946d 100644 --- a/src/qemu/qemu.conf +++ b/src/qemu/qemu.conf @@ -168,3 +168,13 @@ # be assigned to guests. # # relaxed_acs_check = 1 + + +# QEMU implements anextension for providing audio over a VNC connection, +# though if your VNC client does not support it, your only chance for getting +# sound output is through regular audio backends. By default, libvirt will +# disable all QEMU sound backends if using VNC, since they can cause +# permissions issues. Enabling this option will make libvirtd honor the +# QEMU_AUDIO_DRV environment variable when using VNC. +# +# vnc_enable_audio_backend = 0
I think this would be better named as 'vnc_allow_host_audio' since its not toggling VNC audio, just whether it is allowed to use the host audio drivers. NB, even with this toggled things are unlikely to magically 'just work'. If QEMU is running as 'qemu' user ID, that user won't have any permissions to use /dev/snd/* devices. And if running as 'root' then pulseaudio won't autospawn so will need to be run manually. Daniel -- |: Red Hat, Engineering, London -o- http://people.redhat.com/berrange/ :| |: http://libvirt.org -o- http://virt-manager.org -o- http://deltacloud.org :| |: http://autobuild.org -o- http://search.cpan.org/~danberr/ :| |: GnuPG: 7D3B9505 -o- F3C9 553F A1DA 4AC2 5648 23C1 B3DF F742 7D3B 9505 :|

On 05/24/2010 10:14 AM, Daniel P. Berrange wrote:
On Thu, May 20, 2010 at 12:04:04PM -0400, Cole Robinson wrote:
Currently all host audio backends are disabled if a VM is using VNC, in favor of the QEMU VNC audio extension. Unfortunately no released VNC client supports this extension, so users have no way of getting audio to work if using VNC.
Add a new config option in qemu.conf which allows changing libvirt's behavior, but keep the default intact.
Signed-off-by: Cole Robinson <crobinso@redhat.com> --- src/qemu/qemu.conf | 10 ++++++++++ src/qemu/qemu_conf.c | 17 ++++++++++++----- src/qemu/qemu_conf.h | 2 ++ 3 files changed, 24 insertions(+), 5 deletions(-)
diff --git a/src/qemu/qemu.conf b/src/qemu/qemu.conf index 3da332f..fec946d 100644 --- a/src/qemu/qemu.conf +++ b/src/qemu/qemu.conf @@ -168,3 +168,13 @@ # be assigned to guests. # # relaxed_acs_check = 1 + + +# QEMU implements anextension for providing audio over a VNC connection, +# though if your VNC client does not support it, your only chance for getting +# sound output is through regular audio backends. By default, libvirt will +# disable all QEMU sound backends if using VNC, since they can cause +# permissions issues. Enabling this option will make libvirtd honor the +# QEMU_AUDIO_DRV environment variable when using VNC. +# +# vnc_enable_audio_backend = 0
I think this would be better named as 'vnc_allow_host_audio' since its not toggling VNC audio, just whether it is allowed to use the host audio drivers.
Okay, I'll change and resend.
NB, even with this toggled things are unlikely to magically 'just work'. If QEMU is running as 'qemu' user ID, that user won't have any permissions to use /dev/snd/* devices. And if running as 'root' then pulseaudio won't autospawn so will need to be run manually.
Right. Currently getting sound to work in Fedora is a big pain, and there have been quite a few user complaints. I'm going to write up a 'known bug' page, documenting a workaround of qemu.conf user/group = $USER to fix the issue, but this patch will still need to be backported. - Cole

On Mon, May 24, 2010 at 10:26:43AM -0400, Cole Robinson wrote:
On 05/24/2010 10:14 AM, Daniel P. Berrange wrote:
On Thu, May 20, 2010 at 12:04:04PM -0400, Cole Robinson wrote:
Currently all host audio backends are disabled if a VM is using VNC, in favor of the QEMU VNC audio extension. Unfortunately no released VNC client supports this extension, so users have no way of getting audio to work if using VNC.
Add a new config option in qemu.conf which allows changing libvirt's behavior, but keep the default intact.
Signed-off-by: Cole Robinson <crobinso@redhat.com> --- src/qemu/qemu.conf | 10 ++++++++++ src/qemu/qemu_conf.c | 17 ++++++++++++----- src/qemu/qemu_conf.h | 2 ++ 3 files changed, 24 insertions(+), 5 deletions(-)
diff --git a/src/qemu/qemu.conf b/src/qemu/qemu.conf index 3da332f..fec946d 100644 --- a/src/qemu/qemu.conf +++ b/src/qemu/qemu.conf @@ -168,3 +168,13 @@ # be assigned to guests. # # relaxed_acs_check = 1 + + +# QEMU implements anextension for providing audio over a VNC connection, +# though if your VNC client does not support it, your only chance for getting +# sound output is through regular audio backends. By default, libvirt will +# disable all QEMU sound backends if using VNC, since they can cause +# permissions issues. Enabling this option will make libvirtd honor the +# QEMU_AUDIO_DRV environment variable when using VNC. +# +# vnc_enable_audio_backend = 0
I think this would be better named as 'vnc_allow_host_audio' since its not toggling VNC audio, just whether it is allowed to use the host audio drivers.
Okay, I'll change and resend.
NB, even with this toggled things are unlikely to magically 'just work'. If QEMU is running as 'qemu' user ID, that user won't have any permissions to use /dev/snd/* devices. And if running as 'root' then pulseaudio won't autospawn so will need to be run manually.
Right. Currently getting sound to work in Fedora is a big pain, and there have been quite a few user complaints. I'm going to write up a 'known bug' page, documenting a workaround of qemu.conf user/group = $USER to fix the issue, but this patch will still need to be backported.
I'd really recommend against telling people to configure libvirt to run the guests as their own $USER because that'll open a huge can of worms. Better to tell them to add an ACL to /dev/snd/* using setfacl to add the qemu user to the ACL for the sound card, or drop in a udev rule todo the same. Daniel -- |: Red Hat, Engineering, London -o- http://people.redhat.com/berrange/ :| |: http://libvirt.org -o- http://virt-manager.org -o- http://deltacloud.org :| |: http://autobuild.org -o- http://search.cpan.org/~danberr/ :| |: GnuPG: 7D3B9505 -o- F3C9 553F A1DA 4AC2 5648 23C1 B3DF F742 7D3B 9505 :|

On 05/24/2010 10:31 AM, Daniel P. Berrange wrote:
On Mon, May 24, 2010 at 10:26:43AM -0400, Cole Robinson wrote:
On 05/24/2010 10:14 AM, Daniel P. Berrange wrote:
On Thu, May 20, 2010 at 12:04:04PM -0400, Cole Robinson wrote:
Currently all host audio backends are disabled if a VM is using VNC, in favor of the QEMU VNC audio extension. Unfortunately no released VNC client supports this extension, so users have no way of getting audio to work if using VNC.
Add a new config option in qemu.conf which allows changing libvirt's behavior, but keep the default intact.
Signed-off-by: Cole Robinson <crobinso@redhat.com> --- src/qemu/qemu.conf | 10 ++++++++++ src/qemu/qemu_conf.c | 17 ++++++++++++----- src/qemu/qemu_conf.h | 2 ++ 3 files changed, 24 insertions(+), 5 deletions(-)
diff --git a/src/qemu/qemu.conf b/src/qemu/qemu.conf index 3da332f..fec946d 100644 --- a/src/qemu/qemu.conf +++ b/src/qemu/qemu.conf @@ -168,3 +168,13 @@ # be assigned to guests. # # relaxed_acs_check = 1 + + +# QEMU implements anextension for providing audio over a VNC connection, +# though if your VNC client does not support it, your only chance for getting +# sound output is through regular audio backends. By default, libvirt will +# disable all QEMU sound backends if using VNC, since they can cause +# permissions issues. Enabling this option will make libvirtd honor the +# QEMU_AUDIO_DRV environment variable when using VNC. +# +# vnc_enable_audio_backend = 0
I think this would be better named as 'vnc_allow_host_audio' since its not toggling VNC audio, just whether it is allowed to use the host audio drivers.
Okay, I'll change and resend.
NB, even with this toggled things are unlikely to magically 'just work'. If QEMU is running as 'qemu' user ID, that user won't have any permissions to use /dev/snd/* devices. And if running as 'root' then pulseaudio won't autospawn so will need to be run manually.
Right. Currently getting sound to work in Fedora is a big pain, and there have been quite a few user complaints. I'm going to write up a 'known bug' page, documenting a workaround of qemu.conf user/group = $USER to fix the issue, but this patch will still need to be backported.
I'd really recommend against telling people to configure libvirt to run the guests as their own $USER because that'll open a huge can of worms.
What exactly are the downsides, besides the security implications? It should exercise all the same code as user/group = 'qemu', but solves issues like: - Making sure emulator user can access $HOME for install media - Audio - PTY access - SDL (if someone insists on it)
Better to tell them to add an ACL to /dev/snd/* using setfacl to add the qemu user to the ACL for the sound card, or drop in a udev rule todo the same.
I'll try that out, but I wonder will my local user actually hear that sound? Will the audio go to my pulseaudio session? - Cole

On Mon, May 24, 2010 at 10:56:39AM -0400, Cole Robinson wrote:
On 05/24/2010 10:31 AM, Daniel P. Berrange wrote:
On Mon, May 24, 2010 at 10:26:43AM -0400, Cole Robinson wrote:
On 05/24/2010 10:14 AM, Daniel P. Berrange wrote:
On Thu, May 20, 2010 at 12:04:04PM -0400, Cole Robinson wrote:
Currently all host audio backends are disabled if a VM is using VNC, in favor of the QEMU VNC audio extension. Unfortunately no released VNC client supports this extension, so users have no way of getting audio to work if using VNC.
Add a new config option in qemu.conf which allows changing libvirt's behavior, but keep the default intact.
Signed-off-by: Cole Robinson <crobinso@redhat.com> --- src/qemu/qemu.conf | 10 ++++++++++ src/qemu/qemu_conf.c | 17 ++++++++++++----- src/qemu/qemu_conf.h | 2 ++ 3 files changed, 24 insertions(+), 5 deletions(-)
diff --git a/src/qemu/qemu.conf b/src/qemu/qemu.conf index 3da332f..fec946d 100644 --- a/src/qemu/qemu.conf +++ b/src/qemu/qemu.conf @@ -168,3 +168,13 @@ # be assigned to guests. # # relaxed_acs_check = 1 + + +# QEMU implements anextension for providing audio over a VNC connection, +# though if your VNC client does not support it, your only chance for getting +# sound output is through regular audio backends. By default, libvirt will +# disable all QEMU sound backends if using VNC, since they can cause +# permissions issues. Enabling this option will make libvirtd honor the +# QEMU_AUDIO_DRV environment variable when using VNC. +# +# vnc_enable_audio_backend = 0
I think this would be better named as 'vnc_allow_host_audio' since its not toggling VNC audio, just whether it is allowed to use the host audio drivers.
Okay, I'll change and resend.
NB, even with this toggled things are unlikely to magically 'just work'. If QEMU is running as 'qemu' user ID, that user won't have any permissions to use /dev/snd/* devices. And if running as 'root' then pulseaudio won't autospawn so will need to be run manually.
Right. Currently getting sound to work in Fedora is a big pain, and there have been quite a few user complaints. I'm going to write up a 'known bug' page, documenting a workaround of qemu.conf user/group = $USER to fix the issue, but this patch will still need to be backported.
I'd really recommend against telling people to configure libvirt to run the guests as their own $USER because that'll open a huge can of worms.
What exactly are the downsides, besides the security implications? It should exercise all the same code as user/group = 'qemu', but solves issues like:
- Making sure emulator user can access $HOME for install media - Audio - PTY access - SDL (if someone insists on it)
In the contex of desktop usage, these problems are all the result of using the qemu:///system driver instead of the session driver. We've not historically used the session driver, because it can't setup a TAP device for guests out of the box. If we're going down the route of manually post-install config steps as root, then instead of changing libvirtd config, we'd be better of doing the manual config step to allow TAP device access to $USER. This approach is aligned with our driver design for qemu://session being the per user bus, as opposed to hacking qemu://system todo something it was never intended to support. Independantly of this, those 4 problems above can also be addressed for the system driver while maintaining the proper privilege separation. Audio access by fixing GTK-VNC. PTY access by using the libvirt streams API. SDL access by pointing it to the users' xauth file (and setting an ACL on xauth to allow qemu to read it). Install media by adding libvirt APIs to upload a kernel+initrd or boot.iso the appropriate location. This is again aligned with our design of the system instance being highly privileged, but separated from any other accounts on the host.
Better to tell them to add an ACL to /dev/snd/* using setfacl to add the qemu user to the ACL for the sound card, or drop in a udev rule todo the same.
I'll try that out, but I wonder will my local user actually hear that sound? Will the audio go to my pulseaudio session?
This will cause another pulseaudio daemon to open the sound device and play directly, it shouldn't need to connect to the user's own pulse daemon. If PA isn't in use, then QEMU will just try to access the sound card directly. Daniel -- |: Red Hat, Engineering, London -o- http://people.redhat.com/berrange/ :| |: http://libvirt.org -o- http://virt-manager.org -o- http://deltacloud.org :| |: http://autobuild.org -o- http://search.cpan.org/~danberr/ :| |: GnuPG: 7D3B9505 -o- F3C9 553F A1DA 4AC2 5648 23C1 B3DF F742 7D3B 9505 :|

On 05/24/2010 11:18 AM, Daniel P. Berrange wrote:
On Mon, May 24, 2010 at 10:56:39AM -0400, Cole Robinson wrote:
On 05/24/2010 10:31 AM, Daniel P. Berrange wrote:
On Mon, May 24, 2010 at 10:26:43AM -0400, Cole Robinson wrote:
On 05/24/2010 10:14 AM, Daniel P. Berrange wrote:
On Thu, May 20, 2010 at 12:04:04PM -0400, Cole Robinson wrote:
Currently all host audio backends are disabled if a VM is using VNC, in favor of the QEMU VNC audio extension. Unfortunately no released VNC client supports this extension, so users have no way of getting audio to work if using VNC.
Add a new config option in qemu.conf which allows changing libvirt's behavior, but keep the default intact.
Signed-off-by: Cole Robinson <crobinso@redhat.com> --- src/qemu/qemu.conf | 10 ++++++++++ src/qemu/qemu_conf.c | 17 ++++++++++++----- src/qemu/qemu_conf.h | 2 ++ 3 files changed, 24 insertions(+), 5 deletions(-)
diff --git a/src/qemu/qemu.conf b/src/qemu/qemu.conf index 3da332f..fec946d 100644 --- a/src/qemu/qemu.conf +++ b/src/qemu/qemu.conf @@ -168,3 +168,13 @@ # be assigned to guests. # # relaxed_acs_check = 1 + + +# QEMU implements anextension for providing audio over a VNC connection, +# though if your VNC client does not support it, your only chance for getting +# sound output is through regular audio backends. By default, libvirt will +# disable all QEMU sound backends if using VNC, since they can cause +# permissions issues. Enabling this option will make libvirtd honor the +# QEMU_AUDIO_DRV environment variable when using VNC. +# +# vnc_enable_audio_backend = 0
I think this would be better named as 'vnc_allow_host_audio' since its not toggling VNC audio, just whether it is allowed to use the host audio drivers.
Okay, I'll change and resend.
NB, even with this toggled things are unlikely to magically 'just work'. If QEMU is running as 'qemu' user ID, that user won't have any permissions to use /dev/snd/* devices. And if running as 'root' then pulseaudio won't autospawn so will need to be run manually.
Right. Currently getting sound to work in Fedora is a big pain, and there have been quite a few user complaints. I'm going to write up a 'known bug' page, documenting a workaround of qemu.conf user/group = $USER to fix the issue, but this patch will still need to be backported.
I'd really recommend against telling people to configure libvirt to run the guests as their own $USER because that'll open a huge can of worms.
What exactly are the downsides, besides the security implications? It should exercise all the same code as user/group = 'qemu', but solves issues like:
- Making sure emulator user can access $HOME for install media - Audio - PTY access - SDL (if someone insists on it)
In the contex of desktop usage, these problems are all the result of using the qemu:///system driver instead of the session driver.
We've not historically used the session driver, because it can't setup a TAP device for guests out of the box. If we're going down the route of manually post-install config steps as root, then instead of changing libvirtd config, we'd be better of doing the manual config step to allow TAP device access to $USER. This approach is aligned with our driver design for qemu://session being the per user bus, as opposed to hacking qemu://system todo something it was never intended to support.
qemu:///session is the way forward, but its a lot more work then just telling people to manually setup a tap device: better tool support in virt-manager/virt-install, MUCH better/more visible docs covering the differences/pros/cons, not to mention preparation for the onslaught of 'I'm running as root and can't see my VMs' bugs. Maybe docs about moving your qemu:///system machines to qemu:///session. Until this work is done, we should document workarounds, even if it uses qemu:///system in a way it was never intended to support (we already do that since it is used for 99% of all desktop virt libvirt usage).
Independantly of this, those 4 problems above can also be addressed for the system driver while maintaining the proper privilege separation. Audio access by fixing GTK-VNC. PTY access by using the libvirt streams API. SDL access by pointing it to the users' xauth file (and setting an ACL on xauth to allow qemu to read it). Install media by adding libvirt APIs to upload a kernel+initrd or boot.iso the appropriate location. This is again aligned with our design of the system instance being highly privileged, but separated from any other accounts on the host.
That SDL trick doesn't work for me on F13. Even running guests as root doesn't work for SDL anymore, used to work on F11 at least. That aside, I completely agree that we can and should properly solve these issues with qemu:///system. But F12 and F13 users will likely never see this work, so it's important to document all this: bug reports tracking the proper way forward (we have), with possible workarounds in the interim (we don't have). Setting user/group to $USER is a fairly simple change that makes many of these issues disappear, and for a single user system it doesn't seem too outrageous a concept.
Better to tell them to add an ACL to /dev/snd/* using setfacl to add the qemu user to the ACL for the sound card, or drop in a udev rule todo the same.
I'll try that out, but I wonder will my local user actually hear that sound? Will the audio go to my pulseaudio session?
This will cause another pulseaudio daemon to open the sound device and play directly, it shouldn't need to connect to the user's own pulse daemon. If PA isn't in use, then QEMU will just try to access the sound card directly.
Hmm, couldn't get this to work with F13, qemu startup log is filled with 'Connection Refused' pa errors. Could be user error or require more configuration, but it's already entering the realm of more difficulty than user/group=$USER. - Cole
participants (3)
-
Cole Robinson
-
Daniel P. Berrange
-
Eric Blake