2012-03-21 19:02:12

by Mike Brudevold

[permalink] [raw]
Subject: media transport -- when is acquire ok to call?

I'm having some trouble with MediaEndpoint/MediaTransport and A2DP.
When I get the "SetConfiguration" call, I wait 2 seconds and then call
"Acquire", generally giving BlueZ enough time get the D-Bus interface
ready to go. However, the delay isn't always long enough. Shown
below is a time when my phone is attempting to pair with BlueZ. The
error "org.bluez.Error.NotAuthorized" is output from my application.
In this case, the problem is that the audio source is still in the
CONFIGURED state, not in the OPEN state. Is there a recommended
method of how long to wait before calling acquire? Or should I rely
on the AudioSource "State" property to become connected (or playing)?
Is there any reason I can't get the transport when in the Configured
state (does the fd not exist yet?)? Or why is "a2dp_resume" being
called on open (which is what is rejecting my acquire call)?

Thanks,
Mike

bluetoothd[751]: src/adapter.c:adapter_get_device() 00:17:E3:3B:4F:DD
bluetoothd[751]: src/adapter.c:adapter_create_device() 00:17:E3:3B:4F:DD
bluetoothd[751]: src/device.c:device_create() Creating device
/org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD
bluetoothd[751]: src/device.c:btd_device_ref() 0x2a0d4ef0: ref=1
bluetoothd[751]: src/device.c:device_set_temporary() temporary 1
bluetoothd[751]: plugins/hciops.c:remote_features_information() hci0 status 0
bluetoothd[751]: plugins/hciops.c:remote_name_information() hci0 status 0
bluetoothd[751]: audio/avdtp.c:avdtp_confirm_cb() AVDTP: incoming
connect from 00:17:E3:3B:4F:DD
bluetoothd[751]: src/adapter.c:adapter_get_device() 00:17:E3:3B:4F:DD
bluetoothd[751]: src/device.c:btd_device_ref() 0x2a0d4ef0: ref=2
bluetoothd[751]: audio/device.c:audio_device_register() Registered
interface org.bluez.Audio on path
/org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD
bluetoothd[751]: src/device.c:device_probe_drivers() Probing drivers
for 00:17:E3:3B:4F:DD
bluetoothd[751]: audio/manager.c:handle_uuid() server not enabled for
0000110d-0000-1000-8000-00805f9b34fb (0x110d)
bluetoothd[751]: src/agent.c:agent_authorize() authorize request was
sent for /org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD
bluetoothd[751]: plugins/hciops.c:link_key_request() hci0 dba 00:17:E3:3B:4F:DD
bluetoothd[751]: plugins/hciops.c:get_auth_info() hci0 dba 00:17:E3:3B:4F:DD
bluetoothd[751]: plugins/hciops.c:link_key_request() kernel auth
requirements = 0x04
bluetoothd[751]: plugins/hciops.c:link_key_request() Matching key not found
bluetoothd[751]: plugins/hciops.c:pin_code_request() hci0 PIN request
for 00:17:E3:3B:4F:DD
bluetoothd[751]: src/adapter.c:adapter_get_device() 00:17:E3:3B:4F:DD
bluetoothd[751]: src/device.c:device_request_authentication()
Requesting agent authentication for 00:17:E3:3B:4F:DD
bluetoothd[751]: plugins/hciops.c:hciops_pincode_reply() hci0 dba
00:17:E3:3B:4F:DD
bluetoothd[751]: audio/avdtp.c:avdtp_connect_cb() AVDTP: connected
signaling channel to 00:17:E3:3B:4F:DD
bluetoothd[751]: audio/avdtp.c:avdtp_connect_cb() AVDTP imtu=672, omtu=1024
bluetoothd[751]: audio/avdtp.c:session_cb()
bluetoothd[751]: audio/avdtp.c:avdtp_parse_cmd() Received DISCOVER_CMD
bluetoothd[751]: audio/avdtp.c:session_cb()
bluetoothd[751]: audio/avdtp.c:avdtp_parse_cmd() Received GET_CAPABILITIES_CMD
bluetoothd[751]: audio/a2dp.c:endpoint_getcap_ind() Sink 0x2a0d40a8:
Get_Capability_Ind
bluetoothd[751]: audio/avdtp.c:session_cb()
bluetoothd[751]: audio/avdtp.c:avdtp_parse_cmd() Received SET_CONFIGURATION_CMD
bluetoothd[751]: src/device.c:device_probe_drivers() Probing drivers
for 00:17:E3:3B:4F:DD
bluetoothd[751]: audio/manager.c:handle_uuid() Found Audio Source
bluetoothd[751]: audio/source.c:source_init() Registered interface
org.bluez.AudioSource on path
/org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD
bluetoothd[751]: audio/a2dp.c:endpoint_setconf_ind() Sink 0x2a0d40a8:
Set_Configuration_Ind
bluetoothd[751]: audio/avdtp.c:avdtp_ref() 0x2a0d2a00: ref=2
bluetoothd[751]: audio/a2dp.c:setup_ref() 0x2a0a6e00: ref=1
bluetoothd[751]: audio/media.c:media_endpoint_async_call() Calling
SetConfiguration: name = :1.40 path = /com/starkey/a2dp/endpoint
bluetoothd[751]: audio/avdtp.c:avdtp_ref() 0x2a0d2a00: ref=3
bluetoothd[751]: audio/avdtp.c:avdtp_sep_set_state() stream state
changed: IDLE -> CONFIGURED
bluetoothd[751]: audio/a2dp.c:setup_unref() 0x2a0a6e00: ref=0
bluetoothd[751]: audio/a2dp.c:setup_free() 0x2a0a6e00
bluetoothd[751]: audio/avdtp.c:avdtp_unref() 0x2a0d2a00: ref=2
bluetoothd[751]: audio/avdtp.c:session_cb()
bluetoothd[751]: audio/avdtp.c:avdtp_parse_cmd() Received OPEN_CMD
bluetoothd[751]: audio/a2dp.c:open_ind() Sink 0x2a0d40a8: Open_Ind
bluetoothd[751]: audio/transport.c:media_transport_acquire() Transport
/org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD/fd1: read lock acquired
bluetoothd[751]: audio/transport.c:media_transport_acquire() Transport
/org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD/fd1: write lock acquired
bluetoothd[751]: audio/transport.c:media_owner_create() Owner created:
sender=:1.40 accesstype=rw
bluetoothd[751]: audio/avdtp.c:avdtp_ref() 0x2a0d2a00: ref=3
bluetoothd[751]: audio/transport.c:media_transport_release() Transport
/org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD/fd1: read lock released
bluetoothd[751]: audio/transport.c:media_transport_release() Transport
/org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD/fd1: write lock released
bluetoothd[751]: audio/transport.c:media_owner_free() Owner :1.40
getting the reply from the cb failed
GDBus.Error:org.bluez.Error.NotAuthorized: Operation Not Authorized
bluetoothd[751]: plugins/hciops.c:link_key_notify() hci0 dba
00:17:E3:3B:4F:DD type 0
bluetoothd[751]: plugins/hciops.c:link_key_notify() key type 0x00 old
key type 0xff
bluetoothd[751]: plugins/hciops.c:link_key_notify() local auth 0x04
and remote auth 0xff
bluetoothd[751]: src/adapter.c:adapter_get_device() 00:17:E3:3B:4F:DD
bluetoothd[751]: src/event.c:btd_event_link_key_notify() storing link
key of type 0x00
bluetoothd[751]: src/device.c:device_set_bonded() bonded 1
bluetoothd[751]: src/device.c:device_set_temporary() temporary 0
bluetoothd[751]: plugins/hciops.c:bonding_complete() status 0x00
bluetoothd[751]: src/adapter.c:adapter_get_device() 00:17:E3:3B:4F:DD
bluetoothd[751]: src/device.c:device_bonding_complete() bonding (nil)
status 0x00
bluetoothd[751]: src/device.c:device_bonding_complete() setting timer
for reverse service discovery
bluetoothd[751]: plugins/hciops.c:auth_complete() hci0 status 0
bluetoothd[751]: plugins/hciops.c:bonding_complete() status 0x00
bluetoothd[751]: src/adapter.c:adapter_get_device() 00:17:E3:3B:4F:DD
bluetoothd[751]: src/device.c:device_bonding_complete() bonding (nil)
status 0x00
bluetoothd[751]: audio/avdtp.c:avdtp_confirm_cb() AVDTP: incoming
connect from 00:17:E3:3B:4F:DD
bluetoothd[751]: src/device.c:device_probe_drivers() Probing drivers
for 00:17:E3:3B:4F:DD
bluetoothd[751]: audio/manager.c:handle_uuid() Found Handsfree AG record
bluetoothd[751]: audio/manager.c:gateway_auth_cb() Accepted AG
connection from 00:17:E3:3B:4F:DD for
/org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD
bluetoothd[751]: audio/avdtp.c:avdtp_connect_cb() AVDTP: connected
transport channel to 00:17:E3:3B:4F:DD
bluetoothd[751]: audio/avdtp.c:avdtp_sep_set_state() stream state
changed: CONFIGURED -> OPEN


