[pulseaudio-discuss] RFC: Public API for managing nodes

David Henningsson david.henningsson at canonical.com
Thu Aug 8 06:05:58 PDT 2013


On 08/06/2013 03:44 PM, Tanu Kaskinen wrote:
> On Tue, 2013-08-06 at 15:21 +0200, David Henningsson wrote:
>> On 08/06/2013 02:54 PM, Tanu Kaskinen wrote:
>>> On Tue, 2013-08-06 at 14:42 +0200, David Henningsson wrote:
>>>> On 08/06/2013 02:30 PM, Tanu Kaskinen wrote:
>>>>> On Tue, 2013-08-06 at 13:26 +0200, David Henningsson wrote:
>>>>>> On 08/05/2013 01:37 PM, Tanu Kaskinen wrote:
>>>>>>> On Wed, 2013-07-17 at 12:26 +0200, David Henningsson wrote:
>>>>>>>> On 07/17/2013 11:22 AM, Tanu Kaskinen wrote:
>>>>>>>>> On Wed, 2013-07-17 at 09:27 +0200, David Henningsson wrote:
>>>>>>>>>> On 07/16/2013 03:20 PM, Tanu Kaskinen wrote:
>>>>>>>>>>> What operations do you mean? Moving or removing a default connection is
>>>>>>>>>>> not supported as such, but if the client tries that anyway, we can
>>>>>>>>>>> implicitly convert the connection to an explicit one and disable default
>>>>>>>>>>> connections, or we can require the client to do these operations
>>>>>>>>>>> explicitly, but I think the latter would be too inconvenient for the
>>>>>>>>>>> client.
>>>>>>>>>>
>>>>>>>>>> Ok, I think I didn't read the proposal well enough. Having done that, I
>>>>>>>>>> understand that you're suggesting a global switch "default connections
>>>>>>>>>> on/off" only. Or is it a per-node switch?
>>>>>>>>>
>>>>>>>>> It is a per-node switch.
>>>>>>>>>
>>>>>>>>>> I have another idea that might be worth considering: how about that the
>>>>>>>>>> "explicit" layer can both enable and disable connections? So that there
>>>>>>>>>> could be a default connection between A and B, but there is also some
>>>>>>>>>> sort of explicit override that disables it. This would be more flexible
>>>>>>>>>> than a more global on/off switch.
>>>>>>>>>
>>>>>>>>> I'm not sure what you mean. Do you perhaps mean that the default
>>>>>>>>> connection on/off switch should be per-node (which it already is in my
>>>>>>>>> proposal), or that it should be per-connection (so that if there are
>>>>>>>>> multiple default from node A, it's possible to disable only a subset of
>>>>>>>>> those)?
>>>>>>>>>
>>>>>>>>> I didn't make make it possible to disable individual default
>>>>>>>>> connections, because I had a feeling that it would have very messy
>>>>>>>>> semantics. If default connection from A to B is disabled, what is the
>>>>>>>>> routing code supposed to do when conditions change and the default
>>>>>>>>> routing is re-evaluated? Can it ever reactivate the connection between A
>>>>>>>>> and B again? Is the per-connection disabling handled as a blacklist of
>>>>>>>>> connections that must never be automatically activated?
>>>>>>>>
>>>>>>>> If the A -> B route is explicitly_disabled, that overrides any default 
>>>>>>>> connections the routing system tries to make.
>>>>>>>
>>>>>>> What is the use case for explicitly disabled connections? I'll assume
>>>>>>> here that your idea was to allow moving a default connection elsewhere
>>>>>>> (making the connection explicit in the process) without disabling all
>>>>>>> default connections for the node.
>>>>>>>
>>>>>>> When the user moves a default connection, the routing system obviously
>>>>>>> shouldn't immediately create another default connection elsewhere to
>>>>>>> replace the disabled connection.
>>>>>>>
>>>>>>> On the other hand, if the routing system doesn't create replacement
>>>>>>> connections, then that results in weird behaviour. Let's say that
>>>>>>> there's a default connection A -> B, and the user moves the connection
>>>>>>> to A -> C. Then B disappears. The routing changes its opinion of the
>>>>>>> best available routing for A, which might be D. So removing node B
>>>>>>> resulted in audio suddenly appearing in node D, even though nothing was
>>>>>>> playing to B.
>>>>>>>
>>>>>>
>>>>>> Assume your example of a default connection A -> B which the user
>>>>>> changes into A -> C, by adding an explicit A -> C connection. Without
>>>>>> some sort of explicitly_disabled blacklist that would then include A ->
>>>>>> B, the routing system would be free to route A to *both* B and C.
>>>>>
>>>>> My solution is that the application disables the default routing
>>>>> altogether for A, if it doesn't want to have the default connection A ->
>>>>> B. It seems to me that this causes fewer surprises than the blacklisting
>>>>> approach.
>>>>>
>>>>>> Whether this is implemented as a bool flag or as a separate blacklist is
>>>>>> an implementation detail, but a bool flag just seemed simpler and faster
>>>>>> to me, than having to look in several lists to figure out whether a
>>>>>> connection exists or not.
>>>>>
>>>>> You don't need to look in several lists to figure out whether a
>>>>> connection exists or not. If we have connection objects, which I think
>>>>> we both want to have, it's enough to get the list all connections and
>>>>> see whether a particular connection is included in that list.
>>>>>
>>>>
>>>> Okay, so let me see if I understand this right. You propose that you can
>>>> add explicit connections between two specified nodes, but blacklisting
>>>> default connections have to be done on a node wide level (rather than
>>>> per connection).
>>>>
>>>> That sounds interesting, as it would be more resilient towards nodes
>>>> appearing and disappearing later on.
>>>> I think that blacklisting would have to be two booleans per node though,
>>>> one for outgoing connections and one for incoming. And a connection
>>>> cannot exist if it is blocked on *either* side, rather than both sides.
>>>> Does that make sense?
>>>
>>> My plan has so far been to only disable outgoing default connections,
>>> but if there's need for it, I don't see any problem with adding another
>>> bool for disabling incoming default connections. Do you have a use case?
>>>
>>
>> Well, what's outgoing for playback is incoming for recording, so I think
>> this would be the corresponding use case: assume a user changes from B
>> -> A to C -> A, and that later on, a new source D appears. Then you
>> would want to disable A on the incoming side to avoid a new D -> A
>> connection?
> 
> Ok, I misunderstood what you meant by incoming and outgoing. Since a
> node can't be both an input and output node, 

