Re: [linux-audio-dev] priority inversion & inheritance

New Message Reply About this list Date view Thread view Subject view Author view Other groups

Subject: Re: [linux-audio-dev] priority inversion & inheritance
From: Kai Vehmanen (kai.vehmanen_AT_wakkanet.fi)
Date: Thu Jul 11 2002 - 18:19:59 EEST


On Thu, 11 Jul 2002, Martijn Sipkema wrote:

>> For instance if you have
>> a mixer element in the signal graph, it is just easier if all the inputs
>> deliver the same amount of data at every iteration.
> Hmm, why? I can see that it is a requirement that at every iteration there
> is the same data available at the input(s) as is requested on the output(s).
> I don\'t see what makes a mixer that much easier to implement if the amount
> of data to process is the same for every iteration.

If all JACK inputs have x samples of audio and non-JACK input y samples,
'x != y' and you need to mix to a JACK output with x samples of space, you
have a problem. Redesign is needed to make sure that this never happens.

> And my problem is that if JACK goes over to constant nframes there will be
> no need to change it. Even worse, new applications will also use assume
> nframes == constant.

In any case it's good that this is now discussed.

> And you could still for all the cards that have nframes == const. Just add
> some buffering for nframes != const.

I guess I could live with this, but we do need a flag to relay this info
to the clients.

>> The two threads must run with SCHED_FIFO as they both need to complete
>> their cycle before the next soundcard interrupt.
> What I meant was a traditional application not running SCHED_FIFO but using
> a large FIFO to communicate with JACK\'s process() callback.
> And even if they both run SCHED_FIFO, they should then also run at the same
> priority.

If using a large FIFO between a non-rt and rt threads, then the best
solution is to make the FIFO nonblocking using atomic operations. This is
an essential technique when making robust user-space audio apps. Real-life
implementation cans be found from ardour (disk butler subsystem),
ecasound (classes AUDIO_IO_BUFFERED_PROXY and AUDIO_IO_PROXY_SERVER)
and EVO (formerly known as linuxsampler).

>> other subsystems block without deterministic worst-case bounds. No amount
>> of priority (given by priority inheritance) will save your butt if the
>> disk head is physically in the wrong place when you need it. On a
> When the disk is not able to supply the samples in time, then there is a
> problem :)
> Using a fast disk and buffering will normally be sufficient.

Aa, but that is a different issue. The question is about response time,
not bandwidth. For instance ecasound's current disk i/o subsystem (run
in a non-rt thread) sometimes stalls for multiple seconds (!) on my
machine (two IDE-disks on the same bus), but still the audio processing
keeps on going without xruns. The disk i/o system just has to buffer
huge amounts of data to cover even the longest delays. Of course if you
are really running out of disk i/o capacity, then fancy locking mechanisms
won't save you.

With full-blown priority inheritance and mutual exclusion between the
threads, the rt-thread would then block for seconds in the above
example and who knows about the worst-case upper bound!

>> The correct solution is to partition your audio code into real-time
>> capable and non-realtime parts and make sure that the non-real-time part
>> is never ever able to block the real-time part. In essence this very close
> As I see it, it isn\'t a problem when the non-realtime part blocks the
> real-time part, as long as there is a worst case bounded block time for it.

But as is is, theoretically speaking the worst-case time is 'infinity'. ;)

> > the software is woken up are two different things. But as the nframes
> > count in any case has an upper bound, you are not free to directly use the
> > avail_samples count anyways. And natural choice is to always use the
> > period_count. I\'ve posted one alternative approach to this to
> It is not that easy. Say period_count is constantly smaller than the available
> data on each interrupt, you will start to get behind and will have to
> eventually do an extra callback that then has more samples/time to process.

I admit, this is a real problem. If the sampling_rate/interrupt_period is
fractional, the only way for a JACK driver to keep up is to set
JACK's buffersize to ceil(srate/iperiod) and then alternate between
process(nframes) and process(nframes-1).

Ok, I guess here's the first real case against const-nframe. On the hand
at least with ALSA you'd be in trouble anyway as ALSA will wake your
driver only when period_count samples are available. If you set
period_count to floor(srate/iperiod) you will be woken up on every
interrupt but you will slowly fall behind and eventually issue two
process() calls per iteration (as you described). I period_count is set to
ceil(srate/iperiod) you app will be waken only every other hw interrupt
(at least every now and then).

So like Paul said, do we need to support these soundcards...? For
JACK-style operation both the above scenario are really, really bad.

>> Not a problem as there\'s no 2^x limitation.
> Isn\'t there? for FFT?

The trick is that with majority of available soundcards the user is able
to set period_count 2^x samples. JACK clients using FFT are free to raise
on error if a non 2^x buffersize is active. This is pretty good situation
from both developer and user point of view.

Basicly same approach is now in used in regards to the nframes issue. If
you try to use ecasound with a JACK driver (well, if there was such an
driver) with non-const-nframes, ecasound would just raise an error and
exit. In a way this makes sense as until I rewrite ecasound (which will
take months of work if I decide to do it) to properly handle
non-const-nframes, the user is better of using some other app that is
optimized for the the driver. In a JACK setup, an appliacation that almost
works efficiently enough, is not of much use.

--
 http://www.eca.cx
 Audio software for Linux!
 


New Message Reply About this list Date view Thread view Subject view Author view Other groups

This archive was generated by hypermail 2b28 : Thu Jul 11 2002 - 18:46:17 EEST