2012-03-27 14:22:27

by Mike Brudevold

[permalink] [raw]
Subject: Re: media transport -- when is acquire ok to call?

Hi Mikel,

On Tue, Mar 27, 2012 at 1:31 AM, Mikel Astiz <[email protected]> wrote:
> Hi Mike,
>
>> So that has me confused. ?If the MediaTransport interface is somewhat
>> generic, why would I want to listen to another interface to know if I
>> should call Acquire? ?In my case, I would need to listen to
>> HeadsetGateway. ?As it is, the audio from my SCO connection is sent
>> over a PCM bus, so I currently do not even register an SCO endpoint,
>> because it was not needed. ?I agree that if you are the initiator,
>> Acquire/Release is sufficient. ?In my case, as the non-initiator, it is
>> not sufficient because I do not want to open an audio link by calling
>> acquire unless it already exists.
>
> I'm not sure if this solves your specific problem(s) but I would propose that the MediaTransport API is extended with a method such as TryAcquire (or alternatively Acquire can be extended with either one more parameter, or some specific flag in accesstype). In that case the transport would not be acquired unless the audio link already exists.
>
> The current approach of listening to a state property and then calling Acquire is racy, no matter if the property is in the same interface or not.

I think your proposal would fix this race in a way that doesn't
fundamentally change the current design, so I'm in favor of it.

