All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH] Bluetooth: HCI H5 peer reset detection
@ 2014-10-08 14:54 Loic Poulain
  2014-10-31  8:39 ` Johan Hedberg
  0 siblings, 1 reply; 5+ messages in thread
From: Loic Poulain @ 2014-10-08 14:54 UTC (permalink / raw)
  To: marcel, gustavo, johan.hedberg; +Cc: linux-bluetooth, Loic Poulain

H5 Specification says:
If a SYNC message is received while in the Active State, it is
assumed that the peer device has reset. The local device should
therefore perform a full reset of the upper stack, and start Link
Establishment again at the Uninitialized State. Upon entering the
Active State, the first packet sent shall have its SEQ and ACK
numbers set to zero.

This patch resets the HCI H5 driver data/state to unitialized and
reports an HCI hardware error event to notify the upper stack that
HCI synchronization has been lost. H5 will be re-synchronized and
upper stack should generate an HCI Reset command.

Signed-off-by: Loic Poulain <loic.poulain@intel.com>
---
 drivers/bluetooth/hci_h5.c | 34 ++++++++++++++++++++++++++++++++++
 1 file changed, 34 insertions(+)

diff --git a/drivers/bluetooth/hci_h5.c b/drivers/bluetooth/hci_h5.c
index caacb42..5c5e9ac 100644
--- a/drivers/bluetooth/hci_h5.c
+++ b/drivers/bluetooth/hci_h5.c
@@ -168,6 +168,36 @@ wakeup:
 	hci_uart_tx_wakeup(hu);
 }
 
+static void h5_peer_reset(struct hci_uart *hu)
+{
+	struct h5 *h5 = hu->priv;
+	struct sk_buff *skb;
+	const unsigned char hard_err[] = { 0x10, 0x01, 0x00 };
+
+	BT_ERR("Peer device has reset");
+
+	h5->state = H5_UNINITIALIZED;
+
+	del_timer(&h5->timer);
+
+	skb_queue_purge(&h5->rel);
+	skb_queue_purge(&h5->unrel);
+	skb_queue_purge(&h5->unack);
+
+	h5->tx_seq = 0;
+	h5->tx_ack = 0;
+
+	skb = bt_skb_alloc(3, GFP_ATOMIC);
+	if (!skb)
+		return;
+
+	bt_cb(skb)->pkt_type = HCI_EVENT_PKT;
+	memcpy(skb_put(skb, 3), hard_err, 3);
+
+	/* Send Hardware Error to upper stack */
+	hci_recv_frame(hu->hdev, skb);
+}
+
 static int h5_open(struct hci_uart *hu)
 {
 	struct h5 *h5;
@@ -283,8 +313,12 @@ static void h5_handle_internal_rx(struct hci_uart *hu)
 	conf_req[2] = h5_cfg_field(h5);
 
 	if (memcmp(data, sync_req, 2) == 0) {
+		if (h5->state == H5_ACTIVE)
+			h5_peer_reset(hu);
 		h5_link_control(hu, sync_rsp, 2);
 	} else if (memcmp(data, sync_rsp, 2) == 0) {
+		if (h5->state == H5_ACTIVE)
+			h5_peer_reset(hu);
 		h5->state = H5_INITIALIZED;
 		h5_link_control(hu, conf_req, 3);
 	} else if (memcmp(data, conf_req, 2) == 0) {
-- 
1.8.3.2


^ permalink raw reply related	[flat|nested] 5+ messages in thread

end of thread, other threads:[~2014-10-31 17:58 UTC | newest]

Thread overview: 5+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2014-10-08 14:54 [PATCH] Bluetooth: HCI H5 peer reset detection Loic Poulain
2014-10-31  8:39 ` Johan Hedberg
2014-10-31 15:08   ` Loic Poulain
2014-10-31 16:50     ` Marcel Holtmann
2014-10-31 17:58       ` Johan Hedberg

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.