Friday, 7 December 2012

Taking the Pulse

As the Fedora Jam spin rolls onwards, a key component is Jack. The Jack Audio Connection Kit (one of those recursive anagrams so popular in the mid 2000s...) is the glue that binds pro-sound in Linux together. It's used for DAWs, audio plugins, real-time effects processing and generally pushing sound around. To do this it has to play well with another Linux audio layer, PulseAudio, and this is where the trouble starts.
Update 31 Jan 2012 Since this post was written a number of patches have made it through to PulseAudio which may address this issue in the next release (and importantly can be applied to versions already out there). Watch this space...

 For the Jam spin we want pro-audio to work out of the box; why shouldn't it? Anyone trying an audio creation platform is going to be a bit surprised if they find out it isn't configured with sound working. (If you're only here to get Jack working, just skip to the end).

Sound works in Linux: this isn't 2002. There's some rare hardware that isn't supported and the most cutting edge stuff can sometimes take a while to get drivers. On the other hand I had to hunt around to get a driver for my main soundcard for Windows 8, so the grass on both sides is sometimes in need of watering.

PulseAudio

Sound works on the desktop, thanks both to the ALSA developers and PulseAudio, which is the layer that channels sound from different programmes through to the soundcard. I like Pulse, because I remember what things were like before it, if you were lucky and messed around with sample rates and formats you could have two applications playing sound at once. Don't know what I'm talking about? Be glad you have Pulse.
But, to do its real-time, low-latency magic, Jack needs direct access to the sound card. That means getting Pulse to let go. You can still have Pulse and all the good things it gives you, because Jack can pretend to be a device for Pulse to use.
So everything is great.
Except...

Learning to let go

Pulse is a bit possessive of audio devices. The problem it's meant to address is that only one programme can directly use an audio device at a time, pretty much like only being able to call one person on your phone at a time. Pulse solves that problem by being that programme and then combining the streams from everything else (a conference call in the phone analogy). But when something like Jack has a good reason to use the line instead it should hang up.
There's a way to ask it to. Since 2009 there's been a specification for asking Pulse to let go of a sound card and Jack tries to do this.

Deaf ears

In short Pulse is meant to put up a sign (virtually, not an actual message on the screen) for every device it's using. If something else wants to use that device it checks for the sign and if there isn't one it writes to Pulse asking it to let go (or, with our phone analogy, taps it on the shoulder politely). If Pulse isn't doing anything important then it lets go and takes down the sign. However, it's quite common for Pulse to put up the sign and stop listening to it. Other programmes (like Jack) see the sign, and when Pulse ignores them think it must be on an important call and give up.

Anatomy of a bug report

This is a two line change to PulseAudio (the {} don't count):

--- a/src/modules/reserve.c
+++ b/src/modules/reserve.c
@@ -409,6 +409,10 @@ int rd_acquire(
                goto fail;
        }

+       if (k == DBUS_REQUEST_NAME_REPLY_ALREADY_OWNER) {
+               goto success;
+       }
+
        if (k == DBUS_REQUEST_NAME_REPLY_PRIMARY_OWNER)
                goto success;
It looks simple (it is simple). Somewhere in the Pulse code it ends up checking whether a device it has a device it already owns. This is apparently a bug, but no-one currently knows where. If this happens Pulse gets confused and stops watching for messages to the sign.
In our phone analogy, Pulse suddenly thinks, "Where's my phone?" Failing to realise it's in its hand it then stands there, catatonic, while Jack stands beside it trying to be heard. If a person did this you'd consider them rude. Of course what it should do is realise it's holding the phone and carry on with life.
One of the reasons that many people still don't like Pulse is that when it first arrived there were plenty of problems, many were actually issues in other software, especially quirks in ALSA drivers that hadn't been important before. Somewhat justifiably the Pulse position was that these should be fixed at source, not worked around. Gradually, mainly with the hard work of ALSA developers, those bugs were fixed and for normal use it generally now works.
But, if you're going to take the position that other people should fix their interfaces then you shouldn't be surprised if they expect the same of you. Whatever the reason for Pulse to check up on itself, its module for listening to requests should survive that, there are too many ways for this kind of thing to happen in real code to intentionally keep fragile code in an interface.

Killing the Pulse

So things are broken and there's no hope? Do we give up on Jack in Fedora 18? Should you remove Pulse and leave your programmes huddled round your speakers jostling for a chance to speak? No, the solution that has worked for a couple of years still works. If you want to get Pulse off the phone then shoot it (I don't recommend this approach if actually trying to get someone off the phone).
Assuming you use QJackCtl to control Jack (and if you don't, you should take a look, because it's very useful), just open Setup and go to the Options menu, in the 'Execute script on startup' section put:
pulseaudio -k

and in the 'Execute script after startup' section put:
pactl load-module module-jack-source;pactl load-module module-jack-sink

On a standard Fedora setup Pulse starts up again after it's been killed (our phone analogy maybe breaks down here). But in that time Jack has been able to get hold of the sound card. Once it has that it graciously listens out for anything Pulse might want to say and passes it on down the line.

No comments:

Post a Comment