> Regarding your comment on the need to listen to a different interface, I don't think this should be a big problem. Having said that, the Playing state in HeadsetGateway (and equivalents) could be replaced by a state in MediaTransport. That actually seems more appropriate to me.

Agreed. The reason I don't like the current approach is that there is
no explicit connection between the MediaTransport object and the other
object that has the state property.

Mike

2012-03-27 06:31:09

by Mikel Astiz

[permalink] [raw]
Subject: RE: media transport -- when is acquire ok to call?

Hi Mike,

> So that has me confused. If the MediaTransport interface is somewhat
> generic, why would I want to listen to another interface to know if I
> should call Acquire? In my case, I would need to listen to
> HeadsetGateway. As it is, the audio from my SCO connection is sent
> over a PCM bus, so I currently do not even register an SCO endpoint,
> because it was not needed. I agree that if you are the initiator,
> Acquire/Release is sufficient. In my case, as the non-initiator, it is
> not sufficient because I do not want to open an audio link by calling
> acquire unless it already exists.

I'm not sure if this solves your specific problem(s) but I would propose that the MediaTransport API is extended with a method such as TryAcquire (or alternatively Acquire can be extended with either one more parameter, or some specific flag in accesstype). In that case the transport would not be acquired unless the audio link already exists.

The current approach of listening to a state property and then calling Acquire is racy, no matter if the property is in the same interface or not.

Regarding your comment on the need to listen to a different interface, I don't think this should be a big problem. Having said that, the Playing state in HeadsetGateway (and equivalents) could be replaced by a state in MediaTransport. That actually seems more appropriate to me.

Cheers,
Mikel


2012-03-26 17:01:10

by Luiz Augusto von Dentz

[permalink] [raw]
Subject: Re: media transport -- when is acquire ok to call?

Hi Mike,

On Mon, Mar 26, 2012 at 1:10 PM, Mike <[email protected]> wrote:
>> Pushing maybe a good idea in case of not being the initiator the
>> connection as you mentioned, in the other hand the endpoint may not be
>> ready, or willing to use the fd, at that point so I would only signal
>> that it is now available, otherwise the concept of using it on-demand
>> in broken.
>
> Isn't that the point of registering an endpoint? ?If you have
> registered, you are declaring you will accept data.

The endpoint takes care of the configuration, it doesn't mean you need
to Acquire the file descriptor, actually you should only acquire if
you are going to use it, so even if the phone connects and open the
SCO connection it doesn't mean you should pickup it right away since
different policies/routing might be implemented.

>> Btw, this already is possible if you listen to
>> Headset.State, also the interface was designed to have the connection
>> on-demand, so you should only call Acquire when you gonna use the fd,
>> anyway even in the case of audio transfer you maybe the initiator and
>> should be able to directly control the connection via Acquire/Release
>> to be able to do that so Resume/Suspend would not be that great even
>> for IVI/carkit systems.
>
> So that has me confused. ?If the MediaTransport interface is somewhat
> generic, why would I want to listen to another interface to know if I
> should call Acquire? ?In my case, I would need to listen to
> HeadsetGateway. ?As it is, the audio from my SCO connection is sent
> over a PCM bus, so I currently do not even register an SCO endpoint,
> because it was not needed. ?I agree that if you are the initiator,
> Acquire/Release is sufficient. ?In my case, as the non-initiator, it
> is not sufficient because I do not want to open an audio link by
> calling acquire unless it already exists.

That is a broken design, PCM routing also needs proper endpoint
otherwise it is impossible to implement routing policies since the
audio is transparently routed, it only works if you have a single
purpose device. Also please pay attention that with audio transfer you
may be the initiator of SCO connection even in case of IVI/carkit
role.

> My perception is that the interface is written from the point of view
> of the audio source (A2DP Audio Source or HFP AG), but this does not
> translate as well to the audio sinks (A2DP Audio Sink or HFP HF).

Nope it should works in both cases, it only assumes that the endpoint
need to know when it should Acquire the file descriptor not bluetoothd
should push the file descriptor. Anyway I still believe pull is
better, because the client may not be ready or block (using threads)
and it know better when it needs the fd.

--
Luiz Augusto von Dentz

2012-03-26 16:10:19

