* Bluetooth disconnect event / Link layer monitoring
@ 2019-11-18 17:16 Guy Morand
2019-11-18 18:27 ` Luiz Augusto von Dentz
0 siblings, 1 reply; 6+ messages in thread
From: Guy Morand @ 2019-11-18 17:16 UTC (permalink / raw)
To: linux-bluetooth
Hello bluetooth developers,
We are developing a wheelchair that we can controle with a bluetooth
gamepad, the XBOX 360 controller to be more precise. It basically works
fine but when I remove the battery, I get the disconnect event in the
user space around 10 seconds later. That is not acceptable since the
wheelchair will keep rolling to potentially dangerous places!
I tried to implement a ping mechanism on the bluetooth layer, inspired
from bluez sources somewhere:
int _socket_fd = socket(PF_BLUETOOTH, SOCK_RAW, BTPROTO_L2CAP);
// bind on AF_BLUETOOTH
// connect with AF_BLUETOOTH
send_cmd->ident = PING_IDENT;
send_cmd->len = htobs(PING_DATA_SIZE);
send_cmd->code = L2CAP_ECHO_REQ;
if (send(_socket_fd, send_buffer, PING_PACKET_SIZE, 0) <= 0) {
// ...
}
It basically works fine except when the signal gets bad. This will get
printed by the kernel:
[ 859.629431] Bluetooth: hci0 link tx timeout
[ 859.635482] Bluetooth: hci0 killing stalled connection 9c:aa:1b:6b:51:c9
In that case, I don't get event from the /dev/jsX device but the gamepad
seems to still answer to pings??!!
Since I haven't found any acceptable workaround and always find the same
pages again and again, I'm asking here:
* Is it possible to achieve what I want?
* Does it make sense that the ping work but the HID layer seems dead?
* Any recommendation, pointers?
Best regards,
Guy
--
Guy Morand
Software Engineer
Scewo AG, Technoparkstrasse 2, 8406 Winterthur
www.scewo.ch
www.facebook.com/scewo
www.instagram.com/scewo_official
^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: Bluetooth disconnect event / Link layer monitoring
2019-11-18 17:16 Bluetooth disconnect event / Link layer monitoring Guy Morand
@ 2019-11-18 18:27 ` Luiz Augusto von Dentz
2019-11-19 5:06 ` Marcel Holtmann
0 siblings, 1 reply; 6+ messages in thread
From: Luiz Augusto von Dentz @ 2019-11-18 18:27 UTC (permalink / raw)
To: Guy Morand; +Cc: linux-bluetooth
Hi Guy,
On Mon, Nov 18, 2019 at 7:19 PM Guy Morand <g.morand@scewo.ch> wrote:
>
> Hello bluetooth developers,
>
> We are developing a wheelchair that we can controle with a bluetooth
> gamepad, the XBOX 360 controller to be more precise. It basically works
> fine but when I remove the battery, I get the disconnect event in the
> user space around 10 seconds later. That is not acceptable since the
> wheelchair will keep rolling to potentially dangerous places!
>
> I tried to implement a ping mechanism on the bluetooth layer, inspired
> from bluez sources somewhere:
> int _socket_fd = socket(PF_BLUETOOTH, SOCK_RAW, BTPROTO_L2CAP);
> // bind on AF_BLUETOOTH
> // connect with AF_BLUETOOTH
>
> send_cmd->ident = PING_IDENT;
> send_cmd->len = htobs(PING_DATA_SIZE);
> send_cmd->code = L2CAP_ECHO_REQ;
> if (send(_socket_fd, send_buffer, PING_PACKET_SIZE, 0) <= 0) {
> // ...
> }
>
> It basically works fine except when the signal gets bad. This will get
> printed by the kernel:
> [ 859.629431] Bluetooth: hci0 link tx timeout
> [ 859.635482] Bluetooth: hci0 killing stalled connection 9c:aa:1b:6b:51:c9
>
> In that case, I don't get event from the /dev/jsX device but the gamepad
> seems to still answer to pings??!!
>
> Since I haven't found any acceptable workaround and always find the same
> pages again and again, I'm asking here:
> * Is it possible to achieve what I want?
> * Does it make sense that the ping work but the HID layer seems dead?
> * Any recommendation, pointers?
Id look into adjusting the link supervision timeout instead of
creating a raw socket, you can use hcitool to do that, neither is
really great since it require root but at least the supervision
timeout is something a lot more reliable for this.
--
Luiz Augusto von Dentz
^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: Bluetooth disconnect event / Link layer monitoring
2019-11-18 18:27 ` Luiz Augusto von Dentz
@ 2019-11-19 5:06 ` Marcel Holtmann
2019-11-19 9:09 ` Guy Morand
0 siblings, 1 reply; 6+ messages in thread
From: Marcel Holtmann @ 2019-11-19 5:06 UTC (permalink / raw)
To: Luiz Augusto von Dentz; +Cc: Guy Morand, linux-bluetooth
Hi Luiz,
>> We are developing a wheelchair that we can controle with a bluetooth
>> gamepad, the XBOX 360 controller to be more precise. It basically works
>> fine but when I remove the battery, I get the disconnect event in the
>> user space around 10 seconds later. That is not acceptable since the
>> wheelchair will keep rolling to potentially dangerous places!
>>
>> I tried to implement a ping mechanism on the bluetooth layer, inspired
>> from bluez sources somewhere:
>> int _socket_fd = socket(PF_BLUETOOTH, SOCK_RAW, BTPROTO_L2CAP);
>> // bind on AF_BLUETOOTH
>> // connect with AF_BLUETOOTH
>>
>> send_cmd->ident = PING_IDENT;
>> send_cmd->len = htobs(PING_DATA_SIZE);
>> send_cmd->code = L2CAP_ECHO_REQ;
>> if (send(_socket_fd, send_buffer, PING_PACKET_SIZE, 0) <= 0) {
>> // ...
>> }
>>
>> It basically works fine except when the signal gets bad. This will get
>> printed by the kernel:
>> [ 859.629431] Bluetooth: hci0 link tx timeout
>> [ 859.635482] Bluetooth: hci0 killing stalled connection 9c:aa:1b:6b:51:c9
>>
>> In that case, I don't get event from the /dev/jsX device but the gamepad
>> seems to still answer to pings??!!
>>
>> Since I haven't found any acceptable workaround and always find the same
>> pages again and again, I'm asking here:
>> * Is it possible to achieve what I want?
>> * Does it make sense that the ping work but the HID layer seems dead?
>> * Any recommendation, pointers?
>
> Id look into adjusting the link supervision timeout instead of
> creating a raw socket, you can use hcitool to do that, neither is
> really great since it require root but at least the supervision
> timeout is something a lot more reliable for this.
we can add an option to L2CAP sockets to adjust the link supervision timeout.
Anyway, these days, I would _not_ use Bluetooth BR/EDR for controlling anything. I would find a Gamepad that utilizes Bluetooth LE and focus on that.
Regards
Marcel
^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: Bluetooth disconnect event / Link layer monitoring
2019-11-19 5:06 ` Marcel Holtmann
@ 2019-11-19 9:09 ` Guy Morand
2019-11-21 17:37 ` Guy Morand
0 siblings, 1 reply; 6+ messages in thread
From: Guy Morand @ 2019-11-19 9:09 UTC (permalink / raw)
To: Marcel Holtmann; +Cc: Luiz Augusto von Dentz, linux-bluetooth
Thanks everyone for your quick answers!
I tried this already but unfortunately, it seems that the gamepad
doesn't allow that:
$ hcitool lst ec:83:50:de:02:3c 1
HCI write_link_supervision_timeout request failed: Input/output error
< HCI Command: Write Link Supervision Timeout (0x03|0x0037) plen 4
handle 70 timeout 1
> HCI Event: Command Complete (0x0e) plen 6
Write Link Supervision Timeout (0x03|0x0037) ncmd 1
status 0x0c handle 70
Error: Command Disallowed
Yes, if it was me, I would never use bluetooth!
I guess the only place where I can do something is in the kernel space.
I would like to send the error to the user when this happens:
Bluetooth: hci0 link tx timeout
Do you think that would be possible and make sense?
Best regards,
Guy
On Tue, Nov 19, 2019 at 6:06 AM Marcel Holtmann <marcel@holtmann.org> wrote:
>
> Hi Luiz,
>
> >> We are developing a wheelchair that we can controle with a bluetooth
> >> gamepad, the XBOX 360 controller to be more precise. It basically works
> >> fine but when I remove the battery, I get the disconnect event in the
> >> user space around 10 seconds later. That is not acceptable since the
> >> wheelchair will keep rolling to potentially dangerous places!
> >>
> >> I tried to implement a ping mechanism on the bluetooth layer, inspired
> >> from bluez sources somewhere:
> >> int _socket_fd = socket(PF_BLUETOOTH, SOCK_RAW, BTPROTO_L2CAP);
> >> // bind on AF_BLUETOOTH
> >> // connect with AF_BLUETOOTH
> >>
> >> send_cmd->ident = PING_IDENT;
> >> send_cmd->len = htobs(PING_DATA_SIZE);
> >> send_cmd->code = L2CAP_ECHO_REQ;
> >> if (send(_socket_fd, send_buffer, PING_PACKET_SIZE, 0) <= 0) {
> >> // ...
> >> }
> >>
> >> It basically works fine except when the signal gets bad. This will get
> >> printed by the kernel:
> >> [ 859.629431] Bluetooth: hci0 link tx timeout
> >> [ 859.635482] Bluetooth: hci0 killing stalled connection 9c:aa:1b:6b:51:c9
> >>
> >> In that case, I don't get event from the /dev/jsX device but the gamepad
> >> seems to still answer to pings??!!
> >>
> >> Since I haven't found any acceptable workaround and always find the same
> >> pages again and again, I'm asking here:
> >> * Is it possible to achieve what I want?
> >> * Does it make sense that the ping work but the HID layer seems dead?
> >> * Any recommendation, pointers?
> >
> > Id look into adjusting the link supervision timeout instead of
> > creating a raw socket, you can use hcitool to do that, neither is
> > really great since it require root but at least the supervision
> > timeout is something a lot more reliable for this.
>
> we can add an option to L2CAP sockets to adjust the link supervision timeout.
>
> Anyway, these days, I would _not_ use Bluetooth BR/EDR for controlling anything. I would find a Gamepad that utilizes Bluetooth LE and focus on that.
>
> Regards
>
> Marcel
>
--
Guy Morand
Software Engineer
–
Scewo AG, Technoparkstrasse 2, 8406 Winterthur
Office +41 (0)44 500 86 03
www.scewo.ch
www.facebook.com/scewo
www.instagram.com/scewo_official
^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: Bluetooth disconnect event / Link layer monitoring
2019-11-19 9:09 ` Guy Morand
@ 2019-11-21 17:37 ` Guy Morand
2019-12-02 14:17 ` Guy Morand
0 siblings, 1 reply; 6+ messages in thread
From: Guy Morand @ 2019-11-21 17:37 UTC (permalink / raw)
To: Marcel Holtmann; +Cc: Luiz Augusto von Dentz, linux-bluetooth
I found out that the hcitool lst command was working perfectly fine on
my desktop and is doing what I expect!
Unfortunately, on my device it only works after pairing, then I always
get the "Command Disallowed" error. This is weird as I'm using the same
USB dongle and bluez version (5.50). The only thing that changes is the
kernel version that is why I think there is something weird here:
* 4.9 (Yocto) -> Doesn't work
* 4.14 (Yocto) -> Doesn't work
* 4.19 (Debian) -> works!
* 5.0.0 (Ubuntu) -> works!
I know it's boring but updating the kernel is not straightforward, we
use the kernel provided but our silicium vendor (embedded).
I was just wondering if one of you remember a similar bug (and fix?) or
this was just automagically solved without someone noticing it? Or maybe
I'm just missing something else important...
All the best!
Guy
^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: Bluetooth disconnect event / Link layer monitoring
2019-11-21 17:37 ` Guy Morand
@ 2019-12-02 14:17 ` Guy Morand
0 siblings, 0 replies; 6+ messages in thread
From: Guy Morand @ 2019-12-02 14:17 UTC (permalink / raw)
Cc: linux-bluetooth
Bluetooth developers,
To give some feedbacks on my problem and hopefully that could help
someone else who is also struggling...
I compared the connection with my desktop and my device using btmon and
noticed that during the connection, my desktop was configured as master
that is set to slave on my device:
# On host
< HCI Command: Accept Connection Request (0x01|0x0009) plen 7
Address: EC:83:50:DE:02:3C (Microsoft Corporation)
Role: Master (0x00)
# On target
< HCI Command: Accept Connection Request (0x01|0x0009) plen 7
Address: EC:83:50:DE:02:3C (OUI EC-83-50)
Role: Slave (0x01)
So I applied this quick and dirty patch and now I can change the link
supervision timeout without error:
diff --git a/net/bluetooth/hci_event.c b/net/bluetooth/hci_event.c
index e17aacbc5630..c83f66066ce0 100644
--- a/net/bluetooth/hci_event.c
+++ b/net/bluetooth/hci_event.c
@@ -2286,10 +2286,7 @@ static void hci_conn_request_evt(struct hci_dev
*hdev, struct sk_buff *skb)
bacpy(&cp.bdaddr, &ev->bdaddr);
- if (lmp_rswitch_capable(hdev) && (mask & HCI_LM_MASTER))
- cp.role = 0x00; /* Become master */
- else
- cp.role = 0x01; /* Remain slave */
+ cp.role = 0x00; /* Become master */
hci_send_cmd(hdev, HCI_OP_ACCEPT_CONN_REQ, sizeof(cp), &cp);
} else if (!(flags & HCI_PROTO_DEFER)) {
It's weird that in the latest kernel, this part of the file didn't
change and there is for sure a better fix! bluetooth poeple?
Anyway, if this helps or gives some clue to someone else, I'm always
glad for a free beer, even virtually :D!
Happy hacking!
Guy
On Thu, Nov 21, 2019 at 6:37 PM Guy Morand <g.morand@scewo.ch> wrote:
>
> I found out that the hcitool lst command was working perfectly fine on
> my desktop and is doing what I expect!
>
> Unfortunately, on my device it only works after pairing, then I always
> get the "Command Disallowed" error. This is weird as I'm using the same
> USB dongle and bluez version (5.50). The only thing that changes is the
> kernel version that is why I think there is something weird here:
> * 4.9 (Yocto) -> Doesn't work
> * 4.14 (Yocto) -> Doesn't work
> * 4.19 (Debian) -> works!
> * 5.0.0 (Ubuntu) -> works!
>
> I know it's boring but updating the kernel is not straightforward, we
> use the kernel provided but our silicium vendor (embedded).
>
> I was just wondering if one of you remember a similar bug (and fix?) or
> this was just automagically solved without someone noticing it? Or maybe
> I'm just missing something else important...
>
> All the best!
>
> Guy
--
Guy Morand
Software Engineer
–
Scewo AG, Technoparkstrasse 2, 8406 Winterthur
Office +41 (0)44 500 86 03
www.scewo.ch
www.facebook.com/scewo
www.instagram.com/scewo_official
^ permalink raw reply related [flat|nested] 6+ messages in thread
end of thread, other threads:[~2019-12-02 14:17 UTC | newest]
Thread overview: 6+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2019-11-18 17:16 Bluetooth disconnect event / Link layer monitoring Guy Morand
2019-11-18 18:27 ` Luiz Augusto von Dentz
2019-11-19 5:06 ` Marcel Holtmann
2019-11-19 9:09 ` Guy Morand
2019-11-21 17:37 ` Guy Morand
2019-12-02 14:17 ` Guy Morand
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.