Oh? That's a new constraint to me. Are you saying that e g filter sinks
won't show up in the graph at all, or that they have one output and
another input node? What about recording from monitors? Loopback and
null sinks?

> it can never have both
> incoming and outgoing connections in the audio flow direction sense. I
> thought that by "incoming" you meant connections that are initiated by
> other nodes, and by "outgoing" I thought you meant connections that are
> initiated by the node itself. That is, "incoming" and "outgoing"
> wouldn't have anything to do with audio flow direction.
> 
> In your example, are B, C and D sources, and is A a capture stream? 

If you by capture stream mean what PulseAudio calls "source output",
then, yes.

> And
> B -> A was a default connection initiated by A? 

To me, when a routing system decides that a default connection should be
added or removed, it must look at all relevant nodes and connections
before making the best decision. Whether something is initiated by one
side or the other sounds like a strange way to think about it.

> If so, I would do the
> move from B -> A to C -> A so that default connections are disabled for
> A, and an explicit connection is added from C to A.
> 
> D probably won't initiate any default connections (sources and sinks
> usually don't do that), but if it does initiate a default connection to
> A, I think it's more likely that it should be allowed (this would be
> pretty unusual routing rule, though, and you didn't explain why the D ->
> A connection would be created, so it's hard to say anything with great
> confidence).

Maybe the example was a bit contrived, but say that D is a USB
microphone you just plugged in, and you have explicitly told the system
to use your line input (C) instead of your internal mic (B), it would be
bad if the routing switched. While if you had not told the system that,
maybe switching to the USB mic would be something good - you usually
want to use the stuff you plug in.


-- 
David Henningsson, Canonical Ltd.
https://launchpad.net/~diwic


More information about the pulseaudio-discuss mailing list