by Mike Brudevold

[permalink] [raw]
Subject: Re: media transport -- when is acquire ok to call?

Hi Luiz,

On Mon, Mar 26, 2012 at 9:41 AM, Luiz Augusto von Dentz
<[email protected]> wrote:
> Hi Mike,
>
> On Fri, Mar 23, 2012 at 2:51 PM, Mike <[email protected]> wrote:
>>
>> Going back to this idea, it seems like MediaTransport should be
>> redesigned to push the file descriptor to the endpoint, rather than
>> the endpoint having to request it from the transport. ?this would
>> solve this issue. ?The main problem is that acquiring the endpoint
>> forces a call to resume. ?In the case of HFP, this is bad. ?I'm
>> currently needing to implement HFP "Audio Connection Transfer Towards
>> the AG". ?Since I am the HS, all I need to do is drop the SCO
>> connection -- however, there is no interface to do this well. ?I tried
>> implementing an SCO endpoint, since at least then the acquire and
>> release calls would bring up an SCO connection and then allow me to
>> drop it. ?The issue here is that a phone that is connected via HFP
>> will have a MediaTransport even though the SCO connection will not yet
>> exist. ?So, I get the SetConfiguration call which means I should be
>> good to go on calling acquire. ?But, if I call acquire now, it will
>> create a useless SCO connection to my phone that then is dropped.
>> There's no reason at this point to open the SCO connection. ?I would
>> rather be notified when the SCO connection exists, and have two
>> additional methods called suspend and resume. ?In the case of HFP,
>> calling resume would eventually result in a new FD being pushed to me.
>
> Pushing maybe a good idea in case of not being the initiator the
> connection as you mentioned, in the other hand the endpoint may not be
> ready, or willing to use the fd, at that point so I would only signal
> that it is now available, otherwise the concept of using it on-demand
> in broken.

Isn't that the point of registering an endpoint? If you have
registered, you are declaring you will accept data.

> Btw, this already is possible if you listen to
> Headset.State, also the interface was designed to have the connection
> on-demand, so you should only call Acquire when you gonna use the fd,
> anyway even in the case of audio transfer you maybe the initiator and
> should be able to directly control the connection via Acquire/Release
> to be able to do that so Resume/Suspend would not be that great even
> for IVI/carkit systems.

So that has me confused. If the MediaTransport interface is somewhat
generic, why would I want to listen to another interface to know if I
should call Acquire? In my case, I would need to listen to
HeadsetGateway. As it is, the audio from my SCO connection is sent
over a PCM bus, so I currently do not even register an SCO endpoint,
because it was not needed. I agree that if you are the initiator,
Acquire/Release is sufficient. In my case, as the non-initiator, it
is not sufficient because I do not want to open an audio link by
calling acquire unless it already exists.

My perception is that the interface is written from the point of view
of the audio source (A2DP Audio Source or HFP AG), but this does not
translate as well to the audio sinks (A2DP Audio Sink or HFP HF).

2012-03-26 14:41:34

by Luiz Augusto von Dentz

[permalink] [raw]
Subject: Re: media transport -- when is acquire ok to call?

Hi Mike,

On Fri, Mar 23, 2012 at 2:51 PM, Mike <[email protected]> wrote:
>
> Going back to this idea, it seems like MediaTransport should be
> redesigned to push the file descriptor to the endpoint, rather than
> the endpoint having to request it from the transport. ?this would
> solve this issue. ?The main problem is that acquiring the endpoint
> forces a call to resume. ?In the case of HFP, this is bad. ?I'm
> currently needing to implement HFP "Audio Connection Transfer Towards
> the AG". ?Since I am the HS, all I need to do is drop the SCO
> connection -- however, there is no interface to do this well. ?I tried
> implementing an SCO endpoint, since at least then the acquire and
> release calls would bring up an SCO connection and then allow me to
> drop it. ?The issue here is that a phone that is connected via HFP
> will have a MediaTransport even though the SCO connection will not yet
> exist. ?So, I get the SetConfiguration call which means I should be
> good to go on calling acquire. ?But, if I call acquire now, it will
> create a useless SCO connection to my phone that then is dropped.
> There's no reason at this point to open the SCO connection. ?I would
> rather be notified when the SCO connection exists, and have two
> additional methods called suspend and resume. ?In the case of HFP,
> calling resume would eventually result in a new FD being pushed to me.

Pushing maybe a good idea in case of not being the initiator the
connection as you mentioned, in the other hand the endpoint may not be
ready, or willing to use the fd, at that point so I would only signal
that it is now available, otherwise the concept of using it on-demand
in broken. Btw, this already is possible if you listen to
Headset.State, also the interface was designed to have the connection
on-demand, so you should only call Acquire when you gonna use the fd,
anyway even in the case of audio transfer you maybe the initiator and
should be able to directly control the connection via Acquire/Release
to be able to do that so Resume/Suspend would not be that great even
for IVI/carkit systems.



--
Luiz Augusto von Dentz

2012-03-23 17:51:12

by Mike Brudevold

[permalink] [raw]
Subject: Re: media transport -- when is acquire ok to call?

On Thu, Mar 22, 2012 at 12:18 PM, Luiz Augusto von Dentz
<[email protected]> wrote:
> Hi Mike,
>
> On Wed, Mar 21, 2012 at 4:02 PM, Mike <[email protected]> wrote:
>> I'm having some trouble with MediaEndpoint/MediaTransport and A2DP.
>> When I get the "SetConfiguration" call, I wait 2 seconds and then call
>> "Acquire", generally giving BlueZ enough time get the D-Bus interface
>> ready to go. ?However, the delay isn't always long enough. ?Shown
>> below is a time when my phone is attempting to pair with BlueZ. ?The
>> error "org.bluez.Error.NotAuthorized" is output from my application.
>> In this case, the problem is that the audio source is still in the
>> CONFIGURED state, not in the OPEN state. ?Is there a recommended
>> method of how long to wait before calling acquire? ?Or should I rely
>> on the AudioSource "State" property to become connected (or playing)?
>> Is there any reason I can't get the transport when in the Configured
>> state (does the fd not exist yet?)? ?Or why is "a2dp_resume" being
>> called on open (which is what is rejecting my acquire call)?
>
> In case of PA we do wait for Audio.Connected property before loading
> the module which does call MediaTransport.Acquire, but 2 seconds is
> too much there might be something else holding the setup, do you reply
> right away the SetConfiguration, if you do try to Acquire while
> bluetoothd is waiting you to reply it might fail.
>

Going back to this idea, it seems like MediaTransport should be
redesigned to push the file descriptor to the endpoint, rather than
the endpoint having to request it from the transport. this would
solve this issue. The main problem is that acquiring the endpoint
forces a call to resume. In the case of HFP, this is bad. I'm
currently needing to implement HFP "Audio Connection Transfer Towards
the AG". Since I am the HS, all I need to do is drop the SCO
connection -- however, there is no interface to do this well. I tried
implementing an SCO endpoint, since at least then the acquire and
release calls would bring up an SCO connection and then allow me to
drop it. The issue here is that a phone that is connected via HFP
will have a MediaTransport even though the SCO connection will not yet
exist. So, I get the SetConfiguration call which means I should be
good to go on calling acquire. But, if I call acquire now, it will
create a useless SCO connection to my phone that then is dropped.
There's no reason at this point to open the SCO connection. I would
rather be notified when the SCO connection exists, and have two
additional methods called suspend and resume. In the case of HFP,
calling resume would eventually result in a new FD being pushed to me.

2012-03-23 13:49:51

by Dalleau, Frederic

[permalink] [raw]
Subject: Re: media transport -- when is acquire ok to call?

Hi Mike, Luiz,

> I think I've figured out why I didn't see the SEP error print out.
> The function resume_a2dp calls a2dp_sep_lock. ?The only place this
> ever gets unlocked is in a suspend call. ?If a2dp_resume returns an
> error code, the sep remains forever locked. ?And it seems, the SEP
> will no longer let acquire happen on future A2DP connections,
> requiring bluetoothd to be restarted for this to work.

I'm experimenting similar issues right now on hfgw.
Could it be because the endpoint is crashing after acquiring?

Fr?d?ric

2012-03-22 21:21:36

by Mike Brudevold

[permalink] [raw]
Subject: Re: media transport -- when is acquire ok to call?

