Linux bluetooth development
 help / color / mirror / Atom feed
* Re: [RFC] LE connections and advertising management
From: Claudio Takahasi @ 2010-10-27  1:01 UTC (permalink / raw)
  To: Mike Tsai; +Cc: BlueZ development
In-Reply-To: <35B17FE5076C7040809188FBE7913F983F84405C72@SC1EXMB-MBCL.global.atheros.com>

Hi Mike,

On Tue, Oct 26, 2010 at 6:10 PM, Mike Tsai <Mike.Tsai@atheros.com> wrote:
> [Mike Tsai]
> Hi Claudio,
>
>        I look at the API and it is well-defined with high level of abstraction. However, I did have a few questions here, hopefully you can answer them,
>
>        On Client side:
>
>                1. I see you didn't offer any service discovery API for client to discover the server service database (basically to get the attribute handles). So I assume that you consider GATT discovery procedure works the same way as SDP, done automatically by GATT after link is established without application's initiative. Am I correct?
>
>                2. The characteristic descriptor set via SetProperty API is limited to the 6 characteristic descriptors defined in GATT spec. However, there could be profile specific characteristic descriptors beyond these, will the SetProperty able to support these?
>
>                3. The characteristic monitoring is set up via 128 bits UUID. Do you have mechanism to handle duplicated characteristic within a server's database? How do you identify them via your API?
>
>
>        On Server side:
>
>                1. Is there an API that allows server application to register new attributes? (primary service, characteristic, included service, et al),
>
> Regards,
>
> Mike

Client side:
Yes. ALL characteristics are fetched after "create the device"
procedure.  This approach is wrong, some characteristics requires
encryption, authentication or authorization. Another aspect is that we
need to avoid excessive transactions. The idea now is try to search
for the primary service information only and "probe" the clients that
match with the registered service UUID. When "probed" the clients will
receive the GAttrib instance and the primary service handles range. It
is up to them to decide which attributes are relevant. Note that the
clients are only another "layer" implementing profile specific
features inside BlueZ.

It is a little bit unclear to me at the moment, but we can expose
Profile specific features. Such as threshold, alert level, ...

Is it allowed duplicated UUIDs for the same primary service? We are
not handling this right now.
It seems that you already have a proprietary implementation ;-)

Server side:
No API. We wrote an attribute server for testing purpose only. But we
will address this soon.

Regards,
Claudio

^ permalink raw reply

* Re: AVRCP 1.4 : Future on Target Role
From: shivendra.agrawal@stericsson.com @ 2010-10-27  6:57 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <AANLkTi=g+8UDsSQBnqBWk=Ly=xCmfvwX_ZCMsn_kU9Fb@mail.gmail.com>

Hi All,

ST-Ericsson plans to implement the commands to support target role of
AVRCP 1.4 Profile, and we would like to contribute it to BlueZ.
With our initial discussion, I would be aligning with BlueZ
contributors and would propose for the ideas that has not been
touched/developed so far, in order to have a design/implementation
that can be accepted.

As a very first, and very rough, design proposal for the BlueZ parts:
- A new SDP record for AVRCP 1.4 would be added to inform CT of the
version and features supported by target.
- A new callback to accept browsing channel establishment.
- Enhancing similar to bt_io_listen for browsing PSM.
- A new browsing command handler
- Incremental addition to AVRCP 1.4 commands.

Any feedback is very much appreciated!

Regards,
Shivendra