On Thu, Mar 22, 2012 at 3:53 PM, Mike <[email protected]> wrote:
> Hi Luiz,
>
> On Thu, Mar 22, 2012 at 12:18 PM, Luiz Augusto von Dentz
> <[email protected]> wrote:
>> Hi Mike,
>>
>> On Wed, Mar 21, 2012 at 4:02 PM, Mike <[email protected]> wrote:
>>> I'm having some trouble with MediaEndpoint/MediaTransport and A2DP.
>>> When I get the "SetConfiguration" call, I wait 2 seconds and then call
>>> "Acquire", generally giving BlueZ enough time get the D-Bus interface
>>> ready to go. ?However, the delay isn't always long enough. ?Shown
>>> below is a time when my phone is attempting to pair with BlueZ. ?The
>>> error "org.bluez.Error.NotAuthorized" is output from my application.
>>> In this case, the problem is that the audio source is still in the
>>> CONFIGURED state, not in the OPEN state. ?Is there a recommended
>>> method of how long to wait before calling acquire? ?Or should I rely
>>> on the AudioSource "State" property to become connected (or playing)?
>>> Is there any reason I can't get the transport when in the Configured
>>> state (does the fd not exist yet?)? ?Or why is "a2dp_resume" being
>>> called on open (which is what is rejecting my acquire call)?
>>
>> In case of PA we do wait for Audio.Connected property before loading
>> the module which does call MediaTransport.Acquire, but 2 seconds is
>> too much there might be something else holding the setup, do you reply
>> right away the SetConfiguration, if you do try to Acquire while
>> bluetoothd is waiting you to reply it might fail.
>
> I do reply right away. ?This is on an embedded device and it seems
> like BlueZ needs just a bit of time to get the interface ready or else
> I get 'Method "Acquire" with signature "s" on interface
> "org.bluez.MediaTransport" doesn't exist'.
>
>>> bluetoothd[751]: audio/avdtp.c:avdtp_parse_cmd() Received OPEN_CMD
>>> bluetoothd[751]: audio/a2dp.c:open_ind() Sink 0x2a0d40a8: Open_Ind
>>> bluetoothd[751]: audio/transport.c:media_transport_acquire() Transport
>>> /org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD/fd1: read lock acquired
>>> bluetoothd[751]: audio/transport.c:media_transport_acquire() Transport
>>> /org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD/fd1: write lock acquired
>>> bluetoothd[751]: audio/transport.c:media_owner_create() Owner created:
>>> sender=:1.40 accesstype=rw
>>> bluetoothd[751]: audio/avdtp.c:avdtp_ref() 0x2a0d2a00: ref=3
>>> bluetoothd[751]: audio/transport.c:media_transport_release() Transport
>>> /org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD/fd1: read lock released
>>> bluetoothd[751]: audio/transport.c:media_transport_release() Transport
>>> /org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD/fd1: write lock released
>>> bluetoothd[751]: audio/transport.c:media_owner_free() Owner :1.40
>>> getting the reply from the cb failed
>>> GDBus.Error:org.bluez.Error.NotAuthorized: Operation Not Authorized
>>
>> Strange, if what you said is true why there is no "SEP in bad state
>> for resume" error? Anyway I think we can fix this by checking the
>> current state of the SEP and waiting it to go OPEN to resume, so the
>> client don't have to keep tracking of Audio.Connected.
>
> I just tried it again, as I'd seen that message before, and this time
> it was happy enough to provide that error.
>
> bluetoothd[734]: audio/avdtp.c:avdtp_parse_cmd() Received OPEN_CMD
> bluetoothd[734]: audio/a2dp.c:open_ind() Sink 0x2a0f1ff8: Open_Ind
> bluetoothd[734]: audio/transport.c:media_transport_acquire() Transport
> /org/bluez/734/hci0/dev_00_17_E3_3B_4F_DD/fd0: read lock acquired
> bluetoothd[734]: audio/transport.c:media_transport_acquire() Transport
> /org/bluez/734/hci0/dev_00_17_E3_3B_4F_DD/fd0: write lock acquired
> bluetoothd[734]: audio/transport.c:media_owner_create() Owner created:
> sender=:1.12 accesstype=rw
> bluetoothd[734]: audio/avdtp.c:avdtp_ref() 0x2a11d980: ref=3
> bluetoothd[734]: audio/a2dp.c:a2dp_sep_lock() SEP 0x2a0f1ff8 locked
> bluetoothd[734]: audio/avdtp.c:avdtp_ref() 0x2a11d980: ref=4
> bluetoothd[734]: audio/a2dp.c:setup_ref() 0x2a0efb68: ref=1
> bluetoothd[734]: SEP in bad state for resume
>
> In this case, the OPEN_CMD is sent to my phone, but BlueZ and my phone
> are in a pairing process and the phone won't reply to this until the
> two are paired. ?Incidentally, after fixing a bug in avdtp.c,
>
> @@ -1520,7 +1520,7 @@ static gboolean avdtp_setconf_cmd(struct avdtp
> *session, uint8_t transaction,
> ? ? ? ?case AVDTP_SEP_TYPE_SINK:
> ? ? ? ? ? ? ? ?if (!dev->source) {
> ? ? ? ? ? ? ? ? ? ? ? ?btd_device_add_uuid(dev->btd_dev, A2DP_SOURCE_UUID);
> - ? ? ? ? ? ? ? ? ? ? ? if (!dev->sink) {
> + ? ? ? ? ? ? ? ? ? ? ? if (!dev->source) {
>
> my phone will reboot itself after pairing. ?I relaxed the REQ_TIMEOUT
> to 60 seconds, and with this change, my phone no longer reboots after
> pairing. ?I assume that my phone gets confused that the A2DP link was
> disconnected during the pairing operation.

I think I've figured out why I didn't see the SEP error print out.
The function resume_a2dp calls a2dp_sep_lock. The only place this
ever gets unlocked is in a suspend call. If a2dp_resume returns an
error code, the sep remains forever locked. And it seems, the SEP
will no longer let acquire happen on future A2DP connections,
requiring bluetoothd to be restarted for this to work.

2012-03-22 20:53:01

by Mike Brudevold

[permalink] [raw]
Subject: Re: media transport -- when is acquire ok to call?

Hi Luiz,

On Thu, Mar 22, 2012 at 12:18 PM, Luiz Augusto von Dentz
<[email protected]> wrote:
> Hi Mike,
>
> On Wed, Mar 21, 2012 at 4:02 PM, Mike <[email protected]> wrote:
>> I'm having some trouble with MediaEndpoint/MediaTransport and A2DP.
>> When I get the "SetConfiguration" call, I wait 2 seconds and then call
>> "Acquire", generally giving BlueZ enough time get the D-Bus interface
>> ready to go. ?However, the delay isn't always long enough. ?Shown
>> below is a time when my phone is attempting to pair with BlueZ. ?The
>> error "org.bluez.Error.NotAuthorized" is output from my application.
>> In this case, the problem is that the audio source is still in the
>> CONFIGURED state, not in the OPEN state. ?Is there a recommended
>> method of how long to wait before calling acquire? ?Or should I rely
>> on the AudioSource "State" property to become connected (or playing)?
>> Is there any reason I can't get the transport when in the Configured
>> state (does the fd not exist yet?)? ?Or why is "a2dp_resume" being
>> called on open (which is what is rejecting my acquire call)?
>
> In case of PA we do wait for Audio.Connected property before loading
> the module which does call MediaTransport.Acquire, but 2 seconds is
> too much there might be something else holding the setup, do you reply
> right away the SetConfiguration, if you do try to Acquire while
> bluetoothd is waiting you to reply it might fail.

I do reply right away. This is on an embedded device and it seems
like BlueZ needs just a bit of time to get the interface ready or else
I get 'Method "Acquire" with signature "s" on interface
"org.bluez.MediaTransport" doesn't exist'.

>> bluetoothd[751]: audio/avdtp.c:avdtp_parse_cmd() Received OPEN_CMD
>> bluetoothd[751]: audio/a2dp.c:open_ind() Sink 0x2a0d40a8: Open_Ind
>> bluetoothd[751]: audio/transport.c:media_transport_acquire() Transport
>> /org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD/fd1: read lock acquired
>> bluetoothd[751]: audio/transport.c:media_transport_acquire() Transport
>> /org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD/fd1: write lock acquired
>> bluetoothd[751]: audio/transport.c:media_owner_create() Owner created:
>> sender=:1.40 accesstype=rw
>> bluetoothd[751]: audio/avdtp.c:avdtp_ref() 0x2a0d2a00: ref=3
>> bluetoothd[751]: audio/transport.c:media_transport_release() Transport
>> /org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD/fd1: read lock released
>> bluetoothd[751]: audio/transport.c:media_transport_release() Transport
>> /org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD/fd1: write lock released
>> bluetoothd[751]: audio/transport.c:media_owner_free() Owner :1.40
>> getting the reply from the cb failed
>> GDBus.Error:org.bluez.Error.NotAuthorized: Operation Not Authorized
>
> Strange, if what you said is true why there is no "SEP in bad state
> for resume" error? Anyway I think we can fix this by checking the
> current state of the SEP and waiting it to go OPEN to resume, so the
> client don't have to keep tracking of Audio.Connected.

I just tried it again, as I'd seen that message before, and this time
it was happy enough to provide that error.

bluetoothd[734]: audio/avdtp.c:avdtp_parse_cmd() Received OPEN_CMD
bluetoothd[734]: audio/a2dp.c:open_ind() Sink 0x2a0f1ff8: Open_Ind
bluetoothd[734]: audio/transport.c:media_transport_acquire() Transport
/org/bluez/734/hci0/dev_00_17_E3_3B_4F_DD/fd0: read lock acquired
bluetoothd[734]: audio/transport.c:media_transport_acquire() Transport
/org/bluez/734/hci0/dev_00_17_E3_3B_4F_DD/fd0: write lock acquired
bluetoothd[734]: audio/transport.c:media_owner_create() Owner created:
sender=:1.12 accesstype=rw
bluetoothd[734]: audio/avdtp.c:avdtp_ref() 0x2a11d980: ref=3
bluetoothd[734]: audio/a2dp.c:a2dp_sep_lock() SEP 0x2a0f1ff8 locked
bluetoothd[734]: audio/avdtp.c:avdtp_ref() 0x2a11d980: ref=4
bluetoothd[734]: audio/a2dp.c:setup_ref() 0x2a0efb68: ref=1
bluetoothd[734]: SEP in bad state for resume

In this case, the OPEN_CMD is sent to my phone, but BlueZ and my phone
are in a pairing process and the phone won't reply to this until the
two are paired. Incidentally, after fixing a bug in avdtp.c,

@@ -1520,7 +1520,7 @@ static gboolean avdtp_setconf_cmd(struct avdtp
*session, uint8_t transaction,
case AVDTP_SEP_TYPE_SINK:
if (!dev->source) {
btd_device_add_uuid(dev->btd_dev, A2DP_SOURCE_UUID);
- if (!dev->sink) {
+ if (!dev->source) {

my phone will reboot itself after pairing. I relaxed the REQ_TIMEOUT
to 60 seconds, and with this change, my phone no longer reboots after
pairing. I assume that my phone gets confused that the A2DP link was
disconnected during the pairing operation.

2012-03-22 17:18:37

by Luiz Augusto von Dentz

[permalink] [raw]
Subject: Re: media transport -- when is acquire ok to call?

Hi Mike,

On Wed, Mar 21, 2012 at 4:02 PM, Mike <[email protected]> wrote:
> I'm having some trouble with MediaEndpoint/MediaTransport and A2DP.
> When I get the "SetConfiguration" call, I wait 2 seconds and then call
> "Acquire", generally giving BlueZ enough time get the D-Bus interface
> ready to go. ?However, the delay isn't always long enough. ?Shown
> below is a time when my phone is attempting to pair with BlueZ. ?The
> error "org.bluez.Error.NotAuthorized" is output from my application.
> In this case, the problem is that the audio source is still in the
> CONFIGURED state, not in the OPEN state. ?Is there a recommended
> method of how long to wait before calling acquire? ?Or should I rely
> on the AudioSource "State" property to become connected (or playing)?
> Is there any reason I can't get the transport when in the Configured
> state (does the fd not exist yet?)? ?Or why is "a2dp_resume" being
> called on open (which is what is rejecting my acquire call)?

In case of PA we do wait for Audio.Connected property before loading
the module which does call MediaTransport.Acquire, but 2 seconds is
too much there might be something else holding the setup, do you reply
right away the SetConfiguration, if you do try to Acquire while
bluetoothd is waiting you to reply it might fail.

> bluetoothd[751]: audio/avdtp.c:avdtp_parse_cmd() Received OPEN_CMD
> bluetoothd[751]: audio/a2dp.c:open_ind() Sink 0x2a0d40a8: Open_Ind
> bluetoothd[751]: audio/transport.c:media_transport_acquire() Transport
> /org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD/fd1: read lock acquired
> bluetoothd[751]: audio/transport.c:media_transport_acquire() Transport
> /org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD/fd1: write lock acquired
> bluetoothd[751]: audio/transport.c:media_owner_create() Owner created:
> sender=:1.40 accesstype=rw
> bluetoothd[751]: audio/avdtp.c:avdtp_ref() 0x2a0d2a00: ref=3
> bluetoothd[751]: audio/transport.c:media_transport_release() Transport
> /org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD/fd1: read lock released
> bluetoothd[751]: audio/transport.c:media_transport_release() Transport
> /org/bluez/751/hci0/dev_00_17_E3_3B_4F_DD/fd1: write lock released
> bluetoothd[751]: audio/transport.c:media_owner_free() Owner :1.40
> getting the reply from the cb failed
> GDBus.Error:org.bluez.Error.NotAuthorized: Operation Not Authorized

Strange, if what you said is true why there is no "SEP in bad state
for resume" error? Anyway I think we can fix this by checking the
current state of the SEP and waiting it to go OPEN to resume, so the
client don't have to keep tracking of Audio.Connected.


--
Luiz Augusto von Dentz

2012-07-05 06:58:08

by Mikel Astiz

[permalink] [raw]
Subject: AW: media transport -- when is acquire ok to call?

Hi Luiz,

> Hi Mikel,
>
> On Tue, Mar 27, 2012 at 1:31 AM, Mikel Astiz <[email protected]>
> wrote:
> > Hi Mike,
> >
> >> So that has me confused. ?If the MediaTransport interface is somewhat
> >> generic, why would I want to listen to another interface to know if I
> >> should call Acquire? ?In my case, I would need to listen to
> >> HeadsetGateway. ?As it is, the audio from my SCO connection is sent
> >> over a PCM bus, so I currently do not even register an SCO endpoint,
> >> because it was not needed. ?I agree that if you are the initiator,
> >> Acquire/Release is sufficient. ?In my case, as the non-initiator, it
> >> is not sufficient because I do not want to open an audio link by
> >> calling acquire unless it already exists.
> >
> > I'm not sure if this solves your specific problem(s) but I would propose that
> the MediaTransport API is extended with a method such as TryAcquire (or
> alternatively Acquire can be extended with either one more parameter, or
> some specific flag in accesstype). In that case the transport would not be
> acquired unless the audio link already exists.
> >
> > The current approach of listening to a state property and then calling
> Acquire is racy, no matter if the property is in the same interface or not.
>
> I think your proposal would fix this race in a way that doesn't fundamentally
> change the current design, so I'm in favor of it.
>
> > Regarding your comment on the need to listen to a different interface, I
> don't think this should be a big problem. Having said that, the Playing state in
> HeadsetGateway (and equivalents) could be replaced by a state in
> MediaTransport. That actually seems more appropriate to me.
>
> Agreed. The reason I don't like the current approach is that there is no
> explicit connection between the MediaTransport object and the other object
> that has the state property.
>
> Mike

The issue above could be briefly discussed next week as well.

Cheers,
Mikel