2010/10/25 João Paulo Rechi Vita <jprvita@gmail.com>:
> 2010/10/25 Shivendra Agrawal <ag.shivendra@gmail.com>:
>> 2010/10/23 João Paulo Rechi Vita <jprvita@gmail.com>:
>>> Hello all,
>>>
>>> I've seen some discuss regarding how to add support for AVRCP 1.3 and
>>> 1.4 versions on the ML lately, and some expectations over the related
>>> work I've done in BlueZ. Sorry for the long delay on replying, I've
>>> been pretty busy lately and just didn't got the time. I'm planing to
>>> put some effort again on this work on the coming weeks.
>>>
>>> On Tue, Oct 19, 2010 at 14:14, Luiz Augusto von Dentz
>>> <luiz.dentz@gmail.com> wrote:
>>>> Hi,
>>>>
>>>> On Tue, Oct 19, 2010 at 12:47 PM, Sander van Grieken
>>>> <sander@outrightsolutions.nl> wrote:
>>>>> I am very much in favor of not directly depending on MPRIS, but instead letting
>>>>> applications registering themselves as a target. For two reasons:
>>>>>
>>>>> - AVRCP seems to be a superset of MPRIS (which is very limited IMO), and might have
>>>>> different semantics, especially w.r.t. event notifications. So we would limit ourselves to
>>>>> the intersecting subset of both technologies.
>>>>> - A separate AVRCP/TG <-> MPRIS bridge agent would still allow controlling all MPRIS-
>>>>> enabled players, so we can have both full implementation of the AVRCP spec, AND generic
>>>>> MPRIS support.
>>>>
>>>> Sounds good to me, we can use Media API to register players as well.
>>>>
>>>
>>> I agree with Sander's opinion that MPRIS seems a bit limited for 1.4.
>>> OTOH it's an already defined and under-adoption standard. If we have
>>> applications registering themselves directly with us, we'll have to
>>> define a new interface for that and push this to the player
>>> applications. Do you guys already have a draft of these interfaces
>>> (for the applications and extensions to the Media API)? I guess we
>>> should try to define exactly what we need first, and them see what's
>>> missing from MPRIS.
>>>
>>>>>> > I am keen to receive your feedback with some ideas and thoughts to put
>>>>>> > my effort in right direction.
>>>>>> >
>>>>>> > Question:
>>>>>> > Is anyone working on AVRCP 1.4 Target role profile development?
>>>>>>
>>>>>> Joao Paulo (http://jprvita.wordpress.com/2010/07/22/avrcp-metadata/)
>>>>>
>>>>> Actually, the metadata work is not part of v1.4 of the spec, but 1.3
>>>>>
>>>>> Second, I have already added some boilerplate stuff (like a DBUS Connect method for RCP and
>>>>> some fixes for CT commands), but I've based on Joao's branch, so I have to wait until his
>>>>> stuff gets merged. Alternatively, I could rebase that stuff on HEAD, but that would overlap
>>>>> and conflict with Joao's stuff, so I'm hesitant to go there.
>>>>
>>>
>>> Have you published this code somewhere?
>>>
>>>> I hope to see this code being push upstream soon, I will try to
>>>> contact Joao Paulo to get an idea if the code is ready to be
>>>> reviewed/pushed so we get the things rolling.
>>>>
>>>
>>> I'm finally here :) I've focused mostly in the 1.3 version of the spec
>>> and having pulseaudio as a middle-man in my work, and have written
>>> most of the code in pulseaudio to handle these new functionality. Even
>>> if we take the approach described above for 1.4, IMO it makes sense to
>>> upstream this so we can have earlier support for 1.3 and also to
>>> support Sander's work. Luiz, Johan, what do you think?
>>>
>>> I'll review the code once more, since I've written it a few months
>>> ago, but my main concern about pushing it upstream right now is that
>>> it hasn't been tested yet. I have no device to test against and PTS
>>> can't give us no guarantee whether the code really works in practice
>>> or not (but it's still better than nothing). Sander, David, have you
>>> tested my code against any real device?
>>
>> You are right, PTS does not guarantee, but I guess, PTS viewer can support
>> checking the frame that is sent is as per protocol.
>> This could give a safe hands of the implementation. Does that assumption helps?
>
> Yes, you can view what is passing by the bluetooth radio, but it's
> still the same as testing against the PTS only. The best would be to
> have device which someone could test against.
>
> --
> João Paulo Rechi Vita
> http://jprvita.wordpress.com/
>

^ permalink raw reply

* Re: AVRCP 1.4 : Future on Target Role
From: Gustavo F. Padovan @ 2010-10-27  7:33 UTC (permalink / raw)
  To: shivendra.agrawal@stericsson.com; +Cc: linux-bluetooth
In-Reply-To: <AANLkTinodSvkAffPKrHT_Yd9nwXwAdQoqacD9vJt-F96@mail.gmail.com>

Hi Shivendra,

* shivendra.agrawal@stericsson.com <ag.shivendra@gmail.com> [2010-10-27 12:27:54 +0530]:

> Hi All,
> 
> ST-Ericsson plans to implement the commands to support target role of
> AVRCP 1.4 Profile, and we would like to contribute it to BlueZ.
> With our initial discussion, I would be aligning with BlueZ
> contributors and would propose for the ideas that has not been
> touched/developed so far, in order to have a design/implementation
> that can be accepted.
> 
> As a very first, and very rough, design proposal for the BlueZ parts:
> - A new SDP record for AVRCP 1.4 would be added to inform CT of the
> version and features supported by target.
> - A new callback to accept browsing channel establishment.
> - Enhancing similar to bt_io_listen for browsing PSM.
> - A new browsing command handler
> - Incremental addition to AVRCP 1.4 commands.
> 
> Any feedback is very much appreciated!

Top posting is not allowed in this mailing list. Thanks. ;)

-- 
Gustavo F. Padovan
ProFUSION embedded systems - http://profusion.mobi

^ permalink raw reply

* [RFC] AVRCP 1.4 : Design proposal for future on Target Role
From: shivendra.agrawal@stericsson.com @ 2010-10-27  8:23 UTC (permalink / raw)
  To: linux-bluetooth

Hi All,

ST-Ericsson plans to implement the commands to support target role of
AVRCP 1.4 Profile, and we would like to contribute it to BlueZ.
With our initial discussion, I would be aligning with BlueZ
contributors and would propose for the ideas that has not been
touched/developed so far, in order to have a design/implementation
that can be accepted.

As a very first, and very rough, design proposal for the BlueZ parts:
- A new SDP record for AVRCP 1.4 would be added to inform CT of the
version and features supported by target.
- A new callback to accept browsing channel establishment.
- Enhancing similar to bt_io_listen for browsing PSM.
- A new browsing command handler
- Incremental addition to AVRCP 1.4 commands.

Any feedback is very much appreciated!

Ref: Previous discussion subject: "AVRCP 1.4 : Future on Target Role"

Regards,
Shivendra

^ permalink raw reply

* Re: AVRCP 1.4 : Future on Target Role
From: shivendra.agrawal@stericsson.com @ 2010-10-27  8:46 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <AANLkTi=ThA2ojhj8PBHK_VybmFcHO91K0g=y7nhfTBAO@mail.gmail.com>

2010/10/23 João Paulo Rechi Vita <jprvita@gmail.com>:
> Hello all,
>
> I've seen some discuss regarding how to add support for AVRCP 1.3 and
> 1.4 versions on the ML lately, and some expectations over the related
> work I've done in BlueZ. Sorry for the long delay on replying, I've
> been pretty busy lately and just didn't got the time. I'm planing to
> put some effort again on this work on the coming weeks.
>
> On Tue, Oct 19, 2010 at 14:14, Luiz Augusto von Dentz
> <luiz.dentz@gmail.com> wrote:
>> Hi,
>>
>> On Tue, Oct 19, 2010 at 12:47 PM, Sander van Grieken
>> <sander@outrightsolutions.nl> wrote:
>>> I am very much in favor of not directly depending on MPRIS, but instead letting
>>> applications registering themselves as a target. For two reasons:
>>>
>>> - AVRCP seems to be a superset of MPRIS (which is very limited IMO), and might have
>>> different semantics, especially w.r.t. event notifications. So we would limit ourselves to
>>> the intersecting subset of both technologies.
>>> - A separate AVRCP/TG <-> MPRIS bridge agent would still allow controlling all MPRIS-
>>> enabled players, so we can have both full implementation of the AVRCP spec, AND generic
>>> MPRIS support.
>>
>> Sounds good to me, we can use Media API to register players as well.
>>
>
> I agree with Sander's opinion that MPRIS seems a bit limited for 1.4.
> OTOH it's an already defined and under-adoption standard. If we have
> applications registering themselves directly with us, we'll have to
> define a new interface for that and push this to the player
> applications. Do you guys already have a draft of these interfaces
> (for the applications and extensions to the Media API)? I guess we
> should try to define exactly what we need first, and them see what's
> missing from MPRIS.
>
>>>> > I am keen to receive your feedback with some ideas and thoughts to put
>>>> > my effort in right direction.
>>>> >
>>>> > Question:
>>>> > Is anyone working on AVRCP 1.4 Target role profile development?
>>>>
>>>> Joao Paulo (http://jprvita.wordpress.com/2010/07/22/avrcp-metadata/)
>>>
>>> Actually, the metadata work is not part of v1.4 of the spec, but 1.3
>>>
>>> Second, I have already added some boilerplate stuff (like a DBUS Connect method for RCP and
>>> some fixes for CT commands), but I've based on Joao's branch, so I have to wait until his
>>> stuff gets merged. Alternatively, I could rebase that stuff on HEAD, but that would overlap
>>> and conflict with Joao's stuff, so I'm hesitant to go there.
>>
>
> Have you published this code somewhere?
>
>> I hope to see this code being push upstream soon, I will try to
>> contact Joao Paulo to get an idea if the code is ready to be
>> reviewed/pushed so we get the things rolling.
>>
>
> I'm finally here :) I've focused mostly in the 1.3 version of the spec
> and having pulseaudio as a middle-man in my work, and have written
> most of the code in pulseaudio to handle these new functionality. Even
> if we take the approach described above for 1.4, IMO it makes sense to
> upstream this so we can have earlier support for 1.3 and also to
> support Sander's work. Luiz, Johan, what do you think?
>
> I'll review the code once more, since I've written it a few months
> ago, but my main concern about pushing it upstream right now is that
> it hasn't been tested yet. I have no device to test against and PTS
> can't give us no guarantee whether the code really works in practice
> or not (but it's still better than nothing). Sander, David, have you
> tested my code against any real device?
>
I have requested some inputs from all to start exchange our ideas as
Subject: [RFC] AVRCP 1.4 : Design proposal for future on Target Role
I would be keen to receive your feedback. Thanks in advance.

^ permalink raw reply

* [PATCH 1/2] Optimize call history queries
From: Rafał Michalski @ 2010-10-27  8:53 UTC (permalink / raw)
  To: linux-bluetooth; +Cc: Rafał Michalski

[-- Attachment #1: Type: text/plain, Size: 1 bytes --]



[-- Attachment #2: 0001-Optimize-call-history-queries.patch --]
[-- Type: text/x-patch, Size: 5575 bytes --]

From 59bad107ec51e6824b0c4450f4c67ab1e4505cff Mon Sep 17 00:00:00 2001
From: Rafal Michalski <michalski.raf@gmail.com>
Date: Wed, 27 Oct 2010 09:19:21 +0200
Subject: [PATCH 1/2] Optimize call history queries

This patch optimizes call history queries - now there is no redundant
results of invoking them.
---
 plugins/phonebook-tracker.c |   74 ++++++++++++++++++++----------------------
 1 files changed, 35 insertions(+), 39 deletions(-)

diff --git a/plugins/phonebook-tracker.c b/plugins/phonebook-tracker.c
index 3367e49..e037677 100644
--- a/plugins/phonebook-tracker.c
+++ b/plugins/phonebook-tracker.c
@@ -128,6 +128,13 @@
 	"WHERE { "							\
 	"{ "								\
 		"?x a nco:Contact . "					\
+		"?x nco:hasPhoneNumber ?t . "				\
+		"?call a nmo:Call ; "					\
+		"nmo:from ?x ; "					\
+		"nmo:isSent false ; "					\
+		"nmo:isAnswered false . "				\
+	"} UNION { "							\
+		"?x a nco:Contact . "					\
 		"?x nco:hasPhoneNumber ?h . "				\
 		"?call a nmo:Call ; "					\
 		"nmo:from ?x ; "					\
@@ -158,15 +165,8 @@
 		"OPTIONAL { ?a nco:hasEmailAddress ?ew . } "		\
 		"OPTIONAL { ?a nco:hasPostalAddress ?pw . } "		\
 		"OPTIONAL { ?a nco:org ?o . } "				\
-	"} UNION { "							\
-		"?x a nco:Contact . "					\
-		"?x nco:hasPhoneNumber ?t . "				\
-		"?call a nmo:Call ; "					\
-		"nmo:from ?x ; "					\
-		"nmo:isSent false ; "					\
-		"nmo:isAnswered false . "				\
 	"} "								\
-	"} ORDER BY DESC(nmo:receivedDate(?call)) "
+	"} GROUP BY ?call ORDER BY DESC(nmo:receivedDate(?call)) "
 
 #define MISSED_CALLS_LIST						\
 	"SELECT ?c nco:nameFamily(?c) "					\
@@ -221,6 +221,13 @@
 	"WHERE { "							\
 	"{ "								\
 		"?x a nco:Contact . "					\
+		"?x nco:hasPhoneNumber ?t . "				\
+		"?call a nmo:Call ; "					\
+		"nmo:from ?x ; "					\
+		"nmo:isSent false ; "					\
+		"nmo:isAnswered true . "				\
+	"} UNION { "							\
+		"?x a nco:Contact . "					\
 		"?x nco:hasPhoneNumber ?h . "				\
 		"?call a nmo:Call ; "					\
 		"nmo:from ?x ; "					\
@@ -251,15 +258,8 @@
 		"OPTIONAL { ?a nco:hasEmailAddress ?ew . } "		\
 		"OPTIONAL { ?a nco:hasPostalAddress ?pw . } "		\
 		"OPTIONAL { ?a nco:org ?o . } "				\
-	"} UNION { "							\
-		"?x a nco:Contact . "					\
-		"?x nco:hasPhoneNumber ?t . "				\
-		"?call a nmo:Call ; "					\
-		"nmo:from ?x ; "					\
-		"nmo:isSent false ; "					\
-		"nmo:isAnswered true . "				\
 	"} "								\
-	"} ORDER BY DESC(nmo:receivedDate(?call)) "
+	"} GROUP BY ?call ORDER BY DESC(nmo:receivedDate(?call)) "
 
 #define INCOMING_CALLS_LIST						\
 	"SELECT ?c nco:nameFamily(?c) "					\
@@ -314,6 +314,12 @@
 	"WHERE { "							\
 	"{ "								\
 		"?x a nco:Contact . "					\
+		"?x nco:hasPhoneNumber ?t . "				\
+		"?call a nmo:Call ; "					\
+		"nmo:to ?x ; "						\
+		"nmo:isSent true . "					\
+	"} UNION { "							\
+		"?x a nco:Contact . "					\
 		"?x nco:hasPhoneNumber ?h . "				\
 		"?call a nmo:Call ; "					\
 		"nmo:to ?x ; "						\
@@ -342,14 +348,8 @@
 		"OPTIONAL { ?a nco:hasEmailAddress ?ew . } "		\
 		"OPTIONAL { ?a nco:hasPostalAddress ?pw . } "		\
 		"OPTIONAL { ?a nco:org ?o . } "				\
-	"} UNION { "							\
-		"?x a nco:Contact . "					\
-		"?x nco:hasPhoneNumber ?t . "				\
-		"?call a nmo:Call ; "					\
-		"nmo:to ?x ; "						\
-		"nmo:isSent true . "					\
 	"} "								\
-	"} ORDER BY DESC(nmo:sentDate(?call)) "
+	"} GROUP BY ?call ORDER BY DESC(nmo:sentDate(?call)) "
 
 #define OUTGOING_CALLS_LIST						\
 	"SELECT ?c nco:nameFamily(?c) "					\
@@ -400,7 +400,12 @@
 	"nmo:isSent(?call) nmo:isAnswered(?call) ?x "			\
 	"WHERE { "							\
 	"{ "								\
-		"{ "							\
+		"?x a nco:Contact . "					\
+		"?x nco:hasPhoneNumber ?t . "				\
+		"?call a nmo:Call ; "					\
+		"nmo:to ?x ; "						\
+		"nmo:isSent true . "					\
+	"} UNION { "							\
 		"?x a nco:Contact . "					\
 		"?x nco:hasPhoneNumber ?h . "				\
 		"?call a nmo:Call ; "					\
@@ -416,7 +421,7 @@
 			"OPTIONAL { ?a nco:hasPostalAddress ?pw . } "	\
 			"OPTIONAL { ?a nco:org ?o . } "			\
 		"} "							\
-		"} UNION { "						\
+	"} UNION { "							\
 		"?x a nco:Contact . "					\
 		"?x nco:hasPhoneNumber ?w . "				\
 		"?call a nmo:Call ; "					\
@@ -430,15 +435,13 @@
 		"OPTIONAL { ?a nco:hasEmailAddress ?ew . } "		\
 		"OPTIONAL { ?a nco:hasPostalAddress ?pw . } "		\
 		"OPTIONAL { ?a nco:org ?o . } "				\
-		"} UNION { "						\
+	"} UNION { "							\
 		"?x a nco:Contact . "					\
 		"?x nco:hasPhoneNumber ?t . "				\
 		"?call a nmo:Call ; "					\
-		"nmo:to ?x ; "						\
-		"nmo:isSent true . "					\
-		"} "							\
+		"nmo:from ?x ; "					\
+		"nmo:isSent false . "					\
 	"} UNION { "							\
-		"{ "							\
 		"?x a nco:Contact . "					\
 		"?x nco:hasPhoneNumber ?h . "				\
 		"?call a nmo:Call ; "					\
@@ -454,7 +457,7 @@
 			"OPTIONAL { ?a nco:hasPostalAddress ?pw . } "	\
 			"OPTIONAL { ?a nco:org ?o . } "			\
 		"} "							\
-		"} UNION { "						\
+	"} UNION { "							\
 		"?x a nco:Contact . "					\
 		"?x nco:hasPhoneNumber ?w . "				\
 		"?call a nmo:Call ; "					\
@@ -468,15 +471,8 @@
 		"OPTIONAL { ?a nco:hasEmailAddress ?ew . } "		\
 		"OPTIONAL { ?a nco:hasPostalAddress ?pw . } "		\
 		"OPTIONAL { ?a nco:org ?o . } "				\
-		"} UNION { "						\
-		"?x a nco:Contact . "					\
-		"?x nco:hasPhoneNumber ?t . "				\
-		"?call a nmo:Call ; "					\
-		"nmo:from ?x ; "					\
-		"nmo:isSent false . "					\
-		"} "							\
 	"} "								\
-	"} ORDER BY DESC(nmo:receivedDate(?call)) "
+	"} GROUP BY ?call ORDER BY DESC(nmo:receivedDate(?call)) "
 
 #define COMBINED_CALLS_LIST						\
 	"SELECT ?c nco:nameFamily(?c) nco:nameGiven(?c) "		\
-- 
1.6.3.3


^ permalink raw reply related

* [PATCH 2/2] Remove redundant code in phonebook module
From: Rafał Michalski @ 2010-10-27  8:53 UTC (permalink / raw)
  To: linux-bluetooth; +Cc: Rafał Michalski

[-- Attachment #1: Type: text/plain, Size: 1 bytes --]



[-- Attachment #2: 0002-Remove-redundant-code-in-phonebook-module.patch --]
[-- Type: text/x-patch, Size: 1448 bytes --]

From 93465ab642893a508b8543edc4919a1bcd47436b Mon Sep 17 00:00:00 2001
From: Rafal Michalski <michalski.raf@gmail.com>
Date: Wed, 27 Oct 2010 09:20:00 +0200
Subject: [PATCH 2/2] Remove redundant code in phonebook module

Some extra code is redundant and not needed anymore. It is an effect
of call history queries optimization.
---
 plugins/phonebook-tracker.c |   18 ++----------------
 1 files changed, 2 insertions(+), 16 deletions(-)

diff --git a/plugins/phonebook-tracker.c b/plugins/phonebook-tracker.c
index e037677..96290a4 100644
--- a/plugins/phonebook-tracker.c
+++ b/plugins/phonebook-tracker.c
@@ -949,24 +949,10 @@ static struct phonebook_contact *find_contact(GSList *contacts, const char *id)
 static struct phonebook_number *find_phone(GSList *numbers, const char *phone,
 								int type)
 {
-	GSList *l = numbers;
+	GSList *l;
 	struct phonebook_number *pb_num;
 
-	if (g_slist_length(l) == 1 && (pb_num = l->data) &&
-					g_strcmp0(pb_num->tel, phone) == 0) {
-
-		if ((type == TEL_TYPE_HOME || type == TEL_TYPE_WORK) &&
-					pb_num->type == TEL_TYPE_OTHER)	{
-			pb_num->type = type;
-			return pb_num;
-		}
-
-		if (type == TEL_TYPE_OTHER && (pb_num->type == TEL_TYPE_HOME ||
-					pb_num->type == TEL_TYPE_WORK))
-			return pb_num;
-	}
-
-	for (; l; l = l->next) {
+	for (l = numbers; l; l = l->next) {
 		pb_num = l->data;
 		/* Returning phonebook number if phone values and type values
 		 * are equal */
-- 
1.6.3.3


^ permalink raw reply related

* Re: [PATCH 1/2] Optimize call history queries
From: Johan Hedberg @ 2010-10-27 13:49 UTC (permalink / raw)
  To: Rafał Michalski; +Cc: linux-bluetooth
In-Reply-To: <AANLkTikwCntXxSzqc1VpA1L27UChsHK=GLmhcHXb8coX@mail.gmail.com>

Hi Rafal,

On Wed, Oct 27, 2010, Rafał Michalski wrote:
> This patch optimizes call history queries - now there is no redundant
> results of invoking them.
> ---
>  plugins/phonebook-tracker.c |   74 ++++++++++++++++++++----------------------
>  1 files changed, 35 insertions(+), 39 deletions(-)

Pushed upstream. Thanks. Btw, if possible please send the patches in the
message body instead of an attachment (use e.g. git send-email for
this).  This would make your patch submissions more consistent with the
rest and ease my work (by not having to always check if I should pipe
the main message or the attachment to git am).

Johan

^ permalink raw reply

* Re: [PATCH 2/2] Remove redundant code in phonebook module
From: Johan Hedberg @ 2010-10-27 13:51 UTC (permalink / raw)
  To: Rafał Michalski; +Cc: linux-bluetooth
In-Reply-To: <AANLkTinnbp6DFvivhX1WC6cvE5G1tzTSV5VhNNphieqn@mail.gmail.com>

Hi Rafal,

On Wed, Oct 27, 2010, Rafał Michalski wrote:
> Some extra code is redundant and not needed anymore. It is an effect
> of call history queries optimization.
> ---
>  plugins/phonebook-tracker.c |   18 ++----------------
>  1 files changed, 2 insertions(+), 16 deletions(-)

This patch has also been pushed upstream. Thanks.

Johan

^ permalink raw reply

* Re: [PATCH 1/9] mfd: Add support for the ST-Ericsson CG2900.
From: Linus Walleij @ 2010-10-27 14:58 UTC (permalink / raw)
  To: Arnd Bergmann; +Cc: Par-Gunnar Hjalmdahl, linux-bluetooth, linux-kernel
In-Reply-To: <201010261406.10996.arnd@arndb.de>

2010/10/26 Arnd Bergmann <arnd@arndb.de>:

> If CG2900 is a single
> piece of silicon that always looks the same way, it's probably an MFD.

It is:
http://www.stericsson.com/product/223489.jsp

So atleast we have that part right :-)

(And thanks for all the good feedback Arnd, really appreciated!)

Yours,
Linus Walleij

^ permalink raw reply

* [PATCH] Bluetooth: Automate remote name requests
From: johan.hedberg @ 2010-10-27 16:25 UTC (permalink / raw)
  To: linux-bluetooth; +Cc: Johan Hedberg

From: Johan Hedberg <johan.hedberg@nokia.com>

In Bluetooth there are no automatic updates of remote device names when
they get changed on the remote side. Instead, it is a good idea to do a
manual name request when a new connection gets created (for whatever
reason) since at this point it is very cheap (no costly baseband
connection creation needed just for the sake of the name request).

So far userspace has been responsible for this extra name request but
tighter control is needed in order not to flood Bluetooth controllers
with two many commands during connection creation. It has been shown
that some controllers simply fail to function correctly if they get too
many (almost) simultaneous commands during connection creation. The
simplest way to acheive better control of these commands is to move
their sending completely to the kernel side.

This patch inserts name requests into the sequence of events that the
kernel performs during connection creation. It does this after the
remote features have been successfully requested and before any pending
authentication requests are performed. The code will work sub-optimally
with userspace versions that still do the name requesting themselves (it
shouldn't break anything though) so it is recommended to combine this
with a userspace software version that doesn't have automated name
requests.

Signed-off-by: Johan Hedberg <johan.hedberg@nokia.com>
---
 net/bluetooth/hci_event.c |   66 ++++++++++++++++++++++++++++++++++++++++----
 1 files changed, 60 insertions(+), 6 deletions(-)

diff --git a/net/bluetooth/hci_event.c b/net/bluetooth/hci_event.c
index 84093b0..05ad699 100644
--- a/net/bluetooth/hci_event.c
+++ b/net/bluetooth/hci_event.c
@@ -677,9 +677,51 @@ static void hci_cs_set_conn_encrypt(struct hci_dev *hdev, __u8 status)
 	hci_dev_unlock(hdev);
 }
 
+static void request_outgoing_auth(struct hci_dev *hdev, bdaddr_t *bdaddr)
+{
+	struct hci_cp_auth_requested cp;
+	struct hci_conn *conn;
+
+	conn = hci_conn_hash_lookup_ba(hdev, ACL_LINK, bdaddr);
+	if (!conn)
+		return;
+
+	if (conn->state != BT_CONFIG || !conn->out)
+		return;
+
+	if (conn->sec_level == BT_SECURITY_SDP)
+		return;
+
+	/* Only request authentication for SSP connections or non-SSP
+	 * devices with sec_level HIGH */
+	if (!(hdev->ssp_mode > 0 && conn->ssp_mode > 0) &&
+					conn->sec_level != BT_SECURITY_HIGH)
+		return;
+
+	cp.handle = __cpu_to_le16(conn->handle);
+	hci_send_cmd(hdev, HCI_OP_AUTH_REQUESTED, sizeof(cp), &cp);
+}
+
 static void hci_cs_remote_name_req(struct hci_dev *hdev, __u8 status)
 {
+	struct hci_cp_remote_name_req *cp;
+
 	BT_DBG("%s status 0x%x", hdev->name, status);
+
+	/* If successful wait for the name req complete event before
+	 * checking for the need to do authentication */
+	if (status == 0)
+		return;
+
+	cp = hci_sent_cmd_data(hdev, HCI_OP_REMOTE_NAME_REQ);
+	if (!cp)
+		return;
+
+	hci_dev_lock(hdev);
+
+	request_outgoing_auth(hdev, &cp->bdaddr);
+
+	hci_dev_unlock(hdev);
 }
 
 static void hci_cs_read_remote_features(struct hci_dev *hdev, __u8 status)
@@ -1090,9 +1132,17 @@ static inline void hci_auth_complete_evt(struct hci_dev *hdev, struct sk_buff *s
 
 static inline void hci_remote_name_evt(struct hci_dev *hdev, struct sk_buff *skb)
 {
+	struct hci_ev_remote_name *ev = (void *) skb->data;
+
 	BT_DBG("%s", hdev->name);
 
 	hci_conn_check_pending(hdev);
+
+	hci_dev_lock(hdev);
+
+	request_outgoing_auth(hdev, &ev->bdaddr);
+
+	hci_dev_unlock(hdev);
 }
 
 static inline void hci_encrypt_change_evt(struct hci_dev *hdev, struct sk_buff *skb)
@@ -1177,9 +1227,11 @@ static inline void hci_remote_features_evt(struct hci_dev *hdev, struct sk_buff
 							sizeof(cp), &cp);
 			} else if (!ev->status && conn->out &&
 					conn->sec_level == BT_SECURITY_HIGH) {
-				struct hci_cp_auth_requested cp;
-				cp.handle = ev->handle;
-				hci_send_cmd(hdev, HCI_OP_AUTH_REQUESTED,
+				struct hci_cp_remote_name_req cp;
+				memset(&cp, 0, sizeof(cp));
+				bacpy(&cp.bdaddr, &conn->dst);
+				cp.pscan_rep_mode = 0x02;
+				hci_send_cmd(hdev, HCI_OP_REMOTE_NAME_REQ,
 							sizeof(cp), &cp);
 			} else {
 				conn->state = BT_CONNECTED;
@@ -1660,9 +1712,11 @@ static inline void hci_remote_ext_features_evt(struct hci_dev *hdev, struct sk_b
 			if (!ev->status && hdev->ssp_mode > 0 &&
 					conn->ssp_mode > 0 && conn->out &&
 					conn->sec_level != BT_SECURITY_SDP) {
-				struct hci_cp_auth_requested cp;
-				cp.handle = ev->handle;
-				hci_send_cmd(hdev, HCI_OP_AUTH_REQUESTED,
+				struct hci_cp_remote_name_req cp;
+				memset(&cp, 0, sizeof(cp));
+				bacpy(&cp.bdaddr, &conn->dst);
+				cp.pscan_rep_mode = 0x02;
+				hci_send_cmd(hdev, HCI_OP_REMOTE_NAME_REQ,
 							sizeof(cp), &cp);
 			} else {
 				conn->state = BT_CONNECTED;
-- 
1.7.1


^ permalink raw reply related

* [PATCH v2] Fix obexd crash for empty listing invalid cache
From: Dmitriy Paliy @ 2010-10-27 17:56 UTC (permalink / raw)
  To: linux-bluetooth; +Cc: Dmitriy Paliy

This fixes obexd crash in 3-way calling scenario when listing response is
empty. Valid cache and empty pbap buffer mean that cache was already attempted
to be created within a single session, but no data was available. Hence, it
is not notified and no such file error returned. New cache is not created
within current obex session or unless path is changed. Such removes necessity
of querying and filtering contacts for each incoming call in the other case,
which is extensive for large phone books. On the other hand, if user updates
contacts, cache will not be renewed till obex session is closed or path is
changed. Therefore TODO: note is added that clear of cache should be defined
besides of end of session or change of path.
---
 plugins/pbap.c |   14 ++++++++++++++
 1 files changed, 14 insertions(+), 0 deletions(-)

diff --git a/plugins/pbap.c b/plugins/pbap.c
index 11cb678..2a90d4d 100644
--- a/plugins/pbap.c
+++ b/plugins/pbap.c
@@ -751,6 +751,20 @@ static void *vobject_list_open(const char *name, int oflag, mode_t mode,
 	/* PullvCardListing always get the contacts from the cache */
 
 	if (pbap->cache.valid) {
+		/*
+		 * Valid cache and empty buffer mean that cache was already
+		 * created within a single session, but no data is available.
+		 * New cache will not be created in current obex session or
+		 * unless path is changed. If user updates contacts, cache
+		 * will not be renewed, and, therefore:
+		 * TODO: Define clear cache besides end of session or change
+		 * of path.
+		 */
+		if (!pbap->buffer) {
+			ret = -ENOENT;
+			goto fail;
+		}
+
 		cache_ready_notify(pbap);
 		goto done;
 	}
-- 
1.7.0.4


^ permalink raw reply related

* Downstream patches
From: Bastien Nocera @ 2010-10-27 18:02 UTC (permalink / raw)
  To: BlueZ development

[-- Attachment #1: Type: text/plain, Size: 467 bytes --]

Heya,

2 small patches for the current master.

0001-systemd-install-systemd-unit-files.patch installs a systemd unit,
which, when systemd is used, replaces the udev rule to launch
bluetoothd. This was pretty heavily tested as part of the alpha for
Fedora 14, though systemd was not included in the end.

This patch is used in Fedora 15 now.

0002-build-Fix-parallel-build.patch fixes a parallel build problem I
encountered on my machine, running "make -j8".

Cheers

[-- Attachment #2: 0001-systemd-install-systemd-unit-files.patch --]
[-- Type: text/x-patch, Size: 3847 bytes --]

>From b3483ab0b821d29bbeb6aa5630b36bc126a89441 Mon Sep 17 00:00:00 2001
From: Lennart Poettering <lennart@poettering.net>
Date: Wed, 21 Jul 2010 19:20:44 +0200
Subject: [PATCH 3/3] systemd: install systemd unit files

This also enables bus activation for bluetoothd, but only if systemd is
running. Only if that's the case we can make sure in a race-free fashion
that bluetoothd is not started twice at the same time.
---
 Makefile.am                  |   21 ++++++++++++++++++---
 configure.ac                 |    9 +++++++++
 scripts/.gitignore           |    1 +
 scripts/bluetooth.service.in |   12 ++++++++++++
 scripts/org.bluez.service    |    5 +++++
 5 files changed, 45 insertions(+), 3 deletions(-)
 create mode 100644 scripts/.gitignore
 create mode 100644 scripts/bluetooth.service.in
 create mode 100644 scripts/org.bluez.service

diff --git a/Makefile.am b/Makefile.am
index e855713..1edd6a2 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -344,7 +344,8 @@ endif
 CLEANFILES += $(rules_DATA)
 
 EXTRA_DIST += scripts/bluetooth.rules \
-		scripts/bluetooth-hid2hci.rules scripts/bluetooth-serial.rules
+		scripts/bluetooth-hid2hci.rules scripts/bluetooth-serial.rules \
+		scripts/bluetooth.service.in scripts/org.bluez.service
 
 if PCMCIA
 udevdir = $(libexecdir)/udev
@@ -352,6 +353,20 @@ udevdir = $(libexecdir)/udev
 dist_udev_SCRIPTS = scripts/bluetooth_serial
 endif
 
+if HAVE_SYSTEMD
+systemdsystemunit_DATA = \
+       scripts/bluetooth.service
+
+scripts/bluetooth.service: scripts/bluetooth.service.in
+	@$(SED) -e "s|\@sbindir\@|$(sbindir)|" $< >$@
+
+dbussystemservicesdir = $(datadir)/dbus-1/system-services
+
+dbussystemservices_DATA = \
+	scripts/org.bluez.service
+
+endif
+
 EXTRA_DIST += doc/manager-api.txt \
 		doc/adapter-api.txt doc/device-api.txt \
 		doc/service-api.txt doc/agent-api.txt doc/attribute-api.txt \
@@ -376,9 +391,9 @@ pkgconfigdir = $(libdir)/pkgconfig
 
 pkgconfig_DATA = bluez.pc
 
-DISTCHECK_CONFIGURE_FLAGS = --disable-udevrules --enable-attrib
+DISTCHECK_CONFIGURE_FLAGS = --disable-udevrules --enable-attrib --with-systemdsystemunitdir=
 
-DISTCLEANFILES = $(pkgconfig_DATA)
+DISTCLEANFILES = $(pkgconfig_DATA) scripts/bluetooth.service
 
 MAINTAINERCLEANFILES = Makefile.in \
 	aclocal.m4 configure config.h.in config.sub config.guess \
diff --git a/configure.ac b/configure.ac
index d375ac9..6619a42 100644
--- a/configure.ac
+++ b/configure.ac
@@ -56,5 +56,14 @@ if (test "${enable_capng}" = "yes"); then
 	AC_DEFINE(HAVE_CAPNG, 1, [Define to 1 if you have capabilities library.])
 fi
 
+# systemd
+
+AC_ARG_WITH([systemdsystemunitdir],
+	AS_HELP_STRING([--with-systemdsystemunitdir=DIR], [Directory for systemd service files]),
+	[],
+	[with_systemdsystemunitdir=$($PKG_CONFIG --variable=systemdsystemunitdir systemd)])
+AC_SUBST([systemdsystemunitdir], [$with_systemdsystemunitdir])
+AM_CONDITIONAL(HAVE_SYSTEMD, [test -n "$with_systemdsystemunitdir"])
+
 AC_OUTPUT(Makefile scripts/bluetooth.rules doc/version.xml
 					src/bluetoothd.8 bluez.pc)
diff --git a/scripts/.gitignore b/scripts/.gitignore
new file mode 100644
index 0000000..4b9f765
--- /dev/null
+++ b/scripts/.gitignore
@@ -0,0 +1 @@
+bluetooth.service
diff --git a/scripts/bluetooth.service.in b/scripts/bluetooth.service.in
new file mode 100644
index 0000000..f95b0b0
--- /dev/null
+++ b/scripts/bluetooth.service.in
@@ -0,0 +1,12 @@
+[Unit]
+Description=Bluetooth Manager
+After=syslog.target
+
+[Service]
+Type=dbus
+BusName=org.bluez
+ExecStart=@sbindir@/bluetoothd -n
+StandardOutput=syslog
+
+[Install]
+WantedBy=bluetooth.target
diff --git a/scripts/org.bluez.service b/scripts/org.bluez.service
new file mode 100644
index 0000000..2a3b057
--- /dev/null
+++ b/scripts/org.bluez.service
@@ -0,0 +1,5 @@
+[D-BUS Service]
+Name=org.bluez
+Exec=/bin/false
+User=root
+SystemdService=bluetooth.service
-- 
1.7.3.1


[-- Attachment #3: 0002-build-Fix-parallel-build.patch --]
[-- Type: text/x-patch, Size: 1058 bytes --]

>From ad21a880935863d3592cae708147ef54c796222d Mon Sep 17 00:00:00 2001
From: Bastien Nocera <hadess@hadess.net>
Date: Wed, 27 Oct 2010 18:54:49 +0100
Subject: [PATCH 2/3] build: Fix parallel build

Fix parallel build where parser.h won't have been generated when
we're trying to compile kword itself.

 YACC   tools/parser.c
 LEX    tools/lexer.c
conflicts: 3 shift/reduce
 CC     tools/kword.o
tools/kword.c:36:20: fatal error: parser.h: No such file or directory
compilation terminated.
---
 Makefile.tools |    2 ++
 1 files changed, 2 insertions(+), 0 deletions(-)

diff --git a/Makefile.tools b/Makefile.tools
index 405a42b..797b53d 100644
--- a/Makefile.tools
+++ b/Makefile.tools
@@ -12,6 +12,8 @@ sbin_PROGRAMS += tools/hciattach tools/hciconfig
 noinst_PROGRAMS += tools/avinfo tools/ppporc \
 				tools/hcieventmask tools/hcisecfilter
 
+tools/kword.c: tools/parser.h
+
 tools_rfcomm_SOURCES = tools/main.c tools/parser.y tools/lexer.l \
 					tools/kword.h tools/kword.c
 EXTRA_tools_rfcomm_SOURCES = tools/parser.h tools/parser.c \
-- 
1.7.3.1


^ permalink raw reply related

* Re: [PATCH v2] Fix obexd crash for empty listing invalid cache
From: Johan Hedberg @ 2010-10-27 19:03 UTC (permalink / raw)
  To: Dmitriy Paliy; +Cc: linux-bluetooth
In-Reply-To: <1288202201-861-1-git-send-email-dmitriy.paliy@nokia.com>

Hi Dmitriy,

On Wed, Oct 27, 2010, Dmitriy Paliy wrote:
> This fixes obexd crash in 3-way calling scenario when listing response is
> empty. Valid cache and empty pbap buffer mean that cache was already attempted
> to be created within a single session, but no data was available. Hence, it
> is not notified and no such file error returned. New cache is not created
> within current obex session or unless path is changed. Such removes necessity
> of querying and filtering contacts for each incoming call in the other case,
> which is extensive for large phone books. On the other hand, if user updates
> contacts, cache will not be renewed till obex session is closed or path is
> changed. Therefore TODO: note is added that clear of cache should be defined
> besides of end of session or change of path.

The commit message seems to have a max width of 78 characters which
means that it's not viewable with git log on a 80 character terminal
(git log indents the output by 4 characters). Please keep the max commit
message width to 74 characters or so. Also, if possible try to split it
up into multiple paragraphs. Paragraphs longer than 6 lines tend to be a
bit harder to follow.

> +		 * TODO: Define clear cache besides end of session or change
> +		 * of path.

That doesn't sound like proper english to me and I'm not sure what
you're trying to say. Should it be "Define a clear distinction between
end of session and change of path"?

Johan

^ permalink raw reply

* Re: [PATCH 5/6] Bluetooth: Add server socket support for LE connection
From: Anderson Lizardo @ 2010-10-27 19:09 UTC (permalink / raw)
  To: Ville Tervo; +Cc: linux-bluetooth
In-Reply-To: <1288009280-5149-6-git-send-email-ville.tervo@nokia.com>

On Mon, Oct 25, 2010 at 8:21 AM, Ville Tervo <ville.tervo@nokia.com> wrote:
> +static void l2cap_le_conn_ready(struct l2cap_conn *conn)
> +{
> +       struct l2cap_chan_list *list = &conn->chan_list;
> +       struct sock *parent, *uninitialized_var(sk);
> +
> +       BT_DBG("");
> +
> +       /* Check if we have socket listening on cid */
> +       parent = l2cap_get_sock_by_cid(BT_LISTEN, 0x04, conn->src);

You can use L2CAP_CID_LE_DATA instead of 0x04.

Regards,
-- 
Anderson Lizardo
OpenBossa Labs - INdT
Manaus - Brazil

^ permalink raw reply

* HFP Pulseaudio Source destroyed "too quickly" at the end of a call
From: Thomas Wälti @ 2010-10-27 20:03 UTC (permalink / raw)
  To: linux-bluetooth

Hello all

I'm developing an application that records all kinds of audio using GStreamer.
Target platform is the Nokia N900, the app is called Recaller
(http://maemo.org/downloads/product/Maemo5/recaller/)

All works well except when ending the recording of Bluetooth
Conversations: Once a party hangs up the call, the PulseAudio source
and sink disappear before I can stop GStreamer recording (I'm
listening to D-Bus events). Unfortunately, this causes my GStreamer
pipeline to crash.

Is there a way to either delay the destruction of the sink/source by
Bluez or a D-Bus message I could intercept/attach to? How can I "win
the race"?

Thank you for your support and hints (and for the outstanding work you
all do on Bluez - a fascinating part of the Linux ecosystem!)
-Tom

^ permalink raw reply

* RE: [RFC] LE connections and advertising management
From: Mike Tsai @ 2010-10-27 22:01 UTC (permalink / raw)
  To: Claudio Takahasi; +Cc: BlueZ development
In-Reply-To: <AANLkTim7iLhzALuxX07veEwVEObwcfVFuQEpnjTVABAn@mail.gmail.com>

Hi Claudio,

-----Original Message-----
From: Claudio Takahasi [mailto:claudio.takahasi@openbossa.org] 
Sent: Tuesday, October 26, 2010 6:02 PM
To: Mike Tsai
Cc: BlueZ development
Subject: Re: [RFC] LE connections and advertising management

Hi Mike,

On Tue, Oct 26, 2010 at 6:10 PM, Mike Tsai <Mike.Tsai@atheros.com> wrote:
> [Mike Tsai]
> Hi Claudio,
>
>        I look at the API and it is well-defined with high level of abstraction. However, I did have a few questions here, hopefully you can answer them,
>
>        On Client side:
>
>                1. I see you didn't offer any service discovery API for client to discover the server service database (basically to get the attribute handles). So I assume that you consider GATT discovery procedure works the same way as SDP, done automatically by GATT after link is established without application's initiative. Am I correct?
>
>                2. The characteristic descriptor set via SetProperty API is limited to the 6 characteristic descriptors defined in GATT spec. However, there could be profile specific characteristic descriptors beyond these, will the SetProperty able to support these?
>
>                3. The characteristic monitoring is set up via 128 bits UUID. Do you have mechanism to handle duplicated characteristic within a server's database? How do you identify them via your API?
>
>
>        On Server side:
>
>                1. Is there an API that allows server application to register new attributes? (primary service, characteristic, included service, et al),
>
> Regards,
>
> Mike

Client side:
Yes. ALL characteristics are fetched after "create the device"
procedure.  This approach is wrong, some characteristics requires
encryption, authentication or authorization. Another aspect is that we
need to avoid excessive transactions. The idea now is try to search
for the primary service information only and "probe" the clients that
match with the registered service UUID. When "probed" the clients will
receive the GAttrib instance and the primary service handles range. It
is up to them to decide which attributes are relevant. Note that the
clients are only another "layer" implementing profile specific
features inside BlueZ.

[Mike Tsai]Thanks for the detailed info, I know understand more about your architecture approach. More questions below:

	1. So these "clients" (profiles) will be below d-bus and linked directly with GAttrib?

	2. Will these clients cache the discovered attribute handles that it is interested in and respond to "service change" event sent by server? Since we really want to limit the attribute handle discovery only once (same as pairing).

	3. Will these clients check the security (attribute permission) for each characteristic too?  

It is a little bit unclear to me at the moment, but we can expose
Profile specific features. Such as threshold, alert level, ...
[Mike Tsai] Yes, perhaps need to open up the characteristic descriptor for client to register with GAttrib so GAttrib knows to forward to client same as existing 6 characteristic descriptors.

Is it allowed duplicated UUIDs for the same primary service? We are
not handling this right now.
It seems that you already have a proprietary implementation ;-)

[Mike Tsai] I think it is probably not allowed to duplicate characteristic within the same primary services. However, there may be duplicated primary services within a server or duplicated included service within a server, or same characteristic inside 2 different primary services. So I don't know if you have any mechanism to let GAttrib get the correct characteristic within all these duplicated services by just passing the 128 bits UUID?

Server side:
No API. We wrote an attribute server for testing purpose only. But we
will address this soon.

Regards,
Claudio

^ permalink raw reply

* Re: Downstream patches
From: Johan Hedberg @ 2010-10-27 22:16 UTC (permalink / raw)
  To: Bastien Nocera; +Cc: BlueZ development, marcel
In-Reply-To: <1288202527.30124.107.camel@novo.hadess.net>

Hi Bastien,

On Wed, Oct 27, 2010, Bastien Nocera wrote:
> 0001-systemd-install-systemd-unit-files.patch installs a systemd unit,
> which, when systemd is used, replaces the udev rule to launch
> bluetoothd. This was pretty heavily tested as part of the alpha for
> Fedora 14, though systemd was not included in the end.
> 
> This patch is used in Fedora 15 now.

I'll let Marcel comment on this since IIRC he had previously some issues
with systemd related patches.

> 0002-build-Fix-parallel-build.patch fixes a parallel build problem I
> encountered on my machine, running "make -j8".

This one has been pushed upstream. Thanks.

Johan

^ permalink raw reply

* Re: HFP Pulseaudio Source destroyed "too quickly" at the end of a call
From: Johan Hedberg @ 2010-10-27 22:26 UTC (permalink / raw)
  To: Thomas Wälti; +Cc: linux-bluetooth, Krisztian.Litkey, Jyri.Sarha
In-Reply-To: <AANLkTikQqPqJdFgLpUrKiqyAC0HNUFnj+8NtbPxazY18@mail.gmail.com>

Hi Tom,

On Wed, Oct 27, 2010, Thomas Wälti wrote:
> I'm developing an application that records all kinds of audio using GStreamer.
> Target platform is the Nokia N900, the app is called Recaller
> (http://maemo.org/downloads/product/Maemo5/recaller/)

Looks like a pretty cool app!

> All works well except when ending the recording of Bluetooth
> Conversations: Once a party hangs up the call, the PulseAudio source
> and sink disappear before I can stop GStreamer recording (I'm
> listening to D-Bus events). Unfortunately, this causes my GStreamer
> pipeline to crash.
> 
> Is there a way to either delay the destruction of the sink/source by
> Bluez or a D-Bus message I could intercept/attach to? How can I "win
> the race"?

Probably this isn't really BlueZ related, but the audio policy module
(on the PulseAudio side) in the N900 kicks in and requests these changes
to the audio streams. Unfortunately I'm not really an expert with that
code (and afaik the audio policy part is closed) so I can't really offer
more insight on the issue. Just speculating, but you might be able to
accomplish something by hacking in some delays into the pulse bluetooth
modules (but again, I'm not really familiar with them so this might not
be a feasible approach).

Johan

^ permalink raw reply

* (reminder) Re: [PATCH v4] Bluetooth: btwilink driver
From: Pavan Savoy @ 2010-10-28  4:04 UTC (permalink / raw)
  To: padovan, marcel; +Cc: linux-bluetooth, linux-kernel, Pavan Savoy

On Tue, Oct 19, 2010 at 6:06 PM,  <pavan_savoy@ti.com> wrote:
> From: Pavan Savoy <pavan_savoy@ti.com>
>
> v4 comments
>
> module init now returns what platform_driver_register returns.
> type casting of void* private data has been removed
>

Marcel, Gustavo,

Any comments on this?
Was really hoping this would get in for 2.6.37 ...

PS:
deliberately editing the subject..

regards,
Pavan Savoy
> v3 comments
>
> Lizardo,
> I have taken care of most of the comments you had.
> Have re-wrote some of the code commenting you've mentioned.
> Thanks for the comments,
>
> Marcel, Gustavo, & list,
> Please review this version of patch.
>
> The other few like -EPERM for platform driver registration is to keep
> it similar to other drivers, type casting is maintained just to feel safe
> and have style similar to other drivers.
> BT_WILINK in Kconfig is similar to BT_MRVL.
> I hope those aren't too critical.
>
> -- patch description --
>
> This is the bluetooth protocol driver for the TI WiLink7 chipsets.
> Texas Instrument's WiLink chipsets combine wireless technologies
> like BT, FM, GPS and WLAN onto a single chip.
>
> This Bluetooth driver works on top of the TI_ST shared transport
> line discipline driver which also allows other drivers like
> FM V4L2 and GPS character driver to make use of the same UART interface.
>
> Kconfig and Makefile modifications to enable the Bluetooth
> driver for Texas Instrument's WiLink 7 chipset.
>
> Signed-off-by: Pavan Savoy <pavan_savoy@ti.com>
> ---
> =C2=A0drivers/bluetooth/Kconfig =C2=A0 =C2=A0| =C2=A0 10 +
> =C2=A0drivers/bluetooth/Makefile =C2=A0 | =C2=A0 =C2=A01 +
> =C2=A0drivers/bluetooth/btwilink.c | =C2=A0411 ++++++++++++++++++++++++++=
++++++++++++++++
> =C2=A03 files changed, 422 insertions(+), 0 deletions(-)
> =C2=A0create mode 100644 drivers/bluetooth/btwilink.c
>
> diff --git a/drivers/bluetooth/Kconfig b/drivers/bluetooth/Kconfig
> index 02deef4..8e0de9a 100644
> --- a/drivers/bluetooth/Kconfig
> +++ b/drivers/bluetooth/Kconfig
> @@ -219,4 +219,14 @@ config BT_ATH3K
> =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0Say Y here to compile support for "Athe=
ros firmware download driver"
> =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0into the kernel or say M to compile it =
as module (ath3k).
>
> +config BT_WILINK
> + =C2=A0 =C2=A0 =C2=A0 tristate "Texas Instruments WiLink7 driver"
> + =C2=A0 =C2=A0 =C2=A0 depends on TI_ST
> + =C2=A0 =C2=A0 =C2=A0 help
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 This enables the Bluetooth driver for Texas=
 Instrument's BT/FM/GPS
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 combo devices. This makes use of shared tra=
nsport line discipline
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 core driver to communicate with the BT core=
 of the combo chip.
> +
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 Say Y here to compile support for Texas Ins=
trument's WiLink7 driver
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 into the kernel or say M to compile it as m=
odule.
> =C2=A0endmenu
> diff --git a/drivers/bluetooth/Makefile b/drivers/bluetooth/Makefile
> index 71bdf13..f4460f4 100644
> --- a/drivers/bluetooth/Makefile
> +++ b/drivers/bluetooth/Makefile
> @@ -18,6 +18,7 @@ obj-$(CONFIG_BT_HCIBTSDIO) =C2=A0 =C2=A0+=3D btsdio.o
> =C2=A0obj-$(CONFIG_BT_ATH3K) =C2=A0 =C2=A0 =C2=A0 =C2=A0 +=3D ath3k.o
> =C2=A0obj-$(CONFIG_BT_MRVL) =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0+=3D btmrvl=
.o
> =C2=A0obj-$(CONFIG_BT_MRVL_SDIO) =C2=A0 =C2=A0 +=3D btmrvl_sdio.o
> +obj-$(CONFIG_BT_WILINK) =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0=
 =C2=A0+=3D btwilink.o
>
> =C2=A0btmrvl-y =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =
=C2=A0 =C2=A0 =C2=A0 :=3D btmrvl_main.o
> =C2=A0btmrvl-$(CONFIG_DEBUG_FS) =C2=A0 =C2=A0 =C2=A0+=3D btmrvl_debugfs.o
> diff --git a/drivers/bluetooth/btwilink.c b/drivers/bluetooth/btwilink.c
> new file mode 100644
> index 0000000..218efd6
> --- /dev/null
> +++ b/drivers/bluetooth/btwilink.c
> @@ -0,0 +1,411 @@
> +/*
> + * =C2=A0Texas Instrument's Bluetooth Driver For Shared Transport.
> + *
> + * =C2=A0Bluetooth Driver acts as interface between HCI core and
> + * =C2=A0TI Shared Transport Layer.
> + *
> + * =C2=A0Copyright (C) 2009-2010 Texas Instruments
> + * =C2=A0Author: Raja Mani <raja_mani@ti.com>
> + * =C2=A0 =C2=A0 Pavan Savoy <pavan_savoy@ti.com>
> + *
> + * =C2=A0This program is free software; you can redistribute it and/or m=
odify
> + * =C2=A0it under the terms of the GNU General Public License version 2 =
as
> + * =C2=A0published by the Free Software Foundation.
> + *
> + * =C2=A0This program is distributed in the hope that it will be useful,
> + * =C2=A0but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * =C2=A0MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. =C2=A0See =
the
> + * =C2=A0GNU General Public License for more details.
> + *
> + * =C2=A0You should have received a copy of the GNU General Public Licen=
se
> + * =C2=A0along with this program; if not, write to the Free Software
> + * =C2=A0Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA =C2=A0=
02111-1307 =C2=A0USA
> + *
> + */
> +
> +#include <linux/platform_device.h>
> +#include <net/bluetooth/bluetooth.h>
> +#include <net/bluetooth/hci_core.h>
> +
> +#include <linux/ti_wilink_st.h>
> +
> +/* Bluetooth Driver Version */
> +#define VERSION =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 "1.0"
> +
> +/* Number of seconds to wait for registration completion
> + * when ST returns PENDING status.
> + */
> +#define BT_REGISTER_TIMEOUT =C2=A0 6000 =C2=A0 =C2=A0 /* 6 sec */
> +
> +/**
> + * struct ti_st - driver operation structure
> + * @hdev: hci device pointer which binds to bt driver
> + * @reg_status: ST registration callback status
> + * @st_write: write function provided by the ST driver
> + * =C2=A0 =C2=A0 to be used by the driver during send_frame.
> + * @wait_reg_completion - completion sync between ti_st_open
> + * =C2=A0 =C2=A0 and ti_st_registration_completion_cb.
> + */
> +struct ti_st {
> + =C2=A0 =C2=A0 =C2=A0 struct hci_dev *hdev;
> + =C2=A0 =C2=A0 =C2=A0 char reg_status;
> + =C2=A0 =C2=A0 =C2=A0 long (*st_write) (struct sk_buff *);
> + =C2=A0 =C2=A0 =C2=A0 struct completion wait_reg_completion;
> +};
> +
> +static int reset;
> +
> +/* Increments HCI counters based on pocket ID (cmd,acl,sco) */
> +static inline void ti_st_tx_complete(struct ti_st *hst, int pkt_type)
> +{
> + =C2=A0 =C2=A0 =C2=A0 struct hci_dev *hdev;
> + =C2=A0 =C2=A0 =C2=A0 hdev =3D hst->hdev;
> +
> + =C2=A0 =C2=A0 =C2=A0 /* Update HCI stat counters */
> + =C2=A0 =C2=A0 =C2=A0 switch (pkt_type) {
> + =C2=A0 =C2=A0 =C2=A0 case HCI_COMMAND_PKT:
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 hdev->stat.cmd_tx++;
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 break;
> +
> + =C2=A0 =C2=A0 =C2=A0 case HCI_ACLDATA_PKT:
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 hdev->stat.acl_tx++;
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 break;
> +
> + =C2=A0 =C2=A0 =C2=A0 case HCI_SCODATA_PKT:
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 hdev->stat.sco_tx++;
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 break;
> + =C2=A0 =C2=A0 =C2=A0 }
> +}
> +
> +/* ------- Interfaces to Shared Transport ------ */
> +
> +/* Called by ST layer to indicate protocol registration completion
> + * status.ti_st_open() function will wait for signal from this
> + * API when st_register() function returns ST_PENDING.
> + */
> +static void st_registration_completion_cb(void *priv_data, char data)
> +{
> + =C2=A0 =C2=A0 =C2=A0 struct ti_st *lhst =3D priv_data;
> +
> + =C2=A0 =C2=A0 =C2=A0 /* Save registration status for use in ti_st_open(=
) */
> + =C2=A0 =C2=A0 =C2=A0 lhst->reg_status =3D data;
> + =C2=A0 =C2=A0 =C2=A0 /* complete the wait in ti_st_open() */
> + =C2=A0 =C2=A0 =C2=A0 complete(&lhst->wait_reg_completion);
> +}
> +
> +/* Called by Shared Transport layer when receive data is
> + * available */
> +static long st_receive(void *priv_data, struct sk_buff *skb)
> +{
> + =C2=A0 =C2=A0 =C2=A0 int err;
> + =C2=A0 =C2=A0 =C2=A0 struct ti_st *lhst =3D priv_data;
> +
> + =C2=A0 =C2=A0 =C2=A0 if (!skb)
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return -EFAULT;
> +
> + =C2=A0 =C2=A0 =C2=A0 if (!lhst) {
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 kfree_skb(skb);
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return -EFAULT;
> + =C2=A0 =C2=A0 =C2=A0 }
> +
> + =C2=A0 =C2=A0 =C2=A0 skb->dev =3D (struct net_device *)lhst->hdev;
> +
> + =C2=A0 =C2=A0 =C2=A0 /* Forward skb to HCI core layer */
> + =C2=A0 =C2=A0 =C2=A0 err =3D hci_recv_frame(skb);
> + =C2=A0 =C2=A0 =C2=A0 if (err) {
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 kfree_skb(skb);
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 BT_ERR("Unable to push=
 skb to HCI core(%d)", err);
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return err;
> + =C2=A0 =C2=A0 =C2=A0 }
> +
> + =C2=A0 =C2=A0 =C2=A0 lhst->hdev->stat.byte_rx +=3D skb->len;
> +
> + =C2=A0 =C2=A0 =C2=A0 return 0;
> +}
> +
> +/* ------- Interfaces to HCI layer ------ */
> +/* protocol structure registered with shared transport */
> +static struct st_proto_s ti_st_proto =3D {
> + =C2=A0 =C2=A0 =C2=A0 .type =3D ST_BT,
> + =C2=A0 =C2=A0 =C2=A0 .recv =3D st_receive,
> + =C2=A0 =C2=A0 =C2=A0 .reg_complete_cb =3D st_registration_completion_cb=
,
> + =C2=A0 =C2=A0 =C2=A0 .priv_data =3D NULL,
> +};
> +
> +/* Called from HCI core to initialize the device */
> +static int ti_st_open(struct hci_dev *hdev)
> +{
> + =C2=A0 =C2=A0 =C2=A0 unsigned long timeleft;
> + =C2=A0 =C2=A0 =C2=A0 struct ti_st *hst;
> + =C2=A0 =C2=A0 =C2=A0 int err;
> +
> + =C2=A0 =C2=A0 =C2=A0 BT_DBG("%s %p", hdev->name, hdev);
> +
> + =C2=A0 =C2=A0 =C2=A0 /* provide contexts for callbacks from ST */
> + =C2=A0 =C2=A0 =C2=A0 hst =3D hdev->driver_data;
> + =C2=A0 =C2=A0 =C2=A0 ti_st_proto.priv_data =3D hst;
> +
> + =C2=A0 =C2=A0 =C2=A0 err =3D st_register(&ti_st_proto);
> + =C2=A0 =C2=A0 =C2=A0 if (err =3D=3D -EINPROGRESS) {
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 /* Prepare wait-for-co=
mpletion handler data structures.
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0* Needed to sync=
hronize this and
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0* st_registratio=
n_completion_cb() functions.
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0*/
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 init_completion(&hst->=
wait_reg_completion);
> +
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 /* Reset ST registrati=
on callback status flag , this value
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0* will be update=
d in ti_st_registration_completion_cb()
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0* function whene=
ver it called from ST driver.
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0*/
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 hst->reg_status =3D -E=
INPROGRESS;
> +
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 /* ST is busy with eit=
her protocol registration or firmware
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0* download. Wait=
 until the registration callback is called
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0*/
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 BT_DBG(" waiting for r=
egistration completion signal from ST");
> +
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 timeleft =3D wait_for_=
completion_timeout
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =
=C2=A0 (&hst->wait_reg_completion,
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =
=C2=A0 =C2=A0msecs_to_jiffies(BT_REGISTER_TIMEOUT));
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 if (!timeleft) {
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =
=C2=A0 BT_ERR("Timeout(%d sec),didn't get reg "
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =
=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 "completion =
signal from ST",
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =
=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 BT_REGISTER_=
TIMEOUT / 1000);
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =
=C2=A0 return -ETIMEDOUT;
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 }
> +
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 /* Is ST registration =
callback called with ERROR status? */
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 if (hst->reg_status !=
=3D 0) {
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =
=C2=A0 BT_ERR("ST registration completed with invalid "
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =
=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 "status %d",=
 hst->reg_status);
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =
=C2=A0 return -EAGAIN;
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 }
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 err =3D 0;
> + =C2=A0 =C2=A0 =C2=A0 } else if (err =3D=3D -EPERM) {
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 BT_ERR("st_register fa=
iled %d", err);
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return err;
> + =C2=A0 =C2=A0 =C2=A0 }
> +
> + =C2=A0 =C2=A0 =C2=A0 hst->st_write =3D ti_st_proto.write;
> + =C2=A0 =C2=A0 =C2=A0 if (!hst->st_write) {
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 BT_ERR("undefined ST w=
rite function");
> +
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 /* Undo registration w=
ith ST */
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 err =3D st_unregister(=
ST_BT);
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 if (err)
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =
=C2=A0 BT_ERR("st_unregister() failed with error %d", err);
> +
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 hst->st_write =3D NULL=
;
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return err;
> + =C2=A0 =C2=A0 =C2=A0 }
> +
> + =C2=A0 =C2=A0 =C2=A0 /* Registration with ST layer is successful,
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0* hardware is ready to accept commands from =
HCI core.
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0*/
> + =C2=A0 =C2=A0 =C2=A0 set_bit(HCI_RUNNING, &hdev->flags);
> +
> + =C2=A0 =C2=A0 =C2=A0 return err;
> +}
> +
> +/* Close device */
> +static int ti_st_close(struct hci_dev *hdev)
> +{
> + =C2=A0 =C2=A0 =C2=A0 int err;
> + =C2=A0 =C2=A0 =C2=A0 struct ti_st *hst =3D hdev->driver_data;
> +
> + =C2=A0 =C2=A0 =C2=A0 /* continue to unregister from transport */
> + =C2=A0 =C2=A0 =C2=A0 err =3D st_unregister(ST_BT);
> + =C2=A0 =C2=A0 =C2=A0 if (err)
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 BT_ERR("st_unregister(=
) failed with error %d", err);
> +
> + =C2=A0 =C2=A0 =C2=A0 hst->st_write =3D NULL;
> +
> + =C2=A0 =C2=A0 =C2=A0 return err;
> +}
> +
> +static int ti_st_send_frame(struct sk_buff *skb)
> +{
> + =C2=A0 =C2=A0 =C2=A0 struct hci_dev *hdev;
> + =C2=A0 =C2=A0 =C2=A0 struct ti_st *hst;
> + =C2=A0 =C2=A0 =C2=A0 long len;
> +
> + =C2=A0 =C2=A0 =C2=A0 if (!skb)
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return -ENOMEM;
> +
> + =C2=A0 =C2=A0 =C2=A0 hdev =3D (struct hci_dev *)skb->dev;
> + =C2=A0 =C2=A0 =C2=A0 if (!hdev)
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return -ENODEV;
> +
> + =C2=A0 =C2=A0 =C2=A0 if (!test_bit(HCI_RUNNING, &hdev->flags))
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return -EBUSY;
> +
> + =C2=A0 =C2=A0 =C2=A0 hst =3D hdev->driver_data;
> +
> + =C2=A0 =C2=A0 =C2=A0 /* Prepend skb with frame type */
> + =C2=A0 =C2=A0 =C2=A0 memcpy(skb_push(skb, 1), &bt_cb(skb)->pkt_type, 1)=
;
> +
> + =C2=A0 =C2=A0 =C2=A0 BT_DBG(" %s: type %d len %d", hdev->name, bt_cb(sk=
b)->pkt_type,
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =
=C2=A0 skb->len);
> +
> + =C2=A0 =C2=A0 =C2=A0 /* Insert skb to shared transport layer's transmit=
 queue.
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0* Freeing skb memory is taken care in shared=
 transport layer,
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0* so don't free skb memory here.
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0*/
> + =C2=A0 =C2=A0 =C2=A0 if (!hst->st_write) {
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 kfree_skb(skb);
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 BT_ERR(" Could not wri=
te to ST (st_write is NULL)");
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return -EAGAIN;
> + =C2=A0 =C2=A0 =C2=A0 }
> +
> + =C2=A0 =C2=A0 =C2=A0 len =3D hst->st_write(skb);
> + =C2=A0 =C2=A0 =C2=A0 if (len < 0) {
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 kfree_skb(skb);
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 BT_ERR(" ST write fail=
ed (%ld)", len);
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return -EAGAIN;
> + =C2=A0 =C2=A0 =C2=A0 }
> +
> + =C2=A0 =C2=A0 =C2=A0 /* ST accepted our skb. So, Go ahead and do rest *=
/
> + =C2=A0 =C2=A0 =C2=A0 hdev->stat.byte_tx +=3D len;
> + =C2=A0 =C2=A0 =C2=A0 ti_st_tx_complete(hst, bt_cb(skb)->pkt_type);
> +
> + =C2=A0 =C2=A0 =C2=A0 return 0;
> +}
> +
> +static void ti_st_destruct(struct hci_dev *hdev)
> +{
> + =C2=A0 =C2=A0 =C2=A0 if (!hdev)
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return;
> +
> + =C2=A0 =C2=A0 =C2=A0 BT_DBG("%s", hdev->name);
> +
> + =C2=A0 =C2=A0 =C2=A0 /* free ti_st memory */
> + =C2=A0 =C2=A0 =C2=A0 kfree(hdev->driver_data);
> +
> + =C2=A0 =C2=A0 =C2=A0 return;
> +}
> +
> +/* Creates new HCI device */
> +static int ti_st_register_dev(struct ti_st *hst)
> +{
> + =C2=A0 =C2=A0 =C2=A0 int err;
> + =C2=A0 =C2=A0 =C2=A0 struct hci_dev *hdev;
> +
> + =C2=A0 =C2=A0 =C2=A0 /* Initialize and register HCI device */
> + =C2=A0 =C2=A0 =C2=A0 hdev =3D hci_alloc_dev();
> + =C2=A0 =C2=A0 =C2=A0 if (!hdev)
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return -ENOMEM;
> +
> + =C2=A0 =C2=A0 =C2=A0 BT_DBG("hdev %p", hdev);
> +
> + =C2=A0 =C2=A0 =C2=A0 hst->hdev =3D hdev;
> + =C2=A0 =C2=A0 =C2=A0 hdev->bus =3D HCI_UART;
> + =C2=A0 =C2=A0 =C2=A0 hdev->driver_data =3D hst;
> + =C2=A0 =C2=A0 =C2=A0 hdev->open =3D ti_st_open;
> + =C2=A0 =C2=A0 =C2=A0 hdev->close =3D ti_st_close;
> + =C2=A0 =C2=A0 =C2=A0 hdev->flush =3D NULL;
> + =C2=A0 =C2=A0 =C2=A0 hdev->send =3D ti_st_send_frame;
> + =C2=A0 =C2=A0 =C2=A0 hdev->destruct =3D ti_st_destruct;
> + =C2=A0 =C2=A0 =C2=A0 hdev->owner =3D THIS_MODULE;
> +
> + =C2=A0 =C2=A0 =C2=A0 if (reset)
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 set_bit(HCI_QUIRK_NO_R=
ESET, &hdev->quirks);
> +
> + =C2=A0 =C2=A0 =C2=A0 err =3D hci_register_dev(hdev);
> + =C2=A0 =C2=A0 =C2=A0 if (err < 0) {
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 BT_ERR("Can't register=
 HCI device error %d", err);
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 hci_free_dev(hdev);
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return err;
> + =C2=A0 =C2=A0 =C2=A0 }
> +
> + =C2=A0 =C2=A0 =C2=A0 BT_DBG(" HCI device registered (hdev %p)", hdev);
> + =C2=A0 =C2=A0 =C2=A0 return 0;
> +}
> +
> +
> +static int bt_ti_probe(struct platform_device *pdev)
> +{
> + =C2=A0 =C2=A0 =C2=A0 int err;
> + =C2=A0 =C2=A0 =C2=A0 static struct ti_st *hst;
> +
> + =C2=A0 =C2=A0 =C2=A0 BT_DBG(" Bluetooth Driver Version %s", VERSION);
> +
> + =C2=A0 =C2=A0 =C2=A0 hst =3D kzalloc(sizeof(struct ti_st), GFP_KERNEL);
> + =C2=A0 =C2=A0 =C2=A0 if (!hst)
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return -ENOMEM;
> +
> + =C2=A0 =C2=A0 =C2=A0 /* Expose "hciX" device to user space */
> + =C2=A0 =C2=A0 =C2=A0 err =3D ti_st_register_dev(hst);
> + =C2=A0 =C2=A0 =C2=A0 if (err) {
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 kfree(hst);
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return err;
> + =C2=A0 =C2=A0 =C2=A0 }
> +
> + =C2=A0 =C2=A0 =C2=A0 dev_set_drvdata(&pdev->dev, hst);
> + =C2=A0 =C2=A0 =C2=A0 return err;
> +}
> +
> +static int bt_ti_remove(struct platform_device *pdev)
> +{
> + =C2=A0 =C2=A0 =C2=A0 struct ti_st *hst;
> + =C2=A0 =C2=A0 =C2=A0 struct hci_dev *hdev;
> +
> + =C2=A0 =C2=A0 =C2=A0 hst =3D dev_get_drvdata(&pdev->dev);
> +
> + =C2=A0 =C2=A0 =C2=A0 if (!hst)
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return -EFAULT;
> +
> + =C2=A0 =C2=A0 =C2=A0 /* Deallocate local resource's memory =C2=A0*/
> + =C2=A0 =C2=A0 =C2=A0 hdev =3D hst->hdev;
> +
> + =C2=A0 =C2=A0 =C2=A0 if (!hdev) {
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 BT_ERR("Invalid hdev m=
emory");
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 kfree(hst);
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return -EFAULT;
> + =C2=A0 =C2=A0 =C2=A0 }
> +
> + =C2=A0 =C2=A0 =C2=A0 ti_st_close(hdev);
> + =C2=A0 =C2=A0 =C2=A0 hci_unregister_dev(hdev);
> + =C2=A0 =C2=A0 =C2=A0 /* Free HCI device memory */
> + =C2=A0 =C2=A0 =C2=A0 hci_free_dev(hdev);
> +
> + =C2=A0 =C2=A0 =C2=A0 return 0;
> +}
> +
> +static struct platform_driver btwilink_driver =3D {
> + =C2=A0 =C2=A0 =C2=A0 .probe =3D bt_ti_probe,
> + =C2=A0 =C2=A0 =C2=A0 .remove =3D bt_ti_remove,
> + =C2=A0 =C2=A0 =C2=A0 .driver =3D {
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 .name =3D "btwilink",
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 .owner =3D THIS_MODULE=
,
> + =C2=A0 =C2=A0 =C2=A0 },
> +};
> +
> +/* ------- Module Init/Exit interfaces ------ */
> +static int __init bt_drv_init(void)
> +{
> + =C2=A0 =C2=A0 =C2=A0 long ret;
> +
> + =C2=A0 =C2=A0 =C2=A0 ret =3D platform_driver_register(&btwilink_driver)=
;
> + =C2=A0 =C2=A0 =C2=A0 if (ret !=3D 0) {
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 BT_ERR("btwilink platf=
orm driver registration failed");
> + =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return ret;
> + =C2=A0 =C2=A0 =C2=A0 }
> + =C2=A0 =C2=A0 =C2=A0 return 0;
> +}
> +
> +static void __exit bt_drv_exit(void)
> +{
> + =C2=A0 =C2=A0 =C2=A0 platform_driver_unregister(&btwilink_driver);
> +}
> +
> +module_init(bt_drv_init);
> +module_exit(bt_drv_exit);
> +
> +/* ------ Module Info ------ */
> +
> +module_param(reset, bool, 0644);
> +MODULE_PARM_DESC(reset, "Send HCI reset command on initialization");
> +MODULE_AUTHOR("Raja Mani <raja_mani@ti.com>");
> +MODULE_DESCRIPTION("Bluetooth Driver for TI Shared Transport" VERSION);
> +MODULE_VERSION(VERSION);
> +MODULE_LICENSE("GPL");
> --
> 1.6.5
>
> --
> To unsubscribe from this list: send the line "unsubscribe linux-bluetooth=
" in
> the body of a message to majordomo@vger.kernel.org
> More majordomo info at =C2=A0http://vger.kernel.org/majordomo-info.html
>

^ permalink raw reply

* Re: [PATCH] Bluetooth: Automate remote name requests
From: Luiz Augusto von Dentz @ 2010-10-28  7:42 UTC (permalink / raw)
  To: johan.hedberg; +Cc: linux-bluetooth, Johan Hedberg
In-Reply-To: <1288196742-29386-1-git-send-email-johan.hedberg@gmail.com>

Hi Johan,

On Wed, Oct 27, 2010 at 7:25 PM,  <johan.hedberg@gmail.com> wrote:
> From: Johan Hedberg <johan.hedberg@nokia.com>
>
> In Bluetooth there are no automatic updates of remote device names when
> they get changed on the remote side. Instead, it is a good idea to do a
> manual name request when a new connection gets created (for whatever
> reason) since at this point it is very cheap (no costly baseband
> connection creation needed just for the sake of the name request).
>
> So far userspace has been responsible for this extra name request but
> tighter control is needed in order not to flood Bluetooth controllers
> with two many commands during connection creation. It has been shown
> that some controllers simply fail to function correctly if they get too
> many (almost) simultaneous commands during connection creation. The
> simplest way to acheive better control of these commands is to move
> their sending completely to the kernel side.
>
> This patch inserts name requests into the sequence of events that the
> kernel performs during connection creation. It does this after the
> remote features have been successfully requested and before any pending
> authentication requests are performed. The code will work sub-optimally
> with userspace versions that still do the name requesting themselves (it
> shouldn't break anything though) so it is recommended to combine this
> with a userspace software version that doesn't have automated name
> requests.
>
> Signed-off-by: Johan Hedberg <johan.hedberg@nokia.com>
> ---
>  net/bluetooth/hci_event.c |   66 ++++++++++++++++++++++++++++++++++++++++----
>  1 files changed, 60 insertions(+), 6 deletions(-)
>
> diff --git a/net/bluetooth/hci_event.c b/net/bluetooth/hci_event.c
> index 84093b0..05ad699 100644
> --- a/net/bluetooth/hci_event.c
> +++ b/net/bluetooth/hci_event.c
> @@ -677,9 +677,51 @@ static void hci_cs_set_conn_encrypt(struct hci_dev *hdev, __u8 status)
>        hci_dev_unlock(hdev);
>  }
>
> +static void request_outgoing_auth(struct hci_dev *hdev, bdaddr_t *bdaddr)
> +{
> +       struct hci_cp_auth_requested cp;
> +       struct hci_conn *conn;
> +
> +       conn = hci_conn_hash_lookup_ba(hdev, ACL_LINK, bdaddr);
> +       if (!conn)
> +               return;
> +
> +       if (conn->state != BT_CONFIG || !conn->out)
> +               return;
> +
> +       if (conn->sec_level == BT_SECURITY_SDP)
> +               return;
> +
> +       /* Only request authentication for SSP connections or non-SSP
> +        * devices with sec_level HIGH */
> +       if (!(hdev->ssp_mode > 0 && conn->ssp_mode > 0) &&
> +                                       conn->sec_level != BT_SECURITY_HIGH)
> +               return;
> +
> +       cp.handle = __cpu_to_le16(conn->handle);
> +       hci_send_cmd(hdev, HCI_OP_AUTH_REQUESTED, sizeof(cp), &cp);
> +}
> +
>  static void hci_cs_remote_name_req(struct hci_dev *hdev, __u8 status)
>  {
> +       struct hci_cp_remote_name_req *cp;
> +
>        BT_DBG("%s status 0x%x", hdev->name, status);
> +
> +       /* If successful wait for the name req complete event before
> +        * checking for the need to do authentication */
> +       if (status == 0)
> +               return;
> +
> +       cp = hci_sent_cmd_data(hdev, HCI_OP_REMOTE_NAME_REQ);
> +       if (!cp)
> +               return;
> +
> +       hci_dev_lock(hdev);
> +
> +       request_outgoing_auth(hdev, &cp->bdaddr);
> +
> +       hci_dev_unlock(hdev);
>  }
>
>  static void hci_cs_read_remote_features(struct hci_dev *hdev, __u8 status)
> @@ -1090,9 +1132,17 @@ static inline void hci_auth_complete_evt(struct hci_dev *hdev, struct sk_buff *s
>
>  static inline void hci_remote_name_evt(struct hci_dev *hdev, struct sk_buff *skb)
>  {
> +       struct hci_ev_remote_name *ev = (void *) skb->data;
> +
>        BT_DBG("%s", hdev->name);
>
>        hci_conn_check_pending(hdev);
> +
> +       hci_dev_lock(hdev);
> +
> +       request_outgoing_auth(hdev, &ev->bdaddr);
> +
> +       hci_dev_unlock(hdev);
>  }
>
>  static inline void hci_encrypt_change_evt(struct hci_dev *hdev, struct sk_buff *skb)
> @@ -1177,9 +1227,11 @@ static inline void hci_remote_features_evt(struct hci_dev *hdev, struct sk_buff
>                                                        sizeof(cp), &cp);
>                        } else if (!ev->status && conn->out &&
>                                        conn->sec_level == BT_SECURITY_HIGH) {
> -                               struct hci_cp_auth_requested cp;
> -                               cp.handle = ev->handle;
> -                               hci_send_cmd(hdev, HCI_OP_AUTH_REQUESTED,
> +                               struct hci_cp_remote_name_req cp;
> +                               memset(&cp, 0, sizeof(cp));
> +                               bacpy(&cp.bdaddr, &conn->dst);
> +                               cp.pscan_rep_mode = 0x02;
> +                               hci_send_cmd(hdev, HCI_OP_REMOTE_NAME_REQ,
>                                                        sizeof(cp), &cp);
>                        } else {
>                                conn->state = BT_CONNECTED;
> @@ -1660,9 +1712,11 @@ static inline void hci_remote_ext_features_evt(struct hci_dev *hdev, struct sk_b
>                        if (!ev->status && hdev->ssp_mode > 0 &&
>                                        conn->ssp_mode > 0 && conn->out &&
>                                        conn->sec_level != BT_SECURITY_SDP) {
> -                               struct hci_cp_auth_requested cp;
> -                               cp.handle = ev->handle;
> -                               hci_send_cmd(hdev, HCI_OP_AUTH_REQUESTED,
> +                               struct hci_cp_remote_name_req cp;
> +                               memset(&cp, 0, sizeof(cp));
> +                               bacpy(&cp.bdaddr, &conn->dst);
> +                               cp.pscan_rep_mode = 0x02;
> +                               hci_send_cmd(hdev, HCI_OP_REMOTE_NAME_REQ,
>                                                        sizeof(cp), &cp);
>                        } else {
>                                conn->state = BT_CONNECTED;
> --
> 1.7.1

This seems to be done only for some connections which IMO is not the
correct, so for instance it wouldn't request name for SDP connections
nor for incoming connections, is there a reason for that?

Perhaps requesting the name regardless the security level on
hci_remote_features_evt and then latter, when we got the name
response, we continue with security level check and authentication
request if necessary. Wouldn't that work better?

-- 
Luiz Augusto von Dentz
Computer Engineer

^ permalink raw reply

* [PATCH 1/5] Fix issue when setting limited discoverable mode
From: Luiz Augusto von Dentz @ 2010-10-28  8:00 UTC (permalink / raw)
  To: linux-bluetooth

From: Luiz Augusto von Dentz <luiz.dentz-von@nokia.com>

When setting limited discoverable mode it will always switch to
discoverable on adapter_mode_changed which doesn't match the pending mode
requested.
---
 src/adapter.c |    5 +++--
 1 files changed, 3 insertions(+), 2 deletions(-)

diff --git a/src/adapter.c b/src/adapter.c
index 4a9f34e..98d96e2 100644
--- a/src/adapter.c
+++ b/src/adapter.c
@@ -3225,9 +3225,10 @@ void adapter_mode_changed(struct btd_adapter *adapter, uint8_t scan_mode)
 					DBUS_TYPE_BOOLEAN, &pairable);
 
 	if (discoverable && adapter->pairable && adapter->discov_timeout > 0 &&
-						adapter->discov_timeout <= 60)
+						adapter->discov_timeout <= 60) {
+		adapter->mode = MODE_LIMITED;
 		adapter_set_limited_discoverable(adapter, TRUE);
-	else if (!discoverable)
+	} else if (!discoverable)
 		adapter_set_limited_discoverable(adapter, FALSE);
 
 	emit_property_changed(connection, path,
-- 
1.7.1


^ permalink raw reply related

* [PATCH 2/5] Fix not waiting mode change when setting powered property
From: Luiz Augusto von Dentz @ 2010-10-28  8:00 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1288252859-10337-1-git-send-email-luiz.dentz@gmail.com>

From: Luiz Augusto von Dentz <luiz.dentz-von@nokia.com>

This may cause errors if the user application immediately set another
mode.
---
 src/adapter.c |   84 +++++++++++++++++++++++++++++---------------------------
 1 files changed, 43 insertions(+), 41 deletions(-)

diff --git a/src/adapter.c b/src/adapter.c
index 98d96e2..f4fc3c1 100644
--- a/src/adapter.c
+++ b/src/adapter.c
@@ -604,11 +604,11 @@ static DBusMessage *set_powered(DBusConnection *conn, DBusMessage *msg,
 	if (mode == adapter->mode)
 		return dbus_message_new_method_return(msg);
 
-	err = set_mode(adapter, mode, NULL);
+	err = set_mode(adapter, mode, msg);
 	if (err < 0)
 		return failed_strerror(msg, -err);
 
-	return dbus_message_new_method_return(msg);
+	return NULL;
 }
 
 static DBusMessage *set_discoverable(DBusConnection *conn, DBusMessage *msg,
@@ -2570,6 +2570,45 @@ static void unload_drivers(struct btd_adapter *adapter)
 	}
 }
 
+static void set_mode_complete(struct btd_adapter *adapter)
+{
+	struct session_req *pending;
+	const char *modestr;
+	int err;
+
+	if (adapter->pending_mode == NULL)
+		return;
+
+	pending = adapter->pending_mode;
+	adapter->pending_mode = NULL;
+
+	err = (pending->mode != adapter->mode) ? -EINVAL : 0;
+
+	if (pending->msg != NULL) {
+		DBusMessage *msg = pending->msg;
+		DBusMessage *reply;
+
+		if (err < 0)
+			reply = failed_strerror(msg, -err);
+		else
+			reply = g_dbus_create_reply(msg, DBUS_TYPE_INVALID);
+
+		g_dbus_send_message(connection, reply);
+	}
+
+	modestr = mode2str(adapter->mode);
+
+	DBG("%s", modestr);
+
+	/* Only store if the mode matches the pending */
+	if (err == 0)
+		write_device_mode(&adapter->bdaddr, modestr);
+	else
+		error("unable to set mode: %s", mode2str(pending->mode));
+
+	session_unref(pending);
+}
+
 int adapter_stop(struct btd_adapter *adapter)
 {
 	gboolean powered, discoverable, pairable;
@@ -2628,6 +2667,8 @@ int adapter_stop(struct btd_adapter *adapter)
 
 	info("Adapter %s has been disabled", adapter->path);
 
+	set_mode_complete(adapter);
+
 	return 0;
 }
 
@@ -3137,45 +3178,6 @@ int adapter_remove_found_device(struct btd_adapter *adapter, bdaddr_t *bdaddr)
 	return 0;
 }
 
-static void set_mode_complete(struct btd_adapter *adapter)
-{
-	struct session_req *pending;
-	const char *modestr;
-	int err;
-
-	if (adapter->pending_mode == NULL)
-		return;
-
-	pending = adapter->pending_mode;
-	adapter->pending_mode = NULL;
-
-	err = (pending->mode != adapter->mode) ? -EINVAL : 0;
-
-	if (pending->msg != NULL) {
-		DBusMessage *msg = pending->msg;
-		DBusMessage *reply;
-
-		if (err < 0)
-			reply = failed_strerror(msg, -err);
-		else
-			reply = g_dbus_create_reply(msg, DBUS_TYPE_INVALID);
-
-		g_dbus_send_message(connection, reply);
-	}
-
-	modestr = mode2str(adapter->mode);
-
-	DBG("%s", modestr);
-
-	/* Only store if the mode matches the pending */
-	if (err == 0)
-		write_device_mode(&adapter->bdaddr, modestr);
-	else
-		error("unable to set mode: %s", mode2str(pending->mode));
-
-	session_unref(pending);
-}
-
 void adapter_mode_changed(struct btd_adapter *adapter, uint8_t scan_mode)
 {
 	const gchar *path = adapter_get_path(adapter);
-- 
1.7.1


^ permalink raw reply related

* [PATCH 3/5] Fix setting Discoverable when adapter is down
From: Luiz Augusto von Dentz @ 2010-10-28  8:00 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1288252859-10337-1-git-send-email-luiz.dentz@gmail.com>

From: Luiz Augusto von Dentz <luiz.dentz-von@nokia.com>

This cause an error because adapter_up will load the mode from storage
ignoring pending mode which cause modes to mismatch.

To fix this behavior now when attempting to change mode we first store
the new mode and wait DEVUP to complete set the mode stored.
---
 src/adapter.c |   19 +++++++++++--------
 1 files changed, 11 insertions(+), 8 deletions(-)

diff --git a/src/adapter.c b/src/adapter.c
index f4fc3c1..e5f7730 100644
--- a/src/adapter.c
+++ b/src/adapter.c
@@ -533,6 +533,7 @@ static int set_mode(struct btd_adapter *adapter, uint8_t new_mode,
 			DBusMessage *msg)
 {
 	int err;
+	const char *modestr;
 
 	if (adapter->pending_mode != NULL)
 		return -EALREADY;
@@ -541,6 +542,8 @@ static int set_mode(struct btd_adapter *adapter, uint8_t new_mode,
 		err = adapter_ops->set_powered(adapter->dev_id, TRUE);
 		if (err < 0)
 			return err;
+
+		goto done;
 	}
 
 	if (adapter->up && new_mode == MODE_OFF) {
@@ -576,18 +579,18 @@ static int set_mode(struct btd_adapter *adapter, uint8_t new_mode,
 	}
 
 done:
-	DBG("%s", mode2str(new_mode));
+	modestr = mode2str(new_mode);
+	write_device_mode(&adapter->bdaddr, modestr);
+
+	DBG("%s", modestr);
 
 	if (msg != NULL)
 		/* Wait for mode change to reply */
 		adapter->pending_mode = create_session(adapter, connection,
 							msg, new_mode, NULL);
-	else {
+	else
 		/* Nothing to reply just write the new mode */
-		const char *modestr = mode2str(new_mode);
 		adapter->mode = new_mode;
-		write_device_mode(&adapter->bdaddr, modestr);
-	}
 
 	return 0;
 }
@@ -2600,11 +2603,11 @@ static void set_mode_complete(struct btd_adapter *adapter)
 
 	DBG("%s", modestr);
 
-	/* Only store if the mode matches the pending */
-	if (err == 0)
+	/* restore if the mode doesn't matches the pending */
+	if (err != 0) {
 		write_device_mode(&adapter->bdaddr, modestr);
-	else
 		error("unable to set mode: %s", mode2str(pending->mode));
+	}
 
 	session_unref(pending);
 }
-- 
1.7.1


^ permalink raw reply related

* [PATCH 4/5] Fix not replying when mode is limited discoverable or discoverable
From: Luiz Augusto von Dentz @ 2010-10-28  8:00 UTC (permalink / raw)
  To: linux-bluetooth
In-Reply-To: <1288252859-10337-1-git-send-email-luiz.dentz@gmail.com>

From: Luiz Augusto von Dentz <luiz.dentz-von@nokia.com>

When changing from/to limited discoverable or discoverable it won't
change the scan mode thus causing set_mode_complete to not be called.
---
 src/adapter.c |   49 +++++++++++++++++++++++++++++++++----------------
 1 files changed, 33 insertions(+), 16 deletions(-)

diff --git a/src/adapter.c b/src/adapter.c
index e5f7730..b5e73b7 100644
--- a/src/adapter.c
+++ b/src/adapter.c
@@ -584,25 +584,41 @@ done:
 
 	DBG("%s", modestr);
 
-	if (msg != NULL)
-		/* Wait for mode change to reply */
-		adapter->pending_mode = create_session(adapter, connection,
-							msg, new_mode, NULL);
-	else
+	if (msg != NULL) {
+		/* Limited to Discoverable and vice-versa doesn't cause any
+		   change to scan mode */
+		if (g_str_equal(modestr, mode2str(adapter->mode)) == TRUE) {
+			DBusMessage *reply;
+
+			reply = g_dbus_create_reply(msg, DBUS_TYPE_INVALID);
+
+			g_dbus_send_message(connection, reply);
+		} else
+			/* Wait for mode change to reply */
+			adapter->pending_mode = create_session(adapter,
+								connection,
+								msg, new_mode,
+								NULL);
+	} else
 		/* Nothing to reply just write the new mode */
 		adapter->mode = new_mode;
 
 	return 0;
 }
 
-static DBusMessage *set_powered(DBusConnection *conn, DBusMessage *msg,
-				gboolean powered, void *data)
+static DBusMessage *set_discoverable(DBusConnection *conn, DBusMessage *msg,
+				gboolean discoverable, void *data)
 {
 	struct btd_adapter *adapter = data;
 	uint8_t mode;
 	int err;
 
-	mode = powered ? get_mode(&adapter->bdaddr, "on") : MODE_OFF;
+	mode = discoverable ? MODE_DISCOVERABLE : MODE_CONNECTABLE;
+
+	if (mode == MODE_DISCOVERABLE && adapter->pairable &&
+					adapter->discov_timeout > 0 &&
+					adapter->discov_timeout <= 60)
+		mode = MODE_LIMITED;
 
 	if (mode == adapter->mode)
 		return dbus_message_new_method_return(msg);
@@ -614,19 +630,20 @@ static DBusMessage *set_powered(DBusConnection *conn, DBusMessage *msg,
 	return NULL;
 }
 
-static DBusMessage *set_discoverable(DBusConnection *conn, DBusMessage *msg,
-				gboolean discoverable, void *data)
+static DBusMessage *set_powered(DBusConnection *conn, DBusMessage *msg,
+				gboolean powered, void *data)
 {
 	struct btd_adapter *adapter = data;
 	uint8_t mode;
 	int err;
 
-	mode = discoverable ? MODE_DISCOVERABLE : MODE_CONNECTABLE;
+	if (powered) {
+		mode = get_mode(&adapter->bdaddr, "on");
+		return set_discoverable(conn, msg, mode == MODE_DISCOVERABLE,
+									data);
+	}
 
-	if (mode == MODE_DISCOVERABLE && adapter->pairable &&
-					adapter->discov_timeout > 0 &&
-					adapter->discov_timeout <= 60)
-		mode = MODE_LIMITED;
+	mode = MODE_OFF;
 
 	if (mode == adapter->mode)
 		return dbus_message_new_method_return(msg);
@@ -635,7 +652,7 @@ static DBusMessage *set_discoverable(DBusConnection *conn, DBusMessage *msg,
 	if (err < 0)
 		return failed_strerror(msg, -err);
 
-	return 0;
+	return NULL;
 }
 
 static DBusMessage *set_pairable(DBusConnection *conn, DBusMessage *msg,
-- 
1.7.1


^ permalink raw reply related


This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox